拥塞处理相关的介绍
滑动窗口用来做流量控制,可以防止发送端向接受端发送过多的数据,但是它只关注了 发送端 和 接收端 自身的状况,而没有考虑整个网络的通信状况。
网络不好的情况一直丢包重传怎么办???
拥塞处理涉及的主要算法
- 慢启动
- 拥塞避免
- 快速重传 和 快速恢复
为了实现上面的算法,TCP的每条连接都有两个核心状态值:
- 拥塞窗口 (Congestion Window,cwnd)
- 慢启动阈值 (Slow Start Threshold)
拥塞窗口
拥塞窗口指的是收到对端 ACK 之前自己还能传输最大的MSS段数。
拥塞窗口初始化的大小是由操作系统的一个变量 initcwnd 控制,最新的 Linux 系统的默认值是10。
接收窗口与拥塞窗口的区别:
- 接收窗口是接受端的限制,是接受端还能接受的数据量大小。
- 拥塞窗口是发送端的限制,是发送端在未收到对端ACK之前还能发送的数据量大小。
真正的发送窗口大小 = min(接收端接受窗口大小,发送端拥塞窗口大小)
if(接受窗口 < 拥塞窗口){
接收端处理能力不够。
}else{
接收端处理能力够,但网络拥塞。
}
拥塞控制算法的本质是控制拥塞窗口的变化。
拥塞控制是从整个网络的大局观来思考的,如果没有拥塞控制,某一时刻网络的时延增加、丢包频繁,发送端疯狂重传,会造成网络更重的负担,而更重的负担会造成更多的时延和丢包,形成雪崩的网络风暴。
RTT(Round-Trip Time),往返时延。在计算机网络中它是一个重要的性能指标,表示从发送端发送数据开始,到发送端收到来自接收端的确认(接收端收到数据后便立即发送确认),总共经历的时延。
慢启动
最开始拥塞窗口很小,随着时间的推移,在每次发送的数据量如果不丢包的情况下,拥塞窗口会慢慢增长。
慢启动阈值
if cwnd < ssthresh(慢启动阈值) ,拥塞窗口按照指数级别增长(慢启动)
if cwnd > ssthresh(慢启动阈值),拥塞窗口按照线性增长(拥塞避免)
拥塞避免与慢启动的区别:
- 慢启动是在RTT时间内,每收到一个ACK,拥塞窗口 cwnd 就加1 , 也就是每个经过 1 个RTT cwnd 翻倍。
- 拥塞避免是在每经过一个RTT才将拥塞窗口加1,不管期间收到多少个ACK。
快速重传
当接收端收到一个不按序到达的数据段时,TCP 立刻发送 1 个重复 ACK,而不用等有数据捎带确认,当发送端收到 3 个或以上重复 ACK,就意识到之前发的包可能丢了,于是马上进行重传,不用等到重传定时器超时再重传。