TCP拥塞控制

在这里插入图片描述

什么是拥塞控制

流量控制是为了避免发送发的数据塞满接收方的缓存。但并不知道网络中发生了什么。
设想一下,假如网络发生了拥塞,如果继续发送大量的数据时,会造成数据包延时、丢失等。这时TCP就会重传数据,但是重传会导致网络负担更重,于是会导致更大的延迟以及更多的丢包,这个情况就进入了恶性循环并不断放大。
拥塞控制的目的就是避免发送方的数据填满整个网络

为了在发送方发送数据的量,定义一个拥塞窗口的概念。
拥塞窗⼝ cwnd是发送⽅维护的⼀个的状态变量,它会根据⽹络的拥塞程度动态变化的

我们在前⾯提到过发送窗⼝ swnd 和接收窗⼝ rwnd 是约等于的关系,那么由于加⼊了拥塞窗⼝的概念后,此时发送窗⼝的值是swnd = min(cwnd, rwnd),也就是拥塞窗⼝和接收窗⼝中的最⼩值。

拥塞窗口cwnd的变化规律是:

  • 只要网络中没有出现拥塞,cwnd就会增大
  • 网络中出现拥塞,cwnd就减少。

如何判断当前网络出现拥塞?
只要发送方没有在规定的时间内收到ack,也就是发生了超时重传就认为是网络中出现了拥塞。

拥塞控制的方法

拥塞控制的四个算法:

  • 慢启动
  • 拥塞避免
  • 拥塞发生
  • 快速恢复

慢启动

TCP在刚建立连接的时候就有一个慢启动的过程。防止一启动就产生网络拥塞。慢启动的意思就是一点一点的提高发送数据包的量。
慢启动的规则:发送端每接收到一个ACK包,拥塞窗口cwnd的大小就会加1.

假定拥塞窗口cwnd和发送窗口swnd大小一样,举个例子:

  • 建立连接完成后,一开始初始化cwmd=1,表示可以发送一个MSS大小的数据。
  • 当收到ack应答后,cwnd增加1,于是一次可以发送2个MSS大小的数据。
  • 当收到2个ACK应答后,cwnd增加2,于是一次可以发送4个MSS大小的数据。
  • 当收到4个ACK应答后,cwnd增加4,于是一次可以发送8个MSS大小的数据。

可见,慢启动时cwnd的增加是以指数的形式增长的。
在这里插入图片描述
那么cwnd增长到什么时候是个头啊?
有个叫做慢启动门限的状态变量ssthresh(slow start threshold)

  • 当cwnd<ssthresh时,使用慢启动算法
  • 当cwnd >= ssthresh时,就会使用拥塞避免算法。

拥塞避免算法

一般来说ssthresh的大小是65536字节。
那么就如拥塞避免算法时,cwnd的增长规则是,每收到一个ack时,cwnd增长1/cwnd。
接着上面的慢启动的例子,这里设置ssthresh为8,举例:

  • 当8个ACK应答确认到来时,每个确认增加1/8,8个ACK增加1,于是这一次可以发送9个MSS大小的数据,变成了线性增长
    在这里插入图片描述
    由此看出,拥塞避免算法是将慢启动算法的拥塞窗口增长速度由指数增长变成了线性增长,但是总体来说还是增长阶段,就是增长的缓慢了点。

就这么一直增长着后,网络慢慢进入到了拥塞的状态了,于是就出现了丢包的现象,这时候就出现了对数据包的重传。
当触发了重传机制,也进入了拥塞发生算法。

拥塞发生算法

当网络出现拥塞,也就是会发生数据的重传,重传机制主要有2种,

  • 超时重传
  • 快速重传
    这两种使用的拥塞发生算法是不同的,所以需要分别说明。
  1. 发生超时重传的拥塞发生算法。
    当发生超时重传会进入到拥塞发生算法。
    这时候ssthresh和cwnd的值发生变化
  • ssthresh设置为2/cwnd
  • cwnd重置为1
    接着重新进入到慢启动算法。慢启动是会突然减少数据流的,也就是一旦发生了超时重传那就相当于一下回到了解放前。这种方式太激进了,反应太激烈容易造成网络卡顿。
    在这里插入图片描述
  1. 发生快速重传的拥塞发生算法
    当接收⽅发现丢了⼀个中间包的时候,发送三次前⼀个包的ACK,于是发送端就会快速地重传,不必等待超时再重传。
    TCP 认为这种情况不严重,因为⼤部分没丢,只丢了⼀⼩部分,则 ssthresh 和 cwnd 变化如下:
  • cwnd = cwnd/2,也就是设置为之前的一半。
  • ssthresh = cwnd;
  • 进入快速恢复算法

快速恢复

快速恢复算法认为,既然还能收到3个重复的ACK说明网络也没有那么差。所有没有必要像超时重传时那么激烈。
像前面所说的,进入快速恢复之前cwnd和ssthresh已经更新了:

  • cwnd = cwnd/2,也就是设置为之前的一半。
  • ssthresh = cwnd;

然后进入快速恢复算法:
在这里插入图片描述

  • 拥塞窗⼝ cwnd = ssthresh + 3 ( 3 的意思是确认有 3 个数据包被收到了);
  • 重传丢失的数据包;
  • 如果再收到重复的 ACK,那么 cwnd 增加 1;
  • 如果收到新数据的 ACK 后,把 cwnd 设置为第⼀步中的 ssthresh 的值,原因是该 ACK 确认了新的数据,说明从 duplicated ACK 时的数据都已收到,该恢复过程已经结束,可以回到恢复之前的状态了,也即再次进⼊拥塞避免状态;

也就是没有像「超时重传」⼀夜回到解放前,⽽是还在⽐较⾼的值,后续呈线性增⻓。

拥塞算法示意图

在这里插入图片描述
参考:《图解网络–小林coding》

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值