From 8019bdd0c7e2933a4d6f7e046d1cc2ded221784e Mon Sep 17 00:00:00 2001
From: Sheng Yang <[EMAIL PROTECTED]>
Date: Wed, 30 Jul 2008 21:45:58 +0800
Subject: [PATCH] KVM: Fix exiting from HLT emulation with 
MP_STATE_HALTED

VCPU can be forced exit from HLT emulation without setting mp_state to
MP_STATE_RUNNABLE, it's due to QEmu can kick vcpus which are doing HLT
emulation to do something like "stop" or "info cpus". Here are two 
issues of this behaviour:

First, if vcpu exit to QEmu with MP_STATE_HALTED, it would keep in 
this state later for vcpu_run(), which is eerie...

Second, a practical problem: bios load AP boot up code to 0x10000, and 
AP is running HLT there. But later grub load it's stage2 code to the 
same address. Then if the halting vcpu was forced exit to QEmu in 
grub, and come back for vcpu_run later, it can't execute HLT 
instruction anymore, just because the bios code is not there,
and it would follow a piece of code of grub, which would cause 
completely chaos...

The second issue directly lead to guest crash or SMP linux can't boot 
up AP later if we "stop" or "info cpus" in grub.

The patch resumes the HLT emulation after interrupt by QEmu to fix it.

Signed-off-by: Sheng Yang <[EMAIL PROTECTED]>
---
 arch/x86/kvm/x86.c |    6 ++++++
 1 files changed, 6 insertions(+), 0 deletions(-)

diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
index 94a2165..3b31959 100644
--- a/arch/x86/kvm/x86.c
+++ b/arch/x86/kvm/x86.c
@@ -2881,6 +2881,11 @@ again:
        clear_bit(KVM_REQ_PENDING_TIMER, &vcpu->requests);
        kvm_inject_pending_timer_irqs(vcpu);

+       if (vcpu->arch.mp_state == KVM_MP_STATE_HALTED) {
+               r = kvm_emulate_halt(vcpu);
+               goto next_around;
+       }
+
        preempt_disable();

        kvm_x86_ops->prepare_guest_switch(vcpu);
@@ -2962,6 +2967,7 @@ again:

        r = kvm_x86_ops->handle_exit(kvm_run, vcpu);

+next_around:
        if (r > 0) {
                if (dm_request_for_irq_injection(vcpu, kvm_run)) {
                        r = -EINTR;
--
1.5.4.5

From 8019bdd0c7e2933a4d6f7e046d1cc2ded221784e Mon Sep 17 00:00:00 2001
From: Sheng Yang <[EMAIL PROTECTED]>
Date: Wed, 30 Jul 2008 21:45:58 +0800
Subject: [PATCH] KVM: Fix exiting from HLT emulation with MP_STATE_HALTED

VCPU can be forced exit from HLT emulation without setting mp_state to
MP_STATE_RUNNABLE, it's due to QEmu can kick vcpus which are doing HLT
emulation to do something like "stop" or "info cpus". Here are two issues of
this behaviour:

First, if vcpu exit to QEmu with MP_STATE_HALTED, it would keep in this state
later for vcpu_run(), which is eerie...

Second, a practical problem: bios load AP boot up code to 0x10000, and AP is
running HLT there. But later grub load it's stage2 code to the same address. Then
if the halting vcpu was forced exit to QEmu in grub, and come back for vcpu_run later,
it can't execute HLT instruction anymore, just because the bios code is not there,
and it would follow a piece of code of grub, which would cause completely chaos...

The second issue directly lead to guest crash or SMP linux can't boot up AP
later if we "stop" or "info cpus" in grub.

The patch resumes the HLT emulation after interrupt by QEmu to fix it.

Signed-off-by: Sheng Yang <[EMAIL PROTECTED]>
---
 arch/x86/kvm/x86.c |    6 ++++++
 1 files changed, 6 insertions(+), 0 deletions(-)

diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
index 94a2165..3b31959 100644
--- a/arch/x86/kvm/x86.c
+++ b/arch/x86/kvm/x86.c
@@ -2881,6 +2881,11 @@ again:
 	clear_bit(KVM_REQ_PENDING_TIMER, &vcpu->requests);
 	kvm_inject_pending_timer_irqs(vcpu);
 
+	if (vcpu->arch.mp_state == KVM_MP_STATE_HALTED) {
+		r = kvm_emulate_halt(vcpu);
+		goto next_around;
+	}
+
 	preempt_disable();
 
 	kvm_x86_ops->prepare_guest_switch(vcpu);
@@ -2962,6 +2967,7 @@ again:
 
 	r = kvm_x86_ops->handle_exit(kvm_run, vcpu);
 
+next_around:
 	if (r > 0) {
 		if (dm_request_for_irq_injection(vcpu, kvm_run)) {
 			r = -EINTR;
-- 
1.5.4.5

Reply via email to