一、TCP Reno拥塞控制算法回顾
二、基于TCP Reno拥塞控制算法的改进
改进原因分析
TCP Reno 提出的快速恢复算法提高了丢失报文后的吞吐量和顽健性,但是:
仅考虑了每次拥塞发生时只丢失一个报文的情形。
实际网络中,一旦发生拥塞,路由器会丢弃大量的报文,即一次拥塞中丢失多个报文的情形很普遍。
下图是Reno算法中快速恢复状态和拥塞避免状态之间的相互转换:
- 一次拥塞中丢失多个报文时若采用Reno算法:(TCP Reno收到新的 ACK就会结束快速恢复,进入拥塞避免阶段)
会多次将拥塞窗口(cwnd)和慢启动阈值(ssthresh)减半,造成TCP的发送速率呈指数降低系统吞吐量急剧下降,(当发送窗口小于3时)无足够的重复ACK可以触发快速恢复,只能等待超时重传。TCP Reno 终端会陷入仅通过传输超时来发现报文丢失的困境中。
- 超时对于TCP的效果有很大的影响:
- 若遗失的数据包无法使用Fast-Retransmit/ Fast-recovery重送,就必须等待超时来触发重送的机制,在等待超时的这段时间,TCP不能重送新的数据,使得链路的使用率很低;
- 超时之后,cwnd的值会被重设为1,大大较低了TCP的传输效果。
所以,网络在一次拥塞中丢弃了多个报文,被TCP Reno错误地分析为传输中发生了多次拥塞。过度的窗口减小导致了传输超时的发生。因此为了提高一次拥塞中丢弃多个报文情形下TCP的性能,必须使TCP终端减少盲目削减发送窗口的行为。
New Reno:基于Reno算法的改进
NewReno TCP在Reno TCP的基础上对快速恢复算法进行修改,只有一个数据包丢失的情况下,其机制和Reno是一样的;当同时有多个包丢失时就显示出了它的优势。
Reno快速恢复算法中发送方收到一个新的ACK就退出快速恢复状态,New Reno算法中只有当所有报文都被应答后才退出快速恢复状态。
NewReno TCP添加了恢复应答判断功能,以增强TCP终端通过ACK报文信息分析报文传输状况的能力。
使TCP终端可以把一次拥塞丢失多个报文的情形与多次拥塞的情形区分开来,进而在每一次拥塞发生后拥塞窗口仅减半一次,从而提高了TCP的顽健性和吞吐量。
两个概念:部分应答(PACK)、恢复应答(RACK)
记TCP发送端恢复阶段中接收到的ACK报文(非冗余ACK)为ACKx,记在接收到ACKx时TCP终端已发出的序列号(SN)最大的报文是PKTy,如果ACKx不是PKTy的应答报文,则称报文ACKx为部分应答(Partial ACK,简称PACK);若ACKx恰好是PKTy的应答报文则称报文ACKx为恢复应答(Recovery ACK,简称RACK)。
举例来理解:
如果4、5、6号包丢了,现在只重传4,只收到了4的ACK,后面的5、6没有确认,这就是部分应答Partial ACK。如果收到了6的ACK,则是恢复应答Recovery ACK。
TCP发送端接收到恢复应答表明:经过重传,TCP终端发送的所有报文都已经被接收端正确接收,网络已经从拥塞中恢复。
NewReno发送端在收到第一个Partial ACK时,并不会立即结束Fast-recovery,而会持续地重送Partial ACK之后的数据包,直到将所有遗失的数据包重送后才结束Fast-recovery。收到一个Partial ACK时,重传定时器就复位。这使得NewReno的发送端在网络有大量数据包遗失时不需等待Timeout就能更正此错误,减少大量数据包遗失对传输效果造成的影响。
NewReno大约每一个RTT时间可重传一个丢失的数据包,如果一个发送窗口有M个数据包丢失,TCP NewReno的快速恢复阶段将持续M个RTT。
改进的快速恢复算法具体步骤:
- 重新定义恢复阶段
- 进入恢复阶段后,发送端重传被认定为丢失的报文,设置慢启动阈值(ssthresh)和拥塞窗口大小(cwnd)。ssthresh = cwnd/2,cwnd = ssthresh + 3MSS。
- 收到一个重复ACK,cwnd=cwnd+MSS。
- 当收到PACK(部分应答)时,发送端重传PACK所确认报文的下一个报文,如果拥塞窗口允许,继续发送新的数据包。
- 当收到RACK(确认应答)时,发送端认为拥塞中所有被丢弃的报文都已经被重传,拥塞结束,设置cwnd=ssthresh并退出快速恢复状态。
快速恢复是基于数据包守恒的原则,即同一时刻能在网络中传输的数据包是恒定的,只有当旧数据包离开网络后,才能发送新数据包进入网络。一个重复ACK不仅意味着有一个包丢失了,还表示有发送的数据包离开了网络,已经在接收区的缓冲区中,不再占用网络资源,于是将拥塞窗口加一个数据包大小。
三、SACK算法
Reno和NewReno算法仍存在的问题?
虽然NewReno可以解决大量数据包遗失的问题,但是NewReno在每个RTT时间只能一个数据包遗失的错误。为了更有效地处理大量数据包遗失的问题,另一个解决方法就是让传送端知道哪些已经被接收端收到,但用此方法必须同时修改传送端和接收端的传送机制。
缺乏SACK算法时发送端只能选择两种恢复策略:
- 每一个RTT时间内至多重传一个丢弃的包 (Reno和New Reno)
- 重传所有包,其中包括可能已经正确发送的包。 (Tahoe)
TCP SACK在TCP Reno基础上增加了:
- 选择确认(Selective Acknowledgements,SACK)
- 选择重传(Selective Retransmission)
当一个窗口内有多个数据包丢失时:
- 接收端:在ACK中报告其接收到的不连续的报文,使发送方准确地知道哪些数据包被接收方正确接收。
- 发送端:使用选择重传机制,可以在一个窗口中一次重传所有从一个窗口中丢失的数据包。
减少了时延,提高了网络吞吐量,使更快地从拥塞状态恢复。
SACK中加入了一个SACK选项(TCP option field),允许接收端在返回Duplicate ACK时,将已经收到的数据区段(连续收到的数据范围)返回给发送端,数据区段与数据区段之间的间隔就是接收端没有收到的数据。发送端就知道哪些数据包已经收到,哪些该重传,因此SACK的发送端可以在一个RTT时间内重传多个数据包。
整个TCP选项长度不超过40字节,实际最多不超过4组边界值。
通过一个wireshark示例来说明接收端的SACK行为:
上图中ACK确认序列号为12421,SACK的块左边界值为13801,SACK的块右边界值为15181。明确了这三个参数的数值,我们基本上就可以计算出被丢弃的数据报的序列号和长度了。通过上图所示的带有SACK的数据报文,我们可以知道被丢弃的数据报文的TCP序列号为12422,其数据长度为13801-12421=1380B。
改进的快速恢复算法:
- pipe:TCP发送端发出的未被确认的数据报文数的估计值,网络中正在传输的分组数估计值;(决定了什么时候重传)
- scoreboard:发送端保存,记录从SACK选项中得知的未被确认的分组。(指出了哪些分组需要重传)
- 进入快速恢复阶段后,只有当pipe<cwnd时,发送端才发送新数据包或重传丢失数据包。
- 发送端每次新发送或重传一个数据包后,pipe=pipe+1;
发送端每收到一个重复的包含SACK选项的ACK包后(新的分组被接到),pipe=pipe-1; - 当发送端可以发送数据包时,重传scoreboard中指示的最后的数据包,如果计分板为空,则发送新的数据包;
- 当发送端收到PACK,pipe=pipe-2。因为PACK表示两个数据包离开了pipe,一个是丢失的数据包,一个是重传的数据包;
- 当发送端收到RACK后退出快速重传阶段。
【参考文献】:
吴文红,李向丽.TCP拥塞控制机制定量性能分析.计算机工程与应用.2008,44(18)
孙伟,温涛,冯自勤,郭权.基于TCP NewReno的稳态吞吐量分析模型.计算机研究与发展.2010
陈琳,双雪芹.TCP网络拥塞控制算法比较研究.长江大学学报.2010,3
许豫飞,TCP拥塞控制算法集齐性能评估.北京邮电大学.2005,3
刘拥民,年晓红.对SACK拥塞控制算法的研究.信息技术.2003,9
焦程波,窦睿彧,兰巨龙.无线网络中选择性重传机制性能分析与改进.计算机应用研究.2007.3
James F.Kurose,Keith W.Ross,Computer Networking A Top-Down Approach Sixth Edition.机械工业出版社
原文:https://blog.csdn.net/m0_38068229/article/details/80417503