From 2f0efa8c9edae98ec055badd2341afac834ea3e1 Mon Sep 17 00:00:00 2001 From: Alexandre Abadie Date: Wed, 15 Dec 2021 15:53:53 +0100 Subject: [PATCH 1/6] cpu/stm32: add initial support for stm32u5 family --- cpu/stm32/Makefile.cmsis | 1 + cpu/stm32/Makefile.features | 6 +- cpu/stm32/cpu_common.c | 78 +++- cpu/stm32/cpu_init.c | 4 +- cpu/stm32/dist/irqs/gen_irqs.py | 2 + ...on_lx_wx.h => cfg_clock_common_lx_u5_wx.h} | 8 +- cpu/stm32/include/clk/clk_conf.h | 6 +- cpu/stm32/include/clk/u5/cfg_clock_default.h | 130 +++++++ cpu/stm32/include/cpu_conf.h | 13 +- cpu/stm32/include/cpu_conf_stm32_common.h | 5 +- cpu/stm32/include/periph/u5/periph_cpu.h | 42 +++ cpu/stm32/include/periph_cpu.h | 26 +- .../0001-stm32u5xx-remove-ErrorStatus.patch | Bin 0 -> 1375 bytes cpu/stm32/kconfigs/Kconfig.clk | 4 +- cpu/stm32/kconfigs/u5/Kconfig | 26 ++ cpu/stm32/kconfigs/u5/Kconfig.lines | 19 + cpu/stm32/kconfigs/u5/Kconfig.models | 120 +++++++ cpu/stm32/periph/Makefile | 2 +- cpu/stm32/periph/flash_common.c | 11 +- cpu/stm32/periph/flashpage.c | 20 +- cpu/stm32/periph/gpio_all.c | 30 +- cpu/stm32/periph/hwrng.c | 4 + cpu/stm32/periph/pm.c | 7 +- cpu/stm32/periph/uart.c | 15 +- cpu/stm32/stm32_info.mk | 4 +- cpu/stm32/stm32_mem_lengths.mk | 6 + cpu/stm32/stmclk/Makefile | 2 + cpu/stm32/stmclk/stmclk_common.c | 13 +- cpu/stm32/stmclk/stmclk_u5.c | 334 ++++++++++++++++++ 29 files changed, 868 insertions(+), 70 deletions(-) rename cpu/stm32/include/clk/{cfg_clock_common_lx_wx.h => cfg_clock_common_lx_u5_wx.h} (93%) create mode 100644 cpu/stm32/include/clk/u5/cfg_clock_default.h create mode 100644 cpu/stm32/include/periph/u5/periph_cpu.h create mode 100644 cpu/stm32/include/vendor/patches/u5/0001-stm32u5xx-remove-ErrorStatus.patch create mode 100644 cpu/stm32/kconfigs/u5/Kconfig create mode 100644 cpu/stm32/kconfigs/u5/Kconfig.lines create mode 100644 cpu/stm32/kconfigs/u5/Kconfig.models create mode 100644 cpu/stm32/stmclk/stmclk_u5.c diff --git a/cpu/stm32/Makefile.cmsis b/cpu/stm32/Makefile.cmsis index d1cc6c8380..e6f1586105 100644 --- a/cpu/stm32/Makefile.cmsis +++ b/cpu/stm32/Makefile.cmsis @@ -15,6 +15,7 @@ PKG_VERSION_l0=532d96973e7b2ae5546a2c88cb216429f74f5f5d # v1.9.2 PKG_VERSION_l1=1827333a7f7822282a6a46e4169596b5fb58cf61 # v2.3.2 PKG_VERSION_l4=26ed4846f831f730d852507e178061053e522daf # v1.7.1 PKG_VERSION_l5=fcf61cd086e02c7a1cf7535ffe30622d1f5d36aa # v1.0.4 +PKG_VERSION_u5=147947d99f50554101d2a339ad19c2972c3ff161 # v1.0.1 PKG_VERSION_wb=3a801574163338b562f56e7eb503a955818f1a56 # v1.9.0 PKG_VERSION_wl=7bf548678b1132d829072ce86443c8036d538460 # v1.1.0 diff --git a/cpu/stm32/Makefile.features b/cpu/stm32/Makefile.features index 06a7e47285..935cf7a3d2 100644 --- a/cpu/stm32/Makefile.features +++ b/cpu/stm32/Makefile.features @@ -12,12 +12,12 @@ FEATURES_PROVIDED += periph_rtt_overflow FEATURES_PROVIDED += periph_uart_modecfg FEATURES_PROVIDED += periph_uart_nonblocking -ifneq (,$(filter $(CPU_FAM),f0 f1 f3 g0 g4 l0 l1 l4 l5 wb wl)) +ifneq (,$(filter $(CPU_FAM),f0 f1 f3 g0 g4 l0 l1 l4 l5 u5 wb wl)) FEATURES_PROVIDED += periph_flashpage FEATURES_PROVIDED += periph_flashpage_pagewise endif -ifneq (,$(filter $(CPU_FAM),f0 f2 f3 f4 f7 l0 l1 l4 l5 wb wl)) +ifneq (,$(filter $(CPU_FAM),f0 f2 f3 f4 f7 l0 l1 l4 l5 u5 wb wl)) CPU_MODELS_WITHOUT_RTC_BKPR += stm32f030% stm32f070% ifeq (,$(filter $(CPU_MODELS_WITHOUT_RTC_BKPR),$(CPU_MODEL))) FEATURES_PROVIDED += periph_rtc_mem @@ -41,7 +41,7 @@ endif # Not all F4 and L0 parts implement a RNG. CPU_MODELS_WITHOUT_HWRNG = stm32f401% stm32f411% stm32f446% stm32l031% stm32l011% -ifneq (,$(filter $(CPU_FAM),f2 f4 f7 g4 l0 l4 l5 wb)) +ifneq (,$(filter $(CPU_FAM),f2 f4 f7 g4 l0 l4 l5 u5 wb)) ifeq (,$(filter $(CPU_MODELS_WITHOUT_HWRNG),$(CPU_MODEL))) FEATURES_PROVIDED += periph_hwrng endif diff --git a/cpu/stm32/cpu_common.c b/cpu/stm32/cpu_common.c index 73a96e7de5..f1d0055b63 100644 --- a/cpu/stm32/cpu_common.c +++ b/cpu/stm32/cpu_common.c @@ -37,15 +37,17 @@ static const uint8_t apbmul[] = { #if (CLOCK_APB1 < CLOCK_CORECLOCK) [APB1] = 2, #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ - defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) || \ - defined(CPU_FAM_STM32WL) || defined(CPU_FAM_STM32G0) + defined(CPU_FAM_STM32G0) || defined(CPU_FAM_STM32G4) || \ + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) [APB12] = 2, #endif #else [APB1] = 1, #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ - defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) || \ - defined(CPU_FAM_STM32WL) || defined(CPU_FAM_STM32G0) + defined(CPU_FAM_STM32G0) || defined(CPU_FAM_STM32G4) || \ + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) [APB12] = 1, #endif #endif @@ -79,7 +81,7 @@ void periph_clk_en(bus_t bus, uint32_t mask) case APB1: #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) || \ - defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32U5) || defined(CPU_FAM_STM32WL) RCC->APB1ENR1 |= mask; #elif defined(CPU_FAM_STM32G0) RCC->APBENR1 |= mask; @@ -98,14 +100,14 @@ void periph_clk_en(bus_t bus, uint32_t mask) #endif break; #endif -#if defined(CPU_FAM_STM32WL) +#if defined(CPU_FAM_STM32WL) || defined(CPU_FAM_STM32U5) case APB3: RCC->APB3ENR |= mask; break; #endif #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) || \ - defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32U5) || defined(CPU_FAM_STM32WL) case APB12: RCC->APB1ENR2 |= mask; break; @@ -129,15 +131,25 @@ void periph_clk_en(bus_t bus, uint32_t mask) #elif defined(CPU_FAM_STM32F2) || defined(CPU_FAM_STM32F4) || \ defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32F7) || \ defined(CPU_FAM_STM32WB) || defined(CPU_FAM_STM32G4) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) case AHB1: RCC->AHB1ENR |= mask; break; /* STM32F410 RCC doesn't provide AHB2 and AHB3 */ #if !defined(CPU_LINE_STM32F410Rx) case AHB2: +#if defined(CPU_FAM_STM32U5) + RCC->AHB2ENR1 |= mask; +#else RCC->AHB2ENR |= mask; +#endif break; +#if defined(CPU_FAM_STM32U5) + case AHB22: + RCC->AHB2ENR2 |= mask; + break; +#endif case AHB3: RCC->AHB3ENR |= mask; break; @@ -162,7 +174,7 @@ void periph_clk_dis(bus_t bus, uint32_t mask) case APB1: #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) || \ - defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32U5) || defined(CPU_FAM_STM32WL) RCC->APB1ENR1 &= ~(mask); #elif defined(CPU_FAM_STM32G0) RCC->APBENR1 &= ~(mask); @@ -182,14 +194,14 @@ void periph_clk_dis(bus_t bus, uint32_t mask) #endif break; #endif -#if defined(CPU_FAM_STM32WL) +#if defined(CPU_FAM_STM32WL) || defined(CPU_FAM_STM32U5) case APB3: RCC->APB3ENR &= ~(mask); break; #endif #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) || \ - defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32U5) || defined(CPU_FAM_STM32WL) case APB12: RCC->APB1ENR2 &= ~(mask); break; @@ -213,15 +225,25 @@ void periph_clk_dis(bus_t bus, uint32_t mask) #elif defined(CPU_FAM_STM32F2) || defined(CPU_FAM_STM32F4) || \ defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32F7) || \ defined(CPU_FAM_STM32WB) || defined(CPU_FAM_STM32G4) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) case AHB1: RCC->AHB1ENR &= ~(mask); break; /* STM32F410 RCC doesn't provide AHB2 and AHB3 */ #if !defined(CPU_LINE_STM32F410Rx) case AHB2: +#if defined(CPU_FAM_STM32U5) + RCC->AHB2ENR1 &= ~(mask); +#else RCC->AHB2ENR &= ~(mask); +#endif break; +#if defined(CPU_FAM_STM32U5) + case AHB22: + RCC->AHB2ENR2 &= ~(mask); + break; +#endif case AHB3: RCC->AHB3ENR &= ~(mask); break; @@ -239,25 +261,34 @@ void periph_clk_dis(bus_t bus, uint32_t mask) } #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32G4) || \ - defined(CPU_FAM_STM32L5) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) void periph_lpclk_en(bus_t bus, uint32_t mask) { switch (bus) { case APB1: RCC->APB1SMENR1 |= mask; break; - case APB2: - RCC->APB2SMENR |= mask; - break; case APB12: RCC->APB1SMENR2 |= mask; break; + case APB2: + RCC->APB2SMENR |= mask; + break; case AHB1: RCC->AHB1SMENR |= mask; break; case AHB2: +#if defined(CPU_FAM_STM32U5) + RCC->AHB2SMENR1 |= mask; +#else RCC->AHB2SMENR |= mask; +#endif break; +#if defined(CPU_FAM_STM32U5) + case AHB22: + RCC->AHB2SMENR2 |= mask; + break; +#endif case AHB3: RCC->AHB3SMENR |= mask; break; @@ -273,18 +304,27 @@ void periph_lpclk_dis(bus_t bus, uint32_t mask) case APB1: RCC->APB1SMENR1 &= ~(mask); break; - case APB2: - RCC->APB2SMENR &= ~(mask); - break; case APB12: RCC->APB1SMENR2 &= ~(mask); break; + case APB2: + RCC->APB2SMENR &= ~(mask); + break; case AHB1: RCC->AHB1SMENR &= ~(mask); break; case AHB2: +#if defined(CPU_FAM_STM32U5) + RCC->AHB2SMENR1 &= ~(mask); +#else RCC->AHB2SMENR &= ~(mask); +#endif break; +#if defined(CPU_FAM_STM32U5) + case AHB22: + RCC->AHB2SMENR2 &= ~(mask); + break; +#endif case AHB3: RCC->AHB3SMENR &= ~(mask); break; diff --git a/cpu/stm32/cpu_init.c b/cpu/stm32/cpu_init.c index 1ffa72b35c..91312aee57 100644 --- a/cpu/stm32/cpu_init.c +++ b/cpu/stm32/cpu_init.c @@ -336,7 +336,9 @@ void cpu_init(void) /* initialize the Cortex-M core */ cortexm_init(); /* enable PWR module */ -#if !defined(CPU_FAM_STM32WB) && !defined(CPU_FAM_STM32MP1) && \ +#if defined(CPU_FAM_STM32U5) + periph_clk_en(AHB3, RCC_AHB3ENR_PWREN); +#elif !defined(CPU_FAM_STM32WB) && !defined(CPU_FAM_STM32MP1) && \ !defined(CPU_FAM_STM32WL) periph_clk_en(APB1, BIT_APB_PWREN); #endif diff --git a/cpu/stm32/dist/irqs/gen_irqs.py b/cpu/stm32/dist/irqs/gen_irqs.py index 367ac099e4..5e36526034 100755 --- a/cpu/stm32/dist/irqs/gen_irqs.py +++ b/cpu/stm32/dist/irqs/gen_irqs.py @@ -52,6 +52,8 @@ def list_cpu_lines(cmsis_dir, cpu_fam): headers.remove("Templates") if "partition_stm32l5xx.h" in headers: headers.remove("partition_stm32l5xx.h") + if "partition_stm32u5xx.h" in headers: + headers.remove("partition_stm32u5xx.h") headers.remove("stm32{}xx.h".format(cpu_fam)) headers.remove("system_stm32{}xx.h".format(cpu_fam)) return sorted([header.split(".")[0] for header in headers]) diff --git a/cpu/stm32/include/clk/cfg_clock_common_lx_wx.h b/cpu/stm32/include/clk/cfg_clock_common_lx_u5_wx.h similarity index 93% rename from cpu/stm32/include/clk/cfg_clock_common_lx_wx.h rename to cpu/stm32/include/clk/cfg_clock_common_lx_u5_wx.h index ab6e015aa7..9a7a6ae9df 100644 --- a/cpu/stm32/include/clk/cfg_clock_common_lx_wx.h +++ b/cpu/stm32/include/clk/cfg_clock_common_lx_u5_wx.h @@ -13,15 +13,15 @@ * @{ * * @file - * @brief Base STM32Lx/Wx clock configuration + * @brief Base STM32Lx/U5/Wx clock configuration * * @author Hauke Petersen * @author Vincent Dupont * @author Alexandre Abadie */ -#ifndef CLK_CFG_CLOCK_COMMON_LX_WX_H -#define CLK_CFG_CLOCK_COMMON_LX_WX_H +#ifndef CLK_CFG_CLOCK_COMMON_LX_U5_WX_H +#define CLK_CFG_CLOCK_COMMON_LX_U5_WX_H #ifdef __cplusplus extern "C" { @@ -88,5 +88,5 @@ extern "C" { } #endif -#endif /* CLK_CFG_CLOCK_COMMON_LX_WX_H */ +#endif /* CLK_CFG_CLOCK_COMMON_LX_U5_WX_H */ /** @} */ diff --git a/cpu/stm32/include/clk/clk_conf.h b/cpu/stm32/include/clk/clk_conf.h index 28160d2fc6..57e31b611b 100644 --- a/cpu/stm32/include/clk/clk_conf.h +++ b/cpu/stm32/include/clk/clk_conf.h @@ -29,8 +29,8 @@ defined(CPU_FAM_STM32MP1) #include "cfg_clock_common_fx_gx_mp1.h" #else /* CPU_FAM_STM32L0 || CPU_FAM_STM32L1 || CPU_FAM_STM32L4 || - * CPU_FAM_STM32L5 || CPU_FAM_STM32WB */ -#include "cfg_clock_common_lx_wx.h" + * CPU_FAM_STM32L5 || CPU_FAM_STM32U5 || CPU_FAM_STM32WB */ +#include "cfg_clock_common_lx_u5_wx.h" #endif #if defined(CPU_FAM_STM32F0) || defined(CPU_FAM_STM32F1) || \ @@ -46,6 +46,8 @@ #elif defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32L5) || \ defined(CPU_FAM_STM32WB) || defined(CPU_FAM_STM32WL) #include "l4l5wx/cfg_clock_default.h" +#elif defined(CPU_FAM_STM32U5) +#include "u5/cfg_clock_default.h" #elif defined(CPU_FAM_STM32MP1) #include "mp1/cfg_clock_default.h" #else diff --git a/cpu/stm32/include/clk/u5/cfg_clock_default.h b/cpu/stm32/include/clk/u5/cfg_clock_default.h new file mode 100644 index 0000000000..87494ae205 --- /dev/null +++ b/cpu/stm32/include/clk/u5/cfg_clock_default.h @@ -0,0 +1,130 @@ +/* + * Copyright (C) 2021 Inria + * + * This file is subject to the terms and conditions of the GNU Lesser + * General Public License v2.1. See the file LICENSE in the top level + * directory for more details. + */ + +/** + * @ingroup cpu_stm32 + * @{ + * + * @file + * @brief Default STM32U5 clock configuration + * + * @author Alexandre Abadie + */ + +#ifndef CLK_U5_CFG_CLOCK_DEFAULT_H +#define CLK_U5_CFG_CLOCK_DEFAULT_H + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @name U5 clock system configuration + * @{ + */ +#if IS_ACTIVE(CONFIG_BOARD_HAS_HSE) && (CLOCK_HSE < MHZ(4) || CLOCK_HSE > MHZ(48)) +#error "HSE clock frequency must be between 4MHz and 48MHz" +#endif + +/* The following parameters configure a 80MHz system clock with PLL as input clock */ +#ifndef CONFIG_CLOCK_PLL_SRC_MSI +#if IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_HSE) || IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_HSI) || \ + IS_ACTIVE(CONFIG_BOARD_HAS_HSE) +#define CONFIG_CLOCK_PLL_SRC_MSI 0 +#else +#define CONFIG_CLOCK_PLL_SRC_MSI 1 /* Use MSI as input clock by default */ +#endif +#endif /* CONFIG_CLOCK_PLL_SRC_MSI */ +#ifndef CONFIG_CLOCK_PLL_SRC_HSE +#if IS_ACTIVE(CONFIG_BOARD_HAS_HSE) && \ + !IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_HSI) && !IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_MSI) +#define CONFIG_CLOCK_PLL_SRC_HSE 1 +#else +#define CONFIG_CLOCK_PLL_SRC_HSE 0 +#endif +#endif +#ifndef CONFIG_CLOCK_PLL_SRC_HSI +#define CONFIG_CLOCK_PLL_SRC_HSI 0 +#endif +#if IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_MSI) +#define CLOCK_PLL_SRC (CONFIG_CLOCK_MSI) +#elif IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_HSE) +#define CLOCK_PLL_SRC (CLOCK_HSE) +#else /* CONFIG_CLOCK_PLL_SRC_ */ +#define CLOCK_PLL_SRC (CLOCK_HSI) +#endif +#ifndef CONFIG_CLOCK_PLL_M +#if IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_MSI) +#define CONFIG_CLOCK_PLL_M (6) /* MSI at 48MHz */ +#else +#define CONFIG_CLOCK_PLL_M (2) /* HSI/HSE at 16MHz */ +#endif +#endif +#ifndef CONFIG_CLOCK_PLL_N +#define CONFIG_CLOCK_PLL_N (40) +#endif +#ifndef CONFIG_CLOCK_PLL_Q +#define CONFIG_CLOCK_PLL_Q (2) +#endif +#ifndef CONFIG_CLOCK_PLL_R +#define CONFIG_CLOCK_PLL_R (2) +#endif + +#if IS_ACTIVE(CONFIG_USE_CLOCK_HSI) +#define CLOCK_CORECLOCK (CLOCK_HSI) + +#elif IS_ACTIVE(CONFIG_USE_CLOCK_HSE) +#define CLOCK_CORECLOCK (CLOCK_HSE) + +#elif IS_ACTIVE(CONFIG_USE_CLOCK_MSI) +#define CLOCK_CORECLOCK (CONFIG_CLOCK_MSI) + +#elif IS_ACTIVE(CONFIG_USE_CLOCK_PLL) +/* PLL configuration: make sure your values are legit! + * + * compute by: CORECLOCK = (((PLL_IN / M) * N) / R) + * with: + * PLL_IN: input clock, HSE or MSI + * M: pre-divider, allowed range: [1:8] + * N: multiplier, allowed range: [5:512] + * R: post-divider, allowed range: [2:8] + * + * Also the following constraints need to be met: + * (PLL_IN / M) -> [4MHz:16MHz] + * (PLL_IN / M) * N -> [64MHz:344MHz] + * CORECLOCK -> 64MHz, 80MHZ or 120MHz MAX! + */ +#define CLOCK_CORECLOCK \ + ((CLOCK_PLL_SRC / CONFIG_CLOCK_PLL_M) * CONFIG_CLOCK_PLL_N) / CONFIG_CLOCK_PLL_R + +/* Set max allowed sysclk */ +#define CLOCK_CORECLOCK_MAX MHZ(160) + +#if CLOCK_CORECLOCK > CLOCK_CORECLOCK_MAX +#error "SYSCLK cannot exceed 160MHz" +#endif /* CLOCK_CORECLOCK > CLOCK_CORECLOCK_MAX */ +#endif /* CONFIG_USE_CLOCK_PLL */ + +#define CLOCK_AHB CLOCK_CORECLOCK /* HCLK, max: 160MHz */ + +#ifndef CONFIG_CLOCK_APB1_DIV +#define CONFIG_CLOCK_APB1_DIV (4) +#endif +#define CLOCK_APB1 (CLOCK_AHB / CONFIG_CLOCK_APB1_DIV) /* PCLK1, max: 160MHz */ +#ifndef CONFIG_CLOCK_APB2_DIV +#define CONFIG_CLOCK_APB2_DIV (2) +#endif +#define CLOCK_APB2 (CLOCK_AHB / CONFIG_CLOCK_APB2_DIV) /* PCLK1, max: 160MHz */ +/** @} */ + +#ifdef __cplusplus +} +#endif + +#endif /* CLK_U5_CFG_CLOCK_DEFAULT_H */ +/** @} */ diff --git a/cpu/stm32/include/cpu_conf.h b/cpu/stm32/include/cpu_conf.h index 34e9137776..aafc636e91 100644 --- a/cpu/stm32/include/cpu_conf.h +++ b/cpu/stm32/include/cpu_conf.h @@ -64,6 +64,9 @@ #elif CPU_FAM_STM32L5 #include "stm32l5xx.h" #include "irqs/l5/irqs.h" +#elif CPU_FAM_STM32U5 +#include "stm32u5xx.h" +#include "irqs/u5/irqs.h" #elif CPU_FAM_STM32WB #include "stm32wbxx.h" #include "irqs/wb/irqs.h" @@ -100,7 +103,9 @@ extern "C" { * @brief Flash page configuration * @{ */ -#if defined(CPU_FAM_STM32WB) +#if defined(CPU_FAM_STM32U5) +#define FLASHPAGE_SIZE (8192U) +#elif defined(CPU_FAM_STM32WB) #define FLASHPAGE_SIZE (4096U) #elif defined(CPU_LINE_STM32F091xC) || defined(CPU_LINE_STM32F072xB) \ || defined(CPU_LINE_STM32F030xC) || defined(CPU_LINE_STM32F103xE) \ @@ -196,7 +201,8 @@ extern "C" { */ #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32G0) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) #define FLASHPAGE_WRITE_BLOCK_SIZE (8U) typedef uint64_t stm32_flashpage_block_t; #elif defined(CPU_FAM_STM32L0) || defined(CPU_FAM_STM32L1) || \ @@ -211,7 +217,8 @@ typedef uint16_t stm32_flashpage_block_t; #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32G0) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) #define FLASHPAGE_WRITE_BLOCK_ALIGNMENT (8U) #else /* Writing should be always 4 bytes aligned */ diff --git a/cpu/stm32/include/cpu_conf_stm32_common.h b/cpu/stm32/include/cpu_conf_stm32_common.h index 2b2a7fb7c3..bc0875d1dd 100644 --- a/cpu/stm32/include/cpu_conf_stm32_common.h +++ b/cpu/stm32/include/cpu_conf_stm32_common.h @@ -32,7 +32,7 @@ extern "C" { defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32L4) || \ defined(CPU_FAM_STM32WB) || defined(CPU_FAM_STM32G4) || \ defined(CPU_FAM_STM32G0) || defined(CPU_FAM_STM32L5) || \ - defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32U5) || defined(CPU_FAM_STM32WL) /** * @brief Timing register settings @@ -43,7 +43,8 @@ static const i2c_timing_param_t timing_params[] = { #if defined(CPU_FAM_STM32F0) || defined(CPU_FAM_STM32F7) || \ defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32G0) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) [ I2C_SPEED_NORMAL ] = { .presc = 0xB, .scll = 0x13, /* t_SCLL = 5.0us */ diff --git a/cpu/stm32/include/periph/u5/periph_cpu.h b/cpu/stm32/include/periph/u5/periph_cpu.h new file mode 100644 index 0000000000..a5327d4c6e --- /dev/null +++ b/cpu/stm32/include/periph/u5/periph_cpu.h @@ -0,0 +1,42 @@ +/* + * Copyright (C) 2021 Inria + * + * This file is subject to the terms and conditions of the GNU Lesser + * General Public License v2.1. See the file LICENSE in the top level + * directory for more details. + */ + +/** + * @ingroup cpu_stm32 + * @{ + * + * @file + * @brief STM32U5 CPU specific definitions for internal peripheral handling + * + * @author Alexandre Abadie + * + */ + +#ifndef PERIPH_U5_PERIPH_CPU_H +#define PERIPH_U5_PERIPH_CPU_H + +#ifdef __cplusplus +extern "C" { +#endif + +#ifndef DOXYGEN + +/** + * @brief Starting address of the ROM bootloader + * see application note AN2606 + */ +#define STM32_BOOTLOADER_ADDR (0x0BF90000) + +#endif /* ndef DOXYGEN */ + +#ifdef __cplusplus +} +#endif + +#endif /* PERIPH_U5_PERIPH_CPU_H */ +/** @} */ diff --git a/cpu/stm32/include/periph_cpu.h b/cpu/stm32/include/periph_cpu.h index 6fc3cd0036..a47b6cfd25 100644 --- a/cpu/stm32/include/periph_cpu.h +++ b/cpu/stm32/include/periph_cpu.h @@ -50,6 +50,8 @@ #include "periph/l4/periph_cpu.h" #elif defined(CPU_FAM_STM32L5) #include "periph/l5/periph_cpu.h" +#elif defined(CPU_FAM_STM32U5) +#include "periph/u5/periph_cpu.h" #elif defined(CPU_FAM_STM32WB) #include "periph/wb/periph_cpu.h" #elif defined(CPU_FAM_STM32WL) @@ -72,7 +74,8 @@ extern "C" { defined(CPU_FAM_STM32F7) || defined(CPU_FAM_STM32L4) || \ defined(CPU_FAM_STM32WB) || defined(CPU_FAM_STM32G4) || \ defined(CPU_FAM_STM32G0) || defined(CPU_FAM_STM32L5) || \ - defined(CPU_FAM_STM32MP1) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32U5) || defined(CPU_FAM_STM32MP1) || \ + defined(CPU_FAM_STM32WL) #define CLOCK_LSI (32000U) #else #error "error: LSI clock speed not defined for your target CPU" @@ -172,12 +175,13 @@ extern "C" { typedef enum { APB1, /**< APB1 bus */ APB2, /**< APB2 bus */ -#if defined(CPU_FAM_STM32WL) +#if defined(CPU_FAM_STM32WL) || defined(CPU_FAM_STM32U5) APB3, #endif #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32G0) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) APB12, /**< AHB1 bus, second register */ #endif #if defined(CPU_FAM_STM32L0) || defined(CPU_FAM_STM32G0) @@ -189,9 +193,13 @@ typedef enum { #elif defined(CPU_FAM_STM32F2) || defined(CPU_FAM_STM32F4) || \ defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32F7) || \ defined(CPU_FAM_STM32WB) || defined(CPU_FAM_STM32G4) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) AHB1, /**< AHB1 bus */ AHB2, /**< AHB2 bus */ +#if defined(CPU_FAM_STM32U5) + AHB22, /**< AHB2 bus, second register */ +#endif AHB3, /**< AHB3 bus */ #elif defined(CPU_FAM_STM32MP1) AHB1, /**< AHB1 bus */ @@ -671,8 +679,8 @@ typedef struct { #endif #if defined(CPU_FAM_STM32L0) || defined(CPU_FAM_STM32L4) || \ defined(CPU_FAM_STM32WB) || defined(CPU_FAM_STM32G4) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32MP1) || \ - defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32MP1) || defined(CPU_FAM_STM32WL) uart_type_t type; /**< hardware module type (USART or LPUART) */ uint32_t clk_src; /**< clock source used for UART */ #endif @@ -725,7 +733,8 @@ typedef enum { defined(CPU_FAM_STM32F7) || defined(CPU_FAM_STM32L0) || \ defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32G0) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) I2C_SPEED_FAST_PLUS, /**< fast plus mode: ~1Mbit/s */ #endif } i2c_speed_t; @@ -761,7 +770,8 @@ typedef struct { defined(CPU_FAM_STM32F7) || defined(CPU_FAM_STM32L0) || \ defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32G0) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) /** * @brief Structure for I2C timing register settings * diff --git a/cpu/stm32/include/vendor/patches/u5/0001-stm32u5xx-remove-ErrorStatus.patch b/cpu/stm32/include/vendor/patches/u5/0001-stm32u5xx-remove-ErrorStatus.patch new file mode 100644 index 0000000000000000000000000000000000000000..ac1339483c195a142986791c2f9ca628ffa71fe7 GIT binary patch literal 1375 zcmbVM+iuf95PjdTIKWF%$BymP!3`88q^TMS3W`%+5UMuzI9cS_(c11sv_HZBAU=s- zVAgG+EqMT}#Os~eJu~Ob>>lc3jqtf227yc{4gA3GyJ;`=Q?DQQc^Z1I^b?tq8w7Y; zSs|(EQ-Lt|tx|W`I#f7cx&YVYHBmBD|D$7DqOgp~|(APO4vt16k3)Aa>yO za6mC5`5wI8!EQM4_F%c5>x!see5SY>;N$zze0&72>wQ95t$ThQTwDyGX@OBte+;`kam1-`zF&ZbuWAWnnww za0ol>gs{wOI1~VO_<#GT5_PHaCDTE*B8*WMwT_u-kx++ywal_h<6TRYJF$cLiuc@z zQREdH%fTZ|*ccais+P5uMi7)-7c*8X$!cU-abBV-*qoVyJ>Jck*&Kxs&ENL?6D}T0 zd!{(2x}@YT(MswiG1_L6skjLv><7#YLB=V}E)*JhQ8f%Vq}66cT4rBMBwC%3E)D2C zq=tM;Ipl1?MB~M|$}%hn3u%&Ka*5K+1~QJRZ0J1*q-m+jibDzOAG7@N{o7yU`6uds zEj_1QNW1o8$)#ZkG6DY6O0@paK^QN<8W==G{ z5V*sfMyH1-$K(0*-7zCa^U-|LYTj+MT6bUj`#6|Jqt|aHZCqWk<8}qxC&!JsEg2zkUIbX literal 0 HcmV?d00001 diff --git a/cpu/stm32/kconfigs/Kconfig.clk b/cpu/stm32/kconfigs/Kconfig.clk index 2476009f64..7ddc851b91 100644 --- a/cpu/stm32/kconfigs/Kconfig.clk +++ b/cpu/stm32/kconfigs/Kconfig.clk @@ -367,7 +367,7 @@ endif # CPU_FAM_L0 || CPU_FAM_L1 || CPU_FAM_L4 || CPU_FAM_L5 || CPU_FAM_WB choice bool "APB1 prescaler (division factor of HCLK to produce PCLK1)" -default CLOCK_APB1_DIV_4 if CPU_FAM_F2 || (CPU_FAM_F4 && CLOCK_MAX_180MHZ) || CPU_FAM_F7 || CPU_FAM_L4 || CPU_FAM_L5 || CPU_FAM_WB +default CLOCK_APB1_DIV_4 if CPU_FAM_F2 || (CPU_FAM_F4 && CLOCK_MAX_180MHZ) || CPU_FAM_F7 || CPU_FAM_L4 || CPU_FAM_L5 || CPU_FAM_U5 || CPU_FAM_WB default CLOCK_APB1_DIV_2 if CPU_FAM_F1 || CPU_FAM_F3 || CPU_FAM_F4 default CLOCK_APB1_DIV_1 @@ -399,7 +399,7 @@ config CLOCK_APB1_DIV choice bool "APB2 prescaler (division factor of HCLK to produce PCLK2)" depends on !CPU_FAM_G0 && !CPU_FAM_F0 -default CLOCK_APB2_DIV_2 if CPU_FAM_F2 || (CPU_FAM_F4 && CLOCK_MAX_180MHZ) || CPU_FAM_F7 || CPU_FAM_L4 || CPU_FAM_L5 || CPU_FAM_WB +default CLOCK_APB2_DIV_2 if CPU_FAM_F2 || (CPU_FAM_F4 && CLOCK_MAX_180MHZ) || CPU_FAM_F7 || CPU_FAM_L4 || CPU_FAM_L5 || CPU_FAM_U5 || CPU_FAM_WB default CLOCK_APB2_DIV_1 config CLOCK_APB2_DIV_1 diff --git a/cpu/stm32/kconfigs/u5/Kconfig b/cpu/stm32/kconfigs/u5/Kconfig new file mode 100644 index 0000000000..3930166cb1 --- /dev/null +++ b/cpu/stm32/kconfigs/u5/Kconfig @@ -0,0 +1,26 @@ +# Copyright (c) 2021 Inria +# +# This file is subject to the terms and conditions of the GNU Lesser +# General Public License v2.1. See the file LICENSE in the top level +# directory for more details. +# + +config CPU_FAM_U5 + bool + select CPU_STM32 + select CPU_CORE_CORTEX_M33 + select HAS_CPU_STM32U5 + select HAS_PERIPH_FLASHPAGE + select HAS_PERIPH_FLASHPAGE_PAGEWISE + select HAS_PERIPH_HWRNG + select HAS_PERIPH_RTC_MEM + select HAS_PERIPH_WDT + select HAS_BOOTLOADER_STM32 + +config CPU_FAM + default "u5" if CPU_FAM_U5 + +config HAS_CPU_STM32U5 + bool + help + Indicates that the cpu being used belongs to the 'stm32u5' family. diff --git a/cpu/stm32/kconfigs/u5/Kconfig.lines b/cpu/stm32/kconfigs/u5/Kconfig.lines new file mode 100644 index 0000000000..5dc0149b5c --- /dev/null +++ b/cpu/stm32/kconfigs/u5/Kconfig.lines @@ -0,0 +1,19 @@ +# Copyright (c) 2021 Inria +# +# This file is subject to the terms and conditions of the GNU Lesser +# General Public License v2.1. See the file LICENSE in the top level +# directory for more details. +# + +# This file was auto-generated from ST ProductsList.xlsx sheet using the +# script in cpu/stm32/dist/kconfig/gen_kconfig.py +# See cpu/stm32/dist/kconfig/README.md for details + +# CPU lines +config CPU_LINE_STM32U575XX + bool + select CPU_FAM_U5 + +config CPU_LINE_STM32U585XX + bool + select CPU_FAM_U5 diff --git a/cpu/stm32/kconfigs/u5/Kconfig.models b/cpu/stm32/kconfigs/u5/Kconfig.models new file mode 100644 index 0000000000..811a1fcb40 --- /dev/null +++ b/cpu/stm32/kconfigs/u5/Kconfig.models @@ -0,0 +1,120 @@ +# Copyright (c) 2021 Inria +# +# This file is subject to the terms and conditions of the GNU Lesser +# General Public License v2.1. See the file LICENSE in the top level +# directory for more details. +# + +# This file was auto-generated from ST ProductsList.xlsx sheet using the +# script in cpu/stm32/dist/kconfig/gen_kconfig.py +# See cpu/stm32/dist/kconfig/README.md for details + +# CPU models +config CPU_MODEL_STM32U575AG + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575AI + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575CG + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575CI + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575OG + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575OI + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575QG + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575QI + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575RG + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575RI + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575VG + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575VI + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575ZG + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U575ZI + bool + select CPU_LINE_STM32U575XX + +config CPU_MODEL_STM32U585AI + bool + select CPU_LINE_STM32U585XX + +config CPU_MODEL_STM32U585CI + bool + select CPU_LINE_STM32U585XX + +config CPU_MODEL_STM32U585OI + bool + select CPU_LINE_STM32U585XX + +config CPU_MODEL_STM32U585QI + bool + select CPU_LINE_STM32U585XX + +config CPU_MODEL_STM32U585RI + bool + select CPU_LINE_STM32U585XX + +config CPU_MODEL_STM32U585VI + bool + select CPU_LINE_STM32U585XX + +config CPU_MODEL_STM32U585ZI + bool + select CPU_LINE_STM32U585XX + + +# Configure CPU model +config CPU_MODEL + default "stm32u575ag" if CPU_MODEL_STM32U575AG + default "stm32u575ai" if CPU_MODEL_STM32U575AI + default "stm32u575cg" if CPU_MODEL_STM32U575CG + default "stm32u575ci" if CPU_MODEL_STM32U575CI + default "stm32u575og" if CPU_MODEL_STM32U575OG + default "stm32u575oi" if CPU_MODEL_STM32U575OI + default "stm32u575qg" if CPU_MODEL_STM32U575QG + default "stm32u575qi" if CPU_MODEL_STM32U575QI + default "stm32u575rg" if CPU_MODEL_STM32U575RG + default "stm32u575ri" if CPU_MODEL_STM32U575RI + default "stm32u575vg" if CPU_MODEL_STM32U575VG + default "stm32u575vi" if CPU_MODEL_STM32U575VI + default "stm32u575zg" if CPU_MODEL_STM32U575ZG + default "stm32u575zi" if CPU_MODEL_STM32U575ZI + default "stm32u585ai" if CPU_MODEL_STM32U585AI + default "stm32u585ci" if CPU_MODEL_STM32U585CI + default "stm32u585oi" if CPU_MODEL_STM32U585OI + default "stm32u585qi" if CPU_MODEL_STM32U585QI + default "stm32u585ri" if CPU_MODEL_STM32U585RI + default "stm32u585vi" if CPU_MODEL_STM32U585VI + default "stm32u585zi" if CPU_MODEL_STM32U585ZI diff --git a/cpu/stm32/periph/Makefile b/cpu/stm32/periph/Makefile index 8d87395d5a..ae12ec0981 100644 --- a/cpu/stm32/periph/Makefile +++ b/cpu/stm32/periph/Makefile @@ -2,7 +2,7 @@ MODULE = periph # Select the specific implementation for `periph_i2c` ifneq (,$(filter periph_i2c,$(USEMODULE))) - ifneq (,$(filter $(CPU_FAM),f0 f3 f7 g0 g4 l0 l4 l5 wb wl)) + ifneq (,$(filter $(CPU_FAM),f0 f3 f7 g0 g4 l0 l4 l5 u5 wb wl)) SRC += i2c_1.c else ifneq (,$(filter $(CPU_FAM),f1 f2 f4 l1)) SRC += i2c_2.c diff --git a/cpu/stm32/periph/flash_common.c b/cpu/stm32/periph/flash_common.c index 6e5265830d..f47658af89 100644 --- a/cpu/stm32/periph/flash_common.c +++ b/cpu/stm32/periph/flash_common.c @@ -31,13 +31,19 @@ #define CNTRL_REG (FLASH->PECR) #define CNTRL_REG_LOCK (FLASH_PECR_PELOCK) #define KEY_REG (FLASH->PEKEYR) -#elif defined(CPU_FAM_STM32L5) +#elif defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) #define FLASH_KEY1 ((uint32_t)0x45670123) #define FLASH_KEY2 ((uint32_t)0xCDEF89AB) #define CNTRL_REG (FLASH->NSCR) +#if defined(CPU_FAM_STM32U5) +#define CNTRL_REG_LOCK (FLASH_NSCR_LOCK) +#define KEY_REG (FLASH->NSKEYR) +#define FLASH_SR_EOP (FLASH_NSSR_EOP) +#else #define CNTRL_REG_LOCK (FLASH_NSCR_NSLOCK) #define KEY_REG (FLASH->NSKEYR) #define FLASH_SR_EOP (FLASH_NSSR_NSEOP) +#endif #else #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32G0) || \ @@ -58,6 +64,9 @@ #if defined(CPU_FAM_STM32L5) #define FLASH_SR_BSY (FLASH_NSSR_NSBSY) #define FLASH_SR_REG (FLASH->NSSR) +#elif defined(CPU_FAM_STM32U5) +#define FLASH_SR_BSY (FLASH_NSSR_BSY) +#define FLASH_SR_REG (FLASH->NSSR) #else #define FLASH_SR_REG (FLASH->SR) #endif diff --git a/cpu/stm32/periph/flashpage.c b/cpu/stm32/periph/flashpage.c index 50cd060783..565cf7e13e 100644 --- a/cpu/stm32/periph/flashpage.c +++ b/cpu/stm32/periph/flashpage.c @@ -47,6 +47,15 @@ #define FLASH_CR_PER (FLASH_NSCR_NSPER) #define FLASH_CR_BKER (FLASH_NSCR_NSBKER) #define FLASH_CR_PG (FLASH_NSCR_NSPG) +#elif defined(CPU_FAM_STM32U5) +#define CNTRL_REG (FLASH->NSCR) +#define CNTRL_REG_LOCK (FLASH_NSCR_LOCK) +#define FLASH_CR_PNB (FLASH_NSCR_PNB) +#define FLASH_CR_PNB_Pos (FLASH_NSCR_PNB_Pos) +#define FLASH_CR_STRT (FLASH_NSCR_STRT) +#define FLASH_CR_PER (FLASH_NSCR_PER) +#define FLASH_CR_BKER (FLASH_NSCR_BKER) +#define FLASH_CR_PG (FLASH_NSCR_PG) #elif defined(CPU_FAM_STM32F2) || defined(CPU_FAM_STM32F4) || \ defined(CPU_FAM_STM32F7) #define FLASHPAGE_DIV (4U) @@ -63,7 +72,8 @@ extern void _lock(void); extern void _unlock(void); extern void _wait_for_pending_operations(void); -#if defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) +#if defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) || \ + defined(CPU_FAM_STM32U5) #define MAX_PAGES_PER_BANK (128) #else /* CPU_FAM_STM32L4 */ #define MAX_PAGES_PER_BANK (256) @@ -111,7 +121,7 @@ static void _erase_page(void *page_addr) defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32G0) || \ defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32F2) || \ defined(CPU_FAM_STM32F4) || defined(CPU_FAM_STM32F7) || \ - defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32U5) || defined(CPU_FAM_STM32WL) DEBUG("[flashpage] erase: setting the page address\n"); uint8_t pn; #if (FLASHPAGE_NUMOF <= MAX_PAGES_PER_BANK) || defined(CPU_FAM_STM32WB) || \ @@ -262,7 +272,8 @@ void flashpage_write(void *target_addr, const void *data, size_t len) defined(CPU_FAM_STM32WB) || defined(CPU_FAM_STM32G4) || \ defined(CPU_FAM_STM32G0) || defined(CPU_FAM_STM32L5) || \ defined(CPU_FAM_STM32F2) || defined(CPU_FAM_STM32F4) || \ - defined(CPU_FAM_STM32F7) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32F7) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) /* set PG bit and program page to flash */ CNTRL_REG |= FLASH_CR_PG; #endif @@ -282,7 +293,8 @@ void flashpage_write(void *target_addr, const void *data, size_t len) defined(CPU_FAM_STM32WB) || defined(CPU_FAM_STM32G4) || \ defined(CPU_FAM_STM32G0) || defined(CPU_FAM_STM32L5) || \ defined(CPU_FAM_STM32F2) || defined(CPU_FAM_STM32F4) || \ - defined(CPU_FAM_STM32F7) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32F7) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) CNTRL_REG &= ~(FLASH_CR_PG); #endif DEBUG("[flashpage_raw] write: done writing data\n"); diff --git a/cpu/stm32/periph/gpio_all.c b/cpu/stm32/periph/gpio_all.c index 5fd33a0615..68c5fa0737 100644 --- a/cpu/stm32/periph/gpio_all.c +++ b/cpu/stm32/periph/gpio_all.c @@ -46,7 +46,8 @@ static gpio_isr_ctx_t isr_ctx[EXTI_NUMOF]; #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32G0) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) #define EXTI_REG_RTSR (EXTI->RTSR1) #define EXTI_REG_FTSR (EXTI->FTSR1) #define EXTI_REG_PR (EXTI->PR1) @@ -101,10 +102,14 @@ static inline void port_init_clock(GPIO_TypeDef *port, gpio_t pin) periph_clk_en(AHB, (RCC_AHBENR_GPIOAEN << _port_num(pin))); #elif defined (CPU_FAM_STM32L0) || defined(CPU_FAM_STM32G0) periph_clk_en(IOP, (RCC_IOPENR_GPIOAEN << _port_num(pin))); -#elif defined (CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ - defined (CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) || \ - defined (CPU_FAM_STM32WL) +#elif defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ + defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) || \ + defined(CPU_FAM_STM32U5) || defined (CPU_FAM_STM32WL) +#if defined(CPU_FAM_STM32U5) + periph_clk_en(AHB2, (RCC_AHB2ENR1_GPIOAEN << _port_num(pin))); +#else periph_clk_en(AHB2, (RCC_AHB2ENR_GPIOAEN << _port_num(pin))); +#endif #ifdef PWR_CR2_IOSV if (port == GPIOG) { /* Port G requires external power supply */ @@ -170,10 +175,12 @@ void gpio_init_analog(gpio_t pin) periph_clk_en(AHB, (RCC_AHBENR_GPIOAEN << _port_num(pin))); #elif defined (CPU_FAM_STM32L0) || defined(CPU_FAM_STM32G0) periph_clk_en(IOP, (RCC_IOPENR_GPIOAEN << _port_num(pin))); -#elif defined (CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ - defined (CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) || \ +#elif defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ + defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) || \ defined (CPU_FAM_STM32WL) periph_clk_en(AHB2, (RCC_AHB2ENR_GPIOAEN << _port_num(pin))); +#elif defined(CPU_FAM_STM32U5) + periph_clk_en(AHB2, (RCC_AHB2ENR1_GPIOAEN << _port_num(pin))); #elif defined(CPU_FAM_STM32MP1) periph_clk_en(AHB4, (RCC_MC_AHB4ENSETR_GPIOAEN << _port_num(pin))); #else @@ -244,6 +251,8 @@ int gpio_init_int(gpio_t pin, gpio_mode_t mode, gpio_flank_t flank, periph_clk_en(APB2, RCC_APB2ENR_SYSCFGCOMPEN); #elif defined(CPU_FAM_STM32G0) periph_clk_en(APB12, RCC_APBENR2_SYSCFGEN); +#elif defined(CPU_FAM_STM32U5) + periph_clk_en(APB3, RCC_APB3ENR_SYSCFGEN); #else periph_clk_en(APB2, RCC_APB2ENR_SYSCFGEN); #endif @@ -253,7 +262,7 @@ int gpio_init_int(gpio_t pin, gpio_mode_t mode, gpio_flank_t flank, gpio_init(pin, mode); /* enable global pin interrupt */ -#if defined(CPU_FAM_STM32L5) +#if defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) NVIC_EnableIRQ(EXTI0_IRQn + pin_num); #elif defined(CPU_FAM_STM32F0) || defined(CPU_FAM_STM32L0) || \ defined(CPU_FAM_STM32G0) @@ -308,7 +317,8 @@ int gpio_init_int(gpio_t pin, gpio_mode_t mode, gpio_flank_t flank, EXTI_REG_FTSR &= ~(1 << pin_num); EXTI_REG_FTSR |= ((flank >> 1) << pin_num); -#if defined(CPU_FAM_STM32G0) || defined(CPU_FAM_STM32L5) +#if defined(CPU_FAM_STM32G0) || defined(CPU_FAM_STM32L5) || \ + defined(CPU_FAM_STM32U5) /* enable specific pin as exti sources */ EXTI->EXTICR[pin_num >> 2] &= ~(0xf << ((pin_num & 0x03) * 8)); EXTI->EXTICR[pin_num >> 2] |= (port_num << ((pin_num & 0x03) * 8)); @@ -323,7 +333,7 @@ int gpio_init_int(gpio_t pin, gpio_mode_t mode, gpio_flank_t flank, #endif #if defined(CPU_FAM_STM32G0) || defined(CPU_FAM_STM32L5) || \ - defined(CPU_FAM_STM32MP1) + defined(CPU_FAM_STM32U5) || defined(CPU_FAM_STM32MP1) /* clear any pending requests */ EXTI->RPR1 = (1 << pin_num); EXTI->FPR1 = (1 << pin_num); @@ -340,7 +350,7 @@ int gpio_init_int(gpio_t pin, gpio_mode_t mode, gpio_flank_t flank, void isr_exti(void) { #if defined(CPU_FAM_STM32G0) || defined(CPU_FAM_STM32L5) || \ - defined(CPU_FAM_STM32MP1) + defined(CPU_FAM_STM32U5) || defined(CPU_FAM_STM32MP1) /* get all interrupts handled by this ISR */ uint32_t pending_rising_isr = (EXTI->RPR1 & EXTI_MASK); uint32_t pending_falling_isr = (EXTI->FPR1 & EXTI_MASK); diff --git a/cpu/stm32/periph/hwrng.c b/cpu/stm32/periph/hwrng.c index 3318375481..2516a9ee5a 100644 --- a/cpu/stm32/periph/hwrng.c +++ b/cpu/stm32/periph/hwrng.c @@ -45,6 +45,8 @@ void hwrng_read(void *buf, unsigned int num) periph_clk_en(AHB, RCC_AHBENR_RNGEN); #elif defined(CPU_FAM_STM32WB) periph_clk_en(AHB3, RCC_AHB3ENR_RNGEN); +#elif defined(CPU_FAM_STM32U5) + periph_clk_en(AHB2, RCC_AHB2ENR1_RNGEN); #else periph_clk_en(AHB2, RCC_AHB2ENR_RNGEN); #endif @@ -71,6 +73,8 @@ void hwrng_read(void *buf, unsigned int num) periph_clk_dis(AHB, RCC_AHBENR_RNGEN); #elif defined(CPU_FAM_STM32WB) periph_clk_dis(AHB3, RCC_AHB3ENR_RNGEN); +#elif defined(CPU_FAM_STM32U5) + periph_clk_dis(AHB2, RCC_AHB2ENR1_RNGEN); #else periph_clk_dis(AHB2, RCC_AHB2ENR_RNGEN); #endif diff --git a/cpu/stm32/periph/pm.c b/cpu/stm32/periph/pm.c index 055c4ec102..e1518eea6e 100644 --- a/cpu/stm32/periph/pm.c +++ b/cpu/stm32/periph/pm.c @@ -56,6 +56,8 @@ #define PM_STOP_CONFIG (PWR_CR1_LPDS | PWR_CR1_FPDS | PWR_CR1_LPUDS) #elif defined(CPU_FAM_STM32MP1) #define PM_STOP_CONFIG (0) +#elif defined(CPU_FAM_STM32U5) +#define PM_STOP_CONFIG (0) #else #define PM_STOP_CONFIG (PWR_CR_LPDS | PWR_CR_FPDS) #endif @@ -79,6 +81,8 @@ #define PM_STANDBY_CONFIG (PWR_CR1_PDDS | PWR_CR1_CSBF) #elif defined(CPU_FAM_STM32MP1) #define PM_STANDBY_CONFIG (0) +#elif defined(CPU_FAM_STM32U5) +#define PM_STANDBY_CONFIG (0) #else #define PM_STANDBY_CONFIG (PWR_CR_PDDS | PWR_CR_CWUF | PWR_CR_CSBF) #endif @@ -86,7 +90,8 @@ #if defined(CPU_FAM_STM32L4) || defined(CPU_FAM_STM32WB) || \ defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32G0) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) #define PWR_CR_REG PWR->CR1 #define PWR_WUP_REG PWR->CR3 /* Allow overridable SRAM2 retention mode using CFLAGS */ diff --git a/cpu/stm32/periph/uart.c b/cpu/stm32/periph/uart.c index 194cfcde41..b18c8c3921 100644 --- a/cpu/stm32/periph/uart.c +++ b/cpu/stm32/periph/uart.c @@ -35,7 +35,8 @@ #include "pm_layered.h" #if defined(CPU_LINE_STM32L4R5xx) || defined(CPU_FAM_STM32G0) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) #define ISR_REG ISR #define ISR_TXE USART_ISR_TXE_TXFNF #define ISR_RXNE USART_ISR_RXNE_RXFNE @@ -62,7 +63,8 @@ #endif #if defined(CPU_LINE_STM32L4R5xx) || defined(CPU_FAM_STM32G0) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) #define RXENABLE (USART_CR1_RE | USART_CR1_RXNEIE_RXFNEIE) #else #define RXENABLE (USART_CR1_RE | USART_CR1_RXNEIE) @@ -98,7 +100,8 @@ static inline USART_TypeDef *dev(uart_t uart) static inline void uart_init_usart(uart_t uart, uint32_t baudrate); #if defined(CPU_FAM_STM32L0) || defined(CPU_FAM_STM32L4) || \ defined(CPU_FAM_STM32WB) || defined(CPU_FAM_STM32G4) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) #ifdef MODULE_PERIPH_LPUART static inline void uart_init_lpuart(uart_t uart, uint32_t baudrate); #endif @@ -192,7 +195,8 @@ int uart_init(uart_t uart, uint32_t baudrate, uart_rx_cb_t rx_cb, void *arg) #if defined(CPU_FAM_STM32L0) || defined(CPU_FAM_STM32L4) || \ defined(CPU_FAM_STM32WB) || defined(CPU_FAM_STM32G4) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) switch (uart_config[uart].type) { case STM32_USART: uart_init_usart(uart, baudrate); @@ -322,7 +326,8 @@ static inline void uart_init_usart(uart_t uart, uint32_t baudrate) #if defined(CPU_FAM_STM32L0) || defined(CPU_FAM_STM32L4) || \ defined(CPU_FAM_STM32WB) || defined(CPU_FAM_STM32G4) || \ - defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32WL) + defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) || \ + defined(CPU_FAM_STM32WL) #ifdef CPU_FAM_STM32L5 #define RCC_CCIPR_LPUART1SEL_0 RCC_CCIPR1_LPUART1SEL_0 #define RCC_CCIPR_LPUART1SEL_1 RCC_CCIPR1_LPUART1SEL_1 diff --git a/cpu/stm32/stm32_info.mk b/cpu/stm32/stm32_info.mk index 39ec1bfcfe..348bebb283 100644 --- a/cpu/stm32/stm32_info.mk +++ b/cpu/stm32/stm32_info.mk @@ -8,7 +8,7 @@ # - STM32_PINCOUNT: R (64) # - STM32_ROMSIZE: G (1024K) CPU_MODEL_UPPERCASE = $(call uppercase,$(CPU_MODEL)) -STM32_INFO := $(shell echo $(CPU_MODEL_UPPERCASE) | sed -E -e 's/^STM32(F|L|W|G|MP)([0-7]|B|L)([A-Z0-9])([0-9])(.)(.)?(_A)?/\1 \2 \2\3\4 \3 \4 \5 \6 \7/') +STM32_INFO := $(shell echo $(CPU_MODEL_UPPERCASE) | sed -E -e 's/^STM32(F|L|W|G|MP|U)([0-7]|B|L)([A-Z0-9])([0-9])(.)(.)?(_A)?/\1 \2 \2\3\4 \3 \4 \5 \6 \7/') STM32_TYPE = $(word 1, $(STM32_INFO)) STM32_FAMILY = $(word 2, $(STM32_INFO)) STM32_MODEL = $(word 3, $(STM32_INFO)) @@ -42,7 +42,7 @@ else ifeq (f7,$(CPU_FAM)) CPU_CORE = cortex-m7 else ifneq (,$(filter $(CPU_FAM),g0 l0)) CPU_CORE = cortex-m0plus -else ifneq (,$(CPU_FAM),l5) +else ifneq (,$(filter $(CPU_FAM),l5 u5)) CPU_CORE = cortex-m33 else $(error Not supported CPU family: 'stm32$(CPU_FAM)') diff --git a/cpu/stm32/stm32_mem_lengths.mk b/cpu/stm32/stm32_mem_lengths.mk index 0d70ed27d6..7950d3c857 100644 --- a/cpu/stm32/stm32_mem_lengths.mk +++ b/cpu/stm32/stm32_mem_lengths.mk @@ -266,6 +266,12 @@ else ifeq ($(STM32_TYPE), L) RAM_LEN = 256K endif endif +else ifeq ($(STM32_TYPE), U) + ifeq ($(STM32_FAMILY), 5) + ifneq (, $(filter $(STM32_MODEL2), 7 8)) + RAM_LEN = 768K + endif + endif else ifeq ($(STM32_TYPE), W) ifeq ($(STM32_FAMILY), B) ifeq ($(STM32_MODEL), B55) diff --git a/cpu/stm32/stmclk/Makefile b/cpu/stm32/stmclk/Makefile index 7c8e2b386a..37ea80c3e8 100644 --- a/cpu/stm32/stmclk/Makefile +++ b/cpu/stm32/stmclk/Makefile @@ -14,6 +14,8 @@ else ifneq (,$(filter $(CPU_FAM),l4 wb wl)) SRC += stmclk_l4wx.c else ifneq (,$(filter $(CPU_FAM),l5)) SRC += stmclk_l5.c +else ifneq (,$(filter $(CPU_FAM),u5)) + SRC += stmclk_u5.c else ifneq (,$(filter $(CPU_FAM),g0 g4)) SRC += stmclk_gx.c else ifneq (,$(filter $(CPU_FAM),mp1)) diff --git a/cpu/stm32/stmclk/stmclk_common.c b/cpu/stm32/stmclk/stmclk_common.c index 73453199c1..9191d8ae3f 100644 --- a/cpu/stm32/stmclk/stmclk_common.c +++ b/cpu/stm32/stmclk/stmclk_common.c @@ -29,6 +29,9 @@ defined(CPU_FAM_STM32WL) #define REG_PWR_CR CR1 #define BIT_CR_DBP PWR_CR1_DBP +#elif defined(CPU_FAM_STM32U5) +#define REG_PWR_CR DBPR +#define BIT_CR_DBP PWR_DBPR_DBP #else #define REG_PWR_CR CR #define BIT_CR_DBP PWR_CR_DBP @@ -50,7 +53,12 @@ #define RCC_CSR_LSIRDY RCC_CSR_LSI1RDY #endif -#if defined(CPU_FAM_STM32L5) +#if defined (CPU_FAM_STM32U5) +#define RCC_CSR_LSION RCC_BDCR_LSION +#define RCC_CSR_LSIRDY RCC_BDCR_LSIRDY +#endif + +#if defined(CPU_FAM_STM32L5) || defined(CPU_FAM_STM32U5) #define RCC_CFGR_SWS_HSI RCC_CFGR_SWS_0 #endif @@ -74,7 +82,8 @@ void stmclk_enable_lfclk(void) /* Set LSE system clock enable bit. This is required if LSE is to be used by USARTx, LPUARTx, LPTIMx, TIMx, RNG, system LSCO, MCO, MSI PLL mode */ -#if defined(CPU_FAM_STM32WL) || defined (CPU_FAM_STM32L5) +#if defined(CPU_FAM_STM32WL) || defined (CPU_FAM_STM32L5) || \ + defined(CPU_FAM_STM32U5) RCC->BDCR |= RCC_BDCR_LSESYSEN; while (!(RCC->BDCR & RCC_BDCR_LSESYSRDY)) {} #endif diff --git a/cpu/stm32/stmclk/stmclk_u5.c b/cpu/stm32/stmclk/stmclk_u5.c new file mode 100644 index 0000000000..2cd245bdf0 --- /dev/null +++ b/cpu/stm32/stmclk/stmclk_u5.c @@ -0,0 +1,334 @@ +/* + * Copyright (C) 2021 Inria + * + * This file is subject to the terms and conditions of the GNU Lesser + * General Public License v2.1. See the file LICENSE in the top level + * directory for more details. + */ + +/** + * @ingroup cpu_stm32 + * @{ + * + * @file + * @brief Implementation of STM32 clock configuration for U5 family + * + * @author Alexandre Abadie + * @} + */ + +#include "cpu.h" +#include "stmclk.h" +#include "periph_conf.h" + + +#define RCC_CFGR1_SW_MSI (0x00000000U) +#define RCC_CFGR1_SW_HSI (RCC_CFGR1_SW_0) +#define RCC_CFGR1_SW_HSE (RCC_CFGR1_SW_1) +#define RCC_CFGR1_SW_PLL (RCC_CFGR1_SW_1 | RCC_CFGR1_SW_0) +#define RCC_CFGR1_SWS_MSI (0x00000000U) +#define RCC_CFGR1_SWS_HSI (RCC_CFGR1_SWS_0) +#define RCC_CFGR1_SWS_HSE (RCC_CFGR1_SWS_1) +#define RCC_CFGR1_SWS_PLL (RCC_CFGR1_SWS_1 | RCC_CFGR1_SWS_0) + +/* PLL configuration */ +/* figure out which input to use */ +#if IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_MSI) +#define PLL_SRC (RCC_PLL1CFGR_PLL1SRC_0) +#elif IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_HSE) && IS_ACTIVE(CONFIG_BOARD_HAS_HSE) +#define PLL_SRC (RCC_PLL1CFGR_PLL1SRC_1 | RCC_PLL1CFGR_PLL1SRC_0) +#elif IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_HSI) +#define PLL_SRC (RCC_PLL1CFGR_PLL1SRC_1) +#else +#define PLL_SRC 0 +#endif + +/* check configuration and get the corresponding bitfields */ +#if (CONFIG_CLOCK_PLL_M < 1 || CONFIG_CLOCK_PLL_M > 16) +#error "PLL configuration: PLL M value is out of range" +#endif +#define PLL_M ((CONFIG_CLOCK_PLL_M - 1) << RCC_PLL1CFGR_PLL1M_Pos) + +#if (CONFIG_CLOCK_PLL_N < 4 || CONFIG_CLOCK_PLL_N > 512) +#error "PLL configuration: PLL N value is out of range" +#endif +#define PLL_N ((CONFIG_CLOCK_PLL_N - 1) << RCC_PLL1DIVR_PLL1N_Pos) + +#if (CONFIG_CLOCK_PLL_R < 1 || CONFIG_CLOCK_PLL_R > 128) +#error "PLL configuration: PLL R value is out of range" +#endif +#define PLL_R ((CONFIG_CLOCK_PLL_R - 1) << RCC_PLL1DIVR_PLL1R_Pos) + +#if (CONFIG_CLOCK_PLL_Q < 1 || CONFIG_CLOCK_PLL_Q > 128) +#error "PLL configuration: PLL Q value is out of range" +#endif +#define PLL_Q ((CONFIG_CLOCK_PLL_Q - 1) << RCC_PLL1DIVR_PLL1Q_Pos) + +/* Define MSI range bitfields */ +#if CONFIG_CLOCK_MSI == KHZ(100) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_3 | RCC_ICSCR1_MSISRANGE_2 | RCC_ICSCR1_MSISRANGE_1 | RCC_ICSCR1_MSISRANGE_0) +#elif CONFIG_CLOCK_MSI == KHZ(133) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_3 | RCC_ICSCR1_MSISRANGE_2 | RCC_ICSCR1_MSISRANGE_1) +#elif CONFIG_CLOCK_MSI == KHZ(200) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_3 | RCC_ICSCR1_MSISRANGE_2 | RCC_ICSCR1_MSISRANGE_0) +#elif CONFIG_CLOCK_MSI == KHZ(400) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_3 | RCC_ICSCR1_MSISRANGE_2) +#elif CONFIG_CLOCK_MSI == KHZ(768) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_3 | RCC_ICSCR1_MSISRANGE_1 | RCC_ICSCR1_MSISRANGE_0) +#elif CONFIG_CLOCK_MSI == MHZ(1) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_2 | RCC_ICSCR1_MSISRANGE_1 | RCC_ICSCR1_MSISRANGE_0) +#elif CONFIG_CLOCK_MSI == KHZ(1024) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_3 | RCC_ICSCR1_MSISRANGE_1) +#elif CONFIG_CLOCK_MSI == KHZ(1330) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_2 | RCC_ICSCR1_MSISRANGE_1) +#elif CONFIG_CLOCK_MSI == KHZ(1536) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_3 | RCC_ICSCR1_MSISRANGE_0) +#elif CONFIG_CLOCK_MSI == MHZ(2) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_2 | RCC_ICSCR1_MSISRANGE_0) +#elif CONFIG_CLOCK_MSI == KHZ(3072) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_3) +#elif CONFIG_CLOCK_MSI == MHZ(4) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_2) +#elif CONFIG_CLOCK_MSI == MHZ(12) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_1 | RCC_ICSCR1_MSISRANGE_0) +#elif CONFIG_CLOCK_MSI == MHZ(16) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_1) +#elif CONFIG_CLOCK_MSI == MHZ(24) +#define CLOCK_MSIRANGE (RCC_ICSCR1_MSISRANGE_0) +#elif CONFIG_CLOCK_MSI == MHZ(48) +#define CLOCK_MSIRANGE (0) +#else +#error "Invalid MSI clock" +#endif + +/* Configure 48MHz clock source */ +#define CLOCK_PLLQ ((CLOCK_PLL_SRC / CONFIG_CLOCK_PLL_M) * CONFIG_CLOCK_PLL_N) / CONFIG_CLOCK_PLL_Q + +#if CLOCK_PLLQ == MHZ(48) +#define CLOCK48MHZ_USE_PLLQ 1 +#elif CONFIG_CLOCK_MSI == MHZ(48) +#define CLOCK48MHZ_USE_MSI 1 +#else +#define CLOCK48MHZ_USE_PLLQ 0 +#define CLOCK48MHZ_USE_MSI 0 +#endif + +#if IS_ACTIVE(CLOCK48MHZ_USE_PLLQ) +#define CLOCK48MHZ_SELECT (RCC_CCIPR1_CLK48MSEL_1) +#elif IS_ACTIVE(CLOCK48MHZ_USE_MSI) +#define CLOCK48MHZ_SELECT (RCC_CCIPR1_CLK48MSEL_1 | RCC_CCIPR1_CLK48MSEL_0) +#else +#define CLOCK48MHZ_SELECT (0) +#endif + +/* Configure the AHB and APB buses prescalers */ +#define CLOCK_AHB_DIV (0) + +#if CONFIG_CLOCK_APB1_DIV == 1 +#define CLOCK_APB1_DIV (0) +#elif CONFIG_CLOCK_APB1_DIV == 2 +#define CLOCK_APB1_DIV (RCC_CFGR2_PPRE1_2) +#elif CONFIG_CLOCK_APB1_DIV == 4 +#define CLOCK_APB1_DIV (RCC_CFGR2_PPRE1_2 | RCC_CFGR2_PPRE1_0) +#elif CONFIG_CLOCK_APB1_DIV == 8 +#define CLOCK_APB1_DIV (RCC_CFGR2_PPRE1_2 | RCC_CFGR2_PPRE1_1) +#elif CONFIG_CLOCK_APB1_DIV == 16 +#define CLOCK_APB1_DIV (RCC_CFGR2_PPRE1_2 | RCC_CFGR2_PPRE1_1 | RCC_CFGR2_PPRE1_0) +#endif + +#if CONFIG_CLOCK_APB2_DIV == 1 +#define CLOCK_APB2_DIV (0) +#elif CONFIG_CLOCK_APB2_DIV == 2 +#define CLOCK_APB2_DIV (RCC_CFGR2_PPRE2_2) +#elif CONFIG_CLOCK_APB2_DIV == 4 +#define CLOCK_APB2_DIV (RCC_CFGR2_PPRE2_2 | RCC_CFGR2_PPRE2_0) +#elif CONFIG_CLOCK_APB2_DIV == 8 +#define CLOCK_APB2_DIV (RCC_CFGR2_PPRE2_2 | RCC_CFGR2_PPRE2_1) +#elif CONFIG_CLOCK_APB2_DIV == 16 +#define CLOCK_APB2_DIV (RCC_CFGR2_PPRE2_2 | RCC_CFGR2_PPRE2_1 | RCC_CFGR2_PPRE2_0) +#endif + +/* Only periph_hwrng requires 48MHz for the moment */ +#if IS_USED(MODULE_PERIPH_HWRNG) +#if !IS_ACTIVE(CLOCK48MHZ_USE_PLLQ) && !IS_ACTIVE(CLOCK48MHZ_USE_MSI) +#error "No 48MHz clock source available, HWRNG cannot work" +#endif +#define CLOCK_ENABLE_48MHZ 1 +#else +#define CLOCK_ENABLE_48MHZ 0 +#endif + +/* Check if PLL is required + - When used as system clock + - When PLLQ is used as 48MHz clock source +*/ +#if IS_ACTIVE(CONFIG_USE_CLOCK_PLL) || \ + (IS_ACTIVE(CLOCK_ENABLE_48MHZ) && IS_ACTIVE(CLOCK48MHZ_USE_PLLQ)) +#define CLOCK_ENABLE_PLL 1 +#else +#define CLOCK_ENABLE_PLL 0 +#endif + +/* Check if HSE is required: + - When used as system clock + - When used as PLL input clock +*/ +#if IS_ACTIVE(CONFIG_USE_CLOCK_HSE) || \ + (IS_ACTIVE(CLOCK_ENABLE_PLL) && IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_HSE)) +#define CLOCK_ENABLE_HSE 1 +#else +#define CLOCK_ENABLE_HSE 0 +#endif + +/* HSE cannot be enabled if not provided by the board */ +#if IS_ACTIVE(CLOCK_ENABLE_HSE) && !IS_ACTIVE(CONFIG_BOARD_HAS_HSE) +#error "HSE is required by the clock configuration but is not provided by the board." +#endif + +/* Check if HSI is required: + - When used as system clock + - When used as PLL input clock +*/ +#if IS_ACTIVE(CONFIG_USE_CLOCK_HSI) || \ + (IS_ACTIVE(CLOCK_ENABLE_PLL) && IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_HSI)) +#define CLOCK_ENABLE_HSI 1 +#else +#define CLOCK_ENABLE_HSI 0 +#endif + +/* Check if MSI is required + - When used as system clock + - When used as PLL input clock +*/ +#if IS_ACTIVE(CONFIG_USE_CLOCK_MSI) || \ + (IS_ACTIVE(CLOCK_ENABLE_PLL) && IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_MSI)) || \ + (IS_ACTIVE(CLOCK_ENABLE_48MHZ) && IS_ACTIVE(CLOCK48MHZ_USE_MSI)) +#define CLOCK_ENABLE_MSI 1 +#else +#define CLOCK_ENABLE_MSI 0 +#endif + +/* Deduct the needed flash wait states from the core clock frequency */ +#if CLOCK_AHB <= MHZ(32) +#define FLASH_WAITSTATES FLASH_ACR_LATENCY_0WS +#elif CLOCK_AHB <= MHZ(64) +#define FLASH_WAITSTATES FLASH_ACR_LATENCY_1WS +#elif CLOCK_AHB <= MHZ(96) +#define FLASH_WAITSTATES FLASH_ACR_LATENCY_2WS +#elif CLOCK_AHB <= MHZ(128) +#define FLASH_WAITSTATES FLASH_ACR_LATENCY_3WS +#elif CLOCK_AHB <= MHZ(160) +#define FLASH_WAITSTATES FLASH_ACR_LATENCY_4WS +#endif + +void stmclk_init_sysclk(void) +{ + /* disable any interrupts. Global interrupts could be enabled if this is + * called from some kind of bootloader... */ + unsigned is = irq_disable(); + RCC->CIER = 0; + + /* select 1-way cache */ + ICACHE->CR &= ~ICACHE_CR_WAYSEL; + ICACHE->CR |= ICACHE_CR_EN; + + /* enable HSI clock for the duration of initialization */ + stmclk_enable_hsi(); + + /* use HSI as system clock while we do any further configuration and + * configure the AHB and APB clock dividers as configured by the board */ + RCC->CFGR1 = RCC_CFGR1_SW_HSI; + while ((RCC->CFGR1 & RCC_CFGR1_SWS) != RCC_CFGR1_SWS_HSI) {} + RCC->CFGR2 = (CLOCK_AHB_DIV | CLOCK_APB1_DIV | CLOCK_APB2_DIV); + + /* Select the Voltage Range 1 */ + PWR->VOSR = (PWR_VOSR_VOS_1 | PWR_VOSR_VOS_0); + /* Wait Until the Voltage Regulator is ready */ + while (!(PWR->VOSR & PWR_VOSR_VOSRDY)) {} + + /* Switch to SMPS regulator instead of LDO */ + PWR->CR3 |= PWR_CR3_REGSEL; + while (!(PWR->SVMSR & PWR_SVMSR_REGS)) {} + + /* configure flash wait states */ + FLASH->ACR = FLASH_WAITSTATES; + + /* disable all active clocks except HSI -> resets the clk configuration */ + RCC->CR = RCC_CR_HSION; + + /* Enable the HSE clock only when it's used */ + if (IS_ACTIVE(CLOCK_ENABLE_HSE)) { + RCC->CR |= (RCC_CR_HSEON); + while (!(RCC->CR & RCC_CR_HSERDY)) {} + } + + /* Enable the MSI clock only when it's used */ + if (IS_ACTIVE(CLOCK_ENABLE_MSI)) { + RCC->ICSCR1 = RCC_ICSCR1_MSIRGSEL; + RCC->ICSCR1 |= CLOCK_MSIRANGE; + RCC->CR |= (RCC_CR_MSISON | RCC_CR_MSIPLLSEL | RCC_CR_MSIPLLFAST); + while (!(RCC->CR & RCC_CR_MSISRDY)) {} + } + + /* Enable the PLL clock only when it's used */ + if (IS_ACTIVE(CLOCK_ENABLE_PLL)) { + if (IS_ACTIVE(CONFIG_CLOCK_PLL_SRC_MSI) && IS_ACTIVE(CONFIG_BOARD_HAS_LSE)) { + /* configure the low speed clock domain */ + stmclk_enable_lfclk(); + /* now we can enable the MSI PLL mode to enhance accuracy of the MSI */ + RCC->CR |= RCC_CR_MSIPLLEN; + while (!(RCC->CR & RCC_CR_MSISRDY)) {} + } + + /* configure and start the PLL */ + RCC->PLL1CFGR = (PLL_SRC | PLL_M | RCC_PLL1CFGR_PLL1RGE_1 | RCC_PLL1CFGR_PLL1RGE_0); + + if (IS_ACTIVE(CONFIG_USE_CLOCK_PLL)) { + /* Enable PLLCLK if PLL is used as system clock */ + RCC->PLL1CFGR |= RCC_PLL1CFGR_PLL1REN; + } + + if (IS_ACTIVE(CLOCK48MHZ_USE_PLLQ)) { + /* Enable PLLQ if PLL is used as 48MHz source clock */ + RCC->PLL1CFGR |= RCC_PLL1CFGR_PLL1QEN; + } + + RCC->PLL1DIVR = (PLL_N | PLL_R | PLL_Q); + RCC->PLL1FRACR = 0; + RCC->CR |= RCC_CR_PLL1ON; + while (!(RCC->CR & RCC_CR_PLL1RDY)) {} + } + + /* Configure SYSCLK */ + if (!IS_ACTIVE(CONFIG_USE_CLOCK_HSI)) { + RCC->CFGR1 &= ~RCC_CFGR1_SW; + } + + if (IS_ACTIVE(CONFIG_USE_CLOCK_HSE)) { + /* Select HSE as system clock */ + RCC->CFGR1 |= RCC_CFGR1_SW_HSE; + while ((RCC->CFGR1 & RCC_CFGR1_SWS) != RCC_CFGR1_SWS_HSE) {} + } + else if (IS_ACTIVE(CONFIG_USE_CLOCK_MSI)) { + /* Select MSI as system clock */ + RCC->CFGR1 |= RCC_CFGR1_SW_MSI; + while ((RCC->CFGR1 & RCC_CFGR1_SWS) != RCC_CFGR1_SWS_MSI) {} + } + else if (IS_ACTIVE(CONFIG_USE_CLOCK_PLL)) { + /* Select main PLL as system clock */ + RCC->CFGR1 |= RCC_CFGR1_SW_PLL; + while ((RCC->CFGR1 & RCC_CFGR1_SWS) != RCC_CFGR1_SWS_PLL) {} + } + + if (!IS_ACTIVE(CLOCK_ENABLE_HSI)) { + /* Disable HSI only if not used */ + stmclk_disable_hsi(); + } + + if (IS_ACTIVE(CLOCK_ENABLE_48MHZ)) { + /* configure the clock used for the 48MHz clock tree (USB, RNG) */ + RCC->CCIPR1 = CLOCK48MHZ_SELECT; + } + + irq_restore(is); +} From 62a682dd2cfdfa76317895320d458aacb79b7fa8 Mon Sep 17 00:00:00 2001 From: Alexandre Abadie Date: Wed, 15 Dec 2021 15:54:10 +0100 Subject: [PATCH 2/6] boards/b-u585i-iot02a: add initial basic support --- boards/b-u585i-iot02a/Kconfig | 28 +++ boards/b-u585i-iot02a/Makefile | 3 + boards/b-u585i-iot02a/Makefile.dep | 5 + boards/b-u585i-iot02a/Makefile.features | 9 + boards/b-u585i-iot02a/Makefile.include | 13 ++ boards/b-u585i-iot02a/board.c | 33 ++++ boards/b-u585i-iot02a/doc.txt | 43 +++++ boards/b-u585i-iot02a/include/board.h | 88 +++++++++ boards/b-u585i-iot02a/include/gpio_params.h | 67 +++++++ boards/b-u585i-iot02a/include/periph_conf.h | 186 +++++++++++++++++++ boards/common/stm32/dist/stm32u5.cfg | 3 + boards/common/stm32/include/cfg_timer_tim5.h | 3 +- 12 files changed, 480 insertions(+), 1 deletion(-) create mode 100644 boards/b-u585i-iot02a/Kconfig create mode 100644 boards/b-u585i-iot02a/Makefile create mode 100644 boards/b-u585i-iot02a/Makefile.dep create mode 100644 boards/b-u585i-iot02a/Makefile.features create mode 100644 boards/b-u585i-iot02a/Makefile.include create mode 100644 boards/b-u585i-iot02a/board.c create mode 100644 boards/b-u585i-iot02a/doc.txt create mode 100644 boards/b-u585i-iot02a/include/board.h create mode 100644 boards/b-u585i-iot02a/include/gpio_params.h create mode 100644 boards/b-u585i-iot02a/include/periph_conf.h create mode 100644 boards/common/stm32/dist/stm32u5.cfg diff --git a/boards/b-u585i-iot02a/Kconfig b/boards/b-u585i-iot02a/Kconfig new file mode 100644 index 0000000000..a270a59717 --- /dev/null +++ b/boards/b-u585i-iot02a/Kconfig @@ -0,0 +1,28 @@ +# Copyright (c) 2021 Inria +# +# This file is subject to the terms and conditions of the GNU Lesser +# General Public License v2.1. See the file LICENSE in the top level +# directory for more details. +# + +config BOARD + default "b-u585i-iot02a" if BOARD_B_U585I_IOT02A + +config BOARD_B_U585I_IOT02A + bool + default y + select CPU_MODEL_STM32U585AI + + # Put defined MCU peripherals here (in alphabetical order) + select HAS_PERIPH_I2C + select HAS_PERIPH_TIMER + select HAS_PERIPH_UART + + # Clock configuration + select BOARD_HAS_LSE + + select HAVE_SAUL_GPIO + select HAVE_HTS221 + select HAVE_LPS22HH + +source "$(RIOTBOARD)/common/stm32/Kconfig" diff --git a/boards/b-u585i-iot02a/Makefile b/boards/b-u585i-iot02a/Makefile new file mode 100644 index 0000000000..f8fcbb53a0 --- /dev/null +++ b/boards/b-u585i-iot02a/Makefile @@ -0,0 +1,3 @@ +MODULE = board + +include $(RIOTBASE)/Makefile.base diff --git a/boards/b-u585i-iot02a/Makefile.dep b/boards/b-u585i-iot02a/Makefile.dep new file mode 100644 index 0000000000..c33cb91bbf --- /dev/null +++ b/boards/b-u585i-iot02a/Makefile.dep @@ -0,0 +1,5 @@ +ifneq (,$(filter saul_default,$(USEMODULE))) + USEMODULE += saul_gpio + USEMODULE += hts221 + USEMODULE += lps22hh +endif diff --git a/boards/b-u585i-iot02a/Makefile.features b/boards/b-u585i-iot02a/Makefile.features new file mode 100644 index 0000000000..cbf9191987 --- /dev/null +++ b/boards/b-u585i-iot02a/Makefile.features @@ -0,0 +1,9 @@ +CPU = stm32 +CPU_MODEL = stm32u585ai + +# Put defined MCU peripherals here (in alphabetical order) +FEATURES_PROVIDED += periph_i2c +FEATURES_PROVIDED += periph_timer +FEATURES_PROVIDED += periph_uart + +# Put other features for this board (in alphabetical order) diff --git a/boards/b-u585i-iot02a/Makefile.include b/boards/b-u585i-iot02a/Makefile.include new file mode 100644 index 0000000000..a13523caa7 --- /dev/null +++ b/boards/b-u585i-iot02a/Makefile.include @@ -0,0 +1,13 @@ +# we use shared STM32 configuration snippets +INCLUDES += -I$(RIOTBOARD)/common/stm32/include + +# this board has an on-board ST-link adapter +PROGRAMMER ?= openocd +OPENOCD_DEBUG_ADAPTER ?= stlink + +# Add openocd as supported programmer +PROGRAMMERS_SUPPORTED += openocd + +# The board can become un-flashable after some execution, +# use connect_assert_srst to always be able to flash or reset the board. +OPENOCD_RESET_USE_CONNECT_ASSERT_SRST ?= 1 diff --git a/boards/b-u585i-iot02a/board.c b/boards/b-u585i-iot02a/board.c new file mode 100644 index 0000000000..5c1a9cccff --- /dev/null +++ b/boards/b-u585i-iot02a/board.c @@ -0,0 +1,33 @@ +/* + * Copyright (C) 2021 Inria + * + * This file is subject to the terms and conditions of the GNU Lesser + * General Public License v2.1. See the file LICENSE in the top level + * directory for more details. + */ + +/** + * @ingroup boards_b-u585i-iot02a + * @{ + * + * @file + * @brief Board specific implementations for the ST B-U585I-IOT02A board + * + * @author Alexandre Abadie + * + * @} + */ + +#include "board.h" +#include "periph/gpio.h" + +void board_init(void) +{ +#ifdef AUTO_INIT_LED0 + /* The LED pin is also used for SPI, so we enable it + only if explicitly wanted by the user */ + gpio_init(LED0_PIN, GPIO_OUT); +#endif + gpio_init(LED1_PIN, GPIO_OUT); + gpio_init(LED2_PIN, GPIO_OUT); +} diff --git a/boards/b-u585i-iot02a/doc.txt b/boards/b-u585i-iot02a/doc.txt new file mode 100644 index 0000000000..a4bccae3b2 --- /dev/null +++ b/boards/b-u585i-iot02a/doc.txt @@ -0,0 +1,43 @@ +/** +@defgroup boards_b-u585i-iot02a STM32 B-U585I-IOT02A +@ingroup boards +@brief Support for the STM32 B-U585I-IOT02A + +## Flashing the device + +The ST B-U585I-IOT02A board includes an on-board ST-LINK programmer and can be +flashed using OpenOCD. +@note The latest release (v0.11) of OpenOCD doesn't contain yet support for this board, +so the source code version from upstream master must be cloned and built: + +``` +$ git clone https://git.code.sf.net/p/openocd/code openocd +$ cd openocd +$ ./bootstrap +$ ./configure --prefix= +$ make -j +$ sudo make install +``` + +Once the patched OpenOCD is built and installed, you can flash the board simply +by typing + +``` +make BOARD=b-u585i-iot02a flash +``` + +and debug via GDB by simply typing +``` +make BOARD=b-u585i-iot02a debug +``` + +## Supported Toolchains + +For using the ST B-U585I-IOT02A board we recommend the usage of the +[GNU Tools for ARM Embedded Processors](https://launchpad.net/gcc-arm-embedded) +toolchain. + +**Important notice:** With GCC 10, the `tests/malloc` application doesn't work. +To use malloc, prefer GCC 9 which seems to work better. + + */ diff --git a/boards/b-u585i-iot02a/include/board.h b/boards/b-u585i-iot02a/include/board.h new file mode 100644 index 0000000000..6cc09498d2 --- /dev/null +++ b/boards/b-u585i-iot02a/include/board.h @@ -0,0 +1,88 @@ +/* + * Copyright (C) 2021 Inria + * + * This file is subject to the terms and conditions of the GNU Lesser + * General Public License v2.1. See the file LICENSE in the top level + * directory for more details. + */ + +/** + * @ingroup boards_b-u585i-iot02a + * @{ + * + * @file + * @brief Board specific definitions for the ST B-U585I-IOT02A board + * + * @author Alexandre Abadie + */ + +#ifndef BOARD_H +#define BOARD_H + +#include + +#include "cpu.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @name LED pin definitions and handlers + * @{ + */ +#define LED0_PIN GPIO_PIN(PORT_E, 13) +#define LED0_MASK (1 << 13) + +#define LED0_ON (GPIOE->BSRR = LED0_MASK) +#define LED0_OFF (GPIOE->BSRR = (LED0_MASK << 16)) +#define LED0_TOGGLE (GPIOE->ODR ^= LED0_MASK) + +#define LED1_PIN GPIO_PIN(PORT_H, 6) +#define LED1_MASK (1 << 6) + +#define LED1_ON (GPIOH->BSRR = LED1_MASK) +#define LED1_OFF (GPIOH->BSRR = (LED1_MASK << 16)) +#define LED1_TOGGLE (GPIOH->ODR ^= LED1_MASK) + +#define LED2_PIN GPIO_PIN(PORT_H, 7) +#define LED2_MASK (1 << 7) + +#define LED2_ON (GPIOH->BSRR = LED2_MASK) +#define LED2_OFF (GPIOH->BSRR = (LED2_MASK << 16)) +#define LED2_TOGGLE (GPIOH->ODR ^= LED2_MASK) +/** @} */ + +/** + * @name Button pin configuration + * @{ + */ +#define BTN0_PIN GPIO_PIN(PORT_C, 13) +#define BTN0_MODE GPIO_IN_PU +/** @} */ + +/** + * @name HTS221 temperature/humidity sensor configuration + * @{ + */ +#define HTS221_PARAM_I2C I2C_DEV(1) +/** @} */ + +/** + * @name LPS22HH pressure/temperature sensor configuration + * @{ + */ +#define LPSXXX_PARAM_I2C I2C_DEV(1) +/** @} */ + +/** + * @brief Initialize board specific hardware, including clock, LEDs and std-IO + */ +void board_init(void); + +#ifdef __cplusplus +} +#endif + +#endif /* BOARD_H */ +/** @} */ diff --git a/boards/b-u585i-iot02a/include/gpio_params.h b/boards/b-u585i-iot02a/include/gpio_params.h new file mode 100644 index 0000000000..d735db9572 --- /dev/null +++ b/boards/b-u585i-iot02a/include/gpio_params.h @@ -0,0 +1,67 @@ +/* + * Copyright (C) Inria 2021 + * + * This file is subject to the terms and conditions of the GNU Lesser + * General Public License v2.1. See the file LICENSE in the top level + * directory for more details. + */ + +/** + * @ingroup boards_b-u585i-iot02a + * @{ + * + * @file + * @brief Board specific configuration of direct mapped GPIOs + * + * @author Alexandre Abadie + */ + +#ifndef GPIO_PARAMS_H +#define GPIO_PARAMS_H + +#include "board.h" +#include "saul/periph.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @brief GPIO pin configuration + */ +static const saul_gpio_params_t saul_gpio_params[] = +{ +#ifdef AUTO_INIT_LED0 + /* The LED pin is also used for SPI, so we enable it + only if explicitly wanted by the user */ + { + .name = "LD2", /* Blue LED (Arduino D13) */ + .pin = LED0_PIN, + .mode = GPIO_OUT + }, +#endif + { + .name = "LD6", /* Red LED */ + .pin = LED1_PIN, + .mode = GPIO_OUT, + .flags = (SAUL_GPIO_INVERTED | SAUL_GPIO_INIT_CLEAR), + }, + { + .name = "LD7", /* Green LED */ + .pin = LED2_PIN, + .mode = GPIO_OUT, + .flags = (SAUL_GPIO_INVERTED | SAUL_GPIO_INIT_CLEAR), + }, + { + .name = "Button(B1 User)", + .pin = BTN0_PIN, + .mode = BTN0_MODE, + } +}; + +#ifdef __cplusplus +} +#endif + +#endif /* GPIO_PARAMS_H */ +/** @} */ diff --git a/boards/b-u585i-iot02a/include/periph_conf.h b/boards/b-u585i-iot02a/include/periph_conf.h new file mode 100644 index 0000000000..c7de49c36c --- /dev/null +++ b/boards/b-u585i-iot02a/include/periph_conf.h @@ -0,0 +1,186 @@ +/* + * Copyright (C) 2021 Inria + * + * This file is subject to the terms and conditions of the GNU Lesser + * General Public License v2.1. See the file LICENSE in the top level + * directory for more details. + */ + +/** + * @ingroup boards_b-u585i-iot02a + * @{ + * + * @file + * @brief Peripheral MCU configuration for the ST B-U585I-IOT02A board + * + * @author Alexandre Abadie + */ + +#ifndef PERIPH_CONF_H +#define PERIPH_CONF_H + +/* Add specific clock configuration (HSE, LSE) for this board here */ +#ifndef CONFIG_BOARD_HAS_LSE +#define CONFIG_BOARD_HAS_LSE 1 +#endif + +#include "periph_cpu.h" +#include "clk_conf.h" +#include "cfg_timer_tim5.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @name UART configuration + * @{ + */ +static const uart_conf_t uart_config[] = { + { + .dev = USART1, + .rcc_mask = RCC_APB2ENR_USART1EN, + .rx_pin = GPIO_PIN(PORT_A, 10), + .tx_pin = GPIO_PIN(PORT_A, 9), + .rx_af = GPIO_AF7, + .tx_af = GPIO_AF7, + .bus = APB2, + .irqn = USART1_IRQn, + .type = STM32_USART, + .clk_src = 0, /* Use APB clock */ + }, + { /* Connected to Arduino D0/D1 and STMOD+2 */ + .dev = USART3, + .rcc_mask = RCC_APB1ENR1_USART3EN, + .rx_pin = GPIO_PIN(PORT_D, 9), + .tx_pin = GPIO_PIN(PORT_D, 8), + .rx_af = GPIO_AF7, + .tx_af = GPIO_AF7, + .bus = APB1, + .irqn = USART3_IRQn, + .type = STM32_USART, + .clk_src = 0, /* Use APB clock */ + }, + { /* Connected to STMOD+1 */ + .dev = USART2, + .rcc_mask = RCC_APB1ENR1_USART2EN, + .rx_pin = GPIO_PIN(PORT_A, 3), + .tx_pin = GPIO_PIN(PORT_A, 2), + .rx_af = GPIO_AF7, + .tx_af = GPIO_AF7, + .bus = APB1, + .irqn = USART2_IRQn, + .type = STM32_USART, + .clk_src = 0, /* Use APB clock */ + }, + { /* Connected to Wireless */ + .dev = UART4, + .rcc_mask = RCC_APB1ENR1_UART4EN, + .rx_pin = GPIO_PIN(PORT_C, 11), + .tx_pin = GPIO_PIN(PORT_C, 10), + .rx_af = GPIO_AF7, + .tx_af = GPIO_AF7, + .bus = APB1, + .irqn = UART4_IRQn, + .type = STM32_USART, + .clk_src = 0, /* Use APB clock */ + }, +}; + +#define UART_0_ISR (isr_usart1) +#define UART_1_ISR (isr_usart3) +#define UART_2_ISR (isr_usart2) +#define UART_3_ISR (isr_uart4) + +#define UART_NUMOF ARRAY_SIZE(uart_config) +/** @} */ + +/** + * @name SPI configuration + * @{ + */ +static const spi_conf_t spi_config[] = { + { + .dev = SPI1, + .mosi_pin = GPIO_PIN(PORT_E, 15), /* Arduino D11 */ + .miso_pin = GPIO_PIN(PORT_E, 14), /* Arduino D12 */ + .sclk_pin = GPIO_PIN(PORT_E, 13), /* Arduino D13 */ + .cs_pin = GPIO_UNDEF, + .mosi_af = GPIO_AF5, + .miso_af = GPIO_AF5, + .sclk_af = GPIO_AF5, + .cs_af = GPIO_AF5, + .rccmask = RCC_APB2ENR_SPI1EN, + .apbbus = APB2, + }, + { /* Connected to wireless */ + .dev = SPI2, + .mosi_pin = GPIO_PIN(PORT_D, 4), + .miso_pin = GPIO_PIN(PORT_D, 3), + .sclk_pin = GPIO_PIN(PORT_D, 1), + .cs_pin = GPIO_PIN(PORT_B, 12), + .mosi_af = GPIO_AF5, + .miso_af = GPIO_AF5, + .sclk_af = GPIO_AF5, + .cs_af = GPIO_AF5, + .rccmask = RCC_APB1ENR1_SPI2EN, + .apbbus = APB1, + }, + { /* Connected to STMOD+ 2 */ + .dev = SPI3, + .mosi_pin = GPIO_PIN(PORT_D, 6), + .miso_pin = GPIO_PIN(PORT_G, 10), + .sclk_pin = GPIO_PIN(PORT_G, 9), + .cs_pin = GPIO_PIN(PORT_G, 12), + .mosi_af = GPIO_AF5, + .miso_af = GPIO_AF5, + .sclk_af = GPIO_AF5, + .cs_af = GPIO_AF5, + .rccmask = RCC_APB3ENR_SPI3EN, + .apbbus = APB3, + }, +}; + +#define SPI_NUMOF ARRAY_SIZE(spi_config) +/** @} */ + +/** + * @name I2C configuration + * @{ + */ +static const i2c_conf_t i2c_config[] = { + { + .dev = I2C1, + .speed = I2C_SPEED_NORMAL, + .scl_pin = GPIO_PIN(PORT_B, 8), + .sda_pin = GPIO_PIN(PORT_B, 9), + .scl_af = GPIO_AF4, + .sda_af = GPIO_AF4, + .bus = APB1, + .rcc_mask = RCC_APB1ENR1_I2C1EN, + .irqn = I2C1_ER_IRQn, + }, + { + .dev = I2C2, + .speed = I2C_SPEED_NORMAL, + .scl_pin = GPIO_PIN(PORT_H, 4), + .sda_pin = GPIO_PIN(PORT_H, 5), + .scl_af = GPIO_AF4, + .sda_af = GPIO_AF4, + .bus = APB1, + .rcc_mask = RCC_APB1ENR1_I2C2EN, + .irqn = I2C2_ER_IRQn, + }, +}; + +#define I2C_0_ISR isr_i2c1_er +#define I2C_1_ISR isr_i2c2_er +#define I2C_NUMOF ARRAY_SIZE(i2c_config) +/** @} */ + +#ifdef __cplusplus +} +#endif + +#endif /* PERIPH_CONF_H */ +/** @} */ diff --git a/boards/common/stm32/dist/stm32u5.cfg b/boards/common/stm32/dist/stm32u5.cfg new file mode 100644 index 0000000000..5406b40301 --- /dev/null +++ b/boards/common/stm32/dist/stm32u5.cfg @@ -0,0 +1,3 @@ +source [find target/stm32u5x.cfg] +reset_config srst_only +$_TARGETNAME configure -rtos auto diff --git a/boards/common/stm32/include/cfg_timer_tim5.h b/boards/common/stm32/include/cfg_timer_tim5.h index 5f44ef71d9..7b38a2110e 100644 --- a/boards/common/stm32/include/cfg_timer_tim5.h +++ b/boards/common/stm32/include/cfg_timer_tim5.h @@ -33,7 +33,8 @@ static const timer_conf_t timer_config[] = { { .dev = TIM5, .max = 0xffffffff, -#if defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) +#if defined(CPU_FAM_STM32G4) || defined(CPU_FAM_STM32L5) || \ + defined(CPU_FAM_STM32U5) .rcc_mask = RCC_APB1ENR1_TIM5EN, #else .rcc_mask = RCC_APB1ENR_TIM5EN, From 86af5b583271284edd97a80b1f528f38be59790b Mon Sep 17 00:00:00 2001 From: Alexandre Abadie Date: Wed, 15 Dec 2021 18:01:16 +0100 Subject: [PATCH 3/6] tools/doccheck: extend exclude patterns for b-u585i-iot02a --- dist/tools/doccheck/exclude_patterns | 51 ++++++++++++++++++++++++++++ 1 file changed, 51 insertions(+) diff --git a/dist/tools/doccheck/exclude_patterns b/dist/tools/doccheck/exclude_patterns index 7262e6a8cf..09bf50b1cc 100644 --- a/dist/tools/doccheck/exclude_patterns +++ b/dist/tools/doccheck/exclude_patterns @@ -14592,3 +14592,54 @@ drivers/sx126x/include/sx126x_params\.h:[0-9]+: warning: Member SX126X_PARAM_TX_ drivers/sx126x/include/sx126x_params\.h:[0-9]+: warning: Member SX126X_TX_PA_MODE \(macro definition\) of file sx126x_params\.h is not documented\. boards/lora\-e5\-dev/include/periph_conf\.h:[0-9]+: warning: Member ADC_NUMOF \(macro definition\) of file periph_conf\.h is not documented\. boards/lora\-e5\-dev/include/periph_conf\.h:[0-9]+: warning: Member adc_config\[\] \(variable\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member CONFIG_BOARD_HAS_LSE \(macro definition\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member UART_0_ISR \(macro definition\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member UART_1_ISR \(macro definition\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member UART_2_ISR \(macro definition\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member UART_3_ISR \(macro definition\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member UART_NUMOF \(macro definition\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member uart_config\[\] \(variable\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member SPI_NUMOF \(macro definition\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member spi_config\[\] \(variable\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member I2C_0_ISR \(macro definition\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member I2C_1_ISR \(macro definition\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member I2C_NUMOF \(macro definition\) of file periph_conf\.h is not documented\. +boards/b\-u585i\-iot02a/include/periph_conf\.h:[0-9]+: warning: Member i2c_config\[\] \(variable\) of file periph_conf\.h is not documented\. + boards/b\-u585i\-iot02a/include/periph_conf\.h +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED0_PIN \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED0_MASK \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED0_ON \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED0_OFF \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED0_TOGGLE \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED1_PIN \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED1_MASK \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED1_ON \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED1_OFF \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED1_TOGGLE \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED2_PIN \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED2_MASK \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED2_ON \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED2_OFF \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LED2_TOGGLE \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member BTN0_PIN \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member BTN0_MODE \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member HTS221_PARAM_I2C \(macro definition\) of file board\.h is not documented\. +boards/b\-u585i\-iot02a/include/board\.h:[0-9]+: warning: Member LPSXXX_PARAM_I2C \(macro definition\) of file board\.h is not documented\. + boards/b\-u585i\-iot02a/include/board\.h +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CONFIG_CLOCK_PLL_SRC_MSI \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CONFIG_CLOCK_PLL_SRC_HSE \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CONFIG_CLOCK_PLL_SRC_HSI \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CLOCK_PLL_SRC \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CONFIG_CLOCK_PLL_M \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CONFIG_CLOCK_PLL_N \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CONFIG_CLOCK_PLL_Q \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CONFIG_CLOCK_PLL_R \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CLOCK_AHB \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CONFIG_CLOCK_APB1_DIV \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CLOCK_APB1 \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CONFIG_CLOCK_APB2_DIV \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/u5/cfg_clock_default\.h:[0-9]+: warning: Member CLOCK_APB2 \(macro definition\) of file cfg_clock_default\.h is not documented\. +cpu/stm32/include/clk/cfg_clock_common_lx_u5_wx\.h:[0-9]+: warning: Member CLOCK_HSE \(macro definition\) of file cfg_clock_common_lx_u5_wx\.h is not documented\. +cpu/stm32/include/clk/cfg_clock_common_lx_u5_wx\.h:[0-9]+: warning: Member CLOCK_HSI \(macro definition\) of file cfg_clock_common_lx_u5_wx\.h is not documented\. +cpu/stm32/include/clk/cfg_clock_common_lx_u5_wx\.h:[0-9]+: warning: Member CONFIG_CLOCK_MSI \(macro definition\) of file cfg_clock_common_lx_u5_wx\.h is not documented\. +cpu/stm32/include/clk/cfg_clock_common_lx_u5_wx\.h:[0-9]+: warning: Member CONFIG_USE_CLOCK_PLL \(macro definition\) of file cfg_clock_common_lx_u5_wx\.h is not documented\. From 2191859dffe00c052385f05bf8d96f59f0cfa7f0 Mon Sep 17 00:00:00 2001 From: Alexandre Abadie Date: Thu, 16 Dec 2021 15:50:40 +0100 Subject: [PATCH 4/6] pkg/cifra: fix build error with redefined assert --- pkg/cifra/Makefile.include | 2 ++ 1 file changed, 2 insertions(+) diff --git a/pkg/cifra/Makefile.include b/pkg/cifra/Makefile.include index 42612137bb..7816e2fcd8 100644 --- a/pkg/cifra/Makefile.include +++ b/pkg/cifra/Makefile.include @@ -1,2 +1,4 @@ INCLUDES += -I$(PKGDIRBASE)/cifra/src INCLUDES += -I$(PKGDIRBASE)/cifra/src/ext + +CFLAGS += -DFULL_FAT_ASSERT From d645ea89e969f8d549d872f58d7c4e9e00d583da Mon Sep 17 00:00:00 2001 From: Alexandre Abadie Date: Fri, 17 Dec 2021 10:34:04 +0100 Subject: [PATCH 5/6] tests/malloc: increase test timeout for very large mems --- tests/malloc/tests/01-run.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/malloc/tests/01-run.py b/tests/malloc/tests/01-run.py index a29812b9da..622d59a028 100755 --- a/tests/malloc/tests/01-run.py +++ b/tests/malloc/tests/01-run.py @@ -11,7 +11,7 @@ from testrunner import run # For BOARD's with large amount of RAM allocating all chunks takes longer # than 10s -ALLOCATION_TIMEOUT = 20 +ALLOCATION_TIMEOUT = 30 FREE_TIMEOUT = ALLOCATION_TIMEOUT From 8607a9cdfae09f73841fac2780232a3dded42109 Mon Sep 17 00:00:00 2001 From: Benjamin Valentin Date: Thu, 23 Dec 2021 11:04:26 +0100 Subject: [PATCH 6/6] cpu/stm32: extend RAM with SRAM4 --- cpu/stm32/Makefile.include | 3 +++ cpu/stm32/include/cpu_conf.h | 1 + cpu/stm32/ldscripts/stm32.ld | 11 +++++++++++ cpu/stm32/stm32_mem_lengths.mk | 1 + 4 files changed, 16 insertions(+) diff --git a/cpu/stm32/Makefile.include b/cpu/stm32/Makefile.include index 884890ccc1..406f58a34c 100644 --- a/cpu/stm32/Makefile.include +++ b/cpu/stm32/Makefile.include @@ -61,6 +61,9 @@ info-stm32: ifneq (,$(CCMRAM_LEN)) LINKFLAGS += $(LINKFLAGPREFIX)--defsym=_ccmram_length=$(CCMRAM_LEN) endif +ifneq (,$(SRAM4_LEN)) + LINKFLAGS += $(LINKFLAGPREFIX)--defsym=_sram4_length=$(SRAM4_LEN) +endif VECTORS_O ?= $(BINDIR)/stm32_vectors/$(CPU_LINE).o VECTORS_FILE = $(RIOTCPU)/stm32/vectors/$(CPU_LINE).c diff --git a/cpu/stm32/include/cpu_conf.h b/cpu/stm32/include/cpu_conf.h index aafc636e91..8930b13cea 100644 --- a/cpu/stm32/include/cpu_conf.h +++ b/cpu/stm32/include/cpu_conf.h @@ -67,6 +67,7 @@ #elif CPU_FAM_STM32U5 #include "stm32u5xx.h" #include "irqs/u5/irqs.h" +#define NUM_HEAPS 2 #elif CPU_FAM_STM32WB #include "stm32wbxx.h" #include "irqs/wb/irqs.h" diff --git a/cpu/stm32/ldscripts/stm32.ld b/cpu/stm32/ldscripts/stm32.ld index fb50fcf119..1ed6fa43d5 100644 --- a/cpu/stm32/ldscripts/stm32.ld +++ b/cpu/stm32/ldscripts/stm32.ld @@ -19,10 +19,21 @@ */ ccmram_length = DEFINED( ccmram_len ) ? ccmram_len : 0x0 ; +sram4_length = DEFINED( sram4_length ) ? sram4_length : 0x0 ; MEMORY { ccmram : ORIGIN = 0x10000000, LENGTH = ccmram_length + sram4 : ORIGIN = 0x28000000, LENGTH = sram4_length +} + +SECTIONS +{ + .heap2 ALIGN(4) (NOLOAD) : + { + _sheap1 = . ; + _eheap1 = ORIGIN(sram4) + LENGTH(sram4); + } > sram4 } INCLUDE cortexm.ld diff --git a/cpu/stm32/stm32_mem_lengths.mk b/cpu/stm32/stm32_mem_lengths.mk index 7950d3c857..410cd9aa18 100644 --- a/cpu/stm32/stm32_mem_lengths.mk +++ b/cpu/stm32/stm32_mem_lengths.mk @@ -270,6 +270,7 @@ else ifeq ($(STM32_TYPE), U) ifeq ($(STM32_FAMILY), 5) ifneq (, $(filter $(STM32_MODEL2), 7 8)) RAM_LEN = 768K + SRAM4_LEN = 16K endif endif else ifeq ($(STM32_TYPE), W)