soc: rw6xx: Add power management support

Add support for Power modes 1 and 2.
The wakeup from power mode 2 is from the os timer.

Signed-off-by: Mahesh Mahadevan <mahesh.mahadevan@nxp.com>
This commit is contained in:
Mahesh Mahadevan 2024-05-13 16:09:25 -05:00 committed by Anas Nashif
commit 8824fa8bdd
3 changed files with 82 additions and 0 deletions

View file

@ -7,6 +7,10 @@ zephyr_sources(
flexspi_clock_setup.c flexspi_clock_setup.c
) )
zephyr_sources_ifdef(CONFIG_PM
power.c
)
zephyr_linker_sources_ifdef(CONFIG_NXP_RW6XX_BOOT_HEADER zephyr_linker_sources_ifdef(CONFIG_NXP_RW6XX_BOOT_HEADER
ROM_START SORT_KEY 0 boot_header.ld) ROM_START SORT_KEY 0 boot_header.ld)

View file

@ -17,6 +17,7 @@ config SOC_SERIES_RW6XX
select HAS_MCUX_FLEXCOMM select HAS_MCUX_FLEXCOMM
select INIT_SYS_PLL select INIT_SYS_PLL
select HAS_MCUX_CACHE select HAS_MCUX_CACHE
select HAS_PM
if SOC_SERIES_RW6XX if SOC_SERIES_RW6XX

77
soc/nxp/rw/power.c Normal file
View file

@ -0,0 +1,77 @@
/*
* Copyright 2023, NXP
*
* SPDX-License-Identifier: Apache-2.0
*/
#include <zephyr/kernel.h>
#include <zephyr/pm/pm.h>
#include <zephyr/init.h>
#include "fsl_power.h"
#include <zephyr/logging/log.h>
LOG_MODULE_DECLARE(soc, CONFIG_SOC_LOG_LEVEL);
/* Active mode */
#define POWER_MODE0 0
/* Idle mode */
#define POWER_MODE1 1
/* Standby mode */
#define POWER_MODE2 2
/* Sleep mode */
#define POWER_MODE3 3
/* Deep Sleep mode */
#define POWER_MODE4 4
#define NODE_ID DT_INST(0, nxp_pdcfg_power)
power_sleep_config_t slp_cfg;
/* Invoke Low Power/System Off specific Tasks */
__weak void pm_state_set(enum pm_state state, uint8_t substate_id)
{
ARG_UNUSED(substate_id);
/* Set PRIMASK */
__disable_irq();
/* Set BASEPRI to 0 */
irq_unlock(0);
switch (state) {
case PM_STATE_RUNTIME_IDLE:
POWER_SetSleepMode(POWER_MODE1);
__WFI();
break;
case PM_STATE_SUSPEND_TO_IDLE:
POWER_EnterPowerMode(POWER_MODE2, &slp_cfg);
break;
default:
LOG_DBG("Unsupported power state %u", state);
break;
}
}
/* Handle SOC specific activity after Low Power Mode Exit */
__weak void pm_state_exit_post_ops(enum pm_state state, uint8_t substate_id)
{
ARG_UNUSED(state);
ARG_UNUSED(substate_id);
/* Clear PRIMASK */
__enable_irq();
}
static int nxp_rw6xx_power_init(void)
{
uint32_t suspend_sleepconfig[5] = DT_PROP_OR(NODE_ID, deep_sleep_config, {});
slp_cfg.pm2MemPuCfg = suspend_sleepconfig[0];
slp_cfg.pm2AnaPuCfg = suspend_sleepconfig[1];
slp_cfg.clkGate = suspend_sleepconfig[2];
slp_cfg.memPdCfg = suspend_sleepconfig[3];
slp_cfg.pm3BuckCfg = suspend_sleepconfig[4];
return 0;
}
SYS_INIT(nxp_rw6xx_power_init, PRE_KERNEL_1, CONFIG_KERNEL_INIT_PRIORITY_DEFAULT);