KVM: SVM: fix race between interrupt delivery and AVIC inhibition
authorMaxim Levitsky <mlevitsk@redhat.com>
Tue, 8 Feb 2022 11:48:42 +0000 (06:48 -0500)
committerPaolo Bonzini <pbonzini@redhat.com>
Fri, 11 Feb 2022 17:53:02 +0000 (12:53 -0500)
commit66fa226c131fb89287f8f7d004a46e39a859fbf6
treee4cef04d0981cbbf4128773c7a76435ff5a0e07e
parent30811174f0dbe17fd58eba5c22c50292c083c75b
KVM: SVM: fix race between interrupt delivery and AVIC inhibition

If svm_deliver_avic_intr is called just after the target vcpu's AVIC got
inhibited, it might read a stale value of vcpu->arch.apicv_active
which can lead to the target vCPU not noticing the interrupt.

To fix this use load-acquire/store-release so that, if the target vCPU
is IN_GUEST_MODE, we're guaranteed to see a previous disabling of the
AVIC.  If AVIC has been disabled in the meanwhile, proceed with the
KVM_REQ_EVENT-based delivery.

Incomplete IPI vmexit has the same races as svm_deliver_avic_intr, and
in fact it can be handled in exactly the same way; the only difference
lies in who has set IRR, whether svm_deliver_interrupt or the processor.
Therefore, svm_complete_interrupt_delivery can be used to fix incomplete
IPI vmexits as well.

Co-developed-by: Paolo Bonzini <pbonzini@redhat.com>
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
Signed-off-by: Maxim Levitsky <mlevitsk@redhat.com>
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
arch/x86/kvm/svm/avic.c
arch/x86/kvm/svm/svm.c
arch/x86/kvm/svm/svm.h
arch/x86/kvm/x86.c