All of lore.kernel.org
 help / color / mirror / Atom feed
From: Andrew Cooper <andrew.cooper3@citrix.com>
To: Jan Beulich <JBeulich@suse.com>
Cc: Keir Fraser <keir.xen@gmail.com>,
	"xen-devel@lists.xensource.com" <xen-devel@lists.xensource.com>
Subject: Re: 4.0/4.1 requests - IO-APIC EOI [RFC]
Date: Thu, 8 Sep 2011 14:18:19 +0100	[thread overview]
Message-ID: <4E68C09B.8050409@citrix.com> (raw)
In-Reply-To: <4E68C6C10200007800055485@nat28.tlf.novell.com>

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

--- SNIP ---

Attached is my first attempt at expanding the EOI to work on older
IO-APICs.  It has not undergone any significant testing yet.

Does this look suitable?

-- 
Andrew Cooper - Dom0 Kernel Engineer, Citrix XenServer
T: +44 (0)1223 225 900, http://www.citrix.com


[-- Attachment #2: IO-APIC-eoi.patch --]
[-- Type: text/x-patch, Size: 4212 bytes --]

diff -r 0268e7380953 xen/arch/x86/io_apic.c
--- a/xen/arch/x86/io_apic.c	Mon Sep 05 15:10:28 2011 +0100
+++ b/xen/arch/x86/io_apic.c	Thu Sep 08 14:17:31 2011 +0100
@@ -357,7 +357,7 @@ static void __eoi_IO_APIC_irq(unsigned i
         pin = entry->pin;
         if (pin == -1)
             break;
-        io_apic_eoi(entry->apic, vector);
+        io_apic_eoi_vector(entry->apic, vector);
         if (!entry->next)
             break;
         entry = irq_2_pin + entry->next;
@@ -397,18 +397,7 @@ static void clear_IO_APIC_pin(unsigned i
             entry.trigger = 1;
             __ioapic_write_entry(apic, pin, TRUE, entry);
         }
-        if (mp_ioapics[apic].mpc_apicver >= 0x20)
-            io_apic_eoi(apic, entry.vector);
-        else {
-            /*
-             * Mechanism by which we clear remoteIRR in this case is by
-             * changing the trigger mode to edge and back to level.
-             */
-            entry.trigger = 0;
-            __ioapic_write_entry(apic, pin, TRUE, entry);
-            entry.trigger = 1;
-            __ioapic_write_entry(apic, pin, TRUE, entry);
-        }
+        io_apic_eoi_pin(apic, pin);
     }
 
     /*
@@ -1750,7 +1739,7 @@ static void end_level_ioapic_irq (unsign
     {
         int ioapic;
         for (ioapic = 0; ioapic < nr_ioapics; ioapic++)
-            io_apic_eoi(ioapic, i);
+            io_apic_eoi_vector(ioapic, i);
     }
 
     v = apic_read(APIC_TMR + ((i & ~0x1f) >> 1));
@@ -2622,3 +2611,67 @@ void __init init_ioapic_mappings(void)
     printk(XENLOG_INFO "IRQ limits: %u GSI, %u MSI/MSI-X\n",
            nr_irqs_gsi, nr_irqs - nr_irqs_gsi);
 }
+
+/* EOI an IO-APIC entry given the vector it points to */
+void io_apic_eoi_vector(unsigned int apic, unsigned int vector)
+{
+    unsigned int flags;
+    
+    spin_lock_irqsave(&ioapic_lock, flags);
+
+    if ( ioapic_has_eoi_reg(apic) )
+        /* Prefer the use of the EOI register if available */
+        *(IO_APIC_BASE(apic)+16) = vector;
+    else
+    {
+        /* Else search through the IO-APIC entries to find the
+         * correct pin */
+        struct IO_APIC_route_entry entry;
+        unsigned int pin = 0;
+
+        do
+        {
+            entry = __ioapic_read_entry(apic, pin, TRUE);
+
+            if ( entry.vector == vector )
+            {
+                /* And if found, fake an EOI by flipping the
+                 * trigger mode to edge and back */
+                entry.trigger = 0;
+                __ioapic_write_entry(apic, pin, TRUE, entry);
+                entry.trigger = 1;
+                __ioapic_write_entry(apic, pin, TRUE, entry);
+                break;
+            }
+
+        } while ( pin++ < nr_ioapic_registers[apic] );
+    }
+
+    spin_unlock_irqrestore(&ioapic_lock, flags);
+}
+
+/* EOI an IO-APIC entry given its pin */
+void io_apic_eoi_pin(unsigned int apic, unsigned int pin)
+{
+    struct IO_APIC_route_entry entry;
+    unsigned int flags;
+
+    entry = __ioapic_read_entry(apic, pin, TRUE);
+
+    spin_lock_irqsave(&ioapic_lock, flags);
+
+    if ( ioapic_has_eoi_reg(apic) )
+        /* Prefer the use of the EOI register if available */
+        *(IO_APIC_BASE(apic)+16) = entry.vector;
+    else
+    {
+        /* Else fake an EOI by switching to edge triggered mode
+         * and back */
+        entry.trigger = 0;
+        __ioapic_write_entry(apic, pin, TRUE, entry);
+        entry.trigger = 1;
+        __ioapic_write_entry(apic, pin, TRUE, entry);
+    }
+
+    spin_unlock_irqrestore(&ioapic_lock, flags);
+}
diff -r 0268e7380953 xen/include/asm-x86/io_apic.h
--- a/xen/include/asm-x86/io_apic.h	Mon Sep 05 15:10:28 2011 +0100
+++ b/xen/include/asm-x86/io_apic.h	Thu Sep 08 14:17:31 2011 +0100
@@ -157,10 +157,9 @@ static inline void io_apic_write(unsigne
 	__io_apic_write(apic, reg, value);
 }
 
-static inline void io_apic_eoi(unsigned int apic, unsigned int vector)
-{
-	*(IO_APIC_BASE(apic)+16) = vector;
-}
+#define ioapic_has_eoi_reg(apic) (mp_ioapics[(apic)].mpc_apicver >= 0x20)
+void io_apic_eoi_vector(unsigned int apic, unsigned int vector);
+void io_apic_eoi_pin(unsigned int apic, unsigned int pin);
 
 /*
  * Re-write a value: to be used for read-modify-write

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

_______________________________________________
Xen-devel mailing list
Xen-devel@lists.xensource.com
http://lists.xensource.com/xen-devel

  reply	other threads:[~2011-09-08 13:18 UTC|newest]

Thread overview: 21+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2011-09-08  9:19 4.0/4.1 requests Jan Beulich
2011-09-08 10:12 ` Jan Beulich
2011-09-08 11:29   ` Keir Fraser
2011-09-08 10:17 ` Keir Fraser
2011-09-08 10:48   ` Andrew Cooper
2011-09-08 11:11     ` Keir Fraser
2011-09-08 11:44     ` Jan Beulich
2011-09-08 13:18       ` Andrew Cooper [this message]
2011-09-08 13:40         ` 4.0/4.1 requests - IO-APIC EOI [RFC] Jan Beulich
2011-09-08 13:56           ` Andrew Cooper
2011-09-09 15:06             ` Re: 4.0/4.1 requests - IO-APIC EOI v2 [RFC] Andrew Cooper
2011-09-09 15:39               ` Jan Beulich
2011-09-09 15:55                 ` Andrew Cooper
2011-09-09 16:03                   ` Jan Beulich
2011-09-09 16:22                     ` Re: 4.0/4.1 requests - IO-APIC EOI v3 [RFC] Andrew Cooper
2011-09-09 16:47                       ` Re: 4.0/4.1 requests - IO-APIC EOI v4 [RFC] Andrew Cooper
2011-09-09 16:50                         ` Andrew Cooper
2011-09-12  6:50                         ` Jan Beulich
2011-09-12 10:15                           ` Andrew Cooper
2011-09-12 10:23                             ` Jan Beulich
2011-09-12 11:30                               ` Keir Fraser

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=4E68C09B.8050409@citrix.com \
    --to=andrew.cooper3@citrix.com \
    --cc=JBeulich@suse.com \
    --cc=keir.xen@gmail.com \
    --cc=xen-devel@lists.xensource.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.