aboutsummaryrefslogtreecommitdiffstats
path: root/arch/x86/kvm
diff options
context:
space:
mode:
Diffstat (limited to 'arch/x86/kvm')
-rw-r--r--arch/x86/kvm/x86.c17
1 files changed, 10 insertions, 7 deletions
diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
index 63c87adcec48..fc5611b4007f 100644
--- a/arch/x86/kvm/x86.c
+++ b/arch/x86/kvm/x86.c
@@ -4604,13 +4604,15 @@ static int vcpu_enter_guest(struct kvm_vcpu *vcpu)
4604 if (vcpu->fpu_active) 4604 if (vcpu->fpu_active)
4605 kvm_load_guest_fpu(vcpu); 4605 kvm_load_guest_fpu(vcpu);
4606 4606
4607 local_irq_disable(); 4607 atomic_set(&vcpu->guest_mode, 1);
4608 smp_wmb();
4608 4609
4609 clear_bit(KVM_REQ_KICK, &vcpu->requests); 4610 local_irq_disable();
4610 smp_mb__after_clear_bit();
4611 4611
4612 if (vcpu->requests || need_resched() || signal_pending(current)) { 4612 if (!atomic_read(&vcpu->guest_mode) || vcpu->requests
4613 set_bit(KVM_REQ_KICK, &vcpu->requests); 4613 || need_resched() || signal_pending(current)) {
4614 atomic_set(&vcpu->guest_mode, 0);
4615 smp_wmb();
4614 local_irq_enable(); 4616 local_irq_enable();
4615 preempt_enable(); 4617 preempt_enable();
4616 r = 1; 4618 r = 1;
@@ -4655,7 +4657,8 @@ static int vcpu_enter_guest(struct kvm_vcpu *vcpu)
4655 if (hw_breakpoint_active()) 4657 if (hw_breakpoint_active())
4656 hw_breakpoint_restore(); 4658 hw_breakpoint_restore();
4657 4659
4658 set_bit(KVM_REQ_KICK, &vcpu->requests); 4660 atomic_set(&vcpu->guest_mode, 0);
4661 smp_wmb();
4659 local_irq_enable(); 4662 local_irq_enable();
4660 4663
4661 ++vcpu->stat.exits; 4664 ++vcpu->stat.exits;
@@ -5580,7 +5583,7 @@ void kvm_vcpu_kick(struct kvm_vcpu *vcpu)
5580 5583
5581 me = get_cpu(); 5584 me = get_cpu();
5582 if (cpu != me && (unsigned)cpu < nr_cpu_ids && cpu_online(cpu)) 5585 if (cpu != me && (unsigned)cpu < nr_cpu_ids && cpu_online(cpu))
5583 if (!test_and_set_bit(KVM_REQ_KICK, &vcpu->requests)) 5586 if (atomic_xchg(&vcpu->guest_mode, 0))
5584 smp_send_reschedule(cpu); 5587 smp_send_reschedule(cpu);
5585 put_cpu(); 5588 put_cpu();
5586} 5589}