本文配置了单显卡下的显卡直通。由于只有一张显卡,因此 Linux 侧的 Display Manager 和虚拟机无法共存。而这就是单显卡直通的原理所在:在直通期间将显卡释放,通过 PCI 直通给虚拟机使用;在虚拟机不再使用显卡时,重新启动 Display Manager 以继续使用 Linux 桌面。
本文中的配置主要参考了 Single-GPU-Passthrough-for-Arch-Linux 的教程。
ToC
IOMMU
由于个人在配置这篇文章之前就已经开启了 IOMMU,所以本文也跳过这一步骤。在 Hooks 之前的步骤可以参考上文提及的教程。
Hooks
单显卡直通配置的核心,通过配置虚拟机启动和关闭的钩子,实现显卡的自动释放和回收。首先线获得脚本:
sudo wget 'https://raw.githubusercontent.com/PassthroughPOST/VFIO-Tools/master/libvirt_hooks/qemu' -O /etc/libvirt/hooks/qemu
创建目录:
sudo mkdir /etc/libvirt/hooks/qemu.d /etc/libvirt/hooks/qemu.d/win10 /etc/libvirt/hooks/qemu.d/win10/prepare /etc/libvirt/hooks/qemu.d/win10/prepare/begin /etc/libvirt/hooks/qemu.d/win10/release /etc/libvirt/hooks/qemu.d/win10/release/end
创建 /etc/libvirt/hooks/qemu.d/win10/prepare/begin/start.sh:
#!/bin/bash
## Helpful to read output when debugging
set -x
# Stop display manager
systemctl stop display-manager.service
## Uncomment the following line if you use GDM
#killall gdm-x-session
# Unbind VTconsoles
echo 0 > /sys/class/vtconsole/vtcon0/bind
echo 0 > /sys/class/vtconsole/vtcon1/bind
# Unbind EFI-Framebuffer
echo efi-framebuffer.0 > /sys/bus/platform/drivers/efi-framebuffer/unbind
# Avoid a Race condition by waiting 2 seconds. This can be calibrated to be shorter or longer if required for your system
sleep 2
# Unload all Nvidia drivers
modprobe -r nvidia_drm
modprobe -r nvidia_modeset
modprobe -r nvidia_uvm
modprobe -r nvidia
## Load vfio
modprobe vfio
modprobe vfio_iommu_type1
modprobe vfio_pci
创建 /etc/libvirt/hooks/qemu.d/win10/release/end/stop.sh:
#!/bin/bash
set -x
## Unload vfio
modprobe -r vfio_pci
modprobe -r vfio_iommu_type1
modprobe -r vfio
# Rebind VT consoles
echo 1 > /sys/class/vtconsole/vtcon0/bind
echo 1 > /sys/class/vtconsole/vtcon1/bind
nvidia-xconfig --query-gpu-info > /dev/null 2>&1
echo "efi-framebuffer.0" > /sys/bus/platform/drivers/efi-framebuffer/bind
modprobe nvidia_drm
modprobe nvidia_modeset
modprobe nvidia_uvm
modprobe nvidia
# Restart Display Manager
systemctl start display-manager.service
将所有脚本都设置为可执行:
sudo chmod +x /etc/libvirt/hooks/qemu
sudo chmod +x /etc/libvirt/hooks/qemu.d/win10/prepare/begin/start.sh
sudo chmod +x /etc/libvirt/hooks/qemu.d/win10/release/end/stop.sh
创建虚拟机
- 打开
virt-manager,在编辑-Preferences中找到启用 XML 编辑并打勾 - 新建虚拟机,选择本地安装,找到 ISO 并加载。
注意,虚拟机的名称必须为
win10 - 确定
Customize configuration before install是勾选的,因为在启动之前我们需要进行一些设置 - 将固件设置为
OVMF_CODE - 勾选
CPU 数-拓扑-手动设置 CPU 拓扑,根据实际情况设置 - 开始安装
- Windows 安装成功后,关闭虚拟机。然后重启
libvirt以激活Hook:
sudo systemctl restart libvirtd.service
修改 VBIOS
网上很多的教程都需要这一步,但我实际测试下来,现在好像已经不需要这一步的操作了。
最后准备
- 删除
USB Redirector 1和USB Redirector 2 - 删除
Sound ich9 - 删除
Channel spice - 进入
概况页,在XML中找到以下内容并删除
<graphics type="spice" autoport="yes">
<listen type="address"/>
<image compression="off"/>
</graphics>
<audio id="1" type="spice"/>
- 直通鼠标和键盘:在
添加硬件 - USB 主机设备的详情页面中找到对应USB设备
- 直通显卡:在
添加硬件 - PCI 主机设备的详情页中找到显卡和音频设备并添加
- 网卡。因为我显示器上还有一张单独的网卡,所以我选择把它也直通进去
配置完成,试着启动一下虚拟机吧(