一、问题描述

近期,在内网环境中,部分业务设备与内网服务器集群频繁断开连接。经分析,发现问题由异常的 TCP-RST 报文引发,导致设备不断重连。
基本网络拓扑如下图所示:
notion image
嵌入式开发同事通过抓取wifi路由器的空口包,分析报文后反馈断联是由服务端发起的。
Wi-Fi 空口包(Air Interface Packet)是指通过无线电磁波(空中接口)传输的Wi-Fi数据包。它是Wi-Fi设备(如路由器、手机、电脑)之间通信的基本单元,包含了数据、控制信息以及协议头尾等字段。
使用 Wireshark 分析抓包数据可以看到,IP 地址为 11.115 的服务器在回复了 seq=9482 的 TCP-ACK 报文后,立即发送了一个相同序列号的 TCP-RST 报文,导致当前连接被重置。
notion image

二、TCP 发送 RST 报文的常见原因

TCP 发送 RST 报文通常出于以下几类原因:

1. 连接请求到未监听端口

  • 场景:客户端尝试连接未监听端口,服务器直接返回 RST 报文。
  • 原因:服务器无对应套接字处理请求,直接拒绝。

2. 异常关闭后仍收到数据

  • 场景:一方已关闭连接,另一方继续发送数据。
  • 示例
    • 进程崩溃,系统关闭连接并发送 RST。
    • CLOSED 状态下收到数据。

3. 收到不期望的报文

  • 序列号无效或端口/IP 不匹配。
  • 半开连接状态下,一方重启后收到旧数据。

4. 应用层主动重置

  • 应用强制关闭(如 SO_LINGER 设置超时为 0)。
  • 因错误(如超时、资源耗尽)导致终止连接。

5. 中间设备干预

  • 防火墙/NAT 检测异常流量或安全策略阻断。
  • IDS/IPS 等安全设备伪造 RST 阻断连接。

6. 协议错误或异常

  • ACK 确认号异常。
  • 报文格式错误,如 SYN 和 FIN 同时置位。

7. 半开连接检测

  • 网络异常导致一方掉线,另一方发送数据后收到 RST。

8. 系统或资源问题

  • 内存或端口不足,系统发送 RST 释放资源。

9. TCP 握手异常

  • SYN 洪泛攻击防护。
  • 握手阶段收到异常 ACK,返回 RST。

10. Keep-Alive 探测失败

  • Keep-Alive 探测超时后,可能直接发送 RST。
 

三、问题深入排查

通过排查服务器和服务状态,我们排除了大部分常见原因,最终聚焦于:
  • 应用层主动重置
  • 中间设备干预
由于本次问题中使用的 MQTT Broker 是 EMQX,排查其内部逻辑相对困难。这时我们注意到异常 TCP-RST 报文与正常业务报文存在明显差异:TTL 值不同
notion image
 

四、TTL 差异分析

在 TCP/IP 协议中,TTL用于限制数据包在网络中的传播范围。每经过一台路由器,TTL 减 1,直至为 0 丢弃。
不同操作系统的初始 TTL 值各不相同,例如:
  • Windows:128
  • Linux系统:64
在 Linux 上,可通过以下命令查看当前默认 TTL:
通常,在稳定网络环境中,同一 TCP 连接中的数据包,其 TTL 值应保持一致。因此,这里出现 TTL 差异,提示我们考虑一个关键问题:
这个 RST 报文真的来自服务器吗?

五、进一步验证

为了确认,我们在 11.115 服务器上使用 tcpdump 抓包,得到以下信息:
 
notion image
notion image
分析发现,异常 TCP-RST 报文的 TTL 异常,且 IP 层的源 MAC 地址也与正常流量不同。
notion image
进一步查询该 MAC 地址,发现其归属一家安全设备厂商。由此基本确认,该 RST 报文是某个中间安全设备伪造发送的。

六、最终定位与解决

经与公司 IT 和安全部门沟通,确认是内网防火墙设备对接入公司网络的路由器设置了白名单。近期部分白名单到期未续签,导致防火墙开始拦截流量,并伪造 RST 报文重置连接。

七、经验总结

在许多网络环境中,判断 RST 报文是否由中间安全设备注入,可借助 TTL 分析:
  • 某些安全设备发出的 RST 报文,TTL 通常为 64、128、255 等固定值。
  • 通过与正常流量的 TTL 对比,可以反推出拦截设备的大致位置。
当然,也存在部分设备在伪造 RST 报文时调整 TTL,使其难以追踪,此时可能需要逐跳排查。

八、相关资料

抓包、分析、复盘:一站式解决物联网断联难题树莓派4B运行YOLO11:轻量化目标检测实践
Loading...