首页 / 内容指南 / 当前文章

Linux服务器SYN_RECV持续增长或连接超时:队列排查指南

发布于 2026-08-26 · xieyipai.com 编辑部

先固定故障监听 IP/端口和时间窗口,用 ss -lnt 查看监听队列,用 ss -nt state syn-recv 统计半连接来源;保存 /proc/net/netstat、nstat、应用进程 CPU/线程/文件描述符与负载均衡指标。分别在客户端、服务端和前置代理抓取 SYN、SYN-ACK、ACK:服务端发出 SYN-ACK但收不到 ACK,查回程路由、ACL、NAT 和源地址;握手完成却应用不处理,查 accept queue、事件循环和 worker。只有证据显示容量不足时才调整 backlog/somaxconn,并同步修应用处理能力。

本文目录(19 节)

直接答案

先固定故障监听 IP/端口和时间窗口,用 ss -lnt 查看监听队列,用 ss -nt state syn-recv 统计半连接来源;保存 /proc/net/netstat、nstat、应用进程 CPU/线程/文件描述符与负载均衡指标。分别在客户端、服务端和前置代理抓取 SYN、SYN-ACK、ACK:服务端发出 SYN-ACK但收不到 ACK,查回程路由、ACL、NAT 和源地址;握手完成却应用不处理,查 accept queue、事件循环和 worker。只有证据显示容量不足时才调整 backlog/somaxconn,并同步修应用处理能力。

一、确认监听socket与实际进程

执行:

ss -lntp
ss -lnt '( sport = :443 )'

确认监听地址、端口、进程/PID、Recv-Q 与 Send-Q 的含义。监听在 127.0.0.1 或错误 IPv4/IPv6 地址会导致外部不可达;端口由 Nginx/HAProxy监听时,后端应用队列不是客户端握手的第一现场。

二、量化SYN_RECV而不是只看截图

ss -nt state syn-recv '( sport = :443 )'
ss -nt state syn-recv '( sport = :443 )' | awk 'NR>1 {print $5}' | sort | uniq -c | sort -nr

记录数量、持续时间、源 IP/网段和目标地址。瞬时少量 SYN_RECV 是正常握手过程;持续增长、固定重传周期或集中异常来源才值得调查。注意 NAT 后大量合法用户可能共享源 IP,不能仅凭集中度封禁。

三、理解两类队列

Linux 监听路径涉及未完成握手的 SYN backlog 与已完成握手、等待应用 accept() 的队列。listen(backlog) 主要影响后者的上限,并受系统 somaxconn 等约束;半连接处理还有独立内核参数与 SYN cookies机制。

只把 somaxconn 调大不能修复 SYN-ACK 回程丢包,也不能让阻塞的应用更快 accept。先根据内核计数和抓包确认哪一类队列受压。

四、查看内核队列与握手计数

保存:

nstat -az
cat /proc/net/netstat
cat /proc/sys/net/core/somaxconn
cat /proc/sys/net/ipv4/tcp_max_syn_backlog
cat /proc/sys/net/ipv4/tcp_syncookies

重点比较故障前后 listen overflow/drop、SYN 重传、失败和 syncookie 相关计数(具体字段按当前内核文档解释)。看累计值要取时间差,机器运行数月后的大数字不等于当前事故。

五、双端抓包还原三次握手

在授权窗口限制接口、端口、时长与文件大小:

tcpdump -ni eth0 'tcp port 443 and (tcp[tcpflags] & (tcp-syn|tcp-ack) != 0)'

客户端 SYN 到达服务端、服务端 SYN-ACK 发出但客户端看不到,问题在回程或中间网络;客户端看到 SYN-ACK并发 ACK,服务端看不到 ACK,则查回程 ACK路径、NAT/ACL;三次都到达服务端但应用无请求,查 accept queue、TLS/应用层。

六、检查非对称路由与策略路由

多网卡、ECMP、策略路由、云浮动 IP 或 TUN/VPN 可能让 SYN 从接口 A 进入,SYN-ACK 从接口 B 以错误源地址离开,被防火墙或客户端丢弃。使用 ip route get 客户端IP from 服务IP、ip rule 和 conntrack 状态检查实际路径。

不要只用服务器自己 curl localhost验证。外部连接涉及完整回程、NAT 和安全策略。修复要保证源地址和路由对称或让网络设备正确支持非对称流量。

七、防火墙与conntrack压力

Netfilter、云安全组和负载均衡可能丢弃第三次 ACK 或已建立流量。查看 firewall counters、conntrack 使用率与丢弃日志。conntrack 表满时新连接可能被丢弃,但表现不一定只在 SYN_RECV。

不要直接清空 conntrack 或关闭防火墙,这会中断现有连接并扩大风险。先找高连接来源、超时配置和表容量,按变更流程处理。

八、应用accept不及时的症状

如果抓包显示握手完成,但 listen queue 持续接近上限、内核 ListenOverflows/ListenDrops增长,应用可能没有及时 accept。检查进程 CPU、GC、事件循环延迟、worker 数、线程阻塞、文件描述符和 accept() 错误。

反向代理还可能受 worker_connections、文件描述符和连接限制约束。调高内核队列只能缓冲短峰值;应用吞吐长期小于到达率,队列最终仍满。

九、backlog受应用和内核共同限制

应用调用 listen(fd, backlog) 提供期望值,内核再按 somaxconn 等限制。框架可能有自己的 backlog 配置,修改 sysctl却未重启/重新创建监听 socket,不一定改变现有行为。

记录应用实际启动参数和内核值,计算峰值到达率与可接受排队时间。修改后重建监听并用压力测试验证,不要把上限设到远超内存和处理能力。

十、SYN cookies的正确边界

SYN cookies 可在 SYN backlog 溢出时帮助处理连接,属于过载保护,不应替代正常容量规划。启用/触发情况要结合内核文档与计数;持续依赖意味着仍有攻击、流量突发或容量问题。

不要把 tcp_syncookies 当作吞吐调优开关。先修网络和应用,使用上游 DDoS 防护、速率限制和扩容应对攻击,并验证合法客户端兼容性。

十一、识别SYN Flood与合法突发

攻击可能使用伪造、分散源地址,表现为大量不完成握手;营销活动、客户端重连风暴和负载均衡健康检查也会造成真实高峰。结合源 ASN/网段、SYN/ACK完成率、User-Agent后续请求、业务事件和边缘防护数据判断。

不要在源地址可能伪造时依赖服务器逐 IP封禁。优先在具备容量和源验证能力的上游清洗/边缘处理,同时保留合法流量白名单和回滚。

十二、负载均衡器的双层队列

客户端到 LB 与 LB 到后端是两条 TCP 连接。前端 SYN_RECV不一定出现在后端;后端连接池耗尽也可能让客户端等待。分别查看 LB frontend/backend连接、队列、重试和健康状态。

抓包需在两侧关联时间和 request/connection ID。不要根据后端 ss 正常就排除前端网络,也不要把 LB 502/504全部归因于后端应用。

十三、IPv4与IPv6分别验证

双栈域名可能只有 IPv6路径丢 SYN-ACK,部分客户端失败而 IPv4正常。分别用 curl -4/-6、A/AAAA和两套抓包验证。检查监听 socket 是否覆盖双栈、IPv6 firewall和回程路由。

移除 AAAA只能作为明确无 IPv6服务能力时的受控回滚;长期应让发布的地址全部可用并监控。

十四、TIME_WAIT与SYN_RECV不要混淆

TIME_WAIT 是连接关闭后的正常状态,与半连接握手不同。大量 TIME_WAIT可能反映短连接负载,但调它不能直接解决 SYN_RECV。CLOSE_WAIT则说明应用未关闭已由对端关闭的连接。

按 TCP 状态分别统计并建立不同假设。不要使用一个“清理 TCP 连接”的脚本修改多个 sysctl,容易引入端口复用和可靠性问题。

十五、修复后的验收清单

在 canary 上覆盖正常连接、短突发、持续高并发、客户端中断、回程丢包和应用暂停 accept。确认 SYN_RECV短暂消退、accept queue有余量、overflow/drop不增长,P95/P99连接时间和失败率达标。

再验证 LB、IPv4/IPv6、滚动发布和 DDoS 防护切换。监控 SYN速率、握手完成率、SYN_RECV年龄、listen queue、内核增量计数、conntrack、应用 accept延迟和文件描述符。

常见问题 FAQ

大量SYN_RECV一定是攻击吗?

不一定。回程网络丢包、ACL、客户端异常和合法突发都可能导致。需要双端抓包和握手完成率证据。

调大somaxconn能解决吗?

它主要影响已完成连接等待 accept 的队列上限,不能修复 SYN-ACK回程或应用长期处理不足。

SYN cookies应该一直开启吗?

按内核与安全策略配置,但它是过载保护,不是容量与网络根因的替代。持续触发应告警和调查。

为什么服务器抓到ACK但应用仍没有请求?

可能握手完成后卡在 accept queue、TLS握手、文件描述符或应用事件循环。继续检查监听队列和应用层。

如何安全抓包?

限制接口、端口、时长和文件大小,只收集必要头部信息,遵守授权并保护客户端 IP 等敏感元数据。

总结

SYN_RECV 增长的核心是判断第三次握手为什么没有完成,同时不要忽略已完成连接队列。以 ss、内核增量计数和双端抓包建立证据,再查回程路由、ACL、conntrack、应用 accept和负载均衡。队列参数只能吸收短峰值,真正修复必须让网络握手完整、应用处理速率匹配到达率,并通过压力与故障演练验证。

官方资料