Arch Linux啟用GVT-g為KVM虛擬機器提供GPU
0x00 環境
我的環境如下:
- Kernel: 5.14.12-arch1-1
- CPU: Intel i5-8250U
- GPU: Intel UHD Graphics 620
- QEMU: 6.1.0
0x01 啟動GVT-g
1. 新增核心引數
要啟用IOMMU、i915,編輯grub檔案:
$ sudo vim /etc/default/grub
找到GRUB_CMDLINE_LINUX_DEFAULT的引數,在後面新增intel_iommu=on和i915.enable_guc=0
GRUB_CMDLINE_LINUX_DEFAULT="loglevel=3 intel_iommu=on i915.enable_guc=0"
2. 啟用核心模組
要啟用kvmgt、vfio-iommu-typ1、mdev
$ sudo modprobe kvmgt vfio-iommu-type1 mdev
3. 新增核心模組引數
在/etc/modprobe.d/目錄下建立配置檔案來開啟GPU虛擬化
$ sudo echo "options i915 enable_gvt=1" >> /etc/modprobe.d/gvt-g.conf
至此,重新啟動系統。
$ reboot
4. 查詢顯示卡的GUID
$ lspci -D -nn
找到顯示卡的GUID,例如 0000:00:02.0
5. 檢視mdev支援的型別
$ ls /sys/bus/pci/devices/0000:00:02.0/mdev_supported_types/ i915-GVTg_V5_4 i915-GVTg_V5_8
例如,顯示如下兩個資料夾,說明啟動成功
i915-GVTg_V5_4 i915-GVTg_V5_8
若資料夾為空說明GVT-g沒有成功啟動。
進入對應目錄,檢視description檔案獲取資訊
$ cat /sys/bus/pci/devices/0000:00:02.0/mdev_supported_types/i915-GVTg_V5_4/description
low_gm_size: 128MB
high_gm_size: 512MB
fence: 4
resolution: 1920x1200
weight: 4
說明i915-GVTg_V5_4最大支援解析度1920x1200,視訊記憶體佔用128MB~512MB。
Arch wiki還描述了其他型別:
i915-GVTg_V5_1 # Video memory: <512MB, 2048MB>, resolution: up to 1920x1200
i915-GVTg_V5_2 # Video memory: <256MB, 1024MB>, resolution: up to 1920x1200
i915-GVTg_V5_4 # Video memory: <128MB, 512MB>, resolution: up to 1920x1200
i915-GVTg_V5_8 # Video memory: <64MB, 384MB>, resolution: up to 1024x768
6. 建立一個虛擬GPU裝置
使用
$ uuidgen
7d6cff35-231d-4ad2-a9b7-aa53d4d51b1f
來生成一個UUID,用它來標識新建的虛擬顯示卡
建立裝置,這裡我選擇i915-GVTg_V5_4:
$ echo "7d6cff35-231d-4ad2-a9b7-aa53d4d51b1f" > "/sys/devices/pci0000:00/0000:00:02.0/mdev_supported_types/i915-GVTg_V5_4/create"
其中GUID編號和mdev型別根據實際情況修改。
0x02 建立虛擬機器
1. 使用通常方法建立一個普通虛擬機器
使用virtio裝置。虛擬機器命名為vmname。
2. 新增虛擬顯示卡
使用
$ virsh edit vmname
vmname替換成建立虛擬機器的名稱,在<devices>元素中新增
<hostdev mode='subsystem' type='mdev' managed='no' model='vfio-pci' display='off'>
<source>
<address uuid='7d6cff35-231d-4ad2-a9b7-aa53d4d51b1f'/>
</source>
</hostdev>
uuid要修改成建立虛擬顯示卡的UUID
3. 影象顯示設定
找到<graphics>和<video>元素,刪除預設,修改為:
<graphics type='spice'>
<listen type='none'/>
<gl enable='yes' rendernode='/dev/dri/by-path/pci-0000:00:02.0-render'/>
</graphics>
<video>
<model type='none'/>
</video>
pci-後面編號根據實際情況修改。
接著,修改
<domain type='kvm'>
為
<domain type='kvm' xmlns:qemu='http://libvirt.org/schemas/domain/qemu/1.0'>
在<domain>元素中,在</domain>上方新增:
<qemu:commandline>
<qemu:arg value='-set'/>
<qemu:arg value='device.hostdev0.x-igd-opregion=on'/>
<qemu:arg value='-set'/>
<qemu:arg value='device.hostdev0.ramfb=on'/>
<qemu:arg value='-set'/>
<qemu:arg value='device.hostdev0.display=on'/>
<qemu:arg value='-set'/>
<qemu:arg value='device.hostdev0.driver=vfio-pci-nohotplug'/>
<qemu:arg value='-set'/>
<qemu:arg value='device.hostdev0.xres=1920'/>
<qemu:arg value='-set'/>
<qemu:arg value='device.hostdev0.yres=1080'/>
</qemu:commandline>
device.hostdev0.xres和device.hostdev0.yres選項可根據需要調整解析度,要小於mdev支援的解析度。
之後啟動虛擬機器看看。
4. GVT-g自動啟動
為了每次啟動虛擬都自動啟動虛擬顯示卡,故使用qemu的hook功能。
建立/etc/libvirt/hooks/目錄。建立qemu檔案,內容如下:
#!/bin/bash
GVT_PCI="0000:00:02.0"
GVT_GUID="7d6cff35-231d-4ad2-a9b7-aa53d4d51b1f"
MDEV_TYPE="i915-GVTg_V5_4"
DOMAIN="vmname"
if [ $# -ge 3 ]; then
if [ $1 = "$DOMAIN" -a $2 = "prepare" -a $3 = "begin" ]; then
echo "$GVT_GUID" > "/sys/bus/pci/devices/$GVT_PCI/mdev_supported_types/$MDEV_TYPE/create"
elif [ $1 = "$DOMAIN" -a $2 = "release" -a $3 = "end" ]; then
echo 1 > /sys/bus/pci/devices/$GVT_PCI/$GVT_GUID/remove
fi
fi
其中變數根據實際情況修改
0x03 尾聲
在windows中安裝virtio客戶端程式
硬體管理器裡面更新顯示卡驅動,來獲得intel顯示卡驅動