嗯,确实还真有人看了我在雨夜写的上一篇文章:
BBR的startup gain为什么是2/ln2?:https://blog.csdn.net/dog250/article/details/80660091
并且提出了问题。我就再写一篇文字解释一下这些问题。
问题1: 对 求导怎么会是
问题2:如果能用 同时表示速率和BDP,那么对速率积分所得的BDP为什么会比 多出来一个 因子呢?
先来看第一个问题,这个是温州皮鞋厂老板在问我为什么bbr_high_gain是 的时候他自己算出来的,很显然他算错了,至于为什么错,这要问老板,可能是求导公式记错了,但毕竟思路是对的,老板记成了二项式的求导,比如 这种。
长期不用这些公式,谁都会忘,熟记它们毫无意义,紧急用到了现查,不紧急又查不到就用连续性和求极限原理现推导都可以,我的观点就是原理一定要明白,必要时自己能算,公式本身背下来没有意义,大脑的存储空间分为两种用途,一部分是暂时记忆计算的中间过程的,类似寄存器,另一种用途则是记忆生活的,比如某段刻骨铭心的经历或者让你难忘的某个人的音容笑貌,纯粹去记公式或者背诵课文,除了应对该死的考试,毫无意义。
第一个问题回到到此。
来看第二个问题,这个问题比较有意思。
首先你要先明白并且承认,我们可以用以下两种方式表示BDP:
- BDP随着RTT指数倍增,因此使用 表示BDP
- 速率随着RTT指数倍增,速率也可表示为 ,因此 可以表示BDP
现在,矛盾来了,我们注意到两种方式表示的BDP并不相等!
它们之间差了一个 因子!这是为什么??
答案就是BBR试图要回答的:用平滑的曲线去拟合平滑的而不是离散的发送过程,进而求出bbr_high_gain。
我这里形象的用图示解释一下。
我们把TCP BBR在startup阶段发送的数据包想象成一个连续不断向前走的东西,至于什么东西,都可以,可以是汽车,也可以是火车。很显然,发送的速率不断增加,相邻数据包是时间上的间隔会不断缩短,对于第一个表达BDP的式子,它就像下图这样,我用颜色深浅表示发送速率,颜色越深,速率越低:
这像什么?这像越来越快发射的子弹,也像一个城市的一条路上进入早高峰的过程。我们数数看一共多少个包,嗯,是6个,没错,这时的BDP就是6。
那么如果用速率进行积分的话,会是一种什么样的场景呢?我们知道,积分是在一个连续函数上进行的,因此它的样子应该是下面的这样:
这像什么?感觉有点像人留下来的长鼻涕,开始的时候很慢,随着越拉越长,在重力作用下其下端会加速坠落,同时一直到鼻孔处全部黏在一起而不断…
看看这时的BDP怎么算,非常显然,这么一长条除以MSS即是以数据包个数计数的BDP。由于其连续性,填补了直接用 计数数据包时的离散空隙,多出来的那部分就是用因子 来增益的。
BBR算法正是用后面的这个连续函数的积分来计算针对上一个RTT时BDP的增益的,因此便有了:
由这个式子直接可以导出 ,非常直接,以一个确定性的上个RTT周期的 为锚点,求出连续情况下增益为多少,才能达到当前的BDP。
类似的,你也会发现,用BDP的表达式 求导数计算速率时,也会遇到相同的问题,也是连续和离散的问题。这个时候,计算出来的导函数为 ,显然是比 更小,这是因为求导是在连续函数上进行的,因此为了求导,你必须把离散的数据包压缩在一起,必然要缩短总距离:
好了,解释完了,至于说为什么一定要用连续函数来计算bbr_high_gain,纯粹是因为这样算出来的值会更加平滑,因为如果你直接使用曲线 中的增益 ,那么相当于你默认了一个约束,即每到一个RTT倍数的准点,你的PacingRate即速率将会面临一次翻倍,然而具体实现当中,这个约束很难满足,BBR的实现可以看出,其PacingRate的计算是实时的,所得到的结果是一个即时的正确的速率,并没有受到RTT的约束。
既然BBR要以测量而不是假设为准,那么算法执行地越平滑越好。记不记得当初BIC进化到CUBIC的时候,就是去除了RTT的约束,最终CUBIC放弃了BIC二分折线,CUBIC拟合了一条平滑的三次曲线,与RTT彻底无关了,从而解决了RTT公平性问题!唉,日光之下,并无新事。明天将重播今天的故事…
浙江温州皮鞋湿!