2013-12-22 79 views
2

我在處理多線程服務器中的信號處理時遇到了問題。我爲每個連接創建一個線程,但我想要一個選項來終止SIGINT的服務器。然而,當其中一個線程捕捉到信號時,事情會變得很糟糕。有沒有辦法阻止線程獲取主線程以外的信號?多線程服務器,信號處理。 POSIX

+0

的http://計算器.com/a/18314115/412080 –

回答

5

線程從創建它的線程繼承它的信號掩碼。

假設創建線程是「主」線程,您可能希望在創建線程之前阻止所有有問題的信號,並且在完成代碼之後,解除創建線程中的信號。

修改線程的信號掩碼POSIX定義pthread_sigmask()


更新:

當信號處理需要在多線程環境定期基地進行,一個有趣的方法是將所有信號委託給一個單獨的線程裏什麼也不做,但等待信號使用sigwait()抵達。

要做到這一點:

  1. 設置信號屏蔽按你想在「主」線程別的之前使用pthread_sigmask()來處理信號。
  2. 然後創建線程來處理信號。
  3. 然後再次使用pthread_sigmask()來阻止來自「主」線程中的1.的所有信號。
  4. 最後創建所有其他線程。

的結果將是在1規定的所有信號會去下2創建線程。所有其他線程將不會收到任何下1規定的信號..

+0

這裏的問題是我每次獲得連接時都會創建一個新線程,因此絕不可以在創建_all_線程後解鎖信號 – darenn

+0

@darenn:請參閱我的更新答案。 – alk

+0

另一個問題是..我的服務器在運行{msgrcv()...}循環運行。當我捕捉到信號時,我將運行設置爲false,但主線程仍然卡在msgrcv上。有什麼辦法可以處理,除了銷燬ipc隊列並檢查EIDRM錯誤嗎? – darenn

0

pthread_sigmask()正是你需要的。只允許在應該捕獲此信號的線程中進行SIGINT處理。

+0

這種方法引入了線程創建和線程調用'pthread_sigmask()'之間的時間競爭。 – alk

+0

@alk是的,但這不是一個真正的問題,並且很容易以多種方式解決。 – Netch