Hi,
We (MAAS upstream) are having some issues figuring out how to
effectively detect the architecture of a system booting using U-Boot
pxelinux emulation in order to send back an appropriate kernel and
initrd.
In short, we'd like a mechanism that is separate from the DHCP vendor
option which I believe is the only way to differentiate at the moment.
I proposed an alternative mechanism in
https://launchpad.net/bugs/1041092 (description copied below) and it was
suggested to me that I could get feedback from this list.
If this mechanism is appropriate and we can get vendor consensus on it,
then I can continue and implement the other end of it in MAAS. If it is
not suitable then I'd love to hear about alternatives. Either way, I'd
really like to move within a couple of weeks so that I can make our
12.10 release in October.
Without a non-DHCP mechanism for architecture detection, MAAS will be
stuck having to be configured for homogeneous architecture clusters
only, which would be unfortunte.
What do you think? The full text of the bug is below.
Thanks,
Robie
An outcome of a recent MAAS-related sprint is the conclusion that MAAS needs
to be able to operate in an environment where it cannot control the DHCP
server.
This means that we cannot rely on the ability to differentiate architectures
based on ISC dhcpd.conf conditional statements on vendor-class-identifier
setting alternate next-server filenames as we are doing at the moment (see bug
927781 for details of this mechanism).
Instead we need some other way for MAAS to detect the architecture of the
booting system in order to send it the correct architecture kernel/initrd.
If this doesn't happen, then MAAS will have to resort to guessing based on MAC
addresses supplied by vendors, or the user entering in the information on a
per-MAC basis manually, or the user nominating an entire MAAS cluster as
homogeneous on a particular architecture. None of these options are ideal.
Instead, I propose the following minor change to U-Boot to enable architecture
detection outside of DHCP.
The original (Intel) pxelinux.0 falls back through MAC addresses, IP address
and subnets and then to "default". Prior to U-Boot pxelinux emulation, a TFTP
server could assume that sending an i386 kernel would always work.
pxelinux emulation on other architectures breaks this assumption. So I propose
that all alternative architecture pxelinux emulators (eg. U-Boot) fall back to
"default.<arch>-<subarch>" and then "default.<arch>" before further falling
back to "default" as usual.
<arch> and <subarch> must be defined in a new pxelinux emulator namespace, and
MAAS will consequently need to map this namespace to Ubuntu's architecture and
kernel flavour names. But to start with, they'll probably match 1-1.
So: default.arm-highbank default.arm-armadaxp default.arm-omap4
For this proposed change to work, we need all vendors to take this up. I think
the change would be trivial, but I would appreciate feedback from U-Boot
maintainers and vendors before we commit to this direction.
I'm not sure if this has been discussed before, but in working with
various ARM systems (Panda, Trim Slice, Highbank, etc.) I have noticed
that there is little consistency in the load addresses for kernel,
initrd, and device tree, or the commands and devices used. While it may
not be practical to always use the same physical addresses, it seems it
might be possible to set some 'standard' U-Boot environment variables or
macros to provide a more consistent user experience when working on
various boards from different vendors.
Some vendors already provide U-Boot environment variables for the load
addresses, and some for the load commands themselves, but I have not
found much consistency between them. One example is the Genesi Efika MX
(mx51), which provides:
${loadcmd}
${kerneladdr}
${ramdiskaddr}
By providing the kernel and initrd U-Boot images in a boot.scr, you can
load and boot the desired kernel with no other board specific knowledge
(specific addresses or devices).
Highbank provides some similar load address definitions, but with
different names, i.e.,
${ramdisk_addr_r}
${kernel_addr_r}
${fdt_addr_r}
Other boards provide similar features, including some (e.g., Trim-Slice)
that 'scan' through a list of devices until a boot.scr is found, load
it, and then boot using that script, but the load addresses are literals.
Does anyone else think it would be useful to include a 'standard' set of
such definitions in U-Boot (default) that could be used to abstract the
board/vendor specific details and provide a more consistent user
experience? If so, could this list be used to help define such a set,
and encourage its use across ARM systems and distros?
If this has already been discussed, perhaps someone could provide a link
to the thread.
Thank you for your consideration,
d.marlin
I was considering extending the kernel command-line option
root=PARTUUID= to also support MBR (NT disk signatures). I was thinking
of a syntax along the lines of:
root=PARTUUID=UUUUUUUU-PP[/PARTNROFF=%d]
... where UUUUUUUU is the hex representation of the NT disk signature,
and PP is the hex representation of the partition number. Like GPT,
/PARTNROFF could be used too if desired.
Related, I was thinking of changing struct partition_meta_info's uuid
field to be a string, so that it could simply be strcmp'd against the
UUID value on the kernel command-line. That way, the type of the UUID is
irrelevant.
Does anyone have any objection to that?
The reason I aim for that syntax rather than say:
root=MBRSIG=UUUUUUUU-PP[/PARTNROFF=%d]
... is to allow boot-loaders (e.g. U-Boot on ARM) to store just the
partition ID in a variable, and prepend all the Linux-specific stuff on
the front, e.g.
# For GPT:
setenv kernel_part_uuid b2f82cda-2535-4779-b467-094a210fbae7
# For MBR:
setenv kernel_part_uuid UUUUUUUU-PP
In fact, those hard-coded statements would probably be replaced with a
run-time command:
part uuid mmc 0:1 kernel_part_uuid
# Then in a common script:
setenv bootargs root=PARTUUID=${kernel_part_uuid}
Otherwise, the value of the uuid variable (or result of the "part uuid"
command) would need to prepend the PARTUUID= or MBRSIG= to the "uuid"
variable's value, and that's probably Linux-specific rather than part of
a generic UUID for the partition.