|
Threads-Devel : |
From: Kai Brüning (kai_at_[hidden])
Date: 2007-08-13 13:21:19
>Hi,
>
>I am trying to avoid thread locking problems when waiting using a boost::condition
>
>pseudo code:
>
>Main thread
>
> -- Start a worker thread --
> boost::mutex::scoped_lock lock(m_Mutex);
> m_Condition.notify_one();
>
>Worker thread
>
> boost::mutex::scoped_lock lock(m_Mutex);
> while (IsAlive()) {
>
> // do some work
>
> m_Condition.wait(lock);
> }
>
>As we can't predict which thread gets the mutex lock first lets assume that its the main thread. If this happens then m_Condition.wait will wait indefinitely as notify was called before wait. The only reliable way (that I can see) to prevent this is to never use wait, use a timed_wait instead and a loop. Why isn't the notification signal queued in the boost::condition object? Then the order of wait / notification would not be important.
You're missing a piece of the condition-picture: the predicate. That is, you need some shared variable (or suitable accessor methods) which knows whether the worker thread needs to wait at all. This predicate must be checked while holding the lock, which eliminates the race condition.
You either need to write a loop around m_Condition.wait(lock) yourself, checking the predicate each time through, or use the variants of wait() with the predicate argument (http://www.boost.org/doc/html/boost/condition.html).
It's a little hidden...
Regards
Kai