1

这个问题是对这个先前提出的问题的扩展

我使用以下参数 实现了jxh给出的解决方案:

SO_KEEPALIVE = Enabled  
TCP_KEEPIDLE = 120 secs  
TCP_KEEPINTVL = 75 secs  
TCP_KEEPCNT = 1

那么为什么服务器仍然永远等待客户端响应呢?

我也在网上发现

kill <pid>实际上发送SIGTERM到给定的进程。

所以我ps -o pid,cmd,state在“杀死” telnet 应用程序后使用了命令。

我看到 telnet 进程仍然存在,但process state = T它处于STOPPED状态

PS:我对Linux Signals了解不多,请考虑一下。

4

2 回答 2

2

因为客户端还没有退出,仍然处于 STOPPED 状态,因此也没有关闭它的连接。

于 2013-08-19T10:26:05.327 回答
1

由于客户端进程仍然处于活动状态,因此内核中的 TCP 堆栈将处理它接收到的保持活动数据包,并将确认数据包返回给数据包的发送者。因此,即使连接确实空闲,连接也永远不会关闭,因为内核正在愉快地处理数据包。

在真实网络上,给定您的参数,如果来自客户端计算机的 ACK 丢失,连接将被关闭。在您的设置中,由于客户端和服务器位于同一台机器上,您的网络基本上是无损的。

我不清楚你是如何让你的telnet会话处于这种状态的。SIGTERM不会将进程置于停止状态。该进程在接收时进入停止状态SIGSTOP(通常是SIGTSTP,但似乎telnet忽略了那个)。我建议您可能错误地发送了该信号,或者您暂停了会话(使用^]z)。发生这种情况时,您应该已经在窗口中看到,带有您的 telnet 会话的窗口会生成如下输出:

[1]+  Stopped                 telnet ...

这是由外壳打印的。当telnet进程停止时,它不会处理,SIGTERM直到它被放置在前台之后。

A SIGKILL(用 完成kill -9 <pid>)将立即处理。

于 2013-08-19T16:26:19.273 回答