From 36c772aa6d50a722c9f5e3962aa6679ad1999db9 Mon Sep 17 00:00:00 2001 From: Aksel Skauge Mellbye Date: Thu, 3 Oct 2024 21:38:18 +0200 Subject: [PATCH] soc: silabs: Add soc_prep_hook() for Series 2 CMSIS SystemInit is not used in Zephyr. Implement the functionality that isn't already done by Zephyr startup using soc_prep_hook(). The reason the lack of TrustZone init did not cause issues previously is that SMU faults can only happen if the SMU clock is enabled. Signed-off-by: Aksel Skauge Mellbye --- soc/silabs/silabs_s2/Kconfig | 4 +++ soc/silabs/silabs_s2/soc.c | 63 ++++++++++++++++++++++++++++++++++++ west.yml | 2 +- 3 files changed, 68 insertions(+), 1 deletion(-) diff --git a/soc/silabs/silabs_s2/Kconfig b/soc/silabs/silabs_s2/Kconfig index 793a34bd6d2e1e..21129590f14f17 100644 --- a/soc/silabs/silabs_s2/Kconfig +++ b/soc/silabs/silabs_s2/Kconfig @@ -6,10 +6,14 @@ if SOC_FAMILY_SILABS_S2 config SOC_FAMILY_SILABS_S2 select HAS_SEGGER_RTT if ZEPHYR_SEGGER_MODULE select BUILD_OUTPUT_HEX + select SOC_PREP_HOOK select SOC_EARLY_INIT_HOOK rsource "*/Kconfig" +config ARM_SECURE_FIRMWARE + default y + config HW_HAS_SILABS_DCDC def_bool $(dt_compat_enabled,$(DT_COMPAT_SILABS_SERIES2_DCDC)) diff --git a/soc/silabs/silabs_s2/soc.c b/soc/silabs/silabs_s2/soc.c index a4861878f39ae2..e58823c16f9637 100644 --- a/soc/silabs/silabs_s2/soc.c +++ b/soc/silabs/silabs_s2/soc.c @@ -11,6 +11,7 @@ #include #include +#include #include @@ -22,6 +23,18 @@ #include #endif +#if defined(CONFIG_PRINTK) || defined(CONFIG_LOG) +#define PR_EXC(...) LOG_ERR(__VA_ARGS__) +#else +#define PR_EXC(...) +#endif /* CONFIG_PRINTK || CONFIG_LOG */ + +#if (CONFIG_FAULT_DUMP == 2) +#define PR_FAULT_INFO(...) PR_EXC(__VA_ARGS__) +#else +#define PR_FAULT_INFO(...) +#endif + LOG_MODULE_REGISTER(soc, CONFIG_SOC_LOG_LEVEL); void soc_early_init_hook(void) @@ -39,3 +52,53 @@ void soc_early_init_hook(void) sl_hfxo_manager_init(); #endif } + +#if defined(CONFIG_ARM_SECURE_FIRMWARE) && !defined(CONFIG_ARM_FIRMWARE_HAS_SECURE_ENTRY_FUNCS) +static void smu_fault(void) +{ + PR_FAULT_INFO("***** SMU FAULT *****"); + + if (SMU->IF & SMU_IF_BMPUSEC) { + PR_FAULT_INFO("Bus Manager Fault"); + PR_EXC("SMU.BMPUFS=%d", SMU->BMPUFS); + } + if (SMU->IF & SMU_IF_PPUSEC) { + PR_FAULT_INFO("Peripheral Access Fault"); + PR_EXC("SMU.PPUFS=%d", SMU->PPUFS); + } + + z_fatal_error(K_ERR_CPU_EXCEPTION, NULL); +} +#endif + +void soc_prep_hook(void) +{ + /* Initialize TrustZone state of the device. + * If this is a secure app with no non-secure callable functions, it is a secure-only app. + * Configure all peripherals except the SMU and SEMAILBOX to non-secure aliases, and make + * all bus transactions from the CPU have non-secure attribution. + * This makes the secure-only app behave more like a non-secure app, allowing the use of + * libraries that only expect to use non-secure peripherals, such as the radio subsystem. + */ +#if defined(CONFIG_ARM_SECURE_FIRMWARE) && !defined(CONFIG_ARM_FIRMWARE_HAS_SECURE_ENTRY_FUNCS) + CMU_S->CLKEN1_SET = CMU_CLKEN1_SMU; + + SMU->PPUSATD0_CLR = _SMU_PPUSATD0_MASK; +#if defined(SEMAILBOX_PRESENT) + SMU->PPUSATD1_CLR = (_SMU_PPUSATD1_MASK & (~SMU_PPUSATD1_SMU & ~SMU_PPUSATD1_SEMAILBOX)); +#else + SMU->PPUSATD1_CLR = (_SMU_PPUSATD1_MASK & ~SMU_PPUSATD1_SMU); +#endif + + SAU->CTRL = SAU_CTRL_ALLNS_Msk; + __DSB(); + __ISB(); + + NVIC_ClearPendingIRQ(SMU_SECURE_IRQn); + SMU->IF_CLR = SMU_IF_PPUSEC | SMU_IF_BMPUSEC; + SMU->IEN = SMU_IEN_PPUSEC | SMU_IEN_BMPUSEC; + + IRQ_DIRECT_CONNECT(SMU_SECURE_IRQn, 0, smu_fault, 0); + irq_enable(SMU_SECURE_IRQn); +#endif +} diff --git a/west.yml b/west.yml index 8108a1b13a541c..399d7ced23a106 100644 --- a/west.yml +++ b/west.yml @@ -223,7 +223,7 @@ manifest: groups: - hal - name: hal_silabs - revision: pull/73/head + revision: pull/74/head path: modules/hal/silabs groups: - hal