get:
Show a patch.

patch:
Update a patch.

put:
Update a patch.

GET /api/patches/2195166/?format=api
HTTP 200 OK
Allow: GET, PUT, PATCH, HEAD, OPTIONS
Content-Type: application/json
Vary: Accept

{
    "id": 2195166,
    "url": "http://patchwork.ozlabs.org/api/patches/2195166/?format=api",
    "web_url": "http://patchwork.ozlabs.org/project/qemu-devel/patch/20260210135206.229528-14-peter.maydell@linaro.org/",
    "project": {
        "id": 14,
        "url": "http://patchwork.ozlabs.org/api/projects/14/?format=api",
        "name": "QEMU Development",
        "link_name": "qemu-devel",
        "list_id": "qemu-devel.nongnu.org",
        "list_email": "qemu-devel@nongnu.org",
        "web_url": "",
        "scm_url": "",
        "webscm_url": "",
        "list_archive_url": "",
        "list_archive_url_format": "",
        "commit_url_format": ""
    },
    "msgid": "<20260210135206.229528-14-peter.maydell@linaro.org>",
    "list_archive_url": null,
    "date": "2026-02-10T13:51:53",
    "name": "[PULL,13/26] hw, target, accel: whpx: change apic_in_platform to kernel_irqchip",
    "commit_ref": null,
    "pull_url": null,
    "state": "not-applicable",
    "archived": false,
    "hash": "ce74fe946b5f6f886a5e3607baedaf0848e1939f",
    "submitter": {
        "id": 5111,
        "url": "http://patchwork.ozlabs.org/api/people/5111/?format=api",
        "name": "Peter Maydell",
        "email": "peter.maydell@linaro.org"
    },
    "delegate": null,
    "mbox": "http://patchwork.ozlabs.org/project/qemu-devel/patch/20260210135206.229528-14-peter.maydell@linaro.org/mbox/",
    "series": [
        {
            "id": 491680,
            "url": "http://patchwork.ozlabs.org/api/series/491680/?format=api",
            "web_url": "http://patchwork.ozlabs.org/project/qemu-devel/list/?series=491680",
            "date": "2026-02-10T13:51:40",
            "name": "[PULL,01/26] target/arm/kvm: add constants for new PSCI versions",
            "version": 1,
            "mbox": "http://patchwork.ozlabs.org/series/491680/mbox/"
        }
    ],
    "comments": "http://patchwork.ozlabs.org/api/patches/2195166/comments/",
    "check": "pending",
    "checks": "http://patchwork.ozlabs.org/api/patches/2195166/checks/",
    "tags": {},
    "related": [],
    "headers": {
        "Return-Path": "<qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org>",
        "X-Original-To": "incoming@patchwork.ozlabs.org",
        "Delivered-To": "patchwork-incoming@legolas.ozlabs.org",
        "Authentication-Results": [
            "legolas.ozlabs.org;\n\tdkim=pass (2048-bit key;\n unprotected) header.d=linaro.org header.i=@linaro.org header.a=rsa-sha256\n header.s=google header.b=m7nLKRFI;\n\tdkim-atps=neutral",
            "legolas.ozlabs.org;\n spf=pass (sender SPF authorized) smtp.mailfrom=nongnu.org\n (client-ip=209.51.188.17; helo=lists.gnu.org;\n envelope-from=qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org;\n receiver=patchwork.ozlabs.org)"
        ],
        "Received": [
            "from lists.gnu.org (lists.gnu.org [209.51.188.17])\n\t(using TLSv1.2 with cipher ECDHE-ECDSA-AES256-GCM-SHA384 (256/256 bits))\n\t(No client certificate requested)\n\tby legolas.ozlabs.org (Postfix) with ESMTPS id 4f9NNF67ZXz1xtV\n\tfor <incoming@patchwork.ozlabs.org>; Wed, 11 Feb 2026 00:54:37 +1100 (AEDT)",
            "from localhost ([::1] helo=lists1p.gnu.org)\n\tby lists.gnu.org with esmtp (Exim 4.90_1)\n\t(envelope-from <qemu-devel-bounces@nongnu.org>)\n\tid 1vpoAG-0002BG-UQ; Tue, 10 Feb 2026 08:52:28 -0500",
            "from eggs.gnu.org ([2001:470:142:3::10])\n by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256)\n (Exim 4.90_1) (envelope-from <peter.maydell@linaro.org>)\n id 1vpoAD-00026d-S9\n for qemu-devel@nongnu.org; Tue, 10 Feb 2026 08:52:25 -0500",
            "from mail-wm1-x32f.google.com ([2a00:1450:4864:20::32f])\n by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128)\n (Exim 4.90_1) (envelope-from <peter.maydell@linaro.org>)\n id 1vpoAB-0006LZ-5f\n for qemu-devel@nongnu.org; Tue, 10 Feb 2026 08:52:25 -0500",
            "by mail-wm1-x32f.google.com with SMTP id\n 5b1f17b1804b1-48336a6e932so16499115e9.3\n for <qemu-devel@nongnu.org>; Tue, 10 Feb 2026 05:52:19 -0800 (PST)",
            "from lanath.. (wildly.archaic.org.uk. [81.2.115.145])\n by smtp.gmail.com with ESMTPSA id\n 5b1f17b1804b1-4834d5d77f9sm64344875e9.3.2026.02.10.05.52.17\n for <qemu-devel@nongnu.org>\n (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256);\n Tue, 10 Feb 2026 05:52:18 -0800 (PST)"
        ],
        "DKIM-Signature": "v=1; a=rsa-sha256; c=relaxed/relaxed;\n d=linaro.org; s=google; t=1770731539; x=1771336339; darn=nongnu.org;\n h=content-transfer-encoding:mime-version:references:in-reply-to\n :message-id:date:subject:to:from:from:to:cc:subject:date:message-id\n :reply-to; bh=5xPq2fNqcw/oH0dNiPR3/K9/+sAUVQTjTaQpF6aGozQ=;\n b=m7nLKRFItcahzz3AkSBg6nlbmGeI+NHTWkJ0gpJbCydA8pZOl/CEMfqAG6k9WJgySO\n fYxQcQpCpqcrMvfY0uPkfx5o8YrXZQMI8xJ/eZuGaaXFh92xnP94nD44KY1Y92DWu6NW\n XnjMp2i0nzRWQW+CgnMATGLJ0Wp8jGtIu9HcY1gYiwqVdZyb3b9GM8BD2Lxv5FqS3wdg\n bywwH06A09ybx72EUfQIuue4hYkzdDC/9R1tuOYHY0SNyoEHF9TvQtQCfydwFaNMSYwt\n 8zOT4ds6Nm+VWlxd+IVcz0/6Ff+3pee1BcJW0jTnh1Oiq6bDgtoDCT3A3vtLhUwPTkpn\n 348Q==",
        "X-Google-DKIM-Signature": "v=1; a=rsa-sha256; c=relaxed/relaxed;\n d=1e100.net; s=20230601; t=1770731539; x=1771336339;\n h=content-transfer-encoding:mime-version:references:in-reply-to\n :message-id:date:subject:to:from:x-gm-gg:x-gm-message-state:from:to\n :cc:subject:date:message-id:reply-to;\n bh=5xPq2fNqcw/oH0dNiPR3/K9/+sAUVQTjTaQpF6aGozQ=;\n b=TNYp5z4HIiMccbjiCV2luSSbwQY4AqtAwXl9+oc8bktZcGSWpu8QMxTnHnySx4tD1A\n i3AJSX0lBzfk+6Ks2MMhmJNSXp/SfSwE2uNqT5I8U6I512LO0giK6akJM9i4wgjAnNp2\n B0PVFdii0yHdyWsmcpNVx9NG6NFYRr4OukCmQktg1tdNtK58tvbhdmuvXEYk0sBQcGQA\n h/WjAidMS6giikO4d1S2klLcW7tXE53LQCt9IZ2fYnioahKzT7m2ExplAYmmq99TtXKT\n L0Q5pdZfNidr2rrSxxsj+n+L2Bkkj05JG7L1tQkJh0FBGDevcEqfNZQw3VDiWbFIRmQu\n l7UA==",
        "X-Gm-Message-State": "AOJu0YxmmTKdSUipPRB9bu+NMi0Q2Uw7o2T05DJWTfN4ninptEQLKJAg\n pybMhl0bA7oRcSI4hQ1ZgBhrKFFoU4m5DliT0gypgFB82FP25u/VRLGKgYfnp7PL5+DRujzuwd6\n toNJd",
        "X-Gm-Gg": "AZuq6aKxAX/zdU5qC0VhR4jYG35fAWK0ph+oAFko9DF+Wt1LPfjWXoUDFzPjJcKmczx\n eRW/jQQq5mGn6zjoRVuqWltj04kNCZIGBdISNYOUWKhZnTp/De2sWWmDHE+njusPvBsVd6vyrZV\n Eofh8u1ncGKTfXhn0iD4xXOcsCipKb8X90778suUDwzKb75/bhNM5/TfKzLNFPEkel0F5/Gnegn\n bk3zytWXwFfpFqWcVtR3EgZ/+tEMgxPLdCOsM/Gyp7kOVVjQyKNqnXrpqGa/Dpbt0hSW0xvcm3K\n gR4FsX4maVDwAEcoVmbTvJReWb7lixJuQPJwEb9Bqw8XcATv+coq1CkqwLBvCziWx2L2ww0J9ze\n 8E23nDyALpy+RUTuwIq9/U2jcNWVzjEahAUD2bdlfOXcX4WpdL4X8oiMIsHxJSlPSbmUpeS6ZPN\n hxJ8imwQkKtXaKWLfvYfyJDej49sh7MgIRT/XlFoUWToghfm0cNp1Q18Muep2aoWnvMcVliwoyS\n q4+oUrvHC5UVfwKGbqiTSXjoLdGGE89QXhc3eNNjQ==",
        "X-Received": "by 2002:a05:600c:34c5:b0:480:1b65:b744 with SMTP id\n 5b1f17b1804b1-4832021e972mr211015325e9.28.1770731538591;\n Tue, 10 Feb 2026 05:52:18 -0800 (PST)",
        "From": "Peter Maydell <peter.maydell@linaro.org>",
        "To": "qemu-devel@nongnu.org",
        "Subject": "[PULL 13/26] hw, target,\n accel: whpx: change apic_in_platform to kernel_irqchip",
        "Date": "Tue, 10 Feb 2026 13:51:53 +0000",
        "Message-ID": "<20260210135206.229528-14-peter.maydell@linaro.org>",
        "X-Mailer": "git-send-email 2.43.0",
        "In-Reply-To": "<20260210135206.229528-1-peter.maydell@linaro.org>",
        "References": "<20260210135206.229528-1-peter.maydell@linaro.org>",
        "MIME-Version": "1.0",
        "Content-Transfer-Encoding": "8bit",
        "Received-SPF": "pass client-ip=2a00:1450:4864:20::32f;\n envelope-from=peter.maydell@linaro.org; helo=mail-wm1-x32f.google.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,\n DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1,\n RCVD_IN_DNSWL_NONE=-0.0001, SPF_HELO_NONE=0.001,\n 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 <qemu-devel.nongnu.org>",
        "List-Unsubscribe": "<https://lists.nongnu.org/mailman/options/qemu-devel>,\n <mailto:qemu-devel-request@nongnu.org?subject=unsubscribe>",
        "List-Archive": "<https://lists.nongnu.org/archive/html/qemu-devel>",
        "List-Post": "<mailto:qemu-devel@nongnu.org>",
        "List-Help": "<mailto:qemu-devel-request@nongnu.org?subject=help>",
        "List-Subscribe": "<https://lists.nongnu.org/mailman/listinfo/qemu-devel>,\n <mailto:qemu-devel-request@nongnu.org?subject=subscribe>",
        "Errors-To": "qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org",
        "Sender": "qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org"
    },
    "content": "From: Mohamed Mediouni <mohamed@unpredictable.fr>\n\nChange terminology to match the KVM one, as APIC is x86-specific.\n\nAnd move out whpx_irqchip_in_kernel() to make it usable from common\ncode even when not compiling with WHPX support.\n\nSigned-off-by: Mohamed Mediouni <mohamed@unpredictable.fr>\nReviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org>\nReviewed-by: Akihiko Odaki <odaki@rsg.ci.i.u-tokyo.ac.jp>\nSigned-off-by: Peter Maydell <peter.maydell@linaro.org>\n---\n MAINTAINERS                        |   1 +\n accel/stubs/whpx-stub.c            |   1 +\n accel/whpx/whpx-accel-ops.c        |   2 +-\n accel/whpx/whpx-common.c           |  10 +-\n hw/arm/virt.c                      |   9 ++\n hw/i386/x86-cpu.c                  |   4 +-\n hw/intc/arm_gicv3_common.c         |   3 +\n hw/intc/arm_gicv3_whpx.c           | 237 +++++++++++++++++++++++++++++\n hw/intc/meson.build                |   1 +\n include/hw/intc/arm_gicv3_common.h |   3 +\n include/system/whpx-internal.h     |   1 -\n include/system/whpx.h              |   5 +-\n target/i386/cpu-apic.c             |   2 +-\n target/i386/whpx/whpx-all.c        |  14 +-\n 14 files changed, 270 insertions(+), 23 deletions(-)\n create mode 100644 hw/intc/arm_gicv3_whpx.c",
    "diff": "diff --git a/MAINTAINERS b/MAINTAINERS\nindex 54326b1a5a..c6af6e10bb 100644\n--- a/MAINTAINERS\n+++ b/MAINTAINERS\n@@ -566,6 +566,7 @@ M: Mohamed Mediouni <mohamed@unpredictable.fr>\n S: Supported\n F: accel/whpx/\n F: target/i386/whpx/\n+F: hw/intc/arm_gicv3_whpx.c\n F: accel/stubs/whpx-stub.c\n F: include/system/whpx.h\n F: include/system/whpx-accel-ops.h\ndiff --git a/accel/stubs/whpx-stub.c b/accel/stubs/whpx-stub.c\nindex c564c89fd0..4529dc4f78 100644\n--- a/accel/stubs/whpx-stub.c\n+++ b/accel/stubs/whpx-stub.c\n@@ -10,3 +10,4 @@\n #include \"system/whpx.h\"\n \n bool whpx_allowed;\n+bool whpx_irqchip_in_kernel;\ndiff --git a/accel/whpx/whpx-accel-ops.c b/accel/whpx/whpx-accel-ops.c\nindex c84a25c273..50fadea0fd 100644\n--- a/accel/whpx/whpx-accel-ops.c\n+++ b/accel/whpx/whpx-accel-ops.c\n@@ -78,7 +78,7 @@ static void whpx_kick_vcpu_thread(CPUState *cpu)\n \n static bool whpx_vcpu_thread_is_idle(CPUState *cpu)\n {\n-    return !whpx_apic_in_platform();\n+    return !whpx_irqchip_in_kernel();\n }\n \n static void whpx_accel_ops_class_init(ObjectClass *oc, const void *data)\ndiff --git a/accel/whpx/whpx-common.c b/accel/whpx/whpx-common.c\nindex c0610815d9..05f9e520b7 100644\n--- a/accel/whpx/whpx-common.c\n+++ b/accel/whpx/whpx-common.c\n@@ -35,6 +35,7 @@\n #include <winhvplatformdefs.h>\n \n bool whpx_allowed;\n+bool whpx_irqchip_in_kernel;\n static bool whp_dispatch_initialized;\n static HMODULE hWinHvPlatform;\n #ifdef HOST_X86_64\n@@ -488,15 +489,6 @@ static const TypeInfo whpx_cpu_accel_type = {\n     .abstract = true,\n };\n \n-/*\n- * Partition support\n- */\n-\n-bool whpx_apic_in_platform(void)\n-{\n-    return whpx_global.apic_in_platform;\n-}\n-\n static void whpx_accel_class_init(ObjectClass *oc, const void *data)\n {\n     AccelClass *ac = ACCEL_CLASS(oc);\ndiff --git a/hw/arm/virt.c b/hw/arm/virt.c\nindex aa5e992712..b7eb0cec5e 100644\n--- a/hw/arm/virt.c\n+++ b/hw/arm/virt.c\n@@ -49,6 +49,7 @@\n #include \"system/tcg.h\"\n #include \"system/kvm.h\"\n #include \"system/hvf.h\"\n+#include \"system/whpx.h\"\n #include \"system/qtest.h\"\n #include \"system/system.h\"\n #include \"hw/core/loader.h\"\n@@ -2114,6 +2115,8 @@ static void finalize_gic_version(VirtMachineState *vms)\n         /* KVM w/o kernel irqchip can only deal with GICv2 */\n         gics_supported |= VIRT_GIC_VERSION_2_MASK;\n         accel_name = \"KVM with kernel-irqchip=off\";\n+    } else if (whpx_enabled()) {\n+        gics_supported |= VIRT_GIC_VERSION_3_MASK;\n     } else if (tcg_enabled() || hvf_enabled() || qtest_enabled())  {\n         gics_supported |= VIRT_GIC_VERSION_2_MASK;\n         if (module_object_class_by_name(\"arm-gicv3\")) {\n@@ -2154,6 +2157,8 @@ static void finalize_msi_controller(VirtMachineState *vms)\n     if (vms->msi_controller == VIRT_MSI_CTRL_AUTO) {\n         if (vms->gic_version == VIRT_GIC_VERSION_2) {\n             vms->msi_controller = VIRT_MSI_CTRL_GICV2M;\n+        } else if (whpx_enabled()) {\n+            vms->msi_controller = VIRT_MSI_CTRL_GICV2M;\n         } else {\n             vms->msi_controller = VIRT_MSI_CTRL_ITS;\n         }\n@@ -2169,6 +2174,10 @@ static void finalize_msi_controller(VirtMachineState *vms)\n             error_report(\"GICv2 + ITS is an invalid configuration.\");\n             exit(1);\n         }\n+        if (whpx_enabled()) {\n+            error_report(\"ITS not supported on WHPX.\");\n+            exit(1);\n+        }\n     }\n \n     assert(vms->msi_controller != VIRT_MSI_CTRL_AUTO);\ndiff --git a/hw/i386/x86-cpu.c b/hw/i386/x86-cpu.c\nindex 276f2b0cdf..95e08e3c2a 100644\n--- a/hw/i386/x86-cpu.c\n+++ b/hw/i386/x86-cpu.c\n@@ -45,7 +45,7 @@ static void pic_irq_request(void *opaque, int irq, int level)\n \n     trace_x86_pic_interrupt(irq, level);\n     if (cpu_is_apic_enabled(cpu->apic_state) && !kvm_irqchip_in_kernel() &&\n-        !whpx_apic_in_platform()) {\n+        !whpx_irqchip_in_kernel()) {\n         CPU_FOREACH(cs) {\n             cpu = X86_CPU(cs);\n             if (apic_accept_pic_intr(cpu->apic_state)) {\n@@ -71,7 +71,7 @@ int cpu_get_pic_interrupt(CPUX86State *env)\n     X86CPU *cpu = env_archcpu(env);\n     int intno;\n \n-    if (!kvm_irqchip_in_kernel() && !whpx_apic_in_platform()) {\n+    if (!kvm_irqchip_in_kernel() && !whpx_irqchip_in_kernel()) {\n         intno = apic_get_interrupt(cpu->apic_state);\n         if (intno >= 0) {\n             return intno;\ndiff --git a/hw/intc/arm_gicv3_common.c b/hw/intc/arm_gicv3_common.c\nindex 0a2e5a3e2f..9054143ea7 100644\n--- a/hw/intc/arm_gicv3_common.c\n+++ b/hw/intc/arm_gicv3_common.c\n@@ -32,6 +32,7 @@\n #include \"gicv3_internal.h\"\n #include \"hw/arm/linux-boot-if.h\"\n #include \"system/kvm.h\"\n+#include \"system/whpx.h\"\n \n \n static void gicv3_gicd_no_migration_shift_bug_post_load(GICv3State *cs)\n@@ -663,6 +664,8 @@ const char *gicv3_class_name(void)\n {\n     if (kvm_irqchip_in_kernel()) {\n         return \"kvm-arm-gicv3\";\n+    } else if (whpx_enabled()) {\n+        return TYPE_WHPX_GICV3;\n     } else {\n         if (kvm_enabled()) {\n             error_report(\"Userspace GICv3 is not supported with KVM\");\ndiff --git a/hw/intc/arm_gicv3_whpx.c b/hw/intc/arm_gicv3_whpx.c\nnew file mode 100644\nindex 0000000000..849a005242\n--- /dev/null\n+++ b/hw/intc/arm_gicv3_whpx.c\n@@ -0,0 +1,237 @@\n+/* SPDX-License-Identifier: GPL-2.0-or-later */\n+/*\n+ * ARM Generic Interrupt Controller using HVF platform support\n+ *\n+ * Copyright (c) 2025 Mohamed Mediouni\n+ * Based on vGICv3 KVM code by Pavel Fedin\n+ *\n+ */\n+\n+#include \"qemu/osdep.h\"\n+#include \"qapi/error.h\"\n+#include \"hw/intc/arm_gicv3_common.h\"\n+#include \"qemu/error-report.h\"\n+#include \"qemu/module.h\"\n+#include \"system/runstate.h\"\n+#include \"system/whpx.h\"\n+#include \"system/whpx-internal.h\"\n+#include \"gicv3_internal.h\"\n+#include \"vgic_common.h\"\n+#include \"migration/blocker.h\"\n+#include \"qom/object.h\"\n+#include \"target/arm/cpregs.h\"\n+\n+#include \"hw/arm/bsa.h\"\n+#include <winhvplatform.h>\n+#include <winhvplatformdefs.h>\n+#include <winnt.h>\n+\n+struct WHPXARMGICv3Class {\n+    ARMGICv3CommonClass parent_class;\n+    DeviceRealize parent_realize;\n+    ResettablePhases parent_phases;\n+};\n+\n+OBJECT_DECLARE_TYPE(GICv3State, WHPXARMGICv3Class, WHPX_GICV3)\n+\n+/* TODO: Implement GIC state save-restore */\n+static void whpx_gicv3_check(GICv3State *s)\n+{\n+}\n+\n+static void whpx_gicv3_put(GICv3State *s)\n+{\n+    whpx_gicv3_check(s);\n+}\n+\n+static void whpx_gicv3_get(GICv3State *s)\n+{\n+}\n+\n+static void whpx_gicv3_set_irq(void *opaque, int irq, int level)\n+{\n+    struct whpx_state *whpx = &whpx_global;\n+    GICv3State *s = opaque;\n+    WHV_INTERRUPT_CONTROL interrupt_control = {\n+        .InterruptControl.InterruptType = WHvArm64InterruptTypeFixed,\n+        .RequestedVector = GIC_INTERNAL + irq,\n+        .InterruptControl.Asserted = level\n+    };\n+\n+    if (irq > s->num_irq) {\n+        return;\n+    }\n+\n+\n+    whp_dispatch.WHvRequestInterrupt(whpx->partition, &interrupt_control,\n+         sizeof(interrupt_control));\n+}\n+\n+static void whpx_gicv3_icc_reset(CPUARMState *env, const ARMCPRegInfo *ri)\n+{\n+    GICv3CPUState *c;\n+\n+    c = env->gicv3state;\n+\n+    c->icc_pmr_el1 = 0;\n+    /*\n+     * Architecturally the reset value of the ICC_BPR registers\n+     * is UNKNOWN. We set them all to 0 here; when the kernel\n+     * uses these values to program the ICH_VMCR_EL2 fields that\n+     * determine the guest-visible ICC_BPR register values, the\n+     * hardware's \"writing a value less than the minimum sets\n+     * the field to the minimum value\" behaviour will result in\n+     * them effectively resetting to the correct minimum value\n+     * for the host GIC.\n+     */\n+    c->icc_bpr[GICV3_G0] = 0;\n+    c->icc_bpr[GICV3_G1] = 0;\n+    c->icc_bpr[GICV3_G1NS] = 0;\n+\n+    c->icc_sre_el1 = 0x7;\n+    memset(c->icc_apr, 0, sizeof(c->icc_apr));\n+    memset(c->icc_igrpen, 0, sizeof(c->icc_igrpen));\n+}\n+\n+static void whpx_gicv3_reset_hold(Object *obj, ResetType type)\n+{\n+    GICv3State *s = ARM_GICV3_COMMON(obj);\n+    WHPXARMGICv3Class *kgc = WHPX_GICV3_GET_CLASS(s);\n+\n+    if (kgc->parent_phases.hold) {\n+        kgc->parent_phases.hold(obj, type);\n+    }\n+\n+    whpx_gicv3_put(s);\n+}\n+\n+\n+/*\n+ * CPU interface registers of GIC needs to be reset on CPU reset.\n+ * For the calling arm_gicv3_icc_reset() on CPU reset, we register\n+ * below ARMCPRegInfo. As we reset the whole cpu interface under single\n+ * register reset, we define only one register of CPU interface instead\n+ * of defining all the registers.\n+ */\n+static const ARMCPRegInfo gicv3_cpuif_reginfo[] = {\n+    { .name = \"ICC_CTLR_EL1\", .state = ARM_CP_STATE_BOTH,\n+      .opc0 = 3, .opc1 = 0, .crn = 12, .crm = 12, .opc2 = 4,\n+      /*\n+       * If ARM_CP_NOP is used, resetfn is not called,\n+       * So ARM_CP_NO_RAW is appropriate type.\n+       */\n+      .type = ARM_CP_NO_RAW,\n+      .access = PL1_RW,\n+      .readfn = arm_cp_read_zero,\n+      .writefn = arm_cp_write_ignore,\n+      /*\n+       * We hang the whole cpu interface reset routine off here\n+       * rather than parcelling it out into one little function\n+       * per register\n+       */\n+      .resetfn = whpx_gicv3_icc_reset,\n+    },\n+};\n+\n+static void whpx_set_reg(CPUState *cpu, WHV_REGISTER_NAME reg, WHV_REGISTER_VALUE val)\n+{\n+    struct whpx_state *whpx = &whpx_global;\n+    HRESULT hr;\n+\n+    hr = whp_dispatch.WHvSetVirtualProcessorRegisters(whpx->partition, cpu->cpu_index,\n+         &reg, 1, &val);\n+\n+    if (FAILED(hr)) {\n+        error_report(\"WHPX: Failed to set register %08x, hr=%08lx\", reg, hr);\n+    }\n+}\n+\n+static void whpx_gicv3_realize(DeviceState *dev, Error **errp)\n+{\n+    ERRP_GUARD();\n+    GICv3State *s = WHPX_GICV3(dev);\n+    WHPXARMGICv3Class *kgc = WHPX_GICV3_GET_CLASS(s);\n+    int i;\n+\n+    kgc->parent_realize(dev, errp);\n+    if (*errp) {\n+        return;\n+    }\n+\n+    if (s->revision != 3) {\n+        error_setg(errp, \"unsupported GIC revision %d for platform GIC\",\n+                   s->revision);\n+        return;\n+    }\n+\n+    if (s->security_extn) {\n+        error_setg(errp, \"the platform vGICv3 does not implement the \"\n+                   \"security extensions\");\n+        return;\n+    }\n+\n+    if (s->nmi_support) {\n+        error_setg(errp, \"NMI is not supported with the platform GIC\");\n+        return;\n+    }\n+\n+    if (s->nb_redist_regions > 1) {\n+        error_setg(errp, \"Multiple VGICv3 redistributor regions are not \"\n+                   \"supported by WHPX\");\n+        error_append_hint(errp, \"A maximum of %d VCPUs can be used\",\n+                          s->redist_region_count[0]);\n+        return;\n+    }\n+\n+    gicv3_init_irqs_and_mmio(s, whpx_gicv3_set_irq, NULL);\n+\n+    for (i = 0; i < s->num_cpu; i++) {\n+        CPUState *cpu_state = qemu_get_cpu(i);\n+        ARMCPU *cpu = ARM_CPU(cpu_state);\n+        WHV_REGISTER_VALUE val = {.Reg64 = 0x080A0000 + (GICV3_REDIST_SIZE * i)};\n+        whpx_set_reg(cpu_state, WHvArm64RegisterGicrBaseGpa, val);\n+        define_arm_cp_regs(cpu, gicv3_cpuif_reginfo);\n+    }\n+\n+    if (s->maint_irq) {\n+        error_setg(errp, \"Nested virtualisation not currently supported by WHPX.\");\n+        return;\n+    }\n+\n+    error_setg(&s->migration_blocker,\n+        \"Live migration disabled because GIC state save/restore not supported on WHPX\");\n+    if (migrate_add_blocker(&s->migration_blocker, errp) < 0) {\n+        error_report_err(*errp);\n+    }\n+}\n+\n+static void whpx_gicv3_class_init(ObjectClass *klass, const void *data)\n+{\n+    DeviceClass *dc = DEVICE_CLASS(klass);\n+    ResettableClass *rc = RESETTABLE_CLASS(klass);\n+    ARMGICv3CommonClass *agcc = ARM_GICV3_COMMON_CLASS(klass);\n+    WHPXARMGICv3Class *kgc = WHPX_GICV3_CLASS(klass);\n+\n+    agcc->pre_save = whpx_gicv3_get;\n+    agcc->post_load = whpx_gicv3_put;\n+\n+    device_class_set_parent_realize(dc, whpx_gicv3_realize,\n+                                    &kgc->parent_realize);\n+    resettable_class_set_parent_phases(rc, NULL, whpx_gicv3_reset_hold, NULL,\n+                                       &kgc->parent_phases);\n+}\n+\n+static const TypeInfo whpx_arm_gicv3_info = {\n+    .name = TYPE_WHPX_GICV3,\n+    .parent = TYPE_ARM_GICV3_COMMON,\n+    .instance_size = sizeof(GICv3State),\n+    .class_init = whpx_gicv3_class_init,\n+    .class_size = sizeof(WHPXARMGICv3Class),\n+};\n+\n+static void whpx_gicv3_register_types(void)\n+{\n+    type_register_static(&whpx_arm_gicv3_info);\n+}\n+\n+type_init(whpx_gicv3_register_types)\ndiff --git a/hw/intc/meson.build b/hw/intc/meson.build\nindex faae20b93d..96742df090 100644\n--- a/hw/intc/meson.build\n+++ b/hw/intc/meson.build\n@@ -41,6 +41,7 @@ specific_ss.add(when: 'CONFIG_APIC', if_true: files('apic.c', 'apic_common.c'))\n arm_common_ss.add(when: 'CONFIG_ARM_GIC', if_true: files('arm_gicv3_cpuif_common.c'))\n arm_common_ss.add(when: 'CONFIG_ARM_GICV3', if_true: files('arm_gicv3_cpuif.c'))\n specific_ss.add(when: 'CONFIG_ARM_GIC_KVM', if_true: files('arm_gic_kvm.c'))\n+specific_ss.add(when: ['CONFIG_WHPX', 'TARGET_AARCH64'], if_true: files('arm_gicv3_whpx.c'))\n specific_ss.add(when: ['CONFIG_ARM_GIC_KVM', 'TARGET_AARCH64'], if_true: files('arm_gicv3_kvm.c', 'arm_gicv3_its_kvm.c'))\n arm_common_ss.add(when: 'CONFIG_ARM_V7M', if_true: files('armv7m_nvic.c'))\n specific_ss.add(when: 'CONFIG_GRLIB', if_true: files('grlib_irqmp.c'))\ndiff --git a/include/hw/intc/arm_gicv3_common.h b/include/hw/intc/arm_gicv3_common.h\nindex 3d24ad22d2..c55cf18120 100644\n--- a/include/hw/intc/arm_gicv3_common.h\n+++ b/include/hw/intc/arm_gicv3_common.h\n@@ -313,6 +313,9 @@ typedef struct ARMGICv3CommonClass ARMGICv3CommonClass;\n DECLARE_OBJ_CHECKERS(GICv3State, ARMGICv3CommonClass,\n                      ARM_GICV3_COMMON, TYPE_ARM_GICV3_COMMON)\n \n+/* Types for GICv3 kernel-irqchip */\n+#define TYPE_WHPX_GICV3 \"whpx-arm-gicv3\"\n+\n struct ARMGICv3CommonClass {\n     /*< private >*/\n     SysBusDeviceClass parent_class;\ndiff --git a/include/system/whpx-internal.h b/include/system/whpx-internal.h\nindex 609d0e1c08..8ded54a39b 100644\n--- a/include/system/whpx-internal.h\n+++ b/include/system/whpx-internal.h\n@@ -45,7 +45,6 @@ struct whpx_state {\n \n     bool kernel_irqchip_allowed;\n     bool kernel_irqchip_required;\n-    bool apic_in_platform;\n };\n \n extern struct whpx_state whpx_global;\ndiff --git a/include/system/whpx.h b/include/system/whpx.h\nindex 00f6a3e523..4217a27e91 100644\n--- a/include/system/whpx.h\n+++ b/include/system/whpx.h\n@@ -25,11 +25,12 @@\n \n #ifdef CONFIG_WHPX_IS_POSSIBLE\n extern bool whpx_allowed;\n+extern bool whpx_irqchip_in_kernel;\n #define whpx_enabled() (whpx_allowed)\n-bool whpx_apic_in_platform(void);\n+#define whpx_irqchip_in_kernel() (whpx_irqchip_in_kernel)\n #else /* !CONFIG_WHPX_IS_POSSIBLE */\n #define whpx_enabled() 0\n-#define whpx_apic_in_platform() (0)\n+#define whpx_irqchip_in_kernel() (0)\n #endif /* !CONFIG_WHPX_IS_POSSIBLE */\n \n #endif /* QEMU_WHPX_H */\ndiff --git a/target/i386/cpu-apic.c b/target/i386/cpu-apic.c\nindex f7ad7b5139..eaa10ad2a3 100644\n--- a/target/i386/cpu-apic.c\n+++ b/target/i386/cpu-apic.c\n@@ -33,7 +33,7 @@ APICCommonClass *apic_get_class(Error **errp)\n         apic_type = \"kvm-apic\";\n     } else if (xen_enabled()) {\n         apic_type = \"xen-apic\";\n-    } else if (whpx_apic_in_platform()) {\n+    } else if (whpx_irqchip_in_kernel()) {\n         apic_type = \"whpx-apic\";\n     }\n \ndiff --git a/target/i386/whpx/whpx-all.c b/target/i386/whpx/whpx-all.c\nindex 052cda42bf..8210250dc3 100644\n--- a/target/i386/whpx/whpx-all.c\n+++ b/target/i386/whpx/whpx-all.c\n@@ -607,7 +607,7 @@ void whpx_get_registers(CPUState *cpu)\n                      hr);\n     }\n \n-    if (whpx_apic_in_platform()) {\n+    if (whpx_irqchip_in_kernel()) {\n         /*\n          * Fetch the TPR value from the emulated APIC. It may get overwritten\n          * below with the value from CR8 returned by\n@@ -749,7 +749,7 @@ void whpx_get_registers(CPUState *cpu)\n \n     assert(idx == RTL_NUMBER_OF(whpx_register_names));\n \n-    if (whpx_apic_in_platform()) {\n+    if (whpx_irqchip_in_kernel()) {\n         whpx_apic_get(x86_cpu->apic_state);\n     }\n \n@@ -1379,7 +1379,7 @@ static void whpx_vcpu_pre_run(CPUState *cpu)\n     }\n \n     /* Get pending hard interruption or replay one that was overwritten */\n-    if (!whpx_apic_in_platform()) {\n+    if (!whpx_irqchip_in_kernel()) {\n         if (!vcpu->interruption_pending &&\n             vcpu->interruptable && (env->eflags & IF_MASK)) {\n             assert(!new_int.InterruptionPending);\n@@ -1553,7 +1553,7 @@ int whpx_vcpu_run(CPUState *cpu)\n \n     if (exclusive_step_mode == WHPX_STEP_NONE) {\n         whpx_vcpu_process_async_events(cpu);\n-        if (cpu->halted && !whpx_apic_in_platform()) {\n+        if (cpu->halted && !whpx_irqchip_in_kernel()) {\n             cpu->exception_index = EXCP_HLT;\n             qatomic_set(&cpu->exit_request, false);\n             return 0;\n@@ -1642,7 +1642,7 @@ int whpx_vcpu_run(CPUState *cpu)\n             break;\n \n         case WHvRunVpExitReasonX64ApicEoi:\n-            assert(whpx_apic_in_platform());\n+            assert(whpx_irqchip_in_kernel());\n             ioapic_eoi_broadcast(vcpu->exit_ctx.ApicEoi.InterruptVector);\n             break;\n \n@@ -2187,7 +2187,7 @@ int whpx_accel_init(AccelState *as, MachineState *ms)\n                 goto error;\n             }\n         } else {\n-            whpx->apic_in_platform = true;\n+            whpx_irqchip_in_kernel = true;\n         }\n     }\n \n@@ -2196,7 +2196,7 @@ int whpx_accel_init(AccelState *as, MachineState *ms)\n     prop.ExtendedVmExits.X64MsrExit = 1;\n     prop.ExtendedVmExits.X64CpuidExit = 1;\n     prop.ExtendedVmExits.ExceptionExit = 1;\n-    if (whpx_apic_in_platform()) {\n+    if (whpx_irqchip_in_kernel()) {\n         prop.ExtendedVmExits.X64ApicInitSipiExitTrap = 1;\n     }\n \n",
    "prefixes": [
        "PULL",
        "13/26"
    ]
}