1. 直通的必要条件
hyper-v的直通,又名Discrete Device Assignment, DDA,或passthrough
1.1 服务器要求
windows server 2016或更新版本的服务器系统,windows 10等针对普通用户的消费级系统并没有直通功能。
1.2 BIOS支持
开启IOMMU (Intel VT-d或AMD-Vi),备注:有些主板要手动开启,有些主板没有类似选项,但默认已开启。具体情况视主板型号而定。
2. 硬盘要求
m.2接口的硬盘其实有两种,一种是走nvme协议,一种是走sata协议。
2.1 nvme协议的m.2硬盘(也包括u2接口的)可以直通。
2.2 sata协议的m.2硬盘不能直通。
3. 直通的优势
3.1 获得硬盘的最佳性能
可以直接在虚拟机中安装硬盘评测软件进行跑分得知。
3.2 能获取硬盘的硬件参数
例如硬盘型号、制造商、温度等信息。
4. 直通与非直通的区别
4.1 直通的硬盘在虚拟机中有nvme控制器和硬盘信息
4.1.1 直通的硬盘在磁盘管理器中显示具体的硬盘型号

4.1.2 直通的硬盘在存储控制器中有一个对应的nvme控制器

4.2 虚拟的硬盘(vhdx文件)在磁盘管理器中体现为一个micrsoft虚拟磁盘(也没有对应的nvme控制器),如下图所示:

5. 直通具体步骤
直通nvme硬盘本质上就是直通其对应的nvme控制器
因为nvme控制器的属性无法看到具体的硬盘信息,所以这里要通过硬盘信息来定位其对应的nvme控制器
5.1 确定nvme控制器的【位置路径】信息
5.1.1 获取待直通硬盘的总线值
从【设备管理器】中的【磁盘驱动器】中找到具体的硬盘(在这里,我要直通的硬盘为Samsung SSD 970 EVO 500GB),右键选择属性,然后在【详细信息】标签中选择【设备实例路径】项,如下图所示:

其设备实例路径如下:
SCSI\DISK&VEN_NVME&PROD_SAMSUNG_SSD_970\5&33C763C9&0&000000
在这里,需要获取\5&后面的值,即"总线值"(这个名字是我根据上下文取的,实际上是否含有该意义我也不清楚):33C763C9
已成功获取硬盘总线值:33C763C9
5.1.2 查找总线值为33C763C9 的nvme控制器
在【设备管理器】中的【存储控制器】中查看每一个【标准 NVM Express 控制器
】设备,获取其属性【详细信息】中的【总线关系】,其值如下:

SCSI\Disk&Ven_NVMe&Prod_Samsung_SSD_970\5&33c763c9&0&000000
在这里可以看到该nvme控制器(即存储控制器下的第1个nvme控制器)中总线值为:33c763c9
也即与磁盘驱动器中的总线值相同
5.1.3 获取nvme控制器的【位置路径】信息
所以该nvme控制器也即我们要直通的控制器了,从其详细信息中获取【位置路径】即可,即:
PCIROOT(0)#PCI(1C04)#PCI(0000)
如下图所示:

已成功获取nvme控制器【位置路径】:PCIROOT(0)#PCI(1C04)#PCI(0000)
上面获取位置路径的方法有些麻烦,所以这里写了一个powershell脚本,可以查看nvme控制器及其对应的磁盘驱动器关系,如下图所示:
暂略,写完再更新。。。
5.2 设备卸载
5.2.1 设置虚拟机名称与位置路径变量
(记得修改为实际的值),在Powershell下输入:
$vm = "tpl_win10_22h2"
$location_path = "PCIROOT(0)#PCI(1C04)#PCI(0000)"
5.2.2 手动禁用该设备
如下图所示:

5.2.3 卸载硬件(即nvme控制器)
在同一个powershell下执行:
Dismount-VMHostAssignableDevice -LocationPath $location_path -Force
注:如果卸载失败(可能bios未设置好或不支持直通)
成功卸载后,物理机上的【存储控制器】不再显示该nvme控制器,如下图所示:

5.3 关闭虚拟机
5.4 禁用虚拟机状态保存
直通设备的虚拟机不能被暂停(保存)或热迁移,所以自动关机动作必须为 ACPI shutdown 或者硬关机
Set-VM -Name $vm -AutomaticStopAction TurnOff
5.5 挂载nvme控制器到虚拟机中:
Add-VMAssignableDevice -VMName $vm -LocationPath $location_path
5.6 启动虚拟机,在设备管理器中查看nvme控制器是否成功直通

6. 如何取消直通
!!!以下内容在一个全新的powershell下执行
6.1 首先要记得硬盘直接给了哪个虚拟机
也即前述的tpl_win10_22h2, 所以这里先设置$vm变量以备之后使用:
$vm = "tpl_win10_22h2"
6.2 关掉该虚拟机
6.3 获取取该虚拟机直通的设备
# 查看虚拟机直通设备情况
Get-VMAssignableDevice -VMName $vm
显示如下:

6.4 获取直通设备(硬盘)的LocationPath
也即: PCIROOT(0)#PCI(1C04)#PCI(0000)
继续创建该变量以备之后使用:
$location_path = "PCIROOT(0)#PCI(1C04)#PCI(0000)"
6.5 该虚拟机移除此直通的设备
Remove-VMAssignableDevice -VMName $vm -LocationPath $location_path
6.6 重新挂载回物理机
mount-VMHostAssignableDevice -LocationPath $location_path
6.7 在设备管理器中重新启用即可

7. 错误处理
7.1 无法分配不符合当前设置组策略的 PCI Express 设备
如果报类似错误:无法分配不符合当前设置组策略的 PCI Express 设备“PCIP\VEN_10EC&DEV_8125&SUBSYS_012310EC&REV_05\01000000684CE00000”。 有关详细信息,请参阅 HyperV\RequireSecureDeviceAssignment 和 HyperV\RequireSupportedDeviceAssignment。
解决办法:
在注册表 HKLM:HKEY_LOCAL_MACHINE\SOFTWARE\Policies\Microsoft\Windows\HyperV (HyperV项手动添加)下添加RequireSecureDeviceAssignment和RequireSupportedDeviceAssignment两个DWORD值,都设置为0

3942

被折叠的 条评论
为什么被折叠?



