繁体   English   中英

Java套接字选择器不会切换到写入状态

[英]Java Socket selector doesnt switch to write state

我们已经实现了基于选择器的解决方案

喜欢

    @Override
public void run() {
    super.run();
    while (session.isConnectionAlive()) {
        try {
            // Wait for an event
            selector.select();
        } catch (IOException e) {
            log.error("Selector error: {}", e.toString());
            log.debug("Stacktrace: ", e);
            session.closeConnection();
            break;
        }
        handleSelectorkeys(selector.selectedKeys());
    }
    executorService.shutdown();
    log.debug("Ucp worker stopped");
}

private void handleSelectorkeys(Set<SelectionKey> selectedKeys) {
    Iterator<SelectionKey> keys = selector.selectedKeys().iterator();
    while (keys.hasNext()) {
        SelectionKey selKey = keys.next();
        selector.selectedKeys().remove(selKey);
        try {
            processSelectionKey(selKey);
        } catch (IOException e) {
            // Handle error with channel and unregister
            selKey.cancel();
            log.error("Selector error: {}", e.toString());
            log.debug("Stacktrace: ", e);
        }
    }
}

public void processSelectionKey(SelectionKey selKey) throws IOException {

    // Since the ready operations are cumulative,
    // need to check readiness for each operation
    if (selKey.isValid() && selKey.isConnectable()) {
        log.debug("connectable");
        // Get channel with connection request
        SocketChannel sChannel = (SocketChannel) selKey.channel();

        boolean success = sChannel.finishConnect();
        if (!success) {
            // An error occurred; handle it
            log.error("Error on finish");
            // Unregister the channel with this selector
            selKey.cancel();
        }
    }

    if (selKey.isValid() && selKey.isReadable()) {
        readMessage(selKey);
    }

    if (selKey.isValid() && selKey.isWritable()) {
        writeMessage(selKey);
    }

    if (selKey.isValid() && selKey.isAcceptable()) {
    }

}

直到我们开始每秒发送大约100条消息并接收大约100条响应和100条收入消息并发送100条我们的响应(两种方式大约每秒400条消息)为止,它的工作情况一直很好,由于其他问题未知与我们的合作伙伴断开连接。 我们重新建立连接,但由于某种原因选择器不会切换为仅读取状态。 我们收到大量阅读后的消息,但无法发送任何内容。
有任何想法吗? 是我们这方面的操作系统问题吗? 选择器如何工作? 是通过某种逻辑还是自发地从读取切换为写入?

  1. 没有“从读取状态切换到写入状态”这样的事情。 一个套接字可以同时可读可写,并且Selector不会“切换”:它仅报告套接字上存在哪些状态。

  2. 如果写事件从未触发,那是因为套接字发送缓冲区已满,这表明对等方未从连接中读取。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM