2012-01-12 93 views
0

我有一個衆所周知的TCP端口上的服務器連接到一羣客戶端。客戶端使用非阻塞選項連接到服務器。TCP CLOSE_WAIT狀態..&新連接

當我殺死服務器進程時,客戶端套接字進入CLOSE_WAIT狀態。現在,如果我重新啓動服務器進程並嘗試再次連接客戶端,connect()調用似乎會阻止,即使它應該是非阻塞的。

實際的修復可能實際上是關閉套接字時服務器死亡。但我試圖瞭解當前的行爲..

  • 當一個現有的連接在CLOSE_WAIT什麼是阻止建立新的連接?
  • 爲什麼連接阻塞即使是非阻塞選項設置?

這被認爲是在Linux內核2.6.3x ..

+0

2.6.3x內核沒有多大意義。 2.6.30和2.6.38之間有相當大的差異。將內核升級到3.0.0或3.1.0可能會有所幫助。 – 2012-01-12 01:42:50

+0

你在使用'SO_REUSEADDR'嗎?請參閱http://stackoverflow.com/questions/775638/using-so-reuseaddr-what-happens-to-previously-open-socket – 2012-01-12 01:46:12

+0

@BasileStarynkevitch 2.6.3x是足夠的信息爲這個問題。這似乎是一個基本的TCP/IP行爲,不可能經常改變。實際版本是2.6.32。不,我不打算嘗試3.0.0的假設,行爲可能會在3.0.0 – Manohar 2012-01-12 01:47:47

回答

1

這聽起來像客戶端中的錯誤。如果您將套接字設置爲非阻塞狀態,然後調用connect,則不應阻止connect調用。您可以粘貼創建套接字的客戶端代碼,將其設置爲非阻塞,並調用connect?此外,你是積極的,它被阻止在connect調用本身?

+0

它有可能是我在客戶端有一個錯誤..客戶端有一個inotify fd它監視使用libevent追蹤服務器的死亡。看起來像讀取inotify fd被阻止。我的壞...並且謝謝。 – Manohar 2012-01-12 09:38:47

0

我相信你的問題是相當準確回答here和相關SO_REUSEADDR。關於Using SO_REUSEADDR - What happens to previously open socket?的其他answer也是相關的。

+0

我擔心你錯了,SO_REUSEADDR允許你的服務器綁定到處於TIME_WAIT狀態的地址。正如我所說我的問題是在客戶端。 – Manohar 2012-01-12 02:10:02

+0

我對SO_REUSEADDR的不完全理解是,它改變了連接本身,而不僅僅是服務器端。 – 2012-01-12 02:13:05

+0

'SO_REUSEADDR'隻影響服務器是否被允許綁定。 – 2012-01-12 02:33:29