轻松订购是一个信号 [英] relaxed ordering as a signal

查看:73
本文介绍了轻松订购是一个信号的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

假设我们有两个线程.一个发出走"的声音,另一个等待发出去的东西.

Let's say we have two thread. One that give a "go" and one that wait a go to produce something.

此代码是否正确,或者由于缓存或类似原因我是否可以进行无限循环"?

Is this code correct or can I have an "infinite loop" because of cache or something like that?

std::atomic_bool canGo{false};

void producer() {
    while(canGo.load(memory_order_relaxed) == false);
    produce_data();
}

void launcher() {
    canGo.store(true, memory_order_relaxed);
}

int main() {
    thread a{producer};
    thread b{launcher};
}

如果此代码不正确,是否可以用标准c ++刷新/使高速缓存无效?

If this code is not correct, is there a way to flush / invalidate the cache in standard c++?

推荐答案

类似go的信号通常是响应您希望目标看到的某些内存更改.

A go signal like this will usually be in response to some memory changes that you'll want the target to see.

换句话说,您通常希望赋予此类信号以 release / acquire 语义.

In other words, you'll usually want to give release/acquire semantics to such signaling.

这可以通过在商店中使用memory_order_release并在负载中使用memory_order_acquire来完成,也可以通过在宽松的商店中使用 release 栅栏 之前以及轻松加载后的 acquire 栅栏 ,以便信号员可以看到信号员在存储之前执行的存储操作(例如,参见 https://preshing.com/20120913/acquire-and-release-semantics/或C/C ++标准).

That can be done either by using memory_order_release on the store and memory_order_acquire on the load, or by putting a release fence before the relaxed store and and an acquire fence after the relaxed load so that memory operations done by the signaller before the store are visible to the signallee (see for example, https://preshing.com/20120913/acquire-and-release-semantics/ or the C/C++ standard).

据我所知,隔离栅的排序方式是,据我了解,内核之间的共享内存操作实际上是 ="nofollow noreferrer">遵循协议的硬件实现的缓冲IO ,释放防护应类似于输出缓冲刷新和获取防护,如输入缓冲刷新/同步.

The way I remember the ordering of the fences is that, as far as I understand, shared memory operations among cores are effectively hardware implemented buffered IO that follows a protocol, and a release fence should sort of be like an output buffer flush and an acquire fence like an input buffer flush/sync.

现在,如果在发出宽松存储之前刷新内核的内存操作输出缓冲区 ,那么当目标内核看到宽松存储时,前面的内存操作消息必须可用并且需要它所有要查看其内存中的那些内存变化,就是在看到信令存储后将其与获取栅栏同步.

Now if you flush your core's memory op output buffer before issuing a relaxed store, then when the target core sees the relaxed store, the preceding memory op messages must be available to it and all it needs to see those memory changes in its memory is to sync them in with an acquire fence after it sees the signalling store.

这篇关于轻松订购是一个信号的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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