* [PATCH] irq: Fix race condition when stopping the irq thread
@ 2011-12-01 11:55 Ido Yariv
2011-12-01 21:23 ` Thomas Gleixner
2011-12-02 10:59 ` [tip:irq/urgent] genirq: " tip-bot for Ido Yariv
0 siblings, 2 replies; 3+ messages in thread
From: Ido Yariv @ 2011-12-01 11:55 UTC (permalink / raw)
To: Thomas Gleixner, linux-kernel; +Cc: Ido Yariv
In irq_wait_for_interrupt(), the should_stop member is verified before
setting the task's state to TASK_INTERRUPTIBLE and calling schedule().
In case kthread_stop sets should_stop and wakes up the process after
should_stop is checked by the irq thread but before the task's state is
changed, the irq thread might never exit:
kthread_stop irq_wait_for_interrupt
------------ ----------------------
...
... while (!kthread_should_stop()) {
kthread->should_stop = 1;
wake_up_process(k);
wait_for_completion(&kthread->exited);
...
set_current_state(TASK_INTERRUPTIBLE);
...
schedule();
}
...
Fix this by checking if the thread should stop after modifying the
task's state.
Signed-off-by: Ido Yariv <ido@wizery.com>
Cc: stable@kernel.org
---
kernel/irq/manage.c | 6 +++++-
1 files changed, 5 insertions(+), 1 deletions(-)
diff --git a/kernel/irq/manage.c b/kernel/irq/manage.c
index 0e2b179..3194d5e 100644
--- a/kernel/irq/manage.c
+++ b/kernel/irq/manage.c
@@ -631,7 +631,11 @@ static int irq_wait_for_interrupt(struct irqaction *action)
__set_current_state(TASK_RUNNING);
return 0;
}
- schedule();
+
+ if (!kthread_should_stop())
+ schedule();
+ else
+ __set_current_state(TASK_RUNNING);
}
return -1;
}
--
1.7.7.3
^ permalink raw reply [flat|nested] 3+ messages in thread
* Re: [PATCH] irq: Fix race condition when stopping the irq thread
2011-12-01 11:55 [PATCH] irq: Fix race condition when stopping the irq thread Ido Yariv
@ 2011-12-01 21:23 ` Thomas Gleixner
2011-12-02 10:59 ` [tip:irq/urgent] genirq: " tip-bot for Ido Yariv
1 sibling, 0 replies; 3+ messages in thread
From: Thomas Gleixner @ 2011-12-01 21:23 UTC (permalink / raw)
To: Ido Yariv; +Cc: linux-kernel
On Thu, 1 Dec 2011, Ido Yariv wrote:
> In irq_wait_for_interrupt(), the should_stop member is verified before
> setting the task's state to TASK_INTERRUPTIBLE and calling schedule().
> In case kthread_stop sets should_stop and wakes up the process after
> should_stop is checked by the irq thread but before the task's state is
> changed, the irq thread might never exit:
>
> kthread_stop irq_wait_for_interrupt
> ------------ ----------------------
>
> ...
> ... while (!kthread_should_stop()) {
> kthread->should_stop = 1;
> wake_up_process(k);
> wait_for_completion(&kthread->exited);
> ...
> set_current_state(TASK_INTERRUPTIBLE);
>
> ...
>
> schedule();
> }
> ...
>
> Fix this by checking if the thread should stop after modifying the
> task's state.
Good catch! I restructure it to:
--- tip.orig/kernel/irq/manage.c
+++ tip/kernel/irq/manage.c
@@ -623,8 +623,9 @@ static irqreturn_t irq_nested_primary_ha
static int irq_wait_for_interrupt(struct irqaction *action)
{
+ set_current_state(TASK_INTERRUPTIBLE);
+
while (!kthread_should_stop()) {
- set_current_state(TASK_INTERRUPTIBLE);
if (test_and_clear_bit(IRQTF_RUNTHREAD,
&action->thread_flags)) {
@@ -632,7 +633,9 @@ static int irq_wait_for_interrupt(struct
return 0;
}
schedule();
+ set_current_state(TASK_INTERRUPTIBLE);
}
+ __set_current_state(TASK_RUNNING);
return -1;
}
That saves us the extra conditional in the loop.
Thanks,
tglx
^ permalink raw reply [flat|nested] 3+ messages in thread
* [tip:irq/urgent] genirq: Fix race condition when stopping the irq thread
2011-12-01 11:55 [PATCH] irq: Fix race condition when stopping the irq thread Ido Yariv
2011-12-01 21:23 ` Thomas Gleixner
@ 2011-12-02 10:59 ` tip-bot for Ido Yariv
1 sibling, 0 replies; 3+ messages in thread
From: tip-bot for Ido Yariv @ 2011-12-02 10:59 UTC (permalink / raw)
To: linux-tip-commits; +Cc: linux-kernel, hpa, mingo, ido, tglx
Commit-ID: 550acb19269d65f32e9ac4ddb26c2b2070e37f1c
Gitweb: http://git.kernel.org/tip/550acb19269d65f32e9ac4ddb26c2b2070e37f1c
Author: Ido Yariv <ido@wizery.com>
AuthorDate: Thu, 1 Dec 2011 13:55:08 +0200
Committer: Thomas Gleixner <tglx@linutronix.de>
CommitDate: Fri, 2 Dec 2011 11:54:24 +0100
genirq: Fix race condition when stopping the irq thread
In irq_wait_for_interrupt(), the should_stop member is verified before
setting the task's state to TASK_INTERRUPTIBLE and calling schedule().
In case kthread_stop sets should_stop and wakes up the process after
should_stop is checked by the irq thread but before the task's state
is changed, the irq thread might never exit:
kthread_stop irq_wait_for_interrupt
------------ ----------------------
...
... while (!kthread_should_stop()) {
kthread->should_stop = 1;
wake_up_process(k);
wait_for_completion(&kthread->exited);
...
set_current_state(TASK_INTERRUPTIBLE);
...
schedule();
}
Fix this by checking if the thread should stop after modifying the
task's state.
[ tglx: Simplified it a bit ]
Signed-off-by: Ido Yariv <ido@wizery.com>
Link: http://lkml.kernel.org/r/1322740508-22640-1-git-send-email-ido@wizery.com
Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
Cc: stable@kernel.org
---
kernel/irq/manage.c | 5 ++++-
1 files changed, 4 insertions(+), 1 deletions(-)
diff --git a/kernel/irq/manage.c b/kernel/irq/manage.c
index 0e2b179..1da999f 100644
--- a/kernel/irq/manage.c
+++ b/kernel/irq/manage.c
@@ -623,8 +623,9 @@ static irqreturn_t irq_nested_primary_handler(int irq, void *dev_id)
static int irq_wait_for_interrupt(struct irqaction *action)
{
+ set_current_state(TASK_INTERRUPTIBLE);
+
while (!kthread_should_stop()) {
- set_current_state(TASK_INTERRUPTIBLE);
if (test_and_clear_bit(IRQTF_RUNTHREAD,
&action->thread_flags)) {
@@ -632,7 +633,9 @@ static int irq_wait_for_interrupt(struct irqaction *action)
return 0;
}
schedule();
+ set_current_state(TASK_INTERRUPTIBLE);
}
+ __set_current_state(TASK_RUNNING);
return -1;
}
^ permalink raw reply [flat|nested] 3+ messages in thread
end of thread, other threads:[~2011-12-02 11:00 UTC | newest]
Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-12-01 11:55 [PATCH] irq: Fix race condition when stopping the irq thread Ido Yariv
2011-12-01 21:23 ` Thomas Gleixner
2011-12-02 10:59 ` [tip:irq/urgent] genirq: " tip-bot for Ido Yariv
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
Powered by JetHome