设置TIME_WAIT TCP
我们正试图调整一个应用程序接受通过TCP消息,并使用TCP的一些内部消息。 在进行负载testing时,我们注意到响应时间显着下降(然后完全停止),因为同时向系统发出更多的请求。 在此期间,我们看到很多TCP连接处于TIME_WAIT
状态,有人build议将TIME_WAIT
环境variables从默认的60秒降低到30秒。
据我所知 , TIME_WAIT
设置本质上是设置连接closures后TCP资源再次可用的时间。
我不是一个“networking人”,对这些事情知之甚less。 我需要很多链接文章中的内容,但是有一点“虚弱”了。
- 我想我明白为什么
TIME_WAIT
值不能设置为0,但可以安全地设置为5? 什么10? 什么决定了这个值的“安全”设置? - 为什么这个值的默认值是60? 我猜测,比我聪明的人有很好的理由select这个合理的默认值。
- 还有什么我应该知道压倒价值的潜在风险和好处?
TCP连接由元组(源IP,源端口,目标IP,目标端口)指定。
会话closures之后有一个TIME_WAIT状态的原因是因为在向你(或者来自你的请求某种types的响应)的途中networking中可能还有活的数据包。 如果您要重新创build相同的元组,并且其中一个数据包出现了,则会将其视为您的连接的有效数据包(并且可能由于sorting而导致错误)。
所以TIME_WAIT时间一般设置为数据包最大年龄的两倍。 这个值是你的数据包在networking丢弃前允许达到的最大时间。
这就保证了,在你允许创build一个具有相同元组的连接之前,所有属于该元组以前化身的数据包将会死亡。
这通常决定了你应该使用的最小值。 数据包的最大使用时间取决于networking属性,例如卫星的使用寿命高于LAN使用寿命,因为数据包有更多的要求。
通常,只有发出“主动closures”的端点才会进入TIME_WAIT状态。 所以,如果可能的话,让你的客户端发出主动closures,这将使TIME_WAIT在客户端而不在服务器上。
看到这里: http: //www.serverframework.com/asynchronousevents/2011/01/time-wait-and-its-design-implications-for-protocols-and-scalable-servers.html和http://www.isi .edu / touch / pubs / infocomm99 / infocomm99-web /有关详细信息(后面还解释了为什么由于不考虑TIME_WAIT的协议devise而不能始终可用)。
Pax对TIME_WAIT的原因是正确的,为什么你应该小心降低默认设置。
更好的解决scheme是改变用于套接字始发端的端口号。 一旦你这样做,你不会真正在意等待个别套接字的时间。
对于侦听套接字,可以使用SO_REUSEADDR来允许侦听套接字绑定,尽pipeTIME_WAIT套接字位于附近。
在Windows中,您可以 通过registry 进行更改 :
; Set the TIME_WAIT delay to 30 seconds (0x1E) [HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\TCPIP\Parameters] "TcpTimedWaitDelay"=dword:0000001E
设置tcp_reuse比改变time_wait更有用,只要你有参数(内核3.2及以上版本,不幸的是,取消所有版本的RHEL和XenServer的资格)。
删除值(特别是VPN连接用户的值)会导致出站连接上不断重新创build代理隧道。 使用低于默认Linuxconfiguration的默认Netscaler(XenServer)configuration时,Chrome有时必须重新创build代理隧道多达十次来检索一个网页。 不重试的应用程序(如Maven和Eclipse P2)只是失败。
参数的原始动机(避免重复)由指定所有TCP请求中包含时间戳的TCP RFC进行冗余。
我一直使用20个线程的testing程序加载testing服务器应用程序(在Linux上)。
在959,000次连接/closures周期中,我有TIME_WAIT中有44,000次连接失败和数千个套接字。
在closures调用之前,我将SO_LINGER设置为0,并且在testing程序的后续运行中没有连接失败,在TIME_WAIT中没有less于20个的套接字。
TIME_WAIT可能不是罪魁祸首。
int listen(int sockfd, int backlog);
根据Unixnetworking编程卷1,积压被定义为完成连接队列和不完整连接队列的总和。
如果你有3个完成的连接(ESTABLISHED状态)和2个不完整的连接(SYN_RCVD状态),并且有另一个SYN连接请求。 TCP堆栈忽略了SYN数据包,知道它会在其他时间重新传输。 这可能会导致退化。
至less这是我一直在读的。 ;)