From d80611283e0a6927ab49c35a71fc93d830bb4c53 Mon Sep 17 00:00:00 2001 From: Mike Baker Date: Fri, 17 Feb 2006 23:27:51 +0000 Subject: [PATCH] add interrupt debugging; fix bug with the AP60 interrupt handler SVN-Revision: 3250 --- .../linux/aruba-2.6/patches/002-irq.patch | 59 +++++++++++++------ 1 file changed, 41 insertions(+), 18 deletions(-) diff --git a/openwrt/target/linux/aruba-2.6/patches/002-irq.patch b/openwrt/target/linux/aruba-2.6/patches/002-irq.patch index 308c39903d..94e68cfb03 100644 --- a/openwrt/target/linux/aruba-2.6/patches/002-irq.patch +++ b/openwrt/target/linux/aruba-2.6/patches/002-irq.patch @@ -92,11 +92,12 @@ diff -Nur linux-2.6.15/arch/mips/aruba/idtIRQ.S linux-2.6.15-openwrt/arch/mips/a diff -Nur linux-2.6.15/arch/mips/aruba/irq.c linux-2.6.15-openwrt/arch/mips/aruba/irq.c --- linux-2.6.15/arch/mips/aruba/irq.c 1970-01-01 01:00:00.000000000 +0100 +++ linux-2.6.15-openwrt/arch/mips/aruba/irq.c 2006-01-10 00:32:32.000000000 +0100 -@@ -0,0 +1,424 @@ +@@ -0,0 +1,447 @@ +/************************************************************************** + * + * BRIEF MODULE DESCRIPTION -+ * Interrupt routines for IDT EB434 boards ++ * Interrupt routines for IDT EB434 boards / Atheros boards ++ * Modified by Aruba Networks + * + * Copyright 2004 IDT Inc. (rischelp@idt.com) + * @@ -275,7 +276,6 @@ diff -Nur linux-2.6.15/arch/mips/aruba/irq.c linux-2.6.15-openwrt/arch/mips/arub + switch (mips_machtype) { + case MACH_ARUBA_AP70: + addr = intr_group_muscat[group].base_addr; -+ // unmask intr within group + WRITE_MASK_MUSCAT(addr, READ_MASK_MUSCAT(addr) & ~intr_bit); + break; + case MACH_ARUBA_AP65: @@ -342,7 +342,7 @@ diff -Nur linux-2.6.15/arch/mips/aruba/irq.c linux-2.6.15-openwrt/arch/mips/arub + mask = READ_MASK_MERLOT(addr); + mask &= ~intr_bit; + WRITE_MASK_MERLOT(addr, mask); -+ if (!mask) ++ if (READ_MASK_MERLOT(addr)) + disable_local_irq(group_to_ip(group)); + break; + } @@ -381,11 +381,9 @@ diff -Nur linux-2.6.15/arch/mips/aruba/irq.c linux-2.6.15-openwrt/arch/mips/arub + + local_irq_save(flags); + if (irq_desc[irq_nr].status & (IRQ_DISABLED | IRQ_INPROGRESS)) { -+ printk("warning: end_irq %d did not enable (%x) (ignoring)\n", ++ printk("warning: end_irq %d did not enable (%x)\n", + irq_nr, irq_desc[irq_nr].status); -+ } -+ -+ if (ip<0) { ++ } else if (ip<0) { + enable_local_irq(irq_nr); + } else { + @@ -474,6 +472,25 @@ diff -Nur linux-2.6.15/arch/mips/aruba/irq.c linux-2.6.15-openwrt/arch/mips/arub +{ + unsigned int pend, group, ip; + volatile unsigned int *addr; ++ ++ if(cp0_cause == 0) { ++ printk("INTERRUPT(S) FIRED WHILE MASKED\n"); ++ ++ // debuging use -- figure out which interrupt(s) fired ++ cp0_cause = read_c0_cause() & CAUSEF_IP; ++ while (cp0_cause) { ++ unsigned long intr_bit; ++ unsigned int irq_nr; ++ intr_bit = (31 - rc32434_clz(cp0_cause)); ++ irq_nr = intr_bit - GROUP0_IRQ_BASE; ++ printk(" ---> MASKED IRQ %d\n",irq_nr); ++ cp0_cause &= ~(1 << intr_bit); ++ } ++ ++ return; ++ } ++ ++ + switch (mips_machtype) { + case MACH_ARUBA_AP70: + if ((ip = (cp0_cause & 0x7c00))) { @@ -490,7 +507,7 @@ diff -Nur linux-2.6.15/arch/mips/aruba/irq.c linux-2.6.15-openwrt/arch/mips/arub + case MACH_ARUBA_AP65: + case MACH_ARUBA_AP60: + default: -+ if (cp0_cause & 0x4000) { ++ if (cp0_cause & 0x4000) { // 1 << (8 +6) == irq 6 + // Misc Interrupt + group = 0; + addr = intr_group_merlot[group].base_addr; @@ -498,20 +515,26 @@ diff -Nur linux-2.6.15/arch/mips/aruba/irq.c linux-2.6.15-openwrt/arch/mips/arub + pend &= READ_MASK_MERLOT(addr); // only unmasked interrupts + /* handle one misc interrupt at a time */ + while (pend) { -+ unsigned int intr_bit, irq_nr; -+ intr_bit = pend ^ (pend - 1); -+ irq_nr = ((31 - rc32434_clz(pend)) + GROUP0_IRQ_BASE); ++ unsigned long intr_bit; ++ unsigned int irq_nr; ++ ++ intr_bit = (31 - rc32434_clz(pend)); ++ irq_nr = intr_bit + GROUP0_IRQ_BASE; ++ + do_IRQ(irq_nr, regs); -+ pend &= ~intr_bit; ++ pend &= ~(1 << intr_bit); + } + } -+ if (cp0_cause & 0x3c00) { ++ if (cp0_cause & 0x3c00) { // irq 2-5 + while (cp0_cause) { -+ unsigned int intr_bit, irq_nr; -+ intr_bit = cp0_cause ^ (cp0_cause - 1); -+ irq_nr = ((31 - rc32434_clz(cp0_cause)) - GROUP0_IRQ_BASE); ++ unsigned long intr_bit; ++ unsigned int irq_nr; ++ ++ intr_bit = (31 - rc32434_clz(cp0_cause)); ++ irq_nr = intr_bit - GROUP0_IRQ_BASE; ++ + do_IRQ(irq_nr, regs); -+ cp0_cause &= ~intr_bit; ++ cp0_cause &= ~(1 << intr_bit); + } + } + break;