diff options
| author | NeilBrown <neilb@suse.de> | 2006-12-10 05:20:49 -0500 |
|---|---|---|
| committer | Linus Torvalds <torvalds@woody.osdl.org> | 2006-12-10 12:57:21 -0500 |
| commit | b875e531fc82db592d6093594593d5cafde0a1cd (patch) | |
| tree | 4bf23fcee1a1d1675339ea7e5d671dde6dd8641f | |
| parent | 5248861511d6aae4997a5aa7152824d87587b0b6 (diff) | |
[PATCH] md: fix innocuous bug in raid6 stripe_to_pdidx
stripe_to_pdidx finds the index of the parity disk for a given stripe. It
assumes raid5 in that it uses "disks-1" to determine the number of data disks.
This is incorrect for raid6 but fortunately the two usages cancel each other
out. The only way that 'data_disks' affects the calculation of pd_idx in
raid5_compute_sector is when it is divided into the sector number. But as
that sector number is calculated by multiplying in the wrong value of
'data_disks' the division produces the right value.
So it is innocuous but needs to be fixed.
Also change the calculation of raid_disks in compute_blocknr to make it
more obviously correct (it seems at first to always use disks-1 too).
Signed-off-by: Neil Brown <neilb@suse.de>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
| -rw-r--r-- | drivers/md/raid5.c | 10 |
1 files changed, 6 insertions, 4 deletions
diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c index 2e676e33744c..d855f9f59b02 100644 --- a/drivers/md/raid5.c +++ b/drivers/md/raid5.c | |||
| @@ -823,7 +823,8 @@ static sector_t raid5_compute_sector(sector_t r_sector, unsigned int raid_disks, | |||
| 823 | static sector_t compute_blocknr(struct stripe_head *sh, int i) | 823 | static sector_t compute_blocknr(struct stripe_head *sh, int i) |
| 824 | { | 824 | { |
| 825 | raid5_conf_t *conf = sh->raid_conf; | 825 | raid5_conf_t *conf = sh->raid_conf; |
| 826 | int raid_disks = sh->disks, data_disks = raid_disks - 1; | 826 | int raid_disks = sh->disks; |
| 827 | int data_disks = raid_disks - conf->max_degraded; | ||
| 827 | sector_t new_sector = sh->sector, check; | 828 | sector_t new_sector = sh->sector, check; |
| 828 | int sectors_per_chunk = conf->chunk_size >> 9; | 829 | int sectors_per_chunk = conf->chunk_size >> 9; |
| 829 | sector_t stripe; | 830 | sector_t stripe; |
| @@ -859,7 +860,6 @@ static sector_t compute_blocknr(struct stripe_head *sh, int i) | |||
| 859 | } | 860 | } |
| 860 | break; | 861 | break; |
| 861 | case 6: | 862 | case 6: |
| 862 | data_disks = raid_disks - 2; | ||
| 863 | if (i == raid6_next_disk(sh->pd_idx, raid_disks)) | 863 | if (i == raid6_next_disk(sh->pd_idx, raid_disks)) |
| 864 | return 0; /* It is the Q disk */ | 864 | return 0; /* It is the Q disk */ |
| 865 | switch (conf->algorithm) { | 865 | switch (conf->algorithm) { |
| @@ -1355,8 +1355,10 @@ static int stripe_to_pdidx(sector_t stripe, raid5_conf_t *conf, int disks) | |||
| 1355 | int pd_idx, dd_idx; | 1355 | int pd_idx, dd_idx; |
| 1356 | int chunk_offset = sector_div(stripe, sectors_per_chunk); | 1356 | int chunk_offset = sector_div(stripe, sectors_per_chunk); |
| 1357 | 1357 | ||
| 1358 | raid5_compute_sector(stripe*(disks-1)*sectors_per_chunk | 1358 | raid5_compute_sector(stripe * (disks - conf->max_degraded) |
| 1359 | + chunk_offset, disks, disks-1, &dd_idx, &pd_idx, conf); | 1359 | *sectors_per_chunk + chunk_offset, |
| 1360 | disks, disks - conf->max_degraded, | ||
| 1361 | &dd_idx, &pd_idx, conf); | ||
| 1360 | return pd_idx; | 1362 | return pd_idx; |
| 1361 | } | 1363 | } |
| 1362 | 1364 | ||
