Hyper-V 里的虚拟机用宿主机 VPN 吗?取决于虚拟交换机
宿主机 VPN 不是整台机器范围的设置。虚拟交换机类型决定来宾流量是被桥接、经宿主机路由还是被隔离,而这会改变答案。
在 Hyper-V 宿主机上安装 VPN 客户端,在那里打开浏览器,出口地址会变;在虚拟机里打开同一个页面,可能仍显示旧地址,或什么都显示不出来。常见的结论是虚拟机坏了,或者必须启用拆分隧道。这两点都不成立。VPN 客户端不是机器的属性;它是一组路由、一块虚拟网卡,而且常常是绑定在特定接口上的过滤器。来宾流量是否真的会遇到这套机制,取决于来宾使用的虚拟交换机。
这个谬论,直接说清楚
有一种看法认为,装在宿主机上的 VPN 会保护整台机器(包括虚拟机),因为虚拟机不过是运行在那台机器上的一个进程。这种看法让人安心,因为杀毒软件和宿主机防火墙通常确实如此。网络路径却不是这样。
只有当宿主机对来宾的帧进行路由或过滤时,宿主机的 VPN 协议栈才会碰到它。把这句话写在便签上,因为下面每一种情况都是它的变体。
三种交换机,三条路径
外部虚拟交换机把一块虚拟网卡绑定到物理网卡,来宾以自己的 MAC 地址通过这层绑定发送帧。来宾成为物理网络中的对等节点,拥有自己的 DHCP 租约、网关和 DNS 服务器。宿主机的 VPN 默认路由留在宿主机协议栈里,不会搬运这些帧,因为它们是被桥接而不是经宿主机路由的。这也是在 Wi-Fi 网卡上使用外部交换机的糟糕之处:大多数无线驱动不会为第二个 MAC 地址承载帧。
内部虚拟交换机把来宾连接到宿主机的虚拟网卡。它本身不提供互联网出口;宿主机上的 NAT 对象负责转换,相关说明见 Hyper-V NAT 指南。现在来宾的数据包确实进入宿主机的路由与 NAT 路径,因此 VPN 客户端的路由和过滤器又变得重要。正是这种布置下,虚拟机才真正跟随宿主机 VPN,kill switch 也可能把来宾彻底断掉。
专用虚拟交换机没有宿主机网卡,也没有上行链路。来宾只能彼此通信,所以如果专用交换机上的虚拟机没有互联网,原因就是缺少路由器,与 VPN 无关。
默认交换机是另一套布置
Windows 附带一个默认交换机,把内部交换机与 NAT 和 DNS 代理结合在一起。它的子网由宿主机挑选,重启后可能变化,而且与你自建的 NAT 网络不是同一个对象。把它当成实验网络来重建,正是人们最后落得两个 NAT、来宾仍然没有路由的原因。
如果虚拟机位于默认交换机上,先读出来宾拿到的地址,并在动 VPN 客户端之前把它与宿主机的 NAT 表比较。来宾网关与 NAT 前缀不匹配,比任何客户端设置都能解释更多故障。
四个能定论的事实
在改动任何东西之前,先收集这些:交换机类型及其上行链路、虚拟机所接的网卡、来宾自己的地址、网关和 DNS,以及宿主机的 NAT 与默认路由状态。只读命令是 Get-VMSwitch、Get-VMNetworkAdapter -VMName "TestVM"、Get-NetNat 和 Get-NetRoute -DestinationPrefix 0.0.0.0/0;在来宾内部,ipconfig /all 给出其余信息。
然后决定来宾应该做什么。如果它应当留在 VPN 之外,就向服务商申请针对那条确切路径的受支持例外,因为排除宿主机上的可执行文件并不会豁免被转发的虚拟机流量。如果它应当使用 VPN,就确认客户端对虚拟机流量有文档记载的处理方式,而不是假设宿主机上的浏览器测试已经覆盖了这一点。
只有来宾内部的测试才算证据。从来宾检查出口地址、解析一个内部名称、重连 VPN 再重复。宿主机浏览器的结果不能代替其中任何一项。
这个谬论的代价
人们为了让测试通过而关掉 kill switch、添加静态路由,或者删除并重建交换机。每种捷径都会改变故障模式:来宾可能沿着没人设想的路径上网,或者外部交换机重新绑定物理网卡时宿主机失去连接。
重新绑定外部交换机会中断宿主机自身的访问,所以要留一条带外通道,并且在仍在诊断时不要删除交换机。正确的结果是来宾按预期走的路径,包括它如何重连、如何失败,而不是一次页面加载换来的绿色对勾。
持久的答案是清单里每台虚拟机一行:它使用哪个交换机,由哪个组件提供网关。把这些写下来,下一次 VPN 变更就是一次查表,而不是一整个下午的猜测。