0

これはクラスの課題なので、答えよりもヒントが必要です。

4 つの仮想 Linux マシンでプロセスを実行しています。各プロセスは、隣接する 2 つのプロセスと通信します。各プロセスは

server = ServerSocketChannel.open()
server.configureBlocking(false)
server.socket().bind(new InetSocketAddress(port))
server.register(selector, SelectionKey.OP_ACCEPT)

起動時に、プロセス A は誰にも接続しようとしません。プロセス B は

SocketChannel SC = SocketChannel.open()
SC.configureBlocking( false )
SC.connect(new INetSocketAddress( A-machine, A-port )
SC.register( selector, SC.validOps())

プロセス C は B に対して同じことを行います。および D と C。

次に、selector.select を呼び出して、selectedKeys を反復処理します。key.isValid() && key.isAcceptable() の両方が true の場合、ソケットが私に接続しようとしていると思い、私は呼び出します

SocketChannel client = server.accept()
client.configureBlocking(false)
client.register(selector, client.validOps() )

key.isValid() && key.isConnectable() の両方が true の場合、サーバーに接続できると思います。電話する

SocketChannel connectingChannel = (SocketChannel)key.channel()
connectingChannel.finishConnect()

key.isValid() && key.isReadable() が表示されると、受信したメッセージを読み込んでいます。

このプロセスは、A、B、C、D の順にプロセスを開始する限り機能します。B のみを開始すると、finishConnect ステートメントで失敗します。

isConnectable が、このキーのチャネルがソケット接続操作を終了したか、終了に失敗したかをテストするドキュメントを読みました。isConnectable が true で、finishConnect で失敗するのはなぜですか?

4

1 に答える 1

0

私たちはfinishConnectの周りにtry/catchをラップしました。キャッチ内で、現在のSelectionKeyでcancelを呼び出し、次に接続を試みたメソッド(元の問題の説明の2番目のスニペット)を呼び出しました。

SocketChannel SC = SocketChannel.open()
SC.configureBlocking( false )
SC.connect(new INetSocketAddress( A-machine, A-port )
SC.register( selector, SC.validOps())

これを行う必要があることを予想して、SCとA-machineおよびA-portの間の関係を格納するコードを追加したので、再試行時にそれらを取得しました。そのため、キャッチでは、キャンセルする前に、失敗したSocketChannelを使用して、必要なAマシンとAポートのデータを検索しました。

その後、最終的にサーバーが起動し、この接続が正常に確立されました。

私はこれが答えであり、ヒントではないことを知っていますが、それは私たちの割り当てでした:)

于 2011-02-27T05:31:54.810 に答える