diff options
author | Greg Kroah-Hartman <gregkh@suse.de> | 2011-08-19 11:03:38 -0700 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@suse.de> | 2011-08-19 11:03:38 -0700 |
commit | 50a60b8c17c2894c415c7374ab373a03b0bf2003 (patch) | |
tree | b37ae6c4aca7eb5c324b8786cb7763529c17a4be | |
parent | d51f2c3010997fc36384496eca4f79fe8e63af3e (diff) | |
download | stable-queue-50a60b8c17c2894c415c7374ab373a03b0bf2003.tar.gz |
3.0 patches
-rw-r--r-- | queue-3.0/loop-fix-deadlock-when-sysfs-and-loop_clr_fd-race-against.patch | 77 | ||||
-rw-r--r-- | queue-3.0/series | 1 |
2 files changed, 78 insertions, 0 deletions
diff --git a/queue-3.0/loop-fix-deadlock-when-sysfs-and-loop_clr_fd-race-against.patch b/queue-3.0/loop-fix-deadlock-when-sysfs-and-loop_clr_fd-race-against.patch new file mode 100644 index 0000000000..97fead97ea --- /dev/null +++ b/queue-3.0/loop-fix-deadlock-when-sysfs-and-loop_clr_fd-race-against.patch @@ -0,0 +1,77 @@ +From 05eb0f252b04aa94ace0794f73d56c6a02351d80 Mon Sep 17 00:00:00 2001 +From: Kay Sievers <kay.sievers@vrfy.org> +Date: Sun, 31 Jul 2011 22:21:35 +0200 +Subject: loop: fix deadlock when sysfs and LOOP_CLR_FD race against + each other + +From: Kay Sievers <kay.sievers@vrfy.org> + +commit 05eb0f252b04aa94ace0794f73d56c6a02351d80 upstream. + +LOOP_CLR_FD takes lo->lo_ctl_mutex and tries to remove the loop sysfs +files. Sysfs calls show() and waits for lo->lo_ctl_mutex. LOOP_CLR_FD +waits for show() to finish to remove the sysfs file. + + cat /sys/class/block/loop0/loop/backing_file + mutex_lock_nested+0x176/0x350 + ? loop_attr_do_show_backing_file+0x2f/0xd0 [loop] + ? loop_attr_do_show_backing_file+0x2f/0xd0 [loop] + loop_attr_do_show_backing_file+0x2f/0xd0 [loop] + dev_attr_show+0x1b/0x60 + ? sysfs_read_file+0x86/0x1a0 + ? __get_free_pages+0x12/0x50 + sysfs_read_file+0xaf/0x1a0 + + ioctl(LOOP_CLR_FD): + wait_for_common+0x12c/0x180 + ? try_to_wake_up+0x2a0/0x2a0 + wait_for_completion+0x18/0x20 + sysfs_deactivate+0x178/0x180 + ? sysfs_addrm_finish+0x43/0x70 + ? sysfs_addrm_start+0x1d/0x20 + sysfs_addrm_finish+0x43/0x70 + sysfs_hash_and_remove+0x85/0xa0 + sysfs_remove_group+0x59/0x100 + loop_clr_fd+0x1dc/0x3f0 [loop] + lo_ioctl+0x223/0x7a0 [loop] + +Instead of taking the lo_ctl_mutex from sysfs code, take the inner +lo->lo_lock, to protect the access to the backing_file data. + +Thanks to Tejun for help debugging and finding a solution. + +Cc: Milan Broz <mbroz@redhat.com> +Cc: Tejun Heo <tj@kernel.org> +Signed-off-by: Kay Sievers <kay.sievers@vrfy.org> +Signed-off-by: Jens Axboe <jaxboe@fusionio.com> +Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de> + +--- + drivers/block/loop.c | 6 ++++-- + 1 file changed, 4 insertions(+), 2 deletions(-) + +--- a/drivers/block/loop.c ++++ b/drivers/block/loop.c +@@ -750,10 +750,10 @@ static ssize_t loop_attr_backing_file_sh + ssize_t ret; + char *p = NULL; + +- mutex_lock(&lo->lo_ctl_mutex); ++ spin_lock_irq(&lo->lo_lock); + if (lo->lo_backing_file) + p = d_path(&lo->lo_backing_file->f_path, buf, PAGE_SIZE - 1); +- mutex_unlock(&lo->lo_ctl_mutex); ++ spin_unlock_irq(&lo->lo_lock); + + if (IS_ERR_OR_NULL(p)) + ret = PTR_ERR(p); +@@ -1007,7 +1007,9 @@ static int loop_clr_fd(struct loop_devic + + kthread_stop(lo->lo_thread); + ++ spin_lock_irq(&lo->lo_lock); + lo->lo_backing_file = NULL; ++ spin_unlock_irq(&lo->lo_lock); + + loop_release_xfer(lo); + lo->transfer = NULL; diff --git a/queue-3.0/series b/queue-3.0/series index c473522f40..a18651fede 100644 --- a/queue-3.0/series +++ b/queue-3.0/series @@ -11,3 +11,4 @@ nfsv4.1-fix-the-callback-highest_used_slotid-behaviour.patch nfsv4.1-return-nfs4err_badsession-to-callbacks-during.patch x86-mtrr-lock-stop-machine-during-mtrr-rendezvous-sequence.patch btrfs-detect-wether-a-device-supports-discard.patch +loop-fix-deadlock-when-sysfs-and-loop_clr_fd-race-against.patch |