TCP流量控制原理


TCP采用個各種辦法來減少流量的傳輸量以及信道的利用率。

延時確認-減少傳輸數量

TCP允許延遲一會再發送ACK,這樣可以將ACK和相同方向的數據結合起來進行發送,從而降低ACK的數量,在一定程度上減輕網絡負載。

圖中通過延遲ACK減少了一個ACK的傳輸數量

也叫稍帶確認(piggybacking)。一般處理請求並產生應答的時間小於200ms時發生。如果耗時比較長,一般是先確認后應答(發數據)

滑動窗口

滑動窗口的工作原理在之前已經做了詳細的介紹,在滑動窗口中有一個很重要的概念:窗口大小。問題來了,TCP是如何設置窗口大小的呢?在介紹之前先看一下TCP的緩存結構。

 

對於TCP來說接收和發送方都維護着一個緩存。看上圖會發現個問題:如果寫進程寫的速度大於讀進程的讀取速度,這樣會導致接收緩存溢出,最終導致發送失敗。所以引入了窗口大小的概念,接收方通過ACK來實時告知發送方自己剩余緩存的大小(即自己還能接收多少數據),這個大小就是滑動窗口的大小,在傳輸的過程中,每一次ack接收方會根據自己的緩存大小動態的調整窗口的大小,下圖詳細展示了這一過程。

0窗口(Zero Window)

上面滑動窗口的展示中最終發送窗口變成了0.

當發送方收到窗口為0的參數后,便不再發送數據給接收方,這個時候接收方進程一直在讀取數據,最終接收方的TCP緩存會清空,有空間接收數據,這個時候接收方會通過一個ack通知發送方窗口的大小,但是這個ack有可能會丟失(ack沒有重傳功能),發送方因為窗口時0,一直沒有發送數據,所以無法得知最新的窗口大小,通信雙方都進入了一直等待狀態。

為了解決這個問題,TCP為每一個鏈接設計了一個持續計數器(persistence timer),當窗口大小為0時,就會啟動這個計數器,當計數器到期后會發送一個零窗口(zero window)探測報文段(一個字節),接收方通過確認這個探測報文時可以告知發送方最新的窗口大小。(TCP規定,就算窗口為0,也要接收零窗口探測報文)。下圖展示了這種case。

糊塗窗口綜合征(Silly Window Syndrome-SWS)

通俗來解釋這個場景就是一架可以坐500人的飛機只拉1個乘客和5個機組人員,資源極大的浪費。

以太網最大傳輸單元(MTU:max transmission unit)為1500字節,TCP+IP的頭部字段為40字節,所以TCP的最大報文(MSS:Max segment size)長度為1460字節。當傳遞的報文的大小遠遠小於1460。尤其小於頭部40的時候,就出現了上面說的一個大飛機拉一個人的情況,其中MTU為飛機的容量(500),機組乘員為TCP/IP頭部(5),傳輸報文為乘客(1)。

發送端引起的SWS

發送窗口的size大於MSS,但是需要發送的數據遠遠小於MSS,這種情況的解決采用nagle算法:

  if there is new data to send #有數據要發送
        # 發送窗口緩沖區和隊列數據 >=mss,隊列數據(available data)為原有的隊列數據加上新到來的數據
        # 也就是說緩沖區數據超過mss大小,nagle算法盡可能發送足夠大的數據包
        if the window size >= MSS and available data is >= MSS 
            send complete MSS segment now # 立即發送
        else
            if there is unconfirmed data still in the pipe # 前一次發送的包沒有收到ack
                # 將該包數據放入隊列中,直到收到一個ack再發送緩沖區數據
                enqueue data in the buffer until an acknowledge is received 
            else
                send data immediately # 立即發送
            end if
        end if
    end if 

else里面有小塊數據(小於MSS)時候,解釋下:這個時候需要看是否還有已經發送待確認的數據,如果有則等着先不發,等於先在發送端攢數據。某種程度上又變成了停等協議,如果ACK返回的比較慢,小數據等待的時間就會比較長,最終會影響性能。有些情況並不適用nagle算法,比如人機交互的游戲等,可以禁用nagle算法。

接收端引起的SWS

對於接收端來說,如果接收緩存的窗口大小小於MSS或者某個給定的值后,直接ack 接收窗口的size為0。這樣當發送方收到接收窗口為0時,則停止發送數據進行等待,在此期間,接收端的應用一直在讀取數據,這樣接收窗口會慢慢變大,最終通過發送方的0窗口探測請求告知發送方最新的窗口大小,從而再次開始數據傳輸。

以上介紹了TCP流量控制的一個整體過程,全文完。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM