TCP拥塞发生时流量速率未达预期的实验疑问求助
理解TCP拥塞控制在带宽限制后的行为
首先,咱们先澄清几个关键误解,再拆解你看到的现象:
1. 慢启动不是“只要拥塞就触发”
慢启动(Slow Start)只在两种场景下激活:
- TCP连接刚建立的初期
- 发生超时丢包(不是轻微延迟或者少量丢包)时
你的实验中,TCP连接已经稳定运行了一段时间(在你用tc限速之前,流量已经跑了10秒左右),此时TCP处于**拥塞避免(Congestion Avoidance)**阶段,而不是慢启动阶段。当你突然限制带宽时,只要没有触发超时丢包,TCP不会直接回到慢启动的初始窗口(通常是1-2个MSS)。
2. TC TBF的行为导致初期速率未下降
你用的是TBF(Token Bucket Filter)做限速,参数是rate 40mbit latency 10ms burst 1mbit:
burst 1mbit允许短时间内发送超过rate限制的流量(令牌桶的“突发”容量),所以前几秒你的流量还能维持接近70Mbps的速率——因为令牌桶里还有储备的令牌可以消耗。latency 10ms设置了队列的最大延迟,只有当队列满了之后,TBF才会开始丢包。在队列填满之前,数据包只是被延迟发送,不会被丢弃,TCP只会检测到RTT(往返时间)增加,而不是丢包。
3. TCP如何适应新的带宽限制
当令牌桶的储备耗尽,队列开始积累,RTT持续增加,TCP的拥塞控制机制(比如CUBIC,Linux默认的拥塞算法)会通过**平缓调整拥塞窗口(cwnd)**来适应新的带宽,而不是直接把速率减半:
- 没有丢包的情况下,TCP不会触发“乘法减小”(比如
cwnd = cwnd/2),而是通过观察RTT的变化,逐步降低发送速率,直到达到新的平衡点——也就是你看到的38-40Mbps(接近TBF的rate限制)。 - 最后稳定在40Mbps左右,是因为TBF的
rate限制了长期的平均速率,TCP的拥塞窗口也调整到了刚好匹配这个速率的大小。
4. iperf3的-b参数的作用
iperf3的-b 70M是应用层的速率限制,它的逻辑是“尽量发送到这个速率,但不超过TCP窗口允许的范围”。当TCP因为带宽限制导致窗口变小,iperf3自然无法发送到70Mbps,只能跟着TCP的窗口调整实际发送速率——这和你看源码得到的结论一致,它确实不会干扰TCP本身的拥塞控制算法。
验证建议
如果你想看到慢启动的效果,可以试试:
- 在设置TC限速之后,重新建立一个新的iperf3连接(而不是在已有连接上调整),此时新连接会从慢启动开始,你就能看到速率从低到高增长,直到触碰到40Mbps的限制。
- 把TBF的
burst调小(比如burst 100kbit),减少突发容量,这样初期的速率会更快降到40Mbps左右。
内容的提问来源于stack exchange,提问作者nimdrak
相关产品推荐
相关产品推荐

