Porting Checklist 2026: Bootloader → Kernel → RootFS for New Boards

Complete checklist for porting embedded Linux to a new board, from bootloader bring-up through kernel configuration to root filesystem validation, with practical tips for each stage.

Digital Ocean free trial – Cloud VPS Solutions
Porting Checklist 2026: Bootloader → Kernel → RootFS for New Boards

Porting embedded Linux to a new board follows a predictable sequence: get the bootloader running, boot a kernel, mount a root filesystem. Each stage has specific checkpoints and failure modes. This checklist distills the process into verifiable steps, based on practical experience bringing up ARM and RISC-V boards.

Before you start

Gather documentation

  • SoC technical reference manual (TRM) — the essential document
  • Board schematics — for pin muxing and peripheral connections
  • SoC errata sheet — known silicon bugs that affect boot or driver behaviour
  • Vendor BSP (if available) — even if you don't use it directly, it shows what works

Set up serial console

You cannot debug boot problems without a serial console. Identify the debug UART on the schematic, connect a USB-to-UART adapter, and verify you can see characters at the correct baud rate (usually 115200).

This is step zero. Everything else depends on it.

Stage 1: Bootloader

1.1 Identify the boot flow

Most modern SoCs use a multi-stage boot:

  1. ROM bootloader (in silicon) — loads SPL/TPL from boot media
  2. SPL (Secondary Program Loader) — initializes DRAM, loads U-Boot
  3. U-Boot — loads kernel, DTB, and optional initramfs

Determine what the ROM expects: which boot media (eMMC, SPI NOR, SD card), what image format, what header structure.

1.2 Build U-Boot SPL + U-Boot proper

Start with the vendor's defconfig if available. If not, find the closest supported board in mainline U-Boot and adapt.

make CROSS_COMPILE=aarch64-linux- vendor_board_defconfig
make CROSS_COMPILE=aarch64-linux- -j$(nproc)

Checkpoint: U-Boot prints its banner on the serial console and reaches the command prompt.

1.3 DRAM initialization

DRAM initialization is the most common failure point in bootloader bring-up. Symptoms: hang during SPL, garbled output, or random crashes.

Verify:

  • DDR timing parameters match the actual DRAM chips on the board
  • Voltage rail for DRAM is correct and stable
  • If the SoC has a DDR PHY training sequence, verify it completes

If using vendor-provided DRAM initialization blobs, ensure the blob matches the board's DRAM configuration (density, speed grade, topology).

1.4 Storage access

Verify U-Boot can access the boot storage:

U-Boot> mmc info          # eMMC/SD
U-Boot> sf probe          # SPI NOR
U-Boot> ubi part nand0    # NAND/UBI

Checkpoint: U-Boot can list files on the boot partition or read raw blocks.

1.5 Network (optional but valuable)

If the board has Ethernet, enable it in U-Boot. TFTP boot dramatically speeds up kernel development:

U-Boot> dhcp
U-Boot> tftp 0x40000000 Image

Stage 2: Device tree

2.1 Start from the SoC's base DTS

The mainline kernel includes DTS files for most SoCs. Copy the closest board's DTS and modify it for your hardware.

2.2 Pin muxing

Configure pin muxing for all peripherals used on the board. Cross-reference the schematic with the SoC's pin mux register descriptions in the TRM. Incorrect pin muxing is the most common cause of "the peripheral doesn't work" bugs.

2.3 Clock and power trees

Ensure the device tree correctly describes clock parents, rates, and power domains. Many peripherals fail silently if their clock or power domain is not enabled.

2.4 Validate with dtc

dtc -I dts -O dtb -o board.dtb board.dts  # catches syntax errors
# Then check for warnings about missing properties

The device tree debugging documentation covers common DTS errors and validation techniques in detail.

Stage 3: Kernel

3.1 Minimal kernel config

Start with the SoC's defconfig or tinyconfig and add drivers incrementally:

  1. Console driver (UART)
  2. Timer and interrupt controller
  3. DRAM controller (if not handled by bootloader)
  4. Storage driver (eMMC, NAND, NOR)
  5. Network driver (Ethernet)
  6. Any board-specific drivers

3.2 Boot the kernel

Load kernel and DTB via TFTP or from storage:

U-Boot> booti 0x40000000 - 0x43000000

Checkpoint: kernel prints boot messages on the serial console and reaches "Freeing unused kernel memory."

3.3 Common kernel boot failures

Hang after "Starting kernel..." — Wrong load address, DTB not found, or early console not configured. Enable CONFIG_EARLY_PRINTK and earlyprintk on the command line.

Kernel panic: no init found — The kernel booted but cannot find a root filesystem. This is expected at this stage; proceed to Stage 4.

Random crashes or data corruption — DRAM issues that weren't caught by the bootloader. Run memtest from U-Boot.

3.4 Enable remaining peripherals

Once basic boot works, enable drivers one at a time:

  • GPIO and LED
  • I2C and SPI
  • USB
  • Display (if applicable)
  • Audio (if applicable)
  • Wireless (if applicable)

Test each peripheral as you enable it. Do not enable everything at once and hope for the best.

Stage 4: Root filesystem

4.1 Initial rootfs via initramfs

For early bring-up, bundle a minimal initramfs (BusyBox-based) into the kernel or load it as a separate image:

U-Boot> booti 0x40000000 0x45000000:${ramdisk_size} 0x43000000

Checkpoint: you get a shell prompt on the serial console.

4.2 Mount real rootfs from storage

Once storage drivers are working, boot with a root filesystem on eMMC or NAND:

root=/dev/mmcblk0p2 rootwait

4.3 Package installation

With a working rootfs, you can start installing packages. The ProteanOS packaging system and ProKit tools handle package building and installation for the target.

4.4 Persistent storage validation

Write files, reboot, verify they persist. Run fsck after unclean shutdowns. Test power-loss scenarios (pull power during write operations and verify filesystem recovery).

5.1 Secure boot

Once basic boot is reliable, add signature verification. The secure boot guide covers U-Boot FIT image signing.

5.2 dm-verity

Protect the read-only root filesystem. The dm-verity guide covers setup and integration.

5.3 Hardware security features

Enable SoC-specific security features: TrustZone, secure storage, hardware RNG, crypto accelerators. These are SoC-specific and require the TRM and vendor documentation.

Stage 6: Validation

6.1 Stress testing

Run stress tests for at least 72 hours:

  • CPU stress (stress-ng)
  • Memory stress (memtester, mmap stress)
  • Storage stress (fio, bonnie++)
  • Thermal stress (monitor temperatures under load)

6.2 Power consumption

Measure power in all relevant states: active, idle, sleep, deep sleep. Verify that clock gating and power domain management work correctly.

6.3 Peripheral regression

After all drivers are enabled, run a full peripheral regression test. I2C devices that worked in isolation sometimes fail when other buses are active due to shared interrupt lines or clock conflicts.

Summary

Board bring-up is systematic, not heroic. Follow the sequence: serial console → bootloader → DRAM → storage → kernel → rootfs → peripherals → security → validation. Verify each stage before proceeding to the next. Document everything—the next engineer working on this board will thank you.

The porting documentation provides additional context on ProteanOS-specific porting workflows and conventions.