欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

TCP连接中的TIME_WAIT状态

程序员文章站 2022-04-24 13:33:14
...

根据《UNIX网络编程》卷1,TCP的状态转换图可以得知:执行主动关闭的那端(假设客户端)经历了TIME_WAIT状态,该状态停留在那个状态的持续时间是最长分节期(maximum segment  lifetime,MSL)的两倍,称为2MSL。

TIME_WAIT状态的持续时间在1min~4min之间。MSL是任何IP数据包能够在因特网上存活的最长时间。每个数据包在最大跳数(255)之内在网络上的时间不会超过MSL秒。网络在路由失效后重新找到一条连通的路。在此期间如果发生路由环路,TCP超时未收到确认包会重新发送该数据分组,该数据分组正确到达,不久路由修复,环路中的数据包也到达目的地,这个分组叫做漫游的重复分组。

TIME_WAIT状态存在的两个理由是:

1. 可靠的实现TCP全双工连接的终止;

2. 允许老的数据分组在网络中消逝

关于第一个理由:假设最终的ACK丢失了,服务端将重新发送FIN,因此客户必须维护状态信息,以允许它重新发送那个ACK。要是客户端不维护状态信息,响应一个RST给服务器,服务器认为是错误。如果TCP打算执行所有必要的工作以彻底终止某个连接上两个方向的数据流,必须处理连接终止序列4个分节中任何一个分节丢失的情况。

关于第二个理由:假设新建的连接与前一个连接IP地址和端口一样,TCP必须防止来自某个老的连接的数据分组在该连接终止后出现,从而被误解为新连接的新数据分组,为了做到这一点,TCP将不给处于TIME_WAIT状态的连接发起新的连接。一个方向上数据包最多MSL存活期,另一个方向应答最多存活MSL,通过实施这个规则,就能保证每个成功连接的TCP,来自先前连接的老的数据分组都已经在网络中消逝了。

现实来讲,刚终止的./server 重启启动时,需要等一会儿,可采用启用“端口重用”将setsockopt的第四个参数设为1.

    int on = 1;
    setsockopt(listenfd, SOL_SOCKET, SO_REUSEADDR, &on, sizeof(on));