3ウェイハンドシェイクが必要な理由 なぜ2ウェイだけではないのですか?


124

TCP 3ウェイハンドシェイクは次のように機能します。

Client ------SYN-----> Server
Client <---ACK/SYN---- Server
Client ------ACK-----> Server

なぜこれだけではないのですか?

Client ------SYN-----> Server
Client <-----ACK------ Server

24
ハンドシェイクが必要なのはなぜですか?最初のパケットでメッセージを送信できないのはなぜですか?
Mehrdad

4
ハンドシェイクをスキップする場合は、代わりにUDPを使用できます。
OzNetNerd

5
@Mehrdad、ご質問がある場合は、ページ上部の[ 質問をする]リンクを使用してご自身の質問を投稿してください。
YLearn

40
@YLearn:申し訳ありませんが、それは私自身の質問ではありません。むしろ、質問に文字通り記載されているものよりも少し深く掘り下げた答えを読者に提供するよう動機づけることでした。
Mehrdad

3
TCP Fast Open(RFC 7413)を忘れないでください
-Alnitak

回答:


160

ハンドシェイクを実際に実行していることに分解します。

TCPでは、2つのパーティは、シーケンス番号を使用して送信したものを追跡します。事実上、送信されたすべての実行バイト数になります。受信側は、反対側のスピーカーのシーケンス番号を使用して、受信したものを確認できます。

ただし、シーケンス番号は0からは始まりません。ISN(初期シーケンス番号)から始まります。これはランダムに選択された値です。また、TCPは双方向通信であるため、両当事者は「話す」ことができ、したがって両方が開始シーケンス番号としてISNをランダムに生成する必要があります。つまり、両当事者は、開始ISNを相手方に通知する必要があります。

したがって、アリスとボブの間のTCP会話を開始するための次の一連のイベントになります。

Alice ---> Bob    SYNchronize with my Initial Sequence Number of X
Alice <--- Bob    I received your syn, I ACKnowledge that I am ready for [X+1]
Alice <--- Bob    SYNchronize with my Initial Sequence Number of Y
Alice ---> Bob    I received your syn, I ACKnowledge that I am ready for [Y+1]

4つのイベントが発生していることに注意してください。

  1. アリスはISNを選択し、それをボブと同期します。
  2. ボブは認め ISNを。
  3. ボブはISNを選択し、アリスと同期します。
  4. アリスは認め ISNを。

しかし実際には、中央の2つのイベント(#2と#3)は同じパケットで発生します。パケットをa SYNまたはにするのACKは、単に各TCPヘッダー内でオンまたはオフにされるバイナリフラグなので、これらのフラグの両方が同じパケットで有効になるのを妨げるものは何もありません。したがって、3方向ハンドシェイクは次のようになります。

Bob <--- Alice         SYN
Bob ---> Alice     SYN ACK 
Bob <--- Alice     ACK     

双方向の「SYN」と「ACK」の2つのインスタンスに注意してください。


それでは、質問に戻って、双方向のハンドシェイクを使用しないでください。簡単な答えは、双方向ハンドシェイクでは、一方の当事者のみがISNを確立し、他方の当事者はそれを確認することしかできないためです。つまり、データを送信できるのは1者のみです。

ただし、TCPは双方向通信プロトコルであるため、どちらの側もデータを確実に送信できる必要があります。両当事者はISNを確立する必要があり、両当事者は相手のISNを確認する必要があります。

したがって、実際には、双方向ハンドシェイクの正確な説明が、各方向にあります。したがって、4つのイベントが発生します。繰り返しますが、中央の2つのフラグは同じパケットで発生します。そのため、3つのパケットが完全なTCP接続開始プロセスに関与しています。


6
なぜISNが必要なのですか?人間はそれを必要としません、なぜコンピューターが必要ですか?これの証拠はありますか、それとも便利だからといって持っていますか?
Mehrdad

19
@Mehrdad:再送信が適切に(またはまったく)動作するには、シーケンス番号が必要です。シーケンス予測攻撃のためにISNをゼロにすることはできません。
ケビン

4
@Mehrdadチャットルームは必ずしも「リアルタイム」である必要はありません。お互いにメッセージを残すことができます。私がそれを他の場所に向けようと思ったのは、あなたが今別の質問をしているからです。OPは「なぜ2番ではなく3ウェイハンドシェイクなのか」と尋ねましたが、今度は「なぜシーケンス番号が必要なのか」と質問しますが、これは異なります。このスレッドを脱線させるのではなく、チャットで他の質問について話し合うべきだと思いました。 また、新しい質問を投稿することもできます。いくつかの良い答えが得られると確信しています。
エディ

4
素晴らしく簡潔な答え。「ACK SYN」を読むことは根本的に間違っているように感じますが、あなたはその+1を説明しました。
リリエンタール

3
RFC 793、Transmission Control Protocolによると:「3ウェイハンドシェイクの主な理由は、古い重複した接続の開始が混乱を引き起こさないようにすることです。
Ron Maupin

23

3方向のハンドシェイクが必要なのは、両当事者が送信中に使用されるセグメントシーケンス番号を同期する必要があるためです。このため、それらの各々は、(順番に)ランダム値に設定されたシーケンス番号とSYNセグメント送信Nその後され、ACKに設定されたシーケンス番号を有するACKセグメントを介して他の当事者によってnowledged N + 1


なぜ承認が必要なのですか?
パエロエベルマン

4
@PaŭloEbermann:それ以外の場合、サーバーがクライアントがSYNを受信したかどうかわからないため、クライアントがそれを受信することが重要です。
Mooingダック

2
@PaŭloEbermannそしてそれを証明するために、ACKステップは[X + 1]で承認することです。- Eddieのコメントから回答への引用。
-smwikipedia

14

接続が機能するためには、両側がパケットを相手側に送信できることを確認する必要があります。相手側にパケットを確実に取得する唯一の方法は、パケットを取得することです。これは、定義により、送信したパケットが通過しない限り送信されないはずです。TCPは基本的に 2種類のメッセージを使用します:SYN(このパケットが通過したことの証明を要求する)とACK(SYNが通過したことを証明するためにSYNが通過した後にのみ送信される)。実際には3番目の種類のメッセージがありますが、すぐにそれについて説明します。

接続が開始される前に、どちらの側も実際には相手について何も知りません。クライアントは、SYNパケットをサーバーに送信して、メッセージが通過できることの証明を要求します。それはどちらの人にも何も伝えませんが、それは握手の最初のステップです。

SYNが通過すると、サーバーはクライアントがパケットを送信できることを認識します。しかし、それはサーバーがパケットを送り返すことができることを証明しません:クライアントは多くの理由でSYNを送ることができます。そのため、サーバーは、ACK(SYNが通過したことを証明するため)とSYN(独自のACKを要求するため)の2つのメッセージをクライアントに送り返す必要があります。TCPは、ネットワークトラフィックを削減するために、これら2つのメッセージを1つ(SYN-ACKメッセージ(必要な場合))に結合します。これは、ハンドシェイクの2番目のステップです。

SYN-ACKはACKであるため、クライアントはサーバーにパケットを送信できることを確信しています。また、SYN-ACKはSYNであるため、サーバーがこのメッセージが通過したことの証明を必要としていることも知っています。そのため、ACKを送り返します。今回は単なるACKです。これは、パケットが通過できることを証明する必要がなくなったためです。これがハンドシェイクの最後のステップです。クライアントはパケットが双方向に送信できること、そしてサーバーがこれを理解しようとしていることを認識します(ACKが送信されることを知っているため)。

ACKが通過すると、サーバーはクライアントにパケットを送信できることを認識します。また、クライアントがこれを知っていることも知っているので、すぐにデータの送信を開始できます。ハンドシェイクが完了しました。良いチャンネルがあります。

まあ、厳密に言えば、良いチャネルがあるかどうかはわかりません。この一連のパケットが通過したからといって、他のパケットが通過することを厳密に保証するわけではありません。無限の数のSYNとACKを送信しないと、他に何も実行されないことを証明することはできません。したがって、これは実際的な選択肢ではありません。しかし実際には、3つのステップでほとんどの目的に十分であることがわかります


これは正しくありません:「ACK(SYNへの応答でのみ送信され、SYNが通過したことを証明します)」各端から送信された最初のパケットのみにSYNフラグが設定され、3ウェイハンドシェイクの最初のパケット以外のすべてのパケットにはACKフラグが設定されます。2番目のパーティはまだSYNしていないため、最初のパケットはACKできませんが、1番目以降のすべてのパケットは、データが返送されたかどうかに関係なく、相手から既に受信したものにACKを返さなければなりません。
モンティハーダー

ありがとう。言い換え:ACKは、SYNへの応答として送信されるのではなく、SYNが通過すると送信されます。
スプーニエスト

これは、3番目のメッセージが必要な理由を論理的に説明できる最良の回答です。ありがとう、スプーニエスト。
Parth Patel

7

実際、3ウェイハンドシェイクだけがTCP接続を確立する手段ではありません。同時SYN交換も許可されています:http : //www.tcpipguide.com/free/t_TCPConnectionEstablishmentProcessTheThreeWayHandsh-4.htm

それは一種の二重の双方向ハンドシェイクと見ることができます。


1
良い点ですが、両方のデバイスが同じ送信元/宛先ポートを使用する必要があり、他のデバイスがSYNを受信する前に両方のデバイスがSYNを送信する必要があるため、これは非常にまれです。発生した場合でも、4つのパケットが送信されます。これは、従来の3ウェイハンドシェイクに必要な3つのパケットを超えています。最終的には、全体的な効率の低下を犠牲にして、全体的な時間の観点からセットアップがわずかに速くなる可能性のみ(33%以上のパケットを送信する必要があります)。
YLearn

4

TCP接続は双方向です。これが意味することは、実際には一方向の接続のペアであることです。イニシエーターはSYNを送信し、レスポンダーはACKを送信します。1つのシンプレックス接続が開始されます。「その後」レスポンダーがSYNを送信し、イニシエーターがACKを送信します。別のシンプレックス接続が開始されます。2つのシンプレックス接続が1つのデュプレックスTCPセッションを形成します、同意しますか?したがって、論理的には4つのステップが含まれます。ただし、SYNフラグとACKフラグはTCPヘッダーの異なる「フィールド」であるため、同時に設定できます-(4つのうちの)2番目と3番目のステップが組み合わされ、技術的には3つのパケット交換が行われます。あなたが提案したように、各シンプレックス(ハーフ)接続は双方向の交換を使用します。


2

サーバーとクライアントが接続を作成する場合、4つのことを確認する必要があります。

  1. サーバーは、クライアントからパケットを受信できることを確認する必要があります
  2. クライアントは、サーバーからパケットを受信できることを確認する必要があります

  3. クライアントは事を確認する必要があります:サーバーはクライアントからパケットを受信できます

  4. サーバーは事を確認する必要があります:クライアントはサーバーからパケットを受信できます

後にClient ------SYN-----> Server、ルール1が確認されます。

Client <---ACK/SYN---- Server、ルール2および3が確認されます。

そのため、ルール4を確認するために3番目のパケットが必要です。


1

まったく必要ありません。短いメッセージが必要なのは、開始+メッセージを含むサーバーへの1つのパケットと、それを確認するための1つのパケットだけである必要があることは明らかです。

前の回答では、最初にランダムシーケンス番号などの必要性については説明せずに、システムについて説明しました。元々の質問はTCP自体の設計に関するものでした。明らかにTCPプロトコルを使用する場合、それがプロトコルであるため3つのメッセージが必要です。しかし、そもそもTCPがそのように設計されたのはなぜですか?

元々のアイデアは、クライアントとサーバーの間に区別がないということでした。どちらも双方向で相手のポートを認識しており、どちらも会話を開始できます。それにはSynsなどが必要でした。

しかし、これはもちろん、今日の使用方法ではありません。サーバーは、既知のポートでリッスンし、「受け入れ」ます。クライアントのポート番号は一時的です。「受け入れ」を待っているサーバーが、通常のオペレーティングシステムの同じクライアントポート番号で別のサーバーに要求を送信することは不可能だとさえ思います。

(これは接続の双方向の開始に関するものであり、今日では決して行われないことに注意してください。これは、確立された接続に双方向メッセージを送信することとはまったく異なります。)

TCPの非効率性を回避するために、HTTP 1.1などのプロトコルを使用して、複数の要求に同じ接続を再利用できるため、そもそも必要ではなかったTCPハンドシェイクを回避できます。

しかし、Http 1.1は比較的新しいものです。また、SSL / TLSでは、PKIアルゴリズムのコストのために、セッションを最初から再利用する方法が必要でした。そのため、そのプロトコルには、TCP上で実行されるHttp 1.1上で実行される独自のセッション再利用メカニズムが含まれています。

これがソフトウェアの方法です。組み合わされたときに許容できる結果をもたらすクラッジのファッジ。


OSIレイヤー4を超えるもの(HTTP、FTPなど)は、ここでは明示的にオフトピックです。レイヤー1から4では、クライアント/サーバーのようなものはありません。TCPはピア間の接続です。はい、上位層プロトコルはクライアント/サーバー関係を作成しますが、ここではトピックから外れています。
ロンモーピン

1
ところで、HTTPはTCPを使用するため、TCPハンドシェイクは依然として必要です。読むRFCに793伝送制御プロトコルを理由undestandします。HTTPなどのプロトコルでは、アプリケーションがTCPがアプリケーションに対して通常行う多重化を行う必要があります。
ロンモーピン

@RonMaupin元の質問はなぜでしたか?そしてその答えは、実際には上位レベルのレイヤーによって決して使用されないユースケースをサポートすることです。だから、かなり関連しているようだ。
調整可能

@RonMaupinはい、HTTPはTCPを使用します。これを明確にした、ありがとう。しかし、それはTCPハンドシェイクを深い意味で必要にするものではありません。
調整可能

1
ここでは、アプリケーションとアプリケーション層プロトコルは明示的にオフトピックです。@Eddieが質問に回答しました。TCPRFCを読んで理解すれば、ハンドシェイクが必要な理由がわかります。明確に必要な場合、サポートなしで、ハンドシェイクは必要ないと主張するために何かを追加するとは思わない。
ロンモーピン

1

Eddieの回答(正しいと認められた)を読んだ後、なぜ1番目のホストがISNに乱数を割り当てられず、2番目のホストがそれを受け入れることができないのかという疑問が残っています。3ウェイハンドシェイクを使用する本当の理由は、ハーフコネクションを避けるためです。双方向ハンドシェイクの半分の接続シナリオ:
1)クライアント--- SYN- >サーバー
2)クライアントは気が変わり、もう接続したくない
3)クライアント<-X-ACK--サーバー// ACKが失われた
サーバーはSYNの再送信を認識しないため、クライアントはACKを取得して接続が確立されたと考えています。その結果、サーバーには閉じられない接続があります


実際、ホスト(クライアントとサーバーはTCPが何も知らないアプリケーションの概念である)が、存在しない接続(シナリオのステップ3)でACKまたはトラフィックを受信する場合、受信したセグメントを無視せずにRSTを送信します。
ロンモーピン

@RonMaupinそれでは、ACKパケットが失われた状況を想定しましょう。
Sanzhar Yeleuov

ACKが失われた場合、ステップ1で開始された接続はタイムアウトします。RFC 793には、図を含むすべてのタイプのシナリオの完全な説明があります。
ロンモーピン

@RonMaupin私の投稿のシナリオが同じままである場合、変更されたもののみ、そのACKが失われたということです。
Sanzhar Yeleuov

すべてRFCにあります。接続が開くまで、受信したトラフィックはRSTになります。3ウェイハンドシェイクは接続パラメータをネゴシエートするため、「サーバー」は「クライアント」に何も返せませんが、「クライアント」からACKを受信するまではSYN / ACKです。「クライアント」への「サーバー」SYN / ACKが失われた場合、「サーバー」は再試行します。RFCはこれをすべて説明しています。
ロンモーピン
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.