flannel使用host-gw模式

Flannel 的 host-gw 模式要求所有节点(Node)必须位于同一个二层网络(L2 网络) 中,这是由其核心工作原理决定的。理解这个限制需要深入分析 host-gw 的工作机制:

host-gw 的核心工作原理

  1. 路由即网关:

    • Flannel 在每个节点上为其他节点的 Pod 网段创建主机路由(Host Route)

    • 这条路由告诉本机的 Linux 内核:“要访问目标 Pod 网段(如 10.244.2.0/24),其下一跳(Gateway)就是目标 Pod 所在节点的物理 IP 地址(如 192.168.1.102)。”

    • 例如,在节点 192.168.1.101 上,Flannel 会添加一条类似的路由:

      ip route add 10.244.2.0/24 via 192.168.1.102
  2. 直接转发:

    • 当节点 192.168.1.101 上的 Pod(10.244.1.10) 想和节点 192.168.1.102 上的 Pod(10.244.2.10)通信时:

      • 源 Pod 发送包到目标 IP 10.244.2.10

      • 源节点的内核根据路由表匹配到目标网段 10.244.2.0/24 的路由:下一跳是 192.168.1.102

      • 源节点直接将数据包的二层帧(Ethernet Frame) 的目标 MAC 地址设置为 192.168.1.102 对应的 MAC 地址(通过 ARP 解析获得)。

      • 数据包被发送到物理网络。

为什么必须同二层(L2)?

关键在于数据包是如何从源节点到达目标节点的物理 IP(即路由的下一跳 via 地址):

  1. ARP 请求与 MAC 地址解析:

    • 源节点要发送数据包给下一跳 192.168.1.102,它首先需要知道 192.168.1.102 的 MAC 地址

    • 源节点在本地二层广播域(即同一个 VLAN/子网) 内广播一个 ARP 请求Who has 192.168.1.102? Tell 192.168.1.101

    • 只有与源节点 192.168.1.101 在同一个二层网络(同一个交换机或通过 Trunk 互连的交换机) 上的设备才能收到这个广播。

    • 目标节点 192.168.1.102 收到 ARP 请求后,用它的 MAC 地址回复源节点 192.168.1.101

  2. 直接二层可达性:

    • 一旦源节点知道了目标节点物理 IP 对应的 MAC 地址,它就可以构造一个以太网帧,目标 MAC 地址就是目标节点的物理网卡 MAC。

    • 这个以太网帧会被源节点的网卡发出,通过二层交换机直接转发到目标节点的物理网卡上。

    • 目标节点收到这个帧后,解封装,看到目标 IP 是 10.244.2.10(属于它的 PodCIDR),于是将其转发给本机上对应的 Pod 容器。

 

Flannel 的 host-gw 模式,它的工作原理非常简单,为了方便叙述,我用这张图为“host-gw 示意图”:

Node 1 上的 Infra-container-1,要访问 Node 2 上的 Infra-container-2。

当你设置 Flannel 使用 host-gw 模式之后,flanneld 会在宿主机上创建这样一条route路由规则。

以 Node 1 为例:

# ip route
...
10.244.1.0/24 via 10.168.0.3 dev eth0

这条路由规则的含义是:

目的 IP 地址属于 10.244.1.0/24 网段的 IP 包,应该经过本机的 eth0 设备发出去(即:dev eth0);并且,它下一跳地址是 10.168.0.3。

而从 host-gw 示意图中我们可以看到,这个下一跳地址对应的,正是我们的目的宿主机 Node 2。

一旦配置了下一跳地址,那么接下来,当 IP 包从网络层进入链路层封装成帧的时候,eth0 设备就会使用下一跳地址对应的 MAC 地址,作为该数据帧的目的 MAC 地址。显然,这个 MAC 地址,正是 Node 2 的 MAC 地址。

host-gw 模式能够正常工作的核心,就在于 IP 包在封装成帧发送出去的时候,会使用路由表里的“下一跳”来设置目的 MAC 地址。这样,它就会经过二层网络到达目的宿主机。

这样,这个数据帧就会从 Node 1 通过宿主机的二层网络顺利到达 Node 2 上。