genirq: threaded irq handlers review fixups
Delta patch to address the review comments. - Implement warning when IRQ_WAKE_THREAD is requested and no thread handler installed - coding style fixes Pointed-out-by: Christoph Hellwig <hch@infradead.org> Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
This commit is contained in:
parent
935bd5b971
commit
f48fe81e5b
3 changed files with 33 additions and 15 deletions
|
@ -63,10 +63,12 @@
|
|||
* Bits used by threaded handlers:
|
||||
* IRQTF_RUNTHREAD - signals that the interrupt handler thread should run
|
||||
* IRQTF_DIED - handler thread died
|
||||
* IRQTF_WARNED - warning "IRQ_WAKE_THREAD w/o thread_fn" has been printed
|
||||
*/
|
||||
enum {
|
||||
IRQTF_RUNTHREAD,
|
||||
IRQTF_DIED,
|
||||
IRQTF_WARNED,
|
||||
};
|
||||
|
||||
typedef irqreturn_t (*irq_handler_t)(int, void *);
|
||||
|
|
|
@ -338,6 +338,15 @@ irqreturn_t no_action(int cpl, void *dev_id)
|
|||
return IRQ_NONE;
|
||||
}
|
||||
|
||||
static void warn_no_thread(unsigned int irq, struct irqaction *action)
|
||||
{
|
||||
if (test_and_set_bit(IRQTF_WARNED, &action->thread_flags))
|
||||
return;
|
||||
|
||||
printk(KERN_WARNING "IRQ %d device %s returned IRQ_WAKE_THREAD "
|
||||
"but no thread function available.", irq, action->name);
|
||||
}
|
||||
|
||||
/**
|
||||
* handle_IRQ_event - irq action chain handler
|
||||
* @irq: the interrupt number
|
||||
|
@ -360,6 +369,21 @@ irqreturn_t handle_IRQ_event(unsigned int irq, struct irqaction *action)
|
|||
|
||||
switch (ret) {
|
||||
case IRQ_WAKE_THREAD:
|
||||
/*
|
||||
* Set result to handled so the spurious check
|
||||
* does not trigger.
|
||||
*/
|
||||
ret = IRQ_HANDLED;
|
||||
|
||||
/*
|
||||
* Catch drivers which return WAKE_THREAD but
|
||||
* did not set up a thread function
|
||||
*/
|
||||
if (unlikely(!action->thread_fn)) {
|
||||
warn_no_thread(irq, action);
|
||||
break;
|
||||
}
|
||||
|
||||
/*
|
||||
* Wake up the handler thread for this
|
||||
* action. In case the thread crashed and was
|
||||
|
@ -374,11 +398,6 @@ irqreturn_t handle_IRQ_event(unsigned int irq, struct irqaction *action)
|
|||
wake_up_process(action->thread);
|
||||
}
|
||||
|
||||
/*
|
||||
* Set it to handled so the spurious check
|
||||
* does not trigger.
|
||||
*/
|
||||
ret = IRQ_HANDLED;
|
||||
/* Fall through to add to randomness */
|
||||
case IRQ_HANDLED:
|
||||
status |= action->flags;
|
||||
|
|
|
@ -407,19 +407,16 @@ int __irq_set_trigger(struct irq_desc *desc, unsigned int irq,
|
|||
return ret;
|
||||
}
|
||||
|
||||
static inline int irq_thread_should_run(struct irqaction *action)
|
||||
{
|
||||
return test_and_clear_bit(IRQTF_RUNTHREAD, &action->thread_flags);
|
||||
}
|
||||
|
||||
static int irq_wait_for_interrupt(struct irqaction *action)
|
||||
{
|
||||
while (!kthread_should_stop()) {
|
||||
set_current_state(TASK_INTERRUPTIBLE);
|
||||
if (irq_thread_should_run(action)) {
|
||||
|
||||
if (test_and_clear_bit(IRQTF_RUNTHREAD,
|
||||
&action->thread_flags)) {
|
||||
__set_current_state(TASK_RUNNING);
|
||||
return 0;
|
||||
} else
|
||||
}
|
||||
schedule();
|
||||
}
|
||||
return -1;
|
||||
|
|
Loading…
Reference in a new issue