Я получаю следующую ошибку при попытке чтения из сокета. Я делаю readInt() над этим InputStream, и я получаю эту ошибку. При просмотре документации можно предположить, что клиентская часть соединения закрыла соединение. В этом сценарии я являюсь сервером.
У меня есть доступ к файлам журнала клиента, и он не закрывает соединение, а его файлы журнала предполагают, что я закрываю соединение. Итак, у кого-нибудь есть идея, почему это происходит? Что еще нужно проверить? Возникает ли это, когда есть локальные ресурсы, которые, возможно, достигают пороговых значений?
Я отмечаю, что у меня есть следующая строка:
socket.setSoTimeout(10000);
непосредственно перед readInt(). Для этого есть причина (долгая история), но просто любопытно, существуют ли обстоятельства, при которых это может привести к указанной ошибке? У меня запущен сервер в моей IDE, и так получилось, что моя IDE застряла на точке останова, а затем я заметил, что точно такие же ошибки начали появляться в моих собственных журналах в моей IDE.
В любом случае, просто упоминаю об этом, надеюсь, не отвлекающий маневр.
Переведено автоматически
Ответ 1
Существует несколько возможных причин.
Другой конец намеренно сбросил соединение способом, который я не буду здесь документировать. Прикладное программное обеспечение делает это редко и, как правило, некорректно, но это не является чем-то необычным для коммерческого программного обеспечения.
Чаще всего это вызвано записью в соединение, которое на другом конце уже закрыто в обычном режиме. Другими словами, ошибка протокола приложения.
Это также может быть вызвано закрытием сокета, когда в буфере приема сокета остаются непрочитанные данные.
В Windows "прерывание соединения по программному обеспечению", что не то же самое, что "сброс подключения", вызвано сетевыми проблемами при отправке с вашей стороны. Об этом есть статья в базе знаний Microsoft.
Ответ 2
Сброс подключения просто означает, что был получен TCP RST. Это происходит, когда ваш одноранговый узел получает данные, которые он не может обработать, и на это могут быть различные причины.
Самый простой - это когда вы закрываете сокет, а затем записываете дополнительные данные в выходной поток. Закрывая сокет, вы сообщаете своему партнеру, что закончили общение, и он может забыть о вашем подключении. Когда вы все равно отправляете больше данных по этому потоку, одноранговый узел отклоняет их с помощью RST, чтобы сообщить вам, что он не прослушивает.
В других случаях подключенный брандмауэр или даже сам удаленный хост могут "забыть" о вашем TCP-соединении. Это может произойти, если вы долгое время не отправляете никаких данных (2 часа - обычный тайм-аут) или потому, что одноранговый узел был перезагружен и потерял информацию об активных соединениях. Отправка данных по одному из этих несуществующих подключений также вызовет RST.
Обновление в ответ на дополнительную информацию:
Внимательно посмотрите на вашу обработку SocketTimeoutException. Это исключение возникает, если превышен настроенный тайм-аут при блокировке операции с сокетами. Состояние самого сокета не изменяется при возникновении этого исключения, но если ваш обработчик исключений закроет сокет, а затем попытается выполнить запись в него, вы окажетесь в состоянии сброса соединения. setSoTimeout() предназначен для предоставления вам чистого способа прервать read() операцию, которая в противном случае могла бы быть заблокирована навсегда, без выполнения грязных действий, таких как закрытие сокета из другого потока.
Ответ 3
Всякий раз, когда у меня возникают подобные странные проблемы, я обычно сажусь с помощью такого инструмента, как WireShark, и смотрю на необработанные данные, передаваемые взад и вперед. Вы можете быть удивлены, когда что-то отключается, и вы получаете уведомление только при попытке чтения.
Ответ 4
Вам следует очень тщательно проверить полную трассировку,
У меня есть серверное приложение для сокетов, и я исправил java.net.SocketException: Connection reset случай.
В моем случае это происходит при чтении из clientSocket Socket объекта, соединение с которым по какой-либо причине закрыто. (Потеря сети, сбой брандмауэра или приложения или предполагаемое закрытие)
На самом деле я восстанавливал соединение, когда получил сообщение об ошибке при чтении из этого объекта сокета.
SocketclientSocket= ServerSocket.accept(); is = newBufferedReader(newInputStreamReader(clientSocket.getInputStream())); intreaded= is.read(); // WHERE ERROR STARTS !!!
Интересно то, что for my JAVA Socket если клиент подключается к моему ServerSocket и закрывает свое соединение, ничего не отправляя, is.read() вызывается повторно.Кажется, что из-за бесконечного цикла while для чтения из этого сокета вы пытаетесь читать из закрытого соединения. Если вы используете что-то вроде приведенного ниже для операции чтения;
while(true) { Receive(); }
Затем вы получаете stackTrace примерно так, как показано ниже, снова и снова
java.net.SocketException: Socket is closed at java.net.ServerSocket.accept(ServerSocket.java:494)
Что я сделал, так это просто закрыл ServerSocket, обновил свое соединение и стал ждать дальнейших входящих клиентских подключений
Это восстанавливает мое соединение при потерях неизвестного клиентского сокета
privatevoidtryReConnect() { try { ServerSocket.close(); //empty my old lost connection and let it get by garbage col. immediately clientSocket=null; System.gc(); //Wait a new client Socket connection and address this to my local variable clientSocket= ServerSocket.accept(); // Waiting for another Connection System.out.println("Connection established..."); }catch (Exception e) { String message="ReConnect not successful "+e.getMessage(); logit();//etc... } }
Я не смог найти другого способа, потому что, как вы видите на изображении ниже, вы не можете понять, потеряно соединение или нет без try and catch , потому что все кажется правильным. Я получил этот снимок, пока получал Connection reset непрерывно.