7

这段代码是线程安全的吗?我应该在函数 sig 中有 volatile 吗?(例如:)void Unlock() volatile {v=0;}如果不是我如何使这个线程安全?

class SimpleLock {
    std::atomic<int> v;
public:
    bool try_lock() { int z=0; return v.compare_exchange_strong(z, 1); }
    void lock() { while(try_lock()==false) std::this_thread::yield(); }
    void unlock() {v=0;}
};
4

1 回答 1

8

Yes, it is thread-safe, although you could rename Lock to TryLock since you are not calling CAS in a loop until it succeeds. Traditionally Lock operations are supposed to block until the acquire succeeds.

Regarding volatile, the docs of std::atomic specify (about the = operator):

Atomically assigns a value t to the atomic variable. Equivalent to store(desired).

Then about store:

void store( T desired, memory_order = std::memory_order_seq_cst );

Then about memory_order = std::memory_order_seq_cst:

  • No writes in the writer thread can be reordered after the atomic store
  • No reads in the reader thread can be reordered before the atomic load.
  • The synchronization is established between all atomic operations tagged std::memory_order_seq_cst. All threads using such atomic operation see the same order of memory accesses.

So no, you don't need volatile here. Additionally, volatile has weaker guarantees than the ones above (in fact, volatile is mostly useless in C++):

Within a thread of execution, accesses (reads and writes) to all volatile objects are guaranteed to not be reordered relative to each other, but this order is not guaranteed to be observed by another thread, since volatile access does not establish inter-thread synchronization.

于 2012-09-09T15:28:29.237 回答