1. 程式人生 > >資料鏈路層協議視窗的計算問題

資料鏈路層協議視窗的計算問題

首先,我們知道資料鏈路層的協議常用的有三種:

  • 停-等協議
  • 回退N幀協議
  • 選擇重傳協議

這三個協議的知識點除了基本的原理以外,更多的是對視窗大小的計算。

我覺得這個視窗的大小計算,不徹底弄清楚來龍去脈,每一個計算都是天書一樣的,令人頭大。

這三個協議,可以綜合到一個大的概念中:滑動視窗。

在傳送端和接收端,各維護一個視窗。視窗的大小依據協議而不同。

無論如何,有兩個原則不可打破:

  • 傳送視窗不能大於接收視窗
  • 傳送視窗要能區分接收端發出的響應是當前這個輪迴的還是上一個輪迴的

具體到協議裡面來,停等協議很簡單,傳送視窗 = 接收視窗 = 1.

雙方就是很開心的一個一個幀的傳送–接受–傳送響應–傳送下一幀。

而回退N幀協議和選擇重傳協議,牽涉到視窗大小設計的邏輯,就需要一點點思考了。

回退N幀協議裡,傳送視窗>1, 接收視窗 = 1.

所以回退N幀協議裡,接收視窗優哉遊哉的接收,但是傳送端很急,因此會連續傳送一堆,這樣一個心急,一個不著急,兩者在設計上就不在一個調上。傳送方傳送的一堆資料,就有可能需要在接收出錯時,重新發送。
如果接收方仍然是對每一個幀進行確認,那麼,假設傳送方傳送了10個幀,接收方一幀一幀確認,在第五幀時候認為幀出錯,那麼傳送方就需要重發第五幀和第五幀以後的資料。這個邏輯不會錯。即使在捎帶確認中也是一樣。

捎帶確認是,確認幀可以不必對每一個傳送過來的幀進行確認,可以是對當前序號以前的幀全都確認,具體如何實現我們不管。
但是,這裡也顯示出,回退N幀協議,是一種有序傳輸幀的協議。

同時我們提到了對幀進行編號。編號是一種防止幀重複的策略,ps:超時機制是一種應對幀丟失的機制。

假設我們用n個位元對幀進行編號,那麼可編號的個數是2n,這個毫無爭議。需要仔細思考的是:新視窗序號和舊視窗序號如何判別?

一個經典的解釋但我到現在還沒被說服的是:

用三個位元進行編號,共可編出8個不同的序號,假設定傳送視窗為8,編號為0-7.看一種情況:假設8個數據幀全都正確傳送到了接收端,並且對每一個數據幀都發送了確認幀。但是所有的確認幀全都丟了,經過一段時間,觸發了超時重傳機制,重新發送0-7編號的資料幀。接收方會很懵逼,其實這是重傳的,但是接收方認為上一輪我確認過了,這新的8個數據幀是新一輪的吧!這樣就出錯了。

因此,設定傳送視窗大小為8是不行的。

what? 那麼設定傳送視窗為2,3,4,5,6,7就是可以的了嗎,如果按照這個邏輯?
假設就編號0,1共兩個傳送視窗。資料幀正確傳送到了接收端,接收端也同樣對每一幀傳送了確認幀,但是確認幀全都搞丟了。於是傳送端重新發送了0,1編號的資料幀,注意這是重傳的,但是接收端以為這是新的,所以就沒法區分新,舊。
所以,這裡的邏輯並不能推演出來我們需要的結論。想一想很可怕。這根本就是隨便舉個例子,試圖解釋一個自己壓根沒弄明白的問題。

我想了很久,也很痛苦,除了記一個簡單的結論:傳送視窗 + 接收視窗(GBN下是1) <=2n ,n是編號的位元數。

根本理不清到底是為什麼。我只能猜想,或許:我們採用3位位元編號的時候,重複使用的是0-7這8個編號,但是,傳送視窗大小卻必須小於8,即:最大是7.那麼,當0-6編號的資料幀全都發送成功,但是確認幀全都消失在路上的時候,重傳的幀編號變成:0,1,2,3,4,5,6,接收端看到以後就很開心的知道哦,這是重傳的。如果確認幀收到了,繼續傳送的編號是:7 ,0,1, 2, 3, 4。這樣就區別開了上面那個問題。

但是具體是不是這樣的編號,為什麼用比編號數目小一個的數值作為傳送視窗大小,這是我能想到的最合理的解釋。至今也沒看到具體的編號例題,用於證明。看到的都是結論的運用,看到的是根本解釋不了問題的號稱解釋的解釋。

以上猜測,留待證明,更留待被打臉之後的證明。

假設我們帶著這個結論看題目,題目自然是很簡單就可以解決的。

對於視窗大小為n的滑動視窗,最多可以有多少幀已傳送但是沒有確認?
傳送視窗 + 接收視窗 <= 視窗編號總數,也即視窗數 = n
所以當接收視窗數是1的時候,傳送視窗數最大 = n-1

以上。

update1: 看到一個細節,是一個佐證。

在滑動視窗協議中,每一個要傳送的幀都包含一個序號,範圍是從0到某個最大值,最大值通常是2n1,n為幀序號的長度。

所以應證了上面的解釋。即,3個位元編號的時候,最大編號是7,最小編號是0.