TCP協議格式詳解
源/目的端口號:與源,目的IP地址共同構成了一個端點/套接字。
序列號:TCP傳輸的是字節流,該序列號表示當前分組(TCP的一個報文稱為為分組)的第一個字節在字節流中的偏移。
確認號:當ACK置位時,表示接收方希望接收的下一個字節的偏移。
頭部長度:4位(32位為單位),表示TCP頭部最長為60字節。
CWR:擁塞窗口減。
ECE:若其值為 1 則會通知對方,從對方到這邊的網絡有阻塞。
URG:該位設為 1,表示包中有需要緊急處理的數據,對于需要緊急處理的數據,與后面的緊急指針有關。
ACK:該位設為 1,確認應答的字段有效,TCP規定除了最初建立連接時的 SYN 包之外該位必須設為 1。
PSH:該位設為 1,表示需要將收到的數據立刻傳給上層應用協議,若設為 0,則先將數據進行緩存。
RST:該位設為 1,表示 TCP 連接出現異常必須強制斷開連接。
SYN:用于初始化一個連接的同步序列號。
FIN:該位設為 1,表示今后不再有數據發送,希望斷開連接。
窗口大小:滑動窗口中,允許發送并處于未被接收的數據的最大個數。
TCP校驗和:涵蓋TCP頭部和數據以及頭部中的一些字段的校驗和。
緊急指針:該字段為 16 位。只有在 URG 控制位為 1 時有效。該字段的數值表示本報文段中緊急數據的指針。從數據部分的首位到緊急指針所在的位置為止是緊急數據。因此,緊急指針是指出了緊急數據的末尾在報文段中的位置。
TCP連接
一個TCP連接通常分為3個階段:啟動,數據傳輸,退出。
啟動
以下過程俗稱三次握手,目的是建立連接,交換ISN(初始序列號):
- 客戶端主動發送一個SYN報文段,雙方的端口號和ISN(c),通常客戶端會借此發送一些選項。
- 服務器發送自己的SYN報文作為回應,包含了服務器的ISN(s),將ISN(c)+1作為ACK序列號。
- 為了確認服務器的SYN,客戶端將ISN(s)+1作為返回的ACK數值。
三次握手設置的非常巧妙,為什么是3次,這是一個有趣的問題:
TCP對數據的傳輸提供保障,每一個分組都對應序列號,如果序列號沒有被確認接收,將會被重傳直到被確認接收。而SYN數據報占用了一個序列號,因此SYN是被TCP保障的,如果丟失是會重傳的。因此,客戶端發送自己的ISN(初始序列號),服務器回復的SYN一方面包含自己的ISN的同時,也要將該SYN作為ACK,告知客戶端它發送的上一個分段(SYN)以及被接收,而第三次握手是確保服務器的初始序列號被接收。
因此,三次握手,不多不少,非常巧妙。
連接建立超時
由于建立連接是雙向的,所以雙方的超時機制也類似,一般都是最多發送5次SYN,超出則認為連接建立超時,細節如下:
- 客戶端方超時:一般服務器不存在時,服務器無法回復SYN,客戶端會發送多次SYN,但是發送速率呈指數級下降,直到5次超時。
- 服務器方超時:服務器回復了SYN,但是客戶端沒有回復段3,連接無法建立,服務器也會多次發送SYN,直到5次超時,服務器等待時間長達0 + 3 + 6 + 12 + 24 = 45秒,有的還會更多。 SYN flood攻擊就是利用這一弱點對服務器進行攻擊。
關閉
TCP的關閉需要4個報文段:
- 連接的主動關閉者發送一個FIN段表面自己希望結束連接,它攜帶的序列號K是告知對方最終應該確認接收的序列號,同時該數據段還捎帶應答
- 連接的被動關閉者,發送K+1作為ACK,告知主動關閉者已經接收到了它的FIN。
- 接著,被動關閉者告知其上層應用,對方請求關閉連接,這將導致上層執行自己的網絡停止操作。這個時候,被動關閉者成為主動關閉者,發送自己的FIN,即告知對方最終應該接收的數據段。
- 在另一方,接收到FIN,同樣會回復對方。
到這里,連接被終止。