K8s(Kubernetes)管理 GPU 集群的核心是通过设备插件暴露 GPU 资源、调度器识别并分配 GPU、容器运行时隔离 GPU,同时结合扩展组件实现精细化管控,确保 GPU 资源高效利用。
一、核心前提:GPU 集群的基础环境准备
K8s 管理 GPU 的前提是节点已部署 GPU 驱动、CUDA 工具包,且匹配容器运行时(如 Docker/containerd),常见 GPU 类型(NVIDIA/AMD)的环境要求不同,以主流的 NVIDIA GPU 为例:
- 节点安装:NVIDIA 驱动(≥418.x)、CUDA Toolkit、nvidia-container-runtime(替代默认 runc,实现容器内 GPU 调用);
- 验证环境:
nvidia-smi能正常显示 GPU 信息,docker run --rm --gpus all nvidia/cuda:11.8.0-base nvidia-smi可在容器内调用 GPU。
二、核心组件:K8s 识别 GPU 的核心机制
K8s 本身不直接感知 GPU,需通过设备插件(Device Plugin) 暴露 GPU 资源,核心组件分工如下:
| 组件 | 作用 |
|---|---|
| NVIDIA Device Plugin | 以 DaemonSet 部署在 GPU 节点,向 K8s APIServer 注册 GPU 资源(如nvidia.com/gpu),监控 GPU 状态并上报; |
| K8s Scheduler | 识别节点的nvidia.com/gpu资源量,根据 Pod 的 GPU 请求(resources.requests)调度 Pod 到对应节点; |
| Container Runtime | nvidia-container-runtime 负责将 GPU 设备挂载到容器内,隔离 GPU 的使用(如限制 CUDA 核心、显存); |
| Node Feature Discovery (NFD) | 可选扩展,自动识别 GPU 型号 / 算力 / 显存等特征,支持按 GPU 型号调度(如区分 A100/V100); |
三、核心流程:GPU 的分配与调度
1. 部署 GPU 设备插件(以 NVIDIA 为例)
通过官方 YAML 部署 Device Plugin(需提前配置镜像仓库):
yaml
# 部署NVIDIA Device Plugin DaemonSet
kubectl apply -f https://raw.githubusercontent.com/NVIDIA/k8s-device-plugin/v0.14.0/nvidia-device-plugin.yml
部署后,GPU 节点的status.capacity和status.allocatable会新增nvidia.com/gpu字段,值为节点 GPU 数量(如 2 张 GPU 则显示nvidia.com/gpu: 2)。
2. Pod 申请 GPU 资源
在 Pod 的 YAML 中通过resources声明 GPU 请求 / 限制(K8s 要求 GPU 的 request 和 limit 必须相等,且只能整数量申请):
yaml
apiVersion: v1
kind: Pod
metadata:
name: gpu-pod
spec:
containers:
- name: cuda-container
image: nvidia/cuda:11.8.0-base
command: ["nvidia-smi"]
resources:
limits:
nvidia.com/gpu: 1 # 申请1张GPU(必填,request默认等于limit)
requests:
nvidia.com/gpu: 1 # 可选,建议显式声明
提交后,调度器会筛选出有空闲nvidia.com/gpu的节点,将 Pod 调度到该节点,并由 Device Plugin 分配具体的 GPU 设备 ID(如 GPU 0)。
3. GPU 的隔离与限制
-
整卡隔离:默认 K8s 按 "整卡" 分配 GPU(1 个 Pod 申请 1 张 GPU,独占该卡),是最基础的隔离方式;
-
细粒度共享(MIG) :NVIDIA A100/A30 等支持 MIG(Multi-Instance GPU),可将 1 张 GPU 切分为多个独立实例(如 A100 切 8 个实例),Device Plugin 支持按 MIG 实例分配,实现 GPU 分片复用:
yaml
# 申请1个MIG实例 resources: limits: nvidia.com/mig-1g.5gb: 1 -
显存 / 算力限制:通过 NVIDIA DCGM(Data Center GPU Manager)或扩展组件(如 nvidia-gpu-operator),限制 Pod 使用的 GPU 显存、算力百分比,实现非 MIG GPU 的共享(如 1 张 GPU 供 2 个 Pod 共享,各限制 50% 显存)。
四、进阶管控:提升 GPU 资源利用率的扩展方案
1. 按 GPU 特征调度(NFD)
部署 NFD 后,节点会被打上 GPU 型号、算力、显存等标签(如feature.node.kubernetes.io/pci-10de.present=true、nvidia.com/gpu.product=NVIDIA-A100-80GB),Pod 可通过nodeSelector/affinity指定 GPU 型号:
yaml
spec:
affinity:
nodeAffinity:
requiredDuringSchedulingIgnoredDuringExecution:
nodeSelectorTerms:
- matchExpressions:
- key: nvidia.com/gpu.product
operator: In
values: ["NVIDIA-A100-80GB"]
2. GPU 资源监控与调度优化
- 监控:通过 Prometheus + Grafana + DCGM-Exporter 采集 GPU 使用率、显存、温度等指标;
- 调度优化:
- 使用
kube-scheduler的ResourceBinPacking策略,将多个小 GPU 请求的 Pod 调度到同一节点,提升 GPU 整机利用率; - 借助 Volcano、Kubeflow 等调度框架,支持 GPU 的抢占、优先级调度、多卡绑定(如单机多卡训练)。
- 使用
3. 动态 GPU 资源调整(实验性)
K8s 1.26 + 支持DevicePlugins的动态资源调整(Alpha 特性),可在 Pod 运行中调整 GPU 配额(需设备插件支持),适配弹性训练场景。
五、常见问题与优化
- GPU 资源碎片化:避免小请求独占整卡,通过 MIG 或显存限制实现共享,或使用调度器插件(如 Scheduling Framework)合并小任务;
- GPU 利用率低:通过监控识别空闲 GPU,结合 CronJob 自动清理闲置 Pod,或使用 KEDA 实现 GPU 任务的弹性伸缩;
- 多厂商 GPU 管理 :AMD GPU 需部署
amd-device-plugin,Intel GPU 需部署intel-device-plugins-for-kubernetes,K8s 通过不同资源名(如amd.com/gpu)区分。
六、总结
K8s 管理 GPU 集群的核心链路是:设备插件暴露 GPU 资源 → 调度器按请求分配 GPU → 容器运行时隔离 GPU 使用 → 扩展组件实现精细化管控。通过整卡分配、MIG 分片、显存限制等方式,可满足从基础推理到大规模训练的 GPU 使用场景,结合监控和调度优化,能将 GPU 资源利用率提升至 80% 以上(如 AI 训练集群通过 MIG + 任务合并,利用率可从 50% 提升至 85%+)。