aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorDan Williams <dan.j.williams@intel.com>2008-01-08 18:32:53 -0500
committerLinus Torvalds <torvalds@woody.linux-foundation.org>2008-01-08 19:10:35 -0500
commit0f94e87cdeaaac9f0f9a28a5dd2a5070b87cd3e8 (patch)
tree6c35efe23f565d27bec046d8eed3c5901e1d0090 /drivers
parent5b7741b3325d0d94c88b2ad46657a536890aaa2f (diff)
md: fix data corruption when a degraded raid5 array is reshaped
We currently do not wait for the block from the missing device to be computed from parity before copying data to the new stripe layout. The change in the raid6 code is not techincally needed as we don't delay data block recovery in the same way for raid6 yet. But making the change now is safer long-term. This bug exists in 2.6.23 and 2.6.24-rc Cc: <stable@kernel.org> Signed-off-by: Dan Williams <dan.j.williams@intel.com> Acked-by: Neil Brown <neilb@suse.de> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/md/raid5.c6
1 files changed, 4 insertions, 2 deletions
diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c
index a5aad8cad843..e8c8157b02fc 100644
--- a/drivers/md/raid5.c
+++ b/drivers/md/raid5.c
@@ -2865,7 +2865,8 @@ static void handle_stripe5(struct stripe_head *sh)
2865 md_done_sync(conf->mddev, STRIPE_SECTORS, 1); 2865 md_done_sync(conf->mddev, STRIPE_SECTORS, 1);
2866 } 2866 }
2867 2867
2868 if (s.expanding && s.locked == 0) 2868 if (s.expanding && s.locked == 0 &&
2869 !test_bit(STRIPE_OP_COMPUTE_BLK, &sh->ops.pending))
2869 handle_stripe_expansion(conf, sh, NULL); 2870 handle_stripe_expansion(conf, sh, NULL);
2870 2871
2871 if (sh->ops.count) 2872 if (sh->ops.count)
@@ -3067,7 +3068,8 @@ static void handle_stripe6(struct stripe_head *sh, struct page *tmp_page)
3067 md_done_sync(conf->mddev, STRIPE_SECTORS, 1); 3068 md_done_sync(conf->mddev, STRIPE_SECTORS, 1);
3068 } 3069 }
3069 3070
3070 if (s.expanding && s.locked == 0) 3071 if (s.expanding && s.locked == 0 &&
3072 !test_bit(STRIPE_OP_COMPUTE_BLK, &sh->ops.pending))
3071 handle_stripe_expansion(conf, sh, &r6s); 3073 handle_stripe_expansion(conf, sh, &r6s);
3072 3074
3073 spin_unlock(&sh->lock); 3075 spin_unlock(&sh->lock);