diff options
author | Ralf Baechle <ralf@linux-mips.org> | 2006-11-06 17:41:06 +0000 |
---|---|---|
committer | Ralf Baechle <ralf@linux-mips.org> | 2006-11-06 20:55:38 +0000 |
commit | 4a4cf77923eeb3cec40a302656d6ab5ced04ba48 (patch) | |
tree | 6388d7a2227a28697b4c833089980c26df696745 /arch/mips/kernel/irq.c | |
parent | 325d08d1a44b601fbf70c259fb61c38d2af7d309 (diff) | |
download | op-kernel-dev-4a4cf77923eeb3cec40a302656d6ab5ced04ba48.zip op-kernel-dev-4a4cf77923eeb3cec40a302656d6ab5ced04ba48.tar.gz |
[MIPS] Make irq number allocator generally available for fixing EV64120.
Signed-off-by: Ralf Baechle <ralf@linux-mips.org>
Diffstat (limited to 'arch/mips/kernel/irq.c')
-rw-r--r-- | arch/mips/kernel/irq.c | 42 |
1 files changed, 42 insertions, 0 deletions
diff --git a/arch/mips/kernel/irq.c b/arch/mips/kernel/irq.c index dd24434..9b0e49d 100644 --- a/arch/mips/kernel/irq.c +++ b/arch/mips/kernel/irq.c @@ -26,6 +26,48 @@ #include <asm/system.h> #include <asm/uaccess.h> +static unsigned long irq_map[NR_IRQS / BITS_PER_LONG]; + +int __devinit allocate_irqno(void) +{ + int irq; + +again: + irq = find_first_zero_bit(irq_map, NR_IRQS); + + if (irq >= NR_IRQS) + return -ENOSPC; + + if (test_and_set_bit(irq, irq_map)) + goto again; + + return irq; +} + +EXPORT_SYMBOL_GPL(allocate_irqno); + +/* + * Allocate the 16 legacy interrupts for i8259 devices. This happens early + * in the kernel initialization so treating allocation failure as BUG() is + * ok. + */ +void __init alloc_legacy_irqno(void) +{ + int i; + + for (i = 0; i <= 16; i++) + BUG_ON(test_and_set_bit(i, irq_map)); +} + +void __devinit free_irqno(unsigned int irq) +{ + smp_mb__before_clear_bit(); + clear_bit(irq, irq_map); + smp_mb__after_clear_bit(); +} + +EXPORT_SYMBOL_GPL(free_irqno); + /* * 'what should we do if we get a hw irq event on an illegal vector'. * each architecture has to answer this themselves. |