2012-09-10 6 views
7

私はWindows 7でstunnelの2つのインスタンスを実行していて、同じポートをリッスンするように設定されていて、どちらも同じポートで待機しているようです(socket()/ bind()/ listen()を使用しています)。どちらのインスタンスもすべての呼び出しで成功し、netstatに表示されます。2つのプロセスがWindows 7の同じポートをどのようにリッスンしていますか?

C:\>netstat -ano | grep 8000 
    TCP 0.0.0.0:8000   0.0.0.0:0    LISTENING  5828 
    TCP 0.0.0.0:8000   0.0.0.0:0    LISTENING  5852 

最初に受信するすべての要求が受信されます。

これは私の期待とはかなり反対です。 (私はポートがビジーであることをEADDRINUSEに伝えることを期待していました)。だから....

  1. なぜ/どのように機能しますか?この動作はある状況では有効ですか?
  2. 別のアプリケーションが着信要求をキャッチしようとした場合、インスタンスが正常に実行されないようにするにはどうすればいいですか?

答えて

7

これは、ソケットが、TCPソケットアプリケーションでは一般的ではないフラグSO_REUSEADDRで開かれた場合に実行できます。 SO_REUSEADDRは、2つのいずれかのために使用されている

通常、:プロセスがクラッシュしたとき

  1. 、そのソケットをクローズする機会を得ることなく死亡した、または強制的に再起動されて。または、プロセスは終了しましたが、ソケット(または子接続ソケット)は依然としてFIN_WAITまたはFIN_WAIT2状態です。 2番目のプロセスは、 "already in use"エラーコードを取得せずにソケットを開くことができます。私はS.O.にいくつかの記事を読んだ。これがTCPソケットのベストプラクティスであることを示唆しています。

  2. 同じサーバープログラムは、フォークされているか、複数回同時に実行されています。これにより、スレッドを使用するように書かれたサーバプログラムなしでロードバランシングが可能になります。通常、ソケットで待機しているプログラムの「その他のインスタンス」は、最初の接続が別の接続でビジー状態になっている間に、着信接続を受け入れます。

2番目の質問に関して、最も簡単なことはSO_REUSEADDRを使用しないことです。 SO_REUSADDRを使用しようとする不正なアプリがあると懸念される場合、アプリはSO_EXCLUSIVEADDRUSEを使用できます。 (基本的に「他のアプリケーションがSO_REUSEADDRでこの同じポートを開くことを許可しないフラグ」)

+0

このフラグは、同じ名前のUNIXフラグと同じであると考えました。 //msdn.microsoft.com/en-us/library/windows/desktop/ms740621(v=vs.85).aspx – Olson

関連する問題