Re: [PATCH] KVM: x86: Drop redundant call to kvm_deliver_exception_payload()

From: Yosry Ahmed

Date: Mon Mar 02 2026 - 11:16:20 EST


On Mon, Mar 2, 2026 at 7:52 AM Sean Christopherson <seanjc@xxxxxxxxxx> wrote:
>
> On Mon, Mar 02, 2026, Yosry Ahmed wrote:
> > In kvm_check_and_inject_events(), kvm_deliver_exception_payload() is
> > called for pending #DB exceptions. However, shortly after, the
> > per-vendor inject_exception callbacks are made. Both
> > vmx_inject_exception() and svm_inject_exception() unconditionally call
> > kvm_deliver_exception_payload(), so the call in
> > kvm_check_and_inject_events() is redundant.
> >
> > Note that the extra call for pending #DB exceptions is harmless, as
> > kvm_deliver_exception_payload() clears exception.has_payload after the
> > first call.
> >
> > The call in kvm_check_and_inject_events() was added in commit
> > f10c729ff965 ("kvm: vmx: Defer setting of DR6 until #DB delivery"). At
> > that point, the call was likely needed because svm_queue_exception()
> > checked whether an exception for L2 is intercepted by L1 before calling
> > kvm_deliver_exception_payload(), as SVM did not have a
> > check_nested_events callback. Since DR6 is updated before the #DB
> > intercept in SVM (unlike VMX), it was necessary to deliver the DR6
> > payload before calling svm_queue_exception().
> >
> > After that, commit 7c86663b68ba ("KVM: nSVM: inject exceptions via
> > svm_check_nested_events") added a check_nested_events callback for SVM,
> > which checked for L1 intercepts for L2's exceptions, and delivered the
> > the payload appropriately before the intercept. At that point,
> > svm_queue_exception() started calling kvm_deliver_exception_payload()
> > unconditionally, and the call to kvm_deliver_exception_payload() from
> > its caller became redundant.
>
> Nice! I vaguely remember staring at this code when working on 5623f751bd9c
> ("KVM: x86: Treat #DBs from the emulator as fault-like (code and DR7.GD=1)"),
> but never pieced together that it was redundant.

Yeah I was confused by that call a couple of times as well, then it
recently confused an AI bot into thinking there's a bug because we
call it for #DB and not #PF. At that point I thought enough is enough!