Transport-layer Protocols gaunthan Posted on Feb 8 2017 ? Computer Networking ? ? Transport Layer ? ## 简单的无连接协议 **简单的无连接协议**既没有流量控制也没有差错控制,它假设接收方能够立即处理它所收到的任何分组。 发送方的传输层从发送方的应用层接收到报文,从中建立一个分组并发送它。接收方的传输层从网络层接收到这个分组,从分组中提取报文并传递到应用层。发送方和接收方的传输层都为应用层提供传输服务。 ## ARQ协议 在计算机网络环境中,基于确认-重传机制的可靠数据传输协议称为**自动重传请求**(Automatic Repeat reQuest, ARQ)协议。 基本上,ARQ协议还需要另外三种协议功能来处理存在比特差错的情况: 协议功能|说明 --|-- 差错检测|首先,需要一种机制以使接收方检测到何时出现了比特差错 接收方反馈|因为发送方和接收方通常在不同端系统上执行,发送方要了解接收方情况(分组是否被正确接收)的唯一途径就是让接收方提供明确的反馈信息给发送方。“肯定确认”(ACK)和“否定确认”(NAK)就是这种反馈的例子 重传|接收方收到有差错的分组时,发送方将重传该分组 ### 丢包 在实际应用中,除了比特受损,底层信道还会丢包,这在今天的计算机网络中并不罕见。假定分送方传输一个数据分组,该分组或者接收者对该分组的ACK发生了丢失。在这两种情况下,发送方都收不到应当到来的接收方的响应。如果发送方愿意等待足够长的时间以便确定分组已丢失,则它只需重传该数据分组即可。 问题是这个等待时间该如何确定的?很明显发送方至少需要等待这么长的时间:即发送方到接收方之间的一个往返时延(可能会包括在中间路由器的缓冲时延)加上接收方处理一个分组所需的时间。 在很多网络中,最坏情况下的最大时延是很难估计的,确定的因素非常少。此外,理想的协议应尽可能快地从丢包中恢复出来;等待一个最坏情况的时延可能意味着要等待一段较长的时间,直到启动差错恢复为止。因此实践中采取的方法是发送方明智地选择一个时间值。 ### 定时器 为了实现基于时间的重传机制,需要一个**倒计数定时器**(countdown timer),在每一个给定的时间量过期后,可中断发送方。因此,发送方需要能做到: 1. 每次发送一个分组(包括第一个分组和重传分组)时,便启动一个定时器。 2. 响应定时器中断,采取适当的动作。 3. 终止定时器。 ### 冗余分组 注意,分组的重传在发送方到接收方的信道中引入了**冗余分组**。冗余分组的根本困难在于接收方不知道它上次所发送的ACK或NAK是否被发送方正确地收到。因为它无法事先知道接收到的分组是新的还是一次重传。 解决这个问题的一个简单方法(几乎所有现有的传输协议中,包括TCP,都使用了这个方法)是在数据分组中添加一个字段,让发送方对其数据分组编号,即将发送数据分组的**序号**(sequence number)放在该字段。于是,接收方只需要检查序号即可确定收到的分组是否一次重传。 ## 可靠数据传输机制 GBN协议和SR协议都依赖了下表中的某些机制实现可靠数据传输: 机制|用途和说明 --|-- 校验和|用于检测在一个传输分组中的比特错误 定时器|用于超时/重传一个分组,可能因为该分组(或其ACK)在信道中丢失了。由于当一个分组延时但未丢失(过早超时),或当一个分组已被接收方收到当从接收方到发送方的ACK丢失时,可能产生超时事件,所以接收方可能会收到一个分组的多个冗余副本 序号|用于为从发送方流向接收方的数据分组按顺序编号。所接收分组的序号间的空隙可使接收方检测出丢失的分组。具有相同序号的分组可使接收方检测出一个分组的冗余副本 确认|接收方用于告诉发送方一个分组或一组分组已被正确地接收到了。确认报文通常携带着被确认的分组或多个分组的序号。确认可以是逐个的或累计的,这取决于协议的设计 否定确认|接收方可以告诉发送方某个分组未被正确地接收。否定确认报文通常携带着未被正确接收的分组的序号 窗口、流水线|发送方也许被限仅发送那些序号落在一个指定范围内的分组。通过允许一次发送多个分组但未被确认,发送方的利用率可在停止-等待操作模式的基础上得到增加 ## 停止-等待协议 **停止-等待协议**(Stop-and-Wait-protocol)是一个提供流量控制和差错控制的面向连接协议。 发送方和接收方都使用大小为1的滑动窗口。发送方在某一时刻发送一个分组,并且在发送下一个分组之前等待确认。为了发现被破坏分组,需要在每个数据分组中加入校验和。当一个分组到达接收端时,它就被检测。如果校验和不正确,分组就是被破坏分组,它将被接收端**静默丢弃**。 每当发送方发送一个分组时,它都开启一个定时器。如果在定时器超时之前接受到确认,那么定时器就被关闭并且发送下一个分组(如果有待发送分组)。如果定时器超时,发送方就认为分组丢失或被破坏(实际上也可能是响应丢失了),于是重传之前的分组。这意味着在确认到来之前,发送方需要存储分组的副本。 工作示意图如下:  ### 序号 协议使用序号和确认号来防止重复分组。一个字段被加入分组头部来保存分组的序号。假设发送端已经发送了带有序号x的分组,可能会发生以下几种情况: - 分组安全完整地到达接收端;接收方发送一个确认。确认到达发送端,使发送端发送下一个序号为x+1的分组。 - 分组被破坏或未到达接收端;发送方在超时后重新发送分组(序号x)。接收方返回一个确认。 - 分组安全完整地到达接收端;接收方发送一个确认,但是确认被破坏或丢失了。发送方在超时后重传分组(序号x)。 由以上几种情况可见,仅仅需要序号x和x+1,因此,若令x=0,则序号将为0,1,0,1····,这称为模2运算。停止等待协议使用1比特大小的序号字段即可。由于分组序号在0和1之间交替,该协议有时候被称为**比特交替协议**(alternating-bit protocol)。 ### 确认号 由于序号必须适合于数据分组和确认,确认号总声明为接收方预期接收的**下一个分组**(next packet expected)序号。例如,如果0号分组已经完全完整地到达,接收方发送一个确认号为1的ACK。如果1号分组已经安全完整到达,接收方发送一个确认号为0的ACK。 > 在停止-等待协议中,确认号总是以模2运算的方式声明预期接收的下一个分组序号。 ### 效率 当信道有很大的带宽(高数据速率)和往返时间很长时,停止-等待协议将非常低效。其中,将带宽和往返时间的乘积称为**带宽延迟乘积**(bandwidth-delay product),单位为bit。 ### 流水线 在之前的任务结束前,一个新任务开始了,这称为**流水线**(pipeline)。在停止-等待协议中没有流水线,因为发送端必须等待分组到达目的地,并且在下一个分组发送前接收到确认。 ### 评价 当分组进入链路所需的时间远远小于端系统之间的往返传播时延时,停止-等待协议的效率极端低下。如对于1000字节大小的分组、1Gbps的链路而言,信道的利用率大约为0.00027!这就是说,发送方只有万分之2.7时间是忙的。从其他角度看,有效的吞吐量仅为267kbps,即使有1Gbps的链路可用! 这是一个形象的网络协议限制底层网络硬件所提供的能力的示例。而且,我们还忽略了在发送方和接收方的底层协议处理时间,以及可能出现在发送方与接收方之间的任何中间路由器上的处理与排队时延。考虑到这些因素,将进一步增加时延,使其性能更糟糕。 ## 回退N步协议 **回退N步协议**(Go-Back-N,GBN)在接收到确认之前,可以发送多个分组,但它受限于在流水线中未确认的分组数不能超过某个最大允许数N。N被称为**窗口长度**(windows size),因此GBN协议也常被称为**滑动窗口协议**(sliding-windows protocol)。限制窗口大小的原因之一是需要流量控制。 工作示意图如下:  传输过程示意图如下:  ### 序号 序号是模$2^m$的,m是序号字段的大小,单位是比特。 ### 确认号 在回退N步协议中,确认号是积累的并且定义了预期接收的下一个分组序号。 例如,如果确认号是7,意味着序号在7以内的分组都已经安全完整到达,并且接收方等待序号为7的分组。 ### 窗口 #### 发送窗口 发送窗口是一种抽象概念,它定义了一个最大为$2^m-1$的盒子,其中有三个变量: - $S_f$:第一个未完成数组 - $S_n$:下一个待发送分组 - $S_{size}$:窗口大小 在任何时候,发送窗口都可能在序号分成四部分: |序号分组|说明| |--| |已经确认的分组序号|发送方不再关注这些序号且不需要保存它们的副本。| |已发送但未收到ACK的分组序号|发送方需要等待,从而发现这些分组是已经被接收还是丢失。这些分组称为未完成(outstanding)分组。| |可以发送的分组序号|这部分的分组还没有从应用层接收到,属于空槽。| |不能使用的分组序号|这部分序号已经在前面3部分中使用,添加该部分是为了提高可读性。| 示意图如下:  #### 接收窗口 接收窗口是一个抽象概念,它定义了一个大小最大为1的想象的盒子,其中只有一个变量$R_n$。当正确分组到来时,窗口滑动;窗口每次只滑动一个槽。 示意图如下:  #### 窗口大小 在回退N步协议中,发送窗口的大小必须小于$2^m$;接收窗口大小总是为1。 ### 定时器 尽管每个被发送分组都有定时器,但它们都共用一个,因为第一个未完成的分组的定时器总是最先终止。 ### 重传分组 当这个定时器终止时,重传所有未完成分组。例如,假设发送方已经发送了分组6($S_n=7$),但是唯一的定时器终止了。如果$S_f=3$,意味着分组3,4,5和6还没有被确认,发送方回退并重传分组3,4,5和6。这就是为什么这个协议被称为回退N步。一旦超时,机器回退N个位置并重传所有分组。 ### 评价 回退N步协议简化了接收方的进程。接收方只记录一个变量,没有必要缓冲失序分组:它们被简单地丢弃。同时,它潜在地允许发送方用多个分组“填充流水线”,因此避免了停止等待协议中所提到的信道利用率问题。然而,GBN本身也有着一些情况存在着性能问题。 当窗口长度和带宽延迟都很大时,特别是流水线中有很多分组时,单个分组就能够引起GBN重传大量分组,而许多分组根本没有必要重传。每当一个分组丢失或被破坏,发送方要重新发送所有未确认的分组,即使有些失序分组已经被安全完整地接收了。随着信道差错率的提高,流水线可能会被这些不必要重传的分组所充斥。如果网络层由于网络拥塞,丢失了很多分组,那么重传所有这些未完成分组将会使拥塞更严重,最终导致更多分组丢失。这具有雪崩效应,可能导致网络全部瘫痪。 ## 选择重传协议 **选择重传协议**(Selective-Repeat protocol,SR protocol)只是选择性地重传分组,即那些确实丢失的分组,从而避免了不必要的重传。这种个别的、按需的重传要求接收方逐个地确认正确接收的分组。 工作示意图如下:  ### 窗口 选择重传协议也使用两个窗口:一个发送窗口和一个接收窗口。然而,与回退N步协议有所不同。 当窗口长度比序号空间小1时,SR协议无法工作。因为在这种情况下模运算得出的结果(即有一个分组的序号与第一个分组的序号重叠)使得接收方将无法区分某分组是第一个分组的重传还是一次初次传输。 对于SR协议而言,窗口长度必须小于或等于序号空间大小的一半。道理与上面提到的是相同的。假如序号空间总大为 4,那么 4 之后会从 0 循环开始。当窗口大小大于序号空间的一半时,就有可能会出现接收方接收到一个分组但无法判断该分组是一个新的分组或是一个重传分组。 #### 发送窗口 发送窗口的最大值为$2^{m-1}$,即序号空间的一半。 #### 接收窗口 接收窗口的大小和发送窗口等大,最大值为$2^{m-1}$。选择重传协议允许和接收窗口一样多的分组失序到来并被存储,直到有一组连续分组被传递到应用层。因为发送窗口和接收窗口的大小是相同的,在发送窗口的所有分组可以失序到达并被存储,直到它们可以被传递。 发送窗口和接收窗口的工作示意图如下:  ### 定时器 理论上讲,选择重传协议为每个未完成分组使用一个独立的定时器,因为超时发生后只能发送一个分组。当一个定时器终止,只有一个相应分组被发送。然而,绝大多数实现了SR的传输层协议只使用一个定时器。可以使用单个硬件定时器模拟多个逻辑定时器的操作。 ### 确认 在GBN中ackNo是累计的,它定义了下一个预期分组的序号,确认了之前的分组都安全完整地到达。但是在SR中,ackNo定义了被安全完整接收的一个分组,对其他分组没有反馈信息。 在选择重传协议中,确认号定义了已被接收的无错分组的序号。 ## 双向协议:捎带 在现实生活中,数据分组通常是双向流动的:从客户端到服务器以及从服务器到客户端。这意味着确认也需要沿着两个方向流动。 **捎带**(piggybacking)技术被用来提高双向协议的效率:当一个分组携带数据从A到B时,它也携带了确认反馈,这些信息确认了来自B的分组已到达;同理,当一个分组携带数据从B到A时,它也携带了确认反馈,这些信息确认了来自A的分组已到达。 ## References - JamesF.Kurose, KeithW.Ross, 库罗斯,等. 计算机网络:自顶向下方法[M]. 高等教育出版社, 2009. - 谢希仁. 计算机网络.第6版[M]. 电子工业出版社, 2013. 赏 Wechat Pay Alipay swap() 操作的实现讨论 代理模式