no image

TCPの再送時間について

1. TCPの再送制御

TCPの機能にはフロー制御、順序保証、再送制御などがあります。
再送制御では、システムの障害時やパケットの消失時などにパケットの再送を制御しています。再送は一般的には複数回実施され、回数を重ねる毎に再送間隔が広がっていきます。
ネットワークの設計では迂回時間60秒以内などとしているところもありますが、具体的に障害が発生してから何秒後のタイミングで救われるのか計算してみます。

2. TCPの再送時間の計算式と取り得る時間

TCPの再送時間の計算式はOS毎に設定されています。今回はLinux/HP-UXで確認します。

利用システムのバージョンに寄っても変更される可能性がありますが、確認したシステムのHP-UXではRFC2988、LinuxではRFC6298に準拠していました。

RFC6298を確認すると、TCPの再送時間は以下の式により計算され、最小値が1秒、最大値60秒とすべきと規定されています。以下に確認したルールを記載しますが、実装は各OSごとに異なります。

  1. RTT(ラウンドトリップタイム)の計測RTO(再送タイムアウト)には1秒を設定する。(RFC2988では3秒)
  2. 初回のRTTは以下の計算式に従う
    RTO = SRTT + max(G, K * RTTVAR)
    RTTVAR = R / 2 SRTT = R (初回パケットのRTT) K = 4 (G:Clock Granularity(クロック粒度)の事でハードウェアとカーネルバージョンに依存する。参考URL)

    実際には以下の条件より値が小さくなると考えられるが、以下の条件でもRTOは最小値である1秒となる。

    <前提条件>
    ・ Gはkernel2.6のHZが100なので、0.01とする。
    ・ 初回パケットのRTTが300msと仮定し、Rは0.3とする。
    <計算>
     RTO = 0.3 + max(0.01 , 4 * 0.3 / 2)) = 1
      *RTOは0.9となるが1以下は1に繰り上げする。
  3. 2回目以降のRTTの計算には以下のRTTVARとSRTTを計算式に用いる。つまり遅延に大きな揺らぎが無ければ、RTOは更新されません。
    RTTVAR = (1 - beta) * RTTVAR + beta * |SRTT - R'|
    SRTT = (1 - alpha) * SRTT + alpha * R'
    beta = 1/4 = 0.25
    alpha = 1/8 = 0.125
  4. 再送タイマが期限切れになると、再送信の上、新たなRTOを設定する。設定するRTOは現在のRTO値の2倍である。
    RTO = RTO * 2
  5. RTOの最大値は60である。60秒を超える場合は新たなRTOとして60を設定すべきである。

3. TCPの再送時間

3.1. TCPの再送時間(Linux)

Linuxではtcp.hというファイルでRTOの設定をしており、確認する事ができます。Linux 2.6以上のカーネルの場合は、ここも参照

項目 設定 初期値(秒)
最大値 TCP_RTO_MAX 120
最小値 TCP_RTO_MIN 0.2
初期値 TCP_TIMEOUT_INIT 1

実際に初期値である0.2秒から再送を始めた場合は、最初のパケットが送信されてから以下の秒数ACKの返信が無ければ、再送を行います。

再送回数
(回)
RTO設定値
(秒)
タイムアウト(最初のパケットが
送信された時点からの合計秒数)
0(初回送信) 0.2 0.2
1(初回再送) 0.4 0.6
2 0.8 1.4
3 1.6 3.0
4 3.2 6.2
5 6.4 12.6
6 12.8 25.4
7 25.6 51.0
8 51.2 102.2

上記を確認すれば分かりますが、再送回数を重ねる毎に再送間隔は拡大していきます。上位のアプリケーションタイマが60秒であった場合、最初のパケットが送信されてから51秒後に送信される再送7回目のパケットに対する応答が無ければ、TCPタイムアウトが発生します。

3.2. TCPの再送時間(Windows)

Windows7/Server2008 R2の場合はこのページにSYNの再送時間に関する情報があります。

TCP確立後はこのページが参考になります。基本はRFC793に準拠とありますが、初期値であるRTO設定値が3の場合は以下のようになり、RTO設定値が1の場合は「3.1. TCPの再送時間(Linux)」と同等となると想定されます。

再送回数
(回)
RTO設定値
(秒)
タイムアウト(最初のパケットが
送信された時点からの合計秒数)
0(初回送信) 3 3
1(初回再送) 6 9
2 12 21
3 24 45
4 48 93
5 96 189