前回までに、debian で 通常 option で cross build した qemu for windows が Windows10 で起動できる所まで確認した。
hiro20180901.hatenablog.com
hiro20180901.hatenablog.com
今回は、whpx を有効にして build し、Hyper-V 環境で起動できるかを確認してみた。
whpx 有効で configure
先ずは、何も準備しないで whpx を有効にして configure を実施してみた。
# PKG_CONFIG_LIBDIR=/usr/x86_64-w64-mingw32/lib/pkgconfig ../../../configure --cross-prefix=x86_64-w64-mingw32- --disable-guest-agent-msi --disable-werror --enable-whpx ERROR: User requested feature WinHvPlatform configure was not able to find it. WinHvEmulation is not installed
まぁ、そうだよね。
configure :
... 略 ... ########################################## # Windows Hypervisor Platform accelerator (WHPX) check if test "$whpx" != "no" ; then if check_include "WinHvPlatform.h" && check_include "WinHvEmulation.h"; then whpx="yes" else if test "$whpx" = "yes"; then feature_not_found "WinHvPlatform" "WinHvEmulation is not installed" fi whpx="no" fi fi ... 略 ...
WinHvPlatform.h と WinHvEmulation.h の存在を check している。
WinHv 関連の header file の準備
www.douban.com
こちらを参考に git で落としてきた。
# git clone --depth 1 https://android.googlesource.com/platform/prebuilts/gcc/linux-x86/host/x86_64-w64-mingw32-4.8 Cloning into 'x86_64-w64-mingw32-4.8'... remote: Counting objects: 4086, done remote: Finding sources: 100% (4086/4086) remote: Total 4086 (delta 1947), reused 3891 (delta 1947) Receiving objects: 100% (4086/4086), 52.63 MiB | 7.31 MiB/s, done. Resolving deltas: 100% (1947/1947), done. Checking out files: 100% (4002/4002), done. # find x86_64-w64-mingw32-4.8 | grep -i winhv x86_64-w64-mingw32-4.8/x86_64-w64-mingw32/include/WinHvPlatformDefs.h x86_64-w64-mingw32-4.8/x86_64-w64-mingw32/include/WinHvEmulation.h x86_64-w64-mingw32-4.8/x86_64-w64-mingw32/include/WinHvPlatform.h x86_64-w64-mingw32-4.8/x86_64-w64-mingw32/lib/libWinHvPlatform.a x86_64-w64-mingw32-4.8/x86_64-w64-mingw32/lib/libWinHvEmulation.a # cp x86_64-w64-mingw32-4.8/mingw/include/WinHv* /usr/x86_64-w64-mingw32/include # cp x86_64-w64-mingw32-4.8/mingw/lib/libWinHv* /usr/x86_64-w64-mingw32/lib
whpx 有効で configure (再)
WinHv 関連の include と lib が準備できたので、configure に再チャレンジした。
# PKG_CONFIG_LIBDIR=/usr/x86_64-w64-mingw32/lib/pkgconfig ../../../configure --cross-prefix=x86_64-w64-mingw32- --disable-guest-agent-msi --disable-werror --enable-whpx Install prefix c:/Program Files/QEMU BIOS directory c:/Program Files/QEMU firmware path c:/Program Files/QEMU/share/qemu-firmware binary directory c:/Program Files/QEMU library directory c:/Program Files/QEMU/lib module directory c:/Program Files/QEMU/lib libexec directory c:/Program Files/QEMU/libexec include directory c:/Program Files/QEMU/include config directory c:/Program Files/QEMU local state directory queried at runtime Windows SDK no Source path /qemu GIT binary git GIT submodules ui/keycodemapdb tests/fp/berkeley-testfloat-3 tests/fp/berkeley-softfloat-3 dtc capstone C compiler x86_64-w64-mingw32-gcc Host C compiler cc C++ compiler x86_64-w64-mingw32-g++ Objective-C compiler x86_64-w64-mingw32-gcc ARFLAGS rv CFLAGS -O2 -U_FORTIFY_SOURCE -D_FORTIFY_SOURCE=2 -g QEMU_CFLAGS -I/usr/x86_64-w64-mingw32/sys-root/mingw/include/pixman-1 -I$(SRC_PATH)/dtc/libfdt -DHAS_LIBSSH2_SFTP_FSYNC -I/usr/x86_64-w64-mingw32/sys-root/mingw/include -mms-bitfields -I/usr/x86_64-w64-mingw32/sys-root/mingw/include/glib-2.0 -I/usr/x86_64-w64-mingw32/sys-root/mingw/lib/glib-2.0/include -I/usr/x86_64-w64-mingw32/sys-root/mingw/include -m64 -mcx16 -I$(SRC_PATH)/hosts/w32/include -mthreads -D_POSIX=1 -D__USE_MINGW_ANSI_STDIO=1 -DWIN32_LEAN_AND_MEAN -DWINVER=0x501 -D_GNU_SOURCE -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE -Wextra -Wno-error=parentheses -Wno-error=format-extra-args -Wno-error=format -Wno-override-init -Wno-sign-compare -Wno-missing-field-initializers -Wno-unused-parameter -Wstrict-prototypes -Wredundant-decls -Wmissing-format-attribute -Wall -Wundef -Wwrite-strings -Wmissing-prototypes -fno-strict-aliasing -fno-common -fwrapv -Wexpansion-to-defined -Wendif-labels -Wno-shift-negative-value -Wempty-body -Wnested-externs -Wformat-security -Wformat-y2k -Winit-self -Wignored-qualifiers -Wold-style-declaration -Wold-style-definition -Wtype-limits -I/usr/x86_64-w64-mingw32/sys-root/mingw/include -I/usr/x86_64-w64-mingw32/sys-root/mingw/include/p11-kit-1 -I/usr/x86_64-w64-mingw32/sys-root/mingw/include -I/usr/x86_64-w64-mingw32/sys-root/mingw/include -I/usr/x86_64-w64-mingw32/sys-root/mingw/include -I/usr/x86_64-w64-mingw32/sys-root/mingw/include/libpng16 -I/usr/x86_64-w64-mingw32/sys-root/mingw/include -I$(SRC_PATH)/capstone/include LDFLAGS -Wl,--nxcompat -Wl,--no-seh -Wl,--dynamicbase -Wl,--warn-common -m64 -g QEMU_LDFLAGS -L$(BUILD_DIR)/dtc/libfdt make make install install python python -B smbd /usr/sbin/smbd module support no host CPU x86_64 host big endian no target list aarch64-softmmu alpha-softmmu arm-softmmu cris-softmmu hppa-softmmu i386-softmmu lm32-softmmu m68k-softmmu microblaze-softmmu microblazeel-softmmu mips-softmmu mips64-softmmu mips64el-softmmu mipsel-softmmu moxie-softmmu nios2-softmmu or1k-softmmu ppc-softmmu ppc64-softmmu riscv32-softmmu riscv64-softmmu s390x-softmmu sh4-softmmu sh4eb-softmmu sparc-softmmu sparc64-softmmu tricore-softmmu unicore32-softmmu x86_64-softmmu xtensa-softmmu xtensaeb-softmmu gprof enabled no sparse enabled no strip binaries yes profiler no static build no SDL support yes (2.0.7) GTK support yes (3.22.28) GTK GL support no VTE support no TLS priority NORMAL GNUTLS support yes libgcrypt no nettle yes (3.4) libtasn1 yes curses support yes virgl support no curl support yes mingw32 support yes Audio drivers dsound Block whitelist (rw) Block whitelist (ro) VirtFS support no Multipath support no VNC support yes VNC SASL support no VNC JPEG support yes VNC PNG support yes xen support no brlapi support no bluez support no Documentation yes Tools qemu-ga qemu-img$(EXESUF) qemu-io$(EXESUF) qemu-edid$(EXESUF) PIE no vde support no netmap support no Linux AIO support no (X)ATTR support no Install blobs yes KVM support no HAX support yes HVF support no WHPX support yes TCG support yes TCG debug enabled no TCG interpreter no malloc trim support no RDMA support no PVRDMA support no fdt support git membarrier no preadv support no fdatasync no madvise no posix_madvise no posix_memalign no libcap-ng support no vhost-net support no vhost-crypto support no vhost-scsi support no vhost-vsock support no vhost-user support no Trace backends log spice support no rbd support no xfsctl support no smartcard support no libusb yes usb net redir yes OpenGL support no OpenGL dmabufs no libiscsi support no libnfs support no build guest agent yes QGA VSS support no QGA w32 disk info yes QGA MSI support no seccomp support no coroutine backend win32 coroutine pool no debug stack usage no mutex debugging no crypto afalg no GlusterFS support no gcov gcov gcov enabled no TPM support yes libssh2 support yes TPM passthrough no TPM emulator no QOM debugging yes Live block migration yes lzo support yes snappy support no bzip2 support yes NUMA host support no libxml2 yes tcmalloc support no jemalloc support no avx2 optimization yes replication support yes VxHS block device no bochs support yes cloop support yes dmg support yes qcow v1 support yes vdi support yes vvfat support yes qed support yes parallels support yes sheepdog support yes capstone git docker no libpmem support no libudev no NOTE: cross-compilers enabled: 'x86_64-w64-mingw32-gcc'
今度は WHPX support yes となっている。
make
# make -j4 2>&1 > ~/qemu_make.log &
問題なく終了した。
make installer
installer の名前を変えて作成した。Makefile も前回の W64 についての変更を反映済み。
# cd /qemu/bin/ndebug/x86_64-w64-mingw32 && make installer INSTALLER=myinstaller_whpx.exe make install prefix=/tmp/qemu-nsis make[1]: Entering directory '/qemu/bin/ndebug/x86_64-w64-mingw32' install -d -m 0755 "/tmp/qemu-nsis" install -c -m 0644 qemu-doc.html "/tmp/qemu-nsis" install -c -m 0644 qemu-doc.txt "/tmp/qemu-nsis" install -c -m 0644 docs/interop/qemu-qmp-ref.html "/tmp/qemu-nsis" install -c -m 0644 docs/interop/qemu-qmp-ref.txt "/tmp/qemu-nsis" install -d -m 0755 "/tmp/qemu-nsis" install -c -m 0755 qemu-img.exe qemu-io.exe qemu-edid.exe "/tmp/qemu-nsis" x86_64-w64-mingw32-strip "/tmp/qemu-nsis/qemu-img.exe" "/tmp/qemu-nsis/qemu-io.exe" "/tmp/qemu-nsis/qemu-edid.exe" # qemu-ga is included in TOOLS, but we need special install rules for w32 install -d -m 0755 "/tmp/qemu-nsis" install -d -m 0755 "/tmp/qemu-nsis" install -c -m 0755 qemu-ga.exe qemu-img.exe qemu-io.exe qemu-edid.exe "/tmp/qemu-nsis" x86_64-w64-mingw32-strip "/tmp/qemu-nsis/qemu-ga.exe" "/tmp/qemu-nsis/qemu-img.exe" "/tmp/qemu-nsis/qemu-io.exe" "/tmp/qemu-nsis/qemu-edid.exe" set -e; for x in bios.bin bios-256k.bin sgabios.bin vgabios.bin vgabios-cirrus.bin vgabios-stdvga.bin vgabios-vmware.bin vgabios-qxl.bin vgabios-virtio.bin vgabios-ramfb.bin vgabios-bochs-display.bin ppc_rom.bin openbios-sparc32 openbios-sparc64 openbios-ppc QEMU,tcx.bin QEMU,cgthree.bin pxe-e1000.rom pxe-eepro100.rom pxe-ne2k_pci.rom pxe-pcnet.rom pxe-rtl8139.rom pxe-virtio.rom efi-e1000.rom efi-eepro100.rom efi-ne2k_pci.rom efi-pcnet.rom efi-rtl8139.rom efi-virtio.rom efi-e1000e.rom efi-vmxnet3.rom qemu-icon.bmp qemu_logo_no_text.svg bamboo.dtb canyonlands.dtb petalogix-s3adsp1800.dtb petalogix-ml605.dtb multiboot.bin linuxboot.bin linuxboot_dma.bin kvmvapic.bin s390-ccw.img s390-netboot.img spapr-rtas.bin slof.bin skiboot.lid palcode-clipper u-boot.e500 u-boot-sam460-20100605.bin qemu_vga.ndrv hppa-firmware.img; do \ install -c -m 0644 /qemu/pc-bios/$x "/tmp/qemu-nsis"; \ done make -C po install make[2]: Entering directory '/qemu/bin/ndebug/x86_64-w64-mingw32/po' for obj in bg.mo tr.mo it.mo hu.mo fr_FR.mo zh_CN.mo de_DE.mo; do \ base=$(basename $obj .mo); \ install -d /tmp/qemu-nsis/share/locale/$base/LC_MESSAGES; \ install -m644 $obj /tmp/qemu-nsis/share/locale/$base/LC_MESSAGES/qemu.mo; \ done make[2]: Leaving directory '/qemu/bin/ndebug/x86_64-w64-mingw32/po' install -d -m 0755 "/tmp/qemu-nsis/keymaps" set -e; for x in da en-gb et fr fr-ch is lt modifiers no pt-br sv ar de en-us fi fr-be hr it lv nl pl ru th common de-ch es fo fr-ca hu ja mk nl-be pt sl tr bepo cz; do \ install -c -m 0644 /qemu/pc-bios/keymaps/$x "/tmp/qemu-nsis/keymaps"; \ done install -c -m 0644 /qemu/bin/ndebug/x86_64-w64-mingw32/trace-events-all "/tmp/qemu-nsis/trace-events-all" for d in aarch64-softmmu alpha-softmmu arm-softmmu cris-softmmu hppa-softmmu i386-softmmu lm32-softmmu m68k-softmmu microblaze-softmmu microblazeel-softmmu mips-softmmu mips64-softmmu mips64el-softmmu mipsel-softmmu moxie-softmmu nios2-softmmu or1k-softmmu ppc-softmmu ppc64-softmmu riscv32-softmmu riscv64-softmmu s390x-softmmu sh4-softmmu sh4eb-softmmu sparc-softmmu sparc64-softmmu tricore-softmmu unicore32-softmmu x86_64-softmmu xtensa-softmmu xtensaeb-softmmu; do \ make --no-print-directory --quiet BUILD_DIR=/qemu/bin/ndebug/x86_64-w64-mingw32 TARGET_DIR=$d/ -C $d install || exit 1 ; \ done make[1]: Leaving directory '/qemu/bin/ndebug/x86_64-w64-mingw32' (cd /tmp/qemu-nsis; \ for i in qemu-system-*.exe; do \ arch=${i%.exe}; \ arch=${arch#qemu-system-}; \ echo Section \"$arch\" Section_$arch; \ echo SetOutPath \"\$INSTDIR\"; \ echo File \"\${BINDIR}\\$i\"; \ echo SectionEnd; \ done \ ) >/tmp/qemu-nsis/system-emulations.nsh makensis -V2 -NOCD -DW64 \ -DCONFIG_DOCUMENTATION="y" \ -DCONFIG_GTK="y" \ -DBINDIR="/tmp/qemu-nsis" \ \ -DSRCDIR="/qemu" \ -DOUTFILE="myinstaller_whpx.exe" \ -DDISPLAYVERSION="3.1.0" \ /qemu/qemu.nsi rm -r /tmp/qemu-nsis # ls -l myinstaller_whpx.exe -rw-r--r-- 1 root root 80992027 Feb 16 18:05 myinstaller_whpx.exe
すんなり出来た。
Windows10 で whpx 有効で起動
Windows10 で起動し、scp で持ってきた後に install、whpx 有効で起動してみた。どうやら dll が installer に含まれていないようで、配布されている installer に上書きする形で実行ファイルのみ置き換えた。
$ ./qemu-system-x86_64.exe -accel accel=whpx C:\Program Files\qemu\qemu-system-x86_64.exe: WHPX: No accelerator found, hr=00000000 C:\Program Files\qemu\qemu-system-x86_64.exe: failed to initialize WHPX: No space left on device
だめみたい。Virtualbox と同じ現象だと思う。
qemu whpx-all.c whpx_accel_init():
... 略 ... HRESULT hr; ... 略 ... hr = whp_dispatch.WHvGetCapability( WHvCapabilityCodeHypervisorPresent, &whpx_cap, sizeof(whpx_cap), &whpx_cap_size); if (FAILED(hr) || !whpx_cap.HypervisorPresent) { error_report("WHPX: No accelerator found, hr=%08lx", hr); ret = -ENOSPC; goto error; } ... 略 ...
VirtualBox NEMR3Native-win.cpp nemR3WinInitCheckCapabilities():
... 略 ... HRESULT hrc = WHvGetCapabilityWrapper(WHvCapabilityCodeHypervisorPresent, &Caps, sizeof(Caps)); DWORD rcWin = GetLastError(); if (FAILED(hrc)) return RTErrInfoSetF(pErrInfo, VERR_NEM_INIT_FAILED, "WHvGetCapability/WHvCapabilityCodeHypervisorPresent failed: %Rhrc (Last=%#x/%u)", hrc, RTNtLastStatusValue(), RTNtLastErrorValue()); if (!Caps.HypervisorPresent) { if (!RTPathExists(RTPATH_NT_PASSTHRU_PREFIX "Device\\VidExo")) return RTErrInfoSetF(pErrInfo, VERR_NEM_NOT_AVAILABLE, "WHvCapabilityCodeHypervisorPresent is FALSE! Make sure you have enabled the 'Windows Hypervisor Platform' feature."); return RTErrInfoSetF(pErrInfo, VERR_NEM_NOT_AVAILABLE, "WHvCapabilityCodeHypervisorPresent is FALSE! (%u)", rcWin); } LogRel(("NEM: WHvCapabilityCodeHypervisorPresent is TRUE, so this might work...\n")); ... 略 ...
if が単独か多重かの違いで、判断条件は同じ。
結果
- installer に dll が入っていない。make installer の部分でもう少し対処が必要。
- WHPX 有効で起動させると No accelerator found。Hypervisor Platform は有効なのだけどね。
- Virtualbox の error message からすると、FAILED(hr) の条件は通っていて、!whpx_cap.HypervisorPresent の条件で失敗していると思う。
Windows Hypervisor Platform | Microsoft Docs
確か、qemu の whpx 部分は Microsoft の方が GPL2 で提供してくれたはずなので、WHvGetCapability の使い方を間違う事は無いと思う。他の Hyper-V (Docker 含む)の機能が正常に動作しているのに、qemu と Virtualbox が動作しない、というのが残念。
WHvGetCapability | Microsoft Docs
The WHvCapabilityCodeHypervisorPresent capability can be used to determine whether the Windows Hypervisor is running on a host and the functions of the platform APIs can be used to create VM partitions.
Return Value
If the operation completed successfully, the return value is S_OK.
これからすると、やっぱり両方が成立しないと Hyper-V 有効にならないのだが ... 片方をはずしてみるか。