NNetpath
原理预计 30 分钟

SR-IOV、MacVLAN 与 IPvlan:把网卡切给容器

三种让容器贴近物理网的方式,性能与灵活度各有取舍。

学完这节你能做到

  • 解释 PF 与 VF 的关系以及 VF 数量的限制
  • 区分 MacVLAN、IPvlan、SR-IOV 在数据路径上的差异
  • 按场景选出合适的接入方式并说出它的代价

建议先学跳过这几节会看不懂本节的部分推导

为什么要绕开默认 CNI

默认 CNI 给 Pod 的那张网卡走的是软件转发路径:veth → 宿主机数据平面 → 物理网卡。 对绝大多数业务,这条路径的开销完全可以忽略。

但两类场景不行:

  • RDMA / AI 训练:需要 Pod 直接使用物理网卡的 RDMA 能力,软件转发路径帮不上忙
  • 虚拟机(KubeVirt):虚机需要二层网络语义,要能自己收发任意 MAC 的帧

这时候的做法是给 Pod 插第二张网卡:业务流量走默认 CNI,高性能流量走这张直连物理网的卡。 三种实现方式,从软到硬。

MacVLAN:一张卡,多个 MAC

在一张物理网卡上派生出多个虚拟接口,每个都有自己独立的 MAC 地址,直接挂在物理二层网络上。

        物理网卡 bond0(MAC: aa:bb:cc:00:00:01)
                │
    ┌───────────┼───────────┐
 macvlan1    macvlan2    macvlan3
 MAC:...:11   MAC:...:12  MAC:...:13
 (Pod A)      (Pod B)     (Pod C)

优点:配置简单,性能接近物理网卡(不过宿主机协议栈的转发路径),Pod 有真实的物理网 IP。

代价与限制

  • 交换机端口必须允许一个端口上出现多个 MAC(多数交换机默认允许,但有 MAC 数量上限, 开了端口安全策略的会直接拦掉)
  • 同一张物理卡上的 macvlan 子接口默认无法与宿主机自身通信(bridge 模式下子接口之间可以互通, 但和 master 接口之间不行)
  • 需要一个能管的 IP 池:Pod 的 IP 来自物理网段,得有人负责分配和回收

k8s-in-action 里的实际配法(配合 NVIDIA 的 nv-ipam):

apiVersion: mellanox.com/v1alpha1
kind: MacvlanNetwork
metadata:
  name: hca
  namespace: network-operator
spec:
  networkNamespace: "default"
  master: "bond0"          # 派生自哪张物理卡
  mode: "bridge"
  mtu: 1500
  ipam: |
    {
      "type": "nv-ipam",
      "poolName": "hca"
    }
---
apiVersion: nv-ipam.nvidia.com/v1alpha1
kind: IPPool
metadata:
  name: hca
  namespace: network-operator
spec:
  subnet: 192.168.0.0/20
  perNodeBlockSize: 8      # 每节点先领 8 个地址
  gateway: 192.168.0.1

Pod 侧用注解申请这张网卡:

metadata:
  annotations:
    k8s.v1.cni.cncf.io/networks: network-operator/hca
spec:
  containers:
    - name: app
      resources:
        limits:
          rdma/hca: 1      # 同时申请 RDMA 设备
!MacVLAN 场景要留意 perNodeBlockSize

每个节点从 IP 池里领一整块地址(例子里是 8 个)。这意味着: 单节点上用这张网的 Pod 数不能超过块大小,超了就分不到 IP。 同时整个池子的容量也限制了节点数 × 块大小。和 Pod CIDR 一样,这是个一次性决定, 规划时要按未来的并发任务数算,不要按当前用量算。

IPvlan:共用 MAC,只分 IP

和 MacVLAN 几乎一样,唯一区别是所有子接口共用物理网卡的 MAC,只有 IP 不同。

什么时候用它:

  • 交换机开了端口安全,限制一个端口只能有一个 MAC
  • 云环境限制了每个网卡的 MAC 数量
  • 无线网络场景(一个 MAC 一个关联)

代价是二层功能受限:既然共用 MAC,就没法做基于 MAC 的隔离,某些需要独立二层身份的应用会不适应。

SR-IOV:硬件级切分

前两种是内核软件派生。SR-IOV 是网卡硬件自己把自己切成多个设备

概念全称是什么
PFPhysical Function物理功能,就是那张卡本体
VFVirtual Function虚拟功能,硬件切出来的"小网卡",可以直通进容器或虚机
# 看这张卡支持多少个 VF,当前开了几个
cat /sys/class/net/ens1f0/device/sriov_totalvfs
cat /sys/class/net/ens1f0/device/sriov_numvfs

# 开启 8 个 VF(重启失效,要写进启动配置)
echo 8 > /sys/class/net/ens1f0/device/sriov_numvfs

优点:性能最好——VF 在硬件层面就是独立设备,数据路径完全不经过宿主机的软件转发, 延迟和带宽几乎等于独占物理卡。

代价

  • VF 数量由硬件写死,通常几十到一百多个,用完就没了
  • 改 VF 数量要重置网卡,多数情况下需要重启节点或至少中断链路
  • Pod 迁移麻烦:VF 是绑定到具体节点具体网卡的,不像软件方案那样自由
  • 需要 BIOS 里开 SR-IOV、开 IOMMU/VT-d

三者对比

维度MacVLANIPvlanSR-IOV
性能最好
隔离独立 MAC共用 MAC硬件级
数量上限受交换机 MAC 表限制宽松受硬件 VF 数限制
配置复杂度高(BIOS + 驱动 + 插件)
交换机要求允许多 MAC无特殊要求无特殊要求
适合RoCE、需要隔离多任务交换机限制 MAC 的环境极致性能、虚机直通

和 RDMA 的组合:两种模式

跑 RDMA 时有两条常见路线,取舍很实际:

hostNetworkMacVLAN
配置hostNetwork: true + rdma/hca: 1注解申请网卡 + rdma/hca: 1
额外组件不需要需要 Multus/Spiderpool + IP 池
Pod IP就是宿主机 IP独立 IP
单节点并行多任务不行(端口冲突)可以
适合单任务独占整机的训练多任务共享集群

两条关键规则记牢:

  • RoCE 用 hostNetwork 模式时必须设 hostNetwork: true,让宿主机网卡进入 Pod 的网络命名空间—— 因为 RoCE 需要用宿主机 IP 来建链
  • 纯 IB 场景通常只申请 rdma/hca: 1 就够了,不必动网络配置
# RoCE + hostNetwork
spec:
  hostNetwork: true
  containers:
    - name: trainer
      resources:
        limits:
          nvidia.com/gpu: 8
          rdma/hca: 1
      securityContext:
        capabilities:
          add: ["IPC_LOCK"]
×hostNetwork 下同节点跑两个任务会端口冲突

hostNetwork: true 意味着 Pod 直接用宿主机的端口空间。NCCL、sshd(MPI 启动器要用) 这些都要监听固定端口,同一节点上起第二个任务时端口直接撞车, 症状是第二个任务的 Pod 一直 CrashLoopBackOff 或 sshd 起不来。

这就是共享集群里要上 MacVLAN 的实际理由:给每个任务一套独立 IP 和端口空间。 单任务独占整机时,hostNetwork 更省事。

检查点

检查点单选

交换机开了端口安全,限制每个端口只允许一个 MAC 地址。这时候该选哪种方案给 Pod 接入物理网?

检查点单选

共享的 GPU 集群里,同一个节点上要能同时跑多个训练任务。RDMA 该怎么接?

检查点多选

关于 SR-IOV,下面哪些说法正确?(多选)

这节课的落点

  • 默认 CNI 够用,只有 RDMA/AI 与虚拟机两类场景需要 Pod 直连物理网
  • MacVLAN:独立 MAC,配置简单;要求交换机允许多 MAC,注意 perNodeBlockSize 的容量账
  • IPvlan:共用 MAC,专为限制 MAC 数量的环境准备
  • SR-IOV:硬件切分,性能最好,但 VF 数量写死、调整要重置、与节点绑定
  • RoCE + hostNetwork 必须设 hostNetwork: true;纯 IB 只申请 rdma/hca 即可
  • hostNetwork 简单但同节点跑不了第二个任务;共享集群用 MacVLAN 换独立端口空间
  • 容器里做 RDMA 别忘了 IPC_LOCK

延伸资料

  • ·k8s-in-actionnetwork/network-operator/macvlan/README.md
  • ·k8s-in-actionnetwork/network-operator/README.md