スライディングウィンドウ
送信側が、受信側からの確認応答を待たずに続けて送れるデータの量(ウィンドウ)を決め、確認応答が届くたびにその範囲をずらしていく方式。TCPのフロー制御に使われる。
イマシルちゃんの解説
1つ送るたびに「届いた?」「届いたよ」ってやり取りしてたら、時間がかかって仕方ないよね。
そこでTCPは、「返事を待たずに、ここまでは続けて送っていいよ」っていう枠(ウィンドウ)を決めるんだ。
返事が届いたら、その分だけ枠を前にスライドさせて、また続きを送る。
これがスライディングウィンドウ!たくさんのデータをスイスイ送れるんだよ。
より深い解説
定義
スライディングウィンドウは、確認応答を待たずに送信できるデータの範囲(ウィンドウ)を設け、確認応答を受け取るたびにウィンドウを前に移動(スライド)させながら送信を続ける方式である。TCPでは、受信側が受け入れられる量をウィンドウサイズとして通知し、送信側はその範囲内で送る。これにより、受信側の処理が追いつかないほど送りすぎることを防ぐ(フロー制御)。
1つずつ確認する方式との比較
| 方式 | 動作 | 1往復の時間(RTT)あたりに送れる量 |
|---|---|---|
| ストップアンドウェイト | 1つ送るごとに確認応答を待つ | 1セグメント |
| スライディングウィンドウ | ウィンドウの範囲まで続けて送る | ウィンドウサイズ分 |
ウィンドウの動き
送信するデータは、送信側から見て次の4つに分けられる。
| 確認済み | 送信済み・未確認 | 送信可能・未送信 | 送信不可 |
└────────── ウィンドウ ──────────┘
確認応答番号が届くと、ウィンドウの左端がその番号まで進み、右端も同じだけ進む。その結果、新しく送れるデータが増える。
ウィンドウサイズとスループット
ウィンドウ制御を使うTCPでは、1つのコネクションのスループットの上限は、次のように見積もれる。
スループットの上限 ≒ ウィンドウサイズ ÷ RTT
例:ウィンドウサイズ64Kバイト、RTT 10ミリ秒の場合
65,536バイト × 8 ÷ 0.01秒 ≒ 52Mビット/秒
回線がどれだけ速くても、ウィンドウサイズが小さいとこの上限を超えられない。回線の帯域とRTTの積(帯域遅延積)より大きなウィンドウが必要になる。
ウィンドウスケールオプション
TCPヘッダーのウィンドウサイズのフィールドは16ビットで、最大65,535バイトまでしか表せない。高速で遅延の大きい回線では足りないため、ウィンドウスケールオプション(RFC 7323)で、ウィンドウサイズを最大2^14倍(約1Gバイト)まで拡大できる。倍率は、3ウェイハンドシェイクのSYNで交換する。
フロー制御と輻輳制御
TCPが実際に送れる量は、2つのウィンドウの小さいほうで決まる。
| ウィンドウ | 決める側 | 目的 |
|---|---|---|
| 受信ウィンドウ(rwnd) | 受信側が通知する | フロー制御:受信側のバッファがあふれないようにする |
| 輻輳ウィンドウ(cwnd) | 送信側が推測する | 輻輳制御:ネットワークが混雑しないようにする |
輻輳ウィンドウは、スロースタートでは確認応答のたびに大きくなり(1往復ごとにほぼ倍)、パケットの損失を検知すると小さくなる。
ゼロウィンドウ
受信側のバッファがいっぱいになると、ウィンドウサイズ0を通知し、送信側は送信を止める。送信側は、定期的に小さなセグメント(ウィンドウプローブ)を送って、ウィンドウが開いたかを確かめる。