Important
This lesson covers how to define boards in the nRF Connect SDK using both hardware models v1 and v2 (HWMv1 and HWMv2 respectively).
This exercise tab is for nRF Connect SDK v2.6.2 – v2.5.2, where HWMv1 is used. HWMv1 is deprecated and removed in nRF Connect SDK v3.0.0. We recommend using HWMv2 for all new designs (other tabs).
In this topic, we will explore the different options for creating custom board files and the guidelines for naming your custom board. You can watch the video below or read the lesson text.
We will cover the mandatory and optional files required to define a custom board, as well as how to create a revision of the board. We will study these files one by one and understand their role.
In Exercise 1 of this lesson, we will use the Create a new board GUI in the nRF Connect for VS Code extension to define a new board, and populate most of the mandatory files’ content.
Naming your custom board
When naming your custom board, there are some conventions that you need to follow.
- You need to give your board a unique name. Run
west boardsin the nRF Connect Terminal for a list of names that have already been taken; you can’t name your custom board with a name that is already in use. - It’s recommended that your board name include the name of the SoC at the end. For instance, suppose we want to make a new board called DevAcademy, which is based on the nRF52833 SoC. It’s highly recommended that you call your board “DevAcademy nRF52833”.
Note that the Create a new board GUI in nRF Connect for VS Code extension will ask you to provide a human-readable name for your board (e.g., DevAcademy nRF52833), and it will automatically generate the board name (devacademy_nrf52833).
Definition
Human-readable name (full_name) is the descriptive name for the board, which can include spaces and capital letters. The full name is intended for display purposes and documentation, making it easier for users to recognize the board.
Board name is typically a lowercase, underscore-separated version of the human-readable name, with all whitespaces replaced by underscores. The board name uniquely and descriptively identifies a particular system, but does not include additional information that may be required to actually build an image.
Location of custom board
Before diving into the board files that make up the custom board definition, we need to know where to put the files.
When working with custom boards, you have three main options for where to place the board definition files. Each option has its own advantages and limitations:
- Out-of-Tree (dedicated directory): In this approach, your board files are stored outside of the nRF Connect SDK/Zephyr tree in a separate directory. You’ll configure the build system to locate and use these external board files. This method is ideal for closed-source projects where you want to keep board definitions private. This is the method we’ll focus on in this lesson.
- Upstream in Zephyr: Choose this option if you’re developing a development kit, module, reference design, or prototyping platform that you intend to share with the Zephyr community. It’s also appropriate for open-source products. Board definitions submitted upstream must include documentation and go through a review and approval process by the Zephyr maintainers.
- Inside the application’s
boardsfolder: This option is suitable for quick prototyping or debugging. You can place the board files directly in aboardssubdirectory within your application folder. This is a convenient approach for temporary or experimental work.
Board files
Consider our new development kit DevAcademy nRF52833, which is based on the nRF52833 SoC. The board name generated for this board will be .devacademy_nrf52833
When creating a custom board definition, remember that the SDK provides the hardware layer files from Architecture up to SoC. So, we only need to populate the board layer. The board layer consists of these five mandatory files.
boards/<ARCH>/devacademy_nrf52833
├── Kconfig.board
├── Kconfig.defconfig
├── devacademy_nrf52833_defconfig
├── devacademy_nrf52833.dts
└── devacademy_nrf52833-pinctrl.dtsi The term <ARCH> serves as a placeholder for the architecture. The extension will automatically populate this with the architecture used by the SoC, as we will see in exercise 1.
Mandatory files
Let’s take a close look at the five mandatory files in the board layer.
1. Kconfig.board
The Kconfig.board file is automatically generated by the extension, and we typically don’t need to change anything inside it. This file defines a Kconfig symbol for your board BOARD_DEVACADEMY_NRF52833 and it specifies a dependency to the SoC hardware support layer (through the depends on keyword).
# Copyright (c) 2023 Nordic Semiconductor ASA
# SPDX-License-Identifier: Apache-2.0
config BOARD_DEVACADEMY_NRF52833
bool "DevAcademy nRF52833"
depends on SOC_NRF52833_QIAA
2. Kconfig.defconfig
The Kconfig.defconfig file defines board-specific default values for Kconfig options. The extension automatically generates this file, and we typically don’t need to change anything inside it.
The content of this file is wrapped in if /endif blocks that correspond to specific board targets, as shown below.
When the developer passes the selected target board, BOARD_DEVACADEMY_NRF52833 is set, along with CONFIG_BOARD. The CONFIG_BT_CTLR Kconfig option, which enables support for the SoC native Bluetooth LE controller implementation, is only enabled if CONFIG_BT is selected by the application. This is added here because the nRF52833 SoC is widely used for Bluetooth LE applications.
# Copyright (c) 2023 Nordic Semiconductor ASA
# SPDX-License-Identifier: Apache-2.0
if BOARD_DEVACADEMY_NRF52833
config BOARD
default "devacademy_nrf52833"
config BT_CTLR
default BT
endif
3. devacademy_nrf52833_defconfig
The file is a Kconfig fragment that is merged as-is into the final build of any application built for the specified board.devacademyl3e1_nrf52833_defconfig
The default Kconfig symbols that are generated by the extension are:
- Series hardware support, in the case of the nRF52833 SoC, this is
CONFIG_SOC_SERIES_NRF52X, which will enable the CPU and architecture support. - SoC hardware support,
CONFIG_SOC_NRF52833_QIAA - Board hardware support
- MPU, if the hardware supports it.
Below is the default devacademy_nrf52833_defconfig file generated by the tool.
# Copyright (c) 2023 Nordic Semiconductor ASA
# SPDX-License-Identifier: Apache-2.0
CONFIG_SOC_SERIES_NRF52X=y
CONFIG_SOC_NRF52833_QIAA=y
CONFIG_BOARD_DEVACADEMY_NRF52833=y
# Enable MPU
CONFIG_ARM_MPU=y
# Enable hardware stack protection
CONFIG_HW_STACK_PROTECTION=y
In addition to the default Kconfig symbols, we need to manually include any additional Kconfig symbols that we want to be enabled for all applications built for the board.
In the case of our board, DevAcademy nRF52833, it’s a development kit, so we want to add UART, RTT and GPIO support. Therefore, we will append the following:
# Enable RTT
CONFIG_USE_SEGGER_RTT=y
# enable GPIO
CONFIG_GPIO=y
# enable uart driver
CONFIG_SERIAL=y
# enable console
CONFIG_CONSOLE=y
CONFIG_UART_CONSOLE=y
# additional board options
CONFIG_GPIO_AS_PINRESET=y
CONFIG_PINCTRL=y
Note
<boardname>_defconfig is a Kconfig fragment merged as-is into the final build of any application built for the specified board, and must enable the bare minimum. It’s the application configuration’s (prj.conf) responsibility to configure what is needed.
4. devacademy_nrf52833.dts
The board-level devicetree file is a hardware description written in the devicetree format. It represents the schematics of your board, detailing its physical components and connections.
It includes connectors and any other hardware components such as LEDs, buttons, sensors, or communication peripherals (USB, BLE controller, etc). Memory partitioning is also done in this file. We will rely heavily on the automation provided by the nRF Connect for VS Code extension, including the Devicetree Visual Editor, to help us populate this file.
5. devacademy_nrf52833-pinctrl.dtsi
This file defines the pin-mapping of your board’s peripherals.
The extension does not create this file, so we must create it ourselves, which we will learn in Exercise 1 of this lesson.
Optional files
Now that we’ve covered the five mandatory files in the board layer, let’s take a look at the optional files.
Below is a board layer consisting of all mandatory files, optional, and special use cases files:
boards/<ARCH>/devacademy_nrf52833
├── Kconfig.board
├── Kconfig.defconfig
├── devacademy_nrf52833_defconfig
├── devacademy_nrf52833.dts
├── devacademy_nrf52833-pinctrl.dtsi
├── board.cmake # Used for flash and debug
├── CMakeLists.txt # Needed in special cases
├── c_files.c # Needed in special cases
├── doc # Optional
│ ├── devacademy_nrf52833.png
│ └── index.rst
├── Kconfig # Optional to create a board Kconfig options menu
├── devacademy_nrf52833.yaml # Optional for Test Runner (Twister)
├── devacademy_nrf52833_<revision>.conf # Needed to support multiple hardware revisions
├── devacademy_nrf52833_<revision>.overlay # Needed to support multiple hardware revisions
└── revision.cmake # Needed to support multiple hardware revisions
└── dts # Optional
└── bindings
The optional files are:
board.cmake: Used to add Flash and debug support to the board.CMakeLists.txt: Used to include source files to be executed pre- or post-kernel. For example, if your hardware requires custom mux configurations or needs to be configured in a particular way, it can be added to this file. This is done for the nRF52840 Dongle whereboard_nrf52840dongle_nrf52840_init()is executed atPRE_KERNEL_1before the kernel. Note that the extension does not create theCMakeLists.txtfile; you need to manually create it if needed.doc/index.rst,doc/devacademy_nrf52833.png: Documentation and image of the board, only needed if you are Contributing your board to Zephyr.Kconfig: Allows you to create a custom Kconfig menu specific to your board.devacademy_nrf52833.yaml: A YAML file with miscellaneous metadata used by Zephyr’s Test Runner (Twister).
Board revisions
When you create new hardware revisions for your board, such as changes to the schematics or a new PCB layout, you do not need to create a completely new board definition. Instead, you can simply add the revision-specific files within the same board folder: devacademy_nrf52833_<revision>.conf, devacademy_nrf52833_<revision>.overlay and revision.cmake
devacademy_nrf52833_<revision>.conf: The optional Kconfig settings specified here will be merged into the board’s default Kconfig configuration.devacademy_nrf52833_<revision>.overlay: The optional devicetree overlay will be added to the commondevacademy_nrf52833.dtsdevicetree file.revision.cmake: Controls how the Zephyr build system matches the<board>@<revision>string specified by the user when building an application for the board.
Note
When creating a new custom board, it is always a good idea to start looking into the SDK-defined boards with the same SoC/SiP as your custom board for inspiration. There is a long list of Development Kits, Prototyping Platforms, and Reference designs already shipped in the SDK that can serve as a good starting point.
They are available in two locations <install_path>/zephyr/boards/nordic/ and <install_path>/nrf/boards/nordic/
See the Zephyr Board Porting Guide.