0

I'm writing a service in C++, and I have some threads that needs to sleep for given amount of time.

So far so good, boost::this_thread::sleep_for works, but I now need some interruption (for example, stopping signal). Boost has no cancellation_token, and so far I have something like following:

boost::mutex _waiting_mutex;
boost::condition_variable _waiting_cv;

void wait(const boost::chrono::duration& timeout)
{
    boost::unique_lock<boost::mutex> lk(_waiting_mutex);
    _waiting_cv.wait_for(lk, timeout); 
}

void signal_termination()
{
    _waiting_cv.notify_all();
}

This works nicely for one thread (that sleeps for 5 seconds, or until signal_termination() is called), but not for multiple ones - the first thread sleeps nicely, but the second waits for first thread to leave the lock, and then sleeps.

How to overcome this unique_lock? Should I introduce semaphore with maximum number of threads?

In C#, I'd use ManualResetEvent.

nothrow
  • 15,882
  • 9
  • 57
  • 104

1 Answers1

1

I am not sure how you tested it for multiple threads, but you got wrong results. Condition variable wait() or wait_for() call unlocks mutex when it waits for the signal. Otherwhise why would you have to pass lock to that function?

Notice that the lock is passed to wait: wait will atomically add the thread to the set of threads waiting on the condition variable, and unlock the mutex. When the thread is woken, the mutex will be locked again before the call to wait returns. This allows other threads to acquire the mutex in order to update the shared data, and ensures that the data associated with the condition is correctly synchronized.

Slava
  • 43,454
  • 1
  • 47
  • 90
  • it wasn't .. exactly my fault. The issue I ran into was bug in boost - https://svn.boost.org/trac/boost/ticket/9079. – nothrow Nov 14 '13 at 12:19