C++ Logo


Advanced search

Re: Synchronization of atomic notify and wait

From: Andrey Semashev <andrey.semashev_at_[hidden]>
Date: Mon, 18 Jul 2022 23:27:31 +0300
On 7/18/22 22:57, Marcin Jaczewski wrote:
> pon., 18 lip 2022 o 21:49 Andrey Semashev via Std-Discussion
> <std-discussion_at_[hidden]> napisaƂ(a):
>> On 7/18/22 22:04, Nate Eldredge via Std-Discussion wrote:
>>> On Mon, 18 Jul 2022, Marcin Jaczewski via Std-Discussion wrote:
>>>> To compare to `atomics.wait#4` we have:
>>>> ```
>>>> std::atomic<bool> b{false}; //EVENT X
>>>> void thr1() {
>>>> b.store(true, std::memory_order_relaxed); //EVENT Y
>>>> b.notify_one(); //NOTIFY
>>>> }
>>>> int main() {
>>>> std::thread t(thr1);
>>>> b.wait(false); //BLOCK
>>>> t.join();
>>>> return 0;
>>>> }
>>>> ```
>>>> "the atomic waiting operation has blocked after observing the result
>>>> of X," -> this X happens before `main` start, and means should be
>>>> visible for block operation.
>>>> "X precedes Y in the modification order of M, and" -> again X happens
>>>> before thread start
>>>> "Y happens before the call to the atomic notifying operation." -> is
>>>> line before notify
>>>> For mea this is clear that the function should unblock there.
>>>> Is This correct interpretation?
>>> I agree that, if the wait blocks at all, then it unblocks at least once.
>>> That is not the issue. But after it unblocks, it reloads the value of b
>>> to decide whether to return or to block again. The question is whether,
>>> after unblocking in response to the notify, it might load the value
>>> `false` and thus block again.
>> How is this possible, under the current ordering rules?
> Because http://eel.is/c++draft/atomics.wait#4 requires this?

I was asking the OP how was his theoretical scenario of reversed store
and notify possible. Because I don't see how, according to the ordering
rules mentioned so far in the discussion.

> I understand this work the same as `memcpy` in context of object life time.
> You can have a naive `memcpy` but you can't have the same behavior
> that standard gives to the original.
> This means you can't implement `wait` using current ordering rules but still
> `std::wait` works fine because standard demand it to work.

Obviously, wait can be implemented as there are real world
implementations. The standard isn't written to demand something that is
impossible to implement.

Received on 2022-07-18 20:27:44