歡迎來到Linux教程網
Linux教程網
Linux教程網
Linux教程網
Linux教程網 >> Linux基礎 >> Linux教程 >> Linux多線程之線程資源的釋放

Linux多線程之線程資源的釋放

日期:2017/2/28 16:25:04   编辑:Linux教程

一般來說,對一段運行代碼進行加鎖然後解鎖,如下所示:

pthread_mutex_lock(&mutex);

//運行代碼;

pthread_mutex_unlock(&mutex);

如果在運行代碼這塊發生錯誤,有異常,導致這個線程異常退出,那麼怎麼辦,pthread_unlock沒有得到調用,那麼這個鎖資源沒有解鎖。可以用下面的方法修改。

pthread_cleanup_push(pthread_mutex_unlock, (void *) &mutex);

pthread_mutex_lock(&mutex);

/* do some work */

pthread_mutex_unlock(&mutex);

pthread_cleanup_pop(0);

這樣假如運行代碼發生錯誤時沒有調用到解鎖,pthread_cleanup_up會自動來調用,參數為0表示不執行push進來的函數。

但是如果是異常錯誤的話,這個參數並不影響異常終止時清理函數的執行。

必須要注意的是,如果線程處於PTHREAD_CANCEL_ASYNCHRONOUS狀態,上述代碼段就有可能出錯,因為CANCEL事件有可能在pthread_cleanup_push()和pthread_mutex_lock()之間發生,或者在 pthread_mutex_unlock()和pthread_cleanup_pop()之間發生,從而導致清理函數unlock一個並沒有加鎖的 mutex變量,造成錯誤。因此,在使用清理函數的時候,都應該暫時設置成PTHREAD_CANCEL_DEFERRED模式。為此,POSIX的 Linux實現中還提供了一對不保證可移植的 pthread_cleanup_push_defer_np()/pthread_cleanup_pop_defer_np()擴展函數,功能與以下代碼段相當:

{ int oldtype;

pthread_setcanceltype(PTHREAD_CANCEL_DEFERRED, &oldtype);

pthread_cleanup_push(routine, arg);

...

pthread_cleanup_pop(execute);

pthread_setcanceltype(oldtype, NULL);

}

+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

設置退出類型pthread_setcanceltype

#include <pthread.h>

int pthread_setcanceltype(int type, int *oldtype);

返回值:函數成功返回0。任何其他返回值都表示錯誤。

將線程退出類型設置為延遲類型或異步類型。參數type的取值為PTHREAD_CANCEL_DEFERRED或PTHREAD_CANCEL_ASYNCHRONOUS。

當一個線程被創建後,缺省值是延遲類型。在異步方式下,線程可以在執行的任何時候被退出。

Copyright © Linux教程網 All Rights Reserved