一、TCP的可靠傳輸如何保證?
在TCP連接中,數據流必須以正確的順序傳送給對方。TCP的可靠性是通過順序編號和確認(ACK)實現的。TCP在開始傳送一個段時,為准備重傳而首先將該段插入到發送隊列中,同時啟動時鍾。然后,如果收到了接收端對該段的ACK信息,就將該段從隊列中刪去。如果在時鍾規定的時間內,ACK未返回,那么就從發送隊列中再次送出這個段。TCP在協議中就對數據可靠傳輸做了保障,握手與斷開都需要通訊雙方確認,數據傳輸也需要雙方確認成功,在協議中還規定了:分包、重組、重傳等規則;而UDP主要是面向不可靠連接的,不能保證數據正確到達目的地。
二、TCP還提供了以下方式保證可靠傳輸
1.確認和重傳:接收方收到報文就會確認,發送方發送一段時間后沒有收到確認就重傳。
TCP是怎么保證錯誤重傳的?
1)接收方受到錯誤的分組,就直接丟棄,而不做任何操作;
2)發送方在規定的時間(比平均往返時延大一些)沒有收到分組的確認分組,就會自動重傳;
3)為了讓對方知道哪個分組出現了問題,就為分組也編了序號。
2.數據校驗
3.數據合理分片和排序
UDP:IP數據報大於1500字節,大於MTU。這個時候發送方IP層就需要分片(fragmentation)把數據報分成若干片,使每一片都小於MTU,而接受方IP層則需要進行數據報的重組。這樣就會多做許多事情而更嚴重的是,由於UDP的特性,當某一片數據傳送中丟失時,接收方便無法重組數據報,將導致丟棄整個UDP數據報。
TCP會按MTU合理分片,接收方會緩存未按序到達的數據,重新排序后再交給應用層。
4.流量控制
利用滑動窗口實現流量控制,如果發送方把數據發送的過快,接收方可能會來不及接收,這就會造成數據的丟失。所謂流量控制就是讓發送方降低發送速率,讓接收方來得及接收。原理就是運用TCP報文段中的窗口大小字段來控制,發送方的發送窗口不可以大於接受方發回的窗口大小。
時機:目的主機緩沖區變小而不能接收源主機更多的數據時,就要流量控制。
改變接收窗口:可隨時改變窗口大小。目的主機在確認時,還向源主機告知目的主機接收緩沖區的大小。
滑動窗口機制:TCP協議里窗口機制有2種,一種是固定的窗口大小、一種是滑動的窗口。這個窗口大小就是我們一次傳輸幾個數據。
思想:允許發送方不必等確認到來就可以繼續發送下面的分組,但規定一個上限。若多個分組的確認未到時,則暫停發送。
1)數據流的各字節被編上序號。
2)TCP的滑動窗口按字節操作而不是按報文段或分組操作。
3)TCP窗口大小為字節數。最大為65535字節。
4)通信雙方都沒有發送和接收緩沖區(相當於發送窗口和接收窗口)。默認大小各系統有差異,如4096、8192、16384等。發送緩沖區大小為默認窗口大小。
5)TCP連接兩端各有兩個窗口(發送窗口和接收窗口)。
這里我們可以看到假設窗口的大小是1,也就是每次只能發送一個數據,只有接受方對這個數據進行確認了以后才能發送第2個數據。我們可以看到發送方每發送一個數據接受方就要給發送方一個ACK對這個數據進行確認。只有接收到了這個確認數據以后發送方才能傳輸下個數據。
這樣我們考慮一下如果說窗口過小,那么當傳輸比較大的數據時需要不停的對數據進行確認,這個時候就會造成很大的延遲。如果說窗口的大小定義的過大。我們假設發送方一次發送100個數據,但是接受方還是只能處理50個數據。這樣每次都會只對這50個數據進行確認。發送方下一次還是發送100個數據,但是接受方還是只能處理50個數據。這樣就避免了不必要的數據來擁塞我們的鏈路。所以我們就引入了滑動窗口機制,窗口的大小並不是固定的而是根據我們之間的鏈路的帶寬的大小,這個時候鏈路是否擁塞。接受方是否能處理這么多數據了。
TCP滑動窗口協議,窗口過大或過小有什么影響?
滑動窗口的大小對網絡性能有很大的影響。
如果滑動窗口過小,極端的情況就是停止等待協議,發一個報文等一個ACK,會造成通信效率下降。
如果滑動窗口過大,網絡容易擁塞,容易造成接收端的緩存不夠而溢出,容易產生丟包現象,則需要多次發送重復的數據,耗費了網絡帶寬。
Nagle算法
Nagle算法是為了避免網絡中存在太多的小包(協議頭比例非常大)造成擁塞。Nagle算法就是為了盡可能發送大塊數據,避免網絡中充斥着許多小數據塊。
算法如下:若發送應用進程要發送的數據逐個字節地送到TCP的發送緩存,則發送方就把第一個數據字節先發送出去,把后面到達的數據字節都緩存起來。當發送方接收對第一個數據字符的確認后,再把發送緩存中的所有數據組裝成一個報文段再發送出去,同時繼續對隨后到達的數據進行緩存。只有在收到對前一個報文段的確認后才繼續發送下一個報文段。當數據到達較快而網絡速率較慢時,用這樣的方法可明顯地減少所用的網絡帶寬。Nagle算法還規定,當到達的數據已達到發送窗口大小的一半或已達到報文段的最大長度時,就立即發送一個報文段。
它的主要職責是數據的累積,實際上有三個門檻:
1)緩沖區中的字節數達到了一定量(超過閾值MSS)
2)等待了一定的時間(一般的Nagle算法都是等待200ms)
3)緊急數據發送。
糊塗窗口綜合症
設想一種情況:TCP接受方的緩存已滿,而交互式的應用進程一次只從接收緩存中讀取1字節(這樣就使接收緩存空間僅騰出1字節),然后向發送方發送確認,並把窗口設置為1字節(但發送的數據報是40字節長)。接着,發送方又發來1字節的數據(請注意:發送方發送的IP數據報時41字節長)。接收方發回確認,仍然將窗口設置為1字節。這樣進行下去,使網絡的效率很低。
要解決這個問題,可以讓接收方等待一段時間,或者接收方緩存已有足夠空間容納一個最長的報文段,或者等到接收緩存已有一半空閑的空間。只要出現這兩種情況之一,接受方就發出確認報文,並向發送方通知當前的窗口大小。此外,發送方也不要發送太小的報文段,而是把數據積累成足夠大的報文段,或達到接收方緩存的空間的一半大小。
上述兩種方法可配合使用。使得在發送方不發送很小的報文段的同時,接收方也不要在緩存剛剛有一點小的空間就急忙把這個很小的窗口大小信息通知給發送法方。
5.擁塞控制:當網絡擁塞時,減少數據的發送。
1)原理:在某段時間,若對網絡中的某一資源的需求超過了該資源所能提供的可用部分,網絡的性能就要變化,這種情況叫做擁塞。
2)方法:因特網建議標准RFC2581定義了進行擁塞控制的四種算法,即慢開始(Slow-start)、擁塞避免(CongestionAvoidance)、快重傳(Fast Restrangsmit)和快恢復(Fast Recovery)。
慢開始:一開始先將阻塞窗口的cwnd設置為一個最大報文值(目的是試探一下網絡的擁塞情況)。每次收到一個對新報文段的確認后,把擁塞窗口增加至多一個MSS的數值。用這樣的方法逐步增大發送方的擁塞窗口cwnd,可以使分組注入到網絡的速率更加合理。
為了防止擁塞窗口cwnd增長過大引起網絡阻塞,還需要設置一個慢開始門限ssthresh狀態變量(如何設置ssthresh)。慢開始門限ssthresh的用法如下:
當cwnd < ssthresh時,使用上述的滿開始算法。
當cwnd > ssthresh時,停止使用慢開始算法而改用擁塞避免算法。
當cwnd = ssthresh時,即可使用慢開始算法,也可使用擁塞避免算法。
擁塞避免:讓擁塞窗口cwnd緩慢地增長,即每經過一個往返時間RTT就把發送方的擁塞窗口cwnd加1,而不是加倍。這樣擁塞窗口cwnd按線性規律緩慢增長,比慢開始算法的擁塞窗口增長速率緩慢的多。無論在慢開始階段還是在擁塞避免階段,只要發送方判斷網絡出現擁塞(其根據就是沒有收到確認),就要把慢開始門限ssthresh設置為出現擁塞時的發送方窗口值的一半(但不能小於2)。然后把擁塞窗口cwnd重新設置為1,執行慢開始算法。這樣做的目的就是要迅速減少主機發送到網絡中的分組數,使得發生擁塞的路由器有足夠的時間把隊列中積壓的分組處理完畢。
3)擁塞:交換節點(如路由器)數據報負載國中的現象。ICMP源站抑制報文,是一種被動機制。
4)必要性:在TCP層,擁塞造成時延增加,這又會造成超時重傳,控制不當會進一步加重擁塞。TCP采用了一種主動控制機制。
5)擁塞控制技術
a. 擁塞窗口 cwnd
每個連接都有一個擁塞窗口,該窗口大小以字節為單位,但是增加和減少以MSS為單位;
初始大小:1個MSS;臨界值:64KB;
發送方維護一個擁塞窗口(cwnd),擁塞窗口的大小取決於網絡的擁塞程度,並且動態地在變化。發送方讓自己的發送窗口等於擁塞。
擁塞窗口的原則:只要網絡沒有出現擁塞,擁塞窗口就在增大一些,一邊把更多的分組發送出去。但只要網絡出現擁塞,擁塞窗口就減少一些,以減少注入到網絡中的分組數。
b. 加速遞減技術
指數級遞減:出現超時重傳時,將臨界值設為當前擁塞窗口的1/2,擁塞窗口恢復為1個MSS大小;
指數退避:對保留在發送窗口中的報文段,將重傳時限加倍;
c. 慢啟動技術
指數遞增:每次成功發送一個MSS長度的報文段(成功發送是收到對應的確認),則發送方擁塞窗口加倍;
線性遞增:增長到臨界值后,每次增加一個MSS;
發送窗口=min(接受方窗口通告,cwnd)
總結一下:
1、在傳遞數據之前,會有三次握手來建立連接。
2、應用數據被分割成TCP認為最適合發送的數據塊(按字節編號,合理分片)。這和UDP完全不同,應用程序產生的數據報長度將保持不變。(將數據截斷為合理的長度)
3、當TCP發出一個段后,它啟動一個定時器,等待目的端確認收到這個報文段。如果不能及時收到一個確認,將重發這個報文段。(超時重發)
4、當TCP收到發自TCP連接另一端的數據,它將發送一個確認。這個確認不是立即發送,通常將推遲幾分之一秒。(對於收到的請求,給出確認響應)(之所以推遲,可能是對包做完整校驗)
5、TCP將保持它首部和數據的校驗和。這是一個端到端的校驗和,目的是檢測數據在傳輸過程中的任何變化。如果收到段的校驗和有差錯,TCP將丟棄這個報文段和不確認收到此報文段。(校驗出包有錯,丟棄報文段,不給出響應,TCP發送數據端,超時時會重發數據)
6、既然TCP報文段作為IP數據報來傳輸,而IP數據報的到達可能會失序,因此TCP報文段的到達也可能會失序。如果必要,TCP將對收到的數據進行重新排序,將收到的數據以正確的順序交給應用層。(對失序數據進行重新排序,然后才交給應用層)
7、既然IP數據報會發生重復,TCP連接的接收端必須丟棄重復的數據。(對於重復數據,能夠丟棄重復數據)
8、TCP還能提供流量控制。TCP連接的每一方都有固定大小的緩沖空間。TCP的接收端只允許另一端發送接收端緩沖區所能容納的數據。這將防止較快主機致使較慢主機的緩沖區溢出。(TCP可以進行流量控制,防止較快主機致使較慢主機的緩沖區溢出),TCP使用的流量控制協議是可變大小的滑動窗口協議。
9、TCP還能提供擁塞控制。當網絡阻塞時,減少數據的發送。