summaryrefslogtreecommitdiff
path: root/mm/slob.c
diff options
context:
space:
mode:
authorNick Piggin <nickpiggin@yahoo.com.au>2009-03-16 21:00:28 +1100
committerPekka Enberg <penberg@cs.helsinki.fi>2009-03-23 10:40:45 +0200
commit6fb8f424393025674fde7869b59f485d1e352182 (patch)
tree1ba7de5a6c9cba9cf3c3e57b2355b56cb5eb670f /mm/slob.c
parentb578f3fcca1e78624dfb5f358776e63711d7fda2 (diff)
downloadlwn-6fb8f424393025674fde7869b59f485d1e352182.tar.gz
lwn-6fb8f424393025674fde7869b59f485d1e352182.zip
slob: fix lockup in slob_free()
Don't hold SLOB lock when freeing the page. Reduces lock hold width. See the following thread for discussion of the bug: http://marc.info/?l=linux-kernel&m=123709983214143&w=2 Reported-by: Ingo Molnar <mingo@elte.hu> Acked-by: Matt Mackall <mpm@selenic.com> Signed-off-by: Nick Piggin <npiggin@suse.de> Signed-off-by: Pekka Enberg <penberg@cs.helsinki.fi>
Diffstat (limited to 'mm/slob.c')
-rw-r--r--mm/slob.c3
1 files changed, 2 insertions, 1 deletions
diff --git a/mm/slob.c b/mm/slob.c
index bf7e8fc3aed8..f901653707a4 100644
--- a/mm/slob.c
+++ b/mm/slob.c
@@ -393,10 +393,11 @@ static void slob_free(void *block, int size)
/* Go directly to page allocator. Do not pass slob allocator */
if (slob_page_free(sp))
clear_slob_page_free(sp);
+ spin_unlock_irqrestore(&slob_lock, flags);
clear_slob_page(sp);
free_slob_page(sp);
free_page((unsigned long)b);
- goto out;
+ return;
}
if (!slob_page_free(sp)) {