Java 11 Connection Reset overse, когда socket.close () называетсяJAVA

Программисты JAVA общаются здесь
Anonymous
Java 11 Connection Reset overse, когда socket.close () называется

Сообщение Anonymous »

Вопрос связан с программированием сокетов
во время приложения на основе миграции на основе сокетов от Java 8 до Java 11 Ошибка сброса подключения на конце клиента < /p>
Шаги: < /p>

Сочетное соединение принимается в нашем приложении от клиента Browser. inputSteam.read (this.data, смещение, оставшиеся). Это происходит в одной ветке. Если данные не доступны, все еще поток будет находиться в блоке чтения. < /Li>
Заклинание сокета может быть вызвано из другого потока. < /Li>
< /ul>
Наблюдения: < /p>
java 8. Проблема прикреплена ниже. Попробуйте с Java 8, а затем с Java 11 < /p>
// server thread class

import java.net.*;
import java.io.*;
import java.nio.channels.SelectionKey;
import java.nio.channels.Selector;
import java.nio.channels.ServerSocketChannel;
import java.nio.channels.SocketChannel;
import java.nio.channels.spi.SelectorProvider;
import java.util.Set;

public class ServerThread extends Thread {

private final int port;
private Socket s = null;
private InputStream in = null;

// Constructor with port
public ServerThread(int port) {
this.port = port;
}

public Socket getSocket() {
return this.s;
}

public void run() {

// Starts server and accept connection
try {
Selector socketSelector = SelectorProvider.provider().openSelector();
ServerSocketChannel serverSocketChannel = ServerSocketChannel.open();
serverSocketChannel.configureBlocking(false);

InetSocketAddress inetSocketAddress = new InetSocketAddress("127.0.0.1", port);
serverSocketChannel.socket().bind(inetSocketAddress);

serverSocketChannel.register(socketSelector, SelectionKey.OP_ACCEPT);

socketSelector.select();
Set selectedKeys = socketSelector.selectedKeys();

for (SelectionKey selectionKey : selectedKeys) {
if (selectionKey.isAcceptable()) {
ServerSocketChannel sSC =
(ServerSocketChannel) selectionKey.channel();

// Accept the connection
SocketChannel socketChannel = sSC.accept();
s = socketChannel.socket();
System.out.println("Client accepted");

s.setKeepAlive(true);
s.setTcpNoDelay(true);

// Takes input from the client socket
in = s.getInputStream();

int m = 0;
// Reads message from client
while (m != -1) {
try {
m = in.read(new byte[16]);
System.out.println(m);
} catch (IOException i) {
System.out.println("Got exception in server thread: " + i);
break;
}
}
System.out.println("Closing connection");
}
}
selectedKeys.clear();
} catch (IOException i) {
System.out.println("Got from server thread " + i);
}
}
}
--------------------------------------------------------------------------------------
// client class
import java.io .*;
import java.net .*;

public class Client {
private Socket s = null;
private InputStream in = null;

// Constructor to put IP address and port
public Client(String addr, int port) {
// Establish a connection
try {
s = new Socket(addr, port);
in = s.getInputStream();
System.out.println("Connected");
} catch (UnknownHostException u) {
System.out.println(u);
return;
} catch (IOException i) {
System.out.println(i);
return;
}

// String to read message from input
//String m = "";
int m = 0;
// Keep reading until "Over" is input
while (m != -1) {
try {
m = in.read(new byte[16]);
System.out.println(m);
} catch (IOException i) {
System.out.println("Got exception in client: " + i);
break;
}
}

// Close the connection
try {
s.close();
} catch (IOException i) {
System.out.println(i);
}
}
}
-------------------------------------------------------------------------------------
// main class

import java.io.IOException;

public class Main {

public static void main(String[] args) {
ServerThread s = new ServerThread(5000);
s.start();
Thread t = new Thread(() -> {
try {
Thread.sleep(10000);
s.getSocket().close();
} catch (IOException e) {
System.out.println("Got IO exception");
} catch (InterruptedException e) {
System.out.println("Got InterruptedException");
}
});
t.start();

Thread t1 = new Thread(() -> {
try {
Thread.sleep(5000);
Client c = new Client("127.0.0.1", 5000);
} catch (InterruptedException e) {
System.out.println("Got InterruptedException");
}
});
t1.start();

}
}
< /code>
Примечание:
Как работает фактическое приложение < /p>

Один поток запускается через время срока службы приложения, цель которого состоит в том, чтобы принять входящее соединение сокета. (Аналогичный код GIST как ServerThread.Class выше) Новый поток использует входной и выходной поток сокета для чтения и записи данных. Таким образом, ошибка сброса подключения на конце клиента. < /p>
java 8: on socket.close () вызов, отправляет пакет FIN в клиенту, поэтому не наблюдается проблемы, не наблюдаемой на конце клиента. < /p>
Код, вышеупомянутый, просто для воспроизведения проблемы. (Java 11 против Java 8 Изменение поведения) < /p>
Для легкость я написал код выше. Любой может попробовать с конца, чтобы наблюдать за вопросом

Подробнее здесь: https://stackoverflow.com/questions/796 ... ose-called

Вернуться в «JAVA»