tcp爲何要三次握手四次揮手

創建TCP須要三次握手才能創建,而斷開鏈接則須要四次握手。整個過程以下圖所示:服務器

0_131271823564Rx.gif

先來看看如何創建鏈接的。網絡

0_1312718352k8l6.gif

首先Client端發送鏈接請求報文,Server段接受鏈接後回覆ACK報文,併爲此次鏈接分配資源。Client端接收到ACK報文後也向Server段發生ACK報文,並分配資源,這樣TCP鏈接就創建了。ide

那如何斷開鏈接呢?簡單的過程以下:spa

0_1312718564tZXD.gif

【注意】中斷鏈接端能夠是Client端,也能夠是Server端。orm

假設Client端發起中斷鏈接請求,也就是發送FIN報文。Server端接到FIN報文後,意思是說"我Client端沒有數據要發給你了",可是若是你還有數據沒有發送完成,則沒必要急着關閉Socket,能夠繼續發送數據。因此你先發送ACK,"告訴Client端,你的請求我收到了,可是我還沒準備好,請繼續你等個人消息"。這個時候Client端就進入FIN_WAIT狀態,繼續等待Server端的FIN報文。當Server端肯定數據已發送完成,則向Client端發送FIN報文,"告訴Client端,好了,我這邊數據發完了,準備好關閉鏈接了"。Client端收到FIN報文後,"就知道能夠關閉鏈接了,可是他仍是不相信網絡,怕Server端不知道要關閉,因此發送ACK後進入TIME_WAIT狀態,若是Server端沒有收到ACK則能夠重傳。「,Server端收到ACK後,"就知道能夠斷開鏈接了"。Client端等待了2MSL後依然沒有收到回覆,則證實Server端已正常關閉,那好,我Client端也能夠關閉鏈接了。Ok,TCP鏈接就這樣關閉了!資源

整個過程Client端所經歷的狀態以下:同步

0_1312719804oSkK.gif

而Server端所經歷的過程以下it

0_1312719833030b.gif

【注意】 在TIME_WAIT狀態中,若是TCP client端最後一次發送的ACK丟失了,它將從新發送。TIME_WAIT狀態中所須要的時間是依賴於實現方法的。典型的值爲30秒、1分鐘和2分鐘。等待以後鏈接正式關閉,而且全部的資源(包括端口號)都被釋放。io

【問題1】爲何鏈接的時候是三次握手,關閉的時候倒是四次握手?
答:由於當Server端收到Client端的SYN鏈接請求報文後,能夠直接發送SYN+ACK報文。其中ACK報文是用來應答的,SYN報文是用來同步的。可是關閉鏈接時,當Server端收到FIN報文時,極可能並不會當即關閉SOCKET,因此只能先回復一個ACK報文,告訴Client端,"你發的FIN報文我收到了"。只有等到我Server端全部的報文都發送完了,我才能發送FIN報文,所以不能一塊兒發送。故須要四步握手。class

【問題2】爲何TIME_WAIT狀態須要通過2MSL(最大報文段生存時間)才能返回到CLOSE狀態?

答:雖然按道理,四個報文都發送完畢,咱們能夠直接進入CLOSE狀態了,可是咱們必須假象網絡是不可靠的,有能夠最後一個ACK丟失。因此TIME_WAIT狀態就是用來重發可能丟失的ACK報文。


TCP 的三次握手過程?爲何會採用三次握手,若採用二次握手能夠嗎?

  創建鏈接的過程是利用客戶服務器模式,假設主機 A 爲客戶端,主機 B 爲服務器端。

  1 ) TCP 的三次握手過程:主機 A 向 B 發送鏈接請求;主機 B 對收到的主機 A 的報文段進行確認;主機 A 再次對主機 B 的確認進行確認。

  2 )採用三次握手是:爲了防止失效的鏈接請求報文段忽然又傳送到主機 B ,於是產生錯誤。

  失效的鏈接請求報文段是指:主機 A 發出的鏈接請求沒有收到主機 B 的確認,因而通過一段時間後,主機 A 又從新向主機 B 發送鏈接請求,且創建成功,順序完成數據傳輸。考慮這樣一種特殊狀況,主機 A 第一次發送的鏈接請求並無丟失,而是由於網絡節點致使延遲達到主機 B ,主機 B 覺得是主機 A 又發起的新鏈接,因而主機 B 贊成鏈接,並向主機 A 發回確認,可是此時主機 A 根本不會理會,主機 B 就一直在等待主機 A 發送數據,致使主機 B 的資源浪費

相關文章
相關標籤/搜索