Booting a single image on different mx6sabresd boards
The traditional way in U-Boot to build for the different mx6sabreboard variants is like this:
- For mx6qsabresd:
make mx6qsabresd_defconfig make
- For mx6dlsabresd:
make mx6dlsabresd_defconfig make
- For mx6qpsabresd:
make mx6qspabresd_defconfig make
In each case a
u-boot.imx binary is generated and can be directly flashed into
the SD card:
sudo dd if=u-boot.imx of=/dev/mmcblk0 bs=1K seek=1; sync
With this method one different binary is needed for each of the mx6sabresd board variant.
This methods relies on the usage of the DCD tables, which are data structures that the ROM code can use to configure the DRAM and some other peripherals. As each of the three boards have different SoCs and DRAM sizes, their DCD table differ.
For reference the DCD tables are located at (assuming a NXP U-Boot version):
Wouldn’t it be nice if we could build a single U-Boot binary that could run on all the three mx6sabresd board?
Yes, that would be awesome, but how can we achieve this?
The answer is called SPL (Second Phase Loader).
U-Boot community developed this real nice framework called SPL that can make this single binary magic possible.
SPL code runs from the internal RAM of the SoC, which means that it is size constraint and does the job of configuring the DRAM controller in standard C code, instead of static DCD table. It also configure clocks, IOMUX for the peripherals used in SPL (usually UART, MMC, I2C).
SPL code is able to detect the i.MX6 SoC type by reading the fuses and then it can call a specific DRAM initialization for the imx6q, imx6dl or imx6qp sabresd board type.
Can I use it now?
Sure, SPL support is complete for mx6sabresd since U-Boot 2017.09.
Many other mx6 boards use SPL for a long time. Some examples:
The SPL support is also present for the mx6sabreauto since U-Boot 2017.09.
Using SPL has some advantages such as:
- Code maintainance effort is lower as you only need a single U-Boot defconfig target that can support several boards
- Build time for the entire image is reduced as a single one can be used in all boards. Previously we needed to have one different image for each mx6sabresd board.
- SPL framework allows the usage of Falcon mode, which allows the SPL code to boot the Linux kernel directly, without loading the full U-Boot stack.
This is particularly important for users who want to reduce the overall boot time.
How to build SPL U-Boot for mx6sabresd?
Starting with U-Boot 2017.09 the way to build for mx6sabresd board is:
make mx6sabresd_defconfig make
This will generate two binaries:
SPL: This is the small SPL binary that runs from internal RAM.
u-boot.img: This is the full U-Boot, that contains all the complete U-Boot stack and drivers. This one is loaded from SPL and runs from DRAM.
In order to flash these two binaries into the SD card:
sudo dd if=SPL of=/dev/mmcblk0 bs=1K seek=1; sync sudo dd if=u-boot.img of=/dev/mmcblk0 bs=1K seek=69; sync
It is very important to follow the exact offsets shown above.
Then insert the SD card into any mx6sabresd board and the following output should be seen:
U-Boot SPL 2017.09-00221-g0d6ab32 (Oct 02 2017 - 16:44:38) Trying to boot from MMC1 U-Boot 2017.09-00221-g0d6ab32 (Oct 02 2017 - 16:44:38 -0300) CPU: Freescale i.MX6Q rev1.2 996 MHz (running at 792 MHz) CPU: Automotive temperature grade (-40C to 125C) at 31C Reset cause: POR Board: MX6-SabreSD I2C: ready DRAM: 1 GiB PMIC: PFUZE100 ID=0x10 MMC: FSL_SDHC: 0, FSL_SDHC: 1, FSL_SDHC: 2 PCI: pcie phy link never came up No panel detected: default to Hannstar-XGA Display: Hannstar-XGA (1024x768) In: serial Out: serial Err: serial Net: FEC [PRIME] Hit any key to stop autoboot: 0
Generating an image with Buildroot
I have added mx6sabresd target in Buildroot, which uses mainline U-Boot and mainline kernel.
In order to generate a complete image, which contains the bootloader, device tree, kernel and a minimal root file system with Buildroot:
make imx6-sabresd_defconfig make
After the whole build process is finished a SD card image is available
In order to flash the SD card:
sudo dd if=output/images/sdcard.img of=/dev/mmcblk0; sync
This SD card can be used on mx6q, mx6dl or mx6qp sabresd boards :-)