java.nio.channels.ClosedChannelException

时间:2010-05-10 07:48:53

标签: java

我该如何解决这个问题。我收到了以下错误:

java.nio.channels.ClosedChannelException

这是编码:

 public void run() {

    try {
        SocketChannel socketChannel = (SocketChannel) key.channel();
        ByteBuffer buffer = ByteBuffer.allocate(512);
        int i1 = socketChannel.read(buffer);

        if (buffer.limit() == 0 || i1 == -1) {

            Socket s = null;
            try {
                s = socketChannel.socket();
                s.close();
                key.cancel();
            } catch (IOException ie) {
                if (UnitDataServer.isLog) {
                    log.error("Error closing socket " + s + ": " + ie);
                }
            }
        } else {
            buffer.flip();
            if (UnitDataServer.isLog) {
                log.info(" Recvd Message from Unit : " + buffer.array());
            }
            byte byteArray[] = buffer.array();
            log.info("Byte Array length :" + byteArray.length);
            hexString = new StringBuffer();

            for (int i = 0; i < i1 /* byteArray.length */; i++) {
                String hex = Integer.toHexString(0xFF & byteArray[i]);
                if (hex.length() == 1) {
                    // could use a for loop, but we're only dealing with a
                    // single byte
                    hexString.append('0');
                }
                hexString.append(hex);
            }
            hexString.trimToSize();
            log.info("Hex String :" + hexString);

             Communicator.dataReceive(new  DataReceive(
                    socketChannel, hexString.toString(), dst));

        }
    } catch (Exception e) {
        if (UnitDataServer.isLog) {
            // log.error(e);
        }
        try {
            socketChannel.socket().close();
            key.cancel();
        } catch (IOException ex) {
            if (UnitDataServer.isLog) {
                log.error(ex);
            }
        }
    }
}

2 个答案:

答案 0 :(得分:11)

您已关闭频道并仍在尝试使用它。

您的代码存在一些问题。

首先,您对EOS的测试有误。删除limit() == 0测试。这并不表示EOS,它只是指示零长度读取,这可以在任何时间以非阻塞模式发生。这并不意味着同伴关闭了他的连接结束,并不意味着你应该关闭你的结束。

其次,关闭通道也会关闭套接字。您应该只关闭通道,而不是插座。

第三,关闭频道会取消该密钥。您无需通过取消来关注每一次结束。

在使用之前,您可能无法检查就绪密钥在选择循环中是否有效,例如:阅读。

在这个帖子的其他地方声称“源代码在某些情况下是不真实的”,我继续感到惊讶,感到好笑和困惑。

答案 1 :(得分:0)

您需要修复/保护引发此异常的代码。 ClosedChannelException 是......

  

......抛出时   尝试调用或完成   通道上的I / O操作   关闭,或至少关闭   操作。这个例外是   抛出并不一定意味着   通道完全关闭。一个   写入一半的套接字通道   例如,可能仍然关闭了   开放阅读

(如Java 6 API中所述)

但实际上,您需要为我们提供代码剪切和堆栈跟踪,以获得更详细的帮助。