一畳のくつろぎタイム

このブログでは紹介する商品画像をAmazonアソシエイトより借りています。画像やリンクにはアフィリエイト広告が含まれる事があります

2025年2月12日水曜日

SandyおじさんPCはGPU-Pの夢をみれるか?

Electoric sheep dream by fastSDCPU

SandyおじさんPC(※今は厳密にはIvy)は実験用に使用しています。
今回、このPCを有効活用すべく、GPUが使用できるHyper-V仮想マシンを稼働させようと目論見ました。

 

GPU-Pって何?

このような記事にたどり着いている時点でご存じの方がほとんどとは思いますが、一応説明させていただくと、ホストPCが搭載しているGPUをパーティション化(分割)してゲストPCからも使えるようにするというMicrosoftのHyper-Vに搭載されている素晴らしい機能のことです。

何が素晴らしいの?

普通仮想マシンのグラフィック機能はショボいです。

パーティション化の対象にするGPUの性能にもよりますが、これがゲームが動くレベルになるのです。それからParsecという低遅延リモートデスクトップアプリケーションが仮想マシンで使用可能になります。 

普通のパソコンでは、明確に「GPUを搭載していないPC」であっても、実際にはGPUが存在しないわけではなく、CPU内臓グラフィックス(intel HD GraphicsやIrisなど)という形で存在はしています。

CPU内臓グラフィックスは性能は高くないものの、仮想マシンのグラフィック性能よりは性能が高く、CPU内臓グラフィックス性能を基準に動作環境が設定されているアプリケーションもあります。

仮想マシンが、グラフィック要素も扱える普通のパソコンになるという表現がわかりやすいかもしれません。


試す

ホスト環境(こちらの記事のPCです)

  • Windows10Pro
  • Geforce GTX1050
  • IvyBridge(Core i5-3470)
  • B75M-PLUS マザーボード

Hyper-vゲスト仮想マシンは作成済みでWindows10Proが入っている状況です。

ゲスト環境

  • 仮想マシン名前 Win10Pro 
  • Windows10Pro

※GPU-P関連コマンドはホストがWindows10と11では微妙に異なるところがあるのでご注意ください。

GPU情報の取得

まずPowerShellを起動してGPUの情報を得ます。
搭載しているGPUはGeforceなので、調べる名前を
"*GeForce*"
とします。

PS C:\windows\system32>
Get-PnpDevice -PresentOnly | Where-Object { $_.Status -eq "OK" -and $_.Class -eq "Display" -and $_.FriendlyName -like "*GeForce*" } | Select-Object -First 1| Format-Table -AutoSize -Wrap

結果

Status Class   FriendlyName            InstanceId
------ -----   ------------            ----------
OK     Display NVIDIA GeForce GTX 1050 PCI\VEN_10DE&DEV_1C81&SUBSYS_146919DA&REV_A1\4&BAB4994&0&0008

 

結果に出ているInstanceIdが必要です

PCI\VEN_10DE&DEV_1C81&SUBSYS_146919DA&REV_A1\4&BAB4994&0&0008

次のコマンドで必要なため、\を#に置き換える加工をします。

PCI#VEN_10DE&DEV_1C81&SUBSYS_146919DA&REV_A1#4&BAB4994&0&0008

次にGPUパーティションの情報を得ます
 

GPUパーティション情報を得る

先に調べたInstanceIdを指定して調べます。

PS C:\windows\system32>
Get-VMPartitionableGpu |
Where-Object { $_.Name -like "\\?\PCI#VEN_10DE&DEV_1C81&SUBSYS_146919DA&REV_A1#4&BAB4994&0&0008#*" } |
Select-Object -First 1

結果

Name                    : \\?\PCI#VEN_10DE&DEV_1C81&SUBSYS_146919DA&REV_A1#4&bab4994&0&0008#{064092b3-625e-43bf-9eb5-dc
                          845897dd59}\GPUPARAV
ValidPartitionCounts    : {32}
PartitionCount          : 32
TotalVRAM               : 1000000000
AvailableVRAM           : 1000000000
MinPartitionVRAM        : 0
MaxPartitionVRAM        : 1000000000
OptimalPartitionVRAM    : 1000000000
TotalEncode             : 18446744073709551615
AvailableEncode         : 18446744073709551615
MinPartitionEncode      : 0
MaxPartitionEncode      : 18446744073709551615
OptimalPartitionEncode  : 18446744073709551615
TotalDecode             : 1000000000
AvailableDecode         : 1000000000
MinPartitionDecode      : 0
MaxPartitionDecode      : 1000000000
OptimalPartitionDecode  : 1000000000
TotalCompute            : 1000000000
AvailableCompute        : 1000000000
MinPartitionCompute     : 0
MaxPartitionCompute     : 1000000000
OptimalPartitionCompute : 1000000000
CimSession              : CimSession: .
ComputerName            : TEMP01
IsDeleted               : False

GPUパーティション情報が得られます。Windows11の場合はこの文字列を使って取り付けコマンドを発行しますが、Windows10の場合は指定が不可能なので確認しただけです。

\\?\PCI#VEN_10DE&DEV_1C81&SUBSYS_146919DA&REV_A1#4&bab4994&0&0008#{064092b3-625e-43bf-9eb5-dc845897dd59}\GPUPARAV

Windows11ならば-InstancePathでこの文字を使ってどのGPUなのかを指定可能です、Windows10の場合は1つのGPU決め打ちとなるため、GPUパーティション情報の確認作業は実は必須ではなかったりします。

 

取り付けコマンド 

PS C:\windows\system32>Add-VMGpuPartitionAdapter -VMName "Win10Pro"

 

ドライバー配置ディレクトリの作成(ゲストのストレージ)

あとでドライバーファイルを置くため、仮想マシンを起動してExplorerで次のディレクトリを作成しておく
D:\Windows\System32\HostDriverStore\FileRepository 

仮想マシンはシャットダウンします。


仮想マシンで使うGPUドライバを探す

GPU-Pの面倒なところがホストが使ってるドライバと同じものを使用する必要があるというところ。
場所はホストの
C:\WINDOWS\System32\DriverStore\FileRepository
に入ってることはわかってるので、先に作ったゲストの(D:\Windows\System32\HostDriverStore\FileRepository )へ全コピーしてもいいのではあるが、大量にあるためそれなりに時間がかかるし、ディスクも無駄。
対象のドライバーだけコピーするのがよろしい。

ドライバーを探すコマンド

PS C:\windows\system32>Get-CimInstance -ClassName Win32_VideoController -Property * | Format-Table InstalledDisplayDrivers -AutoSize -Wrap 

結果

InstalledDisplayDrivers
-----------------------

igdumd64.dll,igd10umd64.dll,igd10umd64.dll
C:\WINDOWS\System32\DriverStore\FileRepository\nv_dispig.inf_amd64_50916785244854f2\nvldumdx.dll,
C:\WINDOWS\System32\DriverStore\FileRepository\nv_dispig.inf_amd64_50916785244854f2\nvldumdx.dll,
C:\WINDOWS\System32\DriverStore\FileRepository\nv_dispig.inf_amd64_50916785244854f2\nvldumdx.dll,
C:\WINDOWS\System32\DriverStore\FileRepository\nv_dispig.inf_amd64_50916785244854f2\nvldumdx.dll

※上記例は本来はつながって表示されますが、見やすく改行してあります。


つまり場所は

C:\WINDOWS\System32\DriverStore\FileRepository\nv_dispig.inf_amd64_50916785244854f2

 

ドライバーファイルのコピー

ホストのWindows標準の「ディスクの管理」アプリから仮想マシンのvhdファイルへ接続をし
C:\ProgramData\Microsoft\Windows\Virtual Hard Disks
にあるvhdをマウント(仮想マシンの作り方によって場所は違うかも)

するとホストのエクスプローラーからゲストPCのディスクが扱えるようになるので、

あらかじめ作っておいたゲストのディレクトリ
D:\Windows\System32\HostDriverStore\FileRepository

C:\WINDOWS\System32\DriverStore\FileRepository\nv_dispig.inf_amd64_5091
をまるごとコピーする

 

マウントしたVHDをマウント解除し、ゲストを起動するがGPUは生えてはいるが使えない。

 


ゲストを一度シャットダウンして

GPU-Pの詳細設定をする(細かいことはよくわからない)PowerShell上で実行してます。

 

Set-VMGpuPartitionAdapter -VMName "Win10Pro" -MinPartitionVRAM 100000000
Set-VMGpuPartitionAdapter -VMName "Win10Pro" -MaxPartitionVRAM 100000000
Set-VMGpuPartitionAdapter -VMName "Win10Pro" -OptimalPartitionVRAM 100000000

Set-VMGpuPartitionAdapter -VMName "Win10Pro" -MinPartitionEncode 100000000
Set-VMGpuPartitionAdapter -VMName "Win10Pro" -MaxPartitionEncode 100000000
Set-VMGpuPartitionAdapter -VMName "Win10Pro" -OptimalPartitionEncode 100000000

Set-VMGpuPartitionAdapter -VMName "Win10Pro" -MinPartitionDecode 100000000
Set-VMGpuPartitionAdapter -VMName "Win10Pro" -MaxPartitionDecode 100000000
Set-VMGpuPartitionAdapter -VMName "Win10Pro" -OptimalPartitionDecode 100000000

Set-VMGpuPartitionAdapter -VMName "Win10Pro" -MinPartitionCompute 100000000
Set-VMGpuPartitionAdapter -VMName "Win10Pro" -MaxPartitionCompute 100000000
Set-VMGpuPartitionAdapter -VMName "Win10Pro" -OptimalPartitionCompute 100000000
    
Set-VM -GuestControlledCacheTypes $true -VMName "Win10Pro"
Set-VM -LowMemoryMappedIoSpace 1Gb -VMName "Win10Pro"
Set-VM -HighMemoryMappedIoSpace 2GB -VMName "Win10Pro"

設定変えたらゲストが起動不能になる。 

 The upper MMIO region (0x00000017dffff000) is above the supported physical address range

MMIOで調べると、intel-VTがONである必要がある話とか、64bitOSではAbove 4g Decodingが有効である必要があったりするなど出てくるので、確認するが自分の環境では問題ない。

それからCSMというUEFIがBIOSとの互換性を持つ機能が有効になっていて、これもOFFにする必要があるようだが、CSMがONだったのでOFFにするとwindowが起動しない。
どうやら、自分の環境ではCSMを活用しており、使ってるディスクがMBRっぽい
CSMを解除するとディスクが見つからなくなってしまい、困る。

仕方ないので、MBR->GPT変換をする

アプライドネットさんのサイトで、MBRをGPTにデータを失わず、しかも標準ツールでできると知り試す。
https://shop.applied-net.co.jp/blog/cate_news/23507/

チェック

C:\WINDOWS\system32>mbr2gpt /validate /disk:0 /allowFullOS
MBR2GPT: Attempting to validate disk 0
MBR2GPT: Retrieving layout of disk
MBR2GPT: Validating layout, disk sector size is: 512 bytes
MBR2GPT: Validation completed successfully

 変換

C:\WINDOWS\system32>mbr2gpt /convert /disk:0 /allowFullOS

MBR2GPT will now attempt to convert disk 0.
If conversion is successful the disk can only be booted in GPT mode.
These changes cannot be undone!

MBR2GPT: Attempting to convert disk 0
MBR2GPT: Retrieving layout of disk
MBR2GPT: Validating layout, disk sector size is: 512 bytes
MBR2GPT: Trying to shrink the OS partition
MBR2GPT: Creating the EFI system partition
MBR2GPT: Installing the new boot files
MBR2GPT: Performing the layout conversion
MBR2GPT: Migrating default boot entry
MBR2GPT: Adding recovery boot entry
MBR2GPT: Fixing drive letter mapping
MBR2GPT: Conversion completed successfully
Call WinReReapir to repair WinRE
MBR2GPT: Failed to update ReAgent.xml, please try to  manually disable and enable WinRE.
MBR2GPT: Before the new system can boot properly you need to switch the firmware to boot to UEFI mode!

すごい、ディスク初期化が必要だと思ったが、データを失うことなくできてしまった。

CSMを無効にしても、起動できるようになり、しかし仮想マシンは変わらず。
MMIOが・・・といわれる。

GPU-Pの詳細設定の数値の問題かと考え、いろいろ試す。
Set-VM -HighMemoryMappedIoSpace 512Mb -VMName "Win10Pro"
この512Mbを1Mでも超える(例:513Mbなど)と起動不能になるらしい。

かといって512Mbに下げてもGPUが動作するわけでもなく、コード43で動かない

いろいろ調べてるいると こちらの一番下のコメントで

https://learn.microsoft.com/en-us/answers/questions/75243/the-upper-mmio-region-error-if-highmemorymappedios

「ハードウェアが古いんじゃね?」

と言われており、 他も調べてみるとネットの方々たちはRyzen PCでやったら何の問題なかったと語っており、自分もRyzenとRadeon RX580でGPU-Pはできている。

同じ問題に直面している人たちのハードウェアがSandyやIvyで、なんならB75マザーで同じ人までいた。

B75マザーが同じ方

https://www.reddit.com/r/HyperV/comments/nfhrqx/hyperv_gpup_mmio_error/ 

まさにSandyBridgeの方

https://github.com/jamesstringerparsec/Easy-GPU-PV/issues/40


GPU-Pのメモリ設定が良くわかっていないし、私も別環境(Ryzen)ではうまくいっているため

真実はわかりませんが、ハードウェアの古さが問題である可能性は高い。

結論

GPU-Pの夢は見れなさそう・・。
知識不足や設定間違い等もあるかもしれません。

そして外国人にもSandyおじさんがたくさんいた。