1. k8s-device-plugin
https://github.com/NVIDIA/k8s-device-plugin 是 NVIDIA 官方提供的 Kubernetes 设备插件,用于在 Kubernetes 集群中管理和分配 NVIDIA GPU 资源。
k8s-device-plugin 通过与 kubelet 的交互,自动发现和注册 GPU 设备,并将其作为资源提供给 Kubernetes 调度器。它支持多种 GPU 型号,并能够处理 GPU 的分片和共享。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
| apiVersion: v1
kind: Pod
metadata:
name: gpu-pod
spec:
restartPolicy: Never
containers:
- name: cuda-container
image: nvidia/cuda:11.8.0-base
resources:
limits:
nvidia.com/gpu: 1 # 使用一个 GPU
tolerations:
- key: nvidia.com/gpu
operator: Exists
effect: NoSchedule
|
2. gpu-operator
https://github.com/NVIDIA/gpu-operator 是 NVIDIA 官方提供的组件,提供了驱动管理、容器运行集成、设备发现、节点特征发现等 GPU 全生命周期管理功能。
gpu-operator 不仅集成了 k8s-device-plugin,还提供了一下几种 GPU 资源分配方式:
2.1 MIG
Multi-Instance GPU,简称 MIG,是 NVIDIA 提供的一种技术。
MIG 可以将 Blackwell、Hopper、Ampere 架构的一张 GPU 划分为多个独立的实例,每个实例的计算、显存、带宽相互独立。具体型号可以参考 https://docs.nvidia.com/datacenter/tesla/mig-user-guide/
值得注意的是 MIG 是硬件级别的分片技术,只有支持 MIG 的 GPU 才能使用。
在 Kubernetes 上使用时,需要先安装 k8s-device-plugin 和 gpu-feature-discovery 组件。
首先配置 MIG:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
| apiVersion: v1
kind: ConfigMap
metadata:
name: custom-mig-config
namespace: nvidia-device-plugin
data:
config.json: |
{
"mig-configs": [
{
"devices": ["all"],
"mig-enabled": true,
"mig-devices": [
{"profile": "1g.5gb", "count": 7}
]
}
]
}
|
1g.5gb 是 MIG 的配置文件,表示每个实例有 1 个 GPU slice(一张卡分为若干 slice)和 5GB 显存。
在 Pod 中这样使用 MIG 资源:
1
2
3
4
5
6
7
8
9
10
11
12
13
| apiVersion: v1
kind: Pod
metadata:
name: mig-demo
spec:
restartPolicy: Never
containers:
- name: demo
image: nvidia/cuda:11.8.0-base
command: ["nvidia-smi"]
resources:
limits:
nvidia.com/mig-1g.5gb: 1 # 使用一个 MIG 实例
|
2.2 Time-Slicing
几乎所有的 NVIDIA GPU 都支持 Time-Slicing 技术。Time-Slicing 允许将物理 GPU 切分为多个虚拟设备,每个虚拟设备可以分配给不同的 Pod 使用。每个虚拟设备在时间上共享物理 GPU 的计算资源。
Time-Slicing 仅仅只是调度层面的 GPU 共享,并没有进行资源层级的隔离,因此存在资源的竞争问题。
首先配置 Time-Slicing:
1
2
3
4
5
6
7
8
9
10
11
12
| apiVersion: v1
kind: ConfigMap
metadata:
name: time-slicing-config
data:
default: |-
version: v1
sharing:
timeSlicing:
resources:
- name: nvidia.com/gpu # 资源名称
replicas: 4 # 每块物理GPU切分为4个虚拟设备
|
在 Pod 中这样使用 Time-Slicing 资源:
1
2
3
4
5
6
7
8
9
10
11
12
| apiVersion: v1
kind: Pod
metadata:
name: gpu-timeslicing-demo
spec:
containers:
- name: cuda-container
image: nvidia/cuda:11.8.0-base
command: ["bash", "-c", "nvidia-smi && sleep 3600"]
resources:
limits:
nvidia.com/gpu: 1 # 使用一个 GPU,实际可能和另外三个 Pod 共享同一块物理 GPU
|
2.3 MPS
MPS(Multi-Process Service)是 NVIDIA 提供的一种技术,用于在同一物理 GPU 上运行多个 CUDA 应用程序。MPS 允许多个进程共享同一个 GPU 上的计算资源,从而提高 GPU 的利用率。
相较于 Time-Slicing,MPS 提供了更好的资源隔离和性能优化。MPS 通过创建一个 MPS Server 进程来管理多个 CUDA 应用程序的执行。
首先配置 MPS:
1
2
3
4
5
6
7
8
9
10
| apiVersion: nvidia.com/v1
kind: ClusterPolicy
metadata:
name: mps-policy
spec:
devicePlugin:
enabled: true
env:
- name: NVIDIA_MPS_ENABLE
value: "1"
|
在 Pod 中使用 MPS 资源:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
| apiVersion: v1
kind: Pod
metadata:
name: mps-demo
spec:
containers:
- name: mps-container
image: nvidia/cuda:11.8.0-base
env:
- name: NVIDIA_MPS_ENABLE
value: "1"
command: ["/bin/bash", "-c", "nvidia-smi && sleep 3600"]
resources:
limits:
nvidia.com/gpu: 1
|
3. gpu-manager
https://github.com/tkestack/gpu-manager 采用的是 vCUDA 技术。vCUDA(virtual CUDA)技术是 API Forwarding/Remoting vGPU 实现。
vCUDA 在用户层拦截和重定向 CUDA API 的方法,在 VM 中建立 pGPU 的逻辑映像,即:vGPU,以此来实现 GPU 资源的细粒度划分、重组和再利用,支持多机并发、挂起恢复等 VM 的高级特性。
如果是整数倍卡,gpu-manager 会通过环境变 NVIDIA_VISIBLE_DEVICES 控制容器内应用可见的 GPU,同时仅将可见的设备挂载到容器内。
如果是少于 1 张卡,gpu-manager 会注入 LD_LIBRARY_PATH 借助 https://github.com/tkestack/vcuda-controller 项目劫持 CUDA 和 NVML 的库函数调用,修改返回值,实现对 GPU 资源的分片。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
| apiVersion: v1
kind: Pod
metadata:
name: vcuda
spec:
restartPolicy: Never
containers:
- image: nvidia/cuda:11.8.0-base
name: nvidia
command:
- /usr/local/nvidia/bin/nvidia-smi
- pmon
- -d
- 10
resources:
requests:
tencent.com/vcuda-core: 50
tencent.com/vcuda-memory: 30
limits:
tencent.com/vcuda-core: 50
tencent.com/vcuda-memory: 30
|
这里分配 7680 MiB GPU memory 和 0.5 GPU 的资源。tencent.com/vcuda-core
的单位是 0.01 GPU core,tencent.com/vcuda-memory
的单位是 256 MiB 显存。
4. HAMi
https://github.com/Project-HAMi/HAMi 采用的是 vCUDA 方案,通过劫持 CUDA API 调用来实现 GPU 资源的分片和共享。
由于同属于 vCUDA 技术栈,HAMi 与 gpu-manager 的使用方式类似。不同的是 gpu-manager 项目不再维护,而 HAMi 仍在持续更新。
HAMi 不仅集成了 Nvidia 的 MIG、Time-Slicing,还可以管理 NPU、MLU、DCU 等其他 AI 加速卡,同时在调度层面也进行了优化,能够根据自定义策略进行资源分配。
下面是一个使用 HAMi 的示例 Pod 配置:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
| apiVersion: v1
kind: Pod
metadata:
name: mps-demo
spec:
containers:
- name: mps-container
image: nvidia/cuda:11.8.0-base
env:
- name: NVIDIA_MPS_ENABLE
value: "1"
command: ["/bin/bash", "-c", "nvidia-smi && sleep 3600"]
resources:
limits:
nvidia.com/gpu: 1 # 使用 1 个 GPU
nvidia.com/gpucores: 30 # 使用每个 GPU 的 30% 核心
nvidia.com/gpumem: 3000 # 申请 3G 显存
|