public inbox for kvm@vger.kernel.org
 help / color / mirror / Atom feed
* [PATCH] fix PIC interrupt delivery in Qemu when LAPIC is enabled
@ 2007-04-28  6:04 He, Qing
       [not found] ` <37E52D09333DE2469A03574C88DBF40F048D98-wq7ZOvIWXbM/UvCtAeCM4rfspsVTdybXVpNB7YpNyf8@public.gmane.org>
  0 siblings, 1 reply; 2+ messages in thread
From: He, Qing @ 2007-04-28  6:04 UTC (permalink / raw)
  To: kvm-devel

[-- Attachment #1: Type: text/plain, Size: 845 bytes --]

Current interrupt logic in Qemu unconditionally checks pending irqs on
PIC after checking local APIC, however, this is problematic.
	On common platform, PIC is usually connected to the LINT0 of
local APIC. In this way when local APIC is disabled, this pin behaves
like INTR. But when local APIC is enabled, its behavior can be
determined by LVT_LINT0: PIC should only deliver normal irq only when
`external interrupt' delivery mode is set.
	x86_64 Linux kernel uses PIT->PIC->LINT0 as NMI source when
performance counters are not available, but the logic described above
treats the NMI as normal interrupt which yields a 2x faster global timer
because an additional timer interrupt is injected on every tick. This
patch fixes this issue.

Signed-off-by: Qing He <qing.he-ral2JQCrhuEAvxtiuMwx3w@public.gmane.org>


Thanks,
Qing

[-- Attachment #2: kvm-pic-apic-mutual-exclusive.patch --]
[-- Type: application/octet-stream, Size: 1968 bytes --]

diff --git a/qemu/hw/apic.c b/qemu/hw/apic.c
index 8c97761..72bd8f8 100644
--- a/qemu/hw/apic.c
+++ b/qemu/hw/apic.c
@@ -484,6 +484,20 @@ int apic_get_interrupt(CPUState *env)
     return intno;
 }
 
+int apic_accept_pic_intr(CPUState *env)
+{
+    APICState *s = env->apic_state;
+    uint32_t lvt0 = s->lvt[APIC_LVT_LINT0];
+
+    if (s->id == 0 &&
+        ((s->apicbase & MSR_IA32_APICBASE_ENABLE) == 0 ||
+         ((lvt0 & APIC_LVT_MASKED) == 0 &&
+          ((lvt0 >> 8) & 0x7) == APIC_DM_EXTINT)))
+        return 1;
+
+    return 0;
+}
+
 static uint32_t apic_get_current_count(APICState *s)
 {
     int64_t d;
@@ -820,6 +834,13 @@ int apic_init(CPUState *env)
     s->apicbase = 0xfee00000 | 
         (s->id ? 0 : MSR_IA32_APICBASE_BSP) | MSR_IA32_APICBASE_ENABLE;
 
+    /*
+     * LINT0 delivery mode is set to ExtInt at initialization time
+     * typically by BIOS, so PIC interrupt can be delivered to the
+     * processor when local APIC is enabled.
+     */
+    s->lvt[APIC_LVT_LINT0] = 0x700;
+
     /* XXX: mapping more APICs at the same memory location */
     if (apic_io_memory == 0) {
         /* NOTE: the APIC is directly connected to the CPU - it is not
diff --git a/qemu/hw/pc.c b/qemu/hw/pc.c
index ab792a9..eda49cf 100644
--- a/qemu/hw/pc.c
+++ b/qemu/hw/pc.c
@@ -99,6 +99,9 @@ int cpu_get_pic_interrupt(CPUState *env)
         return intno;
     }
     /* read the irq from the PIC */
+    if (!apic_accept_pic_intr(env))
+        return -1;
+
     intno = pic_read_irq(isa_pic);
     return intno;
 }
diff --git a/qemu/vl.h b/qemu/vl.h
index 88b4a3f..debd17c 100644
--- a/qemu/vl.h
+++ b/qemu/vl.h
@@ -1058,6 +1058,7 @@ typedef struct IOAPICState IOAPICState;
 
 int apic_init(CPUState *env);
 int apic_get_interrupt(CPUState *env);
+int apic_accept_pic_intr(CPUState *env);
 IOAPICState *ioapic_init(void);
 void ioapic_set_irq(void *opaque, int vector, int level);
 

[-- Attachment #3: Type: text/plain, Size: 286 bytes --]

-------------------------------------------------------------------------
This SF.net email is sponsored by DB2 Express
Download DB2 Express C - the FREE version of DB2 express and take
control of your XML. No limits. Just data. Click to get it now.
http://sourceforge.net/powerbar/db2/

[-- Attachment #4: Type: text/plain, Size: 186 bytes --]

_______________________________________________
kvm-devel mailing list
kvm-devel-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f@public.gmane.org
https://lists.sourceforge.net/lists/listinfo/kvm-devel

^ permalink raw reply related	[flat|nested] 2+ messages in thread

* Re: [PATCH] fix PIC interrupt delivery in Qemu when LAPIC is enabled
       [not found] ` <37E52D09333DE2469A03574C88DBF40F048D98-wq7ZOvIWXbM/UvCtAeCM4rfspsVTdybXVpNB7YpNyf8@public.gmane.org>
@ 2007-04-28  6:49   ` Avi Kivity
  0 siblings, 0 replies; 2+ messages in thread
From: Avi Kivity @ 2007-04-28  6:49 UTC (permalink / raw)
  To: He, Qing; +Cc: kvm-devel

He, Qing wrote:
> Current interrupt logic in Qemu unconditionally checks pending irqs on
> PIC after checking local APIC, however, this is problematic.
> 	On common platform, PIC is usually connected to the LINT0 of
> local APIC. In this way when local APIC is disabled, this pin behaves
> like INTR. But when local APIC is enabled, its behavior can be
> determined by LVT_LINT0: PIC should only deliver normal irq only when
> `external interrupt' delivery mode is set.
> 	x86_64 Linux kernel uses PIT->PIC->LINT0 as NMI source when
> performance counters are not available, but the logic described above
> treats the NMI as normal interrupt which yields a 2x faster global timer
> because an additional timer interrupt is injected on every tick. This
> patch fixes this issue.
>
> Signed-off-by: Qing He <qing.he-ral2JQCrhuEAvxtiuMwx3w@public.gmane.org>
>
>   

Applied, thanks.

This problem is present in regular qemu, can you submit it to qemu-devel
as well?  I'l like not to diverge from upstream qemu.

As your mailer doesn't mark attachments to be displayed inline, please
submit patches in the future both as attachment and inline, for easier
review.

-- 
Do not meddle in the internals of kernels, for they are subtle and quick to panic.


-------------------------------------------------------------------------
This SF.net email is sponsored by DB2 Express
Download DB2 Express C - the FREE version of DB2 express and take
control of your XML. No limits. Just data. Click to get it now.
http://sourceforge.net/powerbar/db2/

^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2007-04-28  6:49 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2007-04-28  6:04 [PATCH] fix PIC interrupt delivery in Qemu when LAPIC is enabled He, Qing
     [not found] ` <37E52D09333DE2469A03574C88DBF40F048D98-wq7ZOvIWXbM/UvCtAeCM4rfspsVTdybXVpNB7YpNyf8@public.gmane.org>
2007-04-28  6:49   ` Avi Kivity

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox