Commit 290e5305 authored by Felipe Balbi's avatar Felipe Balbi Committed by Sasha Levin

irqchip: omap-intc: Improve IRQ handler

[ Upstream commit 6ed34648 ]

As it turns out the current IRQ number will *always* be available from
SIR register which renders the reads of PENDING registers as plain
unnecessary overhead.

In order to catch any situation where SIR reads as zero, we're adding
a WARN() to turn it into a very verbose error and users actually
report it.

With this patch average running time of omap_intc_handle_irq() reduced
from about 28.5us to 19.8us as measured by the kernel function
profiler.

Tested with BeagleBoneBlack Rev A5C.
Tested-by: default avatarTony Lindgren <tony@atomide.com>
Signed-off-by: default avatarFelipe Balbi <balbi@ti.com>
Cc: Linux ARM Kernel Mailing List <linux-arm-kernel@lists.infradead.org>
Link: http://lkml.kernel.org/r/20150720204910.GH5394@saruman.tx.rr.comSigned-off-by: default avatarThomas Gleixner <tglx@linutronix.de>
Signed-off-by: default avatarSasha Levin <sasha.levin@oracle.com>
parent 4d7a10c5
...@@ -331,37 +331,12 @@ static int __init omap_init_irq(u32 base, struct device_node *node) ...@@ -331,37 +331,12 @@ static int __init omap_init_irq(u32 base, struct device_node *node)
static asmlinkage void __exception_irq_entry static asmlinkage void __exception_irq_entry
omap_intc_handle_irq(struct pt_regs *regs) omap_intc_handle_irq(struct pt_regs *regs)
{ {
u32 irqnr = 0; u32 irqnr;
int handled_irq = 0;
int i;
do {
for (i = 0; i < omap_nr_pending; i++) {
irqnr = intc_readl(INTC_PENDING_IRQ0 + (0x20 * i));
if (irqnr)
goto out;
}
out:
if (!irqnr)
break;
irqnr = intc_readl(INTC_SIR);
irqnr &= ACTIVEIRQ_MASK;
if (irqnr) { irqnr = intc_readl(INTC_SIR);
handle_domain_irq(domain, irqnr, regs); irqnr &= ACTIVEIRQ_MASK;
handled_irq = 1; WARN_ONCE(!irqnr, "Spurious IRQ ?\n");
} handle_domain_irq(domain, irqnr, regs);
} while (irqnr);
/*
* If an irq is masked or deasserted while active, we will
* keep ending up here with no irq handled. So remove it from
* the INTC with an ack.
*/
if (!handled_irq)
omap_ack_irq(NULL);
} }
void __init omap2_init_irq(void) void __init omap2_init_irq(void)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment