5

I have a server that has the following printed in the log

Caused by: java.io.IOException: Connection reset by peer
        at sun.nio.ch.FileDispatcherImpl.write0(Native Method)
        at sun.nio.ch.SocketDispatcher.write(SocketDispatcher.java:47)
        at sun.nio.ch.IOUtil.writeFromNativeBuffer(IOUtil.java:93)
        at sun.nio.ch.IOUtil.write(IOUtil.java:65)
        at sun.nio.ch.SocketChannelImpl.write(SocketChannelImpl.java:471)
        at org.apache.tomcat.util.net.NioChannel.write(NioChannel.java:134)
        at org.apache.tomcat.util.net.NioBlockingSelector.write(NioBlockingSelector.java:101)
        at org.apache.tomcat.util.net.NioSelectorPool.write(NioSelectorPool.java:157)
        at org.apache.tomcat.util.net.NioEndpoint$NioSocketWrapper.doWrite(NioEndpoint.java:1238)
        at org.apache.tomcat.util.net.SocketWrapperBase.doWrite(SocketWrapperBase.java:670)
        at org.apache.tomcat.util.net.SocketWrapperBase.flushBlocking(SocketWrapperBase.java:607)
        at org.apache.tomcat.util.net.SocketWrapperBase.flush(SocketWrapperBase.java:597)
        at org.apache.coyote.http11.Http11OutputBuffer.flushBuffer(Http11OutputBuffer.java:519)
        at org.apache.coyote.http11.Http11OutputBuffer.flush(Http11OutputBuffer.java:260)
        at org.apache.coyote.http11.Http11Processor.flush(Http11Processor.java:1494)
        at org.apache.coyote.AbstractProcessor.action(AbstractProcessor.java:279)
        at org.apache.coyote.Response.action(Response.java:168)
        at org.apache.catalina.connector.OutputBuffer.doFlush(OutputBuffer.java:317)

I know that the client closed the Connection for some reason, but still the server is writing data. And at this time, the client will return the reset flag "RST", and the server's log will get the Connection reset by peer

To replicate it, I made the server sleep for few seconds and also created a client as such:

 private void executePostMethod() throws IOException, InterruptedException {
        Map<String, String> responseMap = new HashMap<>();
        String data = "{\"id\":\"XYZ123\",\"name\":\"John Doe\",\"accountNumber\":\"ABC123\"}";
        URL urlObject = new URL("\"http://localhost/v1/name/validate\"");
        System.out.println("Creating Connection");
        Socket socket = new Socket(InetAddress.getByName(urlObject.getHost()), 7080);
        System.out.println("Connection Established");

        PrintWriter printWriter = new PrintWriter(socket.getOutputStream());
        printWriter.println("POST " + urlObject.getFile() + " HTTP/1.0");
        printWriter.println("Host: " + urlObject.getHost());
        printWriter.println("Content-Length: " + data.length());
        printWriter.println("Content-Type: " + "application/json");
        printWriter.println();   //Writing an empty line just to notify the server the header ends here
        // and next thing written will the data/content
        printWriter.println(data);
        printWriter.println();
        printWriter.flush();
        Thread.sleep(5000);
        socket.setSoLinger(true, 0);
        socket.close();
    }

Before the server sends the response, the close the socket and the line socket.setSoLinger(true, 0); I believe, sends the RST packet. But I get the org.apache.catalina.connector.ClientAbortException: java.io.IOException: Broken pipe error instead of Connection reset by peer.

How to reproduce java.io.IOException: Connection reset by peer ?

UPDATE

I analyzed the TCP connection and this is what I got. The server receives the RST packet before it tries to send the data to the client

enter image description here

Now from what I know, if the client sends RST packet to the server, the server gets Connection reset by peer , all I get it Broken pipe.

Mohendra Amatya
  • 371
  • 6
  • 24
  • Try setting SO_LINGER after you open the socket, and removing the sleep. – Kayaman Apr 30 '21 at 07:56
  • I did that too, I kept the SO_LINGER line below this line Socket socket = new Socket(InetAddress.getByName(urlObject.getHost()), 7080); and removed the Thread.sleep(5000) line too, but still I got broker pipe. Or you mean the sleep from the server? – Mohendra Amatya Apr 30 '21 at 08:00
  • `Broken pipe` and `connection reset by peer` are two messages for the same condition. You have succeeded in your quest. – user207421 May 02 '21 at 06:34

2 Answers2

1

This might be of help to anyone trying to figure out the error and its cause.

The above mentioned program does work, but I found out that it is server dependent. I tried the above code in a different server and I got

Caused by: java.io.IOException: Connection reset by peer
Mohendra Amatya
  • 371
  • 6
  • 24
0

This client/server example replicates it:

import java.net.InetSocketAddress;
import java.net.Socket;
import java.nio.ByteBuffer;
import java.nio.channels.ServerSocketChannel;
import java.nio.channels.SocketChannel;

public class Test {
    private static final int port = 1234;
    public static void main(String[] args) throws Exception {
        if (args.length == 1) { // client
            final Socket socket = new Socket(args[0], port);
            socket.setSoLinger(true, 0);
            socket.close();
        } else { // server
            ServerSocketChannel serverSocket = ServerSocketChannel.open();
            serverSocket.socket().bind(new InetSocketAddress(port));
            SocketChannel client = serverSocket.accept();
            client.read(ByteBuffer.allocate(1));
        }
    }
}

To wit:

$ java Test.java &         # start the server
$ java Test.java 127.0.0.1 # start the client
Exception in thread "main" java.io.IOException: Connection reset by peer
        at java.base/sun.nio.ch.FileDispatcherImpl.read0(Native Method)
        at java.base/sun.nio.ch.SocketDispatcher.read(SocketDispatcher.java:39)
        at java.base/sun.nio.ch.IOUtil.readIntoNativeBuffer(IOUtil.java:276)
        at java.base/sun.nio.ch.IOUtil.read(IOUtil.java:245)
        at java.base/sun.nio.ch.IOUtil.read(IOUtil.java:223)
        at java.base/sun.nio.ch.SocketChannelImpl.read(SocketChannelImpl.java:353)
        at Test.main(Test.java:18)
[1]+  Exit 1                  java Test.java
Evgeniy Berezovsky
  • 18,571
  • 13
  • 82
  • 156