|
@@ -890,17 +890,17 @@ static void allow_barrier(struct r1conf *conf)
|
|
|
wake_up(&conf->wait_barrier);
|
|
|
}
|
|
|
|
|
|
-static void freeze_array(struct r1conf *conf)
|
|
|
+static void freeze_array(struct r1conf *conf, int extra)
|
|
|
{
|
|
|
/* stop syncio and normal IO and wait for everything to
|
|
|
* go quite.
|
|
|
* We increment barrier and nr_waiting, and then
|
|
|
- * wait until nr_pending match nr_queued+1
|
|
|
+ * wait until nr_pending match nr_queued+extra
|
|
|
* This is called in the context of one normal IO request
|
|
|
* that has failed. Thus any sync request that might be pending
|
|
|
* will be blocked by nr_pending, and we need to wait for
|
|
|
* pending IO requests to complete or be queued for re-try.
|
|
|
- * Thus the number queued (nr_queued) plus this request (1)
|
|
|
+ * Thus the number queued (nr_queued) plus this request (extra)
|
|
|
* must match the number of pending IOs (nr_pending) before
|
|
|
* we continue.
|
|
|
*/
|
|
@@ -908,7 +908,7 @@ static void freeze_array(struct r1conf *conf)
|
|
|
conf->barrier++;
|
|
|
conf->nr_waiting++;
|
|
|
wait_event_lock_irq_cmd(conf->wait_barrier,
|
|
|
- conf->nr_pending == conf->nr_queued+1,
|
|
|
+ conf->nr_pending == conf->nr_queued+extra,
|
|
|
conf->resync_lock,
|
|
|
flush_pending_writes(conf));
|
|
|
spin_unlock_irq(&conf->resync_lock);
|
|
@@ -1568,8 +1568,8 @@ static int raid1_add_disk(struct mddev *mddev, struct md_rdev *rdev)
|
|
|
* we wait for all outstanding requests to complete.
|
|
|
*/
|
|
|
synchronize_sched();
|
|
|
- raise_barrier(conf);
|
|
|
- lower_barrier(conf);
|
|
|
+ freeze_array(conf, 0);
|
|
|
+ unfreeze_array(conf);
|
|
|
clear_bit(Unmerged, &rdev->flags);
|
|
|
}
|
|
|
md_integrity_add_rdev(rdev, mddev);
|
|
@@ -1619,11 +1619,11 @@ static int raid1_remove_disk(struct mddev *mddev, struct md_rdev *rdev)
|
|
|
*/
|
|
|
struct md_rdev *repl =
|
|
|
conf->mirrors[conf->raid_disks + number].rdev;
|
|
|
- raise_barrier(conf);
|
|
|
+ freeze_array(conf, 0);
|
|
|
clear_bit(Replacement, &repl->flags);
|
|
|
p->rdev = repl;
|
|
|
conf->mirrors[conf->raid_disks + number].rdev = NULL;
|
|
|
- lower_barrier(conf);
|
|
|
+ unfreeze_array(conf);
|
|
|
clear_bit(WantReplacement, &rdev->flags);
|
|
|
} else
|
|
|
clear_bit(WantReplacement, &rdev->flags);
|
|
@@ -2240,7 +2240,7 @@ static void handle_read_error(struct r1conf *conf, struct r1bio *r1_bio)
|
|
|
* frozen
|
|
|
*/
|
|
|
if (mddev->ro == 0) {
|
|
|
- freeze_array(conf);
|
|
|
+ freeze_array(conf, 1);
|
|
|
fix_read_error(conf, r1_bio->read_disk,
|
|
|
r1_bio->sector, r1_bio->sectors);
|
|
|
unfreeze_array(conf);
|
|
@@ -3020,7 +3020,7 @@ static int raid1_reshape(struct mddev *mddev)
|
|
|
return -ENOMEM;
|
|
|
}
|
|
|
|
|
|
- raise_barrier(conf);
|
|
|
+ freeze_array(conf, 0);
|
|
|
|
|
|
/* ok, everything is stopped */
|
|
|
oldpool = conf->r1bio_pool;
|
|
@@ -3051,7 +3051,7 @@ static int raid1_reshape(struct mddev *mddev)
|
|
|
conf->raid_disks = mddev->raid_disks = raid_disks;
|
|
|
mddev->delta_disks = 0;
|
|
|
|
|
|
- lower_barrier(conf);
|
|
|
+ unfreeze_array(conf);
|
|
|
|
|
|
set_bit(MD_RECOVERY_NEEDED, &mddev->recovery);
|
|
|
md_wakeup_thread(mddev->thread);
|