TIME_WAIT 是什么
主动关闭连接的一方在发出最后一个确认后会进入等待状态,停留两倍报文最大生存时间(在常见实现中固定为约六十秒),之后连接才彻底消失。它存在的理由有两个:一是万一对方没收到最后的确认会重发关闭请求,本方还能重传确认;二是让这条连接四元组的残留报文在网络中过期,避免串进之后建立的新连接。它是保护机制,不是故障。
基本信息
| 停留时长 | 两倍最大报文生存时间,常见实现中固定约六十秒 |
|---|---|
| 所在方 | 主动发起关闭的一方 |
| 作用一 | 保证最后的确认丢失时仍可重传 |
| 作用二 | 让旧连接的重复报文过期,避免污染新连接 |
| 影响 | 同一四元组在停留期内不能被复用 |
典型使用场景
- 高频短连接客户端:每次请求都新建连接并主动关闭,本地端口消耗很快
- 反向代理与网关:作为主动关闭方,会积累大量等待状态的连接
- 压测与拨测:短时间产生海量连接,容易把端口或连接跟踪表打满
- 排查偶发连接被复用错乱:检查是否存在四元组快速复用的异常场景
观测与处置
观测与处置
ss -tan state time-wait | wc -l # 统计当前停留期的连接数量
ss -tan state time-wait | awk '{print $4}' | awk -F: '{print $NF}' | sort | uniq -c | sort -rn | head # 看哪些本地端口被占用
sysctl net.ipv4.tcp_tw_reuse # 出站连接复用开关,客户端与服务之间场景可评估开启
sysctl net.ipv4.tcp_max_tw_buckets # 数量上限,超限会被强制回收并留下日志
sysctl net.ipv4.tcp_fin_timeout # 注意:它影响的是另一侧等待状态,与停留期无关相关参数怎么理解
| 参数 | 实际影响 | 调优建议 |
|---|---|---|
| 出站连接复用 | 允许新连接复用仍处于停留期的四元组 | 客户端与代理侧可评估开启,服务器监听侧不需要 |
| 数量上限 | 限制同时停留的连接数 | 超过上限会被强制回收并打日志,配合监控观察 |
| 另一侧等待超时 | 控制被动关闭方的等待 | 与停留期无关,别拿它来治停留期问题 |
| 端口范围 | 决定可用本地端口数量 | 端口耗尽时可扩大范围,但更要先改连接使用方式 |
端口耗尽怎么查
- 统计本地端口分布,看是否集中在少数端口上反复出现同一四元组
- 确认应用是否在用短连接:能改成长连接或连接池的优先改用法
- 检查是否有一批客户端固定源端口访问同一目标,四元组被写死导致无法复用
- 扩大可用端口范围只是缓解,根因通常是连接使用方式不合理
不要启用已被移除的快速回收参数:它在较新的内核中已不存在,早期在地址转换环境下还曾导致大量连接被丢弃,属于被废除的做法。
停留期本身无法通过参数缩短为该机制的固定值,它是协议正确性的一部分。真正要防的不是「有多少连接在等待」,而是「短连接高频且主动关闭」把本地端口或连接跟踪表打满。
客户端侧的正确做法
- 优先复用连接或使用连接池,从根上减少主动关闭的次数
- 接入层与后端之间使用长连接,避免每次请求都重建连接
- 监控端口使用率与连接跟踪表占用,接近上限时提前扩容或调整用法
- 出现端口耗尽先看调用模式,再考虑扩大可用端口范围