今天有個linux伺服器一直報Too Many Open Files的異常,導致系統進行網路請求失敗,重啟應用程式容器之後恢複正常。
找到了當時的伺服器串連監控,發現close_wait狀態的串連一直在升高,上升到了10k後就引起應用報錯了。因為我們設定的linux的最大的串連數為10240。
在部落格園逛了一下,找到了下面的描述
如果我們的伺服器TCP串連處於CLOSE_WAIT狀態的話,那說明通訊端是被動關閉的!
更多精彩內容:http://www.bianceng.cnhttp://www.bianceng.cn/OS/Linux/
因為如果是CLIENT端主動斷掉當前串連的話,那麼雙方關閉這個TCP串連共需要四個packet:
Client ---> FIN ---> Server
Client <--- ACK <--- Server
這時候Client端處於FIN_WAIT_2狀態;而Server 程式處於CLOSE_WAIT狀態。
Client <--- FIN <--- Server
Server發送FIN給Client,Server 就置為LAST_ACK狀態。
Client ---> ACK ---> Server(這步沒做)
Client回應了ACK,那麼Server 的通訊端才會真正置為CLOSED狀態。
Server 程式處於CLOSE_WAIT狀態,而不是LAST_ACK狀態,說明還沒有發FIN給Client,那麼可能是在關閉串連之前還有許多資料要發送或者其他事要做,導致沒有發這個FIN packet。
通常來說,一個CLOSE_WAIT會維持至少2個小時的時間。
瞭解到這個情況之後,可以定位到應用之所以出現這麼多的close_wait的狀態,是因為一直在接收合作方發送過來的通知,是有個合作方在發送通知後沒有將ACK響應給我們,造成了close_wait狀態積壓,超過系統設定的最大值而無法再建立串連。
通過修改一下TCP/IP的參數,來縮短這個時間:修改tcp_keepalive_*系列參數有助於解決這個問題。
作者:cnblogs 周蝌蚪