線程終止

2009年4月15日

 

前段時間多線程編程,在調試的時候遇到麻煩。多線程的debug太困難,打log是不好用的,因爲log本身也不一定是線程安全的。後來藉助eclipse的可視化debug工具以及helgrind,問題算得到了比較好的解決。

 

這禮拜遇到的bug是,程序在運行一段時間之後異常,而且是不穩定的異常。一開始真的不知道是哪兒有問題。用了各種方法最後確定是分配新線程失敗。而我恰好沒有在開闢新線程的代碼中使用斷言。解這個bug得到最大的收穫就是,不管代碼看上去多麼的正確,只要涉及到系統調用,該斷言的就得斷言,不含糊。

 

本以爲就幾行破代碼,照書寫,怎麼可能出錯。但結果還是出乎預料。仔細查看文檔,才知道真實的代碼並不像書上的例子寫的那麼簡單。分配線程失敗的原因,是因爲我想當然地認爲線程正常return之後便被釋放。但實際情況是,一個默認屬性的線程,即使終止之後,也會一直保持到對該線程調用pthread_join()或pthread_detach()函數。因爲默認屬性的線程認爲結束後的返回值是有價值的,因此等待着pthread_join()來取得其返回值。結果我忽略了這一點,造成結束後的線程大量堆積,直至系統默認的每進程最大分配線程數,然後導致線程分配失敗。

 

解決辦法,一是顯式調用pthread_join()或pthread_detach()函數;二是設置線程屬性:

 

 

PTHREAD_CREATE_DETACHED 意味着這個線程被創建時就是“分離”狀態,一旦自然終止即被自動釋放,不可通過pthread_join()函數得到返回值,通常被用於創建不關心返回值的線程。這是好東西。

 

說到好東西,想起另外一個,就是pthread的mutex。因爲用了半天mutex發現mutex可以設置檢查死鎖的屬性。- -!

 

 

不過這個errorcheck屬性也只能檢查自己的死鎖,即自己被連續加鎖兩次的情況。多mutex複雜死鎖還是得真人糾錯~~。

 

還有,valgrind也是個好東西,--tool=helgrind 參數可以在程序運行時檢查所有多線程競合資源。參考helgrind檢查結果修改多線程邏輯,可以使多線程更加安全穩定,也可以讓鎖加得更少更有針對性。經過一天的努力,俺的一個模塊終於沒有helgrind error了。加鎖是個技術活。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章