打印机在调用打印方法时卡住了



这是一个线程,处理来自服务器端的输入和输出:

    public void run() {
        Thread currentThread = Thread.currentThread();
        while (!currentThread.isInterrupted()) {
            SocketChannel socketChannel = null;
            try {
                socketChannel = serverSocketChannel.accept();
                readFromSocket(socketChannel);
            } catch (ClosedByInterruptException e) {
                // closed due to interrupt
                connected = false;
            } catch (IOException e) {
                if (!isInterrupted()) {
                    e.printStackTrace();
                }
                connected = false;
            } finally {
                quietClose(socketChannel);
            }
        }
    }
    /**
     * Reads an message from socketChannel and executes
     * {@link AbstractServer#handleMessage(String)}. Initializes
     * {@link #writer} with the socketChannel.
     * 
     * @param socketChannel
     * @throws IOException
     */
    public void readFromSocket(SocketChannel socketChannel) throws IOException {
        reader = null;
        writer = null;
        try {
            reader = new BufferedReader(new InputStreamReader(socketChannel.socket().getInputStream()));
            if (writer == null) {
                writer = new PrintWriter(socketChannel.socket().getOutputStream(), true);
            }
            String message;
            while ((message = reader.readLine()) != null) {
                handleMessage(message);
            }
        } catch (ClosedByInterruptException e) {
            throw e;
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            quietClose(reader);
            quietClose(writer);
        }
    }

如果我调用print方法,线程被卡住了。这意味着"before"被打印出来了,但"after"却从未出现过。打印机的CheckError方法返回false!

    /**
     * Sends a message to the client.
     * 
     * @param message
     */
    public void sendMessage(final String message) {
        System.out.println("before");
        writer.print(message);
        System.out.println("after");
        writer.flush();
    }

它在一个AbstractServer中,由两个不同的服务器使用。第一个之前已经使用过,并且总是没有问题(现在仍然如此)。另一个是新的,导致了这个问题。对于每个初始化的连接(两个具有不同端口的本地主机),绝对只有一个写入器。

客户端Datafetcher看起来像这样:

protected void fetchDataFromSocket() {
    if (socketDataFetcher != null) {
        socketDataFetcher.interrupt();
    }
    socketDataFetcher = new Thread(new Runnable() {
        @Override
        public void run() {
            while (!Thread.currentThread().isInterrupted()) {
                try {
                    String message = socketConnection.readLine();
                    if (messageHandler != null) {
                        messageHandler.handleMessage(message);
                    }
                } catch (IOException e) {
                    Thread.currentThread().interrupt();
                }
            }
        }
    });
    socketDataFetcher.start();
}

它也和另一个几乎一样,只有很小的变化,实际上不会引起问题。是什么原因导致印刷工人这样做呢?

编辑:如果我不启动socketDataFetcher在客户端,打印机不会被卡住!

虽然我没有看到声明,但reader和writer对象(在readFromSocket()方法中引用)看起来可能是成员变量。我会担心读写器不是线程安全的。我会看看关于删除这些成员变量,看看你是否仍然有问题的作家。

最新更新