在没有任何锁的情况下加入另一个线程后是不是需要内存围栏?

Posted

技术标签:

【中文标题】在没有任何锁的情况下加入另一个线程后是不是需要内存围栏?【英文标题】:Is memory fence needed after joining another thread without any lock?在没有任何锁的情况下加入另一个线程后是否需要内存围栏? 【发布时间】:2019-12-20 01:29:39 【问题描述】:

如果我想立即读取从该线程存储的值,我想知道是否需要在线程连接后放置一个内存栅栏。线程连接是否已经暗示了内存围栏?

vector<int> v(1 << 21);

thread th([&]() 
    for (int i = 0; i < (1 << 20); i++) 
        v[i] = i * 123; // store some kind of calculation results into the vector
    
);

for (int i = (1 << 20); i < (1 << 21); i++) 
    v[i] = i * 123;


th.join();

// Is any memory fence needed to be here?

// use the values from another thread... 
printf("%d\n", v[1234]);
// ...

【问题讨论】:

【参考方案1】:

没有。不需要内存栅栏,因为thread::join 将阻塞,直到执行线程完成执行。此外,连接操作由主线程运行循环后执行。我看不出在加入操作之后如何需要栅栏。

【讨论】:

那么“执行线程已经执行完毕”是否意味着数据也同步回主线程了? 是的,我相信是的。编译器围绕thread::join 进行的任何重新排序都会破坏加入执行线程的约定。 知道了。谢谢。 "The completion of the thread identified by *this synchronizes with the corresponding successful return from join()."

以上是关于在没有任何锁的情况下加入另一个线程后是不是需要内存围栏?的主要内容,如果未能解决你的问题,请参考以下文章

Java:线程在没有获取锁的情况下持有锁

ReentrantLock源码分析

ReentrantLock源码分析

ReentrantLock源码分析

Java多线程并发编程/锁的理解

C++ 是不是有任何线程安全可以写入(比没有锁的线程安全类似物更快)组件?