pci passthrough with qemu

本文详细介绍了如何在Linux KVM环境下,通过硬件支持iommu实现设备passthrough的方法,包括硬件检查、内核配置、错误分析及解决策略等关键步骤。同时,还探讨了使用vfio进行passthrough的不同之处和具体操作。

http://pic.dhe.ibm.com/infocenter/lnxinfo/v3r0m0/index.jsp?topic=%2Fliaat%2Fliaatbppassthrougtask.htm


http://www.linux-kvm.org/page/How_to_assign_devices_with_VT-d_in_KVM


1. 确定硬件是否支持iommu

这是一个硬件的功能,intel架构上叫vt-d。

从BIOS上可以看出来, 不同版本放的位置不一样。

我的是在 Security->Virtualization->VT-d


2. 配置kernel,支持iommu

在intel机器上有这么个选项,

INTEL_IOMMU

  │   Location:                                                                                                                            │  
  │     -> Device Drivers                                                                                                                  │  
  │ (2)   -> IOMMU Hardware Support (IOMMU_SUPPORT [=y]) 


3. 重启,看看是否enable了。

在intel上,运行

dmesg | grep -e DMAR -e IOMMU


4. 在host上unbind设备

加载pci_stub模块, modprobe pci_stub

选中某个设备, lspci -s 03:00.0 -n, 03:00.0 0280: 8086:0085 (rev 34)

bind/unbind

  • echo "8086 0085" > /sys/bus/pci/drivers/pci-stub/new_id
  • echo 0000:03:00.0 > /sys/bus/pci/devices/0000:01:00.0/driver/unbind
  • echo 0000:03:00.0 > /sys/bus/pci/drivers/pci-stub/bind

5. 把设备给guest

./i386-softmmu/qemu-system-i386 -enable-kvm \

-drive file=../../kvm/ubuntu.qcow2 -boot dc -m 512  \

-monitor stdio \

-netdev user,id=usernet -device rtl8139,netdev=usernet \

-device pci-assign,host=0000:03:00.0


不过偶没有成功,报错了。。。


6. 错误分析,解决

按照上面的办法没成功,我看了一下dmesg,有这么一句。

kvm_iommu_map_guest: No interrupt remapping support, disallowing device assignment. Re-enble with "allow_unsafe_assigned_interrupts=1" module option.


稍微调查了一下,发现和这个选项有关,config IRQ_REMAP。 可惜我enable不了,因为这个必须在x86_64上做。

没办法,那我只好在装载kvm模块的时候加上这个参数的设置了。


加上这个参数后,果然就好了。赞。



接下来我用了vfio来做passthrough。步骤略有不同

1. 安装相关的kernel module

sudo modprobe vfio

sudo modprobe vfio-pci


这样就产生了 /dev/vfio/vfio 设备


2. 按照文档要求,添加设备到一个group

按照现在的要求,需要讲某一个iommu_group下的所有设备都添加到一个vfio group.

cd /sys/bus/pci/devices/0000:0d:00.0/

readlink iommu_group  这样可以显示该设备对应iommu_group的名字

ll iommu_group/devices 这样可以显示和该设备处于一个iommu_group的设备。


echo 0000:0d:00.0 > /sys/bus/pci/devices/0000:0d:00.0/driver/unbind

echo 1180 e823 > /sys/bus/pci/drivers/vfio-pci/new_id

echo 0000:03:00.0 > /sys/bus/pci/devices/0000:03:00.0/driver/unbind

echo 8086 0085 > /sys/bus/pci/drivers/vfio-pci/new_id


这样就生成了 /dev/vfio/6  (数字由iommu_group号决定)


3. 启动 guest

../git/qemu-latest/i386-softmmu/qemu-system-i386 -enable-kvm -drive file=ubuntu.qcow2 -boot dc -m 512  -monitor stdio -netdev user,id=usernet -device vfio-pci,host=0000:03:00.0


如果是在power机器上,则写成

-device "spapr-pci-vfio-host-bridge,id=CXGB3,iommu=4,index=6"


4. fix

默认这么启动会有个错误,当然这是在我的机器上。

vfio_iommu_type1_open: No interrupt remapping support.  Use the module param "allow_unsafe_interrupts" to enable VFIO IOMMU support on this platform


意思是我这个机器不支持remap, 那我就把这个参数直接设成了1.  就好了。





PCI虚拟化技术旨在将物理PCI设备的资源分配给多个虚拟机(VM),从而实现资源的高效利用。该技术的核心原理是通过硬件辅助虚拟化和软件管理机制,将PCI设备的功能虚拟化并提供给每个虚拟机使用。 ### 技术实现原理 1. **硬件辅助虚拟化** 现代处理器和芯片组支持PCI虚拟化技术,例如Intel的VT-d(Virtualization Technology for Directed I/O)和AMD的AMD-Vi(AMD Virtualization Technology with IOMMU)。这些技术允许虚拟机直接访问物理PCI设备,同时确保安全性和隔离性。VT-d和AMD-Vi通过IOMMU(Input-Output Memory Management Unit)将设备地址转换为物理地址,从而实现设备的直接分配[^1]。 2. **设备直通(Device Passthrough)** 设备直通是PCI虚拟化的一种常见实现方式。它允许将一个物理PCI设备直接分配给特定的虚拟机,虚拟机可以直接访问设备的硬件资源,而不需要通过宿主机的中间层。这种技术的优点是性能接近物理设备,但需要硬件支持,并且设备只能被一个虚拟机独占使用。 3. **SR-IOV(Single Root I/O Virtualization)** SR-IOV是一种扩展的PCI标准,允许单个物理设备(如网卡或存储控制器)表现为多个独立的虚拟设备。每个虚拟设备(称为VF,Virtual Function)可以直接分配给不同的虚拟机,而不需要宿主机的干预。这种方式可以显著提高性能并减少宿主机的开销。 4. **软件管理与调度** 在某些情况下,硬件辅助虚拟化可能不可用,或者需要更灵活的资源分配。此时,软件层(如KVM或Xen)可以通过模拟PCI设备的方式实现虚拟化。这种方式的性能通常不如硬件辅助虚拟化,但提供了更高的灵活性。 ### 配置指南 1. **检查硬件支持** 在配置PCI虚拟化之前,首先需要确认处理器和芯片组是否支持硬件辅助虚拟化技术(如Intel VT-d或AMD-Vi)。可以通过以下命令检查Linux系统中的硬件支持情况: ```bash dmesg | grep -i iommu ``` 如果输出中显示`IOMMU enabled`,则表示硬件支持已启用。 2. **启用IOMMU** 在Linux系统中,需要在内核启动参数中启用IOMMU功能。编辑`/etc/default/grub`文件,添加以下参数: ```bash GRUB_CMDLINE_LINUX_DEFAULT="quiet splash iommu=pt iommu=1" ``` 然后更新GRUB配置: ```bash sudo update-grub ``` 3. **配置设备直通** 使用KVM/QEMU时,可以通过命令行或配置文件将物理PCI设备分配给虚拟机。例如: ```bash qemu-system-x86_64 -device vfio-pci,host=01:00.0,id=hostdev0 -other-args... ``` 其中`host=01:00.0`表示物理设备的PCI地址。 4. **配置SR-IOV** 对于支持SR-IOV的设备(如某些网卡),需要在驱动中启用虚拟功能(VF)。例如,使用`ip`命令查看设备的VF支持: ```bash ip link show <device_name> ``` 然后启用指定数量的VF: ```bash ip link set <device_name> vf <number_of_vfs> ``` 5. **虚拟机配置** 在虚拟机管理工具(如libvirt)中,需要将虚拟设备分配给虚拟机。对于SR-IOV,可以将VF直接分配给虚拟机;对于设备直通,则需要将物理设备绑定到`vfio-pci`驱动。 6. **性能优化** 为了提高性能,建议结合硬件加速技术(如DPDK)和性能分析工具(如`perf`)进行优化。定期检查虚拟化网络的健康状况,确保资源分配合理。 ###
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值