diff options
author | Dan Williams <dan.j.williams@intel.com> | 2009-12-12 23:17:06 -0500 |
---|---|---|
committer | NeilBrown <neilb@suse.de> | 2009-12-13 20:57:43 -0500 |
commit | 4e59ca7da05f0d5d3ad40365c502c8b0fd24c7e3 (patch) | |
tree | d5ddc749ec13db16c1ed7a054546c2ea482c0e1e /drivers/md/md.c | |
parent | 93be75ffde6dfd1ad17cc3ff1dbd135bd711baf4 (diff) |
md: rcu_read_lock() walk of mddev->disks in md_do_sync()
Other walks of this list are either under rcu_read_lock() or the list
mutation lock (mddev_lock()). This protects against the improbable case of a
disk being removed from the array at the start of md_do_sync().
Signed-off-by: Dan Williams <dan.j.williams@intel.com>
Diffstat (limited to 'drivers/md/md.c')
-rw-r--r-- | drivers/md/md.c | 8 |
1 files changed, 6 insertions, 2 deletions
diff --git a/drivers/md/md.c b/drivers/md/md.c index 68a8a29a9012..ea64a68e9c75 100644 --- a/drivers/md/md.c +++ b/drivers/md/md.c | |||
@@ -6526,12 +6526,14 @@ void md_do_sync(mddev_t *mddev) | |||
6526 | /* recovery follows the physical size of devices */ | 6526 | /* recovery follows the physical size of devices */ |
6527 | max_sectors = mddev->dev_sectors; | 6527 | max_sectors = mddev->dev_sectors; |
6528 | j = MaxSector; | 6528 | j = MaxSector; |
6529 | list_for_each_entry(rdev, &mddev->disks, same_set) | 6529 | rcu_read_lock(); |
6530 | list_for_each_entry_rcu(rdev, &mddev->disks, same_set) | ||
6530 | if (rdev->raid_disk >= 0 && | 6531 | if (rdev->raid_disk >= 0 && |
6531 | !test_bit(Faulty, &rdev->flags) && | 6532 | !test_bit(Faulty, &rdev->flags) && |
6532 | !test_bit(In_sync, &rdev->flags) && | 6533 | !test_bit(In_sync, &rdev->flags) && |
6533 | rdev->recovery_offset < j) | 6534 | rdev->recovery_offset < j) |
6534 | j = rdev->recovery_offset; | 6535 | j = rdev->recovery_offset; |
6536 | rcu_read_unlock(); | ||
6535 | } | 6537 | } |
6536 | 6538 | ||
6537 | printk(KERN_INFO "md: %s of RAID array %s\n", desc, mdname(mddev)); | 6539 | printk(KERN_INFO "md: %s of RAID array %s\n", desc, mdname(mddev)); |
@@ -6701,12 +6703,14 @@ void md_do_sync(mddev_t *mddev) | |||
6701 | } else { | 6703 | } else { |
6702 | if (!test_bit(MD_RECOVERY_INTR, &mddev->recovery)) | 6704 | if (!test_bit(MD_RECOVERY_INTR, &mddev->recovery)) |
6703 | mddev->curr_resync = MaxSector; | 6705 | mddev->curr_resync = MaxSector; |
6704 | list_for_each_entry(rdev, &mddev->disks, same_set) | 6706 | rcu_read_lock(); |
6707 | list_for_each_entry_rcu(rdev, &mddev->disks, same_set) | ||
6705 | if (rdev->raid_disk >= 0 && | 6708 | if (rdev->raid_disk >= 0 && |
6706 | !test_bit(Faulty, &rdev->flags) && | 6709 | !test_bit(Faulty, &rdev->flags) && |
6707 | !test_bit(In_sync, &rdev->flags) && | 6710 | !test_bit(In_sync, &rdev->flags) && |
6708 | rdev->recovery_offset < mddev->curr_resync) | 6711 | rdev->recovery_offset < mddev->curr_resync) |
6709 | rdev->recovery_offset = mddev->curr_resync; | 6712 | rdev->recovery_offset = mddev->curr_resync; |
6713 | rcu_read_unlock(); | ||
6710 | } | 6714 | } |
6711 | } | 6715 | } |
6712 | set_bit(MD_CHANGE_DEVS, &mddev->flags); | 6716 | set_bit(MD_CHANGE_DEVS, &mddev->flags); |