Escrevi um pequeno programa que interage com um servidor em uma porta específica. O programa funciona bem, mas:
Uma vez que o programa foi encerrado inesperadamente, e desde então essa conexão de soquete é mostrada no CLOSE_WAIT
estado. Se eu tento executar um programa, ele trava e tenho que forçar o fechamento, o que acumula ainda mais CLOSE_WAIT
conexões de soquete.
Existe uma maneira de liberar essas conexões?
Respostas:
CLOSE_WAIT
significa que seu programa ainda está em execução e não fechou o soquete (e o kernel está esperando por isso). Adicione-p
anetstat
para obter o pid e, em seguida, mate-o com mais força (comSIGKILL
se necessário). Isso deve acabar com suasCLOSE_WAIT
tomadas. Você também pode usarps
para localizar o pid.SO_REUSEADDR
é para servidores eTIME_WAIT
sockets, portanto, não se aplica aqui.fonte
Conforme descrito por Crist Clark .
fonte
close()
ouclosesocket()
, dependendo de qual plataforma você está usando.Também estou tendo o mesmo problema com um servidor Tomcat mais recente (7.0.40). Ele fica sem resposta uma vez por alguns dias.
Para ver as conexões abertas, você pode usar:
Conforme mencionado neste post , você pode usar
/proc/sys/net/ipv4/tcp_keepalive_time
para visualizar os valores. O valor parece estar em segundos e o padrão é 7200 (ou seja, 2 horas).Para alterá-los, você precisa editar
/etc/sysctl.conf
.fonte
Embora muitas conexões CLOSE_WAIT signifiquem que há algo errado com seu código no início e isso não é uma boa prática aceita.
Você pode querer verificar: https://github.com/rghose/kill-close-wait-connections
O que este script faz é enviar o ACK que a conexão estava esperando.
Isto é o que funcionou para mim.
fonte
Você pode fechar soquetes à força com o
ss
comando; oss
comando é uma ferramenta usada para despejar estatísticas de soquete e exibe informações de maneira semelhante (embora mais simples e rápida) ao netstat.Para matar qualquer socket no estado CLOSE_WAIT, execute isto (como root)
fonte
Deve ser mencionado que a
Socket
instância tanto no cliente quanto na extremidade do servidor precisa ser chamada explicitamenteclose()
. Se apenas uma das extremidades invocarclose()
, o socket permanecerá no estado CLOSE_WAIT.fonte
Também é importante notar que, se seu programa gerar um novo processo, esse processo pode herdar todos os identificadores abertos. Mesmo após o término do seu próprio programa, esses identificadores herdados ainda podem estar vivos por meio do processo filho órfão. E eles não aparecem necessariamente da mesma forma no netstat. Mas mesmo assim, o soquete ficará em CLOSE_WAIT enquanto o processo filho estiver ativo.
Tive um caso em que estava executando o ADB. O próprio ADB gera um processo de servidor se ainda não estiver em execução. Isso herdou todos os meus identificadores inicialmente, mas não apareceu como o proprietário de nenhum deles quando eu estava investigando (o mesmo acontecia com o macOS e o Windows - não tenho certeza sobre o Linux).
fonte