打开客户端的状态页,看到一个全球 IPv6 地址,人很容易得出结论:隧道已经可有可无。那个页面显示的只是一个地址,不是加密边界,不是私有路由表,也不是访问决策。VPN 通常同时承担三项任务,而 IPv6 只触及与共享稀缺地址有关的那一项。把一项服务从客户端一路走到监听端,才是看清哪项任务在变化后仍然存在的唯一办法。

先给任务命名,再移除工具

人们说「VPN」时,往往指的是三种安排之一,而三者失败的原因各不相同。访问某个团队发布的一个应用,是应用访问问题。加入一组已定义的私有网络,让多个站点能够互相到达,是路由关系。在并不完全掌控的基础设施之上维持一层稳定的管理覆盖,是带有自身地址规划的运维安排。

IPv6 为第一种安排移除了地址共享的障碍,在那里它确实起作用,因为直接地址可以取代转换器。对另外两种安排,它什么也改变不了,因为需求从来就不是地址稀缺。动手改配置之前,先写下你实际运行的到底是三者中的哪一种。

公网地址不是加密

全球范围的地址只告诉你一台主机可以从哪里被到达;它完全不说明抵达那里的流量是否被加密或认证。RFC 8504 的安全讨论把对 IPsec 实现的支持,与在 IPsec、TLS、SSH 及其他方式之间做更宽选择区分开来,而这正是把可达性读成保护时消失的区别。一个支持某种机制的协议栈只证明了该机制可用,从未证明这段流量真的走了它。具体到 IPsec,协商出的关联以及它选择的流量才决定什么受保护,而地址族是数据包的属性,不是针对它的策略。

可达性又是另一个问题。公网地址并不会让未经请求的流量到来,因为路由、防火墙和监听端各有一票,去掉 NAT 只是去掉一个过滤器,而不是全部。要判定隧道当初替掉的是这三者中的哪一个——如果有的话。

覆盖层仍然提供什么

覆盖层在三种情形下仍然物有所值。远程用户可能需要的是一组特定路由,而不是一个应用;两个站点可能需要一份私有可达性约定;运维方可能想要一种不随接入服务商更换而改变的编址。这三者都与 IPv4 地址短缺无关。

全球地址并不会让这些工作免于维护。整洁的内部规划,并不能让外部端点在服务商更换后继续响应;认证、重连和名称更新仍然需要有人负责。在关掉任何东西之前,先定好这些如何恢复。

走一遍即将公开的服务

从主机开始,列出真正在监听的东西,因为你批准的那个应用很少是机器上唯一的东西。ss -lntup 会打印每个 TCP 和 UDP 监听端及其绑定地址,并在权限允许时附上所属进程,一眼就能看出某个管理界面是在通配地址上,还是只在 loopback 上。如果你的协议栈把 IPv6 套接字分开保存,就用 ss -6 -lntup 再跑一遍。

然后按受众给每一行分类。自带认证与传输安全的应用端口,放在公网地址上也许没问题;而管理界面、指标端点和数据库端口通常不行。一个被批准的应用,只是对那个应用的判断,绝不是允许暴露共享同一台主机的所有服务。每一行的绑定地址会告诉你:暴露是已经存在,还是会被你计划中的改动创造出来。

两项测试,再决定关掉什么

在移除一层之前,先在纸上回答两个问题。第一,需求是否需要私有路由,也就是公网地址并不蕴含、接入服务商也不提供的可达性?第二,它是否需要一道保护边界,也就是对一条否则会明文穿越不可信路径的流量做加密与认证?如果对该服务两个答案都是「否」,隧道就是可以移除的候选;只要有一个是「是」,它就留下。

在双栈客户端上,对 IPv4 与 IPv6 分别跑同一项测试,因为受保护的 IPv4 流量说明不了 IPv6 路径的任何事。状态页里的全球 IPv6 地址不是泄漏的证据,缺少它也不是保护的证据。只关掉那些两个答案都已写下、并且仍然是「否」的服务,并在变更记录里注明是哪一问决定了它。

相关文章