gpt4 book ai didi

c++ - 获取/释放语义重新排序

转载 作者:塔克拉玛干 更新时间:2023-11-03 07:45:46 26 4
gpt4 key购买 nike

基于C++11的acquire/release语义,我有以下问题:

Acquire 语义定义:编译器/CPU 不应将发生在 Acquire 之后的读取重新排序为发生在 Acquire 之前。1. 但是它可以将 acquire 语句之后发生的写入重新排序到 Acquire 之前吗??

Release 语义定义:编译器/CPU 不应将发生在 Release 之前的写入重新排序为发生在 Release 之后。2. 但是它能否将Release 语句之前发生的读取重新排序到Release 之后??

例子:

atomic<int> i = 0, j = 0, x = 0;

i = 0;

j = x;

i = 20;
  1. 编译器/CPU 会将上面的内容重新排序(优化)为以下内容:

    原子 i = 0, j = 0, x = 0;

    我 = 20;

    j = x;

  2. 但是如果我们使用获取加载,编译器/CPU 是否会避免重新排序写入 i (i=20) ??

    原子 i = 0, j = 0, x = 0;

    我 = 0;

    原子 j = x.load(memory_order_acquire);

    i = 20;

最佳答案

我认为你切换了获取/释放语义..
来自 cpp reference :

memory_order_acquire: [...] no reads in the current thread can be reordered before this load.

memory_order_release: [...] no writes in the current thread can be reordered after this store.

关于您的问题:

But can it reorder the writes that happen after the acquire statement to before the Acquire??
But can it reorder the reads that happen before the Release statement to after the Release??

一般来说,是的,只要代码效果保持原样,没有重新排序,编译器和CPU可能会重新排序指令,使程序运行得更快。这就是为什么如果需要严格排序,我们会明确使用原子 + 内存顺序和锁。

阻止 CPU/编译器重新排序的一般问题是依赖性,例如,请看下面的示例:

int a = atomicA.load(std::memory_order_relaxed);
a += 10;
atomicB.store(a,std::memory_order_relaxed);

尽管代码中没有明确说明排序(宽松的原子 = 按您的意愿重新排序),atomicB 通过 a 携带 atomicA 的依赖项>,并且在依赖项的情况下——即使代码中没有明确说明顺序——执行必须以保留该依赖项的方式进行,在这种情况下,不要在加载之前重新排序存储。

关于c++ - 获取/释放语义重新排序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39060704/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com