这台虚拟机创建时没有启用 IP 转发,而它已经在运行 VPN 软件,于是直觉是带上标志从模板重建一遍。那次重建并不必要。Compute Engine 把 canIpForward 作为可更新的属性公开,文档中的更新路径会以 refresh 应用它,而不是重启。标志真正控制的范围很窄:没有它,平台会丢弃到达实例、但目标不是实例自身地址的数据包。转发其他机器流量的网关做的正是这件事,所以标志必须打开。此后的一切都属于客户机配置和路由,标志并不触及。

标志允许什么,不允许什么

关闭转发时,平台把实例当作端点。目标是实例自身地址的数据包会被投递;实例本应替他人转发的数据包则不会。

开启转发时,实例可以作为 VPC 路由的下一跳,这正是 VPN 设备需要的角色。标志并不涉及防火墙、客户机路由、隧道配置或返回路径,而且网关坏了,true 值仍然是一个坏掉的网关。

读取当前属性

在改动任何东西之前,先用只读的 describe 针对目标实例、项目和区域检查设置:

gcloud compute instances describe VM_NAME --project PROJECT_ID --zone ZONE --format='value(canIpForward)'

只有当这台虚拟机要充当下一条跳时,false 值才有意义。如果是,路径的其余部分仍需单独检查,因为这个属性只是更长链条中的一行。

更新现有实例

Google 的实例属性更新流程会导出当前资源、修改该属性并提交结果。这与创建时的 --can-ip-forward 标志是不同工作流,而能在运行中的虚拟机上生效的是前者。

先把定义导出到本地文件,并保留一份未改动的副本用于比较:

gcloud compute instances export VM_NAME --project PROJECT_ID --zone ZONE --destination=instance.yaml

在那个导出文件中,只设置该属性,不要改动其他任何内容:

canIpForward: true

保留整个资源,包括它的指纹。用一行 YAML 文档替换文件,或把无关的机器类型、磁盘或接口修改塞进同一次提交,正是属性变更变成故障的原因。

在允许任何实际变更之前,请更新机制校验该文件并报告它将需要什么:

gcloud compute instances update-from-file VM_NAME --project PROJECT_ID --zone ZONE --source=instance.yaml --most-disruptive-allowed-action=NO_EFFECT

这次校验运行不会启用转发。请阅读响应中关于无效属性和所需操作的内容。对于这一处孤立变更,文档中的操作是 REFRESH。如果结果要求重启,说明文件包含的内容多于你想改的那个属性,因此应检查文件,而不是批准重启。

以 refresh 限制应用已审阅的文件:

gcloud compute instances update-from-file VM_NAME --project PROJECT_ID --zone ZONE --source=instance.yaml --most-disruptive-allowed-action=REFRESH

确认操作完成,并再次运行 describe 命令。如果指纹不再匹配,说明在你编辑期间有别人改动了实例,因此应导出新的副本并重新审阅改动,而不是强行提交你那份过期文件。

客户机仍须路由数据包

云端权限不会把设备变成路由器。确认某条 VPC 路由把该虚拟机选为目标前缀的下一跳,并且客户机在启用自身转发策略的前提下在隧道与正确接口之间路由。

防火墙策略必须同时允许内部流量和外部监听。只打开 VPN 端口描述的是加密传输,对其中应用层交换只字未提。

最后,目的地需要一条回到客户端地址池的返回路径,或者设计必须有意识地转换源地址。如果目的地看到的是转换后的流量,就检查转换后的源;如果设计保留地址池,就在返回路由和访问规则中检查该地址池。在决定采用哪种设计之前加 NAT,会掩盖缺失的路由,并改变目的地看到的策略。

在 Linux 网关上,内核转发属于客户机配置。pfSense 设备有自己的等价设置,把 Linux 的 sysctl 命令照搬进去并不是对应步骤。

从需要访问的客户端验证

从 VPN 客户端测试到一个目标服务,而不是从网关本身测试。在网关上发起的连接使用不同的源,永远不会经过你刚刚启用的转发规则。

把该属性记录到管理该设备的任何地方。手工修正的虚拟机能一直工作,直到下一次替换悄悄把原始设置带回来,而那种失败看起来会像 VPN 软件的回归。

工作顺序:读取属性,导出并编辑一行,用 NO_EFFECT 验证,用 REFRESH 应用,确认客户机转发,然后从客户端测试。

相关文章