使用memory_order_relaxed进行存储,并使用memory_order_acquire进行加载 [英] Using memory_order_relaxed for storing with memory_order_acquire for loading

查看:108
本文介绍了使用memory_order_relaxed进行存储,并使用memory_order_acquire进行加载的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我对以下代码有疑问

#include <atomic>
#include <thread>
#include <assert.h>

std::atomic<bool> x, y;
std::atomic<int> z;

void write_x_then_y()
{
    x.store(true, std::memory_order_relaxed);
    y.store(true, std::memory_order_relaxed);
}

void read_y_then_x()
{
    while (!y.load(std::memory_order_acquire));
    if (x.load(std::memory_order_acquire))
        ++z;
}

int main()
{
    x = false;
    y = false;
    z = 0;
    std::thread a(write_x_then_y);
    std::thread b(read_y_then_x);
    a.join();
    b.join();
    assert(z.load() != 0);
}

我可以确定assert(z.load()!= 0)始终为假吗? 我认为x.store和y.store不在数据提供者线程中重新排序(是吗?). 因此,我认为如果加载由x和y存储的值的线程使用memory_order_acquire,那么它是从执行存储操作符的内核缓存中获取x和y的实际值的.

Can i be sure about assert(z.load() != 0) is always be false? I think x.store and y.store is not reordered in data provider thread (that is true?). For this reason i think if thread which loading values stored by x and y uses memory_order_acquire, it was get actual values for x and y from cache of core which performs storing operators.

推荐答案

我认为断言可能会失败. std::memory_order_relaxed允许编译器对write_x_then_y中的存储重新排序. (例如,如果出于某种原因它认为会更快.)因此,它可能在x之前写y.整个read_y_then_x可能在这两次写操作之间发生,因此它将观察到ytruexfalse并且不会递增z.

I think the assert may fail. The std::memory_order_relaxed allows the compiler to reorder the stores inside write_x_then_y. (For example if it thinks it would be faster for any reason.) So it may write y before x. The whole read_y_then_x may happen between those two writes and so it will observe y being true, x being false and it won't increment z.

这篇关于使用memory_order_relaxed进行存储,并使用memory_order_acquire进行加载的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆