天天看點

Protocol(二)[TCP]1.TCP的特性2.TCP通訊時序圖3.TCP的三次握手4.TCP 資料通信5.TCP的四次揮手6.TCP的狀态轉換7.TCP KeepAlive8.SYN攻擊

Protocol-TCP

  • 1.TCP的特性
  • 2.TCP通訊時序圖
  • 3.TCP的三次握手
    • 1.三次握手
    • 2.目的
    • 3.建立連接配接(三次握手)的過程
  • 4.TCP 資料通信
    • 1.資料通信過程
    • 2.滑動視窗概念
  • 5.TCP的四次揮手
    • 1.四次揮手
    • 2.關閉連接配接(四次揮手)的過程
  • 6.TCP的狀态轉換
    • 1.TCP的狀态轉換圖
    • 2.狀态轉換詳解
  • 7.TCP KeepAlive
  • 8.SYN攻擊
    • 1.什麼是 SYN 攻擊(SYN Flood)
    • 2.如何檢測 SYN 攻擊
    • 3.如何防禦 SYN 攻擊

1.TCP的特性

  • TCP 提供一種面向連接配接的、可靠的位元組流服務
  • 在一個 TCP 連接配接中,僅有兩方進行彼此通信,廣播和多點傳播不能用于 TCP
  • TCP 使用校驗和,确認和重傳機制來保證可靠傳輸
  • TCP 給資料分節進行排序,并使用累積确認保證資料的順序不變和非重複
  • TCP 使用滑動視窗機制來實作流量控制,通過動态改變視窗的大小進行擁塞控制

注意

TCP 并不能保證資料一定會被對方接收到,因為這是不可能的。TCP 能夠做到的是,如果有可能,就把資料遞送到接收方,否則就(通過放棄重傳并且中斷連接配接這一手段)通知使用者。是以準确說 TCP 也不是 100% 可靠的協定,它所能提供的是資料的可靠遞送或故障的可靠通知。

2.TCP通訊時序圖

TCP通訊的時序圖。TCP連接配接建立斷開。包含三次握手和四次握手。

Protocol(二)[TCP]1.TCP的特性2.TCP通訊時序圖3.TCP的三次握手4.TCP 資料通信5.TCP的四次揮手6.TCP的狀态轉換7.TCP KeepAlive8.SYN攻擊

在圖中,首先用戶端主動發起連接配接、發送請求,然後伺服器端響應請求,然後用戶端主動關閉連接配接。兩條豎線表示通訊的兩端,從上到下表示時間的先後順序。

注意:資料從一端傳到網絡的另一端也需要時間,是以圖中的箭頭都是斜的。

3.TCP的三次握手

1.三次握手

所謂三次握手(Three-way Handshake),是指建立一個 TCP 連接配接時,需要用戶端和伺服器總共發送3個包。

2.目的

連接配接伺服器指定端口,建立 TCP 連接配接,并同步連接配接雙方的序列号和确認号,交換TCP 視窗大小資訊。在 socket 程式設計中,用戶端執行 connect() 時,将觸發三次握手。

3.建立連接配接(三次握手)的過程

  • 1.主動建立連接配接請求端(用戶端), 發送 SYN 标志位, 攜帶 序号

用戶端發送一個帶SYN标志的TCP封包到伺服器。這是TCP通訊時序圖中三次握手過程中的段1。用戶端發出SYN位表示連接配接請求。序号是1000,這個序号在網絡通訊中用作臨時的位址,每發一個資料位元組,這個序号要加1,這樣在接收端可以根據序号排出資料包的正确順序,也可以發現丢包的情況。

另外,規定SYN位和FIN位也要占一個序号,這次雖然沒發資料,但是由于發了SYN位,是以下次再發送應該用序号1001。

mss表示最大段尺寸,如果一個段太大,封裝成幀後超過了鍊路層的最大長度,就必須在IP層分片,為了避免這種情況,用戶端聲明自己的最大段尺寸,建議伺服器端發來的段不要超過這個長度。

  • 2.被動接受連接配接請求端(伺服器), 接收 SYN 标志,回發 ACK 攜帶 确認序号, 同時 發送 SYN 标志位, 攜帶 序号

伺服器端回應用戶端,是三次握手中的第2個封包段,同時帶ACK标志和SYN标志。表示對剛才用戶端SYN的回應;同時又發送SYN給用戶端,詢問用戶端是否準備好進行資料通訊。

伺服器發出段2,也帶有SYN位,同時置ACK位表示确認,确認序号是1001,表示“我接收到序号1000及其以前所有的段,請你下次發送序号為1001的段”,也就是應答了用戶端的連接配接請求,同時也給用戶端發出一個連接配接請求,同時聲明最大尺寸為1024。

  • 3.主動建立連接配接請求端(用戶端), 接收 SYN 标志, 回發 ACK 攜帶 确認序号。 —— 标志 3 次握手完成

客戶必須再次回應伺服器端一個ACK封包,這是封包段3。

用戶端發出段3,對伺服器的連接配接請求進行應答,确認序号是8001。在這個過程中,用戶端和伺服器分别給對方發了連接配接請求,也應答了對方的連接配接請求,其中伺服器的請求和應答在一個段中發出。

Protocol(二)[TCP]1.TCP的特性2.TCP通訊時序圖3.TCP的三次握手4.TCP 資料通信5.TCP的四次揮手6.TCP的狀态轉換7.TCP KeepAlive8.SYN攻擊

用戶端發起連接配接請求,攜帶SYN标志位、序号、資料大小【0位元組】

服務端響應用戶端的連接配接請求,攜帶ACK标志位,确認序号【用戶端請求序号+1】,同時向用戶端發起連接配接請求,攜帶SYN标志位、序号、資料大小【0位元組】

用戶端響應請求,攜帶ACK标志位,确認序号【服務端請求序号+1】

三次握手完成,對應于socket程式設計的client的Dial( )函數傳回,server端的Accept( )函數傳回

是以一共有三個段用于建立連接配接,稱為三次握手。在建立連接配接的同時,雙方協商了一些資訊,例如,雙方發送序号的初始值、最大段尺寸等。

4.TCP 資料通信

1.資料通信過程

  • 1.用戶端發出段4,包含從序号1001開始的20個位元組資料

    發送端發送資料同時攜帶序号。

  • 2.伺服器發出段5,确認序号為1021,對序号為1001-1020的資料表示确認收到,同時請求發送序号1021開始的資料,伺服器在應答的同時也向用戶端發送從序号8001開始的10個位元組資料。

    接收端接收資料後需要給發送端發送 ACK 應答以及确認序号 (回執),確定TCP通信模式下,資料可靠的傳輸。。

  • 3.用戶端發出段6,對伺服器發來的序号為8001-8010的資料表示确認收到,請求發送序号8011開始的資料。

2.滑動視窗概念

滑動視窗:實時通知對端,本端存儲資料的緩沖區大小。

在資料傳輸過程中,ACK和确認序号是非常重要的,應用程式交給TCP協定發送的資料會暫存在TCP層的發送緩沖區中,發出資料包給對方之後,隻有收到對方應答的ACK段才知道該資料包确實發到了對方,可以從發送緩沖區中釋放掉了,如果因為網絡故障丢失了資料包或者丢失了對方發回的ACK段,經過等待逾時後TCP協定自動将發送緩沖區中的資料包重發。

注意

資料傳輸中的是否丢包,與選擇哪一種通信方式無關,和目前的網絡環境有關系,是以說選擇TCP通信方式進行資料傳輸一定不會丢包的說法是錯誤的。

5.TCP的四次揮手

1.四次揮手

TCP 的連接配接的拆除需要發送四個包,是以稱為四次揮手(Four-way handshake),也叫做改進的三次握手,指斷開一個TCP連接配接時,需要用戶端和服務端總共發送4個包以确認連接配接的斷開。用戶端或伺服器均可主動發起揮手動作,在 socket 程式設計中,任何一方執行 close() 操作即可産生揮手操作。

2.關閉連接配接(四次揮手)的過程

由于TCP連接配接是全雙工的,是以每個方向都必須單獨進行關閉。這原則是當一方完成它的資料發送任務後就能發送一個FIN來終止這個方向的連接配接。收到一個 FIN隻意味着這一方向上沒有資料流動動,一個TCP連接配接在收到一個FIN後仍能發送資料。首先進行關閉的一方将執行主動關閉,而另一方執行被動關閉。

  • 1.用戶端發出段7,FIN位表示關閉連接配接的請求。
  • 2.伺服器發出段8,應答用戶端的關閉連接配接請求。
  • 3.伺服器發出段9,其中也包含FIN位,向用戶端發送關閉連接配接請求。
  • 4.用戶端發出段10,應答伺服器的關閉連接配接請求。

建立連接配接的過程是三次握手,而關閉連接配接通常需要4個段,伺服器的應答和關閉連接配接請求通常不合并在一個段中,因為有連接配接半關閉的情況,這種情況下用戶端關閉連接配接之後就不能再發送資料給伺服器了,但是伺服器還可以發送資料給用戶端,直到伺服器也關閉連接配接為止。

Protocol(二)[TCP]1.TCP的特性2.TCP通訊時序圖3.TCP的三次握手4.TCP 資料通信5.TCP的四次揮手6.TCP的狀态轉換7.TCP KeepAlive8.SYN攻擊

6.TCP的狀态轉換

1.TCP的狀态轉換圖

TCP狀态圖對排除和定位網絡或系統故障時非常有幫助,總共有11中狀态。

Protocol(二)[TCP]1.TCP的特性2.TCP通訊時序圖3.TCP的三次握手4.TCP 資料通信5.TCP的四次揮手6.TCP的狀态轉換7.TCP KeepAlive8.SYN攻擊

CLOSED:表示初始狀态。

LISTEN:該狀态表示伺服器端的某個SOCKET處于監聽狀态,可以接受連接配接。

SYN_SENT:這個狀态與SYN_RCVD遙相呼應,當用戶端SOCKET執行CONNECT連接配接時,它首先發送SYN封包,随即進入到了SYN_SENT狀态,并等待服務端的發送三次握手中的第2個封包。SYN_SENT狀态表示用戶端已發送SYN封包。

SYN_RCVD: 該狀态表示接收到SYN封包,在正常情況下,這個狀态是伺服器端的SOCKET在建立TCP連接配接時的三次握手會話過程中的一個中間狀态,很短暫。此種狀态時,當收到用戶端的ACK封包後,會進入到ESTABLISHED狀态。

ESTABLISHED:表示連接配接已經建立。

FIN_WAIT_1: FIN_WAIT_1和FIN_WAIT_2狀态的真正含義都是表示等待對方的FIN封包。差別是:

FIN_WAIT_1狀态是當socket在ESTABLISHED狀态時,想主動關閉連接配接,向對方發送了FIN封包,此時該socket進入到FIN_WAIT_1狀态。

FIN_WAIT_2狀态是當對方回應ACK後,該socket進入到FIN_WAIT_2狀态,正常情況下,對方應馬上回應ACK封包,是以FIN_WAIT_1狀态一般較難見到,而FIN_WAIT_2狀态可用netstat看到。

FIN_WAIT_2:主動關閉連結的一方,發出FIN收到ACK以後進入該狀态。稱之為半連接配接或半關閉狀态。該狀态下的socket隻能接收資料,不能發。

TIME_WAIT: 表示收到了對方的FIN封包,并發送出了ACK封包,等2MSL後即可回到CLOSED可用狀态。如果FIN_WAIT_1狀态下,收到對方同時帶 FIN标志和ACK标志的封包時,可以直接進入到TIME_WAIT狀态,而無須經過FIN_WAIT_2狀态。

CLOSING: 這種狀态較特殊,屬于一種較罕見的狀态。正常情況下,當你發送FIN封包後,按理來說是應該先收到(或同時收到)對方的 ACK封包,再收到對方的FIN封包。但是CLOSING狀态表示你發送FIN封包後,并沒有收到對方的ACK封包,反而卻也收到了對方的FIN封包。什麼情況下會出現此種情況呢?如果雙方幾乎在同時close一個SOCKET的話,那麼就出現了雙方同時發送FIN封包的情況,也即會出現CLOSING狀态,表示雙方都正在關閉SOCKET連接配接。

CLOSE_WAIT: 此種狀态表示在等待關閉。當對方關閉一個SOCKET後發送FIN封包給自己,系統會回應一個ACK封包給對方,此時則進入到CLOSE_WAIT狀态。接下來呢,察看是否還有資料發送給對方,如果沒有可以 close這個SOCKET,發送FIN封包給對方,即關閉連接配接。是以在CLOSE_WAIT狀态下,需要關閉連接配接。

LAST_ACK: 該狀态是被動關閉一方在發送FIN封包後,最後等待對方的ACK封包。當收到ACK封包後,即可以進入到CLOSED可用狀态。

2MSL (Maximum Segment Lifetime) 和與之對應的TIME_WAIT狀态,可以讓4次握手關閉流程更加可靠。4次握手的最後一個ACK是是由主動關閉方發送出去的,若這個ACK丢失,被動關閉方會再次發一個FIN過來。若主動關閉方能夠保持一個2MSL的TIME_WAIT狀态,則有更大的機會讓丢失的ACK被再次發送出去。注意,TIME_WAIT狀态一定出現在主動關閉這一方。

2.狀态轉換詳解

Protocol(二)[TCP]1.TCP的特性2.TCP通訊時序圖3.TCP的三次握手4.TCP 資料通信5.TCP的四次揮手6.TCP的狀态轉換7.TCP KeepAlive8.SYN攻擊

TCP 狀态轉換圖:

主動連接配接端(用戶端):

CLOSED --> 發送 SYN --> SYN_SENT --> 接收 ACK、SYN,發送 ACK --> ESTABLISHED --> 資料通信

主動關閉端(用戶端):

ESTABLISHED --> 發送 FIN --> FIN_WAIT_1 --> 接收 ACK --> FIN_WAIT_2 (半關閉) --> 接收FIN,發送 ACK --> TIME_WAIT --> 等待 2MSL 時長 --> CLOSED

—— FIN_WAIT_2、TIME_WAIT、2MSL 隻出現 主動端。

被動連接配接端(伺服器):

CLOSED --> LISTEN --> 接收SYN, 發送 ACK, SYN --> SYN_RCVD --> 接收 ACK–>>ESTABLISHED --> 資料通信

被動關閉端(伺服器):

ESTABLISHED --> 接收 FIN, 發送ACK --> CLOSE_WAIT (對應主動端的 FIN_WAIT_2) --> 發送 FIN --> LAST_ACK --> 接收 ACK --> CLOSED

7.TCP KeepAlive

TCP 的連接配接,實際上是一種純軟體層面的概念,在實體層面并沒有“連接配接”這種概念。TCP 通信雙方建立互動的連接配接,但是并不是一直存在資料互動,有些連接配接會在資料互動完畢後,主動釋放連接配接,而有些不會。在長時間無資料互動的時間段内,互動雙方都有可能出現掉電、當機、異常重新開機等各種意外,當這些意外發生之後,這些 TCP 連接配接并未來得及正常釋放,在軟體層面上,連接配接的另一方并不知道對端的情況,它會一直維護這個連接配接,長時間的積累會導緻非常多的半打開連接配接,造成端系統資源的消耗和浪費,為了解決這個問題,在傳輸層可以利用 TCP 的 KeepAlive 機制實作來實作。主流的作業系統基本都在核心裡支援了這個特性。

TCP KeepAlive 的基本原理是,隔一段時間給連接配接對端發送一個探測包,如果收到對方回應的ACK,則認為連接配接還是存活的,在超過一定重試次數之後還是沒有收到對方的回應,則丢棄該 TCP連接配接。

TCP KeepAlive 的局限。首先 TCP KeepAlive 監測的方式是發送一個 probe包,會給網絡帶來額外的流量,另外 TCP KeepAlive 隻能在核心層級監測連接配接的存活與否,而連接配接的存活不一定代表服務的可用。例如當一個伺服器 CPU 程序伺服器占用達到 100%,已經卡死不能響應請求了,此時 TCP KeepAlive 依然會認為連接配接是存活的。是以 TCP KeepAlive 對于應用層程式的價值是相對較小的。需要做連接配接保活的應用層程式,例如 QQ,往往會在應用層實作自己的心跳功能。

8.SYN攻擊

1.什麼是 SYN 攻擊(SYN Flood)

在三次握手過程中,伺服器發送 SYN-ACK 之後,收到用戶端的 ACK 之前的 TCP 連接配接稱為半連接配接(half-open connect)。此時伺服器處于 SYN_RCVD 狀态。當收到 ACK 後,伺服器才能轉入ESTABLISHED 狀态.

SYN 攻擊指的是,攻擊用戶端在短時間内僞造大量不存在的IP位址,向伺服器不斷地發送SYN包,伺服器回複确認包,并等待客戶的确認。由于源位址是不存在的,伺服器需要不斷的重發直至逾時,這些僞造的SYN包将長時間占用未連接配接隊列,正常的SYN請求被丢棄,導緻目标系統運作緩慢,嚴重者會引起網絡堵塞甚至系統癱瘓。

SYN 攻擊是一種典型的 DoS/DDoS 攻擊。

2.如何檢測 SYN 攻擊

檢測 SYN 攻擊非常的友善,當你在伺服器上看到大量的半連接配接狀态時,特别是源IP位址是随機的,基本上可以斷定這是一次SYN攻擊。在 Linux/Unix 上可以使用系統自帶的 netstats指令來檢測 SYN 攻擊。

3.如何防禦 SYN 攻擊

SYN攻擊不能完全被阻止,除非将TCP協定重新設計。我們所做的是盡可能的減輕SYN攻擊的危害,常見的防禦 SYN 攻擊的方法有如下幾種:

  • 1.縮短逾時(SYN Timeout)時間
  • 2.增加最大半連接配接數
  • 3.過濾網關防護
  • 4.SYN cookies技術