Linux MIPS Architecture development
 help / color / mirror / Atom feed
* [PATCH] Toshiba RBHMA3100 IRQ handling
@ 2004-10-26 16:25 Pavel Kiryukhin
  0 siblings, 0 replies; only message in thread
From: Pavel Kiryukhin @ 2004-10-26 16:25 UTC (permalink / raw)
  To: linux-mips; +Cc: Pavel Kiryukhin

Hello.

   We have discovered a number of issues with IRQ handling code in 
linux/arch/mips/jmr3927/rbhma3100/irq.c.
   First, the most serious: if IRQ is get somehow disabled in its IRQ 
handler or just wasn't handled for some reason (or was nesting despite 
being masked off by jmr3927_irq_ack(), and so left unhandled) it 
shouldn't be unmasked by
jmr3927_irq_end(). This check is present for other MIPS boards but is 
still missing for RBHMA3100...
   Second, the most serious, which caused that unwanted IRQ nesting. The 
interrupt controller (IRC) registers are in the reserved KSEG2 area 
which is subject to the write buffering in the TX3927, and the interrupt 
level register (IRL) write masking off IRQ appear to get stuck in the 
write buffer until the CPU interrupts are re-enabled by do_IRQ() after 
calling jmr3927_irq_ack(), and so the IRQs were sometimes re-occuring 
while the IRQ handler was doing its stuff--the result was fatal: board 
was just quietly dying every time this was happening. Flushing the write 
buffer by reading the source status register (IRSSR) in 
[un]mask_irq_irc() fixes this; note, that the buffer flushing code was 
present in [un]mask_irq_*() for the ISA and I/O controller IRQs but was 
missing for the IRC IRQs...
   Below is the patch for 2.4 kernel, and 2.6 kernel seems to be missing 
this too!

Index: linux/arch/mips/jmr3927/rbhma3100/irq.c
===================================================================
RCS file: /home/cvs/linux/arch/mips/jmr3927/rbhma3100/irq.c,v
retrieving revision 1.2.2.6
diff -a -u -r1.2.2.6 irq.c
--- linux/arch/mips/jmr3927/rbhma3100/irq.c    16 Apr 2003 12:59:33 
-0000    1.2.2.6
+++ linux/arch/mips/jmr3927/rbhma3100/irq.c    26 Oct 2004 16:02:36 -0000
@@ -149,7 +149,8 @@
     db_assert(irq >= jmr3927_irq_base);
     db_assert(irq < jmr3927_irq_base + JMR3927_NR_IRQ_IRC + 
JMR3927_NR_IRQ_IOC);

-    jmr3927_irq_enable(irq);
+    if (!(irq_desc[irq].status & (IRQ_DISABLED | IRQ_INPROGRESS)))
+        jmr3927_irq_enable(irq);
 }

 static void jmr3927_irq_disable(unsigned int irq_nr)
@@ -234,6 +235,8 @@
     /* update IRCSR */
     tx3927_ircptr->imr = 0;
     tx3927_ircptr->imr = irc_elevel;
+    /* flush write buffer */
+    (void)tx3927_ircptr->ssr;
 }
 static void unmask_irq_irc(int irq_nr, int space_id)
 {
@@ -245,6 +248,8 @@
     /* update IRCSR */
     tx3927_ircptr->imr = 0;
     tx3927_ircptr->imr = irc_elevel;
+    /* flush write buffer */
+    (void)tx3927_ircptr->ssr;
 }

 struct tb_irq_space jmr3927_isac_irqspace = {

^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2004-10-26 16:25 UTC | newest]

Thread overview: (only message) (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2004-10-26 16:25 [PATCH] Toshiba RBHMA3100 IRQ handling Pavel Kiryukhin

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