You can fix this construct by adding the allowed_unlock_count parameter to each function that works with the mutex object; There are two types of guarantees that can be made with regard to allowed_unlock_count :
(enable-unlock-depth) allowed_unlock_count represents the depth of the allowed mutex unlock: the caller allows the bar unlock the mutexes allowed_unlock_count times. After this unlock, mutex status is not guaranteed.
(promise-unlock) allowed_unlock_count represents the mutex lock depth: the caller ensures that unlocking mutex exactly allowed_unlock_count times allows other threads to capture the mutex object.
These warranties are pre- and post-conditions of the functions.
Here bar depends on (promise-unlock) :
// pre: mutex locking depth is allowed_unlock_count void bar(int allowed_unlock_count) { // mutex locking depth is allowed_unlock_count boost::unique_lock<boost::recursive_mutex> lock(mutex); // mutex locking depth is allowed_unlock_count+1 // you might want to turn theses loops // into an a special lock object! for (int i=0; i<allowed_unlock_count; ++i) mutex.unlock(); // mutex locking depth is 1 condvar.wait(lock); // other threads can grab mutex // mutex locking depth is 1 for (int i=0; i<allowed_unlock_count; ++i) mutex.lock(); // mutex locking depth is allowed_unlock_count+1 } // post: mutex locking depth is allowed_unlock_count
The function being called must explicitly allow the caller to reduce the blocking depth.
source share