TCP滑動視窗與擁塞視窗
一、滑動視窗
滑動視窗協議是傳輸層進行流控的一種措施,接收方通過通告發送方自己的視窗大小,從而控制傳送方的傳送速度,從而達到防止傳送方傳送速度過快而導致自己被淹沒的目的。
對ACK的再認識,ack通常被理解為收到資料後給出的一個確認ACK,ACK包含兩個非常重要的資訊:
一是期望接收到的下一位元組的序號n,該n代表接收方已經接收到了前n-1位元組資料,此時如果接收方收到第n+1位元組資料而不是第n位元組資料,接收方是不會發送序號為n+2的ACK的。舉個例子,假如接收端收到1-1024位元組,它會發送一個確認號為1025的ACK,但是接下來收到的是2049-3072,它是不會發送確認號為3072的ACK,而依舊傳送1025的ACK。
二是當前的視窗大小m,如此傳送方在接收到ACK包含的這兩個資料後就可以計算出還可以傳送多少位元組的資料給對方,假定當前傳送方已傳送到第x位元組,則可以傳送的位元組數就是y=m-(x-n).這就是滑動視窗控制流量的基本原理.
滑動視窗協議如圖所示:
在這個圖中,我們將位元組從1至11進行標號。接收方通告的視窗稱為提出的視窗,它覆蓋了從第4位元組到第9位元組的區域,表明接收方已經確認了包括第3位元組在內的資料,且通告視窗大小為6。我們知道視窗大小是與確認序號相對應的。傳送方計算它的可用視窗,該視窗表明多少資料可以立即被髮送。當接收方確認資料後,這個滑動視窗不時地向右移動。視窗兩個邊沿的相對運動增加或減少了視窗的大小。我們使用三個術語來描述視窗左右邊沿的運動:
稱視窗左邊沿向右邊沿靠近為視窗合攏。這種現象發生在資料被髮送和確認時。
當視窗右邊沿向右移動時將允許傳送更多的資料,我們稱之為視窗張開。這種現象發生在另一端的接收程序讀取已經確認的資料並釋放了T C P的接收快取時。
當右邊緣向左移動時,稱之為視窗收縮。
二、擁塞視窗
迄今為止,在本章所有的例子中,傳送方一開始便向網路傳送多個報文段,直至達到接收方通告的視窗大小為止。當傳送方和接收方處於同一個區域網時,這種方式是可以的。但是如果在傳送方和接收方之間存在多個路由器和速率較慢的鏈路時,就有可能出現一些問題。一些中間路由器必須快取分組,並有可能耗盡快取,[Jacobson 1988]證明了這種連線方式是如何嚴重降低了TCP連線的吞吐量的。現在,TCP需要支援一種被稱為“慢啟動(slow start)”的演算法。該演算法通過觀察到新分組進入網路的速率應該與另一端返回確認的速率相同而進行工作。
慢啟動為傳送方的TCP增加了另一個視窗:擁塞視窗(congestion window),記為cwnd。當與另一個網路的主機建立TCP連線時,擁塞視窗被初始化為1個報文段(即另一端通告的報文段大小)。每收到一個ACK,擁塞視窗就增加一個報文段(cwnd以位元組為單位,但是慢啟動以報文段大小為單位進行增加)。傳送方取擁塞視窗與通告視窗中的最小值作為傳送上限。擁塞視窗是傳送方使用的流量控制,而通告視窗則是接收方使用的流量控制。
傳送方開始時傳送一個報文段,然後等待ACK。當收到該ACK時,擁塞視窗從1增加為2,即可以傳送兩個報文段。當收到這兩個報文段的ACK時,擁塞視窗就增加為4。這是一種指數增加的關係。