um: fix possible race on task->mm
authorAnton Vorontsov <anton.vorontsov@linaro.org>
Thu, 31 May 2012 23:26:25 +0000 (16:26 -0700)
committerLinus Torvalds <torvalds@linux-foundation.org>
Fri, 1 Jun 2012 00:49:30 +0000 (17:49 -0700)
Checking for task->mm is dangerous as ->mm might disappear (exit_mm()
assigns NULL under task_lock(), so tasklist lock is not enough).

We can't use get_task_mm()/mmput() pair as mmput() might sleep, so let's
take the task lock while we care about its mm.

Note that we should also use find_lock_task_mm() to check all process'
threads for a valid mm, but for uml we'll do it in a separate patch.

Signed-off-by: Anton Vorontsov <anton.vorontsov@linaro.org>
Cc: Richard Weinberger <richard@nod.at>
Cc: Oleg Nesterov <oleg@redhat.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
arch/um/kernel/reboot.c

index 66d754c46e7b048492f7587fdcbe08fed2b4630d..1411f4e79f9a667d2bb5457badbbc73189a23780 100644 (file)
@@ -25,10 +25,13 @@ static void kill_off_processes(void)
 
                read_lock(&tasklist_lock);
                for_each_process(p) {
-                       if (p->mm == NULL)
+                       task_lock(p);
+                       if (!p->mm) {
+                               task_unlock(p);
                                continue;
-
+                       }
                        pid = p->mm->context.id.u.pid;
+                       task_unlock(p);
                        os_kill_ptraced_process(pid, 1);
                }
                read_unlock(&tasklist_lock);