Support Booting from FlexSPI Flash (QSPI Flash and HyperFlash) in Linux BSP for the i.MX RT Targets

Support Booting from FlexSPI Flash (QSPI Flash and HyperFlash) in Linux BSP for the i.MX RT Targets

1. Overview

This document describes support for booting from FlexSPI Flash in the Linux i.MX RT BSP. The FlexSPI controller on i.MX RT SoCs provides a unified interface to various types of external NOR Flash memory. The following target boards are supported:

  • IMXRT1170-EVK / IMXRT1170-EVKB — NXP evaluation boards with QSPI NOR Flash connected via the FlexSPI1 controller in quad SPI mode. The EVK uses an ISSI IS25WP128 (16 MB) flash, while the EVKB uses a Winbond W25Q512NW (64 MB) flash. Both chips use the same SPI command set and are auto-detected at runtime via JEDEC ID. The flash partition layout is identical for both boards and uses only 16 MB.

  • MaaXBoard-RT — Avnet evaluation board with 32 MB HyperFlash (Cypress) connected via the FlexSPI1 controller in HyperBus mode.

The two boards differ in flash type, capacity, sector size, and U-Boot boot flow:

Feature

IMXRT1170-EVK / EVKB

MaaXBoard-RT

Feature

IMXRT1170-EVK / EVKB

MaaXBoard-RT

Flash type

QSPI NOR (serial)

HyperFlash (parallel)

Flash chip

ISSI IS25WP128 (EVK) / Winbond W25Q512NW (EVKB)

Cypress HyperFlash

Flash size

16 MB (EVK) / 64 MB (EVKB)

32 MB

Sector size

4 KB

256 KB

Partition layout

16 MB (same for both EVK and EVKB)

32 MB

Boot flow

SPL + U-Boot proper (SPL.flexspi + u-boot.img)

Single image (flash.bin)

Linux MTD driver

SPI NOR (nxp-fspi)

HyperBus Memory Controller (hbmc-imxrt)

The functionality described in this document is delivered as two patches on top of the base linux-cm-imxrt117x distribution:

  • u-boot.patch — adds FlexSPI Flash boot support to U-Boot.

  • projects.patch — adds the rootfs_flash project to projects/.

The Linux kernel in the base distribution already includes FlexSPI controller drivers, MTD subsystem, and flash file system support. No kernel patch is required.

The imxrt_install.sh installation script is included in the base distribution (tools/bin/) and supports both boards.

2. Requirements

2.1. Detailed Requirements

The following are the requirements for this project:

  1. Support booting of U-Boot from FlexSPI Flash on the IMXRT1170-EVK, IMXRT1170-EVKB and MaaXBoard-RT boards, with no reliance on presence of SD Card or any other storage devices.

  2. Support Linux boot from FlexSPI Flash, in the following configuration: multiimage including kernel and DTB loaded from FlexSPI Flash to RAM for execution; root file system mounted in FlexSPI Flash as the read-write flash file system (JFFS2 or optionally UBIFS).

  3. Support FlexSPI Flash in Linux. This must include support for Linux flash file system (JFFS2 and UBIFS).

  4. Store the U-Boot environment in FlexSPI Flash. Support for the fw_printenv and fw_setenv utilities in Linux.

  5. Support installation of the U-Boot images to FlexSPI Flash using the i.MX RT Serial Downloader feature.

  6. Support installation of the Linux and rootfs images to FlexSPI Flash via networking using the U-Boot command line interface, and via Serial Downloader using the imxrt_install.sh script.

2.2. Detailed Non-Requirements

The following are the non-requirements for this project that may otherwise not be obvious:

  1. Support for Linux boot scenarios other than the one listed in Design: Linux Boot from FlexSPI Flash is not required.

    • Rationale: Costs reduction measure.

3. 3. Design

3.1.
Design: U-Boot Boot from FlexSPI Flash

3.1.1. Boot ROM Requirements

The i.MX RT Boot ROM is capable of loading and executing code from an external NOR Flash device connected via the FlexSPI controller. To boot from FlexSPI Flash, the bootable image must contain the following components at specific offsets:

  • FlexSPI Configuration Block (FCFB) — a 488-byte structure identified by the FCFB tag, placed at a well-known offset near the beginning of the flash (the exact offset varies by SoC variant, 1024 bytes in case of i.MX RT1170). The Boot ROM reads this block first to configure the FlexSPI controller for the specific flash device. The block contains device type (Serial NOR or HyperFlash), bus width (1/2/4/8 pads), clock frequency, DDR mode, flash size, and a Lookup Table (LUT) with flash read/write command sequences. This block is board-specific and must match the flash device installed on the board.

  • Image Vector Table (IVT) at offset 0x1000 — a standard i.MX RT boot header containing the entry point address, pointers to the Boot Data and optional Device Configuration Data (DCD), and the image self-address. The IVT is prepended to the SPL binary by the mkimage tool using the board-specific imximage.cfg configuration file.

After the Boot ROM reads the FCFB and initializes the FlexSPI controller, it locates the IVT, loads the SPL binary from the flash into internal RAM, and transfers execution to the SPL entry point.

3.1.2. FlexSPI-Bootable Image Build

When the CONFIG_FSPI_BOOT option is enabled in U-Boot, the build system generates a flash-bootable image by combining the FCFB header with the SPL binary:

  1. The board-specific flexspi_cb.c file is compiled and extracted as a raw binary (flexspi_cb.bin, 512 bytes). This file contains the FCFB structure with FlexSPI controller parameters tailored to the specific flash device on the board.

  2. The SPL binary (with the IVT prepended by mkimage) is placed at the 4 KB offset.

  3. The FCFB binary is placed at the 1 KB offset (for i.MX RT1170).

  4. The resulting combined image is saved as SPL.flexspi.

3.1.3. SPL Boot Device Selection

After the Boot ROM loads and executes the SPL from FlexSPI Flash, the SPL must locate and load the main U-Boot image (U-Boot proper, stored as u-boot.img). The SPL selects the boot media through the board-specific spl_boot_device() function, which returns the boot device type based on the U-Boot configuration.

For the i.MX RT boards in this BSP, spl_boot_device() defaults to BOOT_DEVICE_MMC1, directing the SPL to load U-Boot proper from an SD Card. To boot entirely from FlexSPI Flash, the CONFIG_FSPI_BOOT and CONFIG_SPL_NOR_SUPPORT options must be enabled in the U-Boot configuration. When both options are set, spl_boot_device() returns BOOT_DEVICE_NOR, directing the SPL to load U-Boot proper from the same NOR Flash device where the SPL itself resides.

3.1.4. IMXRT1170-EVK / IMXRT1170-EVKB

A dedicated configuration file imxrt1170-evk-qspi_defconfig will be added to U-Boot to support booting from the QSPI Flash on the NXP IMXRT1170-EVK and IMXRT1170-EVKB boards. This configuration enables CONFIG_FSPI_BOOT and CONFIG_SPL_NOR_SUPPORT so that both SPL and U-Boot proper are loaded from QSPI Flash. Support for both ISSI and Winbond SPI NOR flash chips is enabled (CONFIG_SPI_FLASH_ISSI, CONFIG_SPI_FLASH_WINBOND), so that the same U-Boot image works on both EVK and EVKB. The flash chip is auto-detected at runtime via JEDEC ID. The resultant binaries from the make command will be SPL.flexspi and u-boot.img images:

$ make imxrt1170-evk-qspi_defconfig $ make $ ls SPL.flexspi u-boot.img

The SPL.flexspi image must be programmed to the QSPI Flash at offset 0. The FCFB header in this image is configured for QSPI NOR Flash (quad SPI, SDR mode, 133 MHz) and is compatible with both the ISSI IS25WP128 (EVK) and Winbond W25Q512NW (EVKB) flash chips. The board-specific files are:

  • board/freescale/imxrt1170-evk/flexspi_cb.c — FlexSPI Configuration Block for QSPI NOR (4-pad, SDR read command 0xEB).

  • board/freescale/imxrt1170-evk/imximage.cfg — IVT configuration for the IMXRT1170-EVK.

Note: The same bootable image works on both EVK and EVKB because both flash chips use the same SPI quad I/O protocol and command set (0xEB read command). The FCFB configures the FlexSPI controller for this common protocol, and the SPI NOR driver identifies the specific chip and its capacity via JEDEC ID at runtime. The flash partition layout uses only 16 MB to ensure compatibility with the smaller EVK flash. To utilize the full 64 MB flash on the EVKB, the user can resize the existing partitions (kernel, rootfs) or add new partitions in the device tree, and update the corresponding U-Boot environment variables. Note that resizing the rootfs partition also requires adjusting the UBINIZE_FLAGS and MKFSUBIFS_FLAGS build parameters to match the new partition size when building the UBIFS image.

The u-boot.img image is U-Boot proper. It must be programmed to the QSPI Flash at offset 0x10000.

3.1.5. MaaXBoard-RT

The existing maaxboard-rt_defconfig is already configured to boot from the FlexSPI controller (CONFIG_FSPI_BOOT=y).

Unlike the IMXRT1170-EVK which uses separate SPL and U-Boot proper images, the MaaXBoard-RT uses a single flash.bin image that combines both SPL and U-Boot proper. This design choice is driven by the HyperFlash geometry: the minimum erase sector size on HyperFlash is 256 KB, so dedicating a separate partition to the small SPL image would waste most of a 256 KB sector. Combining SPL and U-Boot proper into a single image makes more efficient use of the available flash space. The flash.bin image must be programmed to the HyperFlash at offset 0:

$ make maaxboard-rt_defconfig $ make $ ls flash.bin

The FCFB header in this image is configured for the Cypress HyperFlash (8-pad, DDR mode, 133 MHz, word-addressable) installed on the board. The board-specific files are:

  • board/avnet/MaaXBoard-RT/flexspi_cb.c — FlexSPI Configuration Block for HyperFlash (8-pad, DDR read command 0xA0).

  • board/avnet/MaaXBoard-RT/imximage.cfg — IVT configuration for the MaaXBoard-RT.

3.2.
Design: Linux Boot from FlexSPI Flash

The u-boot.patch introduces U-Boot environment commands and configuration changes to support booting Linux from FlexSPI Flash. The boot process involves loading the kernel multiimage from flash (either reading it to RAM or booting directly from memory-mapped flash), configuring the root file system boot arguments based on the selected flash file system type, and transferring control to the kernel.

3.2.1. U-Boot Flash Access via FlexSPI

Although both QSPI NOR and HyperFlash devices are connected through the same FlexSPI controller, U-Boot uses different subsystems to manage them:

  • SPI NOR Flash (IMXRT1170-EVK/EVKB) — accessed through the U-Boot SPI memory layer (CONFIG_SPI_FLASH, CONFIG_SPI_MEM) and the NXP FlexSPI driver (CONFIG_SPI_NXP_FSPI). Flash operations are performed using the sf (SPI Flash) command family (sf probe, sf read, sf write, sf erase), which sends SPI commands to the flash device through the FlexSPI controller.

  • HyperFlash / CFI NOR (MaaXBoard-RT) — accessed as a memory-mapped CFI-compliant NOR Flash (CONFIG_CFI_FLASH, CONFIG_FLASH_CFI_DRIVER). The FlexSPI controller maps the HyperFlash into the CPU address space, so the flash contents are directly readable at their physical addresses. Write and erase operations use the standard CFI protocol commands (erase, cp.b). The FlexSPI controller configuration for write access via the AHB bus is performed in the board-specific U-Boot code (board/avnet/MaaXBoard-RT/MaaXBoard-RT.c).

This distinction determines the boot commands, update commands, and environment variable naming conventions used on each board.

3.2.2. Common Environment

The u-boot.patch refactors the common environment file include/env/nxp/imxrt_env.env to split flash-related commands into separate SPI NOR and CFI NOR sections, and adds new CFI flash commands (flashboot, flash_kernel_update, flash_rootfs_update) for HyperFlash-based boards.

The following environment variables are shared by both SPI NOR and CFI NOR boards:

  • project — project name used to construct image filenames, default is rootfs_flash.

  • fstype — flash file system type: jffs2 (default) or ubi.

  • addrootfs — command that appends the rootfs-specific kernel boot arguments based on the fstype variable. For JFFS2 it sets root=/dev/mtdblock3, for UBIFS it sets ubi.mtd=3 root=ubi0:rootfs.

3.2.3. IMXRT1170-EVK / IMXRT1170-EVKB

The CONFIG_CMD_SF option is enabled in imxrt1170-evk-qspi_defconfig to provide the sf commands for QSPI NOR Flash access. The CONFIG_BOOTCOMMAND is set to run sfboot.

The sfboot command performs the following sequence:

  1. Probes the SPI NOR Flash device (sf probe 0).

  2. Reads the kernel multiimage from flash to RAM (sf read).

  3. Configures IP and rootfs boot arguments (run addip && run addrootfs).

  4. Boots the kernel (bootm).

The flash offsets and sizes used by sfboot are defined as environment variables in the board-specific board/freescale/imxrt1170-evk/imxrt1170-evk.env file (kernel_sf_offset, kernel_sf_size).

3.2.4. MaaXBoard-RT

The MaaXBoard-RT uses CFI flash commands to access the HyperFlash. Since HyperFlash is memory-mapped, the kernel multiimage can be booted directly from its flash address without reading it to RAM first. The CONFIG_CFI_FLASH option is enabled in maaxboard-rt_defconfig.

The maaxboard-rt_defconfig will be updated to set CONFIG_BOOTCOMMAND to run flashboot. The flashboot command performs the following sequence:

  1. Configures IP and rootfs boot arguments (run addip && run addrootfs).

  2. Boots the kernel directly from the memory-mapped flash address (bootm ${kernel_flash_addr}).

The flash addresses and sizes used by flashboot are defined in the board-specific board/avnet/MaaXBoard-RT/maaxboard-rt.env file (kernel_flash_addr, kernel_flash_size).

3.3.
Design: Linux Device Driver for FlexSPI Flash and Flash File System

3.3.1. The rootfs_flash Project

The separate project projects/rootfs_flash will be created (delivered as projects.patch) to demonstrate booting Linux from FlexSPI Flash. The following main features will be enabled in the new project:

  • Support for the FlexSPI Flash will be enabled in the kernel configuration.

  • initramfs will be disabled in the kernel configuration. Instead the root filesystem will be mounted on JFFS2 or alternatively on a UBIFS file system in the FlexSPI Flash.

  • The kernel and the DTB images will be built in a single multi-part image.

To implement these features the following options from the common build rules will be used in Makefile for the rootfs_flash project:

  • RFS_BUILD_DIR - temporary directory to build the root file system image

  • FLASHFS_TYPE - to select certain file system image to build: jffs2 or ubi

  • MKFSUBIFS_FLAGS - Flash-specific flags for the mkfs.ubifs utility (if FLASHFS_TYPE is ubi)

  • UBINIZE_FLAGS - Flash-specific flags for the ubinize utility (if FLASHFS_TYPE is ubi)

  • SEPARATE_DTB - tells make to either build the multi-part image or save the DTB separately.

The build produces the following output images:

  • rootfs_flash.uImage — multiimage containing the Linux kernel and DTB, to be installed to the kernel partition of the FlexSPI Flash.

  • rootfs_flash.jffs2 — JFFS2 root filesystem image (when FLASHFS_TYPE=jffs2, the default), to be installed to the rootfs partition.

  • rootfs_flash.ubi — UBIFS root filesystem image (when FLASHFS_TYPE=ubi), to be installed to the rootfs partition.

Board-specific files will be provided for both the IMXRT1170-EVK and MaaXBoard-RT targets:

  • IMXRT117X_NXPEVK_defconfig, MAAXBOARD_RT_defconfig — kernel configurations.

  • rootfs_flash.dts.IMXRT117X_NXPEVK, rootfs_flash.dts.MAAXBOARD_RT — device trees, including the FlexSPI Flash MTD partition layout for each board.

  • rootfs_flash.initramfs — root filesystem description (shared, with board-specific entries selected via ifarch directives).

3.3.2. Build Procedure

The default make command in the rootfs_flash project directory builds the kernel multiimage and the JFFS2 rootfs image:

$ cd projects/rootfs_flash $ make $ ls rootfs_flash.uImage rootfs_flash.jffs2

To build the UBIFS rootfs image instead, override the FLASHFS_TYPE variable:

$ make FLASHFS_TYPE=ubi $ ls rootfs_flash.uImage rootfs_flash.ubi

3.3.3. Linux FlexSPI Flash Drivers

3.3.3.1. IMXRT1170-EVK / IMXRT1170-EVKB

The NXP FlexSPI NOR driver (nxp-fspi) from the common NXP codebase will be used to provide support for the FlexSPI controller in SPI NOR mode. The MTD, SPI_MEM, SPI_NXP_FLEXSPI, MTD_SPI_NOR kernel features will be enabled in the rootfs_flash project's configuration, so that the QSPI Flash will be available in Linux as a standard MTD device.

3.3.3.2. MaaXBoard-RT

The HyperBus Memory Controller driver (hbmc-imxrt) will be used to provide support for the FlexSPI controller in HyperBus mode. The MTD, MTD_CFI, MTD_CFI_AMDSTD, MTD_HYPERBUS, HBMC_IMXRT kernel features will be enabled in the rootfs_flash project's configuration.

3.3.4. Flash File Systems

The UBI, UBIFS and JFFS2 related options will be enabled on both boards to support Linux flash file systems.

The FlexSPI Flash will be partitioned into MTD devices as described in Design: Install U-Boot Images to FlexSPI Flash. The partition layout is defined in the board-specific device tree files. The root file system will be mounted from the rootfs partition (mtd3).

3.4.
Design: U-Boot Environment in FlexSPI Flash

The U-Boot environment will be stored in the FlexSPI Flash. The relevant U-Boot configuration options are:

  • IMXRT1170-EVK/EVKB: CONFIG_ENV_IS_IN_SPI_FLASH — environment stored in SPI NOR Flash via sf commands.

  • MaaXBoard-RT: CONFIG_ENV_IS_IN_FLASH — environment stored in CFI NOR Flash (memory-mapped).

Both boards enable CONFIG_SYS_REDUNDAND_ENVIRONMENT to maintain a redundant copy of the environment for reliability.

The environment, along with the redundant copy, will be placed in the uboot_env partition (mtd1) of the FlexSPI Flash. The partition holds two environment copies, so its total size is twice the individual environment size:

Board

Env offset

Env size

Redundant offset

Sector size

Partition size

Board

Env offset

Env size

Redundant offset

Sector size

Partition size

IMXRT1170-EVK/EVKB

0x60000

0x10000 (64 KB)

0x70000

0x10000 (64 KB)

0x20000 (128 KB)

MaaXBoard-RT

0x80000

0x40000 (256 KB)

0xC0000

0x40000 (256 KB)

0x80000 (512 KB)

The fw_printenv and fw_setenv utilities will be included in the rootfs_flash project's root file system to allow reading and modifying the U-Boot environment from Linux. Board-specific fw_env.config configuration files will be provided:

  • fw_env.config.qspi for the IMXRT1170-EVK/EVKB

  • fw_env.config.hyperflash for the MaaXBoard-RT

The correct configuration file will be automatically selected during the root file system build based on the target board.

3.5.
Design: Install U-Boot Images to FlexSPI Flash

The FlexSPI Flash device will be logically divided into 4 partitions to store the software components of the system.

3.5.1. IMXRT1170-EVK / IMXRT1170-EVKB (QSPI Flash, 16 MB)

Partition

Label

Offset

Size

Image

Partition

Label

Offset

Size

Image

mtd0

uboot

0x000000

0x060000 (384 KB)

SPL.flexspi at offset 0, u-boot.img at offset 0x10000

mtd1

uboot_env

0x060000

0x020000 (128 KB)

U-Boot environment (managed by U-Boot)

mtd2

kernel

0x080000

0x800000 (8 MB)

rootfs_flash.uImage

mtd3

rootfs

0x880000

0x780000 (7.5 MB)

rootfs_flash.jffs2 or rootfs_flash.ubi

3.5.2. MaaXBoard-RT (HyperFlash, 32 MB)