The startup header

Updated: April 19, 2023

The startup header (or boot header) structure is defined in startup.h.

This header file is located in the /src/hardware/startup/lib/public/sys/ directory in the BSP. The structure is named startup_header, is 256 bytes, and its members are populated by mkifs when the bootable image is built. The IPL and/or startup code examine the members of the structure to learn about the contents of the image and how to use it. These members include:

signature, version, flags1, flags2, header_size, machine, startup_vaddr, paddr_bias, image_paddr, ram_paddr, ram_size, startup_size, stored_size, imagefs_paddr, imagefs_size, preboot_size, zero0, zero[3], info[48]

The table below lists the startup_header members and describes their uses. The “Used by” column indicates which components use the member: the IPL, the startup code, both, or N/A.
Member Type Description Used by
signature _Uint32t

The signature field is the first 32 bits of the header. It is used to identify the header, and always contains 0x00FF7EEB in native byte order.

Platforms that can be either big-endian or little-endian (bi-endian) typically have a hardware strap that sets the board's endianness. The signature member must be set appropriately for the selected endianness.

IPL
version _Uint16t Version of mkifs that made the image. IPL
flags1 _Uint8t

flags1 is single-byte to ensure that it's endian-neutral. The following values are defined for flags1 (flags2 is currently not used):

STARTUP_HDR_FLAGS1_VIRTUAL
If this flag is set, the OS is to run with the Memory Management Unit (MMU) enabled.
Note: You should always specify a virtual system, by using the virtual= attribute in your buildfile, which then sets the STARTUP_HDR_FLAGS1_VIRTUAL flag.
STARTUP_HDR_FLAGS1_BIGENDIAN
If this flag is set, the IPL is configured for a big-endian processor. If it isn't set, the IPL is configured for a little-endian processor.
The IPL should always examine this flag to check that the endianness is correctly set for the processor.
STARTUP_HDR_FLAGS1_COMPRESS_NONE
The image isn't compressed.
STARTUP_HDR_FLAGS1_COMPRESS_ZLIB
The image is compressed using libz (gzip).
STARTUP_HDR_FLAGS1_COMPRESS_LZO
The image is compressed with liblzo.
STARTUP_HDR_FLAGS1_COMPRESS_UCL
The image is compressed with libucl. This format is chosen when using the [+compress] attribute in the mkifs build script.
Note:
  • The STARTUP_HDR_FLAGS1_COMPRESS_* constants enumerate compression types. They may set more than one bit, so they aren't strictly flags.
  • The standard startup-* programs are built to understand only the UCL compression method. However, you can adjust the SUPPORT_CMP_* macro definitions in startup/lib/uncompress.c to change to one of the other supported compression methods.
IPL and Startup
flags2 _Uint8t For future use. N/A
header_size _Uint16t Size of the startup header, in bytes. Startup
machine _Uint16t Machine type, from sys/elf.h. IPL and Startup
startup_vaddr _Uint32t Virtual address to jump to after IPL is done. IPL
paddr_bias _Uint32t Value to add to a physical address to calculate the value to put into a pointer. Startup
image_paddr _Uint32t Set by the IPL to the physical address of the image filesystem. IPL and Startup
ram_paddr _Uint32t Physical address in RAM to which the startup code must be copied. The size of the startup code is stored in startup_size member. IPL and Startup
ram_size _Uint32t Number of bytes the image will occupy when it has been copied into RAM. This size may be greater than stored_size if the image was compressed, or smaller than stored_size if the image is XIP. Startup
startup_size _Uint32t Size of the startup code. Copy this number of bytes from the start of the image into RAM, at the location specified by ram_paddr. The startup code is never compressed, so this size is true in all cases. IPL
stored_size _Uint32t Size of the image including the header. The stored_size member is also used in the copy and extraction routines for non-XIP images. IPL
imagefs_paddr _Uint32t Set by the IPL to the physical address of the image filesystem. This value is then used by the startup code. IPL and Startup
imagefs_size _Uint32t Size of the uncompressed image filesystem. Startup
preboot_size unsigned short

Number of bytes from the beginning of the loaded image to the startup header. This value will usually be zero on ARM boards, indicating that nothing precedes the startup portion.

On an x86 board with a BIOS or UEFI, this value is non-zero, because there's a small piece of code that gets data from the BIOS or UEFI in real mode, then switches into protected mode and performs the startup. On an x86 board without an BIOS or UEFI, this value is zero.

IPL
zero0 _Uint16t Zero filler; reserved for future expansion. N/A
zero[3] _Uint32t Zero filler; reserved for future expansion. N/A
info[48] _Uint32t The info member is an array of startup_info* structures, which are described in the next section. IPL and Startup