[ Upstream commit 8a713e7df3352b8d9392476e9cf29e4e185dac32 ]

Do not remain stuck forever if something goes wrong.  Using a killable
lock permits cleanup of stuck tasks and simplifies investigation.

This function is also used for /proc/pid/smaps.

Link: http://lkml.kernel.org/r/156007493160.3335.14447544314127417266.stgit@buzz
Signed-off-by: Konstantin Khlebnikov <khlebni...@yandex-team.ru>
Reviewed-by: Roman Gushchin <g...@fb.com>
Reviewed-by: Cyrill Gorcunov <gorcu...@gmail.com>
Reviewed-by: Kirill Tkhai <ktk...@virtuozzo.com>
Acked-by: Michal Hocko <mho...@suse.com>
Cc: Alexey Dobriyan <adobri...@gmail.com>
Cc: Al Viro <v...@zeniv.linux.org.uk>
Cc: Matthew Wilcox <wi...@infradead.org>
Cc: Michal Koutný <mkou...@suse.com>
Cc: Oleg Nesterov <o...@redhat.com>
Signed-off-by: Andrew Morton <a...@linux-foundation.org>
Signed-off-by: Linus Torvalds <torva...@linux-foundation.org>
Signed-off-by: Sasha Levin <sas...@kernel.org>
---
 fs/proc/task_mmu.c   | 6 +++++-
 fs/proc/task_nommu.c | 6 +++++-
 2 files changed, 10 insertions(+), 2 deletions(-)

diff --git a/fs/proc/task_mmu.c b/fs/proc/task_mmu.c
index abcd9513efff..7f84d1477b5b 100644
--- a/fs/proc/task_mmu.c
+++ b/fs/proc/task_mmu.c
@@ -166,7 +166,11 @@ static void *m_start(struct seq_file *m, loff_t *ppos)
        if (!mm || !mmget_not_zero(mm))
                return NULL;
 
-       down_read(&mm->mmap_sem);
+       if (down_read_killable(&mm->mmap_sem)) {
+               mmput(mm);
+               return ERR_PTR(-EINTR);
+       }
+
        hold_task_mempolicy(priv);
        priv->tail_vma = get_gate_vma(mm);
 
diff --git a/fs/proc/task_nommu.c b/fs/proc/task_nommu.c
index 36bf0f2e102e..7907e6419e57 100644
--- a/fs/proc/task_nommu.c
+++ b/fs/proc/task_nommu.c
@@ -211,7 +211,11 @@ static void *m_start(struct seq_file *m, loff_t *pos)
        if (!mm || !mmget_not_zero(mm))
                return NULL;
 
-       down_read(&mm->mmap_sem);
+       if (down_read_killable(&mm->mmap_sem)) {
+               mmput(mm);
+               return ERR_PTR(-EINTR);
+       }
+
        /* start from the Nth VMA */
        for (p = rb_first(&mm->mm_rb); p; p = rb_next(p))
                if (n-- == 0)
-- 
2.20.1



Reply via email to