
简介Wireshark 数据包分析实战第3版中的一节故障排查案例适合网络运维、安全分析与协议学习人员参考。内容围绕分公司工作站访问总部应用失败的场景演示如何从 DNS A 记录查询响应入手利用 Wireshark 抓包逐层定位问题先是 DNS 服务器返回 server failure随后分公司 DNS 通过 TCP 53 端口与总部 DNS 通信SYN 包未获回应说明区域传送失败最终经过中心办公室流量嗅探和路由器配置检查发现路由器仅放行 UDP 53 而阻断 TCP 53导致 DNS 区域传送无法完成。案例将 DNS 查询机制、区域传送原理、TCP/UDP 差异与抓包分析思路相结合有助于提升真实网络故障的诊断能力。资源为 1 个 PDF 格式文档大小 644KB已有 327 人学习。读者可从中获得完整排查路径和协议细节解读适合作为数据包分析入门或进阶时的辅助材料。1. 一个 DNS SERVFAIL 就能让整个分公司瘫痪先搞清故障链条再动手DNS 故障是网络排错里最折磨人的一类服务器明明活着、应用日志一片干净、客户端却集体报“连不上”浏览器转几圈最后给你一个“无法解析服务器地址”。很多运维的第一反应是重启 DNS 服务、改 hosts、甚至重装客户端结果折腾一整天问题照旧。这套路我太熟悉了——直到打开 Wireshark 抓到前两个数据包才发现一切表象都指向一条被忽略的链路。本文复盘的就是某抓包分析实战手册里一个经典案例工作站访问总部应用服务器失败第一包 DNS 查询返回“服务器故障”根因却藏在 53 端口 TCP 流量被路由器丢弃这个细节里。适合正在被 DNS 解析失败、区域传送异常、SERVFAIL 报错卡住的网络工程师和运维同学。2. 现象初判A 记录查询返回服务器故障先确认不是客户端“玄学”问题2.1 原始抓包里到底发生了什么两个数据包还原故障起点先看场景工作站172.16.16.101试图访问托管在总部应用服务器172.16.16.200上的应用程序捕获文件里只有两个数据包。第一个包是工作站发给 DNS 服务器172.16.16.251的 DNS 请求查询应用服务器的 A 记录——也就是把应用服务器的域名解析成172.16.16.200这个 IP。第二个包是 DNS 响应应答码却是“服务器故障”SERVFAIL整包只有错误标志没有携带任何查询结果。打开抓包文件后我一般先用下面的命令快速还原这两个包的轮廓tshark -r capture.pcap -Y dns -T fields \ -e frame.number -e ip.src -e ip.dst \ -e dns.qry.name -e dns.qry.type -e dns.flags.rcode执行后你会看到类似这样两行第一行是172.16.16.101 → 172.16.16.251的查询dns.qry.type为1A 记录第二行是响应包dns.flags.rcode为2。这里-Y dns过滤出所有 DNS 报文-e指定要打印的字段dns.flags.rcode就是应答码字段。看到 rcode 为 2基本可以确认问题出在 DNS 解析链路本身而不是客户端配置或应用层故障。2.2 别把 SERVFAIL 当成“服务器宕机”应答码是定位的第一把钥匙很多同学看到“服务器故障”几个字就慌了直接判断是 DNS 服务器挂了。这个误判在实战中出现的频率极高。DNS 应答码RCODE是排查时的第一把钥匙常见取值就三个RCODE含义典型场景0NOERROR查询成功能拿到解析结果2SERVFAILDNS 服务器无法完成查询通常是上游链路或权威数据问题3NXDOMAIN域名确实不存在关键区别在于SERVFAIL 意味着 DNS 服务器“想查但查不到”服务器进程本身是活着的NXDOMAIN 才是域名本身不存在。这个案例里 DNS 服务器能正常回应查询说明它在线真正断掉的是它获取解析数据的链条。如果此时你去重启 DNS 服务相当于对着错误的方向开火问题当然不会消失。所以收到 SERVFAIL 第一步不是动服务而是把排查焦点移到“服务器是从哪里拿到这些记录的”。2.3 为什么要切换端口镜像而不是拔线插嗅探器确定了问题在 DNS 链路后手册里做了一个很关键的操作把嗅探器留在原地只改变交换机端口镜像设置。很多人习惯直接拔掉网线把嗅探器插到 DNS 服务器上这在生产环境里是高风险动作——会中断业务流量而且如果 DNS 服务器是虚拟机你根本没地方插线。端口镜像SPAN的作用是把交换机某个端口的流量复制一份给监听端口不影响原始流量转发是生产环境抓包的默认姿势。这一步的意义在于对分公司来说客户端发出的 DNS 请求最终由172.16.16.251这台 DNS 服务器负责迭代解析。要看清这台服务器为什么回 SERVFAIL就必须把嗅探目标从客户端网段切到 DNS 服务器所在网段。捕获结果保存为stranded_branchdns.pcap这个文件里多出来的那个“怪异”数据包才是整个故障的真正突破口。3. 根因深挖看到 TCP 53 的 SYN 数据包故障性质就变了3.1 DNS 为什么突然走 TCP大响应、EDNS 与区域传送三种场景打开stranded_branchdns.pcap后除了之前看到的查询和响应还多了一个额外数据包。这个包看起来非常“违和”它尝试与中心办公室的首选 DNS 服务器172.16.16.250的标准 DNS 服务端口 53 通信但协议类型不是我们熟悉的 UDP而是 TCP并且是一个干净的 SYN 握手包。在大多数人的认知里DNS 就等于 UDP 53看到 TCP 53 的包第一反应是“是不是有什么非法扫描流量混进来了”。实际上 DNS 走 TCP 有三种正经场景一是 DNS 响应超过 UDP 承载上限通常是 512 字节启用 EDNS 后可能更大二是 DNS 区域传送Zone Transfer用于在 DNS 服务器之间同步资源记录三是某些解析器主动选择 TCP 重试。对照这个案例分公司 DNS 服务器向总部 DNS 服务器发起 TCP 连接方向是“服务器对服务器”且没有先看到大体积 UDP 响应基本可以断定这不是普通查询而是区域传送。tshark -r stranded_branchdns.pcap -Y tcp.port 53 \ -T fields -e frame.number -e ip.src -e ip.dst \ -e tcp.flags.syn -e tcp.flags.ack这条命令过滤出所有 53 端口的 TCP 包重点看 SYN 和 ACK 标志位。如果只看到syn1, ack0的包而没有对应的syn1, ack1响应说明 TCP 三次握手压根没建立起来。TCP 不像 UDP 那样“发了就不管”握手失败是一个强信号——要么包没到对端要么对端拒绝连接。3.2 SYN 发出后没有任何 ACK 响应最可能丢在中间链路区域传送为什么会失败从协议层面看TCP 连接建立失败只有三种可能源端没发出、中间网络丢弃、目的端拒绝。源端这里已经看到 SYN 包了可以排除目的端如果活着且服务正常一般会回 RST 或 SYN-ACK而不是完全沉默。剩下的最大嫌疑就是中间链路——也就是连接分公司和中心办公室的路由器。这里有一个实战中容易犯的方向性错误一看到 TCP 握手失败就去查 DNS 服务器配置、查区域传送权限设置这属于检查“服务端愿不愿意接”。但更常见的情况是包根本就没到服务端。判断方法很简单在总部 DNS 服务器入方向再抓一次包。如果总部那边完全看不到这个 SYN问题就百分百在中间路由器上而不是 DNS 服务器本身。手册里明确提到“没有给出中心办公室 DNS 服务器的流量捕获文件因为根本就没有”——这句话翻译过来就是SYN 数据包从未到达服务器中间设备是唯一的嫌疑对象。3.3 区域传送失败如何传导成客户端的 SERVFAIL把整条故障链串起来就非常清晰了分公司用户访问总部应用服务器需要先解析应用服务器的域名。分公司 DNS 服务器是总部 DNS 服务器的从属服务器它没有独立维护这些记录而是依赖从总部同步资源记录。总部 DNS 服务器是被查询应用的权威 DNS 服务器。分公司 DNS 服务器要完成解析必须先把总部那边的 A 记录“搬”到自己这里这个过程就是区域传送。区域传送走 TCP 53SYN 包被路由器丢弃导致分公司 DNS 服务器一直缺少应用服务器的 A 记录。客户端来查询时分公司 DNS 服务器手里没有数据、上游也同步不下来只能回一个 SERVFAIL。这条链路解释了为什么客户端看到的是“服务器故障”而不是“超时”——分公司 DNS 服务器确实响应了只是它给不出答案。排查这类问题一定要顺着“数据从哪来”这个思路走而不是盯着最后那一跳的响应结果发呆。4. 逐段定位与修复SYN 没到总部服务器问题锁定路由器 ACL4.1 分段抓包法包在哪一段消失故障就在哪一段前面网络是黑匣子分段抓包是打开黑匣子的唯一方式。我的排查顺序固定如下客户端网段抓包确认请求发出、响应返回的情况这里是 SERVFAIL。分公司 DNS 服务器网段抓包确认它是否向上游发起查询或区域传送这里看到 TCP SYN。总部 DNS 服务器入方向抓包确认包是否抵达这里什么都抓不到说明中间断了。路由器两侧分别抓包定位丢弃点。第五步是最终实锤。在这个案例里分公司 DNS 服务器的 SYN 包没有到达总部服务器那么问题必然出在两个办公室之间的路由器上。判断依据不需要复杂的工具只要在路由器入口、出口各做一次镜像对比两次抓包结果包在哪个方向“消失”问题就在哪个方向的那台设备。4.2 实锤路由器只放行了 UDP 53把 TCP 53 静默丢弃技术员查看路由器配置后找到了罪魁祸首中心办公室的路由器被配置成只允许 53 端口的 UDP 流量进入而 53 端口的 TCP 流量被 ACL 规则阻止。这是一种非常隐蔽的配置错误——从表面看DNS 服务“没有被封”因为 UDP 53 是通的实际效果却是区域传送这条关键链路被无声无息地切断。下面给出这个场景下最常见的 ACL 配置形态帮助你对比自己的设备ip access-list extended DNS-IN permit udp any any eq domain deny ip any any问题就在第二行它只放行了 UDP 53把 TCP 53 连同所有其他流量一起拒之门外。ACL 默认隐式拒绝所有未匹配的流量所以 TCP SYN 包会被静默丢弃不会触发 ICMP 报错抓包时看起来就是“发了没回”。修复方法是在deny之前追加一条允许 TCP 53 的规则ip access-list extended DNS-IN permit udp any any eq domain permit tcp any any eq domain deny ip any any追加规则后原 ACK 包和区域传送的数据流就能正常通过了。注意这里any any eq domain对应的是“所有来源访问 53 端口”如果实际环境里区域传送只发生在特定的主从服务器之间更稳妥的做法是把any换成具体的服务器 IP缩小放行范围。4.3 修复后的验证区域传送恢复客户端解析回到 NOERROR改完 ACL 之后我一般会按顺序做三个验证确保问题真正闭环# 1. 在分公司 DNS 服务器上测试区域传送是否成功 dig 172.16.16.251 应用服务器域名 AXFR # 2. 模拟客户端向分公司 DNS 查询 A 记录 dig 172.16.16.251 应用服务器域名 A # 3. 在总部 DNS 服务器入方向重新抓包确认 TCP 53 流量到达 tshark -i eth0 -Y tcp.port 53第一条命令会从分公司 DNS 服务器直接发起一次完整的区域传送请求如果配置修复成功能看到一串资源记录被传输过来第二条命令模拟客户端视角此时应答码应该从 SERVFAIL 变成 NOERROR并返回172.16.16.200第三条命令确认 SYN 包能顺利到达总部服务器。三步全部通过才说明修复没有留下死角——我在实际排错中经常看到有人改完配置就收工第二天问题复现就是漏了回归验证这一步。5. 避坑清单DNS 排错里最容易误判的 5 个常见问题5.1 看到 SERVFAIL 就去重启 DNS 服务器现象客户端大量报“DNS 解析失败”抓包看到应答码是 SERVFAIL运维第一反应是重启 DNS 服务或清缓存。原因SERVFAIL 表示 DNS 服务器想查但查不到进程本身是健康的问题出在上游链路、区域传送或权威数据同步上。解决先看应答码区分故障类型再用分段抓包定位是“发不出去”还是“拿不回来”不要动服务。5.2 只在客户端一个点抓包把问题定性为“DNS 服务器不回包”现象客户端抓包看到请求发出后没有正常响应直接断定 DNS 服务器有问题。原因中间链路丢包和设备过滤同样会导致客户端看不到响应客户端的抓包只能证明“这一段不通”证明不了是谁丢的。解决至少抓三个点——客户端、本地 DNS、上游/权威 DNS对比数据包的到达情况哪个点开始看不到流量问题就在那个点之前的设备上。5.3 过滤条件只写udp.port 53把关键包漏掉现象分析抓包文件时只过滤了udp.port 53从头到尾没看到异常判定“网络是好的”。原因DNS 区域传送走 TCP 53在大多数 DNS 服务环境里默认就存在只过滤 UDP 就把这条关键链路整个忽略了。解决排查 DNS 故障时把过滤条件写成port 53同时覆盖 TCP 和 UDP再结合tcp.flags.syn判断连接是否建立成功。5.4 不区分“包没到对端”和“对端没回包”方向性错误现象SYN 包没有收到 SYN-ACK排错时一直在检查目标 DNS 服务器的配置、权限和监听状态。原因TCP 握手失败可以是目的端拒绝也可以是中间路由器静默丢弃两种原因的处理方向完全不同。解决在目标服务器入方向单独抓包确认包是否到达没到达就顺着链路往前找不要对着服务器瞎折腾。5.5 改完 ACL 或防火墙不做回归验证现象前一天改了防火墙规则第二天用户反馈同样的故障又出现了。原因很多防火墙同时存在多条规则新加的放行规则可能被后面的拒绝规则覆盖或者改的是错误的接口方向。解决改完立即做端到端验证既测试区传送又测试正常解析必要的话在两端同时抓包对比确认业务流量真的通了再宣布修复完成。6. 快速定位这类 DNS 故障的固定套路面对 DNS 解析失败、SERVFAIL、区域传送异常这类问题我现在的套路已经固化成三步每一步都有明确的判断标准。第一步客户端抓包定性。用dns.flags.response 1过滤出所有响应包看应答码再用dns.flags.rcode 2把所有 SERVFAIL 挑出来确认故障类型。第二步本地 DNS 服务器抓包定段。重点看它是否向上游发起了 TCP 53 的连接用tcp.flags.syn 1 tcp.flags.ack 0找到所有握手请求再确认有没有对应的tcp.flags.syn 1 tcp.flags.ack 1响应。没有响应就不要急着查服务器配置而是继续往下游走。第三步在权威或上游 DNS 入方向抓包定责。这里需要一个判断准则如果 SYN 到了而没有任何回应重点查服务器本身的监听和防火墙如果 SYN 根本没到重点查中间路由器。验证工具上dig比 nslookup 好用得多用dig DNS服务器 域名 A看正常解析用dig DNS服务器 域名 AXFR测试区域传送返回 NOERROR 且带资源记录才算真正恢复。Wireshark 的显示过滤器里我会同时打开port 53、tcp.flags.syn 1、dns.flags.rcode三组条件确保 TCP 和 UDP 两个维度的流量都在视野内。那次故障过后我养成了一个习惯凡是 DNS 类报错先强制把“客户端 → 本地 DNS → 上游/权威 DNS”三步抓包走完再动任何配置。这条流程帮我挡掉了至少三次“看起来是 DNS 挂了、实际上是中间设备过滤”的翻车现场。希望这一套思路也能帮你少走点弯路。本文还有配套的精品资源点击获取