本文总结一下当前 360 云平台虚拟机GPU 直通方案落地和容器+MIG 方案验证

1. 背景

AI 大模型作为 360 公司的重点战略目标,GPU 卡同时也作为战略资源,如果用物理机直接给用户使用,一个物理机默认带 8 张卡,有时用户用不到这么多,会造成 GPU 卡的浪费。所以,给用户提供的 GPU 卡需要精细划分,要求按卡分配,并且要有隔离机制。

kvm 虚拟机和容器本身带有资源小单位划分和隔离的特性,于是团队采用了虚拟机和容器作为GPU资源提供方式来满足用户需求。

2. 方案调研

3. 方案验证与落地

记录下GPU 直通和Docker+Mig 方案的原理与落地方式

3.1 GPU 直通方案

原理分析

GPU 直通方案对 GPU 的兼容性好,性能损耗低,而且GPU 厂商也不收取额外费用,所以被各大云厂商广泛使用

                                                    性能损耗图

IOMMU

IOMMU的主要功能就是完成映射,需要用到页表。页表记录了 GPA 与 HPA的映射关系。Guest只能看到 GPA, 通过写入GPA 的方式将数据写入到 GPA(硬件自动实现)。

页表转换规则:在设备发起DMA请求时,Guest会将自己的Source Identifier(包含Bus、Device、Func)包含在请求中,IOMMU根据这个标识,以RTADDR_REG指向空间为基地址,然后利用Bus、Device、Func在Context Table中找到对应的Context Entry,即页表首地址,然后利用页表即可将设备请求的虚拟地址翻译成物理地址。

iommu 的作用:

  1. 建立 GPA 到 HPA 的关系映射,从而屏蔽了 Guest 对物理地址的直接访问,达到了物理地址的隔离作用

  2. IOMMU可以将连续的虚拟地址映射到不连续的多个物理内存片段,对于没有IOMMU的情况,设备访问的物理空间必须是连续的,IOMMU可有效的解决这个问题.

VFIO 驱动

Virtual Function I/O (VFIO) 是一种现代化的设备直通方案,它充分利用了VT-d/AMD-Vi技术提供的DMA Remapping和Interrupt Remapping特性, 在保证直通设备的DMA安全性同时可以达到接近物理设备的I/O的性能。用户态进程可以直接使用VFIO驱动直接访问硬件,并且由于整个过程是在IOMMU的保护下进行因此十分安全, 而且非特权用户也是可以直接使用。换句话说,VFIO是一套完整的用户态驱动(userspace driver)方案,因为它可以安全地把设备I/O、中断、DMA等能力呈现给用户空间。

为了达到最高的IO性能,虚拟机就需要VFIO这种设备直通方式,因为它具有低延时、高带宽的特点,并且guest也能够直接使用设备的原生驱动。这些优异的特点得益于VFIO对VT-d/AMD-Vi所提供的DMA RemappingInterrupt Remapping机制的应用。VFIO使用DMA Remapping为每个Domain建立独立的IOMMU Page Table将直通设备的DMA访问限制在Domain的地址空间之内保证了用户态DMA的安全性, 使用Interrupt Remapping来完成中断重映射和Interrupt Posting来达到中断隔离和中断直接投递的目的。

透传GPU设备实现步骤

1. 物理机启动,BIOS完成PCI设备的配置,包括初始化config空间,分配BAR地址空间;

2. 由于内核开启IOMMU支持,会为当前设备分配iommu group;

3. 加载vfio驱动,并与GPU卡关联;

4. qemu启动虚机,并将GPU卡设备透传给虚机;

5. 虚机启动,根据qemu构建的虚机PCI拓扑为oci设备初始化,包括配置confg空间、分配BAR地址空间;

7. 绝大部分指令是通过 IOMMU 建立的页表寻址(将 GPA 转换为 HPA),一些特殊的config寄存器,如Max Payload,虚拟机 in、out指令,通过 vm exit 寻址;

方案落地

物理机启动配置调整
  • ubuntu系统

打开iommu 、gpu网卡配置vfio驱动

vim /etc/default/grub
GRUB_CMDLINE_LINUX_DEFAULT="intel_iommu=on vfio-pci.ids=10de:xxxx quiet"

升级grub:

update-grub
  • 龙蜥系统

打开iommu

grubby --update-kernel="/boot/vmlinuz-`uname -r`" --args="intel_iommu=on"

gpu网卡配置vfio驱动

新增配置文件:

[root@hpclov2020 ~]# cat /etc/modules-load.d/openstack-gpu.conf
vfio_pci

新增配置文件:

[root@hpclov2020 ~]# cat /etc/modprobe.d/vfio.conf
options vfio-pci ids=10de:xxxx
  • 设置内核模块黑名单

禁用nvidia和nouveau驱动

vim /etc/modprobe.d/blacklist.conf
blacklist nouveau
options nouveau modeset=0
blacklist xhci_hcd
blacklist nvidia
blacklist nvidia_modeset
blacklist nvidia_drm
blacklist snd_hda_intel
blacklist nvidiafb
blacklist ast
blacklist drm_kms_helper
blacklist drm_vram_helper
blacklist ttm
blacklist drm
  • 验证配置是否生效

验证iommu: dmesg | grep iommu

验证gpu使用vfio驱动

lspci -nn | grep NVIDIA

lspci -s 3e:00.0 -k  | grep driver

openstack 侧调整
  • nova-api配置调整

新增配置:

[pci]
alias = {"vendor_id":"10de", "product_id":"xxx", "device_type":"type-PCI", "name":"nvidia-xxx"}
  • nova-compute配置调整

新增配置:

[pci]
passthrough_whitelist = [{"vendor_id":"10de", "product_id":"xxx"}]
  • 创建套餐和验证

创建trait:

openstack trait create CUSTOM_SHARE_GPU_XXX_HOST_LEVEL3

设置trait:

openstack  resource provider trait set  --trait CUSTOM_SHARE_GPU_XXX_HOST_LEVEL3 2a5769e2-78fa-4a15-8f36-9b82407c4b56

创建套餐:

# XXX的4个套餐
openstack flavor create --vcpus 10 --ram 102400 --ephemeral 800 --property trait:CUSTOM_SHARE_GPU_XXX_HOST_LEVEL3='required' --property pci_passthrough:alias='nvidia-xxx:1' v.xxxgn3i-1x.c10g100-1i
openstack flavor create --vcpus 20 --ram 204800 --ephemeral 1600 --property trait:CUSTOM_SHARE_GPU_XXX_HOST_LEVEL3='required' --property pci_passthrough:alias='nvidia-xxx:2' v.xxxgn3i-2x.c20g200-2i
openstack flavor create --vcpus 40 --ram 409600 --ephemeral 3200 --property trait:CUSTOM_SHARE_GPU_XXX_HOST_LEVEL3='required' --property pci_passthrough:alias='nvidia-xxx:4' v.xxxgn3i-4x.c40g400-4i
openstack flavor create --vcpus 80 --ram 819200 --ephemeral 6500 --property trait:CUSTOM_SHARE_GPU_XXX_HOST_LEVEL3='required' --property pci_passthrough:alias='nvidia-xxx:8' v.xxxgn3i-8x.c80g800-8i

创建虚拟机:

# zzzc2
nova boot --availability-zone nova:hpctur02.aitc.xxx.xxx.net --flavor gpu-flavor --security-groups f9f068b4-f247-4e29-a21d-fc98da18e99f  --nic net-id=f0dd296e-dee9-422b-b538-3560fbe145f9 --block-device id=edc2a95c-6e73-4bf8-8891-4bb19d23ca94,source=image,dest=volume,bus=scsi,type=disk,size=50,bootindex=0,shutdown=remove,volume_type=sata  test_gpu_08


# zzdt
nova boot --availability-zone nova:hpclov2017.aitc.xxx.xxx.net --flavor v.s2.80c800G.gpu --security-groups a37b6670-0fb6-48ba-90cd-468f0532bbe8  --nic net-id=0d683c7b-6275-4f1a-80da-28a52498d14a --block-device id=f592985e-5b34-4dbf-93ff-c9f86be7596a,source=image,dest=volume,bus=scsi,type=disk,size=50,bootindex=0,shutdown=remove,volume_type=sata  gpu_test_01


# shyc2
nova boot --availability-zone nova:hpclov2016.aitc.xxx.xxx.net --flavor v.xxxgn3i-1x.c10g100-1i --security-groups 7730b14e-4f25-4828-939f-f2f094cd2ee9 --nic net-id=6d2395f0-2f95-48c1-ae5d-073b95637e0e --block-device id=2f9e989d-de4e-4e43-a56d-28105a4fd088,source=image,dest=volume,bus=scsi,type=disk,size=50,bootindex=0,shutdown=remove,volume_type=sata hpclov2016v.aitc.xxx.xxx.net
绑定fip
neutron floatingip-associate ffc8c74b-299d-45e7-9780-19d90e703e69 74a6c1c9-9bff-43cc-8341-572276090fa2

登陆虚拟机验证:

lspci -nn | grep -i nvidia

3.2 Docker+Mig 方案

方案落地

创建 mig instance

打开0 号 GPU 设备 mig 功能:nvidia-smi -i 0 -mig 1

查看 0 号 GPU 设备 mig 是否打开:nvidia-smi -i 0 --query-gpu=pci.bus_id,mig.mode.current --format=csv

查看 mig profile:nvidia-smi mig -lgip

创建 mig:nvidia-smi mig -cgi 14,14,14,14 -C

查看划分的 instance:nvidia-smi -L

安装 NVIDIA 驱动

APQA网盘 - /foxi/Virtualization/vGPU/ (buduanwang.vip)

yum install dkms
curl -SL https://foxi.buduanwang.vip/pan/foxi/Virtualization/vGPU/NVIDIA-Linux-x86_64-510.85.03-vgpu-kvm.run -O
sh NVIDIA-Linux-x86_64-510.85.03-vgpu-kvm.run --dkms
安装nvidia-container-toolkit
#vim /etc/yum.repos.d/nvidia-container-toolkit.repo
[nvidia-container-toolkit]
name=nvidia-container-toolkit
baseurl=https://nvidia.github.io/libnvidia-container/stable/rpm/$basearch
repo_gpgcheck=1
gpgcheck=0
enabled=1
gpgkey=https://nvidia.github.io/libnvidia-container/gpgkey
sslverify=1
sslcacert=/etc/pki/tls/certs/ca-bundle.crt


[nvidia-container-toolkit-experimental]
name=nvidia-container-toolkit-experimental
baseurl=https://nvidia.github.io/libnvidia-container/experimental/rpm/$basearch
repo_gpgcheck=1
gpgcheck=0
enabled=0
gpgkey=https://nvidia.github.io/libnvidia-container/gpgkey
sslverify=1
sslcacert=/etc/pki/tls/certs/ca-bundle.crt


# 安装
yum install -y nvidia-container-toolkit
配置 docker runtime
nvidia-ctk runtime configure --runtime=docker
systemctl restart docker
拉取 cuda 镜像
docker pull harbor.qihoo.net/nvidia/cuda:11.4.1-base-centos8
运行容器并查看 mig 设备
sudo docker run --runtime=nvidia -e NVIDIA_VISIBLE_DEVICES=MIG-a75f333a-f233-5ba4-b4c5-65598abb8f33 harbor.qihoo.net/nvidia/cuda:11.4.1-base-centos8 nvidia-smi

4. 总结与展望

360 智汇云云平台在 GPU 直通和 Docker+Mig方案上实现了落地,但是对 VGPU 方案还需要继续探索,补全 VGPU 方案后可以为用户提供全面的 GPU 虚拟化功能。

Logo

火山引擎开发者社区是火山引擎打造的AI技术生态平台,聚焦Agent与大模型开发,提供豆包系列模型(图像/视频/视觉)、智能分析与会话工具,并配套评测集、动手实验室及行业案例库。社区通过技术沙龙、挑战赛等活动促进开发者成长,新用户可领50万Tokens权益,助力构建智能应用。

更多推荐