使用WireShark探究TCP傳輸過程

因爲最近在搞OpenSSL加密通信,想看看加密傳輸的數據和不加密傳輸的數據有什麼不同,所以就使用WireShark抓包軟件一探究竟。突然發現WireShark抓包太強了,能清楚的看到TCP三次握手過程和數據傳輸過程,這也是這篇Blog的重點。

目錄

不加密TCP傳輸

加密TCP傳輸

擴展


前提提醒:

  1. 因爲測試程序是公司的程序代碼,所以不再提供(之後可能出一篇使用OpenSSL加密通信編程Blog)。
  2. 使用WireShark軟件抓包。要注意服務器和客戶端是不是使用本地迴環地址。如果是,走的是迴環虛擬網卡,不走物理網卡。如果WireShark檢測不了虛擬網卡就抓不了包(網上好像有解決方案,在這裏不是重點)。當然你可以部署到不同機器上,下面就是使用該方法。
  3. 以下服務器IP/PORT:192.168.18.165:11000 客戶端IP:192.168.3.141

不加密TCP傳輸

直接看抓包結果:

可以清楚的看到TCP的三次握手,以及客戶端服務器收發數據過程,包括髮送大數據包,TCP採取發送端分包策略和接收端的延遲確認機制(見文末)等。

TCP理論知識:

  • TCP數據包中,Seq表示這個包的序號,注意,這個序號不是按1遞增的,而是按TCP包內數據字節長度加上,如包內數據是21字節,而當前A發到B的包的Seq是10的話,那下個A發到B的包的Seq就是10+21=31。
  • 每個TCP包都帶有Win、Ack,這些是告訴對方,我還可以接收數據的滑動窗口是多少,如果A發到B的包的Win爲0,就是A告訴B說我現在滑動窗口爲0了,飽了,你不要再發給我了,就說明A端環境有壓力(如帶寬滿了等)。
  • 如果A發到B連續幾個包(不一定是數據包),Seq號不變,Ack號一直在變大,說明A一直在收B的數據,一直在給B確認。
  • 如果A發到B連續幾個包(不一定是數據包),Seq號一直變大,Ack號一直沒變,說明A一直在向B發數據,沒有發送確認,而是在等B的確認。
  • 可以接收多個數據包後,一次性給一個確認,不用每個數據包一一對應給應答。

加密TCP傳輸

OpenSSL加密通信就是在TCP協議上再封裝的一層協議,以供應用層使用。具體就不再細說,不是本Blog重點。

SSL握手

上圖可以清楚看到,SSL協議的握手過程:

  1. SSLclient通過Client Hello消息將它支持的SSL版本號、加密算法、密鑰交換算法、MAC算法等信息發送給SSLserver。
  2.  SSLserver確定本次通信採用的SSL版本號和加密套件,並通過Server Hello消息通知給SSLclient。假設SSLserver同意SSLclient在以後的通信中重用本次會話,則SSLserver會爲本次會話分配會話ID(顯然這裏沒有同意,而是在第四步創建一個新的Session)。並通過Server Hello消息發送給SSLclient;SSLserver將攜帶自己公鑰信息的數字證書通過Certificate消息發送給SSLclient;SSLserver發送Server Hello Done消息。通知SSLclient版本號和加密套件協商結束。開始進行密鑰交換。
  3. SSLclient驗證SSLserver的證書合法後,利用證書中的公鑰加密SSLclient隨機生成的premaster secret,並通過Client Key Exchange消息發送給SSLserver;SSLclient發送Change Cipher Spec消息,通知SSLserver興許報文將採用協商好的密鑰和加密套件進行加密和MAC計算;SSLclient計算已交互的握手消息(除Change Cipher Spec消息外全部已交互的消息)的Hash值,利用協商好的密鑰和加密套件處理Hash值(計算並加入MAC值、加密等),並通過Finished消息發送給SSLserver。SSLserver利用相同的方法計算已交互的握手消息的Hash值,並與Finished消息的解密結果比較,假設二者相同,且MAC值驗證成功,則證明密鑰和加密套件協商成功。
  4. SSLserver創建新的Session發送,接下來通信是用這個Session通信;SSLserver發送Change Cipher Spec消息,通知SSLclient興許報文將採用協商好的密鑰和加密套件進行加密和MAC計算;SSLserver計算已交互的握手消息的Hash值,利用協商好的密鑰和加密套件處理Hash值(計算並加入MAC值、加密等),並通過Finished消息發送給SSLclient。SSLclient利用相同的方法計算已交互的握手消息的Hash值,並與Finished消息的解密結果比較,假設二者相同。且MAC值驗證成功。則證明密鑰和加密套件協商成功。

SSL傳輸數據

 

SSL加密的強大之處在於,在後續的傳輸中,可能會重新非對稱加密,重新生成對稱密鑰,然後繼續傳輸。
SSL之所以很難破解甚至無法破解,是因爲算法都是利用一些大素數計算,計算起來也要半天,所以很難破解。

擴展

ACK機制:

  • 發送方連續發送多個數據包或者一個數據很大被分爲多個數據包(大小大於 MSS 的話,就會被打包成多個包)時,每次接收方並不是需要對每個連續的包進行ACK,可能接受幾個包的時候發送ACK。而這些TCP數據包達到的順序是不保證的,這樣接收方可能先接收到後發送的TCP包。
  • 爲了降低網絡流量,ACK有延遲確認機制
  • Ack的值到達最大值後,又會從0開始。

ACK延遲確認機制

接收方在收到數據後,並不會立即回覆ACK,而是延遲一定時間。一般ACK延遲發送的時間爲200ms,但這個200ms並非收到數據後需要延遲的時間。系統有一個固定的定時器每隔200ms會來檢查是否需要發送ACK包。這樣做有兩個目的:

  • 這樣做的目的是ACK是可以合併的,也就是指如果連續收到兩個TCP包,並不一定需要ACK兩次,只要回覆最終的ACK就可以了,可以降低網絡流量。
  • 如果接收方有數據要發送,那麼就會在發送數據的TCP數據包裏,帶上ACK信息(見不加密TCP傳輸圖中的客戶端確認+發送數據)。這樣做,可以避免大量的ACK以一個單獨的TCP包發送,減少了網絡流量。

 

PSH標誌
TCP發送方什麼時候將發送緩衝區數據發送出去,以及 接收方什麼時候將數據從接收緩衝區讀取都是未知的。如果使用 PSH 標誌(但實際我們應用層控制不了,只是爲了解釋),上面這件事就確認下來了:

發送端:
對於發送方來說,由 TCP 自行決定,何時將接收緩衝區中的數據打包成 TCP 報文,並加上 PSH 標誌(假設)。
一般來說,每一次 write,都會將這一次的數據打包成一個或多個 TCP 報文段(如果數據量大於 MSS(服務器端 MSS 爲 1460,而客戶端只有 1260) 的話,就會被打包成多個 TCP 段),並將最後一個 TCP 報文段標記爲 PSH。
當然上面說的只是一般的情況,如果發送緩衝區滿了,TCP 同樣會將發送緩衝區中的所有數據打包發送。

接收端:
如果接收方接收到了某個 TCP 報文段包含了 PSH 標誌,則立即將緩衝區中的所有數據推送給應用進程(read 函數返回)。
當然有時候接收緩衝區滿了,也會推送。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章