TCP為何采用三次握手來建立連接,若采用兩次握手可以嗎,請說明理由?
不可以。采用三次握手是為了防止失效的連接請求報文段突然又傳送到服務器,從而發生錯誤。當客戶端發出的連接請求報文段由於某些原因沒有及時到達服務器,而客戶端在等待一段時間后,又重新向服務器發送連接請求,且建立成功,順序完成數據傳輸,那么第一次發送的連接請求報文段就稱為失效的連接請求報文段。
考慮這樣一種情況,客戶端第一次發送的連接請求並沒有丟失,而是因為網絡問題導致延遲到達服務器,服務器以為是客戶端又發起的新連接,於是服務器同意連接,並向客戶端發回確認,但是此時客戶端不予理會,服務器就一直等待客戶端發送數據,導致服務器資源浪費。
TCP為何會采用四次揮手來釋放連接?
關閉連接時,當收到對方的FIN報文通知時,它僅僅表示對方沒有數據發送給你了,但未必你所有的數據都發送給對方了,所以你未必會馬上關閉socket,也即你可能還需要發送一些數據給對方之后,再發送FIN報文給對方來表示你沒有數據發送給對方了,針對每個FIN報文,都需要ack報文。所以需要四次揮手。
為何需要TIME_WAIT狀態?
1. 實現終止TCP全雙工連接的可靠性
假設最終的ACK狀態消失,服務器將重新發送最終的FIN。因此客戶必須維護狀態信息以允許它重發最終的ACK,如果不維護狀態信息,它將最終響應以RST,而服務器則把該分節解釋成一個錯誤。如果TCP打算執行所有必要的工作以徹底終止某個連接方向的數據流,那么它必須能夠處理連接終止序列四個分節中任何一個分節丟失的情況,也即主動關閉的那一端進入TIME_WAIT狀態,因為它可能不得不重新發送最終的ACK。
2. 允許老的重復分節在網絡中消失
我們假設12.106.32.254端口1500和206.168.112.219端口21之間有一個TCP連接,我們關閉這個連接后,在以后某個時候又建立起相同的IP地址和端口之間的TCP連接。后一個連接稱為前一個連接的化身,因為它們的IP地址和端口號是相同的,TCP必須防止來自某個連接的老的重復分組在連接終止后再現,從而被誤解成屬於同一個連接的化身。要實現這種功能,TCP不能給處於TIME_WAIT狀態的連接啟動新的化身,既然TIME_WAIT狀態的持續時間是2MSL,這就足夠讓某個方向上的分組存活MSL秒即被丟棄,另一個方向上的應答最多存活MSL秒也被丟棄,通過實施這個規則,我們就能保證當成功建立一個TCP連接時,來自該連接的先前的化身的老重復分組都已在網絡中消失了。
參考資料:
1.http://coolshell.cn/articles/11564.html
2.《王道程序員求職寶典》