一、概念
RTT:往返时延。
RTO:就是tcp发送一个数据包后,会启动一个重传定时器,RTO就是这个定时器的重传时间。
由于RTO是指这次发送当前数据包所预估超时时间,那么RTO就需要一个很好的统计方法,来更好的预测这次的超时时间。
SRTT:smoothed tound-trip time
RTTVAR:round-trip time variation
二、我们能想到的计算方法(取平均数)
比如第一次RTT是500毫秒,第二次是800毫秒,那么第三次发送的时候,RTO就应该是650毫秒。
三、RFC793计算方法
和取平均数类似。
3.1 方法
SRTT = ( ALPHA * SRTT ) + ( ( 1-ALPHA ) * RTT )
RTO = min [ UBOUND, max [ LBOUND, ( BETA * SRTT ) ] ]
3.2 参数意义
UBOUND是RTO的最大值;
LBOUND是RTO的最小值;
ALPHA取值是0.8~0.9;
BETA取值是1.3~2.0。
RFC793:http://tools.ietf.org/html/rfc793
四、paper《Congestion Avoidance and Control》计算方法
和RFC793相比增加了均差(mean deviation)。
4.1 方法
Err ≡ m−a
a ← a + gErr
v ← v + g(|Err|−v)
4.2 参数意义
m是RTT;
a是SRTT;
v是均差;
g是一个因子。
4.3 方法变化
由于g的存在可能会出现浮点数,因此我们只需要做个变化让g=1/2^n,那么上面等式就变为了下面这个:
2^na ← 2^na + Err
2^nv ← 2^nv + g(|Err|−v)
4.4 伪代码
/∗ update Average estimator ∗/
m −= (sa >> 3);
sa += m;
/∗ update Deviation estimator ∗/
if (m < 0)
m = −m;
m −= (sv >> 2);
sv += m;
rto = (sa >> 3) + sv;
paper《Congestion Avoidance and Control》:http://ee.lbl.gov/papers/congavoid.pdf
五、RFC6298计算方法
5.1 计算方法
第一个RTT时:
SRTT <- R
RTTVAR <- R/2
RTO <- SRTT + max (G, K*RTTVAR)
后续RTT时:
RTTVAR <- (1 - beta) * RTTVAR + beta * |SRTT - R'|
SRTT <- (1 - alpha) * SRTT + alpha * R'
RTO <- SRTT + max (G, K*RTTVAR)
5.2 参数意义
R、R'是RTT;
alpha = 1/8;
beta = 1/4;
K = 4。
5.3 变化后的计算方法(该方式同上面的计算方式)
delta = RTT - SRTT
SRTT = SRTT + g * delta
rttvar = rttvar + h(|delta| - rttvar)
RTO = srtt + 4*rttvar
其中:
g = 1/8
h = 1/4
RFC6298:http://tools.ietf.org/html/rfc6298
六、一些计算RTO的开源实现
Linux内核中:net/ipv4/tcp_input.c tcp_rtt_estimator()
Unbound中:util/rtt.c
参考资料:
RFC793:http://tools.ietf.org/html/rfc793
paper《Congestion Avoidance and Control》:http://ee.lbl.gov/papers/congavoid.pdf
RFC6298:http://tools.ietf.org/html/rfc6298
tcp中RTO的计算以及linux下的实现:http://www.cnblogs.com/hfww/archive/2012/08/01/2618109.html
TCP可靠传输及流量控制系列三:重传时间RTO计算:http://zenhumany.blog.163.com/blog/static/1718066332010827104042708/