Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

understanding of pthread_cond_wait() and pthread_cond_signal()

Generally speaking, pthread_cond_wait() and pthread_cond_signal() are called as below:

//thread 1: pthread_mutex_lock(&mutex); pthread_cond_wait(&cond, &mutex); do_something() pthread_mutex_unlock(&mutex);  //thread 2: pthread_mutex_lock(&mutex); pthread_cond_signal(&cond);   pthread_mutex_unlock(&mutex); 

The steps are

  1. pthread_cond_wait(&cond, &mutex); is called, it unlocks the mutex

  2. Thread 2 locks the mutex and calls pthread_cond_signal(), which unlocks the mutex

  3. In thread 1, pthread_cond_wait() is called and locks the mutex again

Now in thread 2, after pthread_cond_signal() is called, pthread_mutex_unlock(&mutex) is going to run, it seems to me that it wants to unlock a the mutex which is now locked by thread 1. Is there anything wrong in my understanding?

Besides, it also seems to me that pthread_cond_wait() can be called by only 1 thread for the same cond-mutex pair. But there is a saying "The pthread_cond_signal() function shall unblock at least one of the threads that are blocked on the specified condition variable cond (if any threads are blocked on cond)." So, it means pthread_cond_wait() can be called by many threads for the same cond-mutex pair?

like image 867
user1944267 Avatar asked May 13 '13 13:05

user1944267


People also ask

What is pthread_cond_signal?

The pthread_cond_signal() function wakes up at least one thread that is currently waiting on the condition variable specified by cond. If no threads are currently blocked on the condition variable, this call has no effect.

What is pthread_cond_wait?

The pthread_cond_wait() function blocks the calling thread, waiting for the condition specified by cond to be signaled or broadcast to. When pthread_cond_wait() is called, the calling thread must have mutex locked. The pthread_cond_wait() function atomically unlocks mutex and performs the wait for the condition.

What does pthread_cond_wait return?

The pthread_cond_wait() routine always returns with the mutex locked and owned by the calling thread, even when returning an error. This function blocks until the condition is signaled. The function atomically releases the associated mutex lock before blocking, and atomically acquires the mutex again before returning.

What is Pthread_cond_t in C?

In C under Linux, there is a function pthread_cond_wait() to wait or sleep.


2 Answers

pthread_cond_signal does not unlock the mutex (it can't as it has no reference to the mutex, so how could it know what to unlock?) In fact, the signal need not have any connection to the mutex; the signalling thread does not need to hold the mutex, though for most algorithms based on condition variables it will.

pthread_cond_wait unlocks the mutex just before it sleeps (as you note), but then it reaquires the mutex (which may require waiting) when it is signalled, before it wakes up. So if the signalling thread holds the mutex (the usual case), the waiting thread will not proceed until the signalling thread also unlocks the mutex.

The common use of condition vars is something like:

thread 1:     pthread_mutex_lock(&mutex);     while (!condition)         pthread_cond_wait(&cond, &mutex);     /* do something that requires holding the mutex and condition is true */     pthread_mutex_unlock(&mutex);  thread2:     pthread_mutex_lock(&mutex);     /* do something that might make condition true */     pthread_cond_signal(&cond);     pthread_mutex_unlock(&mutex); 

The two threads have some shared data structure that the mutex is protecting access to. The first thread wants to wait until some condition is true then immediately do some operation (with no race condition opportunity for some other thread to come in between the condition check and action and make the condition false.) The second thread is doing something that might make the condition true, so it needs to wake up anyone that might be waiting for it.

like image 53
Chris Dodd Avatar answered Oct 05 '22 01:10

Chris Dodd


Here is a typical example: thread 1 is waiting for a condition, which may be fulfilled by thread 2.

We use one mutex and one condition.

pthread_mutex_t mutex; pthread_cond_t condition; 

thread 1 :

pthread_mutex_lock(&mutex); //mutex lock while(!condition){     pthread_cond_wait(&condition, &mutex); //wait for the condition }  /* do what you want */  pthread_mutex_unlock(&mutex); 

thread 2:

pthread_mutex_lock(&mutex);  /* do something that may fulfill the condition */  pthread_mutex_unlock(&mutex); pthread_cond_signal(&condition); //wake up thread 1 

Edit

As you can see in the pthread_cond_wait manual:

It atomically releases mutex and causes the calling thread to block on the condition variable cond; atomically here means "atomically with respect to access by another thread to the mutex and then the condition variable".

like image 44
Ludzu Avatar answered Oct 05 '22 01:10

Ludzu