2009-04-22 47 views
27

在unix網絡編程中,我總是在服務器使用的套接字上設置SO_REUSEADDR選項來監聽連接。這基本上說,另一個套接字可以在機器的同一端口上打開。當從崩潰中恢復並且套接字沒有被正確關閉時,這非常有用 - 應用程序可以重新啓動,並且只需在同一端口上打開另一個套接字並繼續監聽。使用SO_REUSEADDR - 先前打開的套接字會發生什麼?

我的問題是,舊插座會發生什麼?毫無疑問,所有數據/連接仍舊會在舊套接字上接收。它是否被操作系統自動關閉?

+1

澄清:程序崩潰後,操作系統例如Linux Kernel,將自動關閉套接字。有協議原因(TCP)爲什麼你不想立即重新打開連接。 – unixman83 2012-01-29 08:39:53

+2

關於這個主題必須閱讀:http://www.serverframework.com/asynchronousevents/2011/01/time-wait-and-its-implications-implications-for-protocols-and-scalable-servers.html – 2012-04-03 08:57:15

回答

24

是的,當舊進程結束時,OS自動關閉前一個套接字。你無法正常在同一端口上監聽的原因是套接字雖然關閉,但在一段時間(通常幾分鐘)內仍處於2MSL狀態。當超時到期時,操作系統會自動將舊套接字從此狀態轉換出來。

29

當使用它的程序死亡時,套接字被視爲關閉。操作系統處理的內容很多,操作系統將拒絕接受任何進一步的通信。但是,如果套接字意外關閉,另一端的計算機可能不知道對話結束,並且可能仍在嘗試進行通信。

這就是爲什麼在TCP規範中設計了一個等待期,然後才能重用相同的端口號。因爲從理論上講,儘管不太可能,但是舊會話中的數據包可能會有適當的IP地址,端口號和序列號到達,這樣接收服務器就會錯誤地將它插入到錯誤的TCP流中。

SO_REUSEADDR選項將覆蓋該行爲,允許您立即重新使用該端口。實際上,你的意思是:「我瞭解風險,並且願意使用該端口。」

相關問題