Linus, 
  it is possible to start an md array from the boot command line with,
  e.g.
     md=0,/dev/something,/dev/somethingelse

  However only names recognised by name_to_kdev_t work here.  devfs
  based names do not work.
  To fix this, the follow patch moves the name lookup from __setup
  time to __init time so that the devfs routines can be called.

  This patch is largely due to Dave Cinege, though I have made a few
  improvements (particularly removing the devices array from
  md_setup_args). 

  The "#ifdef MODULE" that this patch removes it wholy within another
  "#ifdef MODULE" and so it totally pointless.

NeilBrown



--- ./drivers/md/md.c   2001/06/21 00:51:42     1.2
+++ ./drivers/md/md.c   2001/06/21 00:53:09     1.3
@@ -3638,7 +3638,7 @@
        char device_set [MAX_MD_DEVS];
        int pers[MAX_MD_DEVS];
        int chunk[MAX_MD_DEVS];
-       kdev_t devices[MAX_MD_DEVS][MD_SB_DISKS];
+       char *device_names[MAX_MD_DEVS];
 } md_setup_args md__initdata;
 
 /*
@@ -3657,14 +3657,15 @@
  *             md=n,device-list      reads a RAID superblock from the devices
  *             elements in device-list are read by name_to_kdev_t so can be
  *             a hex number or something like /dev/hda1 /dev/sdb
+ * 2001-06-03: Dave Cinege <[EMAIL PROTECTED]>
+ *             Shifted name_to_kdev_t() and related operations to md_set_drive()
+ *             for later execution. Rewrote section to make devfs compatible.
  */
-#ifndef MODULE
-extern kdev_t name_to_kdev_t(char *line) md__init;
 static int md__init md_setup(char *str)
 {
-       int minor, level, factor, fault, i=0;
-       kdev_t device;
-       char *devnames, *pername = "";
+       int minor, level, factor, fault;
+       char *pername = "";
+       char *str1 = str;
 
        if (get_option(&str, &minor) != 2) {    /* MD Number */
                printk("md: Too few arguments supplied to md=.\n");
@@ -3673,9 +3674,8 @@
        if (minor >= MAX_MD_DEVS) {
                printk ("md: Minor device number too high.\n");
                return 0;
-       } else if (md_setup_args.device_set[minor]) {
-               printk ("md: Warning - md=%d,... has been specified twice;\n"
-                       "    will discard the first definition.\n", minor);
+       } else if (md_setup_args.device_names[minor]) {
+               printk ("md: md=%d, Specified more then once. Replacing previous 
+definition.\n", minor);
        }
        switch (get_option(&str, &level)) {     /* RAID Personality */
        case 2: /* could be 0 or -1.. */
@@ -3706,53 +3706,72 @@
                }
                /* FALL THROUGH */
        case 1: /* the first device is numeric */
-               md_setup_args.devices[minor][i++] = level;
+               str = str1;
                /* FALL THROUGH */
        case 0:
                md_setup_args.pers[minor] = 0;
                pername="super-block";
        }
-       devnames = str;
-       for (; i<MD_SB_DISKS && str; i++) {
-               if ((device = name_to_kdev_t(str))) {
-                       md_setup_args.devices[minor][i] = device;
-               } else {
-                       printk ("md: Unknown device name, %s.\n", str);
-                       return 0;
-               }
-               if ((str = strchr(str, ',')) != NULL)
-                       str++;
-       }
-       if (!i) {
-               printk ("md: No devices specified for md%d?\n", minor);
-               return 0;
-       }
-
+       
        printk ("md: Will configure md%d (%s) from %s, below.\n",
-               minor, pername, devnames);
-       md_setup_args.devices[minor][i] = (kdev_t) 0;
-       md_setup_args.device_set[minor] = 1;
+               minor, pername, str);
+       md_setup_args.device_names[minor] = str;
+                       
        return 1;
 }
-#endif /* !MODULE */
 
+extern kdev_t name_to_kdev_t(char *line) md__init;
 void md__init md_setup_drive(void)
 {
        int minor, i;
        kdev_t dev;
        mddev_t*mddev;
+       kdev_t devices[MD_SB_DISKS+1];
 
        for (minor = 0; minor < MAX_MD_DEVS; minor++) {
+               int err = 0;
+               char *devname;
                mdu_disk_info_t dinfo;
 
-               int err = 0;
-               if (!md_setup_args.device_set[minor])
+               if ((devname = md_setup_args.device_names[minor]) == 0) continue;
+       
+               for (i = 0; i < MD_SB_DISKS && devname != 0; i++) {
+
+                       char *p;
+                       void *handle;
+       
+                       if ((p = strchr(devname, ',')) != NULL)
+                               *p++ = 0;
+
+                       dev = name_to_kdev_t(devname);
+                       handle = devfs_find_handle(NULL, devname, MAJOR (dev), MINOR 
+(dev),
+                                                   DEVFS_SPECIAL_BLK, 1);
+                       if (handle != 0) {
+                               unsigned major, minor;
+                               devfs_get_maj_min(handle, &major, &minor);
+                               dev = MKDEV(major, minor);
+                       }
+                       if (dev == 0) {
+                               printk ("md: Unknown device name: %s\n", devname);
+                               break;
+                       }
+                       
+                       devices[i] = dev;
+                       md_setup_args.device_set[minor] = 1;
+                       
+                       devname = p;
+               }
+               devices[i] = 0;
+               
+               if (md_setup_args.device_set[minor] == 0)
                        continue;
-               printk("md: Loading md%d.\n", minor);
+               
                if (mddev_map[minor].mddev) {
-                       printk(".. md%d already autodetected - use 
raid=noautodetect\n", minor);
+                       printk("md: Ignoring md=%d, already autodetected. (Use 
+raid=noautodetect)\n", minor);
                        continue;
                }
+               printk("md: Loading md%d: %s\n", minor, 
+md_setup_args.device_names[minor]);
+               
                mddev = alloc_mddev(MKDEV(MD_MAJOR,minor));
                if (mddev == NULL) {
                        printk("md: kmalloc failed - cannot start array %d\n", minor);
@@ -3776,7 +3795,7 @@
                        ainfo.layout = 0;
                        ainfo.chunk_size = md_setup_args.chunk[minor];
                        err = set_array_info(mddev, &ainfo);
-                       for (i = 0; !err && (dev = md_setup_args.devices[minor][i]); 
i++) {
+                       for (i = 0; !err && (dev = devices[i]); i++) {
                                dinfo.number = i;
                                dinfo.raid_disk = i;
                                dinfo.state = (1<<MD_DISK_ACTIVE)|(1<<MD_DISK_SYNC);
@@ -3790,7 +3809,7 @@
                        }
                } else {
                        /* persistent */
-                       for (i = 0; (dev = md_setup_args.devices[minor][i]); i++) {
+                       for (i = 0; (dev = devices[i]); i++) {
                                dinfo.major = MAJOR(dev);
                                dinfo.minor = MINOR(dev);
                                add_new_disk (mddev, &dinfo);
-
To unsubscribe from this list: send the line "unsubscribe linux-raid" in
the body of a message to [EMAIL PROTECTED]

Reply via email to