Back in February this year I added Multiboot support to NetBSD/i386. Unfortunately, the implemenation was quite hackish because it required the application of a patch to GRUB-Legacy: the code used the "a.out kludge" present in the Multiboot specification which this bootloader incorrectly omitted in ELF kernels; the patch fixed this issue. However, this prevented booting NetBSD with mainstream GRUB builds (those used by all Linux distributions), thus making this feature mostly useless.

The need for the "a.out kludge" came from two different problems:
  • The kernel's ELF image was incorrectly linked because it did not set the correct physical load addresses for the segments it contained, thus GRUB could not load it because it thought there was not enough memory.
    The "a.out kludge" was used here to tell the boot loader which was the correct address to load the binary image into. Pavel Cahyna fixed this issue back in May, removing the need for the hack in this specific case.
  • The native boot loader constructs a minimal ELF image that contains the kernel symbol table (ksyms) and sticks it just after the BSS space in memory. GRUB did not do this so the NetBSD kernel resorted to manually creating this image itself based on the data passed in by GRUB. In order to be successful, some space was reserved after the BSS section by using the "a.out kludge" (tricking the bootloader to think that this section was larger than it actually was) so that the kernel's bootstrapping process could freely access it. Pavel's fix did not address this problem so, when booting a NetBSD Multiboot kernel with an unpatched GRUB, ksyms did not work.
I've now finally fixed this long-standing issue appropriately. All the code to create the minimal ELF image is gone and instead the kernel simply moves the data passed in by GRUB to a memory region that is available after bootstrapping. Then, it uses a custom function (ksyms_init_explicit instead of ksyms_init) which does not need any ELF headers to initialize the ksyms.

The results are much clearer and less error-prone code as well as the ability to boot NetBSD straight from a stock GRUB installation! Keep in mind that this will go into 4.0, so setting up dual-boot machines will be easier than ever :-)

I've prepared a couple of screenshots for your pleasure. First, a look at the configuration used to boot a Multiboot-enabled NetBSD kernel:
And then a look at the messages printed by the kernel as well as a demonstration that ksyms work by invoking a backtrace in the debugger (ddb):

Go to posts index

Comments from the original Blogger-hosted post: