KVM exit to userspace on WFI

From: Jan Henrik Weinstock
Date: Fri Oct 20 2023 - 14:45:23 EST


Hi all,

I am looking for a way to have KVM_RUN exit back to userspace once the
vcpu encounters a WFI. It seems the kvm_run->request_interrupt_window
flag is currently ignored by arm64. So my solution thus far is to
patch kvm_handle_wfx in arch/arm64/kvm/handle_exit.c and return to
userspace with KVM_EXIT_IRQ_WINDOW_OPEN - working example attached.
Any chance to get this (or something similar) mainline?

--
Dr.-Ing. Jan Henrik Weinstock
Managing Director

MachineWare GmbH | www.machineware.de
Hühnermarkt 19, 52062 Aachen, Germany
Amtsgericht Aachen HRB25734

Geschäftsführung
Lukas Jünger
Dr.-Ing. Jan Henrik Weinstock
diff --git a/arch/arm64/kvm/arm.c b/arch/arm64/kvm/arm.c
index 54d26f13f..7be42e3f1 100644
--- a/arch/arm64/kvm/arm.c
+++ b/arch/arm64/kvm/arm.c
@@ -215,6 +215,7 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext)
case KVM_CAP_SET_GUEST_DEBUG:
case KVM_CAP_VCPU_ATTRIBUTES:
case KVM_CAP_PTP_KVM:
+ case KVM_CAP_ARM_WFX_EXIT:
r = 1;
break;
case KVM_CAP_SET_GUEST_DEBUG2:
diff --git a/arch/arm64/kvm/handle_exit.c b/arch/arm64/kvm/handle_exit.c
index a5ab52150..d0386faeb 100644
--- a/arch/arm64/kvm/handle_exit.c
+++ b/arch/arm64/kvm/handle_exit.c
@@ -88,6 +88,11 @@ static int handle_no_fpsimd(struct kvm_vcpu *vcpu)
*/
static int kvm_handle_wfx(struct kvm_vcpu *vcpu)
{
+ if (vcpu->run->request_interrupt_window) {
+ vcpu->run->exit_reason = KVM_EXIT_IRQ_WINDOW_OPEN;
+ return 0;
+ }
+
if (kvm_vcpu_get_esr(vcpu) & ESR_ELx_WFx_ISS_WFE) {
trace_kvm_wfx_arm64(*vcpu_pc(vcpu), true);
vcpu->stat.wfe_exit_stat++;
diff --git a/include/uapi/linux/kvm.h b/include/uapi/linux/kvm.h
index 83a2185d9..1073269f2 100644
--- a/include/uapi/linux/kvm.h
+++ b/include/uapi/linux/kvm.h
@@ -1124,6 +1124,7 @@ struct kvm_ppc_resize_hpt {
#define KVM_CAP_SYS_ATTRIBUTES 209
#define KVM_CAP_S390_MEM_OP_EXTENSION 211
#define KVM_CAP_S390_ZPCI_OP 221
+#define KVM_CAP_ARM_WFX_EXIT 222

#ifdef KVM_CAP_IRQ_ROUTING