答應我不要問TCP三次握手四次揮手

衍生頭疼問題如下。

  1. 請畫出三次握手和四次揮手的示意圖
  2. 為什么連接的時候是三次握手?
  3. 什么是半連接隊列?
  4. ISN(Initial Sequence Number)是固定的嗎?
  5. 三次握手過程中可以攜帶數據嗎?
  6. 如果第三次握手丟失了,客戶端服務端會如何處理?
  7. SYN攻擊是什么?
  8. 揮手為什么需要四次?
  9. 四次揮手釋放連接時,等待2MSL的意義?

1. 三次握手

三次握手(Three-way Handshake)其實就是指建立一個TCP連接時,需要客戶端和服務器總共發送3個包。進行三次握手的主要作用就是為了確認雙方的接收能力和發送能力是否正常、指定自己的初始化序列號為后面的可靠性傳送做準備。實質上其實就是連接服務器指定端口,建立TCP連接,并同步連接雙方的序列號和確認號,交換TCP窗口大小信息。

剛開始客戶端處于 Closed 的狀態,服務端處于 Listen 狀態。
進行三次握手:

  • 第一次握手:客戶端給服務端發一個 SYN 報文,并指明客戶端的初始化序列號 ISN。此時客戶端處于?SYN_SENT?狀態。

    首部的同步位SYN=1,初始序號seq=x,SYN=1的報文段不能攜帶數據,但要消耗掉一個序號。

  • 第二次握手:服務器收到客戶端的 SYN 報文之后,會以自己的 SYN 報文作為應答,并且也是指定了自己的初始化序列號 ISN(s)。同時會把客戶端的 ISN + 1 作為ACK 的值,表示自己已經收到了客戶端的 SYN,此時服務器處于?SYN_RCVD?的狀態。

    在確認報文段中SYN=1,ACK=1,確認號ack=x+1,初始序號seq=y。

  • 第三次握手:客戶端收到 SYN 報文之后,會發送一個 ACK 報文,當然,也是一樣把服務器的 ISN + 1 作為 ACK 的值,表示已經收到了服務端的 SYN 報文,此時客戶端處于?ESTABLISHED?狀態。服務器收到 ACK 報文之后,也處于?ESTABLISHED?狀態,此時,雙方已建立起了連接。

    確認報文段ACK=1,確認號ack=y+1,序號seq=x+1(初始為seq=x,第二個報文段所以要+1),ACK報文段可以攜帶數據,不攜帶數據則不消耗序號。

發送第一個SYN的一端將執行主動打開(active open),接收這個SYN并發回下一個SYN的另一端執行被動打開(passive open)。

在socket編程中,客戶端執行connect()時,將觸發三次握手。

三次握手.png

1.1 為什么需要三次握手,兩次不行嗎?

弄清這個問題,我們需要先弄明白三次握手的目的是什么,能不能只用兩次握手來達到同樣的目的。

  • 第一次握手:客戶端發送網絡包,服務端收到了。
    這樣服務端就能得出結論:客戶端的發送能力、服務端的接收能力是正常的。
  • 第二次握手:服務端發包,客戶端收到了。
    這樣客戶端就能得出結論:服務端的接收、發送能力,客戶端的接收、發送能力是正常的。不過此時服務器并不能確認客戶端的接收能力是否正常。
  • 第三次握手:客戶端發包,服務端收到了。
    這樣服務端就能得出結論:客戶端的接收、發送能力正常,服務器自己的發送、接收能力也正常。

因此,需要三次握手才能確認雙方的接收與發送能力是否正常。

試想如果是用兩次握手,則會出現下面這種情況:

如客戶端發出連接請求,但因連接請求報文丟失而未收到確認,于是客戶端再重傳一次連接請求。后來收到了確認,建立了連接。數據傳輸完畢后,就釋放了連接,客戶端共發出了兩個連接請求報文段,其中第一個丟失,第二個到達了服務端,但是第一個丟失的報文段只是在某些網絡結點長時間滯留了,延誤到連接釋放以后的某個時間才到達服務端,此時服務端誤認為客戶端又發出一次新的連接請求,于是就向客戶端發出確認報文段,同意建立連接,不采用三次握手,只要服務端發出確認,就建立新的連接了,此時客戶端忽略服務端發來的確認,也不發送數據,則服務端一致等待客戶端發送數據,浪費資源。

1.2 什么是半連接隊列?

服務器第一次收到客戶端的 SYN 之后,就會處于 SYN_RCVD 狀態,此時雙方還沒有完全建立其連接,服務器會把此種狀態下請求連接放在一個隊列里,我們把這種隊列稱之為半連接隊列

當然還有一個全連接隊列,就是已經完成三次握手,建立起連接的就會放在全連接隊列中。如果隊列滿了就有可能會出現丟包現象。

這里在補充一點關于SYN-ACK 重傳次數的問題:
服務器發送完SYN-ACK包,如果未收到客戶確認包,服務器進行首次重傳,等待一段時間仍未收到客戶確認包,進行第二次重傳。如果重傳次數超過系統規定的最大重傳次數,系統將該連接信息從半連接隊列中刪除。
注意,每次重傳等待的時間不一定相同,一般會是指數增長,例如間隔時間為 1s,2s,4s,8s…

1.3 ISN(Initial Sequence Number)是固定的嗎?

當一端為建立連接而發送它的SYN時,它為連接選擇一個初始序號。ISN隨時間而變化,因此每個連接都將具有不同的ISN。ISN可以看作是一個32比特的計數器,每4ms加1 。這樣選擇序號的目的在于防止在網絡中被延遲的分組在以后又被傳送,而導致某個連接的一方對它做錯誤的解釋。

三次握手的其中一個重要功能是客戶端和服務端交換 ISN(Initial Sequence Number),以便讓對方知道接下來接收數據的時候如何按序列號組裝數據。如果 ISN 是固定的,攻擊者很容易猜出后續的確認號,因此 ISN 是動態生成的。

1.4 三次握手過程中可以攜帶數據嗎?

其實第三次握手的時候,是可以攜帶數據的。但是,第一次、第二次握手不可以攜帶數據

為什么這樣呢?大家可以想一個問題,假如第一次握手可以攜帶數據的話,如果有人要惡意攻擊服務器,那他每次都在第一次握手中的 SYN 報文中放入大量的數據。因為攻擊者根本就不理服務器的接收、發送能力是否正常,然后瘋狂著重復發 SYN 報文的話,這會讓服務器花費很多時間、內存空間來接收這些報文。

也就是說,第一次握手不可以放數據,其中一個簡單的原因就是會讓服務器更加容易受到攻擊了。而對于第三次的話,此時客戶端已經處于 ESTABLISHED 狀態。對于客戶端來說,他已經建立起連接了,并且也已經知道服務器的接收、發送能力是正常的了,所以能攜帶數據也沒啥毛病。

1.5 SYN攻擊是什么?

服務器端的資源分配是在二次握手時分配的,而客戶端的資源是在完成三次握手時分配的,所以服務器容易受到SYN洪泛攻擊。SYN攻擊就是Client在短時間內偽造大量不存在的IP地址,并向Server不斷地發送SYN包,Server則回復確認包,并等待Client確認,由于源地址不存在,因此Server需要不斷重發直至超時,這些偽造的SYN包將長時間占用未連接隊列,導致正常的SYN請求因為隊列滿而被丟棄,從而引起網絡擁塞甚至系統癱瘓。SYN 攻擊是一種典型的 DoS/DDoS 攻擊。

檢測 SYN 攻擊非常的方便,當你在服務器上看到大量的半連接狀態時,特別是源IP地址是隨機的,基本上可以斷定這是一次SYN攻擊。在 Linux/Unix 上可以使用系統自帶的 netstat 命令來檢測 SYN 攻擊。

netstat -n -p TCP | grep SYN_RECV
  • 1

常見的防御 SYN 攻擊的方法有如下幾種:

  • 縮短超時(SYN Timeout)時間
  • 增加最大半連接數
  • 過濾網關防護
  • SYN cookies技術

2. 四次揮手

建立一個連接需要三次握手,而終止一個連接要經過四次揮手(也有將四次揮手叫做四次握手的)。這由TCP的半關閉(half-close)造成的。所謂的半關閉,其實就是TCP提供了連接的一端在結束它的發送后還能接收來自另一端數據的能力。

TCP 連接的拆除需要發送四個包,因此稱為四次揮手(Four-way handshake),客戶端或服務端均可主動發起揮手動作。

剛開始雙方都處于ESTABLISHED?狀態,假如是客戶端先發起關閉請求。四次揮手的過程如下:

  • 第一次揮手:客戶端發送一個 FIN 報文,報文中會指定一個序列號。此時客戶端處于?FIN_WAIT1?狀態。
    即發出連接釋放報文段(FIN=1,序號seq=u),并停止再發送數據,主動關閉TCP連接,進入FIN_WAIT1(終止等待1)狀態,等待服務端的確認。
  • 第二次揮手:服務端收到 FIN 之后,會發送 ACK 報文,且把客戶端的序列號值 +1 作為 ACK 報文的序列號值,表明已經收到客戶端的報文了,此時服務端處于?CLOSE_WAIT?狀態。
    即服務端收到連接釋放報文段后即發出確認報文段(ACK=1,確認號ack=u+1,序號seq=v),服務端進入CLOSE_WAIT(關閉等待)狀態,此時的TCP處于半關閉狀態,客戶端到服務端的連接釋放。客戶端收到服務端的確認后,進入FIN_WAIT2(終止等待2)狀態,等待服務端發出的連接釋放報文段。
  • 第三次揮手:如果服務端也想斷開連接了,和客戶端的第一次揮手一樣,發給 FIN 報文,且指定一個序列號。此時服務端處于?LAST_ACK?的狀態。
    即服務端沒有要向客戶端發出的數據,服務端發出連接釋放報文段(FIN=1,ACK=1,序號seq=w,確認號ack=u+1),服務端進入LAST_ACK(最后確認)狀態,等待客戶端的確認。
  • 第四次揮手:客戶端收到 FIN 之后,一樣發送一個 ACK 報文作為應答,且把服務端的序列號值 +1 作為自己 ACK 報文的序列號值,此時客戶端處于?TIME_WAIT?狀態。需要過一陣子以確保服務端收到自己的 ACK 報文之后才會進入 CLOSED 狀態,服務端收到 ACK 報文之后,就處于關閉連接了,處于?CLOSED狀態。
    即客戶端收到服務端的連接釋放報文段后,對此發出確認報文段(ACK=1,seq=u+1,ack=w+1),客戶端進入TIME_WAIT(時間等待)狀態。此時TCP未釋放掉,需要經過時間等待計時器設置的時間2MSL后,客戶端才進入CLOSED狀態。

收到一個FIN只意味著在這一方向上沒有數據流動。客戶端執行主動關閉并進入TIME_WAIT是正常的,服務端通常執行被動關閉,不會進入TIME_WAIT狀態。

在socket編程中,任何一方執行close()操作即可產生揮手操作。
image.png

2.1 揮手為什么需要四次?

因為當服務端收到客戶端的SYN連接請求報文后,可以直接發送SYN+ACK報文。其中ACK報文是用來應答的,SYN報文是用來同步的。但是關閉連接時,當服務端收到FIN報文時,很可能并不會立即關閉SOCKET,所以只能先回復一個ACK報文,告訴客戶端,“你發的FIN報文我收到了”。只有等到我服務端所有的報文都發送完了,我才能發送FIN報文,因此不能一起發送。故需要四次揮手。

2.2 2MSL等待狀態

TIME_WAIT狀態也成為2MSL等待狀態。每個具體TCP實現必須選擇一個報文段最大生存時間MSL(Maximum Segment Lifetime),它是任何報文段被丟棄前在網絡內的最長時間。這個時間是有限的,因為TCP報文段以IP數據報在網絡內傳輸,而IP數據報則有限制其生存時間的TTL字段。

對一個具體實現所給定的MSL值,處理的原則是:當TCP執行一個主動關閉,并發回最后一個ACK,該連接必須在TIME_WAIT狀態停留的時間為2倍的MSL。這樣可讓TCP再次發送最后的ACK以防這個ACK丟失(另一端超時并重發最后的FIN)。

這種2MSL等待的另一個結果是這個TCP連接在2MSL等待期間,定義這個連接的插口(客戶的IP地址和端口號,服務器的IP地址和端口號)不能再被使用。這個連接只能在2MSL結束后才能再被使用。

2.3 四次揮手釋放連接時,等待2MSL的意義?

MSL是Maximum Segment Lifetime的英文縮寫,可譯為“最長報文段壽命”,它是任何報文在網絡上存在的最長時間,超過這個時間報文將被丟棄。

為了保證客戶端發送的最后一個ACK報文段能夠到達服務器。因為這個ACK有可能丟失,從而導致處在LAST-ACK狀態的服務器收不到對FIN-ACK的確認報文。服務器會超時重傳這個FIN-ACK,接著客戶端再重傳一次確認,重新啟動時間等待計時器。最后客戶端和服務器都能正常的關閉。假設客戶端不等待2MSL,而是在發送完ACK之后直接釋放關閉,一但這個ACK丟失的話,服務器就無法正常的進入關閉連接狀態。

兩個理由:

  1. 保證客戶端發送的最后一個ACK報文段能夠到達服務端

    這個ACK報文段有可能丟失,使得處于LAST-ACK狀態的B收不到對已發送的FIN+ACK報文段的確認,服務端超時重傳FIN+ACK報文段,而客戶端能在2MSL時間內收到這個重傳的FIN+ACK報文段,接著客戶端重傳一次確認,重新啟動2MSL計時器,最后客戶端和服務端都進入到CLOSED狀態,若客戶端在TIME-WAIT狀態不等待一段時間,而是發送完ACK報文段后立即釋放連接,則無法收到服務端重傳的FIN+ACK報文段,所以不會再發送一次確認報文段,則服務端無法正常進入到CLOSED狀態。

  2. 防止“已失效的連接請求報文段”出現在本連接中

    客戶端在發送完最后一個ACK報文段后,再經過2MSL,就可以使本連接持續的時間內所產生的所有報文段都從網絡中消失,使下一個新的連接中不會出現這種舊的連接請求報文段。

2.4 為什么TIME_WAIT狀態需要經過2MSL才能返回到CLOSE狀態?

理論上,四個報文都發送完畢,就可以直接進入CLOSE狀態了,但是可能網絡是不可靠的,有可能最后一個ACK丟失。所以TIME_WAIT狀態就是用來重發可能丟失的ACK報文

3. 總結

《TCP/IP詳解 卷1:協議》有一張TCP狀態變遷圖,很具有代表性,有助于大家理解三次握手和四次揮手的狀態變化。如下圖所示,粗的實線箭頭表示正常的客戶端狀態變遷,粗的虛線箭頭表示正常的服務器狀態變遷。

TCP狀態變遷圖.jpg

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:
http://www.pswp.cn/news/247186.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/247186.shtml
英文地址,請注明出處:http://en.pswp.cn/news/247186.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

專業術語常用名詞縮寫中英文對照

A:Actuator 執行器A:Amplifier 放大器A:Attendance員工考勤A:Attenuation衰減AA:Antenna amplifier 開線放大器AA:Architectural Acoustics建筑聲學AC:Analogue Controller 模擬控制器ACD:Automatic Call Distribution 自動分配話務ACS:Access Control System出入控制系統AD:Ad…

推薦!國外程序員整理的機器學習資源大全

本列表選編了一些機器學習領域牛B的框架、庫以及軟件(按編程語言排序)。 C 計算機視覺 CCV —基于C語言/提供緩存/核心的機器視覺庫,新穎的機器視覺庫OpenCV—它提供C, C, Python, Java 以及 MATLAB接口,并支持Windows, Linux,…

做任務一定要看測試用例

做任務的時候一定要一開始就看測試用例。雖然有的任務自己很熟,但是如果不時時關注測試用例的話,還是容易走偏,到后頭再去修改的話,會浪費不少時間。 轉載于:https://www.cnblogs.com/superhuake/archive/2011/09/09/2172008.html…

深度學習鼻祖杰夫·辛頓及巨頭們的人才搶奪戰

摘要:深度學習已經誕生了數十年時間,但直到近幾年才受到各大科技公司的重視,被認為是硅谷科技企業的未來,今天為大家介紹的是深度學習的開山鼻祖Geoffrey Hinton。在過去的三十年,深度學習運動一度被認為是學術界的一個…

EM算法(Expectation Maximization Algorithm)

文章目錄 1. 前言 2.基礎數學知識2.1.凸函數2.2.Jensen不等式 3.EM算法所解決問題的例子 4.EM算法4.1.模型說明 4.2.EM算法推導 4.3.EM算法收斂性證明 4.4. EM算法E步說明 5.小結 6.主要參考文獻1. 前言 這是本人寫的第一篇博客(2013年4月5日發在cnblogs上,現在遷移過來)&#…

Julia語言:讓高性能科學計算人人可用

摘要:一群科學家對現有計算工具感到不滿:他們想要一套開源系統,有C的快速,Ruby的動態,Python的通用,R般在統計分析上得心應手,Perl的處理字符串處理,Matlab的線性代數運算能力……易…

View Animation

轉載一篇關于view animation的文章 http://blog.csdn.net/nerohoop/article/details/7245909 補充:當啟用animation來改變值的時候,值是立刻就改變了的,然后才開始動畫。 轉載于:https://www.cnblogs.com/mystory/archive/2012/12/18/2824029…

編程能力的四種境界

人類心理學研究中的一個基礎支撐科目就是分析人的潛意識和意識。 弗洛伊德是最早的一位能夠清楚的認定和描述我們的心理活動“領域”的人。 在他這著名的一生的早期,他就指出我們的意識里分“潛意識”,“前意識”,“意識”。 如 果我們想能清…

ファイルアップロード関連のjQueryプラグイン10攻略

ファイルアップロード関連のjQueryプラグイン10ファイルアップロードといってもSWFを使ったりAJAXを使ったりと方法が色々あって、いろんなやり方ができるjQueryプラグインです。望みの挙動に近いものを選んでカスタマイズすれば作りたいものが最速で作れ…

HTTP報文(轉)

HTTP報文http://www.cnblogs.com/kissdodog/archive/2013/04/01/2993228.html之前寫過一篇HTML報文,但是感覺寫完之后還是不懂,最近終于有時間開始看《HTTP權威指南》,看完之后覺得還是比之前的理解更加深入了,提取HTTP報文出來做…

C#基礎-應用程序域

文章導讀同一臺計算上的應用程序是通過進程來隔離的,每個應用程序都是加載到不同的進程中,從而達到應用程序的互不影響。操作系統【OS】通過進程控制塊【PCB】感知進程的存在,分析【PCB】的數據結構可以發現,【PCB】維護進程運行的…

Java生鮮電商平臺-微服務入門與服務的拆分架構實戰

Java生鮮電商平臺-微服務入門與服務的拆分架構實戰 剛開始進入軟件行業時還是單體應用的時代,前后端分離的概念都還沒普及,開發的時候需要花大量的時間在“強大”的JSP上面,那時候SOA已經算是新技術了。現在,微服務已經大行其道&a…

詳解MTK系統中字符轉換問題

詳解MTK系統中字符轉換問題 2011-09-05 19:02 佚名 互聯網 字號:T | TMTK系統中字符轉換問題是本文要介紹的內容,主要是來了解并學習MTK中一些小案例的應用,具體內容來看本文詳解。 AD:2014WOT全球軟件技術峰會北京站 課程視頻發布…

Java生鮮電商平臺-微服務架構概述

Java生鮮電商平臺-微服務架構概述 單體架構存在的問題 在傳統的軟件技術架構系統中,基本上將業務功能集中在單一應用內,或者是單一進程中。盡管現代化的軟件架構理論以及設計原則已推廣多年,但實際技術衍化的速度遲緩并且變革動力不足。 其中…

Jensen不等式及其證明

? 詹森不等式以丹麥數學家約翰詹森(JohanJensen)命名。它給出積分的凸函數值和凸函數的積分值間的關系。 關于凸函數: if (-f)是凸函數(convex),則f是凹的(concave…

ios自帶NSURLConnection下載文件

//同步下載,同步請求的主要代碼如下 - (IBAction)downLoad:(id)sender { NSString *urlAsString"http://7jpnsh.com1.z0.glb.clouddn.com/TravelDemo.plist";//文件地址 NSURL *url[NSURL URLWithString:urlAsString]; NSURLRequest *request[NSURLRequest requestWi…

國外程序員整理的機器學習資源大全

本列表選編了一些機器學習領域牛B的框架、庫以及軟件(按編程語言排序)。 C 計算機視覺 CCV —基于C語言/提供緩存/核心的機器視覺庫,新穎的機器視覺庫 OpenCV—它提供C, C, Python, Java 以及 MATLAB接口,并支持Windo…

五款幫助創業者迅速熟悉互聯網創業的在線學習工具

相信很多有志青年都想借助互聯網開拓自己的事業,可是經常面臨一個很現實的問題——缺乏一定的專業知識和技能。沒關系,互聯網中的豐富教育資源就可以讓你迅速地跨越這一障礙,熟悉與創業相關的運營、管理、融資等操作技巧。下面介紹的五個在線…

C++ 中復雜的聲明

1、方法也是有類型的,方法的類型由返回類型和形參表決定。比如int F (int)的類型就是去掉方法名,int (int)。 2、對于方法類型,在返回類型和形參表之間,加上一個名稱F,就表示一個特定的方法F。 3、思考,如果…

caffe 下測試 MNIST數據

詳細說明可參考網頁:http://blog.csdn.net/wangchuansnnu/article/details/44341753http://blog.sina.com.cn/s/blog_49ea41a20102w4uu.htmlhttp://www.cnblogs.com/yymn/p/4553671.html caffe 下 mnist 進行實驗: MNIST,一個經典的手寫數字庫…