2017-05-08 7 views
0

私は、バックグラウンドで動作するサーバープロセスが制御プログラムによって制御されるシステムを持っています。LinuxのTIME_WAITとEADDRINUSE

制御プログラムは、1つのコマンドを実行して終了する単純なスクリプトです。実行コマンドでは、新しいサーバープロセスを作成します。それ以外の場合(シャットダウンを含む)、コマンドは予約された制御ポートを介してサーバーに送信されます。

制御プログラムは、ソケットを作成し、サーバーの制御ポートに接続し、データの1文字(コマンド)を送信し、ソケットから応答を読み取り、ソケットをクローズし、ユーザーに応答を表示して終了します。サーバーは、コントロールソケット上の接続を受け入れ、データの文字を読み取り、応答を送信し、子ソケットを閉じてリスニングを続行します。サーバがシャットダウンすると、親制御ソケットも閉じます。

これは、Windows XP/Python 2.6.6で長年働いています。最近、私たちはLinuxへの移植を試みましたが(Ubuntu 16.04.2 GNU/Linux 4.4.0-62-一般x86_64/Python 2.7.12)、Restartコマンド(Shutdownの直後にRunが続く)が失敗します。新しいサーバプロセスがコントロールソケットにコントロールソケットをバインドするには、EADDRINUSEが返されます。

netstatからの出力では、Shutdownコマンドに使用された接続がTIME_WAIT状態のままで、約2分間続きます。

このトピックに関する以前の投稿を確認しました。私はサーバーのコントロールソケットでSO_REUSEADDRおよび/またはSO_REUSEPORTを設定しようとしました。私はサーバと制御プログラムの間のプロトコルを強化して、制御プログラムが最初に接続の側を閉じるようにしましたが、これまでの組み合わせでは動作しませんでした。私は解決策があるのだろうかと思います。

サーバと制御プログラムの両方が同じマシン上で実行されると、接続の両側の詳細はオペレーティングシステムの状態テーブルにあり、残りの1つまたはそれ以上はTIME_WAITに残す必要があります。

制御プログラムのエントリは、サーバーがポートにバインドできないようにしますか?

WindowsではTIME_WAIT状態でも接続が残っていますが、Windowsでは新しいサーバープロセスが同じコントロールポートにバインドされないことに注意してください。

+0

こんにちは、歓迎StackOverflow!質問を編集していくつかの書式を含めることができます。今は読むのが大変です! –

答えて

0

私は自分の質問に答えました。目的の動作を得るためには、サーバーの制御ソケット(only)にSO_REUSEADDR(only)を設定する必要があります。 SO_REUSEPORTを使用する必要はありません。制御プログラムに何もする必要はありません。どちらの側が最初に接続を閉じても違いはありません。

私は愚かな間違いをしたため、私の最初の試みは機能しませんでした。 (私は間違った変数を使用しました)

関連する問題