Predicates and wakeups
What this concept is
The predicate is a statement about protected state, not about whether a notification occurred. A consumer may proceed when an item exists or closure makes further waiting pointless. A producer waits while full and open. Check and modify these conditions under the same lock.
Why it matters here
A wakeup does not transfer ownership of an item or free slot. Between notification and lock reacquisition another thread can change the state. Correct code therefore rechecks the predicate in a loop, including when a wake returns without a relevant state change.
Concrete example
Consumer A waits on an empty queue. A producer adds x and notifies. Consumer B obtains the lock first and removes x. When A reacquires the lock, the queue is empty again. A while-loop waits again; an if-check proceeds to an invalid removal. No spontaneous wakeup is needed for this failure.
Common confusion / misconception
Calling notify does not release the lock, and a notification is not a remembered item token. Waiting while holding an unrelated lock can prevent the producer from making progress. A condition wait releases its associated lock while blocked and reacquires it before returning.
How to use it
Write state predicates before code: consumers wait while empty and open; producers wait while full and open. On return from the loop, inspect closed state as appropriate. Keep contents and closed flag under one Condition. This lab notifies all on each transition for simplicity, trading extra wakeups for a simpler correctness story.
Check yourself
If a producer wakes because close occurred while the queue remains full, should it append? No. If a consumer wakes because close occurred with one accepted item remaining, should it stop immediately? No: it must drain the item first.
Mini drill or application
Inject a synthetic return from wait with unchanged state. Predict the next line for both if and while versions. Then describe the competing-consumer schedule above without assuming a particular thread wins the lock.
Read this only if stuck
Review OSTEP concurrency introduction, then return to the condition-variable reading on the extension page with your exact predicate written down.