在与原子加载和存储同步的线程之间共享变量是否安全?

Mar*_*les 5 c multithreading gcc pthreads atomic

在 GNU/Linux 中的 GCC 下编译的 C 程序中,使用非原子和非易失性变量在线程之间共享数据是否安全(从它不会引入意外行为的意义上说),前提是使用这些变量的线程变量通过原子加载和存储同步?。如果没有,我应该用什么代替?。

对于例如,是否GCC保证下面的代码将如预期(thread_2始终返回1)?假设这两个函数是从不同的线程调用的。如果它是使用 C11 原子原语编写的,如果我使用 POSIX 线程互斥锁来同步,或者如果我使用 POSIX 信号量,会不会有什么不同?我仅将以下代码作为特定情况包含在内。

int data = 0;
int flag = 0;

int thread_1 (void) {
    data = 1;
    __atomic_store_n (&flag, 1, __ATOMIC_RELEASE);
    return -1;
}

int thread_2 (void) {
    while (!__atomic_load_n (&flag, __ATOMIC_ACQUIRE));
    return data;
}
Run Code Online (Sandbox Code Playgroud)

提前致谢。

Snp*_*nps 3

根据GCC Wiki,这应该是安全的,因为获取/释放data内存模型保证线程 1 中的存储将发生在原子存储之前, flagasdata不是原子变量。

“原子操作之前的任何存储都必须在同步的其他线程中看到。”

线程 2 将始终等待(使用busy waiting),直到 的值flag不同于零,然后返回 1。