一直搞不明白為什么TCP連接一定需要三次握手和四次揮手。現在終於想明白了。三次握手是為了建立可靠的連接。注意可靠這兩個字。四次揮手是為了可靠的關閉連接,同樣注意可靠這兩個字。
下面分享一下我的想法和總結:
具體的三次握手和四次揮手的過程可以查閱下面的鏈接。
下面來說說“為什么”。
第一:為什么是三次握手,不是一次、兩次、四次?
為什么不是一次?
如果一次就建立連接:那么客戶端怎么知道服務端接收到了呢?
ok,我們假設一次握手就建立連接的情況,
客戶端向服務端發送建立連接的報文,然后不管服務端有沒有收到報文信息,直接發送數據報文?這種情況可靠嗎?答案肯定是不可靠的,類似與UDP。建
立連接的報文和數據報文到達服務端的時間無法確定,連接報文是否丟失也不一定。
服務端忽然收到一個數據報文會很懵逼。
為什么不是兩次?
由於網路阻塞,客戶端第一次發送的連接沒有及時到達,然后重新發送報文,然后建立通信,然后通信結束,然后第一次發送的報文到達了。然后服務端無端端的又激活了,但是客戶端已經不需要在和服務端通信了。這種情況是不是浪費服務端資源?
所以兩次也不可靠,為什么不是兩次的原因下面的參考連接也有說。
為什么不是四次?
如果是四次握手:仔細看看第四次要做的是不是和第二次很像?其實非要說四次行不行?我覺得是行的,但是四次就冗余了,所以其實4次、5次、6次都是可以的,為了兼顧性能和可靠性三次就夠了。第四次以后的握手已經可以用來傳輸數據了
為什么是三次?
因為三次握手剛好完成了兩次一問一答的通信。說明可以建立全雙工的通信了。
下面來說說,為什么是四次揮手?
因為四次最可靠,最順利。
客服端告訴服務端,我的數據發完了。你看看你還有沒有數據要發給我,沒有的話,我們的通信就可以斷了。
服務端也告訴客戶端,我的數據也發完了,我們一起關閉吧。 你看都順暢,一點都沒有冗余,也不用等待,大家都順順利利,愉快的快速結束。
我們來看看一次揮手行不行?
答案是行,其實0次都行。客戶端和服務端都有重試和超時機制,如果觸發了這兩個機制,就會主動關閉。
應用層,也可以主動關閉tcp並且不發出通信信息。想想兩台電腦同時斷電了?是不是一次揮手也沒有?但是連接已經斷了。
所以實際情況0次揮手,1次揮手,2次揮手,3次揮手都是可能發生。超過四次的揮手就冗余了,不需要那么多次。
所以兼顧性能和可靠性,四次揮手是最合適的。1次、2次、3次都是不可靠的。
為什么A要先進入TIME-WAIT狀態,等待2MSL時間后才進入CLOSED狀態?
解釋是說為了保證B能收到A的確認應答。這一點我一直有點疑惑,等待2MSL的時間就一直能保證B收到應答了嗎?我認為是不能的。
我們想象這個情況,A向B回復了應答,但是因為網絡阻塞沒有在規定時間內到達,然后B在向A發送FIN報文,巧了,因為網絡阻塞,到達A的時間,超過了2MSL。這時候客戶端已經關閉了。之前A回復的應答也因為網絡丟包,消失了。
最后的結果就是客服端關閉了,服務端一直在等待直到超時,然后關閉。
所以我認為客戶端等待2MSL時間,是為了盡最大努力確保服務端可以及時關閉。不是為了確保服務端一定可以及時關閉。這是一種取舍。在性能,效率,可靠性之間的取舍。
等待2MSL的時間可以在一定程序上減少服務端因為網絡阻塞不能及時關閉的情況。
參考鏈接:
https://www.zhihu.com/question/24853633/answer/254224088
https://www.cnblogs.com/zxpo/p/5234220.html