Andrea Arcangeli wrote:
On Wed, Aug 13, 2008 at 10:05:06AM +0200, Jan Kiszka wrote:
Should this issue have been fixed meanwhile? I just gave latest git a
try and - as far as I recall my tests before holiday correctly - things
look the same. At least some Linux 2.6.23 kernel still hangs here during
early boot with -no-kvm-irqchip.

The trouble was that clearing the idt_vectoring_info before handling
the exit_reason would lead to the handle_exception to fail setting the
irq_pending bit because is_external_interrupt was run on zero instead
of the vmcs IDT_VECTORING_INFO_FIELD, so it didn't notice it was an
external interrupt generating the exit.

This makes the userland irqchip code work again for me, there seem to
be no good reason to clear this value before returning in guest mode
and only setting it to zero didn't look an effective debugging aid, so
it's a microoptimization for the kernel irqchip too.

I don't like the usage of idt_vectoring_info; so I've switched the !irqchip_in_kernel path to use the interrupt queue. Attached patch boots Windows XP ACPI here.

Will push it out once it passes regression testing.

--
I have a truly marvellous patch that fixes the bug which this
signature is too narrow to contain.

>From 37304c6f9ced347cf013bcd4bf808d6fd4fb6ce1 Mon Sep 17 00:00:00 2001
From: Avi Kivity <[EMAIL PROTECTED]>
Date: Thu, 14 Aug 2008 11:13:16 +0300
Subject: [PATCH] KVM: VMX: Use interrupt queue for !irqchip_in_kernel

Signed-off-by: Avi Kivity <[EMAIL PROTECTED]>
---
 arch/x86/kvm/vmx.c |   11 +++++------
 1 files changed, 5 insertions(+), 6 deletions(-)

diff --git a/arch/x86/kvm/vmx.c b/arch/x86/kvm/vmx.c
index 337670b..8693fb5 100644
--- a/arch/x86/kvm/vmx.c
+++ b/arch/x86/kvm/vmx.c
@@ -2173,7 +2173,7 @@ static void kvm_do_inject_irq(struct kvm_vcpu *vcpu)
        clear_bit(bit_index, &vcpu->arch.irq_pending[word_index]);
        if (!vcpu->arch.irq_pending[word_index])
                clear_bit(word_index, &vcpu->arch.irq_summary);
-       vmx_inject_irq(vcpu, irq);
+       kvm_queue_interrupt(vcpu, irq);
 }
 
 
@@ -2187,13 +2187,12 @@ static void do_interrupt_requests(struct kvm_vcpu *vcpu,
                 (vmcs_read32(GUEST_INTERRUPTIBILITY_INFO) & 3) == 0);
 
        if (vcpu->arch.interrupt_window_open &&
-           vcpu->arch.irq_summary &&
-           !(vmcs_read32(VM_ENTRY_INTR_INFO_FIELD) & INTR_INFO_VALID_MASK))
-               /*
-                * If interrupts enabled, and not blocked by sti or mov ss. 
Good.
-                */
+           vcpu->arch.irq_summary && !vcpu->arch.interrupt.pending)
                kvm_do_inject_irq(vcpu);
 
+       if (vcpu->arch.interrupt_window_open && vcpu->arch.interrupt.pending)
+               vmx_inject_irq(vcpu, vcpu->arch.interrupt.nr);
+
        cpu_based_vm_exec_control = vmcs_read32(CPU_BASED_VM_EXEC_CONTROL);
        if (!vcpu->arch.interrupt_window_open &&
            (vcpu->arch.irq_summary || kvm_run->request_interrupt_window))
-- 
1.5.6.3

Reply via email to