全网最强TCP/IP拥塞控制总结( 三 )


  • 拥塞时如何调整
拥塞发生时我们需要有一套应对措施来防止拥塞恶化并且恢复连接流量 , 这也是拥塞控制算法的精要所在 。
4.3 拥塞控制的细节前面我们提了拥塞控制的必要性以及重要问题 , 接下来一起看下前辈们是如何设计实现精彩的拥塞控制策略的吧!
4.3.1 拥塞窗口cwnd从流量控制可以知道接收方在header中给出了rwnd接收窗口大小 , 发送方不能自顾自地按照接收方的rwnd限制来发送数据 , 因为网络链路是复用的 , 需要考虑当前链路情况来确定数据量 , 这也是我们要提的另外一个变量cwnd , 笔者找了一个关于rwnd和cwnd的英文解释:
Congestion Window (cwnd) is a TCP state variable that limits the amount of data the TCP can send into the network before receiving an ACK.
The Receiver Window (rwnd) is a variable that advertises the amount of data that the destination side can receive.
Together, the two variables are used to regulate data flow in TCP connections, minimize congestion, and improve network performance.
笔者在rfc5681文档中也看到cwnd的定义:
全网最强TCP/IP拥塞控制总结

文章插图
 
这个解释指出了cwnd是在发送方维护的 , cwnd和rwnd并不冲突 , 发送方需要结合rwnd和cwnd两个变量来发送数据 , 如图所示:
全网最强TCP/IP拥塞控制总结

文章插图
 
cwnd的大小和MSS最大数据段有直接关系 , MSS是TCP报文段中的数据字段的最大长度 , 即MSS=TCP报文段长度-TCP首部长度 。
4.3.2 拥塞控制基本策略拥塞控制是一个动态的过程 , 它既要提高带宽利用率发送尽量多的数据又要避免网络拥堵丢包RTT增大等问题 , 基于这种高要求并不是单一策略可以搞定的 , 因此TCP的拥塞控制策略实际上是分阶段分策略的综合过程:
全网最强TCP/IP拥塞控制总结

文章插图
 
如图为典型的包含4个策略的拥塞控制:
全网最强TCP/IP拥塞控制总结

文章插图
 
如图为发生超时重传RTO时的过程:
全网最强TCP/IP拥塞控制总结

文章插图
 
4.4 拥塞控制过程详解我们以典型慢启动、拥塞避免、快速重传、快速恢复四个过程进行阐述 。
  • 慢启动
慢启动就是对于刚启动的网络连接 , 发送速度不是一步到位而是试探性增长 , 具体来说:连接最初建立时发送方初始化拥塞窗口cwnd为m , 之后发送方在一个RTT内每收到一个ACK数据包时cwnd线性自增1 , 发送方每经过一个RTT时间 , cwnd=cwnd*2指数增长 , 经过一段时间增长直到cwnd达到慢启动阈值ssthresh 。
之后cwnd不再呈指数增长从而进入拥塞避免阶段(注cwnd增长的单位是MSS) , 当然如果在慢启动阶段还未到达阈值ssthresh而出现丢包时进入快速重传等阶段 , 需要注意的是如果网络状况良好RTT时间很短 , 那么慢启动阶段将很快到达一个比较高的发送速率 , 所以将慢启动理解为试探启动更形象 。
全网最强TCP/IP拥塞控制总结

文章插图
 
  • 拥塞避免
当慢启动阶段cwnd的值到达ssthresh时就不再疯狂增长 , 进入更加理性的线性阶段直至发送丢包 , 本次的阈值ssthresh是上一次发生丢包时cwnd的1/2 , 因此这是一个承上启下的过程 。
本次发送丢包时仍然会调整ssthresh的值 , 具体拥塞避免增长过程:发送方每收到一个ACK数据包时将cwnd=cwnd+1/cwnd , 每经过一个RTT将cwnd自增1 。
  • 超时重传和快速重传
TCP作为一个可靠的协议面临的很大的问题就是丢包 , 丢包就要重传因此发送方需要根据接收方回复的ACK来确认是否丢包了 , 并且发送方在发送数据之后启动定时器 , 如图所示:
全网最强TCP/IP拥塞控制总结

文章插图
 
RTO是随着复杂网络环境而动态变化的 , 在拥塞控制中发生超时重传将会极大拉低cwnd , 如果网络状况并没有那么多糟糕 , 偶尔出现网络抖动造成丢包或者阻塞也非常常见 , 因此触发的慢启动将降低通信性能 , 故出现了快速重传机制 。


推荐阅读