近期发现生产的环境windows 2008 r2有较多的TCP连接,其中TIME_WAIT状态占据绝大部分。测试过程发现,windows 2016 和linux 处理效果就好很多。所以,我觉得很有必要,要把这个的原理说一下。同时,应该定个各个操作系统的大体的配置建议。
首先,time—wait是ok的。没有问题。只是过多可能会引发问题。

原理:
原理的介绍,大家可以看我名词的解释顺序,这个顺序就是实际连接的过程。
盗图一张:

下面描述tcp连接的建立过程和关闭过程:
1、建立连接协议(三次握手)
(1)客户端发送一个带SYN标志的TCP报文到服务器。这是三次握手过程中的报文1。
(2) 服务器端回应客户端的,这是三次握手中的第2个报文,这个报文同时带ACK标志和SYN标志。因此它表示对刚才客户端SYN报文的回应;同时又标志SYN给客户端,询问客户端是否准备好进行数据通讯。
(3) 客户必须再次回应服务段一个ACK报文,这是报文段3。
2、连接终止协议(四次握手)
由于TCP连接是全双工的,因此每个方向都必须单独进行关闭。这原则是当一方完成它的数据发送任务后就能发送一个FIN来终止这个方向的连接。收到一个 FIN只意味着这一方向上没有数据流动,一个TCP连接在收到一个FIN后仍能发送数据。首先进行关闭的一方将执行主动关闭,而另一方执行被动关闭。
(1) TCP客户端发送一个FIN,用来关闭客户到服务器的数据传送(报文段4)。
(2) 服务器收到这个FIN,它发回一个ACK,确认序号为收到的序号加1(报文段5)。和SYN一样,一个FIN将占用一个序号。
(3) 服务器关闭客户端的连接,发送一个FIN给客户端(报文段6)。
(4) 客户段发回ACK报文确认,并将确认序号设置为收到序号加1(报文段7)。
注:MSL(最大分段生存期)指明TCP报文在Internet上最长生存时间,每个具体的TCP实现都必须选择一个确定的MSL值.RFC 1122建议是2分钟,但BSD传统实现采用了30秒.TIME_WAIT 状态最大保持时间是2 * MSL,也就是1-4分钟.
命令查看现在的服务器上tcp连接的情况:
linux:
netstat -n|awk '/^tcp/{++S[$NF]}END{for (key in S) print key,S[key]}'
windows:
netstat -an | find "TIME_WAIT" /c
tcp连接过多影响:
会占用一点内存等性能;如果tcp连接过多,比如6万个左右,那就比较危险了,因为你的端口可能会不够用了。
修改:
linux:
如发现系统存在大量TIME_WAIT状态的连接,通过调整内核参数解决:
编辑文件/etc/sysctl.conf,加入以下内容:
net.ipv4.tcp_syncookies = 1
net.ipv4.tcp_tw_reuse = 1
net.ipv4.tcp_tw_recycle = 1
net.ipv4.tcp_fin_timeout = 30
windows:
修改注册表。重启才能生效,
或者重启explorer.exe进程。
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters
On the Edit menu, click New, DWORD Value
1. Value name:TcpTimedWaitDelay
2. Value data :<Enter a decimal value between 30 and 300 here>
针对nginx情况单独说明:
nginx连接: 短连接
nginx默认是短连接,那么系统TIME_WAIT的数量会变得比较多,这是由于nginx代理使用了短链接的方式和后端交互的原因,使得nginx和后端的ESTABLISHED变得很少而TIME_WAIT很多。这不但发生在安装nginx的代理服务器上,而且也会使后端的app服务器上有大量的TIME_WAIT。
可以调整的方式:
可以让nginx开启长连接模式。下面说一下相关参数。



注意:upstream模块下的keepalive特别说明一下:
The keepalive directive deserves special mention. NGINX will keep this number of connections per worker open to an upstream server. This connection cache is useful in situations where NGINX has to constantly maintain a certain number of open connections to an upstream server. If the upstream server speaks HTTP, NGINX can use the HTTP/1.1 Persistent Connections mechanism for maintaining these open connections.




