signal(SIGPIPE, SIG_IGN)(轉)


signal(SIGPIPE, SIG_IGN)  linux

當服務器close一個鏈接時,若client端接着發數據。
根據TCP 協議的規定,會收到一個RST響應,client再往這個服務器發送數據時,系統會發出一個SIGPIPE信號給進程,告訴進程這個鏈接已經斷開了,不要再寫了。 
根據信號的默認處理規則SIGPIPE信號的默認執行動做是terminate(終止、退出),因此client會退出。
若不想客戶端退出能夠把SIGPIPE設爲SIG_IGN 
如:    signal(SIGPIPE,SIG_IGN); 
這時SIGPIPE交給了系統處理。 
服務器採用了fork的話,要收集垃圾進程,防止殭屍進程的產生,能夠這樣處理: 
signal(SIGCHLD,SIG_IGN); 交給系統init去回收。 
這裏子進程就不會產生殭屍進程了。 
 
============
寫了一個服務器程序,在Linux下測試,而後用C++寫了客戶端用千萬級別數量的短連接進行壓力測試.  可是服務器老是莫名退出,沒有core文件.
最後問題肯定爲, 對一個對端已經關閉的socket調用兩次write, 第二次將會生成SIGPIPE信號, 該信號默認結束進程.安全

具體的分析能夠結合TCP的"四次握手"關閉. TCP是全雙工的信道, 能夠看做兩條單工信道, TCP鏈接兩端的兩個端點各負責一條.服務器

當對端調用close時, 雖然本意是關閉整個兩條信道, 但本端只是收到FIN包.socket

按照TCP協議的語義, 表示對端只是關閉了其所負責的那一條單工信道, 仍然能夠繼續接收數據.函數

也就是說, 由於TCP協議的限制, 一個端點沒法獲知對端的socket是調用了close仍是shutdown.測試

對一個已經收到FIN包的socket調用read方法, 若是接收緩衝已空, 則返回0, 這就是常說的表示鏈接關閉..net

但第一次對其調用write方法時, 若是發送緩衝沒問題, 會返回正確寫入(發送).線程

但發送的報文會致使對端發送RST報文, 由於對端的socket已經調用了close, 徹底關閉, 既不發送, 也不接收數據.server

因此, 第二次調用write方法(假設在收到RST以後), 會生成SIGPIPE信號, 致使進程退出.blog

爲了不進程退出, 能夠捕獲SIGPIPE信號, 或者忽略它, 給它設置SIG_IGN信號處理函數:

signal(SIGPIPE, SIG_IGN);

這樣, 第二次調用write方法時, 會返回-1, 同時errno置爲SIGPIPE. 程序便能知道對端已經關閉.

 

在linux下寫socket的程序的時候,若是嘗試send到一個disconnected socket上,就會讓底層拋出一個SIGPIPE信號。

這個信號的缺省處理方法是退出進程,大多數時候這都不是咱們指望的。所以咱們須要重載這個信號的處理方法。

調用如下代碼,便可安全的屏蔽SIGPIPE:

signal(SIGPIPE, SIG_IGN);

個人程序產生這個信號的緣由是:  client端經過 pipe 發送信息到server端後,就關閉client端, 這時server端,返回信息給 client 端時就產生Broken pipe 信號了,服務器就會被系統結束了。

 

對於產生信號,咱們能夠在產生信號前利用方法 signal(int signum, sighandler_t handler) 設置信號的處理。

若是沒有調用此方法,系統就會調用默認處理方法:停止程序,顯示提示信息(就是咱們常常遇到的問題)。

咱們能夠調用系統的處理方法,也能夠自定義處理方法。 
系統裏邊定義了三種處理方法: 

(1)SIG_DFL信號專用的默認動做:   

(a)若是默認動做是暫停線程,則該線程的執行被暫時掛起。

當線程暫停期間,發送給線程的任何附加信號都不交付,直到該線程開始執行,可是SIGKILL除外。   

(b)把掛起信號的信號動做設置成SIG_DFL,且其默認動做是忽略信號 (SIGCHLD)。

(2)SIG_IGN忽略信號   

(a)該信號的交付對線程沒有影響  

(b)系統不容許把SIGKILL或SIGTOP信號的動做設置爲SIG_DFL 3)SIG_ERR   

項目中我調用了signal(SIGPIPE, SIG_IGN), 這樣產生  SIGPIPE 信號時就不會停止程序,直接把這個信號忽略掉。 ———————————————— 版權聲明:本文爲CSDN博主「工程師WWW」的原創文章,遵循CC 4.0 by-sa版權協議,轉載請附上原文出處連接及本聲明。原文連接:https://blog.csdn.net/weiwangchao_/article/details/38901857

相關文章
相關標籤/搜索