From: David Matlack <dmatlack@google.com>
To: Paolo Bonzini <pbonzini@redhat.com>
Cc: linux-kernel@vger.kernel.org, kvm@vger.kernel.org,
seanjc@google.com, stable@vger.kernel.org
Subject: Re: [PATCH 3/4] KVM: x86: check PIR even for vCPUs with disabled APICv
Date: Mon, 29 Nov 2021 23:39:05 +0000 [thread overview]
Message-ID: <YaVkmfqkau2EYuy+@google.com> (raw)
In-Reply-To: <20211123004311.2954158-4-pbonzini@redhat.com>
On Mon, Nov 22, 2021 at 07:43:10PM -0500, Paolo Bonzini wrote:
> The IRTE for an assigned device can trigger a POSTED_INTR_VECTOR even
> if APICv is disabled on the vCPU that receives it. In that case, the
> interrupt will just cause a vmexit and leave the ON bit set together
> with the PIR bit corresponding to the interrupt.
>
> Right now, the interrupt would not be delivered until APICv is re-enabled.
> However, fixing this is just a matter of always doing the PIR->IRR
> synchronization, even if the vCPU has temporarily disabled APICv.
>
> This is not a problem for performance, or if anything it is an
> improvement. First, in the common case where vcpu->arch.apicv_active is
> true, one fewer check has to be performed. Second, static_call_cond will
> elide the function call if APICv is not present or disabled. Finally,
> in the case for AMD hardware we can remove the sync_pir_to_irr callback:
> it is only needed for apic_has_interrupt_for_ppr, and that function
> already has a fallback for !APICv.
>
> Cc: stable@vger.kernel.org
> Co-developed-by: Sean Christopherson <seanjc@google.com>
> Signed-off-by: Sean Christopherson <seanjc@google.com>
> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
Reviewed-by: David Matlack <dmatlack@google.com>
> ---
> arch/x86/kvm/lapic.c | 2 +-
> arch/x86/kvm/svm/svm.c | 1 -
> arch/x86/kvm/x86.c | 18 +++++++++---------
> 3 files changed, 10 insertions(+), 11 deletions(-)
>
> diff --git a/arch/x86/kvm/lapic.c b/arch/x86/kvm/lapic.c
> index 759952dd1222..f206fc35deff 100644
> --- a/arch/x86/kvm/lapic.c
> +++ b/arch/x86/kvm/lapic.c
> @@ -707,7 +707,7 @@ static void pv_eoi_clr_pending(struct kvm_vcpu *vcpu)
> static int apic_has_interrupt_for_ppr(struct kvm_lapic *apic, u32 ppr)
> {
> int highest_irr;
> - if (apic->vcpu->arch.apicv_active)
> + if (kvm_x86_ops.sync_pir_to_irr)
> highest_irr = static_call(kvm_x86_sync_pir_to_irr)(apic->vcpu);
> else
> highest_irr = apic_find_highest_irr(apic);
> diff --git a/arch/x86/kvm/svm/svm.c b/arch/x86/kvm/svm/svm.c
> index 5630c241d5f6..d0f68d11ec70 100644
> --- a/arch/x86/kvm/svm/svm.c
> +++ b/arch/x86/kvm/svm/svm.c
> @@ -4651,7 +4651,6 @@ static struct kvm_x86_ops svm_x86_ops __initdata = {
> .load_eoi_exitmap = svm_load_eoi_exitmap,
> .hwapic_irr_update = svm_hwapic_irr_update,
> .hwapic_isr_update = svm_hwapic_isr_update,
> - .sync_pir_to_irr = kvm_lapic_find_highest_irr,
> .apicv_post_state_restore = avic_post_state_restore,
>
> .set_tss_addr = svm_set_tss_addr,
> diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
> index 441f4769173e..a8f12c83db4b 100644
> --- a/arch/x86/kvm/x86.c
> +++ b/arch/x86/kvm/x86.c
> @@ -4448,8 +4448,7 @@ void kvm_arch_vcpu_put(struct kvm_vcpu *vcpu)
> static int kvm_vcpu_ioctl_get_lapic(struct kvm_vcpu *vcpu,
> struct kvm_lapic_state *s)
> {
> - if (vcpu->arch.apicv_active)
> - static_call(kvm_x86_sync_pir_to_irr)(vcpu);
> + static_call_cond(kvm_x86_sync_pir_to_irr)(vcpu);
>
> return kvm_apic_get_state(vcpu, s);
> }
> @@ -9528,8 +9527,7 @@ static void vcpu_scan_ioapic(struct kvm_vcpu *vcpu)
> if (irqchip_split(vcpu->kvm))
> kvm_scan_ioapic_routes(vcpu, vcpu->arch.ioapic_handled_vectors);
> else {
> - if (vcpu->arch.apicv_active)
> - static_call(kvm_x86_sync_pir_to_irr)(vcpu);
> + static_call_cond(kvm_x86_sync_pir_to_irr)(vcpu);
> if (ioapic_in_kernel(vcpu->kvm))
> kvm_ioapic_scan_entry(vcpu, vcpu->arch.ioapic_handled_vectors);
> }
> @@ -9802,10 +9800,12 @@ static int vcpu_enter_guest(struct kvm_vcpu *vcpu)
>
> /*
> * This handles the case where a posted interrupt was
> - * notified with kvm_vcpu_kick.
> + * notified with kvm_vcpu_kick. Assigned devices can
> + * use the POSTED_INTR_VECTOR even if APICv is disabled,
> + * so do it even if APICv is disabled on this vCPU.
> */
> - if (kvm_lapic_enabled(vcpu) && vcpu->arch.apicv_active)
> - static_call(kvm_x86_sync_pir_to_irr)(vcpu);
> + if (kvm_lapic_enabled(vcpu))
> + static_call_cond(kvm_x86_sync_pir_to_irr)(vcpu);
>
> if (kvm_vcpu_exit_request(vcpu)) {
> vcpu->mode = OUTSIDE_GUEST_MODE;
> @@ -9849,8 +9849,8 @@ static int vcpu_enter_guest(struct kvm_vcpu *vcpu)
> if (likely(exit_fastpath != EXIT_FASTPATH_REENTER_GUEST))
> break;
>
> - if (kvm_lapic_enabled(vcpu) && vcpu->arch.apicv_active)
> - static_call(kvm_x86_sync_pir_to_irr)(vcpu);
> + if (kvm_lapic_enabled(vcpu))
> + static_call_cond(kvm_x86_sync_pir_to_irr)(vcpu);
>
> if (unlikely(kvm_vcpu_exit_request(vcpu))) {
> exit_fastpath = EXIT_FASTPATH_EXIT_HANDLED;
> --
> 2.27.0
>
>
next prev parent reply other threads:[~2021-11-29 23:39 UTC|newest]
Thread overview: 16+ messages / expand[flat|nested] mbox.gz Atom feed top
2021-11-23 0:43 [PATCH 0/4] KVM: VMX: process posted interrupts on APICv-disable vCPUs Paolo Bonzini
2021-11-23 0:43 ` [PATCH 1/4] KVM: x86: ignore APICv if LAPIC is not enabled Paolo Bonzini
2021-11-25 1:36 ` Sean Christopherson
2021-11-29 23:32 ` David Matlack
2021-11-30 7:50 ` Maxim Levitsky
2021-11-23 0:43 ` [PATCH 2/4] KVM: VMX: prepare sync_pir_to_irr for running with APICv disabled Paolo Bonzini
2021-11-29 22:14 ` Sean Christopherson
2021-11-30 8:31 ` Paolo Bonzini
2021-11-29 23:34 ` David Matlack
2021-11-30 7:57 ` Maxim Levitsky
2021-11-23 0:43 ` [PATCH 3/4] KVM: x86: check PIR even for vCPUs with disabled APICv Paolo Bonzini
2021-11-29 23:39 ` David Matlack [this message]
2021-11-30 7:58 ` Maxim Levitsky
2021-11-23 0:43 ` [PATCH 4/4] KVM: x86: Use a stable condition around all VT-d PI paths Paolo Bonzini
2021-11-29 23:41 ` David Matlack
2021-11-30 8:05 ` Maxim Levitsky
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=YaVkmfqkau2EYuy+@google.com \
--to=dmatlack@google.com \
--cc=kvm@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=pbonzini@redhat.com \
--cc=seanjc@google.com \
--cc=stable@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.