Skip site navigation (1)Skip section navigation (2)
Date:      Tue, 4 Aug 2015 08:11:34 +0200
From:      Ganael Laplanche <ganael.laplanche@corp.ovh.com>
To:        Ian Lepore <ian@freebsd.org>
Cc:        Eric McCorkle <emc2@metricspace.net>, <freebsd-hackers@freebsd.org>
Subject:   Re: Boot loader arguments (was: ZFS support for EFI)
Message-ID:  <201508040811.34730.ganael.laplanche@corp.ovh.com>
In-Reply-To: <1438627213.70393.19.camel@freebsd.org>
References:  <201508031532.44478.ganael.laplanche@corp.ovh.com> <1438627213.70393.19.camel@freebsd.org>

next in thread | previous in thread | raw e-mail | index | archive | help
On Monday, August 03, 2015 08:40:13 PM Ian Lepore wrote:

Hi Ian,

> It looks like your patches got scrubbed off somehow.

Yes, sorry, here they are, inline :

This one sets the environment reading argv[] :

8<--------------------------------->8
=2D-- sys/boot/efi/loader/main.c.orig     2015-07-28 09:31:08.648856000 +02=
00
+++ sys/boot/efi/loader/main.c  2015-07-30 09:02:42.695337864 +0200
@@ -67,7 +67,10 @@
        char vendor[128];
        EFI_LOADED_IMAGE *img;
        EFI_GUID *guid;
=2D       int i;
+       int i, j;
+
+#define MAX_ARG_LEN 128
+       char var[MAX_ARG_LEN];
=20
        /*
         * XXX Chicken-and-egg problem; we want to have console output
@@ -83,6 +86,17 @@
        }
=20
        /*
+        * Initialize environment using argv[] after converting from UCS-2 =
to=20
ASCII
+        */
+       for (i =3D 1; i < argc; i++) {
+               for(j =3D 0; ((char)argv[i][j] !=3D 0) && (j < (MAX_ARG_LEN=
 - 1));=20
j++)
+                       var[j] =3D (char)argv[i][j];
+               var[j] =3D 0;
+               putenv(var);
+               /* printf("main: added environment variable: %s\n", var); */
+       }
+
+       /*
         * March through the device switch probing for things.
         */
        for (i =3D 0; devsw[i] !=3D NULL; i++)
8<--------------------------------->8

and this one overrides the BOOTP root-path if dhcp.root-path.override is se=
t :

8<--------------------------------->8
=2D-- lib/libstand/bootp.c.orig   2015-07-29 08:38:28.970379976 +0200
+++ lib/libstand/bootp.c        2015-07-29 09:08:59.747891922 +0200
@@ -383,8 +383,20 @@
                        bcopy(cp, &rootip.s_addr, sizeof(swapip.s_addr));
                }
                if (tag =3D=3D TAG_ROOTPATH) {
=2D                       strncpy(rootpath, (char *)cp, sizeof(rootpath));
=2D                       rootpath[size] =3D '\0';
+                       /*
+                        * XXX Set dhcp.root-path.override to force rootpath
+                        * locally and ignore BOOTP vendor tag 17 (root-pat=
h)
+                        */
+                       char *rootpath_o =3D getenv("dhcp.root-path.overrid=
e");
+                       if (rootpath_o =3D=3D NULL) {
+                               strncpy(rootpath, (char *)cp,=20
sizeof(rootpath));
+                               rootpath[size] =3D '\0';
+                               /* printf("vend_rfc1048: rootpath set from=
=20
BOOTP: %s\n", rootpath); */
+                       }
+                       else {
+                               strcpy(rootpath, rootpath_o);
+                               /* printf("vend_rfc1048: rootpath set to:=20
%s\n", rootpath); */
+                       }
                }
                if (tag =3D=3D TAG_HOSTNAME) {
                        strncpy(hostname, (char *)cp, sizeof(hostname));
8<--------------------------------->8

Again, those patches would probably need improvements, as there is (for=20
example) no sanitization done before setenv().

Anyway, this allows to chainload the loader and pass your root-path (and an=
y=20
other variable) this way (e.g. with iPXE) :

#!ipxe
chain http://path.to/loader.efi dhcp.root-
path.override=3Dserver_ip:/path/to/root some_other_var=3Dvalue

> I recently tweaked loader(8) to make it easier for the data normally
> gathered from bootp/dhcp to be provided "from the environment" --
> whatever that may mean for a given flavor of loader.  The network code
> already had some provisions for setting the required variables before
> the first attempt to do network access, my changes just shuffled things
> around a bit to make it easier to parse a "rootpath" var formatted as
> "rootserverip:/path/stuff" into the existing global vars.
>=20
> See r283062 for those changes, and r283066 for an example of obtaining
> the values from "somewhere" (in this case the u-boot environment) and
> setting the corresponding global vars for netbooting.

Interesting, thanks for the pointers. U-boot might be useful here, I have t=
o=20
check that.

> The comments in r283066 might be a useful guide to implementing the same
> kind of thing based on parsing an EFI command line.

Yep, that would probably be a cleaner way to go.

> It may be that my changes didn't cover all situations and more tweaking
> is needed, especially if the situation is that some data should come
> from bootp/dhcp and other data should be overridden from the command
> line.

Yes, that's *exactly* the case we are facing, where the root-path given by=
=20
BOOTP cannot always be used :/

Best regards,

=2D-=20
Gana=EBl LAPLANCHE <ganael.laplanche@corp.ovh.com>



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