私はハードウェアやカーネルの設定(すべてのデフォルト設定、新しいOSのインストール、Linuxカーネル3.11 TCP / IPスタック)に対して特別な作業をしていませんでした。毎秒100万のメッセージがUDPを介して送信されます。これは、両方のプロトコルに対する私の期待に完全に反対しているようです。
大きな違いが発生する最大の理由は何ですか? Ubuntu 13.10で診断する方法は?
#TCP RESULTS
Recv Send Send Utilization Service Demand
Socket Socket Message Elapsed Send Recv Send Recv
Size Size Size Time Throughput local remote local remote
bytes bytes bytes secs. 10^6bits/s % S % S us/KB us/KB
87380 65536 64 10.00 1963.43 32.96 17.09 5.500 2.852
#UDP RESULTS
Socket Message Elapsed Messages CPU Service
Size Size Time Okay Errors Throughput Util Demand
bytes bytes secs # # 10^6bits/sec % SS us/KB
4194304 64 10.00 7491010 0 383.5 28.97 24.751
212992 10.00 1404941 71.9 25.03 21.381
このテストには、10Gクロスオーバーケーブルを介して直接接続された2つの同じテストサーバーがあります。この例で使用されるNICは、デフォルトで設定され、マザーボードのPCIe 3.0 x8スロットに接続され、NUMAコントローラを介してCPUと通信するIntel X520です。
答え1
テスト設定の詳細を取得できないことに加えて、主な問題は64バイトのメッセージサイズを使用していることです。これは、1500バイトの一般的なMTUから離れており、UDPを非常に非効率的にします。 TCPは、リンクを効率的に活用するために回線上の複数の送信を単一のパケットに結合します(TCP_NODELAYが設定されていない場合)、各UDPメッセージは単一のパケットになります。数字を見ると、約23個の64バイトのメッセージが1つのMTUサイズTCPパケットに結合されますが、UDPは同じ量のデータに対して23個の個別のパケットを必要とします。これらの各パケットは、ホストから送信され、オンラインで送信され、ピアで受信されるオーバーヘッドを表します。お客様のケースに示すように、ハードウェアがすべてのパケットを送受信するのに十分速くないため、UDPパケットの約80%が失われます。
したがって、このベンチマークで学べる内容は次のとおりです。
- UDPは信頼できません(80%パケット損失)。
- パケットサイズがMTUよりはるかに小さい場合、UDPは非効率的です。
- TCPは、リンクを完全に活用するために高度に最適化されています。
あなたの期待によると、UDPはより良いでしょう。すべての主要なファイル転送(ftp、http...)がなぜTCPベースのプロトコルを使用して実行されるのか疑問に思ったことはありますか?ベンチマークを見ると、その理由がわかります。
それでは、人々はなぜUDPを使用するのでしょうか?
- リアルタイムデータ(VoIPなど)の場合、古いメッセージは気にしないため、送信者はリンクを効率的に活用するためにメッセージをより大きなパケットに結合したくありません。そして、パケットが遅すぎるのではなく、パケット損失を受け入れるほうが良いです。
- 待ち時間の長いリンク(衛星など)の場合、TCPのデフォルトの動作はリンクを効率的に使用するのには適していません。したがって、この場合、一部のユーザーはUDPに切り替えてTCPの信頼性層を再実装して待ち時間の長いリンクに合わせて最適化し、他の人はリンクをよりよく活用するために既存のTCPスタックを調整します。
- データ「削除」:時には、ログメッセージ(syslog)などのパケット損失を気にせずにデータを送信することがより重要です。
- 短い対話:TCPを使用すると、接続を確立して状態を維持する必要があります。これは、クライアントとサーバーの両方で時間とリソースを消費します。短い対話(短い要求や応答など)では、オーバーヘッドが多すぎる可能性があります。したがって、DNSは通常UDPを使用して実行されますが、再試行はUDPに基づいて構築されます。