Kernel KVM virtualization development
 help / color / mirror / Atom feed
* [PATCH] KVM: x86: Don't patch L2's hypercall if L1 intercepts #UD
@ 2026-11-12 13:25 Like Xu
  2026-11-12 16:39 ` Sean Christopherson
  0 siblings, 1 reply; 2+ messages in thread
From: Like Xu @ 2026-11-12 13:25 UTC (permalink / raw)
  To: Sean Christopherson; +Cc: Paolo Bonzini, Oliver Upton, kvm

From: Like Xu <likexu@tencent.com>

The fix_hypercall_test selftest fails when run in an L1 VM on an AMD host:

  ret == (u64)-EFAULT

On SVM, L0 always intercepts #UD in vmcb01, so nested_svm_exit_special()
claims every #UD from L2 for L0, before L1's intercepts are consulted.
L0 then emulates L2's VMCALL and, based on the quirk that L0 userspace
configured for L1, patches it to VMMCALL. This ignores L1's decision to
disable KVM_X86_QUIRK_FIX_HYPERCALL_INSN for L2.

Synthesize #UD instead if the vCPU is in L2 and L1 intercepts #UD, so
the nested exception machinery reflects it to L1.  Keep patching L2's
instruction when L1 doesn't intercept #UD, as existing userspace relies
on it, e.g. nested SVM selftests execute VMCALL in L2 and expect L1 to
see SVM_EXIT_VMMCALL.

Fixes: f1a9761fbb00 ("KVM: x86: Allow userspace to opt out of hypercall patching")
Signed-off-by: Like Xu <likexu@tencent.com>
---
 arch/x86/kvm/x86.c | 12 +++++++++---
 1 file changed, 9 insertions(+), 3 deletions(-)

diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
index 2cd9ee316aada..8c1ae90f1f4b4 100644
--- a/arch/x86/kvm/x86.c
+++ b/arch/x86/kvm/x86.c
@@ -7507,9 +7507,15 @@ static int emulator_fix_hypercall(struct x86_emulate_ctxt *ctxt)
 
 	/*
 	 * If the quirk is disabled, synthesize a #UD and let the guest pick up
-	 * the pieces.
-	 */
-	if (!kvm_check_has_quirk(vcpu->kvm, KVM_X86_QUIRK_FIX_HYPERCALL_INSN)) {
+	 * the pieces.  Do the same if L1 intercepts #UD from L2, as fixing up
+	 * L2's hypercall is then L1's responsibility; the #UD is reflected to
+	 * L1.  If L1 doesn't intercept #UD, keep patching L2's instruction, as
+	 * existing L1 code (e.g. nested SVM selftests executing VMCALL in L2)
+	 * relies on it.
+	 */
+	if (!kvm_check_has_quirk(vcpu->kvm, KVM_X86_QUIRK_FIX_HYPERCALL_INSN) ||
+	    (is_guest_mode(vcpu) &&
+	     kvm_nested_call(is_exception_vmexit)(vcpu, UD_VECTOR, 0))) {
 		ctxt->exception.error_code_valid = false;
 		ctxt->exception.vector = UD_VECTOR;
 		ctxt->have_exception = true;
-- 
2.43.7


^ permalink raw reply related	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2026-11-12 16:39 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-11-12 13:25 [PATCH] KVM: x86: Don't patch L2's hypercall if L1 intercepts #UD Like Xu
2026-11-12 16:39 ` Sean Christopherson

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox