From nobody Sun Apr 12 06:08:21 2026 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=pass(p=reject dis=none) header.from=unpredictable.fr ARC-Seal: i=1; a=rsa-sha256; t=1770954444; cv=none; d=zohomail.com; s=zohoarc; b=XKnCfO/RwHpsq06LsFrhqNM1sAunk0vpUZAiAThTAwb5XeSnVn4Q0z5zf21Sp8CB8rnXNVaNt277w/aidO7Lyc3ccX5WI7PdBTqDPAHZ/zt5b/mEf66dVriMrmJrRjSScyvrRxaV/9GAsL02ydNZxgA0YO/84tn0D2gXw3o0UNI= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1770954444; h=Content-Transfer-Encoding:Cc:Cc:Date:Date:From:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:Subject:To:To:Message-Id:Reply-To; bh=7W6Lt13Z1XJSZmU+RzaMy+Ab1ScstdHKGazxZ1Eo+0Y=; b=WVl9wB/sWJ2h/9TmalejRwYpt1L22C/EYl9c2Qwoqtt3ON6xBLJg8Zp4HK7QRCvO26V+jTcOeg/xU0mX9LTUQ9x/N9Cl+0LAgxIALIKRJ2AId2jTarTRkAmKPcNjY4nbPxBJfsd5371hXDomQqgbpguRUIPYbi7A7wXOHiBtSh0= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=pass header.from= (p=reject dis=none) Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1770954443898188.79806197221785; Thu, 12 Feb 2026 19:47:23 -0800 (PST) Received: from localhost ([::1] helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1vqk8Z-0008Jr-3Y; Thu, 12 Feb 2026 22:46:35 -0500 Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1vqk8Y-0008JZ-2T for qemu-devel@nongnu.org; Thu, 12 Feb 2026 22:46:34 -0500 Received: from p-west1-cluster4-host6-snip4-4.eps.apple.com ([57.103.65.245] helo=outbound.pv.icloud.com) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1vqk8V-0005dp-Hf for qemu-devel@nongnu.org; Thu, 12 Feb 2026 22:46:33 -0500 Received: from outbound.pv.icloud.com (unknown [127.0.0.2]) by p00-icloudmta-asmtp-us-west-1a-60-percent-11 (Postfix) with ESMTPS id F25E018002DA; Fri, 13 Feb 2026 03:46:25 +0000 (UTC) Received: from localhost.localdomain (unknown [17.56.9.36]) by p00-icloudmta-asmtp-us-west-1a-60-percent-11 (Postfix) with ESMTPSA id 190CD18002DF; Fri, 13 Feb 2026 03:46:21 +0000 (UTC) Dkim-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=unpredictable.fr; s=sig1; t=1770954390; x=1773546390; bh=7W6Lt13Z1XJSZmU+RzaMy+Ab1ScstdHKGazxZ1Eo+0Y=; h=From:To:Subject:Date:Message-ID:MIME-Version:x-icloud-hme; b=aBvInLKQp5IsGA3jJshKK2O1Qojo7n7oSbi3KPf5Bo2hwOJY5ooAcOuwvBup+GxQ+neoEKEk/wGfPCRc1r8A3vPN1JBrYzZ61ckDsWtELLqseToyNV8tu4pIXbCvm/t2DuF71pNP7KUNhIUbFuaiN1QwYdLTsJtQhXSyc9VTb3odl9P2Q4XEw+U3yQx6QChEYNKmux1jz7TfQyWapVJB038oLiFUzHZ09p/Mmxe75AOulvUL9iqlr/hpEGBnsSJKnBZyinCP4AUeSyel87KCs+mENK0mL1NyO043JlL21Bir08EyyV16QOthLG5yCF43aKQOdIftGW2Q7/p74ZxprA== mail-alias-created-date: 1752046281608 From: Mohamed Mediouni To: qemu-devel@nongnu.org Cc: =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= , Magnus Kulke , =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= , Bernhard Beschow , Paolo Bonzini , Mohamed Mediouni , Wei Liu , Pedro Barbuda , Cameron Esfahani , Peter Maydell , Phil Dennis-Jordan , Zhao Liu , Roman Bolshakov , =?UTF-8?q?Daniel=20P=2E=20Berrang=C3=A9?= Subject: [PATCH v2 06/10] whpx: x86: switch over from winhvemulation to target/i386/emulate Date: Fri, 13 Feb 2026 04:45:49 +0100 Message-ID: <20260213034556.13471-7-mohamed@unpredictable.fr> X-Mailer: git-send-email 2.50.1 In-Reply-To: <20260213034556.13471-1-mohamed@unpredictable.fr> References: <20260213034556.13471-1-mohamed@unpredictable.fr> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Authority-Info-Out: v=2.4 cv=E7XAZKdl c=1 sm=1 tr=0 ts=698e9e93 cx=c_apl:c_apl_out:c_pps a=azHRBMxVc17uSn+fyuI/eg==:117 a=azHRBMxVc17uSn+fyuI/eg==:17 a=HzLeVaNsDn8A:10 a=VkNPw1HP01LnGYTKEx00:22 a=Mpw57Om8IfrbqaoTuvik:22 a=GgsMoib0sEa3-_RKJdDe:22 a=1q5U6jd5_WdO0fZ7RH8A:9 X-Proofpoint-GUID: ZpnCxrVR65V0ZC5p4YTlkXHeIANvixmM X-Proofpoint-Spam-Details-Enc: AW1haW4tMjYwMjEzMDAyNSBTYWx0ZWRfXwqHG6SbFKonJ ggVBJ5X8i+jsLcg9M+0VhaoaRgDPPTm0GuOPINNEjV7QVNApcqozU+kst2RG+CSRp5ztjSvx1jG YK2MhBIADXJufNud4aZ2KAFZ2CuxjpSEUgDsbfERP6LvTpz6F5rUnlV4Qw4u7eglPh73aJGHdkx z4fR5yPzzjDQJfQiN+G2dZ9stGAd8y9psV3ZmkUrlNKxtpUc5BKY1YAcu9isnzaPwFxbmo8XoAC +C4U1Wl0OOHIFIqmhFT+nxNO62m9ssAQqy3cPjI9zSETsZU8zCj3PKXVtmdlnsQ7sIwa2ro8Tud CUicV4OojFimniwixMKK//cXOhz++5Lh0dHZ99d+jxJEBUDNdz0QTMZ6sCMX3A= X-Proofpoint-ORIG-GUID: ZpnCxrVR65V0ZC5p4YTlkXHeIANvixmM X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1121,Hydra:6.1.51,FMLib:17.12.100.49 definitions=2026-02-12_05,2026-02-12_03,2025-10-01_01 X-Proofpoint-Spam-Details: rule=notspam policy=default score=0 adultscore=0 spamscore=0 clxscore=1030 bulkscore=0 mlxscore=0 mlxlogscore=999 suspectscore=0 malwarescore=0 lowpriorityscore=0 phishscore=0 classifier=spam authscore=0 adjust=0 reason=mlx scancount=1 engine=8.22.0-2601150000 definitions=main-2602130025 X-JNJ: AAAAAAABFgBvSnawIyD3hkH+5yB/wXQl0QDziFHUEGJexEBxmTcnIYNmN1On+weP0ODX0JWOD9qlVQG7PWx0w8jcbmfYmH6HE8Rny5q/w04CPu4D9svUkkbZyUJUUYfN/DRmrqNOZikGdHeQZ+vYNuDPMOy2u+kunspOhk6RHccJST0ZwxgCcSV36QE3Y9UaYWixGBuM00FAJgWCrBFV484kY7hq4vqf2hPd2IgVuXmOmkAoRI5rNaugg4hgsa2/u8MZfIae5laj78ZqfClmTeLV4n3QAWaiGH64F1Gu2nRgI48mo4KwKlWWd4aiPmTOOPJJMQNlCTbg9Sjnr1WuF/Kf3DkWSxS2ZEIBQx0a5leQP926E80YbNTF9fxshsDwQM53VhBmrtWYnjbGCvXANl6JJ9UXlxUyj5sYJripfKdfrew0JexTlU8+5OTB0NOgTPG3jQrVMMZU6EP3LrBshhQ2wZPd3xi8gItRdAJKZbvL6Mcn/oPWStuuhD1acEkYBN/+XYiIymHsCiAC1Tx26Ta2V9l5PX/LMNAXqf4GfTkXmetk0cTRQnZ0W2Zka8UlWiFO0Kbtw+tEpI2ot1GD6z5cN0vm2lOW/J7dk5HuvVxT8Zfbj9GHvOiIkPl6WjEZ6dtjYw8b2pi/dhTaMZzxXWIkToKV7nhC9rpm5yXS1YvA9ul0/FIAkiURHZ5RJVwU1V4dF7PFbLLGgbnb+kTIblGF1ai7hwMVLocpZ2bfy7GdRS8OtSa4YI2MYcJRJzFetpQEawgNC357C1Vk0hP4NhFaqRjjkETSAF3DkOFO Received-SPF: pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Received-SPF: pass client-ip=57.103.65.245; envelope-from=mohamed@unpredictable.fr; helo=outbound.pv.icloud.com X-Spam_score_int: -20 X-Spam_score: -2.1 X-Spam_bar: -- X-Spam_report: (-2.1 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, RCVD_IN_VALIDITY_RPBL_BLOCKED=0.001, RCVD_IN_VALIDITY_SAFE_BLOCKED=0.001, SPF_HELO_PASS=-0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: qemu development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: qemu-devel-bounces+importer=patchew.org@nongnu.org X-ZohoMail-DKIM: pass (identity @unpredictable.fr) X-ZM-MESSAGEID: 1770954446986154100 Content-Type: text/plain; charset="utf-8" Using the mshv backend as a base, move away from winhvemulation to using common QEMU code used by the HVF and mshv backends. Signed-off-by: Mohamed Mediouni --- target/i386/whpx/whpx-all.c | 250 ++++++++++++++++-------------------- 1 file changed, 114 insertions(+), 136 deletions(-) diff --git a/target/i386/whpx/whpx-all.c b/target/i386/whpx/whpx-all.c index cdcaebbe16..eabb0ef913 100644 --- a/target/i386/whpx/whpx-all.c +++ b/target/i386/whpx/whpx-all.c @@ -15,6 +15,7 @@ #include "gdbstub/helpers.h" #include "qemu/accel.h" #include "accel/accel-ops.h" +#include "system/memory.h" #include "system/whpx.h" #include "system/cpus.h" #include "system/runstate.h" @@ -36,8 +37,12 @@ #include "system/whpx-all.h" #include "system/whpx-common.h" =20 +#include "emulate/x86_decode.h" +#include "emulate/x86_emu.h" +#include "emulate/x86_flags.h" +#include "emulate/x86_mmu.h" + #include -#include =20 #define HYPERV_APIC_BUS_FREQUENCY (200000000ULL) =20 @@ -756,158 +761,138 @@ void whpx_get_registers(CPUState *cpu) x86_update_hflags(env); } =20 -static HRESULT CALLBACK whpx_emu_ioport_callback( - void *ctx, - WHV_EMULATOR_IO_ACCESS_INFO *IoAccess) +static int emulate_instruction(CPUState *cpu, const uint8_t *insn_bytes, s= ize_t insn_len) { - MemTxAttrs attrs =3D { 0 }; - address_space_rw(&address_space_io, IoAccess->Port, attrs, - &IoAccess->Data, IoAccess->AccessSize, - IoAccess->Direction); - return S_OK; -} + X86CPU *x86_cpu =3D X86_CPU(cpu); + CPUX86State *env =3D &x86_cpu->env; + struct x86_decode decode =3D { 0 }; + x86_insn_stream stream =3D { .bytes =3D insn_bytes, .len =3D insn_len = }; =20 -static HRESULT CALLBACK whpx_emu_mmio_callback( - void *ctx, - WHV_EMULATOR_MEMORY_ACCESS_INFO *ma) -{ - CPUState *cs =3D (CPUState *)ctx; - AddressSpace *as =3D cpu_addressspace(cs, MEMTXATTRS_UNSPECIFIED); + whpx_get_registers(cpu); + decode_instruction_stream(env, &decode, &stream); + exec_instruction(env, &decode); + whpx_set_registers(cpu, WHPX_SET_RUNTIME_STATE); =20 - address_space_rw(as, ma->GpaAddress, MEMTXATTRS_UNSPECIFIED, - ma->Data, ma->AccessSize, ma->Direction); - return S_OK; + return 0; } =20 -static HRESULT CALLBACK whpx_emu_getreg_callback( - void *ctx, - const WHV_REGISTER_NAME *RegisterNames, - UINT32 RegisterCount, - WHV_REGISTER_VALUE *RegisterValues) +static int whpx_handle_mmio(CPUState *cpu, WHV_RUN_VP_EXIT_CONTEXT *exit_c= tx) { - HRESULT hr; - struct whpx_state *whpx =3D &whpx_global; - CPUState *cpu =3D (CPUState *)ctx; + WHV_MEMORY_ACCESS_CONTEXT *ctx =3D &exit_ctx->MemoryAccess; + int ret; =20 - hr =3D whp_dispatch.WHvGetVirtualProcessorRegisters( - whpx->partition, cpu->cpu_index, - RegisterNames, RegisterCount, - RegisterValues); - if (FAILED(hr)) { - error_report("WHPX: Failed to get virtual processor registers," - " hr=3D%08lx", hr); + ret =3D emulate_instruction(cpu, ctx->InstructionBytes, exit_ctx->VpCo= ntext.InstructionLength); + if (ret < 0) { + error_report("failed to emulate mmio"); + return -1; } =20 - return hr; + return 0; } =20 -static HRESULT CALLBACK whpx_emu_setreg_callback( - void *ctx, - const WHV_REGISTER_NAME *RegisterNames, - UINT32 RegisterCount, - const WHV_REGISTER_VALUE *RegisterValues) +static void handle_io(CPUState *env, uint16_t port, void *buffer, + int direction, int size, int count) { - HRESULT hr; - struct whpx_state *whpx =3D &whpx_global; - CPUState *cpu =3D (CPUState *)ctx; + int i; + uint8_t *ptr =3D buffer; =20 - hr =3D whp_dispatch.WHvSetVirtualProcessorRegisters( - whpx->partition, cpu->cpu_index, - RegisterNames, RegisterCount, - RegisterValues); - if (FAILED(hr)) { - error_report("WHPX: Failed to set virtual processor registers," - " hr=3D%08lx", hr); + for (i =3D 0; i < count; i++) { + address_space_rw(&address_space_io, port, MEMTXATTRS_UNSPECIFIED, + ptr, size, + direction); + ptr +=3D size; } - - /* - * The emulator just successfully wrote the register state. We clear t= he - * dirty state so we avoid the double write on resume of the VP. - */ - cpu->vcpu_dirty =3D false; - - return hr; } =20 -static HRESULT CALLBACK whpx_emu_translate_callback( - void *ctx, - WHV_GUEST_VIRTUAL_ADDRESS Gva, - WHV_TRANSLATE_GVA_FLAGS TranslateFlags, - WHV_TRANSLATE_GVA_RESULT_CODE *TranslationResult, - WHV_GUEST_PHYSICAL_ADDRESS *Gpa) +static void whpx_bump_rip(CPUState *cpu, WHV_RUN_VP_EXIT_CONTEXT *exit_ctx) { - HRESULT hr; - struct whpx_state *whpx =3D &whpx_global; - CPUState *cpu =3D (CPUState *)ctx; - WHV_TRANSLATE_GVA_RESULT res; - - hr =3D whp_dispatch.WHvTranslateGva(whpx->partition, cpu->cpu_index, - Gva, TranslateFlags, &res, Gpa); - if (FAILED(hr)) { - error_report("WHPX: Failed to translate GVA, hr=3D%08lx", hr); - } else { - *TranslationResult =3D res.ResultCode; - } - - return hr; + WHV_REGISTER_VALUE reg; + whpx_get_reg(cpu, WHvX64RegisterRip, ®); + reg.Reg64 =3D exit_ctx->VpContext.Rip + exit_ctx->VpContext.Instructio= nLength; + whpx_set_reg(cpu, WHvX64RegisterRip, reg); } =20 -static const WHV_EMULATOR_CALLBACKS whpx_emu_callbacks =3D { - .Size =3D sizeof(WHV_EMULATOR_CALLBACKS), - .WHvEmulatorIoPortCallback =3D whpx_emu_ioport_callback, - .WHvEmulatorMemoryCallback =3D whpx_emu_mmio_callback, - .WHvEmulatorGetVirtualProcessorRegisters =3D whpx_emu_getreg_callback, - .WHvEmulatorSetVirtualProcessorRegisters =3D whpx_emu_setreg_callback, - .WHvEmulatorTranslateGvaPage =3D whpx_emu_translate_callback, -}; - -static int whpx_handle_mmio(CPUState *cpu, WHV_MEMORY_ACCESS_CONTEXT *ctx) +static int whpx_handle_portio(CPUState *cpu, + WHV_RUN_VP_EXIT_CONTEXT *exit_ctx) { - HRESULT hr; - AccelCPUState *vcpu =3D cpu->accel; - WHV_EMULATOR_STATUS emu_status; - - hr =3D whp_dispatch.WHvEmulatorTryMmioEmulation( - vcpu->emulator, cpu, - &vcpu->exit_ctx.VpContext, ctx, - &emu_status); - if (FAILED(hr)) { - error_report("WHPX: Failed to parse MMIO access, hr=3D%08lx", hr); - return -1; - } + WHV_X64_IO_PORT_ACCESS_CONTEXT *ctx =3D &exit_ctx->IoPortAccess; + X86CPU *x86_cpu =3D X86_CPU(cpu); + CPUX86State *env =3D &x86_cpu->env; + int ret; =20 - if (!emu_status.EmulationSuccessful) { - error_report("WHPX: Failed to emulate MMIO access with" - " EmulatorReturnStatus: %u", emu_status.AsUINT32); + if (!ctx->AccessInfo.StringOp && !ctx->AccessInfo.IsWrite) { + uint64_t val =3D 0; + WHV_REGISTER_VALUE reg; + + whpx_get_reg(cpu, WHvX64RegisterRax, ®); + handle_io(cpu, ctx->PortNumber, &val, 0, ctx->AccessInfo.AccessSiz= e, 1); + if (ctx->AccessInfo.AccessSize =3D=3D 1) { + reg.Reg8 =3D val; + } else if (ctx->AccessInfo.AccessSize =3D=3D 2) { + reg.Reg16 =3D val; + } else if (ctx->AccessInfo.AccessSize =3D=3D 4) { + reg.Reg64 =3D (uint32_t)val; + } else { + reg.Reg64 =3D (uint64_t)val; + } + whpx_bump_rip(cpu, exit_ctx); + whpx_set_reg(cpu, WHvX64RegisterRax, reg); + return 0; + } else if (!ctx->AccessInfo.StringOp && ctx->AccessInfo.IsWrite) { + RAX(env) =3D ctx->Rax; + handle_io(cpu, ctx->PortNumber, &RAX(env), 1, ctx->AccessInfo.Acce= ssSize, 1); + whpx_bump_rip(cpu, exit_ctx); + return 0; + } + + ret =3D emulate_instruction(cpu, ctx->InstructionBytes, exit_ctx->VpCo= ntext.InstructionLength); + if (ret < 0) { + error_report("failed to emulate I/O port access"); return -1; } =20 return 0; } =20 -static int whpx_handle_portio(CPUState *cpu, - WHV_X64_IO_PORT_ACCESS_CONTEXT *ctx) +static void write_mem(CPUState *cpu, void *data, target_ulong addr, int by= tes) { - HRESULT hr; - AccelCPUState *vcpu =3D cpu->accel; - WHV_EMULATOR_STATUS emu_status; + vmx_write_mem(cpu, addr, data, bytes); +} =20 - hr =3D whp_dispatch.WHvEmulatorTryIoEmulation( - vcpu->emulator, cpu, - &vcpu->exit_ctx.VpContext, ctx, - &emu_status); - if (FAILED(hr)) { - error_report("WHPX: Failed to parse PortIO access, hr=3D%08lx", hr= ); - return -1; - } +static void read_mem(CPUState *cpu, void *data, target_ulong addr, int byt= es) +{ + vmx_read_mem(cpu, data, addr, bytes); +} =20 - if (!emu_status.EmulationSuccessful) { - error_report("WHPX: Failed to emulate PortIO access with" - " EmulatorReturnStatus: %u", emu_status.AsUINT32); - return -1; +static void read_segment_descriptor(CPUState *cpu, + struct x86_segment_descriptor *desc, + enum X86Seg seg_idx) +{ + bool ret; + X86CPU *x86_cpu =3D X86_CPU(cpu); + CPUX86State *env =3D &x86_cpu->env; + SegmentCache *seg =3D &env->segs[seg_idx]; + x86_segment_selector sel =3D { .sel =3D seg->selector & 0xFFFF }; + + ret =3D x86_read_segment_descriptor(cpu, desc, sel); + if (ret =3D=3D false) { + error_report("failed to read segment descriptor"); + abort(); } +} =20 - return 0; + +static const struct x86_emul_ops whpx_x86_emul_ops =3D { + .read_mem =3D read_mem, + .write_mem =3D write_mem, + .read_segment_descriptor =3D read_segment_descriptor, + .handle_io =3D handle_io +}; + +static void whpx_init_emu(void) +{ + init_decoder(); + init_emu(&whpx_x86_emul_ops); } =20 /* @@ -1279,8 +1264,9 @@ bool whpx_arch_supports_guest_debug(void) =20 void whpx_arch_destroy_vcpu(CPUState *cpu) { - AccelCPUState *vcpu =3D cpu->accel; - whp_dispatch.WHvEmulatorDestroyEmulator(vcpu->emulator); + X86CPU *x86cpu =3D X86_CPU(cpu); + CPUX86State *env =3D &x86cpu->env; + g_free(env->emu_mmio_buf); } =20 /* Returns the address of the next instruction that is about to be execute= d. */ @@ -1639,11 +1625,11 @@ int whpx_vcpu_run(CPUState *cpu) =20 switch (vcpu->exit_ctx.ExitReason) { case WHvRunVpExitReasonMemoryAccess: - ret =3D whpx_handle_mmio(cpu, &vcpu->exit_ctx.MemoryAccess); + ret =3D whpx_handle_mmio(cpu, &vcpu->exit_ctx); break; =20 case WHvRunVpExitReasonX64IoPortAccess: - ret =3D whpx_handle_portio(cpu, &vcpu->exit_ctx.IoPortAccess); + ret =3D whpx_handle_portio(cpu, &vcpu->exit_ctx); break; =20 case WHvRunVpExitReasonX64InterruptWindow: @@ -1990,22 +1976,11 @@ int whpx_init_vcpu(CPUState *cpu) =20 vcpu =3D g_new0(AccelCPUState, 1); =20 - hr =3D whp_dispatch.WHvEmulatorCreateEmulator( - &whpx_emu_callbacks, - &vcpu->emulator); - if (FAILED(hr)) { - error_report("WHPX: Failed to setup instruction completion support= ," - " hr=3D%08lx", hr); - ret =3D -EINVAL; - goto error; - } - hr =3D whp_dispatch.WHvCreateVirtualProcessor( whpx->partition, cpu->cpu_index, 0); if (FAILED(hr)) { error_report("WHPX: Failed to create a virtual processor," " hr=3D%08lx", hr); - whp_dispatch.WHvEmulatorDestroyEmulator(vcpu->emulator); ret =3D -EINVAL; goto error; } @@ -2067,6 +2042,8 @@ int whpx_init_vcpu(CPUState *cpu) max_vcpu_index =3D max(max_vcpu_index, cpu->cpu_index); qemu_add_vm_change_state_handler(whpx_cpu_update_state, env); =20 + env->emu_mmio_buf =3D g_new(char, 4096); + return 0; =20 error: @@ -2256,6 +2233,7 @@ int whpx_accel_init(AccelState *as, MachineState *ms) } =20 whpx_memory_init(); + whpx_init_emu(); =20 printf("Windows Hypervisor Platform accelerator is operational\n"); return 0; --=20 2.50.1 (Apple Git-155)