c++mutexrace-conditioncritical-section

c++ mutex with different data in the critical section


class MyTest {

   void getter() {
      std::unique_lock lock(mutex_);
      if (!set_) {
         cout << "set already" << endl;
      }
      lock.unlock();

      // question is: can this thread see the latest update of x_?
      cout << x_ << endl;
   }

   void setter() {
      std::unique_lock lock(mutex_);
      set_ = true;
      x_ = 5;
   }

private:
   bool set_ = false;
   int x_ = 0;
   std::mutex mutex_;
};

There are two threads: thread A calls setter(), and thread B calls getter().

In thread A, set_ = true and x_ = 5 are inside the critical section, while in thread B, only set_ is in the critical section under the mutex.

After thread A changes both set_ and x_, unblock syncs data via memory barrier?

Thread B gets the lock and thus can get the latest set_ value. then, unlock. At this moment, can thread B see the latest update from x_ given that x_ is not inside the critical section of thread B?


Solution

  • At this moment, can thread B [guarantee to] see the latest update from x_ given that x_ is not inside the critical section of thread B?

    No. Suppose, for example, that the getter thread has the mutex and the setter thread is waiting for it. When the getter thread releases the lock, the setter thread can acquire it but might not get scheduled immediately. The getter thread then reads the 'old' value of x.

    In general, don't take chances like this when writing multi-threaded code. It's hard enough to get right as it is, and the last thing you want is subtle, once-every-two-weeks bugs.