1 /* 2 * Copyright (c) 2021 Vestas Wind Systems A/S 3 * Copyright 2021, 2024 NXP 4 * 5 * SPDX-License-Identifier: Apache-2.0 6 */ 7 8 #include <zephyr/kernel.h> 9 #include <zephyr/logging/log.h> 10 #include <zephyr/pm/pm.h> 11 #include <soc.h> 12 13 LOG_MODULE_DECLARE(power, CONFIG_PM_LOG_LEVEL); 14 wait_for_flash_prefetch_and_idle(void)15__ramfunc static void wait_for_flash_prefetch_and_idle(void) 16 { 17 uint32_t i; 18 19 for (i = 0; i < 8; i++) { 20 arch_nop(); 21 } 22 23 k_cpu_idle(); 24 } 25 pm_state_set(enum pm_state state,uint8_t substate_id)26void pm_state_set(enum pm_state state, uint8_t substate_id) 27 { 28 switch (state) { 29 case PM_STATE_RUNTIME_IDLE: 30 k_cpu_idle(); 31 break; 32 case PM_STATE_SUSPEND_TO_IDLE: 33 /* Set partial stop mode and enable deep sleep */ 34 SMC->STOPCTRL = SMC_STOPCTRL_PSTOPO(substate_id); 35 SCB->SCR |= SCB_SCR_SLEEPDEEP_Msk; 36 if (IS_ENABLED(CONFIG_XIP)) { 37 wait_for_flash_prefetch_and_idle(); 38 } else { 39 k_cpu_idle(); 40 } 41 if (SMC->PMCTRL & SMC_PMCTRL_STOPA_MASK) { 42 LOG_DBG("partial stop aborted"); 43 } 44 break; 45 default: 46 LOG_WRN("Unsupported power state %u", state); 47 break; 48 } 49 } 50 pm_state_exit_post_ops(enum pm_state state,uint8_t substate_id)51void pm_state_exit_post_ops(enum pm_state state, uint8_t substate_id) 52 { 53 ARG_UNUSED(substate_id); 54 55 if (state == PM_STATE_SUSPEND_TO_IDLE) { 56 /* Disable deep sleep upon exit */ 57 SCB->SCR &= ~(SCB_SCR_SLEEPDEEP_Msk); 58 } 59 60 irq_unlock(0); 61 } 62