soc: arm: st_stm32 add low power to stm32wb series
This patch introduces the support of low power modes for the STM32WBxx from STMicroelectronics based on the lptim Here, the power modes are sleep modes have lptimer as wakeup source. The sleep modes are configured by the SYS_POWER_MANAGEMENT. Signed-off-by: Francois Ramu <francois.ramu@st.com>
This commit is contained in:
parent
edcee97346
commit
fd5ce64db4
5 changed files with 141 additions and 1 deletions
|
@ -7,3 +7,7 @@ zephyr_linker_sources_ifdef(CONFIG_BT_STM32_IPM
|
|||
SECTIONS
|
||||
ipm.ld
|
||||
)
|
||||
|
||||
zephyr_sources_ifdef(CONFIG_SYS_POWER_MANAGEMENT
|
||||
power.c
|
||||
)
|
||||
|
|
|
@ -10,6 +10,11 @@ source "soc/arm/st_stm32/stm32wb/Kconfig.defconfig.stm32wb*"
|
|||
config SOC_SERIES
|
||||
default "stm32wb"
|
||||
|
||||
config STM32_LPTIM_TIMER
|
||||
bool
|
||||
default y
|
||||
depends on SYS_POWER_MANAGEMENT
|
||||
|
||||
config DMA_STM32_V2
|
||||
default y
|
||||
depends on DMA_STM32
|
||||
|
|
|
@ -13,5 +13,8 @@ config SOC_SERIES_STM32WBX
|
|||
select HAS_STM32CUBE
|
||||
select CPU_HAS_ARM_MPU
|
||||
select HAS_SWO
|
||||
select HAS_SYS_POWER_STATE_SLEEP_1
|
||||
select HAS_SYS_POWER_STATE_SLEEP_2
|
||||
select HAS_SYS_POWER_STATE_SLEEP_3
|
||||
help
|
||||
Enable support for STM32WB MCU series
|
||||
|
|
128
soc/arm/st_stm32/stm32wb/power.c
Normal file
128
soc/arm/st_stm32/stm32wb/power.c
Normal file
|
@ -0,0 +1,128 @@
|
|||
/*
|
||||
* Copyright (c) 2019 STMicroelectronics.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
#include <zephyr.h>
|
||||
#include <power/power.h>
|
||||
#include <soc.h>
|
||||
#include <init.h>
|
||||
|
||||
#include <stm32wbxx_ll_bus.h>
|
||||
#include <stm32wbxx_ll_cortex.h>
|
||||
#include <stm32wbxx_ll_pwr.h>
|
||||
#include <stm32wbxx_ll_rcc.h>
|
||||
|
||||
#include <logging/log.h>
|
||||
LOG_MODULE_DECLARE(soc, CONFIG_SOC_LOG_LEVEL);
|
||||
|
||||
/* Invoke Low Power/System Off specific Tasks */
|
||||
void sys_set_power_state(enum power_states state)
|
||||
{
|
||||
switch (state) {
|
||||
#ifdef CONFIG_SYS_POWER_SLEEP_STATES
|
||||
#ifdef CONFIG_HAS_SYS_POWER_STATE_SLEEP_1
|
||||
case SYS_POWER_STATE_SLEEP_1:
|
||||
|
||||
/* this corresponds to the STOP0 mode: */
|
||||
#ifdef CONFIG_DEBUG
|
||||
/* Enable the Debug Module during STOP mode */
|
||||
LL_DBGMCU_EnableDBGStopMode();
|
||||
#endif /* CONFIG_DEBUG */
|
||||
/* ensure HSI is the wake-up system clock */
|
||||
LL_RCC_SetClkAfterWakeFromStop(LL_RCC_STOP_WAKEUPCLOCK_HSI);
|
||||
/* enter STOP0 mode */
|
||||
LL_PWR_SetPowerMode(LL_PWR_MODE_STOP0);
|
||||
LL_LPM_EnableDeepSleep();
|
||||
/* enter SLEEP mode : WFE or WFI */
|
||||
k_cpu_idle();
|
||||
break;
|
||||
#endif /* CONFIG_HAS_SYS_POWER_STATE_SLEEP_1 */
|
||||
#ifdef CONFIG_HAS_SYS_POWER_STATE_SLEEP_2
|
||||
case SYS_POWER_STATE_SLEEP_2:
|
||||
/* this corresponds to the STOP1 mode: */
|
||||
#ifdef CONFIG_DEBUG
|
||||
/* Enable the Debug Module during STOP mode */
|
||||
LL_DBGMCU_EnableDBGStopMode();
|
||||
#endif /* CONFIG_DEBUG */
|
||||
/* ensure HSI is the wake-up system clock */
|
||||
LL_RCC_SetClkAfterWakeFromStop(LL_RCC_STOP_WAKEUPCLOCK_HSI);
|
||||
/* enter STOP1 mode */
|
||||
LL_PWR_SetPowerMode(LL_PWR_MODE_STOP1);
|
||||
LL_LPM_EnableDeepSleep();
|
||||
k_cpu_idle();
|
||||
break;
|
||||
#endif /* CONFIG_HAS_SYS_POWER_STATE_SLEEP_2 */
|
||||
#ifdef CONFIG_HAS_SYS_POWER_STATE_SLEEP_3
|
||||
case SYS_POWER_STATE_SLEEP_3:
|
||||
/* this corresponds to the STOP2 mode: */
|
||||
#ifdef CONFIG_DEBUG
|
||||
/* Enable the Debug Module during STOP mode */
|
||||
LL_DBGMCU_EnableDBGStopMode();
|
||||
#endif /* CONFIG_DEBUG */
|
||||
/* ensure HSI is the wake-up system clock */
|
||||
LL_RCC_SetClkAfterWakeFromStop(LL_RCC_STOP_WAKEUPCLOCK_HSI);
|
||||
#ifdef PWR_CR1_RRSTP
|
||||
LL_PWR_DisableSRAM3Retention();
|
||||
#endif /* PWR_CR1_RRSTP */
|
||||
/* enter STOP2 mode */
|
||||
LL_PWR_SetPowerMode(LL_PWR_MODE_STOP2);
|
||||
LL_LPM_EnableDeepSleep();
|
||||
k_cpu_idle();
|
||||
break;
|
||||
#endif /* CONFIG_HAS_SYS_POWER_STATE_SLEEP_3 */
|
||||
#endif /* CONFIG_SYS_POWER_SLEEP_STATES */
|
||||
default:
|
||||
LOG_DBG("Unsupported power state %u", state);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Handle SOC specific activity after Low Power Mode Exit */
|
||||
void _sys_pm_power_state_exit_post_ops(enum power_states state)
|
||||
{
|
||||
switch (state) {
|
||||
#ifdef CONFIG_SYS_POWER_SLEEP_STATES
|
||||
#ifdef CONFIG_HAS_SYS_POWER_STATE_SLEEP_1
|
||||
case SYS_POWER_STATE_SLEEP_1:
|
||||
#endif /* CONFIG_HAS_SYS_POWER_STATE_SLEEP_1 */
|
||||
#ifdef CONFIG_HAS_SYS_POWER_STATE_SLEEP_2
|
||||
case SYS_POWER_STATE_SLEEP_2:
|
||||
#endif /* CONFIG_HAS_SYS_POWER_STATE_SLEEP_2 */
|
||||
#ifdef CONFIG_HAS_SYS_POWER_STATE_SLEEP_3
|
||||
case SYS_POWER_STATE_SLEEP_3:
|
||||
#endif /* CONFIG_HAS_SYS_POWER_STATE_SLEEP_3 */
|
||||
LL_LPM_DisableSleepOnExit();
|
||||
break;
|
||||
#endif /* CONFIG_SYS_POWER_SLEEP_STATES */
|
||||
default:
|
||||
LOG_DBG("Unsupported power state %u", state);
|
||||
break;
|
||||
}
|
||||
|
||||
/*
|
||||
* System is now in active mode.
|
||||
* Reenable interrupts which were disabled
|
||||
* when OS started idling code.
|
||||
*/
|
||||
irq_unlock(0);
|
||||
}
|
||||
|
||||
/* Initialize STM32 Power */
|
||||
static int stm32_power_init(struct device *dev)
|
||||
{
|
||||
unsigned int ret;
|
||||
|
||||
ARG_UNUSED(dev);
|
||||
|
||||
ret = irq_lock();
|
||||
|
||||
/* enable Power clock */
|
||||
LL_APB1_GRP1_EnableClock(LL_APB1_GRP1_PERIPH_PWR);
|
||||
|
||||
irq_unlock(ret);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
SYS_INIT(stm32_power_init, POST_KERNEL, CONFIG_KERNEL_INIT_PRIORITY_DEFAULT);
|
|
@ -45,7 +45,7 @@ static const char *const core_devices[] = {
|
|||
static const char *const core_devices[] = {
|
||||
"",
|
||||
};
|
||||
#elif defined(CONFIG_SOC_SERIES_STM32L4X)
|
||||
#elif defined(CONFIG_SOC_SERIES_STM32L4X) || defined(CONFIG_SOC_SERIES_STM32WBX)
|
||||
#define MAX_PM_DEVICES 1
|
||||
static const char *const core_devices[] = {
|
||||
"sys_clock",
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue