Skip to content

Commit 3f4e152

Browse files
Vge0rgetomi-font
authored andcommitted
platform: nordic_nrf: Add nRF54L15 initial support
Before this there was only support for building the nRF54L15. This updates the nRF54L15 files to add an initial support for running TF-M. This is NOT full upstream support. There are important limitations: - Hardware crypto acceleration with Cracen is not supported - Random number generation with Cracen is not supported - The tests suites PSA arch tests and TF-M regression tests are not tested - BL2 is not supported - Some soc related configurations are not supported and they rely on hard-coded values (check nordicsemi_nrf54l_init for more info) This was tested using some basic Zephyr samples. This change updates the flash_layout.h and the region_maps.h headers with a layout that makes sense for the nRF54L15. Only one layout is supported at the moment. The RTE_Device.h is modified to use the UART20 and UART30 ports in order to support UART serial output. The function nordicsemi_nrf54l_init was copied from the soc.c in Zephyr and was simplified to support one single configuration. Later it can be considered to add configurability if needed. Signed-off-by: Georgios Vasilakis <[email protected]> Change-Id: I0369987cc1f4e7994078202e9d1bcb53c6372281 (cherry picked from commit 01b4551)
1 parent 75146b4 commit 3f4e152

File tree

11 files changed

+443
-500
lines changed

11 files changed

+443
-500
lines changed

platform/ext/target/nordic_nrf/common/nrf54l15/CMakeLists.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@
55
# SPDX-License-Identifier: BSD-3-Clause
66
#
77
#-------------------------------------------------------------------------------
8-
98
cmake_policy(SET CMP0076 NEW)
109
set(CMAKE_CURRENT_SOURCE_DIR ${CMAKE_CURRENT_LIST_DIR})
1110

@@ -22,6 +21,7 @@ target_include_directories(platform_s
2221
target_sources(platform_s
2322
PRIVATE
2423
${HAL_NORDIC_PATH}/nrfx/mdk/system_nrf54l.c
24+
${CMAKE_CURRENT_SOURCE_DIR}/nrf54l15_init.c
2525
)
2626

2727
target_compile_definitions(platform_s

platform/ext/target/nordic_nrf/common/nrf54l15/config.cmake

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88

99
include(${PLATFORM_PATH}/common/core/config.cmake)
1010

11-
set(SECURE_UART30 ON CACHE BOOL "Enable secure UART")
12-
set(NRF_NS_STORAGE OFF CACHE BOOL "Enable non-secure storage partition")
13-
set(BL2 OFF CACHE BOOL "Whether to build BL2")
14-
set(NRF_NS_SECONDARY OFF CACHE BOOL "Enable non-secure secondary partition")
11+
set(SECURE_UART30 ON CACHE BOOL "Enable secure UART" FORCE)
12+
set(BL2 OFF CACHE BOOL "Whether to build BL2" FORCE)
13+
set(NRF_NS_SECONDARY OFF CACHE BOOL "Enable non-secure secondary partition" FORCE)
14+
set(NRF_SECURE_UART_INSTANCE 30 CACHE STRING "The UART instance number to use for secure UART" FORCE)
Lines changed: 156 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,156 @@
1+
/*
2+
* Copyright (c) 2024 Nordic Semiconductor ASA
3+
*
4+
* SPDX-License-Identifier: BSD-3-Clause
5+
*
6+
*/
7+
#include <stdint.h>
8+
#include <nrfx.h>
9+
#include <hal/nrf_oscillators.h>
10+
#include <nrf_erratas.h>
11+
12+
/* This handler needs to be ported to the upstream TF-M project when Cracen is supported there.
13+
* The implementation of this is currently in sdk-nrf. We define it to avoid warnings when we build
14+
* the target_cfg.c file which is the same for both upsteam TF-M and sdk-nrf.
15+
* It is defined as weak to allow the sdk-nrf version to be used when available. */
16+
void __attribute__((weak)) CRACEN_IRQHandler(void){};
17+
18+
/* This is a simplified version of the function existing in the Zephyr's soc.c file for
19+
* the nRF54L15.
20+
* This function only supports one static configuration.
21+
* It is defined as weak to allow the sdk-nrf version to be used when available.
22+
*
23+
* The LFXO, HFXO configuration are taken from a sample build in sdk-nrf with the following
24+
* properties:
25+
*
26+
* lfxo: lfxo {
27+
* compatible = "nordic,nrf-lfxo";
28+
* #clock-cells = < 0x0 >;
29+
* clock-frequency = < 0x8000 >;
30+
* load-capacitors = "internal";
31+
* load-capacitance-femtofarad = < 0x3c8c >;
32+
* phandle = < 0xc >;
33+
* };
34+
* hfxo: hfxo {
35+
* compatible = "nordic,nrf-hfxo";
36+
* #clock-cells = < 0x0 >;
37+
* clock-frequency = < 0x1e84800 >;
38+
* load-capacitors = "internal";
39+
* load-capacitance-femtofarad = < 0x3a98 >;
40+
* phandle = < 0x6 >;
41+
* };
42+
*
43+
* The CONFIG_SOC_NRF_FORCE_CONSTLAT is not enabled.
44+
*
45+
* The following vreg configuration is supported:
46+
*
47+
* vregmain: regulator@120600 {
48+
* compatible = "nordic,nrf5x-regulator";
49+
* reg = < 0x120600 0x1 >;
50+
* status = "okay";
51+
* regulator-name = "VREGMAIN";
52+
* regulator-initial-mode = < 0x1 >; # 1 means NRF5X_REG_MODE_DCDC
53+
* };
54+
* And the NRF54L_ERRATA_31_ENABLE_WORKAROUND is enabled.
55+
*
56+
*/
57+
int __attribute__((weak)) nordicsemi_nrf54l_init(void){
58+
uint32_t xosc32ktrim = NRF_FICR->XOSC32KTRIM;
59+
60+
uint32_t offset_k =
61+
(xosc32ktrim & FICR_XOSC32KTRIM_OFFSET_Msk) >> FICR_XOSC32KTRIM_OFFSET_Pos;
62+
63+
uint32_t slope_field_k =
64+
(xosc32ktrim & FICR_XOSC32KTRIM_SLOPE_Msk) >> FICR_XOSC32KTRIM_SLOPE_Pos;
65+
uint32_t slope_mask_k = FICR_XOSC32KTRIM_SLOPE_Msk >> FICR_XOSC32KTRIM_SLOPE_Pos;
66+
uint32_t slope_sign_k = (slope_mask_k - (slope_mask_k >> 1));
67+
int32_t slope_k = (int32_t)(slope_field_k ^ slope_sign_k) - (int32_t)slope_sign_k;
68+
69+
/* As specified in the nRF54L15 PS:
70+
* CAPVALUE = round( (CAPACITANCE - 4) * (FICR->XOSC32KTRIM.SLOPE + 0.765625 * 2^9)/(2^9)
71+
* + FICR->XOSC32KTRIM.OFFSET/(2^6) );
72+
* where CAPACITANCE is the desired capacitor value in pF, holding any
73+
* value between 4 pF and 18 pF in 0.5 pF steps.
74+
*/
75+
76+
/* Encoding of desired capacitance (single ended) to value required for INTCAP core
77+
* calculation: (CAP_VAL - 4 pF)* 0.5
78+
* That translate to ((CAP_VAL_FEMTO_F - 4000fF) * 2UL) / 1000UL
79+
*
80+
* NOTE: The desired capacitance value is used in encoded from in INTCAP calculation formula
81+
* That is different than in case of HFXO.
82+
*/
83+
uint32_t cap_val_encoded =
84+
(((0x3c8c - 4000UL) * 2UL) / 1000UL);
85+
86+
/* Calculation of INTCAP code before rounding. Min that calculations here are done on
87+
* values multiplied by 2^9, e.g. 0.765625 * 2^9 = 392.
88+
* offset_k should be divided by 2^6, but to add it to value shifted by 2^9 we have to
89+
* multiply it be 2^3.
90+
*/
91+
uint32_t mid_val =
92+
(cap_val_encoded - 4UL) * (uint32_t)(slope_k + 392UL) + (offset_k << 3UL);
93+
94+
/* Get integer part of the INTCAP code */
95+
uint32_t lfxo_intcap = mid_val >> 9UL;
96+
97+
/* Round based on fractional part */
98+
if ((mid_val & BIT_MASK(9)) > (BIT_MASK(9) / 2)) {
99+
lfxo_intcap++;
100+
}
101+
102+
nrf_oscillators_lfxo_cap_set(NRF_OSCILLATORS, lfxo_intcap);
103+
104+
uint32_t xosc32mtrim = NRF_FICR->XOSC32MTRIM;
105+
/* The SLOPE field is in the two's complement form, hence this special
106+
* handling. Ideally, it would result in just one SBFX instruction for
107+
* extracting the slope value, at least gcc is capable of producing such
108+
* output, but since the compiler apparently tries first to optimize
109+
* additions and subtractions, it generates slightly less than optimal
110+
* code.
111+
*/
112+
uint32_t slope_field =
113+
(xosc32mtrim & FICR_XOSC32MTRIM_SLOPE_Msk) >> FICR_XOSC32MTRIM_SLOPE_Pos;
114+
uint32_t slope_mask = FICR_XOSC32MTRIM_SLOPE_Msk >> FICR_XOSC32MTRIM_SLOPE_Pos;
115+
uint32_t slope_sign = (slope_mask - (slope_mask >> 1));
116+
int32_t slope_m = (int32_t)(slope_field ^ slope_sign) - (int32_t)slope_sign;
117+
uint32_t offset_m =
118+
(xosc32mtrim & FICR_XOSC32MTRIM_OFFSET_Msk) >> FICR_XOSC32MTRIM_OFFSET_Pos;
119+
/* As specified in the nRF54L15 PS:
120+
* CAPVALUE = (((CAPACITANCE-5.5)*(FICR->XOSC32MTRIM.SLOPE+791)) +
121+
* FICR->XOSC32MTRIM.OFFSET<<2)>>8;
122+
* where CAPACITANCE is the desired total load capacitance value in pF,
123+
* holding any value between 4.0 pF and 17.0 pF in 0.25 pF steps.
124+
*/
125+
126+
/* NOTE 1: Requested HFXO internal capacitance in femto Faradas is used directly in formula
127+
* to calculate INTCAP code. That is different than in case of LFXO.
128+
*
129+
* NOTE 2: PS formula uses piko Farads, the implementation of the formula uses femto Farads
130+
* to avoid use of floating point data type.
131+
*/
132+
uint32_t cap_val_femto_f = 0x3a98;
133+
134+
uint32_t mid_val_intcap = (((cap_val_femto_f - 5500UL) * (uint32_t)(slope_m + 791UL)) +
135+
(offset_m << 2UL) * 1000UL) >>
136+
8UL;
137+
138+
/* Convert the calculated value to piko Farads */
139+
uint32_t hfxo_intcap = mid_val_intcap / 1000;
140+
141+
/* Round based on fractional part */
142+
if (mid_val_intcap % 1000 >= 500) {
143+
hfxo_intcap++;
144+
}
145+
146+
nrf_oscillators_hfxo_cap_set(NRF_OSCILLATORS, true, hfxo_intcap);
147+
148+
/* Workaround for Errata 31 */
149+
if (nrf54l_errata_31()) {
150+
*((volatile uint32_t *)0x50120624ul) = 20 | 1<<5;
151+
*((volatile uint32_t *)0x5012063Cul) &= ~(1<<19);
152+
}
153+
154+
155+
return 0;
156+
}

platform/ext/target/nordic_nrf/common/nrf54l15/partition/flash_layout.h

Lines changed: 142 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
/*
2-
* Copyright (c) 2018-2022 Arm Limited. All rights reserved.
3-
* Copyright (c) 2020 Nordic Semiconductor ASA. All rights reserved.
2+
* Copyright (c) 2025 Nordic Semiconductor ASA. All rights reserved.
43
*
54
* Licensed under the Apache License, Version 2.0 (the "License");
65
* you may not use this file except in compliance with the License.
@@ -18,6 +17,146 @@
1817
#ifndef __FLASH_LAYOUT_H__
1918
#define __FLASH_LAYOUT_H__
2019

21-
#error "not supported yet"
20+
#ifdef BL2
21+
#error "BL2 is not supported for this platform"
22+
#endif
23+
24+
/* Flash layout on NRF54L15 Application MCU without BL2:
25+
*
26+
* 0x0000_0000 Secure image primary (512 KB)
27+
* 0x0008_0000 Protected Storage Area (16 KB)
28+
* 0x0008_4000 Internal Trusted Storage Area (16 KB)
29+
* 0x0008_8000 OTP / NV counters area (8 KB)
30+
* 0x0008_A000 Non-secure image primary (844 KB)
31+
* 0x0015_D000 Non-secure storage, used when built with NRF_NS_STORAGE=ON,
32+
* otherwise unused (32 KB)
33+
*/
34+
35+
/* This header file is included from linker scatter file as well, where only a
36+
* limited C constructs are allowed. Therefore it is not possible to include
37+
* here the platform_base_address.h to access flash related defines. To resolve
38+
* this some of the values are redefined here with different names, these are
39+
* marked with comment.
40+
*/
41+
42+
/* Use Flash memory to store Code data */
43+
#define FLASH_BASE_ADDRESS (0x0)
44+
45+
/* nRF54L15 has 1524 kB of non volatile memory (RRAM) but the last 96kB are reserved
46+
* for FLPR MCU in Zephyr. For simplicity and for possible support for running FLPR along
47+
* with TF-M later FLPR non volatile memory is not used by TF-M. */
48+
#define FLASH_TOTAL_SIZE (0x165000) /* 1428 kB since the last 96kB are reserved for FLPR */
49+
#define TOTAL_ROM_SIZE FLASH_TOTAL_SIZE
50+
51+
/* nRF54L15 has 256 kB of volatile memory (SRAM) but the last 96kB are reserved
52+
* for FLPR MCU in Zephyr. For simplicity and for possible support for running FLPR along
53+
* with TF-M later FLPR volatile memory is not used by TF-M. */
54+
#define SRAM_BASE_ADDRESS (0x20000000)
55+
#define TOTAL_RAM_SIZE (0x00028000) /* 160 kB, since the last 96kB are reserved for FLPR */
56+
57+
#define FLASH_S_PARTITION_SIZE (0x80000) /* S partition: 512 kB*/
58+
#define FLASH_NS_PARTITION_SIZE (0xD3000) /* NS partition: 844 kB*/
59+
60+
#define S_ROM_ALIAS_BASE FLASH_BASE_ADDRESS
61+
#define NS_ROM_ALIAS_BASE FLASH_BASE_ADDRESS
62+
63+
/* Use SRAM memory to store RW data */
64+
#define S_RAM_ALIAS_BASE SRAM_BASE_ADDRESS
65+
#define NS_RAM_ALIAS_BASE SRAM_BASE_ADDRESS
66+
67+
/* Sector size of the embedded flash hardware (erase/program) */
68+
#define FLASH_AREA_IMAGE_SECTOR_SIZE (0x1000) /* 4 KB. Flash memory program/erase operations have a page granularity. */
69+
70+
#if (FLASH_S_PARTITION_SIZE > FLASH_NS_PARTITION_SIZE)
71+
#define FLASH_MAX_PARTITION_SIZE FLASH_S_PARTITION_SIZE
72+
#else
73+
#define FLASH_MAX_PARTITION_SIZE FLASH_NS_PARTITION_SIZE
74+
#endif
75+
76+
/* Offset and size definition in flash area used by assemble.py */
77+
#define SECURE_IMAGE_MAX_SIZE FLASH_S_PARTITION_SIZE
78+
#define NON_SECURE_IMAGE_MAX_SIZE FLASH_NS_PARTITION_SIZE
79+
80+
#define SECURE_STORAGE_PARTITIONS_START (FLASH_BASE_ADDRESS + FLASH_S_PARTITION_SIZE)
81+
82+
/* Protected Storage (PS) Service definitions */
83+
#define FLASH_PS_AREA_OFFSET (SECURE_STORAGE_PARTITIONS_START)
84+
#define FLASH_PS_AREA_SIZE (0x4000) /* 16 KB */
85+
86+
/* Internal Trusted Storage (ITS) Service definitions */
87+
#define FLASH_ITS_AREA_OFFSET (FLASH_PS_AREA_OFFSET + FLASH_PS_AREA_SIZE)
88+
#define FLASH_ITS_AREA_SIZE (0x4000) /* 16 KB */
89+
90+
/* OTP_definitions */
91+
#define FLASH_OTP_NV_COUNTERS_AREA_OFFSET (FLASH_ITS_AREA_OFFSET + FLASH_ITS_AREA_SIZE)
92+
#define FLASH_OTP_NV_COUNTERS_AREA_SIZE (0x2000) /* 8KB */
93+
94+
#define FLASH_OTP_NV_COUNTERS_SECTOR_SIZE FLASH_AREA_IMAGE_SECTOR_SIZE
95+
96+
#define SECURE_STORAGE_PARTITIONS_END (FLASH_OTP_NV_COUNTERS_AREA_OFFSET + FLASH_OTP_NV_COUNTERS_AREA_SIZE)
97+
/* END OF PARTITIONS LAYOUT */
98+
99+
#define SECURE_IMAGE_OFFSET (0x0)
100+
#define NON_SECURE_IMAGE_OFFSET (SECURE_STORAGE_PARTITIONS_END)
101+
102+
/* Non-secure storage region */
103+
#define NRF_FLASH_NS_STORAGE_AREA_SIZE (0x8000) /* 32 KB */
104+
#define NRF_FLASH_NS_STORAGE_AREA_OFFSET (FLASH_TOTAL_SIZE - \
105+
NRF_FLASH_NS_STORAGE_AREA_SIZE)
106+
107+
/* Flash device name used by BL2
108+
* Name is defined in flash driver file: Driver_Flash.c
109+
*/
110+
//#define FLASH_DEV_NAME Driver_FLASH0
111+
/* Smallest flash programmable unit in bytes */
112+
#define TFM_HAL_FLASH_PROGRAM_UNIT (0x4)
113+
114+
/* Protected Storage (PS) Service definitions
115+
* Note: Further documentation of these definitions can be found in the
116+
* TF-M PS Integration Guide.
117+
*/
118+
#define TFM_HAL_PS_FLASH_DRIVER Driver_FLASH0
119+
120+
/* In this target the CMSIS driver requires only the offset from the base
121+
* address instead of the full memory address.
122+
*/
123+
/* Base address of dedicated flash area for PS */
124+
#define TFM_HAL_PS_FLASH_AREA_ADDR FLASH_PS_AREA_OFFSET
125+
/* Size of dedicated flash area for PS */
126+
#define TFM_HAL_PS_FLASH_AREA_SIZE FLASH_PS_AREA_SIZE
127+
#define PS_RAM_FS_SIZE TFM_HAL_PS_FLASH_AREA_SIZE
128+
/* Number of physical erase sectors per logical FS block */
129+
#define TFM_HAL_PS_SECTORS_PER_BLOCK (1)
130+
/* Smallest flash programmable unit in bytes */
131+
#define TFM_HAL_PS_PROGRAM_UNIT (0x4)
132+
133+
/* Internal Trusted Storage (ITS) Service definitions
134+
* Note: Further documentation of these definitions can be found in the
135+
* TF-M ITS Integration Guide. The ITS should be in the internal flash, but is
136+
* allocated in the external flash just for development platforms that don't
137+
* have internal flash available.
138+
*/
139+
#define TFM_HAL_ITS_FLASH_DRIVER Driver_FLASH0
140+
141+
/* In this target the CMSIS driver requires only the offset from the base
142+
* address instead of the full memory address.
143+
*/
144+
/* Base address of dedicated flash area for ITS */
145+
#define TFM_HAL_ITS_FLASH_AREA_ADDR FLASH_ITS_AREA_OFFSET
146+
/* Size of dedicated flash area for ITS */
147+
#define TFM_HAL_ITS_FLASH_AREA_SIZE FLASH_ITS_AREA_SIZE
148+
#define ITS_RAM_FS_SIZE TFM_HAL_ITS_FLASH_AREA_SIZE
149+
/* Number of physical erase sectors per logical FS block */
150+
#define TFM_HAL_ITS_SECTORS_PER_BLOCK (1)
151+
/* Smallest flash programmable unit in bytes */
152+
#define TFM_HAL_ITS_PROGRAM_UNIT (0x4)
153+
154+
/* OTP / NV counter definitions */
155+
#define TFM_OTP_NV_COUNTERS_AREA_SIZE (FLASH_OTP_NV_COUNTERS_AREA_SIZE / 2)
156+
#define TFM_OTP_NV_COUNTERS_AREA_ADDR FLASH_OTP_NV_COUNTERS_AREA_OFFSET
157+
#define TFM_OTP_NV_COUNTERS_SECTOR_SIZE FLASH_OTP_NV_COUNTERS_SECTOR_SIZE
158+
#define TFM_OTP_NV_COUNTERS_BACKUP_AREA_ADDR (TFM_OTP_NV_COUNTERS_AREA_ADDR + \
159+
TFM_OTP_NV_COUNTERS_AREA_SIZE)
160+
22161

23162
#endif /* __FLASH_LAYOUT_H__ */

0 commit comments

Comments
 (0)