首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >java.nio.channels.ClosedChannelException

java.nio.channels.ClosedChannelException
EN

Stack Overflow用户
提问于 2010-05-10 15:48:53
回答 2查看 72.8K关注 0票数 15

我该如何解决这个问题呢?我得到了以下错误:

java.nio.channels.ClosedChannelException

这是编码:

代码语言:javascript
复制
 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);
            }
        }
    }
}
EN

回答 2

Stack Overflow用户

发布于 2013-06-01 08:51:01

您已关闭通道,但仍在尝试使用它。

你的代码有几个问题。

首先,你的EOS测试是错误的。删除limit() == 0测试。这并不表示EOS,它只是表示读取长度为零,这在非阻塞模式下随时都可能发生。这并不意味着对等体已经关闭了他的连接,也不意味着你应该关闭你的连接。

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

第三,关闭通道将取消密钥。你不需要在每一个结束语后面都加上一个取消。

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

我仍然对这篇文章中其他地方关于“源代码在某些情况下是不真实的”的说法感到惊讶、有趣和困惑。

票数 11
EN

Stack Overflow用户

发布于 2010-05-10 15:55:47

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

...当尝试调用或完成通道上的I/O操作时抛出,该通道已关闭,或至少已关闭该操作。抛出此异常并不一定意味着通道已完全关闭。例如,其写半部分已被关闭的套接字通道可能仍然打开以供读取

(如Java 6 API中所述)

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

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/2801087

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档