声明:本文由 Gemini 2.0 Flash Thinking Experimental 辅助编写

本文记录并分享一次由华硕路由器(包括刷入 Merlin 固件的型号)引起的智能家居设备(主要为米家设备)间歇性离线问题的排查过程及解决方案。由于篇幅所限,本文将侧重于问题分析与解决,涉及的相关技术名词请读者自行查阅了解。

解决方案

此问题普遍存在于使用华硕路由器(包括刷入 Merlin 固件)的用户中。关闭路由器设置中的“系统管理 -> 开启 WAN 中断的浏览器导页通知”功能,即可彻底解决此问题。

问题现象

用户有时会在手机客户端上发现智能家居设备离线,但登录路由器管理界面查看时,却显示这些设备的 WiFi 连接状态正常。在同一局域网内尝试 Ping 这些设备,也能得到正常的响应。

然而,通过在路由器端使用 tcpdump 抓包分析,可以观察到设备发送了 DNS 查询请求以解析域名,但路由器却应答了 10.0.0.1 这个错误的地址。这直接导致设备后续连接服务器的操作均失败。

抓包结果显示路由器错误应答 DNS 请求

问题根源

问题的核心在于华硕路由器提供的“开启 WAN 中断的浏览器导页通知”功能。当 WAN 连接中断时(例如,每 48 小时重新拨号),路由器内部的防火墙会修改 iptables 规则,将所有 DNS 请求重定向 (REDIRECT) 到本地的 18018 端口。路由器上的 wanduck 进程监听在这个端口,并对收到的所有 DNS 请求都回应 10.0.0.1,目的是引导用户访问路由器断网提示页面。

按照设计,当 WAN 连接恢复时,上述 iptables 规则应该被删除,从而使网络流量恢复正常。然而,这里可能存在一个潜在的疏忽……

REDIRECT 涉及到连接跟踪 (conntrack)。这意味着,只要一个连接的第一个数据包匹配了 iptables 规则,接下来的数据包,无论 iptables 规则如何变化,只要 conntrack 内的对应条目仍然有效,REDIRECT 就会持续生效。wanduck 进程是一个常驻进程,即使 WAN 连接已恢复正常,只要有 DNS 请求发送到 18018 端口,它仍然会响应。

更糟糕的是,智能家居设备在连接服务器失败后,会不断地尝试重新解析域名。对于 conntrack 来说,它看到了智能设备的 DNS 请求,也看到了 wanduck 的 DNS 应答,因此它会认为连接仍然处于活动状态,从而使 REDIRECT 规则持续生效。

简而言之,一旦 WAN 中断时,有设备发送了 DNS 解析请求,并且 wanduck 进行了错误应答,设备就会因为无法连接到真正的服务器而不断尝试重新解析,并重复得到错误的 DNS 应答。这种情况下,只要连接跟踪条目没有过期或被清除,这个重定向关系就不会解除,设备也就陷入了永无止境的死循环。 (实际上,只要此时客户端或服务端有一方停止发送请求一段时间,或者在 WAN 恢复时刷新 conntrack 表即可解决。)

连接跟踪状态展示