diff options
author | Matt Gingell <gingell@google.com> | 2015-11-16 18:26:00 -0500 |
---|---|---|
committer | Paolo Bonzini <pbonzini@redhat.com> | 2015-11-18 06:25:38 -0500 |
commit | 782d422bcaee4680c640fbc8ce8c45524fd11790 (patch) | |
tree | 7728d0951df231b2126b211d7856f1b4fbe4eb6d | |
parent | 127a457acb2131fdb31c68c98cf11eda8ba7b380 (diff) |
KVM: x86: split kvm_vcpu_ready_for_interrupt_injection out of dm_request_for_irq_injection
This patch breaks out a new function kvm_vcpu_ready_for_interrupt_injection.
This routine encapsulates the logic required to determine whether a vcpu
is ready to accept an interrupt injection, which is now required on
multiple paths.
Reviewed-by: Steve Rutherford <srutherford@google.com>
Signed-off-by: Matt Gingell <gingell@google.com>
Fixes: 1c1a9ce973a7863dd46767226bce2a5f12d48bc6
Cc: stable@vger.kernel.org
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
-rw-r--r-- | arch/x86/kvm/x86.c | 43 |
1 files changed, 19 insertions, 24 deletions
diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c index 46ed8edad793..32f6b760682c 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c | |||
@@ -2769,6 +2769,20 @@ static int kvm_cpu_accept_dm_intr(struct kvm_vcpu *vcpu) | |||
2769 | kvm_apic_accept_pic_intr(vcpu)); | 2769 | kvm_apic_accept_pic_intr(vcpu)); |
2770 | } | 2770 | } |
2771 | 2771 | ||
2772 | /* | ||
2773 | * if userspace requested an interrupt window, check that the | ||
2774 | * interrupt window is open. | ||
2775 | * | ||
2776 | * No need to exit to userspace if we already have an interrupt queued. | ||
2777 | */ | ||
2778 | static int kvm_vcpu_ready_for_interrupt_injection(struct kvm_vcpu *vcpu) | ||
2779 | { | ||
2780 | return kvm_arch_interrupt_allowed(vcpu) && | ||
2781 | !kvm_cpu_has_interrupt(vcpu) && | ||
2782 | !kvm_event_needs_reinjection(vcpu) && | ||
2783 | kvm_cpu_accept_dm_intr(vcpu); | ||
2784 | } | ||
2785 | |||
2772 | static int kvm_vcpu_ioctl_interrupt(struct kvm_vcpu *vcpu, | 2786 | static int kvm_vcpu_ioctl_interrupt(struct kvm_vcpu *vcpu, |
2773 | struct kvm_interrupt *irq) | 2787 | struct kvm_interrupt *irq) |
2774 | { | 2788 | { |
@@ -5916,27 +5930,10 @@ static int emulator_fix_hypercall(struct x86_emulate_ctxt *ctxt) | |||
5916 | return emulator_write_emulated(ctxt, rip, instruction, 3, NULL); | 5930 | return emulator_write_emulated(ctxt, rip, instruction, 3, NULL); |
5917 | } | 5931 | } |
5918 | 5932 | ||
5919 | /* | ||
5920 | * Check if userspace requested an interrupt window, and that the | ||
5921 | * interrupt window is open. | ||
5922 | * | ||
5923 | * No need to exit to userspace if we already have an interrupt queued. | ||
5924 | */ | ||
5925 | static int dm_request_for_irq_injection(struct kvm_vcpu *vcpu) | 5933 | static int dm_request_for_irq_injection(struct kvm_vcpu *vcpu) |
5926 | { | 5934 | { |
5927 | if (!vcpu->run->request_interrupt_window || pic_in_kernel(vcpu->kvm)) | 5935 | return vcpu->run->request_interrupt_window && |
5928 | return false; | 5936 | likely(!pic_in_kernel(vcpu->kvm)); |
5929 | |||
5930 | if (!kvm_arch_interrupt_allowed(vcpu)) | ||
5931 | return false; | ||
5932 | |||
5933 | if (kvm_cpu_has_interrupt(vcpu)) | ||
5934 | return false; | ||
5935 | |||
5936 | if (kvm_event_needs_reinjection(vcpu)) | ||
5937 | return false; | ||
5938 | |||
5939 | return kvm_cpu_accept_dm_intr(vcpu); | ||
5940 | } | 5937 | } |
5941 | 5938 | ||
5942 | static void post_kvm_run_save(struct kvm_vcpu *vcpu) | 5939 | static void post_kvm_run_save(struct kvm_vcpu *vcpu) |
@@ -5949,10 +5946,7 @@ static void post_kvm_run_save(struct kvm_vcpu *vcpu) | |||
5949 | kvm_run->apic_base = kvm_get_apic_base(vcpu); | 5946 | kvm_run->apic_base = kvm_get_apic_base(vcpu); |
5950 | kvm_run->ready_for_interrupt_injection = | 5947 | kvm_run->ready_for_interrupt_injection = |
5951 | pic_in_kernel(vcpu->kvm) || | 5948 | pic_in_kernel(vcpu->kvm) || |
5952 | (kvm_arch_interrupt_allowed(vcpu) && | 5949 | kvm_vcpu_ready_for_interrupt_injection(vcpu); |
5953 | !kvm_cpu_has_interrupt(vcpu) && | ||
5954 | !kvm_event_needs_reinjection(vcpu) && | ||
5955 | kvm_cpu_accept_dm_intr(vcpu)); | ||
5956 | } | 5950 | } |
5957 | 5951 | ||
5958 | static void update_cr8_intercept(struct kvm_vcpu *vcpu) | 5952 | static void update_cr8_intercept(struct kvm_vcpu *vcpu) |
@@ -6668,7 +6662,8 @@ static int vcpu_run(struct kvm_vcpu *vcpu) | |||
6668 | if (kvm_cpu_has_pending_timer(vcpu)) | 6662 | if (kvm_cpu_has_pending_timer(vcpu)) |
6669 | kvm_inject_pending_timer_irqs(vcpu); | 6663 | kvm_inject_pending_timer_irqs(vcpu); |
6670 | 6664 | ||
6671 | if (dm_request_for_irq_injection(vcpu)) { | 6665 | if (dm_request_for_irq_injection(vcpu) && |
6666 | kvm_vcpu_ready_for_interrupt_injection(vcpu)) { | ||
6672 | r = 0; | 6667 | r = 0; |
6673 | vcpu->run->exit_reason = KVM_EXIT_IRQ_WINDOW_OPEN; | 6668 | vcpu->run->exit_reason = KVM_EXIT_IRQ_WINDOW_OPEN; |
6674 | ++vcpu->stat.request_irq_exits; | 6669 | ++vcpu->stat.request_irq_exits; |