diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2011-05-22 22:03:03 -0700 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2011-05-22 22:03:03 -0700 |
commit | 4b382d0643603819e8b48da58efc254cabc22574 (patch) | |
tree | 71ae8bc989af8a0137c065e4741a76dc4e4d4cb8 /drivers/md/md.c | |
parent | wireless: fix fatal kernel-doc error + warning in mac80211.h (diff) | |
parent | md: allow resync_start to be set while an array is active. (diff) | |
download | linux-dev-4b382d0643603819e8b48da58efc254cabc22574.tar.xz linux-dev-4b382d0643603819e8b48da58efc254cabc22574.zip |
Merge branch 'for-linus' of git://neil.brown.name/md
* 'for-linus' of git://neil.brown.name/md:
md: allow resync_start to be set while an array is active.
md/raid10: reformat some loops with less indenting.
md/raid10: remove unused variable.
md/raid10: make more use of 'slot' in raid10d.
md/raid10: some tidying up in fix_read_error
md/raid1: improve handling of pages allocated for write-behind.
md/raid1: try fix_sync_read_error before process_checks.
md/raid1: tidy up new functions: process_checks and fix_sync_read_error.
md/raid1: split out two sub-functions from sync_request_write
md: make error_handler functions more uniform and correct.
md/multipath: discard ->working_disks in favour of ->degraded
md/raid1: clean up read_balance.
md: simplify raid10 read_balance
md/bitmap: fix saving of events_cleared and other state.
md: reject a re-add request that cannot be honoured.
md: Fix race when creating a new md device.
Diffstat (limited to 'drivers/md/md.c')
-rw-r--r-- | drivers/md/md.c | 23 |
1 files changed, 19 insertions, 4 deletions
diff --git a/drivers/md/md.c b/drivers/md/md.c index 7d6f7f18a920..aa640a85bb21 100644 --- a/drivers/md/md.c +++ b/drivers/md/md.c @@ -3324,7 +3324,7 @@ resync_start_store(mddev_t *mddev, const char *buf, size_t len) char *e; unsigned long long n = simple_strtoull(buf, &e, 10); - if (mddev->pers) + if (mddev->pers && !test_bit(MD_RECOVERY_FROZEN, &mddev->recovery)) return -EBUSY; if (cmd_match(buf, "none")) n = MaxSector; @@ -4347,13 +4347,19 @@ static int md_alloc(dev_t dev, char *name) disk->fops = &md_fops; disk->private_data = mddev; disk->queue = mddev->queue; + blk_queue_flush(mddev->queue, REQ_FLUSH | REQ_FUA); /* Allow extended partitions. This makes the * 'mdp' device redundant, but we can't really * remove it now. */ disk->flags |= GENHD_FL_EXT_DEVT; - add_disk(disk); mddev->gendisk = disk; + /* As soon as we call add_disk(), another thread could get + * through to md_open, so make sure it doesn't get too far + */ + mutex_lock(&mddev->open_mutex); + add_disk(disk); + error = kobject_init_and_add(&mddev->kobj, &md_ktype, &disk_to_dev(disk)->kobj, "%s", "md"); if (error) { @@ -4367,8 +4373,7 @@ static int md_alloc(dev_t dev, char *name) if (mddev->kobj.sd && sysfs_create_group(&mddev->kobj, &md_bitmap_group)) printk(KERN_DEBUG "pointless warning\n"); - - blk_queue_flush(mddev->queue, REQ_FLUSH | REQ_FUA); + mutex_unlock(&mddev->open_mutex); abort: mutex_unlock(&disks_mutex); if (!error && mddev->kobj.sd) { @@ -5211,6 +5216,16 @@ static int add_new_disk(mddev_t * mddev, mdu_disk_info_t *info) } else super_types[mddev->major_version]. validate_super(mddev, rdev); + if ((info->state & (1<<MD_DISK_SYNC)) && + (!test_bit(In_sync, &rdev->flags) || + rdev->raid_disk != info->raid_disk)) { + /* This was a hot-add request, but events doesn't + * match, so reject it. + */ + export_rdev(rdev); + return -EINVAL; + } + if (test_bit(In_sync, &rdev->flags)) rdev->saved_raid_disk = rdev->raid_disk; else |