Socat не закрывает TCP-соединение

Socat не закрывает TCP-соединение

Я использую socat 1.7.3.1-r0и запускаю следующую команду на alpine 3.3сервере Linux:

socat -d -d -d PTY,link=/dev/ttyFOOBAR,echo=0,raw,unlink-close=0 TCP-LISTEN:7000,forever,reuseaddr

Socatбудет прослушивать клиентов и создавать двунаправленную связь, передавая данные из виртуального последовательного порта /dev/ttyFOOBARклиенту и обратно по TCP. После отключения клиента socatследует выйти.

При установлении такого соединения socat регистрирует следующее:

I socat by Gerhard Rieger - see www.dest-unreach.org
I This product includes software developed by the OpenSSL Project for use in the OpenSSL Toolkit. (http://www.openssl.org/)
I This product includes software written by Tim Hudson ([email protected])
I setting option "symbolic-link" to "/dev/ttyFOOBAR"
I setting option "echo" to 0
I setting option "raw"
I setting option "unlink-close" to 0
I openpty({5}, {6}, {"/dev/pts/3"},,) -> 0
N PTY is /dev/pts/3
I setting option "forever" to 1
I setting option "so-reuseaddr" to 1
I socket(2, 1, 6) -> 7
I starting accept loop
N listening on AF=2 0.0.0.0:7000
I accept(7, {2, AF=2 CLIENT_IP:PORT}, 16) -> 8
N accepting connection from AF=2 CLIENT_IP:PORT on AF=2 172.20.0.2:7000
I permitting connection from AF=2 CLIENT_IP:PORT
I close(7)
I resolved and opened all sock addresses
N starting data transfer loop with FDs [5,5] and [8,8]

ssкоманда на сервере выводит:

Netid  State      Recv-Q Send-Q Local Address:Port                 Peer Address:Port                
tcp    ESTAB      0      0      172.20.0.2:7000                 CLIENT_IP:PORT

Проблема в том, что когда я отключаю клиента (выключая его), tcp-соединение все еще установлено, и никаких дополнительных записей в журнале от socat не поступает. ssпо-прежнему показывает соединение как ESTAB. Есть идеи, почему? Когда я снова подключаю клиента, в журналах появляется следующее:

W read(8, 0x7fa8f48c4020, 8192): Connection reset by peer
N socket 2 to socket 1 is in error
N socket 2 (fd 8) is at EOF
I poll timed out (no data within 0.500000 seconds)
I close(5)
I shutdown(8, 2)
I shutdown(8, 2): Socket not connected
N exiting with status 0

Но почему это происходит при подключении, а не при отключении?

решение1

Когда вы отключаете клиента, у него нет возможности сообщить другой стороне, что он уходит. Единственный способ узнать, что пир ушел, — это попытаться отправить ему что-нибудь и заметить, что он не отвечает.

Если в вашем приложении требуется обнаружение мертвого пира, вам придется реализовать обнаружение мертвого пира. Вы можете сделать это, включив опцию keepaliveв socat, но это все равно может занять несколько часов, чтобы обнаружить мертвого пира. Вы также можете сделать это, отправляя что-то периодически — отправка будет заблокирована, если пир мертв, вызывая обнаружение. Если другая сторона должна отправлять вам данные, вы можете прервать отправку, если вы не получили ожидаемые данные (возможно, с помощью socatфлага -T).

Связанный контент