双重 NAT 与你的 VPN:客户端能用,服务器不行
两台做地址转换的路由器很少挡住出站的 VPN 客户端;在它们后面架服务器则难得多,尤其当外层是运营商级 NAT 时。
你的路由器位于另一台路由器之后,WAN 地址是私有地址,而 VPN 客户端依然能连上。这个组合会让以为双重 NAT 必然打断隧道的人感到意外,但出站连接恰恰是地址转换最擅长的场景。把 VPN 服务器放在同样的两层之后,才是通常失败的那种情况。动手之前,先把连接的方向画出来。
先画出连接的方向
打开内层路由器的状态页,记下它的 WAN 地址,再和某个公共服务报告给你的地址作比较。若两者不同,说明你的路由器与互联网之间至少有一台转换设备。若 WAN 地址落在 100.64.0.0/10 之内,外层转换多半属于运营商,你无法控制它。这两点决定了后续步骤里哪些还有可能奏效。
curl -s https://ifconfig.me
ip -brief address
traceroute -n 1.1.1.1
双重 NAT 不等于双重 VPN。地址转换只改写地址和端口,既不会多出一条加密隧道,也不做任何加密。把这两个概念分开很重要,因为对应的解法完全不同,其中一种需要你和运营商沟通,而不是去改设置页。
出站:客户端发问,转换设备做映射
出站隧道从你的机器发出的数据包开始,所以每台转换设备都能建立映射并把回包放进来。协议、端口和空闲超时决定了这条映射能不能存活到真正有用。多数家用路由器无需任何配置就能处理这件事。
真正出现的故障通常与超时和协议支持有关,而不是路由器的数量。沉默几分钟后掉线的隧道,是映射过期,keepalive 是标准解法。IPsec 有标准的 NAT-traversal 扩展,所以说它不能穿越地址转换纯属错误。若隧道根本建立不起来,先看对端和凭据,别急着怪拓扑。
wg show
ping -c3 10.8.0.1
如果出站隧道在某个网络能用、换一个网络就不能用,请停下来。这个比较针对的是网络,而不是路由器的数量。
入站:端口转发只覆盖你自己拥有的设备
架服务器是反方向:一条新连接从互联网进来,必须穿过每一层才能到达你的机器。内层路由器上的端口转发规则,只有在外层转换也把流量送到你这里时才有用。重复本地规则并不会让你获得运营商设备的控制权。
nc -vz 203.0.113.10 51820
ss -lunp 'sport = :51820'
把内层路由器的 WAN 地址和你观察到的公网地址作比较,并记下每个值来自哪里。若 WAN 地址是私有地址或落在共享地址段,外层就在做你无法配置的转换。在为一个晚上都可能白费的规则折腾之前,先问清运营商支持哪种入站可达性。拆掉一台路由器或大范围关掉防火墙不是诊断,为一个开放端口付出这种代价并不划算。
如果外层属于运营商且它不做转发,请停下来。此时可支持的答案是换一种接入方式或使用中继,而不是在你这边再加一条规则。
一次只测一个变量
每次只改一处并记录结果,因为双重 NAT 的路径比单路由器路径有更多变量。保持配置文件和设备不变,再换一个接入网络作比较。留意是协商失败、空闲后会话掉线,还是只有私有目的地不通。这三种现象分别指向三个不同的层。
journalctl -u wg-quick@wg0 -n 30 --no-pager
ip route get 10.20.30.40
重叠的私有子网是另一个陷阱,再多地址转换也修不好。如果家里网络和远端网络使用同一网段,无论中间隔多少台转换设备,路由冲突都会出现。给其中一侧重新编号,是唯一持久的答案。
远端网关同样值得关注,因为它的转发规则和回程路由可能就是缺失的那块。一条通过认证的隧道,仍可能没有可用的应用路径,而这种故障从客户端一侧看毫无区别。当你能说清是哪个方向失败、由哪一层负责时,这趟排查就结束了。