运输层:流水线可靠数据传输协议
禁止码迷,布布扣,豌豆代理,码农教程,爱码网等第三方爬虫网站爬取!
比特交替协议性能
我们来考虑比特交替协议,会发现由于协议需要等待 ACK,中间的等待时间内发送端和接收端都是无所事事的。
根据分析,我们可以计算出比特交替协议的信道利用率,我们会发现这个量级是十分可怜的。而且我们还忽略了发送方和接收方的底层协议的处理时延,还有发送方和接收方之间任何一跳路由器的处理、排队时延。也就是说比特交替协议虽然可以实现可靠传输,但是也限制了物理资源的应用。
流水线传输
对于这类性能问题,一个简单的想法是:不以停等的方式运行,允许发送方发送多个分组而无需等待确认。此时发送方可连续发送多个分组,不必每发完一个分组就停顿下来等待对方的确认,这种手法被称之为流水线传输。由于信道上一直有数据不间断地传送,这种传输方式可获得很高的信道利用率。
引入流水线传输,会对已有的可靠传输带来什么影响呢?主要在于以下 3 个方面:
- 必须增加序号范围,考虑到有多个正在传输的 ACK,所以每个传输中的分组必须有唯一的序号;
- 协议的发送方、接收方都需要缓存多个分组,发送发需要缓存已发送但是没有收到 ACK 的分组,接收方需要缓存正确接收的分组(防止冗余),这意味着需要更大的缓存空间;
- 流水线传输的差错恢复更为复杂,2 种恢复差错的方式为:回退 N 步、选择重传。
回退 N 步(GBN)协议
滑动窗口
回退 N 步的手法是基于序号实现的,对于发送方中的每个分组都会有不同的序号。流水线未确认分组的上限称之为窗口长度(N)最早为确认分组的序号称之为基序号(base),最小未使用的序号称之为下一个序号(nextseqnum)。基于这 2 个序号就可以把分组切割为 4 个部分,[0,base-1]是已经发送并被确认的分组,[base,nextseqnum - 1]是已经发送但未被确认的分组,[nextseqnum ,base + N - 1]是分组可以利用的序号,base + N 以上的序号是不可用的。
已发送但还未被确认的端口的序号范围,可以被抽象为一个长度为 N 的窗口,因此 GBN 协议也被称之为滑动窗口协议。随着协议的运行,窗口在序号空间内向前滑动。
GBN 发送方
对于 GBN 的发送方而言,需要对以下 3 种情况做出相应。首先是需要发送数据的时候,发送方首先检查发送窗口是否已满,若窗口未满就产生一个分组并发送,然后自增变量。如果窗口已满,则发送方需要提示上层窗口已经满了,请上层贵一会儿再尝试。
接着是收到 ACK 的时候,GBN 协议对序号为 n 分组的确认方式是累积确认。因为发送方收到的不一定是基序号对应的 ACK,累积确认支持一次性确认序号 n 及 n 之前所有序号的分组,然后进行“窗口滑动”。
第三是遇到超时事件时,首先需要重启定时器,然后发送方要重传所有已发送但未确认的分组。这也是所谓的“回退 N 步”的具体实现,就是只要未确认就全部重传。这种方式是否会带来资源浪费的问题?
GBN 接收方
如果一个序号为 n 的分组被正确接收,并且是按需接收的,则发送方就对分组 n 发送 ACK,并且将该分组中的数据部分交付上层。对于其他情况都是直接丢包,并且为最近按序接收的分组重新发送 ACK。
为了保证数据按序交付,接收方需要丢弃所有的失序分组。这是因为对于发送方而言,如果分组 n 丢包,则分组 n 及分组 n+1 之后的所有未确认分组都会被重传。这种方式的优点在于接收方不需要缓存任何失序分组,接收方需要维护的唯一信息就是下一个按序接收的分组序号。
协议流程
选择重传
GBN 协议最大的问题在于单个分组的查错会引起 GBN 重传大量分组,但是很多分组根本没必要重传,当信道的差错率增加是流水线会充满大量不必要分组。所谓选择重传(SR)协议通过让发送方仅重传出错的分组,避免不必要的重传。
SR 发送方
首先是从上层收到数据,此时 SR 检查下一个可用于该分组的序号,若序号位于发送窗口内则打包数据并发送。若序号不可用就暂时缓存数据,或者返回给上层等待一段时间。
对于超时,SR 仍然使用定时器防止丢失分组,此时想在每个分组都需要有自己的逻辑计时器,因为超时事件发生时仅重传一个分组。
对于收到 ACK时,若 ACK 对应的分组序号在窗口内,则 SR 发送方将被确认分组标记为已接收。如果 ACK 对应的分组序号是基序号,则窗口基序号向前移动到未确认分组的最小序号。若窗口移动时有序号对应的分组没发送,就将这些分组发出去。
SR 接收方
若收到的分组序号在接收方的窗口内,则向发送方发送 ACK,若该分组是之前没收到过的就缓存。若该分组序号等于接收窗口的基序号,则该分组之前缓存过的序号连续的分组都交付给上层。
若收到的分组序号在接收方的窗口外(已成功接收),也向发送方发送 ACK。接收方重新确认已收到过的序号小于基序号的分组是很重要的操作,如果基序号的 ACK 没有被发送方接收到的话,发送方将再次重传。也就是说如果接收方不确认这类分组,发送方窗口将永远不向前滑动。
其他情况都直接忽略分组,不做任何事情。
新分组还是重传?
对于哪些分组被正确接收,哪些分组没有被接收,发送方和接收方并不能同步地知道结果,这也说明 SR 协议中发送方和接收方窗口并不总一致。接下来通过 2 个例子说明,SR 协议保证窗口同步的重要性。
首先看第一个例子,该例子中 3 个分组的 ACK 全部丢失,因此发送方会重传这些分组。但是接收方的窗口已经发生了滑动,此时即使接收方收到了期望序号的分组,但显然接下来的分组会全部出错。
在第二个例子中,接收方并不能同步得知发送方的动作,因此无法区分分组是第 1 个分组的重传,还是第 5 个分组的传输。
因此为了同步发送方和接收方的窗口,对于窗口长度规模需要进行控制,窗口长度必须小于或等于序号空间大小的一半。
参考资料
《计算机网络(第七版)》 谢希仁 著,电子工业出版社
《计算机网络 自顶向下方法》 [美] James F.Kurose,Keith W.Ross 著,陈鸣 译,机械工业出版社