whpx: i386: move whpx_vcpu_kick_out_of_hlt() invocation to interrupt raise time
This fixes the sti followed by hlt kvm_unit_tests. Signed-off-by: Mohamed Mediouni <mohamed@unpredictable.fr> Link: https://lore.kernel.org/r/20260228214704.19048-2-mohamed@unpredictable.fr Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
Mohamed Mediouni committed
Feb 28, 2026 at 22:46 UTC
3588d68bc8da44639405ad8d9a0fc3bb94611ca3
1 file changed
+21
-28
target/i386/whpx/whpx-all.c
+21
-28
@@ -1323,6 +1323,16 @@ static int whpx_handle_halt(CPUState *cpu)
1323
return ret;
1324
}
1325
1326
+static void whpx_vcpu_kick_out_of_hlt(CPUState *cpu)
1327
+{
1328
+ WHV_REGISTER_VALUE reg;
1329
+ whpx_get_reg(cpu, WHvRegisterInternalActivityState, ®);
1330
+ if (reg.InternalActivity.HaltSuspend) {
1331
+ reg.InternalActivity.HaltSuspend = 0;
1332
+ whpx_set_reg(cpu, WHvRegisterInternalActivityState, reg);
1333
+ }
1334
+}
1335
+
1336
static void whpx_vcpu_pre_run(CPUState *cpu)
1337
{
1338
HRESULT hr;
@@ -1406,6 +1416,17 @@ static void whpx_vcpu_pre_run(CPUState *cpu)
1416
.Vector = irq,
1417
};
1418
reg_count += 1;
1419
+ /*
1420
+ * When the Hyper-V APIC is enabled, to get out of HLT we
1421
+ * either have to request an interrupt or manually get it away
1422
+ * from HLT.
1423
+ *
1424
+ * We also manually do inject some interrupts via WHvRegisterPendingEvent
1425
+ * instead of WHVRequestInterrupt, which does not reset the HLT state.
1426
+ */
1427
+ if (whpx_irqchip_in_kernel()) {
1428
+ whpx_vcpu_kick_out_of_hlt(cpu);
1429
+ }
1430
}
1431
}
1432
@@ -1468,15 +1489,6 @@ static void whpx_vcpu_post_run(CPUState *cpu)
1489
!vcpu->exit_ctx.VpContext.ExecutionState.InterruptShadow;
1490
}
1491
1471
-static void whpx_vcpu_kick_out_of_hlt(CPUState *cpu)
1472
-{
1473
- WHV_REGISTER_VALUE reg;
1474
- whpx_get_reg(cpu, WHvRegisterInternalActivityState, ®);
1475
- if (reg.InternalActivity.HaltSuspend) {
1476
- reg.InternalActivity.HaltSuspend = 0;
1477
- whpx_set_reg(cpu, WHvRegisterInternalActivityState, reg);
1478
- }
1479
-}
1492
1493
static void whpx_vcpu_process_async_events(CPUState *cpu)
1494
{
@@ -1785,25 +1797,6 @@ int whpx_vcpu_run(CPUState *cpu)
1797
cpu->exception_index = EXCP_INTERRUPT;
1798
ret = 1;
1799
}
1788
- /*
1789
- * When the Hyper-V APIC is enabled, to get out of HLT we
1790
- * either have to request an interrupt or manually get it away
1791
- * from HLT.
1792
- *
1793
- * We also manually do inject some interrupts via WHvRegisterPendingEvent
1794
- * instead of WHVRequestInterrupt, which does not reset the HLT state.
1795
- *
1796
- * However, even with this done, if the guest does an HLT without
1797
- * interrupts enabled (which the test_sti_inhibit KVM unit test does)
1798
- * then the guest will stay in HLT forever.
1799
- *
1800
- * Keep it this way for now, with perhaps adding a heartbeat later
1801
- * so that we get the CPU time savings from having Hyper-V handle HLT
1802
- * instead of going away from it as soon as possible.
1803
- */
1804
- if (whpx_irqchip_in_kernel()) {
1805
- whpx_vcpu_kick_out_of_hlt(cpu);
1806
- }
1800
break;
1801
case WHvRunVpExitReasonX64MsrAccess: {
1802
WHV_REGISTER_VALUE reg_values[3] = {0};