On Sun, 28 May 2000, Benjamin Close wrote: > Hi All, > I have a raid 0 setup used primarly for speed (I know there is no > redundancy - I don't need it). However, I can't seem to get it > autodetecting the raid array at startup with the 2.3 or 2.4 kernels. Is > there something I'm missing? Autodetection doesn't work in 2.3 yet. I have a patch [attached] that fixes this issue and a few others. The patch was sent to Ingo, and either this or some other fix should hopefully appear soon in the 2.4.0-test1-acX series I guess. > > Also where would I find suitable raid tools to manually start the raid > array under these kernels. > raidstart should still work. It worked for me at least. -- ................................................................ : [EMAIL PROTECTED] : And I see the elder races, : :.........................: putrid forms of man : : Jakob Østergaard : See him rise and claim the earth, : : OZ9ABN : his downfall is at hand. : :.........................:............{Konkhra}...............:
diff -ru linux-test1/drivers/block/ll_rw_blk.c linux/drivers/block/ll_rw_blk.c --- linux-test1/drivers/block/ll_rw_blk.c Thu May 25 23:49:34 2000 +++ linux/drivers/block/ll_rw_blk.c Thu May 25 22:30:43 2000 @@ -395,6 +395,35 @@ } /* + * The nacct() variant is implemented in order to let the RAID subsystem + * correct statistics during resynchronization of arrays. + * + * After a call to drive_stat_acct(A) a following call to drive_stat_nacct(A) + * must bring back statistics counters to their values before the call to + * drive_stat_acct(A). + */ +inline void drive_stat_nacct (kdev_t dev, int rw, + unsigned long nr_sectors, int new_io) +{ + unsigned int major = MAJOR(dev); + unsigned int index; + + index = disk_index(dev); + if ((index >= DK_MAX_DISK) || (major >= DK_MAX_MAJOR)) + return; + + kstat.dk_drive[major][index] -= new_io; + if (rw == READ) { + kstat.dk_drive_rio[major][index] -= new_io; + kstat.dk_drive_rblk[major][index] -= nr_sectors; + } else if (rw == WRITE) { + kstat.dk_drive_wio[major][index] -= new_io; + kstat.dk_drive_wblk[major][index] -= nr_sectors; + } else + printk(KERN_ERR "drive_stat_nacct: cmd not R/W?\n"); +} + +/* * add-request adds a request to the linked list. * It disables interrupts (aquires the request spinlock) so that it can muck * with the request-lists in peace. Thus it should be called with no spinlocks @@ -1061,6 +1090,8 @@ }; EXPORT_SYMBOL(io_request_lock); +EXPORT_SYMBOL(drive_stat_acct); +EXPORT_SYMBOL(drive_stat_nacct); EXPORT_SYMBOL(end_that_request_first); EXPORT_SYMBOL(end_that_request_last); EXPORT_SYMBOL(blk_init_queue); diff -ru linux-test1/drivers/block/md.c linux/drivers/block/md.c --- linux-test1/drivers/block/md.c Thu May 25 23:49:34 2000 +++ linux/drivers/block/md.c Thu May 25 22:22:59 2000 @@ -2075,7 +2075,6 @@ */ void md__init autodetect_raid(void) { -#ifdef CONFIG_AUTODETECT_RAID struct gendisk *disk; mdk_rdev_t *rdev; int i; @@ -2115,7 +2114,6 @@ } autorun_devices(); -#endif } static int get_version (void * arg) @@ -3313,6 +3311,7 @@ err = blocks; goto out; } + atomic_add(blocks, &mddev->recovery_active); j += blocks; diff -ru linux-test1/drivers/block/raid1.c linux/drivers/block/raid1.c --- linux-test1/drivers/block/raid1.c Fri May 12 20:36:30 2000 +++ linux/drivers/block/raid1.c Thu May 25 23:59:54 2000 @@ -908,6 +908,7 @@ if (mbh) { q = blk_get_queue(mbh->b_rdev); generic_make_request(q, WRITE, mbh); + drive_stat_nacct(mbh->b_rdev, WRITE, +mbh->b_size/512, 0); } } } else { @@ -1103,7 +1104,16 @@ q = blk_get_queue(bh->b_rdev); generic_make_request(q, READ, bh); - drive_stat_acct(bh->b_rdev, READ, -bh->b_size/512, 0); + + /* We must assure that this access is not accounted for as + * ordinary mddev rdev access, because that would slow down + * the resync process (it would believe that someone was using + * the disks, while in fact the resync is the only thing happening). + * + * This does not work, as nr_sectors is unsigned: + * drive_stat_acct(bh->b_rdev, READ, -bh->b_size/512, 0); + */ + drive_stat_nacct(bh->b_rdev, READ, bh->b_size/512, 0); return (bsize >> 10); } Only in linux/drivers/block: raid1.c.orig diff -ru linux-test1/drivers/block/raid5.c linux/drivers/block/raid5.c --- linux-test1/drivers/block/raid5.c Thu May 25 23:56:06 2000 +++ linux/drivers/block/raid5.c Fri May 12 20:36:30 2000 @@ -1270,7 +1270,7 @@ bh->b_rdev = conf->disks[i].dev; q = blk_get_queue(bh->b_rdev); generic_make_request(q, READ, bh); - drive_stat_nacct(bh->b_rdev, READ, bh->b_size/512, 0); + drive_stat_acct(bh->b_rdev, READ, -bh->b_size/512, 0); atomic_dec(&sh->bh_old[i]->b_count); } PRINTK("handle_stripe_sync() %lu, phase READ_OLD, pending %d buffers\n", sh->sector, md_atomic_read(&sh->nr_pending)); @@ -1300,7 +1300,7 @@ bh->b_rdev = conf->spare->dev; q = blk_get_queue(bh->b_rdev); generic_make_request(q, WRITERAW, bh); - drive_stat_nacct(bh->b_rdev, WRITE, bh->b_size/512, 0); + drive_stat_acct(bh->b_rdev, WRITE, -bh->b_size/512, 0); atomic_dec(&bh->b_count); PRINTK("handle_stripe_sync() %lu, phase WRITE, pending %d buffers\n", sh->sector, md_atomic_read(&sh->nr_pending)); } @@ -1327,7 +1327,7 @@ bh->b_rdev = conf->disks[pd_idx].dev; q = blk_get_queue(bh->b_rdev); generic_make_request(q, WRITERAW, bh); - drive_stat_nacct(bh->b_rdev, WRITE, bh->b_size/512, 0); + drive_stat_acct(bh->b_rdev, WRITE, -bh->b_size/512, 0); atomic_dec(&bh->b_count); PRINTK("handle_stripe_sync() %lu phase WRITE, pending %d buffers\n", sh->sector, md_atomic_read(&sh->nr_pending)); diff -ru linux-test1/fs/partitions/check.c linux/fs/partitions/check.c --- linux-test1/fs/partitions/check.c Thu May 25 23:49:35 2000 +++ linux/fs/partitions/check.c Thu May 25 21:17:33 2000 @@ -184,6 +184,25 @@ #endif } +void add_md_partition(struct gendisk *hd, int minor, int start, int size) +{ +#ifndef CONFIG_DEVFS_FS + char buf[40]; +#endif + + hd->part[minor].start_sect = start; + hd->part[minor].nr_sects = size; + hd->part[minor].type = LINUX_RAID_PARTITION; +#ifdef CONFIG_DEVFS_FS + printk(" r%d", (minor & ((1 << hd->minor_shift) - 1))); +#else + if (hd->major >= COMPAQ_SMART2_MAJOR+0 && hd->major <= COMPAQ_SMART2_MAJOR+7) + printk(" r%d", (minor & ((1 << hd->minor_shift) - 1))); + else + printk(" %s", disk_name(hd, minor, buf)); +#endif +} + int get_hardsect_size(kdev_t dev) { if (hardsect_size[MAJOR(dev)] != NULL) diff -ru linux-test1/fs/partitions/check.h linux/fs/partitions/check.h --- linux-test1/fs/partitions/check.h Thu Feb 17 00:42:06 2000 +++ linux/fs/partitions/check.h Thu May 25 21:16:32 2000 @@ -3,6 +3,7 @@ * description. */ void add_gd_partition(struct gendisk *hd, int minor, int start, int size); +void add_md_partition(struct gendisk *hd, int minor, int start, int size); /* * Get the default block size for this device diff -ru linux-test1/fs/partitions/msdos.c linux/fs/partitions/msdos.c --- linux-test1/fs/partitions/msdos.c Thu May 25 23:49:35 2000 +++ linux/fs/partitions/msdos.c Thu May 25 21:16:08 2000 @@ -436,8 +436,12 @@ for (i=1 ; i<=4 ; minor++,i++,p++) { if (!NR_SECTS(p)) continue; - add_gd_partition(hd, minor, first_sector+START_SECT(p)*sector_size, - NR_SECTS(p)*sector_size); + if(SYS_IND(p) == LINUX_RAID_PARTITION) + add_md_partition(hd, minor, +first_sector+START_SECT(p)*sector_size, + NR_SECTS(p)*sector_size); + else + add_gd_partition(hd, minor, +first_sector+START_SECT(p)*sector_size, + NR_SECTS(p)*sector_size); if (is_extended_partition(p)) { printk(" <"); /* diff -ru linux-test1/include/linux/blkdev.h linux/include/linux/blkdev.h --- linux-test1/include/linux/blkdev.h Tue May 23 23:19:37 2000 +++ linux/include/linux/blkdev.h Thu May 25 22:18:50 2000 @@ -165,5 +165,7 @@ extern void drive_stat_acct (kdev_t dev, int rw, unsigned long nr_sectors, int new_io); +extern void drive_stat_nacct (kdev_t dev, int rw, + unsigned long nr_sectors, int new_io); #endif