Skip site navigation (1)Skip section navigation (2)
Date:      Sun, 12 Dec 1999 15:59:32 +0100
From:      Juergen Lock <nox@jelal.kn-bremen.de>
To:        Mike Smith <mike@smith.net.au>
Cc:        zzhang@cs.binghamton.edu, freebsd-stable@FreeBSD.ORG, freebsd-hackers@FreeBSD.ORG
Subject:   loader hacks (was: Re: easyboot far into disk)
Message-ID:  <19991212155932.A1107@saturn.kn-bremen.de>
In-Reply-To: <19991111224730.A739@saturn.kn-bremen.de>
References:  <19991107035454.B59629@saturn.kn-bremen.de> <199911071957.LAA13619@dingo.cdrom.com> <19991111224730.A739@saturn.kn-bremen.de>

next in thread | previous in thread | raw e-mail | index | archive | help
(Cc'd to -hackers because, well, it contains hacks...)

On Thu, Nov 11, 1999 at 10:47:30PM +0100, nox wrote:
> On Sun, Nov 07, 1999 at 11:57:26AM -0800, Mike Smith wrote:
> > > > Rootdev ought to work, actually.  But if you get it wrong, the loader 
> > > > will fall back to using currdev.
> > > 
> > > Hmm then thats strange.  I first tried rootdev, which didn't work, and
> > > then later currdev, which did work, and i believe i used the same value
> > > both times!  Or was rootdev fixed only recently, the boot floppies i
> > > had lying around and tested this on weren't the latest...
> > 
> > I thought rootdev was fixed a long time back.  If it's not, please tell 
> > me and I'll fix it again.  8)
> 
> Alright I finally got around testing this with a later kern.flp
> (3.3-R actually), and it still didn't work.  ...

Well i played with this once more yesterday and now i know what was
wrong:  Unlike currdev, rootdev needs a `:' at the end...  So either
I'm blind or the manpage needs fixing. :)

 I also actually started making that FAQ entry (yeah!), and then
wondered if you could also make an automagic boot floppy for a root
disk that is entirely invisible to the BIOS, like when its on a
BIOS-less (but otherwise supported) SCSI controller.  I didn't find
a way to do it with the original (-stable) loader, but when i made
this patch,

Index: biosdisk.c
===================================================================
RCS file: /home/cvs/cvs/src/sys/boot/i386/libi386/biosdisk.c,v
retrieving revision 1.20.2.7
diff -u -u -r1.20.2.7 biosdisk.c
--- biosdisk.c	1999/08/29 16:20:59	1.20.2.7
+++ biosdisk.c	1999/12/12 00:14:52
@@ -785,23 +785,45 @@
 int
 bd_getdev(struct i386_devdesc *dev)
 {
-    struct open_disk		*od;
+    struct open_disk		*od = NULL;
     int				biosdev;
     int 			major;
     int				rootdev;
     char			*nip, *cp;
     int				unitofs = 0, i, unit;
 
+    /* XXX kludge to allow the type of the root disk to be specified */
+    cp = getenv("root_disk_type");
     biosdev = bd_unit2bios(dev->d_kind.biosdisk.unit);
     DEBUG("unit %d BIOS device %d", dev->d_kind.biosdisk.unit, biosdev);
-    if (biosdev == -1)				/* not a BIOS device */
+    if (biosdev == -1) {			/* not a BIOS device */
+	int lastbiosdev;
+	/*
+	 * BIOS doesn't know about this disk, this is not an error
+	 * when root_disk_type is set unless the number is
+	 * completely bogus
+	 * (set root_disk_type=da and you may e.g. have the root
+	 * disk hanging off a BIOS-less SCSI controller...)
+	 */
+	if (!cp || dev->d_kind.biosdisk.unit < 0 ||
+	    dev->d_kind.biosdisk.unit >= 256)
+	    return(-1);
+	/*
+	 * numbering of unknown-to-BIOS units starts with the first
+	 * hard disk above the last one the BIOS saw, this is 0x80
+	 * if the BIOS only saw floppies
+	 */
+	lastbiosdev = bd_unit2bios(nbdinfo - 1);
+	biosdev = dev->d_kind.biosdisk.unit - nbdinfo +
+	    (lastbiosdev < 0x80 ? 0x80 : lastbiosdev + 1);
+    } else if (bd_opendisk(&od, dev) != 0)	/* oops, not a viable device */
 	return(-1);
-    if (bd_opendisk(&od, dev) != 0)		/* oops, not a viable device */
-	return(-1);
 
-    if (biosdev < 0x80) {
+    /* only assume floppy if root_disk_type is not set or is *fd* */
+    if ((biosdev < 0x80 && !cp) || strstr(cp, "fd")) {
 	/* floppy (or emulated floppy) or ATAPI device */
-	if (bdinfo[dev->d_kind.biosdisk.unit].bd_type == DT_ATAPI) {
+	if ((cp && !strcmp(cp, "wfd")) ||
+	    bdinfo[dev->d_kind.biosdisk.unit].bd_type == DT_ATAPI) {
 	    /* is an ATAPI disk */
 	    major = WFDMAJOR;
 	} else {
@@ -810,8 +832,10 @@
 	}
     } else {
 	/* harddisk */
-	if ((od->od_flags & BD_LABELOK) && (od->od_disklabel.d_type == DTYPE_SCSI)) {
-	    /* label OK, disk labelled as SCSI */
+	if ((cp && !strcmp(cp, "da")) ||
+	    (od && (od->od_flags & BD_LABELOK) &&
+	     (od->od_disklabel.d_type == DTYPE_SCSI))) {
+	    /* label OK or root_disk_type set, disk labelled as SCSI */
 	    major = DAMAJOR;
 	    /* check for unit number correction hint, now deprecated */
 	    if ((nip = getenv("num_ide_disks")) != NULL) {
@@ -820,23 +844,24 @@
 		if ((cp != nip) && (*cp == 0))
 		    unitofs = i;
 	    }
-	} else if ((od->od_flags & BD_LABELOK) && 
-	  (od->od_disklabel.d_type == DTYPE_DOC2K)) {
+	} else if ((cp && !strcmp(cp, "fla")) ||
+	    (od && (od->od_flags & BD_LABELOK) && 
+	     (od->od_disklabel.d_type == DTYPE_DOC2K))) {
 	    major = FLAMAJOR;
 	} else {
 	    /* assume an IDE disk */
 	    major = WDMAJOR;
 	}
     }
+    /* allow for #wd compenstation in da case */
+    unit = (biosdev & 0x7f) - unitofs;
+
     /* XXX a better kludge to set the root disk unit number */
     if ((nip = getenv("root_disk_unit")) != NULL) {
 	i = strtol(nip, &cp, 0);
 	/* check for parse error */
 	if ((cp != nip) && (*cp == 0))
 	    unit = i;
-    } else {
-/* allow for #wd compenstation in da case */
-	unit = (biosdev & 0x7f) - unitofs;
     }
 
     rootdev = MAKEBOOTDEV(major,
Index: bootinfo.c
===================================================================
RCS file: /home/cvs/cvs/src/sys/boot/i386/libi386/bootinfo.c,v
retrieving revision 1.15.2.3
diff -u -u -r1.15.2.3 bootinfo.c
--- bootinfo.c	1999/08/29 16:21:01	1.15.2.3
+++ bootinfo.c	1999/12/11 20:12:40
@@ -262,6 +262,7 @@
 
     default:
 	printf("aout_exec: WARNING - don't know how to boot from device type %d\n", rootdev->d_type);
+	return(EINVAL);
     }
     free(rootdev);
     *bootdevp = bootdevnr;

 (the last changes are actually fixes for what looked like genuine bugs,
tho they don't seem to matter much.)

 I was then able to boot from a floppy with the SCSI BIOS turned off:

	set root_disk_type=da
	set root_disk_unit=2
	set rootdev=disk0s1a:

 although when i tried a cold boot i got a panic because apparently
the kernel didn't expect to have to `start unit' some disks and wait
for them to come online.  (well it did send the start unit to one,
paniced, then the at the next boot started another... until when all
were up, so in the end the boot `just' took longer...)  Should i try
to make a proper bugreport for that or is it to be expected?

 And note how you still have to split the actual device name up
(da2s1a here) if you don't want to depend on how the BIOS numbers
the disks which often differs from the kernel. (`da' goes into
root_disk_type, `2' goes into root_disk_unit und the slice/partition
`s1a' goes into rootdev.  at least the 0 in disk0 should not matter
anymore now when both of the others are set so these three lines
could then also be generated by e.g. sysinstall without any additional
knowledge about the BIOS.)  I believe -current now also has a fix
for this although i don't know if the way its been done there would
still work with older kernels.  With this you should be able to
boot even pre-loader systems if you put the old kernel on the
floppy...

 Regards,
-- 
Juergen Lock <nox.foo@jelal.kn-bremen.de>
(remove dot foo from address to reply)


To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe freebsd-stable" in the body of the message




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?19991212155932.A1107>