不靠脉冲的负反馈。
BBR \text{BBR} BBR 依赖固定参数的 ProbeRTT \text{ProbeRTT} ProbeRTT 与 cwnd_gain=2 \text{cwnd\_gain=2} cwnd_gain=2 来控制 buffer \text{buffer} buffer,这并不是一种动力学的方案。先看一下标准的 BBR \text{BBR} BBR 仿真:

看上去不错,脉动锯齿很规整,脉动意味着反馈的灵敏度,没有持续堆积 buffer \text{buffer} buffer,但如果去掉 ProbeRTT \text{ProbeRTT} ProbeRTT, BBR \text{BBR} BBR 将会是:

很显然, buffer \text{buffer} buffer 会被 gain = 1.25 \text{gain}=1.25 gain=1.25 的阶段持续挤占,导致 RTT_min \text{RTT\_{min}} RTT_min 不断上升,从而 gain = 1.25 \text{gain}=1.25 gain=1.25 的阶段周期不断变宽,最终失去灵敏性。参见 bbr 对 buffer 的侵用。
如果再将 cwnd_gain=2 \text{cwnd\_gain=2} cwnd_gain=2 限制去掉, buffer \text{buffer} buffer 将随 BDP \text{BDP} BDP 快速跑飞。
gain = 1.25 \text{gain}=1.25 gain=1.25 阶段释放了更多的 inflight \text{inflight} inflight 就一定会挤出更高的带宽,在 buffer \text{buffer} buffer 动力学中,公平性就需要这种不停的 buffer \text{buffer} buffer 腾挪来获得,因此 gain = 0.75 \text{gain}=0.75 gain=0.75 阶段必须承认这些挤出来的带宽,否则将无法收敛。
这一点点在 gain = 1.25 \text{gain}=1.25 gain=1.25 阶段挤出的带宽与当时 RTT m i n \text{RTT}_{min} RTTmin 的乘积,就是不断增加的 buffer \text{buffer} buffer 占用,因此 BBR \text{BBR} BBR 必须依赖周期性的 ProbeRTT \text{ProbeRTT} ProbeRTT 与 cwnd_gain = 2 \text{cwnd\_gain}=2 cwnd_gain=2 硬限制来控制 buffer \text{buffer} buffer 的占用。
这种方法并不优雅,脏样本和脏数据叠加运算后的结果只能更脏。依靠周期性主动排空,远不如一个自适应的负反馈更稳定,更可扩展以及更优雅。
你得去度量 I = delivery_rate SRTT I=\dfrac{\text{delivery\_rate}}{\text{SRTT}} I=SRTTdelivery_rate 做综合判定,而不只是任意其中一个,因为它自带了带宽和时延的相互作用,而 I I I 值的统计分布在一个固定的网络是确定的,我们也不必管它是正态还是指数,哪怕它是发散的, S S S 曲线的参数甚至一个简单的单调函数足以收住它,网络本身就是统计动力学的,稳定性,公平性,扩展性,自适应性,尺度不变性大于一切。
我并没有基于 " I I I 不再增加" 来替换 bbr_is_next_cycle_phase \text{bbr\_is\_next\_cycle\_phase} bbr_is_next_cycle_phase 里的 " delivery_rate \text{delivery\_rate} delivery_rate 判定",因为这可能会退掉 buffer \text{buffer} buffer 中挤出的虚高带宽而影响公平收敛,换句话说,不能直接用 I I I 做探测指标,因为要保留 buffer \text{buffer} buffer 腾挪的收敛动力学效果,只用它来矫正 gain \text{gain} gain.
直接替换 cwnd_gain \text{cwnd\_gain} cwnd_gain,将它化作 I I I 的函数,给出 ( 0.1 , 2 ] (0.1,2] (0.1,2] 的界定,在 I I I 高时为 2 2 2, I I I 很低时维持低 buffer \text{buffer} buffer 占用,基于不同网络调节区间下界。在此自适应收敛机制上,我关掉了 ProbeRTT \text{ProbeRTT} ProbeRTT。
设 win g \text{win}_g wing 为 cwnd_gain \text{cwnd\_gain} cwnd_gain,合成窗口上限增益:
win g = clip ( g b u f ( I i ) + Δ f a i r , i , g min , g max ) \text{win}g=\text{clip}(g{buf}(I_i)+\Delta_{\mathrm{fair},i}, g_{\min}, g_{\max}) wing=clip(gbuf(Ii)+Δfair,i,gmin,gmax)
其中 g b u f ( I i ) g_{buf}(I_i) gbuf(Ii) 为 buffer \text{buffer} buffer 本地控制器,只依赖 I I I,负责稳定队列延时 r r r,采用 I I I 的单调递增函数:
g b u f ( I i ) = 2 + k b ( I i − I r e f ) g_{buf}(I_i)=2+k_b(I_i−I_{ref}) gbuf(Ii)=2+kb(Ii−Iref)
排队延时 r r r 上升,速率高的流应当承担更大的削减量,采用和 AIMD \text{AIMD} AIMD 类似,无固定目标的增量调整规则,每一步给窗口上限附加一个衰减惩罚,惩罚强度正比于自身带宽:
Δ f a i r , i = − k f ⋅ x i \Delta_{\mathrm{fair},i}= -k_f \cdot x_i Δfair,i=−kf⋅xi
即带宽越大,每一步削减越多,速率低的流削减少,慢慢追上来,两条流博弈后自动均分。
以下就是一个尚未调参的仿真:
python
# -------- Buffer控制器参数 (I递增→增益递增;I_ref仅为缓冲区工作点,和公平份额无关) --------
I_ref = 7.0
k_buffer = 0.12
WIN_BUF_MIN = 1.0
WIN_BUF_MAX = 20.0
# -------- 分布式公平反馈:不需要预先知道流数目N、不需要公平带宽目标 --------
k_fair = 0.07

即使关掉了 ProbeRTT \text{ProbeRTT} ProbeRTT,依然完美收敛。
在同一个网络中, I I I 的最佳值符合确定的分布,基于这些分布调参就是一个完美的端到端传输网络。
- 带宽若振荡,发散,则减小公平反馈强度 k_fair \text{k\_fair} k_fair;
- 收敛慢,带宽差距长期存在,则适度增大 k_fair \text{k\_fair} k_fair;
- r r r 震荡剧烈,则减小 k_buffer \text{k\_buffer} k_buffer;
- 若 ProbeBW \text{ProbeBW} ProbeBW 周期性脉冲经常旁路 win g \text{win}_g wing 上限,可将公平反馈项从窗口上限叠加到 pacing_gain \text{pacing\_gain} pacing_gain;
这只是一个最简单的想法,涉及到确定网络所有流 I I I 最佳值随 N N N 的波动,统计特征,从数学上分析,上述 win g \text{win}_g wing 的公平点并非唯一的平衡点,系统存在一大族不公平的不动点。
再看 win g \text{win}_g wing 表达式:
w i n g = g b u f ( I i ) − k f x i \mathrm{win}g = g{\mathrm{buf}}(I_i)-k_f\,x_i wing=gbuf(Ii)−kfxi
g b u f ( I ) g_{\mathrm{buf}}(I) gbuf(I) 随 I I I 上升而上升的递增项,它会补偿掉 − k f x i -k_f x_i −kfxi 的公平力,当 k b / r ≈ k f k_b/r \approx k_f kb/r≈kf,公平校正力归零,系统变成中性,带宽可停在任意分配。因此需换一条非线性惩罚曲线,让高带宽流受到的惩罚加速变大,破坏中性条件。
如以下均为可选替代:
Δ f a i r , i = − k f ⋅ x i 2 \Delta_{\mathrm{fair},i}= -k_f \cdot x_i^2 Δfair,i=−kf⋅xi2
它的不动点条件的解有唯二两个,其中一个是公平解,另一个伪稳态解为 k b r = k f ( x 1 + x 2 ) \dfrac{k_b}{r}=k_f(x_1+x_2) rkb=kf(x1+x2),可见伪稳态被一条双曲线约束,不再允许全部带宽组合。
不公平范围被压缩,带宽差距不会无限拉大,不会出现严重饥饿现象,这就是近似公平,即偏差存在但有上界。在统计公平的系统中,这是可接受的。
同理,公平项也可以跟着 I I I 走:
w i n g , i = c l i p ( g b u f ( I i ) − k f ⋅ I i α , g min , g max ) \mathrm{win}{g,i}= \mathrm{clip}\Big(\;g{\mathrm{buf}}(I_i)-k_f \cdot I_i^\alpha,\;g_{\min},\,g_{\max}\Big) wing,i=clip(gbuf(Ii)−kf⋅Iiα,gmin,gmax)
取 α > 1 \alpha>1 α>1,如 α = 2 \alpha=2 α=2。
裤衩子锁着边儿,而且绣着花儿。
我这是在做一个稳定的系统,而不是在优化这个系统中的一条流。有空再来讲讲关于多发选收的笑话。
浙江温州皮鞋湿,下雨进水不会胖。