public inbox for linux-kernel@vger.kernel.org
 help / color / mirror / Atom feed
* [PATCH -rt][RESEND] fix preempt hardirqs on OMAP
@ 2006-12-10 16:35 Daniel Walker
  2006-12-11 19:05 ` Ingo Molnar
  0 siblings, 1 reply; 6+ messages in thread
From: Daniel Walker @ 2006-12-10 16:35 UTC (permalink / raw)
  To: mingo; +Cc: tglx, linux-kernel

This should fix hardirq threading when the chained handler disables an interrupt 
while setting IRQ_PENDING. Which happens on ARM OMAP. It also has the effect of 
re-running the interrupt on IRQ_PENDING, which would normally be handled inside
the chained handler. Since this happens inside a thread the chained handler will
just wake up the thread multiple times, leaving the thread to actually rerun the
interrupt.

Signed-Off-By: Daniel Walker <dwalker@mvista.com>

---
 kernel/irq/manage.c |   14 ++++++++++++++
 1 files changed, 14 insertions(+)

Index: linux-2.6.19/kernel/irq/manage.c
===================================================================
--- linux-2.6.19.orig/kernel/irq/manage.c
+++ linux-2.6.19/kernel/irq/manage.c
@@ -546,6 +546,7 @@ static void thread_simple_irq(irq_desc_t
 	unsigned int irq = desc - irq_desc;
 	irqreturn_t action_ret;
 
+restart:
 	if (action && !desc->depth) {
 		spin_unlock(&desc->lock);
 		action_ret = handle_IRQ_event(irq, action);
@@ -555,6 +556,19 @@ static void thread_simple_irq(irq_desc_t
 		if (!noirqdebug)
 			note_interrupt(irq, desc, action_ret);
 	}
+
+	/*
+	 * Some boards will disable an interrupt when it
+	 * sets IRQ_PENDING . So we have to remove the flag
+	 * and re-enable to handle it.
+	 */
+	if (desc->status & IRQ_PENDING) {
+		desc->status &= ~IRQ_PENDING;
+		if (desc->chip)
+			desc->chip->enable(irq);
+		goto restart;
+	}
+
 	desc->status &= ~IRQ_INPROGRESS;
 }
 
--

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH -rt][RESEND] fix preempt hardirqs on OMAP
  2006-12-10 16:35 [PATCH -rt][RESEND] fix preempt hardirqs on OMAP Daniel Walker
@ 2006-12-11 19:05 ` Ingo Molnar
  2006-12-11 19:38   ` Daniel Walker
  0 siblings, 1 reply; 6+ messages in thread
From: Ingo Molnar @ 2006-12-11 19:05 UTC (permalink / raw)
  To: Daniel Walker; +Cc: tglx, linux-kernel


* Daniel Walker <dwalker@mvista.com> wrote:

> +	/*
> +	 * Some boards will disable an interrupt when it
> +	 * sets IRQ_PENDING . So we have to remove the flag
> +	 * and re-enable to handle it.
> +	 */
> +	if (desc->status & IRQ_PENDING) {
> +		desc->status &= ~IRQ_PENDING;
> +		if (desc->chip)
> +			desc->chip->enable(irq);
> +		goto restart;
> +	}

what if the irq got disabled meanwhile? Also, chip->enable is a 
compatibility method, not something we should use in a flow handler.

	Ingo

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH -rt][RESEND] fix preempt hardirqs on OMAP
  2006-12-11 19:05 ` Ingo Molnar
@ 2006-12-11 19:38   ` Daniel Walker
  2006-12-11 19:53     ` Tony Lindgren
  2006-12-11 19:54     ` Russell King
  0 siblings, 2 replies; 6+ messages in thread
From: Daniel Walker @ 2006-12-11 19:38 UTC (permalink / raw)
  To: Ingo Molnar; +Cc: tglx, linux-kernel

On Mon, 2006-12-11 at 20:05 +0100, Ingo Molnar wrote:
> * Daniel Walker <dwalker@mvista.com> wrote:
> 
> > +	/*
> > +	 * Some boards will disable an interrupt when it
> > +	 * sets IRQ_PENDING . So we have to remove the flag
> > +	 * and re-enable to handle it.
> > +	 */
> > +	if (desc->status & IRQ_PENDING) {
> > +		desc->status &= ~IRQ_PENDING;
> > +		if (desc->chip)
> > +			desc->chip->enable(irq);
> > +		goto restart;
> > +	}
> 
> what if the irq got disabled meanwhile? Also, chip->enable is a 
> compatibility method, not something we should use in a flow handler.

I don't know how other arches deal with IRQ_PENDING, but ARM (OMAP at
least) disables the IRQ on IRQ_PENDING. The problem is that by threading
the IRQ we take some control away from the low level code, which needs
to be replaced.

I'm open to potentially removing the irq disable()->enable() cycle on
IRQ_PENDING if it's only done on OMAP. My feeling is that it's in other
ARM's which would make that change more invasive, but I haven't actually
researched that.

Daniel



^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH -rt][RESEND] fix preempt hardirqs on OMAP
  2006-12-11 19:38   ` Daniel Walker
@ 2006-12-11 19:53     ` Tony Lindgren
  2006-12-11 19:54     ` Russell King
  1 sibling, 0 replies; 6+ messages in thread
From: Tony Lindgren @ 2006-12-11 19:53 UTC (permalink / raw)
  To: Daniel Walker; +Cc: Ingo Molnar, tglx, linux-kernel

Hi,

* Daniel Walker <dwalker@mvista.com> [061211 11:41]:
> On Mon, 2006-12-11 at 20:05 +0100, Ingo Molnar wrote:
> > * Daniel Walker <dwalker@mvista.com> wrote:
> > 
> > > +	/*
> > > +	 * Some boards will disable an interrupt when it
> > > +	 * sets IRQ_PENDING . So we have to remove the flag
> > > +	 * and re-enable to handle it.
> > > +	 */
> > > +	if (desc->status & IRQ_PENDING) {
> > > +		desc->status &= ~IRQ_PENDING;
> > > +		if (desc->chip)
> > > +			desc->chip->enable(irq);
> > > +		goto restart;
> > > +	}
> > 
> > what if the irq got disabled meanwhile? Also, chip->enable is a 
> > compatibility method, not something we should use in a flow handler.
> 
> I don't know how other arches deal with IRQ_PENDING, but ARM (OMAP at
> least) disables the IRQ on IRQ_PENDING. The problem is that by threading
> the IRQ we take some control away from the low level code, which needs
> to be replaced.
> 
> I'm open to potentially removing the irq disable()->enable() cycle on
> IRQ_PENDING if it's only done on OMAP. My feeling is that it's in other
> ARM's which would make that change more invasive, but I haven't actually
> researched that.

Hmm, I wonder if this is just legacy left over from earlier when
set_irq_type() was used and the flags not passed with request_irq().
This was causing some omap gpio interrupts to trigger immediately
after request_irq().

Regards,

Tony

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH -rt][RESEND] fix preempt hardirqs on OMAP
  2006-12-11 19:38   ` Daniel Walker
  2006-12-11 19:53     ` Tony Lindgren
@ 2006-12-11 19:54     ` Russell King
  2006-12-11 19:59       ` Daniel Walker
  1 sibling, 1 reply; 6+ messages in thread
From: Russell King @ 2006-12-11 19:54 UTC (permalink / raw)
  To: Daniel Walker; +Cc: Ingo Molnar, tglx, linux-kernel

On Mon, Dec 11, 2006 at 11:38:28AM -0800, Daniel Walker wrote:
> On Mon, 2006-12-11 at 20:05 +0100, Ingo Molnar wrote:
> > * Daniel Walker <dwalker@mvista.com> wrote:
> > 
> > > +	/*
> > > +	 * Some boards will disable an interrupt when it
> > > +	 * sets IRQ_PENDING . So we have to remove the flag
> > > +	 * and re-enable to handle it.
> > > +	 */
> > > +	if (desc->status & IRQ_PENDING) {
> > > +		desc->status &= ~IRQ_PENDING;
> > > +		if (desc->chip)
> > > +			desc->chip->enable(irq);
> > > +		goto restart;
> > > +	}
> > 
> > what if the irq got disabled meanwhile? Also, chip->enable is a 
> > compatibility method, not something we should use in a flow handler.
> 
> I don't know how other arches deal with IRQ_PENDING, but ARM (OMAP at
> least) disables the IRQ on IRQ_PENDING.

Please point out where it's doing that, and I'll take a look to see
if it's doing something it shouldn't.

-- 
Russell King
 Linux kernel    2.6 ARM Linux   - http://www.arm.linux.org.uk/
 maintainer of:

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH -rt][RESEND] fix preempt hardirqs on OMAP
  2006-12-11 19:54     ` Russell King
@ 2006-12-11 19:59       ` Daniel Walker
  0 siblings, 0 replies; 6+ messages in thread
From: Daniel Walker @ 2006-12-11 19:59 UTC (permalink / raw)
  To: Russell King; +Cc: Ingo Molnar, tglx, linux-kernel

On Mon, 2006-12-11 at 19:54 +0000, Russell King wrote:

> > > what if the irq got disabled meanwhile? Also, chip->enable is a 
> > > compatibility method, not something we should use in a flow handler.
> > 
> > I don't know how other arches deal with IRQ_PENDING, but ARM (OMAP at
> > least) disables the IRQ on IRQ_PENDING.
> 
> Please point out where it's doing that, and I'll take a look to see
> if it's doing something it shouldn't.

It's in arch/arm/plat-omap/gpio.c . It uses the lowlevel function to
disable the interrupt, not chip->disable() . In gpio_irq_handler() .

Daniel


^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2006-12-11 19:59 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2006-12-10 16:35 [PATCH -rt][RESEND] fix preempt hardirqs on OMAP Daniel Walker
2006-12-11 19:05 ` Ingo Molnar
2006-12-11 19:38   ` Daniel Walker
2006-12-11 19:53     ` Tony Lindgren
2006-12-11 19:54     ` Russell King
2006-12-11 19:59       ` Daniel Walker

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