The following code is a race condition:

Because memory_order_relaxed is used the compiler and the CPU are free to reorder the two writes in thread t1. They are also free to reorder the two reads in thread t2. Hence undefined behavior.

The fix is to either use memory_order_seq_cst on the store and load calls, or memory_order_release on the store call and memory_order_acquire on the load call. Release prevents any prior loads and stores to be reordered past it; acquire guarantees that all stores from the thread that released the atomic variable are visible to the current thread; it also prevents reads and writes to be reordered before it. See here.

Leave a Reply