Subj : Re: Challenge: Multithreading & Synchronization To : comp.programming.threads From : Peter Dimov Date : Sat May 21 2005 03:27 pm doug wrote: > "David Holmes" wrote in > message news:428d693c_2@news.melbourne.pipenetworks.com... >> mon_enter() { >> if (mon.owner == currentThread()) >> count++; >> else >> mon_enter_slow(); // blocks until monitor is free >> >> mon_exit() { >> if (mon.owner == currentThread()) { >> if (--count == 0) >> mon_release_slow(); >> } >> else throw an error > I don't think this is safe - I think it's a disguised case of the > double-checked locking pattern. > Without a memory barrier before readig mon.owner, you risk reading an > old value. As long as mon_release_slow unsets mon.owner (before unlocking) and mon_enter_slow sets the owner (after locking), it seems to work. A thread that is holding the lock will always see its id in the owner field because of the release barrier in mon_release_slow and the acquire barrier in mon_enter_slow. This makes the unset in the other thread precede its store to mon.owner. A thread that does not hold the lock will never see its id in mon.owner because of the preceding unset in mon_release_slow. It doesn't matter whether the current value of owner becomes visible or not; it will always be different from currentThread() if the thread doesn't hold the lock. .