多线程:pthread_cond_wait 实现原理
函數原型
int pthread_cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex)
第一個參數為需要等待的條件,第二個參數為互斥鎖
一般該函數和 int pthread_cond_signal(pthread_cond_t *cond);函數一同使用,用來喚醒在cond條件上等待且處于就緒隊列的線程執行。
代碼舉例
#include<stdio.h>
#include<sys/types.h>
#include<stdlib.h>
#include<unistd.h>
#include<pthread.h>pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t cond = PTHREAD_COND_INITIALIZER;int count = 0;void *decrement(void *arg) {printf("in derement.\n");pthread_mutex_lock(&mutex);if (count == 0)pthread_cond_wait(&cond, &mutex);count--;printf("----decrement:%d.\n", count);printf("out decrement.\n");pthread_mutex_unlock(&mutex);return NULL;
}void *increment(void *arg) {printf("in increment.\n");pthread_mutex_lock(&mutex);count++;printf("----increment:%d.\n", count);if (count != 0)pthread_cond_signal(&cond);printf("out increment.\n");pthread_mutex_unlock(&mutex);return NULL;
}int main(int argc, char *argv[]) {pthread_t tid_in, tid_de;pthread_create(&tid_de, NULL, (void*)decrement, NULL);sleep(2);pthread_create(&tid_in, NULL, (void*)increment, NULL);sleep(5);pthread_join(tid_de, NULL);pthread_join(tid_in, NULL);pthread_mutex_destroy(&mutex);pthread_cond_destroy(&cond);return 0;
}
原理描述
我們能夠發現decrement使用pthread_cond_wait之前需要先對互斥變量加鎖,同時將互斥變量做為參數傳入到該函數之中,為什么要做這樣的鎖操作呢?
這里pthread_cond_wait() 的作用非常重要 – 它是 POSIX 線程信號發送系統的核心
關于該過程在《unix高級環境編程》中的描述如下:
The mutex passed to pthread_cond_wait protects the condition.The caller passes it locked to the function, which then atomically places them calling thread on the list of threads waiting for the condition and unlocks the mutex. This closes the window between the time that the condition is checked and the time that the thread goes to sleep waiting for the condition to change, so that the thread doesn’t miss a change in the condition. When pthread_cond_wait returns, the mutex is again locked
大體意思如下:
pthread_cond_wait函數傳入的參數mutex用于保護條件,因為我們在調用pthread_cond_wait時,如果條件不成立我們就進入阻塞,但是進入阻塞這個期間,如果條件變量改變了的話(假如多個喚醒信號所處線程并行執行),那我們就漏掉了這個條件。但此時這個線程還沒有放到等待隊列上,所以就無法執行phtread_cond_wait所處線程。
解決辦法即調用pthread_cond_wait前要先鎖互斥量,即調用pthread_mutex_lock(),pthread_cond_wait在把線程放進阻塞隊列后,自動對mutex進行解鎖,使得其它線程可以獲得加鎖的權利。這樣其它線程才能對臨界資源進行訪問并在適當的時候喚醒這個阻塞的進程,當pthread_cond_wait返回的時候又自動給mutex加鎖。
所以以上代碼中pthread_cond_wait和pthread_cond_signal配對使用過程如下
pthread_cond_wait前要先加鎖
pthread_cond_wait內部會解鎖,然后等待條件變量被其它線程激活
pthread_cond_wait被激活后會再自動加鎖
激活線程:
加鎖(和等待線程用同一個鎖)
pthread_cond_signal發送信號
解鎖
激活線程的上面三個操作在運行時間上都在等待線程的pthread_cond_wait函數內部
總結
以上是生活随笔為你收集整理的多线程:pthread_cond_wait 实现原理的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 普化天尊水陆画是谁画的啊?
- 下一篇: ceph存储 PG的状态机 源码分析