Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 9 additions & 1 deletion boards/nxp/frdm_mcxn947/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,8 +1,16 @@
#
# Copyright 2024 NXP
# Copyright 2024-2025 NXP
#
# SPDX-License-Identifier: Apache-2.0
#

zephyr_library()
zephyr_library_sources(board.c)

if(CONFIG_FLEXSPI_CONFIG_BLOCK_OFFSET)
# Include flash configuration block
zephyr_compile_definitions(XIP_BOOT_HEADER_ENABLE=1)
set(BOARD_DIR "${ZEPHYR_HAL_NXP_MODULE_DIR}/mcux/mcux-sdk-ng/boards/frdmmcxn947")
zephyr_library_sources(${BOARD_DIR}/xip/mcxn_flexspi_nor_config.c)
zephyr_library_include_directories(${BOARD_DIR}/xip)
endif()
165 changes: 128 additions & 37 deletions boards/nxp/frdm_mcxn947/doc/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -206,43 +206,6 @@ Here is an example for the :zephyr:code-sample:`mbox_data` application.
:goals: flash
:west-args: --sysbuild

Flashing to QSPI
================

Here is an example for the :zephyr:code-sample:`hello_world` application.

.. zephyr-app-commands::
:app: zephyr/samples/hello_world
:board: frdm_mcxn947/mcxn947/cpu0/qspi
:gen-args: -DCONFIG_MCUBOOT_SIGNATURE_KEY_FILE=\"bootloader/mcuboot/root-rsa-2048.pem\" -DCONFIG_BOOTLOADER_MCUBOOT=y
:goals: flash


In order to load Zephyr application from QSPI you should program a bootloader like
MCUboot bootloader to internal flash. Here are the steps.

.. zephyr-app-commands::
:app: bootloader/mcuboot/boot/zephyr
:board: frdm_mcxn947/mcxn947/cpu0/qspi
:goals: flash

Open a serial terminal, reset the board (press the RESET button), and you should
see the following message in the terminal:

.. code-block:: console

*** Booting MCUboot v2.1.0-rc1-2-g9f034729d99a ***
*** Using Zephyr OS build v3.6.0-4046-gf279a03af8ab ***
I: Starting bootloader
I: Primary image: magic=unset, swap_type=0x1, copy_done=0x3, image_ok=0x3
I: Secondary image: magic=unset, swap_type=0x1, copy_done=0x3, image_ok=0x3
I: Boot source: none
I: Image index: 0, Swap type: none
I: Bootloader chainload address offset: 0x0
I: Jumping to the first image slot
*** Booting Zephyr OS build v3.6.0-4046-gf279a03af8ab ***
Hello World! frdm_mcxn947/mcxn947/cpu0/qspi

Debugging
=========

Expand All @@ -269,6 +232,122 @@ then a debugger can be attached.
As a reference please see (`AN13264`_, section 4.2.3 for more information).
The reference is for the RT1170 but similar technique can be also used here.

Using QSPI board variant
========================
The FRDM-MCXN947 board includes an external QSPI flash. The MCXN947 can boot and
XIP directly from this flash using the FlexSPI interface. The QSPI variant
enables building applications and code to execute from the QSPI.

Programming the ROM bootloader for external QSPI
------------------------------------------------
By default, the MCXN947 bootloader in ROM will boot using internal flash. But
the MCU can be programmed to boot from external memory on the FlexSPI interface.
Before using the QSPI board variant, the board should be programmed to boot from
QSPI using the steps below.

To configure the ROM bootloader, the Protected Flash Region (PFR) must be
programmed. Programming the PFR is done using NXP's ROM bootloader tools.
Some simple steps are provided in NXP's
`MCUXpresso SDK example hello_world_qspi_xip readme`_. The binary to program
with blhost is found at `bootfromflexspi.bin`_. A much more detailed explanation
is available at this post `Running code from external memory with MCX N94x`_.
The steps below program the FRDM-MCXN947 board. Note that these steps interface
to the ROM bootloader through the UART serial port, but USB is another option.

1. Disconnect any terminal from the UART serial port, since these steps use that
serial port.
#. Connect a USB Type-C cable to the host computer and J17 on the board, in the
upper left corner. This powers the board, connects the debug probe, and
connects the UART serial port used for the ``blhost`` command.
#. Place the MCU in ISP mode. On the FRDM-MCXN947 board, the ISP button
can be used for this. Press and hold the ISP button SW3, on the bottom right
corner of the board. Press and release the Reset button SW1 on the upper left
corner of the board. The MCU has booted into ISP mode. Release the ISP
button.
#. Run the ``blhost`` command:

.. tabs::

.. group-tab:: Ubuntu

This step assumes the MCU serial port is connected to `/dev/ttyACM0`

.. code-block:: shell

blhost -t 2000 -p /dev/ttyACM0,115200 -j -- write-memory 0x01004000 bootfromflexspi.bin

.. group-tab:: Windows

Change `COMxx` to match the COM port number connected to the MCU serial port.

.. code-block:: shell

blhost -t 2000 -p COMxx -j -- write-memory 0x01004000 bootfromflexspi.bin

Successful programming should look something like this:

.. code-block:: console

$ blhost -t 2000 -p /dev/ttyACM0,115200 -j -- write-memory 0x01004000 bootfromflexspi.bin
{
"command": "write-memory",
"response": [
256
],
"status": {
"description": "0 (0x0) Success.",
"value": 0
}
}

5. Reset the board with SW1 to exit ISP mode. Now the MCU is ready to boot from
QSPI.

The ROM bootloader can be configured to boot from internal flash again. Repeat
the steps above to program the PFR, and program the file `bootfromflash.bin`_.

Build, flash, and debug with the QSPI variant
---------------------------------------------

Once the PFR is programmed to boot from QSPI, the normal Zephyr steps to build,
flash, and debug can be used with the QSPI board variant. Here are some examples.

Here is an example for the :zephyr:code-sample:`hello_world` application:

.. zephyr-app-commands::
:app: zephyr/samples/hello_world
:board: frdm_mcxn947//cpu0/qspi
:goals: flash

MCUboot can also be used with the QSPI variant. By default, this places the
MCUboot bootloader in the ``boot-partition`` in QSPI flash, with the application
images. The ROM bootloader will boot first and load MCUboot in the QSPI, which
will load the app. This example builds and loads the :zephyr:code-sample:`blinky`
sample with MCUboot using Sysbuild:

.. zephyr-app-commands::
:app: zephyr/samples/basic/blinky
:board: frdm_mcxn947//cpu0/qspi
:west-args: --sysbuild
:gen-args: -DSB_CONFIG_BOOTLOADER_MCUBOOT=y
:goals: flash

Open a serial terminal, reset the board with the SW1 button, and the console
will print:

.. code-block:: console

*** Booting MCUboot vX.Y.Z ***
*** Using Zephyr OS build vX.Y.Z ***
I: Starting bootloader
I: Image index: 0, Swap type: none
I: Bootloader chainload address offset: 0x14000
I: Image version: v0.0.0
I: Jumping to the first image slot
*** Booting Zephyr OS build vX.Y.Z ***
LED state: OFF
LED state: ON

Troubleshooting
===============

Expand Down Expand Up @@ -301,3 +380,15 @@ Troubleshooting

.. _AN13264:
https://www.nxp.com/docs/en/application-note/AN13264.pdf

.. _MCUXpresso SDK example hello_world_qspi_xip readme:
https://github.com/nxp-mcuxpresso/mcuxsdk-examples/blob/main/_boards/frdmmcxn947/demo_apps/hello_world_qspi_xip/example_board_readme.md

.. _bootfromflash.bin:
https://github.com/nxp-mcuxpresso/mcuxsdk-examples/blob/main/_boards/frdmmcxn947/demo_apps/hello_world_qspi_xip/cm33_core0/bootfromflash.bin

.. _bootfromflexspi.bin:
https://github.com/nxp-mcuxpresso/mcuxsdk-examples/blob/main/_boards/frdmmcxn947/demo_apps/hello_world_qspi_xip/cm33_core0/bootfromflexspi.bin

.. _Running code from external memory with MCX N94x:
https://community.nxp.com/t5/MCX-Microcontrollers-Knowledge/Running-code-from-external-memory-with-MCX-N94x/ta-p/1792204
17 changes: 11 additions & 6 deletions boards/nxp/frdm_mcxn947/frdm_mcxn947_mcxn947_cpu0_qspi.dts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@

#include "frdm_mcxn947_mcxn947_cpu0.dtsi"

/delete-node/ &boot_partition;
/delete-node/ &slot0_partition;
/delete-node/ &slot1_partition;
/delete-node/ &storage_partition;
Expand All @@ -28,17 +29,21 @@
#address-cells = <1>;
#size-cells = <1>;

slot0_partition: partition@0 {
boot_partition: partition@0 {
label = "mcuboot";
reg = <0x00000000 DT_SIZE_K(80)>;
};
slot0_partition: partition@14000 {
label = "image-0";
reg = <0x00000000 DT_SIZE_M(3)>;
reg = <0x00014000 DT_SIZE_M(3)>;
};
slot1_partition: partition@300000 {
slot1_partition: partition@314000 {
label = "image-1";
reg = <0x00300000 DT_SIZE_M(3)>;
reg = <0x00314000 DT_SIZE_M(3)>;
};
storage_partition: partition@600000 {
storage_partition: partition@614000 {
label = "storage";
reg = <0x00600000 DT_SIZE_M(2)>;
reg = <0x00614000 DT_SIZE_K(1968)>;
};
};
};
10 changes: 9 additions & 1 deletion boards/nxp/mcx_n9xx_evk/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,8 +1,16 @@
#
# Copyright 2024 NXP
# Copyright 2024-2025 NXP
#
# SPDX-License-Identifier: Apache-2.0
#

zephyr_library()
zephyr_library_sources(board.c)

if(CONFIG_FLEXSPI_CONFIG_BLOCK_OFFSET)
# Include flash configuration block
zephyr_compile_definitions(XIP_BOOT_HEADER_ENABLE=1)
set(BOARD_DIR "${ZEPHYR_HAL_NXP_MODULE_DIR}/mcux/mcux-sdk-ng/boards/mcxn9xxevk")
zephyr_library_sources(${BOARD_DIR}/xip/mcxn_flexspi_nor_config.c)
zephyr_library_include_directories(${BOARD_DIR}/xip)
endif()
Loading
Loading