この記事を書く理由は怠でした。それは、ご存知のように、進歩のエンジンであり、信じられないほど人生を楽にするものの誕生の証です。
私の場合、クライアントがポイントツーポイントチャネルをリースし、イーサネット1 Gbit / sが契約で白黒で書かれている理由を1000回説明するのは面倒で、彼はそれを測定しますが、それより少し少ないです。
残りはどこですか? なぜ不足するのですか? インターネットはどこから来たのですか? それとも、彼は完全にscarされて怖がっていたのでしょうか?
さて、見てみましょうが、同時に、速度が落ちる最初の1000人の顧客に恥ずかしくないメモを書きます。
重要です
ネットワークエンジニアの方は、この記事を読んではいけません。 彼女はあなたのすべての気持ちを怒らせます。 最も単純で最もアクセスしやすい言語で書かれており、多くの省略があります。
窓に関する物語。 窓の世界
そのため、速度がどこにあるかを理解するために、信頼できる接続を確保するという点でTCPがどのように機能するかを理解する必要があります。
誰もが知っているように、TCPには最後の希望があります。フレームを受信者に配信するすべてのトリックが機能しなかった場合、TCPは破損したフレームまたは失われたフレームを再度送信します。
最も単純な場合の外観:
- フレームは送信機によって送信されます。 送信機では、タイマーがアクティブになります。その間に、受信機は受信機からフレームの正常な受信の確認またはフレームが送信中に破損/紛失したという明示的な指示を受信する必要があります-NACK
- タイマーの後にACKが受信されない場合、パケットは再度送信されます
- NACKが到着すると、ソースはフレームの送信を再試行します
- そして、ASKが受信されると、ソースは次のフレームを送信します
グラフィカルに、このアルゴリズムはタイムラインで簡単に表現できます。
このアルゴリズムはソースアイドルメソッドと呼ばれ、通信チャネルの壊滅的な非効率的な使用という主な短所をすぐに理解できます。 技術的には、送信機が最初のフレームを送信した直後に2番目のフレームを送信することを妨げるものはありませんが、ACK / NACKの到着またはタイマーの期限切れを強制的に待機させます。
したがって、ACKの送信と受信のプロセスは互いに独立して実行できることを理解することが重要です。 この考えに基づいて、スライディングウィンドウ方式が生まれました。
最初のウィンドウ。 スライディング。 理論的
前の方法のマイナスを実現した後、アイデアは、ソースが受信者からの確認を待たずに、可能な限り最高のレートでパケットを送信できるようにするというアイデアになります。 しかし、その無限の数ではなく、ウィンドウと呼ばれる特定のバッファによって制限され、そのサイズは確認を待たずに送信できるフレームの数を示します。
写真に戻る:
わかりやすくするために、ある時点でパケット(1 ... N)があるサイズKフレームのウィンドウ、つまり 一連のフレームを送信しました。各フレームは可能な限り受信者に届き、受信者はそれらを処理して、それぞれの確認を送信しました。
次に、時間をオンにして状況を複雑にします。
ACKが最初のフレームに到着した時点で、最後のフレームはまだ送信されていませんが、配信の成功がわかっているため、ウィンドウ内の次のフレームをウィンドウに追加できます。 ウィンドウがシフトされ、フレーム2 ... N + 1が含まれるようになりました。 ACKがフレーム2に到着すると、ウィンドウは再びシフトします:3 ... N + 2。 などなど。 ウィンドウがパケットのストリームに沿って何らかの形で「スライド」することがわかりました。 または、それを介してパッケージ化してから、提示する方が便利です。
したがって、すべてのフレームはグローバルに3つのタイプに分けられます。
- 過去。送信され、確認が受信されました。
- 厳しい存在。 送信されたフレームで構成されますが、確認は受信されず、すでにウィンドウ内にいるが、送信のためにキューに立っている人
- 明るい未来。 ウィンドウに入るためのラインのフレーム。
そして、これは通信速度にどのように影響しますか? -お願いします。
グラフからわかるように、通信チャネルを最大限に活用するために必要な条件は、ウィンドウの一部として確認を定期的に受信することです。 ASKは明確な順序で到着する義務はありません。主なことは、ASKは最後のフレームが送信される前にウィンドウの最初のフレームに到達することです。
また、スライディングウィンドウアルゴリズムのほとんどの実装では、すべてのパケットではなく、受信したパケット全体(Selective Ackと呼ばれる)に対して直ちに確認が行われることに注意してください。 これにより、サービス情報の量を減らすことで、チャネルの有効利用率をさらに高めることができます。
では、最終的には何が得られますか? 2つのポイント間のデータ転送の効率に大きな影響を与えるパラメーターは何ですか?
それらの2つがあります。
- ウィンドウのサイズ。2つのうち小さい方が選択されます。受信者が宣言したウィンドウ(そのバッファーのサイズ)またはCWND-RTTに基づいて送信者が決定したサイズ
- RTT自体:信号の送信にかかった時間に等しい受信および送信の時間に、受信の確認に必要な時間を加えたもの。
そして、受信者がネットワークを受け入れるかスキップする準備ができている以上に送信するべきではありません。
パケットがほとんど失われたり壊れたりしない、非常に信頼性の高いネットワークがあると想像してみましょう。 このようなネットワークでは、可能な限り大きなサイズのウィンドウを用意することが有益です。これにより、フレームの送信間の一時停止を最小限に抑えることができます。
悪いネットワークでは、状況は逆です-頻繁な損失と多数の壊れたパケットでは、それぞれを無傷で配信することが重要です。そのため、トラフィックができるだけ失われないようにウィンドウを縮小し、致命的な転送を回避します。 この場合、犠牲はスピードです。
そして、ご存じのとおり、現実には2つの極端なケースが混在しているため、実際のネットワークではウィンドウサイズは可変です。 さらに、どちらか一方の側で、または合意により、両方を変更できます。
中間サマリー。 ご覧のとおり、特定のプロトコルに縛られていなくても、チャネルを100%完全に利用することは技術的に非常に困難です。 必要かどうかは、実験室の条件であっても、フレーム間は最小限に抑えられますが、遅延により切望されている100%の帯域幅使用率に到達することはできません。
また、実際のネットワークについて何を言えるでしょうか? 2番目の部分では、TCPを使用した実装の1つを例として検討します。
2番目のウィンドウ。 TCP実装
TCPの注目すべき点は何ですか? 信頼できないIPデータグラムに基づいて、信頼できるメッセージ配信を提供します。
論理接続を確立すると、TCPモジュールは次のパラメーターを相互に交換します。
- 受信者のバッファサイズはウィンドウサイズの上限です
- このセッション内のデータストリームのカウントダウンを開始するバイトの初期シーケンス番号
すぐに重要な機能を覚えています。TCPでは、ウィンドウはフレーム数ではなくバイト数で動作します。 これは、ウィンドウが上位プロトコルからの非構造化データストリームの一連の番号付きバイトであることを意味します。 面倒に聞こえますが、書きやすいです。
したがって、TCPは二重プロトコルです。つまり、各サイドはいつでも送信側と受信側の両方として機能します。 したがって、各側には、セグメントを受信するためのバッファーと、まだ送信されていないセグメント用のバッファーが必要です。 ただし、さらに、すでに送信済みのセグメントのコピー用のバッファーも用意する必要があります。これらのセグメントについては、受信確認をまだ受信していません。
ところで、これは見落とされている機能につながります。2方向では、ネットワークの状態が異なる場合があります。つまり、異なるウィンドウサイズと異なる帯域幅を意味します。
この状況では、ダンスは受信者から行われます。 接続が確立されると、両側が互いに受信ウィンドウを送信します。 受信者はそのサイズを記憶し、ACKを待たずに送信できるバイト数を理解します。
次に、最初の章で説明したメカニズムが含まれています。 セグメントの送信、確認の待機、必要に応じて再送信など。 理論的研究との重要な違いは、さまざまな手法の組み合わせです。 たとえば、順番どおりに到着した複数のセグメントの受信は自動的に行われ、受信の順序が失われた場合にのみ中断されます。 これは、レシーババッファの機能の1つです。セグメントの順序を復元します。 そして、ストリームにギャップが検出された場合、TCPモジュールは失われたセグメントに対してリクエストを繰り返すことができます。
送信者のコピーバッファに関するいくつかの単語。 このバッファにあるすべてのセグメントにはタイマーがあります。 タイマー中に対応するACKが到着すると、セグメントは削除されます。 そうでない場合は、再度送信されます。 タイマーによって、ACKが到着する前にセグメントが再度送信される可能性がありますが、この場合、繰り返されたセグメントは受信者によって単に破棄されます。
TCPのパフォーマンスは、この待機タイムアウトに依存します。 短すぎる-冗長パケット転送が表示されます。 長すぎる-存在しないASKが予想されるため、ダウンタイムが発生します。
実際、TCPは複雑な適応アルゴリズムを使用してタイムアウトサイズを決定します。このアルゴリズムでは、速度、信頼性、回線の長さ、その他多くの要因が考慮されます。 ただし、一般的には次のとおりです。
- 各セグメントを送信するときに、ASKの到着までの時間が測定されます。
- 結果の値は、過去から未来にかけて増加する重み係数で平均化されます。 これにより、新しいデータが最終結果に大きな影響を与えることができます。
- 次に、前のステップの平均からの平均値が考慮され、タイムアウト値が取得されますが、値の広がりが非常に大きい場合は、分散も考慮されます。
しかし、受信ウィンドウはより興味深いエンティティですが、送信ウィンドウについてはますます何かがあります。 接続の異なる端では、ウィンドウのサイズは通常異なります。 勝っているクライアントサーバーテクノロジーの世界では、サーバーが処理できるのと同じサイズのウィンドウでクライアントが動作する準備ができていることを期待する必要はありません。
同様に、ネットワークの状態に応じてそのサイズは動的に変化する可能性がありますが、ここでは間違った選択は「二重の」責任を意味します。 TCPモジュールが処理できるよりも大きいデータを受信した場合、それらは破棄され、タイマーはソースで動作し、データを転送し、再びウィンドウサイズに落ちません。
一方、ウィンドウの設定が小さすぎると、1つのセグメントの伝送速度に等しい速度でチャネルが使用されることになります。そのため、TCP開発者は、接続を確立するときにウィンドウサイズを比較的大きく設定し、問題が発生した場合にステップで半分に縮小し始める方式を提案しました。 それは本当に奇妙に見えます。それが、通常のロジックを繰り返してTCP実装が作成された理由です。小さなウィンドウから開始し、ネットワークがうまくいけば、それを増やし始めます。
ただし、受信ウィンドウのサイズは、受信側だけでなく、データ送信者によっても影響を受ける可能性があります。 ACKがタイマーよりも定期的に遅く、セグメントを再送信する必要があることが多いことがわかった場合、ソースは独自の受信ウィンドウ値を設定でき、最小ルールが適用されます-最小値は、それを割り当てる人なら誰でも受け入れられます。
さらに別のシナリオ、つまりTCP接続のオーバーロードを検討する必要があります。 ネットワークのこの状態は、パケットキューが中間ノードと端末ノードで発生するという事実によって特徴付けられます。 この場合、受信機には2つのオプションがあります。
- ウィンドウサイズを小さくします。
- ウィンドウサイズをゼロに設定して、受信を完全に終了します。
この方法では接続を完全に閉じることはできませんが。 既存のバッファをクリアする必要がある場合でも、ポートにデータセグメントの受け入れを強制する特別な緊急インジケータがあります。 また、ウィンドウサイズ0を受け入れる送信者は希望を失わず、定期的に受信者に制御要求を送信します。新しいデータを受信する準備ができている場合、ゼロ以外の新しいウィンドウサイズを受信します。
合計
キャプテンが教えてくれます-1つのTCPセッションが原則としてチャネルの100%の使用率を提供できない場合、2つを使用します。 ポイントツーポイントチャネルをリースし、その中にGREトンネルを作成したクライアントについて話している場合、2番目のチャネルを作成します。 彼らが車線のために戦わないように、私たちは最初の重要なトラフィック、2番目のトラフィックでラップします-あらゆる種類のごみとひどく彼の速度を下げます。 これはバンドの名残を選択するのにちょうど十分であり、最初のセッションでは純粋に技術的に取ることができません。