aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/md
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/md')
-rw-r--r--drivers/md/dm-crypt.c11
-rw-r--r--drivers/md/dm-ioctl.c9
-rw-r--r--drivers/md/dm-raid1.c22
-rw-r--r--drivers/md/dm-round-robin.c2
-rw-r--r--drivers/md/dm.c4
-rw-r--r--drivers/md/md.c11
-rw-r--r--drivers/md/multipath.c2
-rw-r--r--drivers/md/raid1.c4
-rw-r--r--drivers/md/raid10.c4
-rw-r--r--drivers/md/raid5.c2
10 files changed, 47 insertions, 24 deletions
diff --git a/drivers/md/dm-crypt.c b/drivers/md/dm-crypt.c
index a625576fdeeb..08a40f4e4f60 100644
--- a/drivers/md/dm-crypt.c
+++ b/drivers/md/dm-crypt.c
@@ -915,8 +915,6 @@ static int crypt_status(struct dm_target *ti, status_type_t type,
915 char *result, unsigned int maxlen) 915 char *result, unsigned int maxlen)
916{ 916{
917 struct crypt_config *cc = (struct crypt_config *) ti->private; 917 struct crypt_config *cc = (struct crypt_config *) ti->private;
918 const char *cipher;
919 const char *chainmode = NULL;
920 unsigned int sz = 0; 918 unsigned int sz = 0;
921 919
922 switch (type) { 920 switch (type) {
@@ -925,14 +923,11 @@ static int crypt_status(struct dm_target *ti, status_type_t type,
925 break; 923 break;
926 924
927 case STATUSTYPE_TABLE: 925 case STATUSTYPE_TABLE:
928 cipher = crypto_blkcipher_name(cc->tfm);
929
930 chainmode = cc->chainmode;
931
932 if (cc->iv_mode) 926 if (cc->iv_mode)
933 DMEMIT("%s-%s-%s ", cipher, chainmode, cc->iv_mode); 927 DMEMIT("%s-%s-%s ", cc->cipher, cc->chainmode,
928 cc->iv_mode);
934 else 929 else
935 DMEMIT("%s-%s ", cipher, chainmode); 930 DMEMIT("%s-%s ", cc->cipher, cc->chainmode);
936 931
937 if (cc->key_size > 0) { 932 if (cc->key_size > 0) {
938 if ((maxlen - sz) < ((cc->key_size << 1) + 1)) 933 if ((maxlen - sz) < ((cc->key_size << 1) + 1))
diff --git a/drivers/md/dm-ioctl.c b/drivers/md/dm-ioctl.c
index d13bb15a8a02..4510ad8f971c 100644
--- a/drivers/md/dm-ioctl.c
+++ b/drivers/md/dm-ioctl.c
@@ -606,9 +606,14 @@ static struct hash_cell *__find_device_hash_cell(struct dm_ioctl *param)
606 return __get_name_cell(param->name); 606 return __get_name_cell(param->name);
607 607
608 md = dm_get_md(huge_decode_dev(param->dev)); 608 md = dm_get_md(huge_decode_dev(param->dev));
609 if (md) 609 if (!md)
610 mdptr = dm_get_mdptr(md); 610 goto out;
611 611
612 mdptr = dm_get_mdptr(md);
613 if (!mdptr)
614 dm_put(md);
615
616out:
612 return mdptr; 617 return mdptr;
613} 618}
614 619
diff --git a/drivers/md/dm-raid1.c b/drivers/md/dm-raid1.c
index 659224cb7c53..48a653b3f518 100644
--- a/drivers/md/dm-raid1.c
+++ b/drivers/md/dm-raid1.c
@@ -24,6 +24,7 @@
24 24
25static struct workqueue_struct *_kmirrord_wq; 25static struct workqueue_struct *_kmirrord_wq;
26static struct work_struct _kmirrord_work; 26static struct work_struct _kmirrord_work;
27static DECLARE_WAIT_QUEUE_HEAD(_kmirrord_recovery_stopped);
27 28
28static inline void wake(void) 29static inline void wake(void)
29{ 30{
@@ -83,6 +84,7 @@ struct region_hash {
83 struct list_head *buckets; 84 struct list_head *buckets;
84 85
85 spinlock_t region_lock; 86 spinlock_t region_lock;
87 atomic_t recovery_in_flight;
86 struct semaphore recovery_count; 88 struct semaphore recovery_count;
87 struct list_head clean_regions; 89 struct list_head clean_regions;
88 struct list_head quiesced_regions; 90 struct list_head quiesced_regions;
@@ -191,6 +193,7 @@ static int rh_init(struct region_hash *rh, struct mirror_set *ms,
191 193
192 spin_lock_init(&rh->region_lock); 194 spin_lock_init(&rh->region_lock);
193 sema_init(&rh->recovery_count, 0); 195 sema_init(&rh->recovery_count, 0);
196 atomic_set(&rh->recovery_in_flight, 0);
194 INIT_LIST_HEAD(&rh->clean_regions); 197 INIT_LIST_HEAD(&rh->clean_regions);
195 INIT_LIST_HEAD(&rh->quiesced_regions); 198 INIT_LIST_HEAD(&rh->quiesced_regions);
196 INIT_LIST_HEAD(&rh->recovered_regions); 199 INIT_LIST_HEAD(&rh->recovered_regions);
@@ -382,6 +385,8 @@ static void rh_update_states(struct region_hash *rh)
382 rh->log->type->clear_region(rh->log, reg->key); 385 rh->log->type->clear_region(rh->log, reg->key);
383 rh->log->type->complete_resync_work(rh->log, reg->key, 1); 386 rh->log->type->complete_resync_work(rh->log, reg->key, 1);
384 dispatch_bios(rh->ms, &reg->delayed_bios); 387 dispatch_bios(rh->ms, &reg->delayed_bios);
388 if (atomic_dec_and_test(&rh->recovery_in_flight))
389 wake_up_all(&_kmirrord_recovery_stopped);
385 up(&rh->recovery_count); 390 up(&rh->recovery_count);
386 mempool_free(reg, rh->region_pool); 391 mempool_free(reg, rh->region_pool);
387 } 392 }
@@ -502,11 +507,21 @@ static int __rh_recovery_prepare(struct region_hash *rh)
502 507
503static void rh_recovery_prepare(struct region_hash *rh) 508static void rh_recovery_prepare(struct region_hash *rh)
504{ 509{
505 while (!down_trylock(&rh->recovery_count)) 510 /* Extra reference to avoid race with rh_stop_recovery */
511 atomic_inc(&rh->recovery_in_flight);
512
513 while (!down_trylock(&rh->recovery_count)) {
514 atomic_inc(&rh->recovery_in_flight);
506 if (__rh_recovery_prepare(rh) <= 0) { 515 if (__rh_recovery_prepare(rh) <= 0) {
516 atomic_dec(&rh->recovery_in_flight);
507 up(&rh->recovery_count); 517 up(&rh->recovery_count);
508 break; 518 break;
509 } 519 }
520 }
521
522 /* Drop the extra reference */
523 if (atomic_dec_and_test(&rh->recovery_in_flight))
524 wake_up_all(&_kmirrord_recovery_stopped);
510} 525}
511 526
512/* 527/*
@@ -1177,6 +1192,11 @@ static void mirror_postsuspend(struct dm_target *ti)
1177 struct dirty_log *log = ms->rh.log; 1192 struct dirty_log *log = ms->rh.log;
1178 1193
1179 rh_stop_recovery(&ms->rh); 1194 rh_stop_recovery(&ms->rh);
1195
1196 /* Wait for all I/O we generated to complete */
1197 wait_event(_kmirrord_recovery_stopped,
1198 !atomic_read(&ms->rh.recovery_in_flight));
1199
1180 if (log->type->suspend && log->type->suspend(log)) 1200 if (log->type->suspend && log->type->suspend(log))
1181 /* FIXME: need better error handling */ 1201 /* FIXME: need better error handling */
1182 DMWARN("log suspend failed"); 1202 DMWARN("log suspend failed");
diff --git a/drivers/md/dm-round-robin.c b/drivers/md/dm-round-robin.c
index c5a16c550122..6f9fcd4db9b5 100644
--- a/drivers/md/dm-round-robin.c
+++ b/drivers/md/dm-round-robin.c
@@ -136,7 +136,7 @@ static int rr_add_path(struct path_selector *ps, struct path *path,
136 136
137 path->pscontext = pi; 137 path->pscontext = pi;
138 138
139 list_add(&pi->list, &s->valid_paths); 139 list_add_tail(&pi->list, &s->valid_paths);
140 140
141 return 0; 141 return 0;
142} 142}
diff --git a/drivers/md/dm.c b/drivers/md/dm.c
index b5764a86c8b5..fc4f743f3b53 100644
--- a/drivers/md/dm.c
+++ b/drivers/md/dm.c
@@ -1285,7 +1285,7 @@ int dm_suspend(struct mapped_device *md, int do_lockfs)
1285 down(&md->suspend_lock); 1285 down(&md->suspend_lock);
1286 1286
1287 if (dm_suspended(md)) 1287 if (dm_suspended(md))
1288 goto out; 1288 goto out_unlock;
1289 1289
1290 map = dm_get_table(md); 1290 map = dm_get_table(md);
1291 1291
@@ -1361,6 +1361,8 @@ out:
1361 } 1361 }
1362 1362
1363 dm_table_put(map); 1363 dm_table_put(map);
1364
1365out_unlock:
1364 up(&md->suspend_lock); 1366 up(&md->suspend_lock);
1365 return r; 1367 return r;
1366} 1368}
diff --git a/drivers/md/md.c b/drivers/md/md.c
index 7daa7b1e145f..8cbf9c9df1c3 100644
--- a/drivers/md/md.c
+++ b/drivers/md/md.c
@@ -2003,6 +2003,7 @@ static mdk_rdev_t *md_import_device(dev_t newdev, int super_format, int super_mi
2003 kobject_init(&rdev->kobj); 2003 kobject_init(&rdev->kobj);
2004 2004
2005 rdev->desc_nr = -1; 2005 rdev->desc_nr = -1;
2006 rdev->saved_raid_disk = -1;
2006 rdev->flags = 0; 2007 rdev->flags = 0;
2007 rdev->data_offset = 0; 2008 rdev->data_offset = 0;
2008 rdev->sb_events = 0; 2009 rdev->sb_events = 0;
@@ -3199,6 +3200,7 @@ static int do_md_run(mddev_t * mddev)
3199 3200
3200 mddev->changed = 1; 3201 mddev->changed = 1;
3201 md_new_event(mddev); 3202 md_new_event(mddev);
3203 kobject_uevent(&mddev->gendisk->kobj, KOBJ_CHANGE);
3202 return 0; 3204 return 0;
3203} 3205}
3204 3206
@@ -4044,11 +4046,8 @@ static int update_size(mddev_t *mddev, unsigned long size)
4044 return -EBUSY; 4046 return -EBUSY;
4045 ITERATE_RDEV(mddev,rdev,tmp) { 4047 ITERATE_RDEV(mddev,rdev,tmp) {
4046 sector_t avail; 4048 sector_t avail;
4047 if (rdev->sb_offset > rdev->data_offset) 4049 avail = rdev->size * 2;
4048 avail = (rdev->sb_offset*2) - rdev->data_offset; 4050
4049 else
4050 avail = get_capacity(rdev->bdev->bd_disk)
4051 - rdev->data_offset;
4052 if (fit && (size == 0 || size > avail/2)) 4051 if (fit && (size == 0 || size > avail/2))
4053 size = avail/2; 4052 size = avail/2;
4054 if (avail < ((sector_t)size << 1)) 4053 if (avail < ((sector_t)size << 1))
@@ -4487,6 +4486,7 @@ static int md_thread(void * arg)
4487 * many dirty RAID5 blocks. 4486 * many dirty RAID5 blocks.
4488 */ 4487 */
4489 4488
4489 current->flags |= PF_NOFREEZE;
4490 allow_signal(SIGKILL); 4490 allow_signal(SIGKILL);
4491 while (!kthread_should_stop()) { 4491 while (!kthread_should_stop()) {
4492 4492
@@ -4503,7 +4503,6 @@ static int md_thread(void * arg)
4503 test_bit(THREAD_WAKEUP, &thread->flags) 4503 test_bit(THREAD_WAKEUP, &thread->flags)
4504 || kthread_should_stop(), 4504 || kthread_should_stop(),
4505 thread->timeout); 4505 thread->timeout);
4506 try_to_freeze();
4507 4506
4508 clear_bit(THREAD_WAKEUP, &thread->flags); 4507 clear_bit(THREAD_WAKEUP, &thread->flags);
4509 4508
diff --git a/drivers/md/multipath.c b/drivers/md/multipath.c
index a6260f0e3b9e..14da37fee37b 100644
--- a/drivers/md/multipath.c
+++ b/drivers/md/multipath.c
@@ -277,6 +277,7 @@ static void multipath_error (mddev_t *mddev, mdk_rdev_t *rdev)
277 set_bit(Faulty, &rdev->flags); 277 set_bit(Faulty, &rdev->flags);
278 set_bit(MD_CHANGE_DEVS, &mddev->flags); 278 set_bit(MD_CHANGE_DEVS, &mddev->flags);
279 conf->working_disks--; 279 conf->working_disks--;
280 mddev->degraded++;
280 printk(KERN_ALERT "multipath: IO failure on %s," 281 printk(KERN_ALERT "multipath: IO failure on %s,"
281 " disabling IO path. \n Operation continuing" 282 " disabling IO path. \n Operation continuing"
282 " on %d IO paths.\n", 283 " on %d IO paths.\n",
@@ -336,6 +337,7 @@ static int multipath_add_disk(mddev_t *mddev, mdk_rdev_t *rdev)
336 blk_queue_max_sectors(mddev->queue, PAGE_SIZE>>9); 337 blk_queue_max_sectors(mddev->queue, PAGE_SIZE>>9);
337 338
338 conf->working_disks++; 339 conf->working_disks++;
340 mddev->degraded--;
339 rdev->raid_disk = path; 341 rdev->raid_disk = path;
340 set_bit(In_sync, &rdev->flags); 342 set_bit(In_sync, &rdev->flags);
341 rcu_assign_pointer(p->rdev, rdev); 343 rcu_assign_pointer(p->rdev, rdev);
diff --git a/drivers/md/raid1.c b/drivers/md/raid1.c
index dc9d2def0270..656fae912fe3 100644
--- a/drivers/md/raid1.c
+++ b/drivers/md/raid1.c
@@ -1474,8 +1474,8 @@ static void fix_read_error(conf_t *conf, int read_disk,
1474 "raid1:%s: read error corrected " 1474 "raid1:%s: read error corrected "
1475 "(%d sectors at %llu on %s)\n", 1475 "(%d sectors at %llu on %s)\n",
1476 mdname(mddev), s, 1476 mdname(mddev), s,
1477 (unsigned long long)sect + 1477 (unsigned long long)(sect +
1478 rdev->data_offset, 1478 rdev->data_offset),
1479 bdevname(rdev->bdev, b)); 1479 bdevname(rdev->bdev, b));
1480 } 1480 }
1481 } 1481 }
diff --git a/drivers/md/raid10.c b/drivers/md/raid10.c
index 74f17a9a6ebb..7492d6033ac6 100644
--- a/drivers/md/raid10.c
+++ b/drivers/md/raid10.c
@@ -1470,8 +1470,8 @@ static void fix_read_error(conf_t *conf, mddev_t *mddev, r10bio_t *r10_bio)
1470 "raid10:%s: read error corrected" 1470 "raid10:%s: read error corrected"
1471 " (%d sectors at %llu on %s)\n", 1471 " (%d sectors at %llu on %s)\n",
1472 mdname(mddev), s, 1472 mdname(mddev), s,
1473 (unsigned long long)sect+ 1473 (unsigned long long)(sect+
1474 rdev->data_offset, 1474 rdev->data_offset),
1475 bdevname(rdev->bdev, b)); 1475 bdevname(rdev->bdev, b));
1476 1476
1477 rdev_dec_pending(rdev, mddev); 1477 rdev_dec_pending(rdev, mddev);
diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c
index e14f45780720..69c3e201fa3b 100644
--- a/drivers/md/raid5.c
+++ b/drivers/md/raid5.c
@@ -3659,7 +3659,7 @@ static void end_reshape(raid5_conf_t *conf)
3659 bdev = bdget_disk(conf->mddev->gendisk, 0); 3659 bdev = bdget_disk(conf->mddev->gendisk, 0);
3660 if (bdev) { 3660 if (bdev) {
3661 mutex_lock(&bdev->bd_inode->i_mutex); 3661 mutex_lock(&bdev->bd_inode->i_mutex);
3662 i_size_write(bdev->bd_inode, conf->mddev->array_size << 10); 3662 i_size_write(bdev->bd_inode, (loff_t)conf->mddev->array_size << 10);
3663 mutex_unlock(&bdev->bd_inode->i_mutex); 3663 mutex_unlock(&bdev->bd_inode->i_mutex);
3664 bdput(bdev); 3664 bdput(bdev);
3665 } 3665 }