443 lines
12 KiB
C
443 lines
12 KiB
C
/*
|
|
* Copyright (c) 2016, Freescale Semiconductor, Inc.
|
|
* Copyright 2016-2018, 2020-2021 NXP
|
|
* All rights reserved.
|
|
*
|
|
* SPDX-License-Identifier: BSD-3-Clause
|
|
*/
|
|
#ifndef _FSL_POWER_H_
|
|
#define _FSL_POWER_H_
|
|
|
|
#include "fsl_common.h"
|
|
|
|
/*******************************************************************************
|
|
* Definitions
|
|
******************************************************************************/
|
|
|
|
/*!
|
|
* @addtogroup power
|
|
* @{
|
|
*/
|
|
|
|
/*! @name Driver version */
|
|
/*@{*/
|
|
/*! @brief power driver version 2.1.0. */
|
|
#define FSL_POWER_DRIVER_VERSION (MAKE_VERSION(2, 1, 0))
|
|
/*@}*/
|
|
|
|
/*! @brief PMU PCON reserved mask, used to clear reserved field which should not write 1*/
|
|
#define PMUC_PCON_RESERVED_MASK ((0xf << 4) | (0x6 << 8) | 0xfffff000u)
|
|
|
|
#define POWER_EnbaleLPO POWER_EnableLPO
|
|
#define POWER_EnbaleLPOInDeepPowerDownMode POWER_EnableLPOInDeepPowerDownMode
|
|
|
|
/*! @brief power down configurations mask */
|
|
typedef enum pd_bits
|
|
{
|
|
kPDRUNCFG_PD_FRO_OUT = SYSCON_PDRUNCFG_FROOUT_PD_MASK,
|
|
kPDRUNCFG_PD_FRO = SYSCON_PDRUNCFG_FRO_PD_MASK,
|
|
kPDRUNCFG_PD_FLASH = SYSCON_PDRUNCFG_FLASH_PD_MASK,
|
|
kPDRUNCFG_PD_BOD = SYSCON_PDRUNCFG_BOD_PD_MASK,
|
|
kPDRUNCFG_PD_ADC0 = SYSCON_PDRUNCFG_ADC_PD_MASK,
|
|
kPDRUNCFG_PD_SYSOSC = SYSCON_PDRUNCFG_SYSOSC_PD_MASK,
|
|
kPDRUNCFG_PD_WDT_OSC = SYSCON_PDRUNCFG_WDTOSC_PD_MASK,
|
|
kPDRUNCFG_PD_SYSPLL = SYSCON_PDRUNCFG_SYSPLL_PD_MASK,
|
|
kPDRUNCFG_PD_DAC0 = SYSCON_PDRUNCFG_DAC0_MASK,
|
|
kPDRUNCFG_PD_DAC1 = SYSCON_PDRUNCFG_DAC1_MASK,
|
|
kPDRUNCFG_PD_ACMP = SYSCON_PDRUNCFG_ACMP_MASK,
|
|
|
|
/*
|
|
This enum member has no practical meaning,it is used to avoid MISRA issue,
|
|
user should not trying to use it.
|
|
*/
|
|
kPDRUNCFG_ForceUnsigned = (int)0x80000000U,
|
|
} pd_bit_t;
|
|
|
|
/*! @brief Deep sleep and power down mode wake up configurations */
|
|
enum _power_wakeup
|
|
{
|
|
kPDAWAKECFG_Wakeup_FRO_OUT = SYSCON_PDAWAKECFG_FROOUT_PD_MASK,
|
|
kPDAWAKECFG_Wakeup_FRO = SYSCON_PDAWAKECFG_FRO_PD_MASK,
|
|
kPDAWAKECFG_Wakeup_FLASH = SYSCON_PDAWAKECFG_FLASH_PD_MASK,
|
|
kPDAWAKECFG_Wakeup_BOD = SYSCON_PDAWAKECFG_BOD_PD_MASK,
|
|
kPDAWAKECFG_Wakeup_ADC = SYSCON_PDAWAKECFG_ADC_PD_MASK,
|
|
kPDAWAKECFG_Wakeup_SYSOSC = SYSCON_PDAWAKECFG_SYSOSC_PD_MASK,
|
|
kPDAWAKECFG_Wakeup_WDT_OSC = SYSCON_PDAWAKECFG_WDTOSC_PD_MASK,
|
|
kPDAWAKECFG_Wakeup_SYSPLL = SYSCON_PDAWAKECFG_SYSPLL_PD_MASK,
|
|
kPDAWAKECFG_Wakeup_VREFF2 = SYSCON_PDAWAKECFG_VREF2_PD_MASK,
|
|
kPDAWAKECFG_Wakeup_DAC0 = SYSCON_PDAWAKECFG_DAC0_MASK,
|
|
kPDAWAKECFG_Wakeup_DAC1 = SYSCON_PDAWAKECFG_DAC1_MASK,
|
|
kPDAWAKECFG_Wakeup_ACMP = SYSCON_PDAWAKECFG_ACMP_MASK,
|
|
};
|
|
|
|
/*! @brief Deep sleep/power down mode active part */
|
|
enum _power_deep_sleep_active
|
|
{
|
|
kPDSLEEPCFG_DeepSleepBODActive = SYSCON_PDSLEEPCFG_BOD_PD_MASK,
|
|
kPDSLEEPCFG_DeepSleepWDTOscActive = SYSCON_PDSLEEPCFG_WDTOSC_PD_MASK,
|
|
};
|
|
|
|
/*! @brief pmu general purpose register index */
|
|
typedef enum _power_gen_reg
|
|
{
|
|
kPmu_GenReg0 = 0U, /*!< general purpose register0 */
|
|
kPmu_GenReg1 = 1U, /*!< general purpose register1 */
|
|
kPmu_GenReg2 = 2U, /*!< general purpose register2 */
|
|
kPmu_GenReg3 = 3U, /*!< general purpose register3 */
|
|
kPmu_GenReg4 = 4U, /*!< DPDCTRL bit 31-8 */
|
|
} power_gen_reg_t;
|
|
|
|
/* Power mode configuration API parameter */
|
|
typedef enum _power_mode_config
|
|
{
|
|
kPmu_Sleep = 0U,
|
|
kPmu_Deep_Sleep = 1U,
|
|
kPmu_PowerDown = 2U,
|
|
kPmu_Deep_PowerDown = 3U,
|
|
} power_mode_cfg_t;
|
|
|
|
/*!
|
|
* @brief BOD reset level, if VDD below reset level value, the reset will be
|
|
* asserted.
|
|
*/
|
|
typedef enum _power_bod_reset_level
|
|
{
|
|
kBod_ResetLevelReserved = 0U, /*!< BOD Reset Level reserved. */
|
|
kBod_ResetLevel1, /*!< BOD Reset Level1: 2.05V */
|
|
kBod_ResetLevel2, /*!< BOD Reset Level2: 2.35V */
|
|
kBod_ResetLevel3, /*!< BOD Reset Level3: 2.63V */
|
|
} power_bod_reset_level_t;
|
|
|
|
/*!
|
|
* @brief BOD interrupt level, if VDD below interrupt level value, the BOD interrupt
|
|
* will be asserted.
|
|
*/
|
|
typedef enum _power_bod_interrupt_level
|
|
{
|
|
kBod_InterruptLevelReserved = 0U, /*!< BOD interrupt level reserved. */
|
|
kBod_InterruptLevel1, /*!< BOD interrupt level1: 2.25V. */
|
|
kBod_InterruptLevel2, /*!< BOD interrupt level2: 2.55V. */
|
|
kBod_InterruptLevel3, /*!< BOD interrupt level3: 2.84V. */
|
|
} power_bod_interrupt_level_t;
|
|
|
|
/*******************************************************************************
|
|
* API
|
|
******************************************************************************/
|
|
|
|
#ifdef __cplusplus
|
|
extern "C" {
|
|
#endif
|
|
|
|
/*!
|
|
* @name SYSCON Power Configuration
|
|
* @{
|
|
*/
|
|
|
|
/*!
|
|
* @brief API to enable PDRUNCFG bit in the Syscon. Note that enabling the bit powers down the peripheral
|
|
*
|
|
* @param en peripheral for which to enable the PDRUNCFG bit
|
|
* @return none
|
|
*/
|
|
static inline void POWER_EnablePD(pd_bit_t en)
|
|
{
|
|
SYSCON->PDRUNCFG |= (uint32_t)en;
|
|
}
|
|
|
|
/*!
|
|
* @brief API to disable PDRUNCFG bit in the Syscon. Note that disabling the bit powers up the peripheral
|
|
*
|
|
* @param en peripheral for which to disable the PDRUNCFG bit
|
|
* @return none
|
|
*/
|
|
static inline void POWER_DisablePD(pd_bit_t en)
|
|
{
|
|
SYSCON->PDRUNCFG &= ~(uint32_t)en;
|
|
}
|
|
|
|
/*!
|
|
* @brief API to config wakeup configurations for deep sleep mode and power down mode.
|
|
*
|
|
* @param mask: wake up configurations for deep sleep mode and power down mode, reference _power_wakeup.
|
|
* @param powerDown: true is power down the mask part, false is powered part.
|
|
*/
|
|
static inline void POWER_WakeUpConfig(uint32_t mask, bool powerDown)
|
|
{
|
|
if (powerDown)
|
|
{
|
|
SYSCON->PDAWAKECFG |= mask;
|
|
}
|
|
else
|
|
{
|
|
SYSCON->PDAWAKECFG &= ~mask;
|
|
}
|
|
}
|
|
|
|
/*!
|
|
* @brief API to config active part for deep sleep mode and power down mode.
|
|
*
|
|
* @param mask: active part configurations for deep sleep mode and power down mode, reference _power_deep_sleep_active.
|
|
* @param powerDown: true is power down the mask part, false is powered part.
|
|
*/
|
|
static inline void POWER_DeepSleepConfig(uint32_t mask, bool powerDown)
|
|
{
|
|
if (powerDown)
|
|
{
|
|
SYSCON->PDSLEEPCFG |= mask;
|
|
}
|
|
else
|
|
{
|
|
SYSCON->PDSLEEPCFG &= ~mask;
|
|
}
|
|
}
|
|
|
|
/* @} */
|
|
|
|
/*!
|
|
* @name ARM core Power Configuration
|
|
* @{
|
|
*/
|
|
|
|
/*!
|
|
* @brief API to enable deep sleep bit in the ARM Core.
|
|
*
|
|
* @return none
|
|
*/
|
|
static inline void POWER_EnableDeepSleep(void)
|
|
{
|
|
SCB->SCR |= SCB_SCR_SLEEPDEEP_Msk;
|
|
}
|
|
|
|
/*!
|
|
* @brief API to disable deep sleep bit in the ARM Core.
|
|
*
|
|
* @return none
|
|
*/
|
|
static inline void POWER_DisableDeepSleep(void)
|
|
{
|
|
SCB->SCR &= ~SCB_SCR_SLEEPDEEP_Msk;
|
|
}
|
|
|
|
/* @} */
|
|
|
|
/*!
|
|
* @name PMU functionality
|
|
* @{
|
|
*/
|
|
|
|
/*!
|
|
* @brief API to enter sleep power mode.
|
|
*
|
|
* @return none
|
|
*/
|
|
void POWER_EnterSleep(void);
|
|
|
|
/*!
|
|
* @brief API to enter deep sleep power mode.
|
|
*
|
|
* @param activePart: should be a single or combine value of _power_deep_sleep_active .
|
|
* @return none
|
|
*/
|
|
void POWER_EnterDeepSleep(uint32_t activePart);
|
|
|
|
/*!
|
|
* @brief API to enter power down mode.
|
|
*
|
|
* @param activePart: should be a single or combine value of _power_deep_sleep_active .
|
|
* @return none
|
|
*/
|
|
void POWER_EnterPowerDown(uint32_t activePart);
|
|
|
|
/*!
|
|
* @brief API to enter deep power down mode.
|
|
*
|
|
* @return none
|
|
*/
|
|
void POWER_EnterDeepPowerDownMode(void);
|
|
|
|
/*!
|
|
* @brief API to get sleep mode flag.
|
|
*
|
|
* @return sleep mode flag: 0 is active mode, 1 is sleep mode entered.
|
|
*/
|
|
static inline uint32_t POWER_GetSleepModeFlag(void)
|
|
{
|
|
return (PMU->PCON & PMU_PCON_SLEEPFLAG_MASK) >> PMU_PCON_SLEEPFLAG_SHIFT;
|
|
}
|
|
|
|
/*!
|
|
* @brief API to clear sleep mode flag.
|
|
*
|
|
*/
|
|
static inline void POWER_ClrSleepModeFlag(void)
|
|
{
|
|
PMU->PCON |= PMU_PCON_SLEEPFLAG_MASK;
|
|
}
|
|
|
|
/*!
|
|
* @brief API to get deep power down mode flag.
|
|
*
|
|
* @return sleep mode flag: 0 not deep power down, 1 is deep power down mode entered.
|
|
*/
|
|
static inline uint32_t POWER_GetDeepPowerDownModeFlag(void)
|
|
{
|
|
return (PMU->PCON & PMU_PCON_DPDFLAG_MASK) >> PMU_PCON_DPDFLAG_SHIFT;
|
|
}
|
|
|
|
/*!
|
|
* @brief API to clear deep power down mode flag.
|
|
*
|
|
*/
|
|
static inline void POWER_ClrDeepPowerDownModeFlag(void)
|
|
{
|
|
PMU->PCON |= PMU_PCON_DPDFLAG_MASK;
|
|
}
|
|
|
|
/*!
|
|
* @brief API to enable non deep power down mode.
|
|
*
|
|
* @param enable: true is enable non deep power down, otherwise disable.
|
|
*/
|
|
static inline void POWER_EnableNonDpd(bool enable)
|
|
{
|
|
if (enable)
|
|
{
|
|
PMU->PCON |= PMU_PCON_NODPD_MASK;
|
|
}
|
|
else
|
|
{
|
|
PMU->PCON &= ~PMU_PCON_NODPD_MASK;
|
|
}
|
|
}
|
|
|
|
/*!
|
|
* @brief API to enable LPO.
|
|
*
|
|
* @param enable: true to enable LPO, false to disable LPO.
|
|
*/
|
|
static inline void POWER_EnableLPO(bool enable)
|
|
{
|
|
if (enable)
|
|
{
|
|
PMU->DPDCTRL |= PMU_DPDCTRL_LPOSCEN_MASK;
|
|
}
|
|
else
|
|
{
|
|
PMU->DPDCTRL &= ~PMU_DPDCTRL_LPOSCEN_MASK;
|
|
}
|
|
}
|
|
|
|
/*!
|
|
* @brief API to enable LPO in deep power down mode.
|
|
*
|
|
* @param enable: true to enable LPO, false to disable LPO.
|
|
*/
|
|
static inline void POWER_EnableLPOInDeepPowerDownMode(bool enable)
|
|
{
|
|
if (enable)
|
|
{
|
|
PMU->DPDCTRL |= PMU_DPDCTRL_LPOSCDPDEN_MASK;
|
|
}
|
|
else
|
|
{
|
|
PMU->DPDCTRL &= ~PMU_DPDCTRL_LPOSCDPDEN_MASK;
|
|
}
|
|
}
|
|
|
|
/*!
|
|
* @brief API to retore data to general purpose register which can be retain during deep power down mode.
|
|
* Note the kPMU_GenReg4 can retore 3 byte data only, so the general purpose register can store 19bytes data.
|
|
* @param index: general purpose data register index.
|
|
* @param data: data to restore.
|
|
*/
|
|
static inline void POWER_SetRetainData(power_gen_reg_t index, uint32_t data)
|
|
{
|
|
if (index <= kPmu_GenReg3)
|
|
{
|
|
PMU->GPREG[index] = data;
|
|
}
|
|
else
|
|
{
|
|
/* only three byte can store in GPDATA field */
|
|
PMU->DPDCTRL = (PMU->DPDCTRL & (~PMU_DPDCTRL_GPDATA_MASK)) | PMU_DPDCTRL_GPDATA(data);
|
|
}
|
|
}
|
|
|
|
/*!
|
|
* @brief API to get data from general purpose register which retain during deep power down mode.
|
|
* Note the kPMU_GenReg4 can retore 3 byte data only, so the general purpose register can store 19bytes data.
|
|
* @param index: general purpose data register index.
|
|
* @return data stored in the general purpose register.
|
|
*/
|
|
static inline uint32_t POWER_GetRetainData(power_gen_reg_t index)
|
|
{
|
|
if (index == kPmu_GenReg4)
|
|
{
|
|
return (PMU->DPDCTRL & PMU_DPDCTRL_GPDATA_MASK) >> PMU_DPDCTRL_GPDATA_SHIFT;
|
|
}
|
|
|
|
return PMU->GPREG[index];
|
|
}
|
|
|
|
/*!
|
|
* @brief API to enable external clock input for self wake up timer.
|
|
*
|
|
* @param enable: true is enable external clock input for self-wake-up timer, otherwise disable.
|
|
* @param enHysteresis: true is enable Hysteresis for the pin, otherwise disable.
|
|
*/
|
|
static inline void POWER_EnableWktClkIn(bool enable, bool enHysteresis)
|
|
{
|
|
PMU->DPDCTRL = (PMU->DPDCTRL & (~(PMU_DPDCTRL_WAKEUPCLKHYS_MASK | PMU_DPDCTRL_WAKECLKPAD_DISABLE_MASK))) |
|
|
PMU_DPDCTRL_WAKECLKPAD_DISABLE(enable) | PMU_DPDCTRL_WAKEUPCLKHYS(enHysteresis);
|
|
}
|
|
|
|
/*!
|
|
* @brief API to enable wake up pin for deep power down mode.
|
|
*
|
|
* @param enable: true is enable, otherwise disable.
|
|
* @param enHysteresis: true is enable Hysteresis for the pin, otherwise disable.
|
|
*/
|
|
static inline void POWER_EnableWakeupPinForDeepPowerDown(bool enable, bool enHysteresis)
|
|
{
|
|
PMU->DPDCTRL = (PMU->DPDCTRL & (~(PMU_DPDCTRL_WAKEUPHYS_MASK | PMU_DPDCTRL_WAKEPAD_DISABLE_MASK))) |
|
|
PMU_DPDCTRL_WAKEPAD_DISABLE(!enable) | PMU_DPDCTRL_WAKEUPHYS(enHysteresis);
|
|
}
|
|
|
|
/*!
|
|
* @brief API to enable external clock input for self wake up timer.
|
|
*
|
|
* @param enable: true is enable , otherwise disable.
|
|
* @param enHysteresis: true is enable Hysteresis for the pin, otherwise disable.
|
|
*/
|
|
static inline void POWER_EnableResetPinForDeepPowerDown(bool enable, bool enHysteresis)
|
|
{
|
|
PMU->DPDCTRL = (PMU->DPDCTRL & (~(PMU_DPDCTRL_RESETHYS_MASK | PMU_DPDCTRL_RESET_DISABLE_MASK))) |
|
|
PMU_DPDCTRL_RESET_DISABLE(!enable) | PMU_DPDCTRL_RESETHYS(enHysteresis);
|
|
}
|
|
|
|
/*!
|
|
* @brief Set Bod interrupt level and reset level.
|
|
*
|
|
* @param resetLevel BOD reset threshold level, please refer to @ref power_bod_reset_level_t.
|
|
* @param interruptLevel BOD interrupt threshold level, please refer to @ref power_bod_interrupt_level_t.
|
|
* @param enable Used to enable/disable the BOD interrupt and BOD reset.
|
|
*/
|
|
static inline void POWER_SetBodLevel(power_bod_reset_level_t resetLevel,
|
|
power_bod_interrupt_level_t interruptLevel,
|
|
bool enable)
|
|
{
|
|
SYSCON->BODCTRL = SYSCON_BODCTRL_BODRSTLEV(resetLevel) | SYSCON_BODCTRL_BODINTVAL(interruptLevel) |
|
|
SYSCON_BODCTRL_BODRSTENA(enable);
|
|
}
|
|
/* @} */
|
|
|
|
#ifdef __cplusplus
|
|
}
|
|
#endif
|
|
|
|
/*!
|
|
* @}
|
|
*/
|
|
|
|
#endif /* _FSL_POWER_H_ */
|