summaryrefslogtreecommitdiff
path: root/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers
diff options
context:
space:
mode:
Diffstat (limited to 'FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers')
-rw-r--r--FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_clock.c33
-rw-r--r--FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_clock.h5
-rw-r--r--FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common.c12
-rw-r--r--FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common.h306
-rw-r--r--FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common_arm.c32
-rw-r--r--FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common_arm.h357
-rw-r--r--FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_power.c1816
-rw-r--r--FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_power.h15
-rw-r--r--FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_reset.h20
-rw-r--r--FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_usart.c156
-rw-r--r--FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_usart.h143
11 files changed, 2589 insertions, 306 deletions
diff --git a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_clock.c b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_clock.c
index 117d27eda..730943b9d 100644
--- a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_clock.c
+++ b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_clock.c
@@ -1,5 +1,5 @@
/*
- * Copyright 2017 - 2020 , NXP
+ * Copyright 2017 - 2021 , NXP
* All rights reserved.
*
* SPDX-License-Identifier: BSD-3-Clause
@@ -127,7 +127,7 @@ void CLOCK_AttachClk(clock_attach_id_t connection)
sel = GET_ID_ITEM_SEL(item);
if (mux == CM_RTCOSC32KCLKSEL)
{
- PMC->RTCOSC32K |= sel;
+ PMC->RTCOSC32K = (PMC->RTCOSC32K & ~PMC_RTCOSC32K_SEL_MASK) | PMC_RTCOSC32K_SEL(sel);
}
else
{
@@ -388,7 +388,7 @@ void CLOCK_SetFLASHAccessCyclesForFreq(uint32_t iFreq)
/* Set EXT OSC Clk */
/**
* brief Initialize the external osc clock to given frequency.
- * Crystal oscillator with an operating frequency of 12 MHz to 32 MHz.
+ * Crystal oscillator with an operating frequency of 12 MHz to 32 MHz.
* Option for external clock input (bypass mode) for clock frequencies of up to 25 MHz.
* param iFreq : Desired frequency (must be equal to exact rate in Hz)
* return returns success or fail status.
@@ -848,12 +848,14 @@ uint32_t CLOCK_GetFlexCommInputClock(uint32_t id)
/* Get FLEXCOMM Clk */
uint32_t CLOCK_GetFlexCommClkFreq(uint32_t id)
{
- uint32_t freq = 0U;
- uint32_t temp;
-
- freq = CLOCK_GetFlexCommInputClock(id);
- temp = SYSCON->FLEXFRGXCTRL[id] & SYSCON_FLEXFRG0CTRL_MULT_MASK;
- return freq / (1U + (temp) / ((SYSCON->FLEXFRGXCTRL[id] & SYSCON_FLEXFRG0CTRL_DIV_MASK) + 1U));
+ uint32_t freq = 0U;
+ uint32_t frgMul = 0U;
+ uint32_t frgDiv = 0U;
+
+ freq = CLOCK_GetFlexCommInputClock(id);
+ frgMul = (SYSCON->FLEXFRGXCTRL[id] & SYSCON_FLEXFRG0CTRL_MULT_MASK) >> 8U;
+ frgDiv = SYSCON->FLEXFRGXCTRL[id] & SYSCON_FLEXFRG0CTRL_DIV_MASK;
+ return (uint32_t)(((uint64_t)freq * ((uint64_t)frgDiv + 1ULL)) / (frgMul + frgDiv + 1UL));
}
/* Get HS_LPSI Clk */
@@ -1159,7 +1161,7 @@ static float findPll0MMult(void)
(float)(uint32_t)(1UL << PLL0_SSCG_MD_INT_P));
mMult = (float)mMult_int + mMult_fract;
}
- if (mMult == 0.0F)
+ if (0ULL == ((uint64_t)mMult))
{
mMult = 1.0F;
}
@@ -1882,7 +1884,8 @@ bool CLOCK_EnableUsbfs0DeviceClock(clock_usbfs_src_t src, uint32_t freq)
/* Turn ON FRO HF */
POWER_DisablePD(kPDRUNCFG_PD_FRO192M);
/* Enable FRO 96MHz output */
- ANACTRL->FRO192M_CTRL = ANACTRL->FRO192M_CTRL | ANACTRL_FRO192M_CTRL_ENA_96MHZCLK_MASK | ANACTRL_FRO192M_CTRL_USBCLKADJ_MASK;
+ ANACTRL->FRO192M_CTRL =
+ ANACTRL->FRO192M_CTRL | ANACTRL_FRO192M_CTRL_ENA_96MHZCLK_MASK | ANACTRL_FRO192M_CTRL_USBCLKADJ_MASK;
/* Select FRO 96 or 48 MHz */
CLOCK_AttachClk(kFRO_HF_to_USB0_CLK);
}
@@ -2093,3 +2096,11 @@ bool CLOCK_EnableUsbhs0HostClock(clock_usbhs_src_t src, uint32_t freq)
return true;
}
+
+/*! @brief Enable the OSTIMER 32k clock.
+ * @return Nothing
+ */
+void CLOCK_EnableOstimer32kClock(void)
+{
+ PMC->OSTIMERr |= PMC_OSTIMER_CLOCKENABLE_MASK;
+}
diff --git a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_clock.h b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_clock.h
index f70c55990..be1a8fc38 100644
--- a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_clock.h
+++ b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_clock.h
@@ -1492,6 +1492,11 @@ bool CLOCK_EnableUsbhs0DeviceClock(clock_usbhs_src_t src, uint32_t freq);
*/
bool CLOCK_EnableUsbhs0HostClock(clock_usbhs_src_t src, uint32_t freq);
+/*! @brief Enable the OSTIMER 32k clock.
+ * @return Nothing
+ */
+void CLOCK_EnableOstimer32kClock(void);
+
#if defined(__cplusplus)
}
#endif /* __cplusplus */
diff --git a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common.c b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common.c
index aa1394d05..f7483b9f1 100644
--- a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common.c
+++ b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common.c
@@ -21,13 +21,14 @@ typedef struct _mem_align_control_block
#define FSL_COMPONENT_ID "platform.drivers.common"
#endif
+#if !((defined(__DSC__) && defined(__CW__)))
void *SDK_Malloc(size_t size, size_t alignbytes)
{
mem_align_cb_t *p_cb = NULL;
uint32_t alignedsize;
/* Check overflow. */
- alignedsize = SDK_SIZEALIGN(size, alignbytes);
+ alignedsize = (uint32_t)(unsigned int)SDK_SIZEALIGN(size, alignbytes);
if (alignedsize < size)
{
return NULL;
@@ -38,15 +39,15 @@ void *SDK_Malloc(size_t size, size_t alignbytes)
return NULL;
}
- alignedsize += alignbytes + sizeof(mem_align_cb_t);
+ alignedsize += alignbytes + (uint32_t)sizeof(mem_align_cb_t);
union
{
void *pointer_value;
- uint32_t unsigned_value;
+ uintptr_t unsigned_value;
} p_align_addr, p_addr;
- p_addr.pointer_value = malloc(alignedsize);
+ p_addr.pointer_value = malloc((size_t)alignedsize);
if (p_addr.pointer_value == NULL)
{
@@ -67,7 +68,7 @@ void SDK_Free(void *ptr)
union
{
void *pointer_value;
- uint32_t unsigned_value;
+ uintptr_t unsigned_value;
} p_free;
p_free.pointer_value = ptr;
mem_align_cb_t *p_cb = (mem_align_cb_t *)(p_free.unsigned_value - 4U);
@@ -81,3 +82,4 @@ void SDK_Free(void *ptr)
free(p_free.pointer_value);
}
+#endif
diff --git a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common.h b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common.h
index 09a668e05..7662c0cc9 100644
--- a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common.h
+++ b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common.h
@@ -1,6 +1,6 @@
/*
* Copyright (c) 2015-2016, Freescale Semiconductor, Inc.
- * Copyright 2016-2021 NXP
+ * Copyright 2016-2022 NXP
* All rights reserved.
*
* SPDX-License-Identifier: BSD-3-Clause
@@ -40,142 +40,163 @@
******************************************************************************/
/*! @brief Construct a status code value from a group and code number. */
-#define MAKE_STATUS(group, code) ((((group)*100) + (code)))
+#define MAKE_STATUS(group, code) ((((group)*100L) + (code)))
-/*! @brief Construct the version number for drivers. */
-#define MAKE_VERSION(major, minor, bugfix) (((major) << 16) | ((minor) << 8) | (bugfix))
+/*! @brief Construct the version number for drivers.
+ *
+ * The driver version is a 32-bit number, for both 32-bit platforms(such as Cortex M)
+ * and 16-bit platforms(such as DSC).
+ *
+ * @verbatim
+
+ | Unused || Major Version || Minor Version || Bug Fix |
+ 31 25 24 17 16 9 8 0
+
+ @endverbatim
+ */
+#define MAKE_VERSION(major, minor, bugfix) (((major)*65536L) + ((minor)*256L) + (bugfix))
/*! @name Driver version */
/*@{*/
/*! @brief common driver version. */
-#define FSL_COMMON_DRIVER_VERSION (MAKE_VERSION(2, 3, 0))
+#define FSL_COMMON_DRIVER_VERSION (MAKE_VERSION(2, 4, 0))
/*@}*/
/* Debug console type definition. */
-#define DEBUG_CONSOLE_DEVICE_TYPE_NONE 0U /*!< No debug console. */
-#define DEBUG_CONSOLE_DEVICE_TYPE_UART 1U /*!< Debug console based on UART. */
-#define DEBUG_CONSOLE_DEVICE_TYPE_LPUART 2U /*!< Debug console based on LPUART. */
-#define DEBUG_CONSOLE_DEVICE_TYPE_LPSCI 3U /*!< Debug console based on LPSCI. */
-#define DEBUG_CONSOLE_DEVICE_TYPE_USBCDC 4U /*!< Debug console based on USBCDC. */
-#define DEBUG_CONSOLE_DEVICE_TYPE_FLEXCOMM 5U /*!< Debug console based on FLEXCOMM. */
-#define DEBUG_CONSOLE_DEVICE_TYPE_IUART 6U /*!< Debug console based on i.MX UART. */
-#define DEBUG_CONSOLE_DEVICE_TYPE_VUSART 7U /*!< Debug console based on LPC_VUSART. */
-#define DEBUG_CONSOLE_DEVICE_TYPE_MINI_USART 8U /*!< Debug console based on LPC_USART. */
-#define DEBUG_CONSOLE_DEVICE_TYPE_SWO 9U /*!< Debug console based on SWO. */
-#define DEBUG_CONSOLE_DEVICE_TYPE_QSCI 10U /*!< Debug console based on QSCI. */
+#define DEBUG_CONSOLE_DEVICE_TYPE_NONE 0U /*!< No debug console. */
+#define DEBUG_CONSOLE_DEVICE_TYPE_UART 1U /*!< Debug console based on UART. */
+#define DEBUG_CONSOLE_DEVICE_TYPE_LPUART 2U /*!< Debug console based on LPUART. */
+#define DEBUG_CONSOLE_DEVICE_TYPE_LPSCI 3U /*!< Debug console based on LPSCI. */
+#define DEBUG_CONSOLE_DEVICE_TYPE_USBCDC 4U /*!< Debug console based on USBCDC. */
+#define DEBUG_CONSOLE_DEVICE_TYPE_FLEXCOMM 5U /*!< Debug console based on FLEXCOMM. */
+#define DEBUG_CONSOLE_DEVICE_TYPE_IUART 6U /*!< Debug console based on i.MX UART. */
+#define DEBUG_CONSOLE_DEVICE_TYPE_VUSART 7U /*!< Debug console based on LPC_VUSART. */
+#define DEBUG_CONSOLE_DEVICE_TYPE_MINI_USART 8U /*!< Debug console based on LPC_USART. */
+#define DEBUG_CONSOLE_DEVICE_TYPE_SWO 9U /*!< Debug console based on SWO. */
+#define DEBUG_CONSOLE_DEVICE_TYPE_QSCI 10U /*!< Debug console based on QSCI. */
/*! @brief Status group numbers. */
enum _status_groups
{
- kStatusGroup_Generic = 0, /*!< Group number for generic status codes. */
- kStatusGroup_FLASH = 1, /*!< Group number for FLASH status codes. */
- kStatusGroup_LPSPI = 4, /*!< Group number for LPSPI status codes. */
- kStatusGroup_FLEXIO_SPI = 5, /*!< Group number for FLEXIO SPI status codes. */
- kStatusGroup_DSPI = 6, /*!< Group number for DSPI status codes. */
- kStatusGroup_FLEXIO_UART = 7, /*!< Group number for FLEXIO UART status codes. */
- kStatusGroup_FLEXIO_I2C = 8, /*!< Group number for FLEXIO I2C status codes. */
- kStatusGroup_LPI2C = 9, /*!< Group number for LPI2C status codes. */
- kStatusGroup_UART = 10, /*!< Group number for UART status codes. */
- kStatusGroup_I2C = 11, /*!< Group number for UART status codes. */
- kStatusGroup_LPSCI = 12, /*!< Group number for LPSCI status codes. */
- kStatusGroup_LPUART = 13, /*!< Group number for LPUART status codes. */
- kStatusGroup_SPI = 14, /*!< Group number for SPI status code.*/
- kStatusGroup_XRDC = 15, /*!< Group number for XRDC status code.*/
- kStatusGroup_SEMA42 = 16, /*!< Group number for SEMA42 status code.*/
- kStatusGroup_SDHC = 17, /*!< Group number for SDHC status code */
- kStatusGroup_SDMMC = 18, /*!< Group number for SDMMC status code */
- kStatusGroup_SAI = 19, /*!< Group number for SAI status code */
- kStatusGroup_MCG = 20, /*!< Group number for MCG status codes. */
- kStatusGroup_SCG = 21, /*!< Group number for SCG status codes. */
- kStatusGroup_SDSPI = 22, /*!< Group number for SDSPI status codes. */
- kStatusGroup_FLEXIO_I2S = 23, /*!< Group number for FLEXIO I2S status codes */
- kStatusGroup_FLEXIO_MCULCD = 24, /*!< Group number for FLEXIO LCD status codes */
- kStatusGroup_FLASHIAP = 25, /*!< Group number for FLASHIAP status codes */
- kStatusGroup_FLEXCOMM_I2C = 26, /*!< Group number for FLEXCOMM I2C status codes */
- kStatusGroup_I2S = 27, /*!< Group number for I2S status codes */
- kStatusGroup_IUART = 28, /*!< Group number for IUART status codes */
- kStatusGroup_CSI = 29, /*!< Group number for CSI status codes */
- kStatusGroup_MIPI_DSI = 30, /*!< Group number for MIPI DSI status codes */
- kStatusGroup_SDRAMC = 35, /*!< Group number for SDRAMC status codes. */
- kStatusGroup_POWER = 39, /*!< Group number for POWER status codes. */
- kStatusGroup_ENET = 40, /*!< Group number for ENET status codes. */
- kStatusGroup_PHY = 41, /*!< Group number for PHY status codes. */
- kStatusGroup_TRGMUX = 42, /*!< Group number for TRGMUX status codes. */
- kStatusGroup_SMARTCARD = 43, /*!< Group number for SMARTCARD status codes. */
- kStatusGroup_LMEM = 44, /*!< Group number for LMEM status codes. */
- kStatusGroup_QSPI = 45, /*!< Group number for QSPI status codes. */
- kStatusGroup_DMA = 50, /*!< Group number for DMA status codes. */
- kStatusGroup_EDMA = 51, /*!< Group number for EDMA status codes. */
- kStatusGroup_DMAMGR = 52, /*!< Group number for DMAMGR status codes. */
- kStatusGroup_FLEXCAN = 53, /*!< Group number for FlexCAN status codes. */
- kStatusGroup_LTC = 54, /*!< Group number for LTC status codes. */
- kStatusGroup_FLEXIO_CAMERA = 55, /*!< Group number for FLEXIO CAMERA status codes. */
- kStatusGroup_LPC_SPI = 56, /*!< Group number for LPC_SPI status codes. */
- kStatusGroup_LPC_USART = 57, /*!< Group number for LPC_USART status codes. */
- kStatusGroup_DMIC = 58, /*!< Group number for DMIC status codes. */
- kStatusGroup_SDIF = 59, /*!< Group number for SDIF status codes.*/
- kStatusGroup_SPIFI = 60, /*!< Group number for SPIFI status codes. */
- kStatusGroup_OTP = 61, /*!< Group number for OTP status codes. */
- kStatusGroup_MCAN = 62, /*!< Group number for MCAN status codes. */
- kStatusGroup_CAAM = 63, /*!< Group number for CAAM status codes. */
- kStatusGroup_ECSPI = 64, /*!< Group number for ECSPI status codes. */
- kStatusGroup_USDHC = 65, /*!< Group number for USDHC status codes.*/
- kStatusGroup_LPC_I2C = 66, /*!< Group number for LPC_I2C status codes.*/
- kStatusGroup_DCP = 67, /*!< Group number for DCP status codes.*/
- kStatusGroup_MSCAN = 68, /*!< Group number for MSCAN status codes.*/
- kStatusGroup_ESAI = 69, /*!< Group number for ESAI status codes. */
- kStatusGroup_FLEXSPI = 70, /*!< Group number for FLEXSPI status codes. */
- kStatusGroup_MMDC = 71, /*!< Group number for MMDC status codes. */
- kStatusGroup_PDM = 72, /*!< Group number for MIC status codes. */
- kStatusGroup_SDMA = 73, /*!< Group number for SDMA status codes. */
- kStatusGroup_ICS = 74, /*!< Group number for ICS status codes. */
- kStatusGroup_SPDIF = 75, /*!< Group number for SPDIF status codes. */
- kStatusGroup_LPC_MINISPI = 76, /*!< Group number for LPC_MINISPI status codes. */
- kStatusGroup_HASHCRYPT = 77, /*!< Group number for Hashcrypt status codes */
- kStatusGroup_LPC_SPI_SSP = 78, /*!< Group number for LPC_SPI_SSP status codes. */
- kStatusGroup_I3C = 79, /*!< Group number for I3C status codes */
- kStatusGroup_LPC_I2C_1 = 97, /*!< Group number for LPC_I2C_1 status codes. */
- kStatusGroup_NOTIFIER = 98, /*!< Group number for NOTIFIER status codes. */
- kStatusGroup_DebugConsole = 99, /*!< Group number for debug console status codes. */
- kStatusGroup_SEMC = 100, /*!< Group number for SEMC status codes. */
+ kStatusGroup_Generic = 0, /*!< Group number for generic status codes. */
+ kStatusGroup_FLASH = 1, /*!< Group number for FLASH status codes. */
+ kStatusGroup_LPSPI = 4, /*!< Group number for LPSPI status codes. */
+ kStatusGroup_FLEXIO_SPI = 5, /*!< Group number for FLEXIO SPI status codes. */
+ kStatusGroup_DSPI = 6, /*!< Group number for DSPI status codes. */
+ kStatusGroup_FLEXIO_UART = 7, /*!< Group number for FLEXIO UART status codes. */
+ kStatusGroup_FLEXIO_I2C = 8, /*!< Group number for FLEXIO I2C status codes. */
+ kStatusGroup_LPI2C = 9, /*!< Group number for LPI2C status codes. */
+ kStatusGroup_UART = 10, /*!< Group number for UART status codes. */
+ kStatusGroup_I2C = 11, /*!< Group number for UART status codes. */
+ kStatusGroup_LPSCI = 12, /*!< Group number for LPSCI status codes. */
+ kStatusGroup_LPUART = 13, /*!< Group number for LPUART status codes. */
+ kStatusGroup_SPI = 14, /*!< Group number for SPI status code.*/
+ kStatusGroup_XRDC = 15, /*!< Group number for XRDC status code.*/
+ kStatusGroup_SEMA42 = 16, /*!< Group number for SEMA42 status code.*/
+ kStatusGroup_SDHC = 17, /*!< Group number for SDHC status code */
+ kStatusGroup_SDMMC = 18, /*!< Group number for SDMMC status code */
+ kStatusGroup_SAI = 19, /*!< Group number for SAI status code */
+ kStatusGroup_MCG = 20, /*!< Group number for MCG status codes. */
+ kStatusGroup_SCG = 21, /*!< Group number for SCG status codes. */
+ kStatusGroup_SDSPI = 22, /*!< Group number for SDSPI status codes. */
+ kStatusGroup_FLEXIO_I2S = 23, /*!< Group number for FLEXIO I2S status codes */
+ kStatusGroup_FLEXIO_MCULCD = 24, /*!< Group number for FLEXIO LCD status codes */
+ kStatusGroup_FLASHIAP = 25, /*!< Group number for FLASHIAP status codes */
+ kStatusGroup_FLEXCOMM_I2C = 26, /*!< Group number for FLEXCOMM I2C status codes */
+ kStatusGroup_I2S = 27, /*!< Group number for I2S status codes */
+ kStatusGroup_IUART = 28, /*!< Group number for IUART status codes */
+ kStatusGroup_CSI = 29, /*!< Group number for CSI status codes */
+ kStatusGroup_MIPI_DSI = 30, /*!< Group number for MIPI DSI status codes */
+ kStatusGroup_SDRAMC = 35, /*!< Group number for SDRAMC status codes. */
+ kStatusGroup_POWER = 39, /*!< Group number for POWER status codes. */
+ kStatusGroup_ENET = 40, /*!< Group number for ENET status codes. */
+ kStatusGroup_PHY = 41, /*!< Group number for PHY status codes. */
+ kStatusGroup_TRGMUX = 42, /*!< Group number for TRGMUX status codes. */
+ kStatusGroup_SMARTCARD = 43, /*!< Group number for SMARTCARD status codes. */
+ kStatusGroup_LMEM = 44, /*!< Group number for LMEM status codes. */
+ kStatusGroup_QSPI = 45, /*!< Group number for QSPI status codes. */
+ kStatusGroup_DMA = 50, /*!< Group number for DMA status codes. */
+ kStatusGroup_EDMA = 51, /*!< Group number for EDMA status codes. */
+ kStatusGroup_DMAMGR = 52, /*!< Group number for DMAMGR status codes. */
+ kStatusGroup_FLEXCAN = 53, /*!< Group number for FlexCAN status codes. */
+ kStatusGroup_LTC = 54, /*!< Group number for LTC status codes. */
+ kStatusGroup_FLEXIO_CAMERA = 55, /*!< Group number for FLEXIO CAMERA status codes. */
+ kStatusGroup_LPC_SPI = 56, /*!< Group number for LPC_SPI status codes. */
+ kStatusGroup_LPC_USART = 57, /*!< Group number for LPC_USART status codes. */
+ kStatusGroup_DMIC = 58, /*!< Group number for DMIC status codes. */
+ kStatusGroup_SDIF = 59, /*!< Group number for SDIF status codes.*/
+ kStatusGroup_SPIFI = 60, /*!< Group number for SPIFI status codes. */
+ kStatusGroup_OTP = 61, /*!< Group number for OTP status codes. */
+ kStatusGroup_MCAN = 62, /*!< Group number for MCAN status codes. */
+ kStatusGroup_CAAM = 63, /*!< Group number for CAAM status codes. */
+ kStatusGroup_ECSPI = 64, /*!< Group number for ECSPI status codes. */
+ kStatusGroup_USDHC = 65, /*!< Group number for USDHC status codes.*/
+ kStatusGroup_LPC_I2C = 66, /*!< Group number for LPC_I2C status codes.*/
+ kStatusGroup_DCP = 67, /*!< Group number for DCP status codes.*/
+ kStatusGroup_MSCAN = 68, /*!< Group number for MSCAN status codes.*/
+ kStatusGroup_ESAI = 69, /*!< Group number for ESAI status codes. */
+ kStatusGroup_FLEXSPI = 70, /*!< Group number for FLEXSPI status codes. */
+ kStatusGroup_MMDC = 71, /*!< Group number for MMDC status codes. */
+ kStatusGroup_PDM = 72, /*!< Group number for MIC status codes. */
+ kStatusGroup_SDMA = 73, /*!< Group number for SDMA status codes. */
+ kStatusGroup_ICS = 74, /*!< Group number for ICS status codes. */
+ kStatusGroup_SPDIF = 75, /*!< Group number for SPDIF status codes. */
+ kStatusGroup_LPC_MINISPI = 76, /*!< Group number for LPC_MINISPI status codes. */
+ kStatusGroup_HASHCRYPT = 77, /*!< Group number for Hashcrypt status codes */
+ kStatusGroup_LPC_SPI_SSP = 78, /*!< Group number for LPC_SPI_SSP status codes. */
+ kStatusGroup_I3C = 79, /*!< Group number for I3C status codes */
+ kStatusGroup_LPC_I2C_1 = 97, /*!< Group number for LPC_I2C_1 status codes. */
+ kStatusGroup_NOTIFIER = 98, /*!< Group number for NOTIFIER status codes. */
+ kStatusGroup_DebugConsole = 99, /*!< Group number for debug console status codes. */
+ kStatusGroup_SEMC = 100, /*!< Group number for SEMC status codes. */
kStatusGroup_ApplicationRangeStart = 101, /*!< Starting number for application groups. */
- kStatusGroup_IAP = 102, /*!< Group number for IAP status codes */
- kStatusGroup_SFA = 103, /*!< Group number for SFA status codes*/
- kStatusGroup_SPC = 104, /*!< Group number for SPC status codes. */
- kStatusGroup_PUF = 105, /*!< Group number for PUF status codes. */
- kStatusGroup_TOUCH_PANEL = 106, /*!< Group number for touch panel status codes */
-
- kStatusGroup_HAL_GPIO = 121, /*!< Group number for HAL GPIO status codes. */
- kStatusGroup_HAL_UART = 122, /*!< Group number for HAL UART status codes. */
- kStatusGroup_HAL_TIMER = 123, /*!< Group number for HAL TIMER status codes. */
- kStatusGroup_HAL_SPI = 124, /*!< Group number for HAL SPI status codes. */
- kStatusGroup_HAL_I2C = 125, /*!< Group number for HAL I2C status codes. */
- kStatusGroup_HAL_FLASH = 126, /*!< Group number for HAL FLASH status codes. */
- kStatusGroup_HAL_PWM = 127, /*!< Group number for HAL PWM status codes. */
- kStatusGroup_HAL_RNG = 128, /*!< Group number for HAL RNG status codes. */
- kStatusGroup_TIMERMANAGER = 135, /*!< Group number for TiMER MANAGER status codes. */
- kStatusGroup_SERIALMANAGER = 136, /*!< Group number for SERIAL MANAGER status codes. */
- kStatusGroup_LED = 137, /*!< Group number for LED status codes. */
- kStatusGroup_BUTTON = 138, /*!< Group number for BUTTON status codes. */
- kStatusGroup_EXTERN_EEPROM = 139, /*!< Group number for EXTERN EEPROM status codes. */
- kStatusGroup_SHELL = 140, /*!< Group number for SHELL status codes. */
- kStatusGroup_MEM_MANAGER = 141, /*!< Group number for MEM MANAGER status codes. */
- kStatusGroup_LIST = 142, /*!< Group number for List status codes. */
- kStatusGroup_OSA = 143, /*!< Group number for OSA status codes. */
- kStatusGroup_COMMON_TASK = 144, /*!< Group number for Common task status codes. */
- kStatusGroup_MSG = 145, /*!< Group number for messaging status codes. */
- kStatusGroup_SDK_OCOTP = 146, /*!< Group number for OCOTP status codes. */
- kStatusGroup_SDK_FLEXSPINOR = 147, /*!< Group number for FLEXSPINOR status codes.*/
- kStatusGroup_CODEC = 148, /*!< Group number for codec status codes. */
- kStatusGroup_ASRC = 149, /*!< Group number for codec status ASRC. */
- kStatusGroup_OTFAD = 150, /*!< Group number for codec status codes. */
- kStatusGroup_SDIOSLV = 151, /*!< Group number for SDIOSLV status codes. */
- kStatusGroup_MECC = 152, /*!< Group number for MECC status codes. */
- kStatusGroup_ENET_QOS = 153, /*!< Group number for ENET_QOS status codes. */
- kStatusGroup_LOG = 154, /*!< Group number for LOG status codes. */
- kStatusGroup_I3CBUS = 155, /*!< Group number for I3CBUS status codes. */
- kStatusGroup_QSCI = 156, /*!< Group number for QSCI status codes. */
- kStatusGroup_SNT = 157, /*!< Group number for SNT status codes. */
+ kStatusGroup_IAP = 102, /*!< Group number for IAP status codes */
+ kStatusGroup_SFA = 103, /*!< Group number for SFA status codes*/
+ kStatusGroup_SPC = 104, /*!< Group number for SPC status codes. */
+ kStatusGroup_PUF = 105, /*!< Group number for PUF status codes. */
+ kStatusGroup_TOUCH_PANEL = 106, /*!< Group number for touch panel status codes */
+ kStatusGroup_VBAT = 107, /*!< Group number for VBAT status codes */
+
+ kStatusGroup_HAL_GPIO = 121, /*!< Group number for HAL GPIO status codes. */
+ kStatusGroup_HAL_UART = 122, /*!< Group number for HAL UART status codes. */
+ kStatusGroup_HAL_TIMER = 123, /*!< Group number for HAL TIMER status codes. */
+ kStatusGroup_HAL_SPI = 124, /*!< Group number for HAL SPI status codes. */
+ kStatusGroup_HAL_I2C = 125, /*!< Group number for HAL I2C status codes. */
+ kStatusGroup_HAL_FLASH = 126, /*!< Group number for HAL FLASH status codes. */
+ kStatusGroup_HAL_PWM = 127, /*!< Group number for HAL PWM status codes. */
+ kStatusGroup_HAL_RNG = 128, /*!< Group number for HAL RNG status codes. */
+ kStatusGroup_HAL_I2S = 129, /*!< Group number for HAL I2S status codes. */
+ kStatusGroup_TIMERMANAGER = 135, /*!< Group number for TiMER MANAGER status codes. */
+ kStatusGroup_SERIALMANAGER = 136, /*!< Group number for SERIAL MANAGER status codes. */
+ kStatusGroup_LED = 137, /*!< Group number for LED status codes. */
+ kStatusGroup_BUTTON = 138, /*!< Group number for BUTTON status codes. */
+ kStatusGroup_EXTERN_EEPROM = 139, /*!< Group number for EXTERN EEPROM status codes. */
+ kStatusGroup_SHELL = 140, /*!< Group number for SHELL status codes. */
+ kStatusGroup_MEM_MANAGER = 141, /*!< Group number for MEM MANAGER status codes. */
+ kStatusGroup_LIST = 142, /*!< Group number for List status codes. */
+ kStatusGroup_OSA = 143, /*!< Group number for OSA status codes. */
+ kStatusGroup_COMMON_TASK = 144, /*!< Group number for Common task status codes. */
+ kStatusGroup_MSG = 145, /*!< Group number for messaging status codes. */
+ kStatusGroup_SDK_OCOTP = 146, /*!< Group number for OCOTP status codes. */
+ kStatusGroup_SDK_FLEXSPINOR = 147, /*!< Group number for FLEXSPINOR status codes.*/
+ kStatusGroup_CODEC = 148, /*!< Group number for codec status codes. */
+ kStatusGroup_ASRC = 149, /*!< Group number for codec status ASRC. */
+ kStatusGroup_OTFAD = 150, /*!< Group number for codec status codes. */
+ kStatusGroup_SDIOSLV = 151, /*!< Group number for SDIOSLV status codes. */
+ kStatusGroup_MECC = 152, /*!< Group number for MECC status codes. */
+ kStatusGroup_ENET_QOS = 153, /*!< Group number for ENET_QOS status codes. */
+ kStatusGroup_LOG = 154, /*!< Group number for LOG status codes. */
+ kStatusGroup_I3CBUS = 155, /*!< Group number for I3CBUS status codes. */
+ kStatusGroup_QSCI = 156, /*!< Group number for QSCI status codes. */
+ kStatusGroup_SNT = 157, /*!< Group number for SNT status codes. */
+ kStatusGroup_QUEUEDSPI = 158, /*!< Group number for QSPI status codes. */
+ kStatusGroup_POWER_MANAGER = 159, /*!< Group number for POWER_MANAGER status codes. */
+ kStatusGroup_IPED = 160, /*!< Group number for IPED status codes. */
+ kStatusGroup_CSS_PKC = 161, /*!< Group number for CSS PKC status codes. */
+ kStatusGroup_HOSTIF = 162, /*!< Group number for HOSTIF status codes. */
+ kStatusGroup_CLIF = 163, /*!< Group number for CLIF status codes. */
+ kStatusGroup_BMA = 164, /*!< Group number for BMA status codes. */
+ kStatusGroup_NETC = 165, /*!< Group number for NETC status codes. */
};
/*! \public
@@ -183,14 +204,17 @@ enum _status_groups
*/
enum
{
- kStatus_Success = MAKE_STATUS(kStatusGroup_Generic, 0), /*!< Generic status for Success. */
- kStatus_Fail = MAKE_STATUS(kStatusGroup_Generic, 1), /*!< Generic status for Fail. */
- kStatus_ReadOnly = MAKE_STATUS(kStatusGroup_Generic, 2), /*!< Generic status for read only failure. */
- kStatus_OutOfRange = MAKE_STATUS(kStatusGroup_Generic, 3), /*!< Generic status for out of range access. */
- kStatus_InvalidArgument = MAKE_STATUS(kStatusGroup_Generic, 4), /*!< Generic status for invalid argument check. */
- kStatus_Timeout = MAKE_STATUS(kStatusGroup_Generic, 5), /*!< Generic status for timeout. */
- kStatus_NoTransferInProgress = MAKE_STATUS(kStatusGroup_Generic, 6), /*!< Generic status for no transfer in progress. */
- kStatus_Busy = MAKE_STATUS(kStatusGroup_Generic, 7), /*!< Generic status for module is busy. */
+ kStatus_Success = MAKE_STATUS(kStatusGroup_Generic, 0), /*!< Generic status for Success. */
+ kStatus_Fail = MAKE_STATUS(kStatusGroup_Generic, 1), /*!< Generic status for Fail. */
+ kStatus_ReadOnly = MAKE_STATUS(kStatusGroup_Generic, 2), /*!< Generic status for read only failure. */
+ kStatus_OutOfRange = MAKE_STATUS(kStatusGroup_Generic, 3), /*!< Generic status for out of range access. */
+ kStatus_InvalidArgument = MAKE_STATUS(kStatusGroup_Generic, 4), /*!< Generic status for invalid argument check. */
+ kStatus_Timeout = MAKE_STATUS(kStatusGroup_Generic, 5), /*!< Generic status for timeout. */
+ kStatus_NoTransferInProgress =
+ MAKE_STATUS(kStatusGroup_Generic, 6), /*!< Generic status for no transfer in progress. */
+ kStatus_Busy = MAKE_STATUS(kStatusGroup_Generic, 7), /*!< Generic status for module is busy. */
+ kStatus_NoData =
+ MAKE_STATUS(kStatusGroup_Generic, 8), /*!< Generic status for no data is found for the operation. */
};
/*! @brief Type used for all status and error return values. */
@@ -233,7 +257,7 @@ typedef int32_t status_t;
*/
/* @{ */
#if defined(__GNUC__) && !defined(__ARMCC_VERSION)
-#define SUPPRESS_FALL_THROUGH_WARNING() __attribute__ ((fallthrough))
+#define SUPPRESS_FALL_THROUGH_WARNING() __attribute__((fallthrough))
#else
#define SUPPRESS_FALL_THROUGH_WARNING()
#endif
@@ -247,6 +271,7 @@ typedef int32_t status_t;
extern "C" {
#endif
+#if !((defined(__DSC__) && defined(__CW__)))
/*!
* @brief Allocate memory with given alignment and aligned size.
*
@@ -264,15 +289,16 @@ void *SDK_Malloc(size_t size, size_t alignbytes);
* @param ptr The memory to be release.
*/
void SDK_Free(void *ptr);
+#endif
/*!
-* @brief Delay at least for some time.
-* Please note that, this API uses while loop for delay, different run-time environments make the time not precise,
-* if precise delay count was needed, please implement a new delay function with hardware timer.
-*
-* @param delayTime_us Delay time in unit of microsecond.
-* @param coreClock_Hz Core clock frequency with Hz.
-*/
+ * @brief Delay at least for some time.
+ * Please note that, this API uses while loop for delay, different run-time environments make the time not precise,
+ * if precise delay count was needed, please implement a new delay function with hardware timer.
+ *
+ * @param delayTime_us Delay time in unit of microsecond.
+ * @param coreClock_Hz Core clock frequency with Hz.
+ */
void SDK_DelayAtLeastUs(uint32_t delayTime_us, uint32_t coreClock_Hz);
#if defined(__cplusplus)
diff --git a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common_arm.c b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common_arm.c
index e77a265ce..241005e92 100644
--- a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common_arm.c
+++ b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common_arm.c
@@ -116,9 +116,9 @@ void DisableDeepSleepIRQ(IRQn_Type interrupt)
#endif /* FSL_FEATURE_POWERLIB_EXTEND */
#endif /* FSL_FEATURE_SOC_SYSCON_COUNT */
-#if defined(SDK_DELAY_USE_DWT) && defined(DWT)
+#if defined(DWT)
/* Use WDT. */
-static void enableCpuCycleCounter(void)
+void MSDK_EnableCpuCycleCounter(void)
{
/* Make sure the DWT trace fucntion is enabled. */
if (CoreDebug_DEMCR_TRCENA_Msk != (CoreDebug_DEMCR_TRCENA_Msk & CoreDebug->DEMCR))
@@ -136,11 +136,13 @@ static void enableCpuCycleCounter(void)
}
}
-static uint32_t getCpuCycleCount(void)
+uint32_t MSDK_GetCpuCycleCount(void)
{
return DWT->CYCCNT;
}
-#else /* defined(SDK_DELAY_USE_DWT) && defined(DWT) */
+#endif /* defined(DWT) */
+
+#if !(defined(SDK_DELAY_USE_DWT) && defined(DWT))
/* Use software loop. */
#if defined(__CC_ARM) /* This macro is arm v5 specific */
/* clang-format off */
@@ -152,6 +154,20 @@ loop
BNE loop
BX LR
}
+#elif defined(__ARM_ARCH_8A__) /* This macro is ARMv8-A specific */
+static void DelayLoop(uint32_t count)
+{
+ __ASM volatile(" MOV X0, %0" : : "r"(count));
+ __ASM volatile(
+ "loop: \n"
+ " SUB X0, X0, #1 \n"
+ " CMP X0, #0 \n"
+
+ " BNE loop \n"
+ :
+ :
+ : "r0");
+}
/* clang-format on */
#elif defined(__ARMCC_VERSION) || defined(__ICCARM__) || defined(__GNUC__)
/* Cortex-M0 has a smaller instruction set, SUBS isn't supported in thumb-16 mode reported from __GNUC__ compiler,
@@ -198,21 +214,21 @@ void SDK_DelayAtLeastUs(uint32_t delayTime_us, uint32_t coreClock_Hz)
#if defined(SDK_DELAY_USE_DWT) && defined(DWT) /* Use DWT for better accuracy */
- enableCpuCycleCounter();
+ MSDK_EnableCpuCycleCounter();
/* Calculate the count ticks. */
- count += getCpuCycleCount();
+ count += MSDK_GetCpuCycleCount();
if (count > UINT32_MAX)
{
count -= UINT32_MAX;
/* Wait for cyccnt overflow. */
- while (count < getCpuCycleCount())
+ while (count < MSDK_GetCpuCycleCount())
{
}
}
/* Wait for cyccnt reach count value. */
- while (count > getCpuCycleCount())
+ while (count > MSDK_GetCpuCycleCount())
{
}
#else
diff --git a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common_arm.h b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common_arm.h
index 8b28aa888..1da9dff8d 100644
--- a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common_arm.h
+++ b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_common_arm.h
@@ -1,6 +1,6 @@
/*
* Copyright (c) 2015-2016, Freescale Semiconductor, Inc.
- * Copyright 2016-2021 NXP
+ * Copyright 2016-2022 NXP
* All rights reserved.
*
* SPDX-License-Identifier: BSD-3-Clause
@@ -214,69 +214,82 @@ static inline void _SDK_AtomicLocalClearAndSet4Byte(volatile uint32_t *addr, uin
_SDK_ATOMIC_LOCAL_OPS_4BYTE(addr, s_val, s_val = (s_val & ~clearBits) | setBits);
}
-#define SDK_ATOMIC_LOCAL_ADD(addr, val) \
- ((1UL == sizeof(*(addr))) ? _SDK_AtomicLocalAdd1Byte((volatile uint8_t*)(volatile void*)(addr), (val)) : \
- ((2UL == sizeof(*(addr))) ? _SDK_AtomicLocalAdd2Byte((volatile uint16_t*)(volatile void*)(addr), (val)) : \
- _SDK_AtomicLocalAdd4Byte((volatile uint32_t *)(volatile void*)(addr), (val))))
-
-#define SDK_ATOMIC_LOCAL_SET(addr, bits) \
- ((1UL == sizeof(*(addr))) ? _SDK_AtomicLocalSet1Byte((volatile uint8_t*)(volatile void*)(addr), (bits)) : \
- ((2UL == sizeof(*(addr))) ? _SDK_AtomicLocalSet2Byte((volatile uint16_t*)(volatile void*)(addr), (bits)) : \
- _SDK_AtomicLocalSet4Byte((volatile uint32_t *)(volatile void*)(addr), (bits))))
-
-#define SDK_ATOMIC_LOCAL_CLEAR(addr, bits) \
- ((1UL == sizeof(*(addr))) ? _SDK_AtomicLocalClear1Byte((volatile uint8_t*)(volatile void*)(addr), (bits)) : \
- ((2UL == sizeof(*(addr))) ? _SDK_AtomicLocalClear2Byte((volatile uint16_t*)(volatile void*)(addr), (bits)) : \
- _SDK_AtomicLocalClear4Byte((volatile uint32_t *)(volatile void*)(addr), (bits))))
-
-#define SDK_ATOMIC_LOCAL_TOGGLE(addr, bits) \
- ((1UL == sizeof(*(addr))) ? _SDK_AtomicLocalToggle1Byte((volatile uint8_t*)(volatile void*)(addr), (bits)) : \
- ((2UL == sizeof(*(addr))) ? _SDK_AtomicLocalToggle2Byte((volatile uint16_t*)(volatile void*)(addr), (bits)) : \
- _SDK_AtomicLocalToggle4Byte((volatile uint32_t *)(volatile void*)(addr), (bits))))
-
-#define SDK_ATOMIC_LOCAL_CLEAR_AND_SET(addr, clearBits, setBits) \
- ((1UL == sizeof(*(addr))) ? _SDK_AtomicLocalClearAndSet1Byte((volatile uint8_t*)(volatile void*)(addr), (clearBits), (setBits)) : \
- ((2UL == sizeof(*(addr))) ? _SDK_AtomicLocalClearAndSet2Byte((volatile uint16_t*)(volatile void*)(addr), (clearBits), (setBits)) : \
- _SDK_AtomicLocalClearAndSet4Byte((volatile uint32_t *)(volatile void*)(addr), (clearBits), (setBits))))
+#define SDK_ATOMIC_LOCAL_ADD(addr, val) \
+ ((1UL == sizeof(*(addr))) ? \
+ _SDK_AtomicLocalAdd1Byte((volatile uint8_t *)(volatile void *)(addr), (uint8_t)(val)) : \
+ ((2UL == sizeof(*(addr))) ? _SDK_AtomicLocalAdd2Byte((volatile uint16_t *)(volatile void *)(addr), (uint16_t)(val)) : \
+ _SDK_AtomicLocalAdd4Byte((volatile uint32_t *)(volatile void *)(addr), (uint32_t)(val))))
+
+#define SDK_ATOMIC_LOCAL_SET(addr, bits) \
+ ((1UL == sizeof(*(addr))) ? \
+ _SDK_AtomicLocalSet1Byte((volatile uint8_t *)(volatile void *)(addr), (uint8_t)(bits)) : \
+ ((2UL == sizeof(*(addr))) ? _SDK_AtomicLocalSet2Byte((volatile uint16_t *)(volatile void *)(addr), (uint16_t)(bits)) : \
+ _SDK_AtomicLocalSet4Byte((volatile uint32_t *)(volatile void *)(addr), (uint32_t)(bits))))
+
+#define SDK_ATOMIC_LOCAL_CLEAR(addr, bits) \
+ ((1UL == sizeof(*(addr))) ? \
+ _SDK_AtomicLocalClear1Byte((volatile uint8_t *)(volatile void *)(addr), (uint8_t)(bits)) : \
+ ((2UL == sizeof(*(addr))) ? \
+ _SDK_AtomicLocalClear2Byte((volatile uint16_t *)(volatile void *)(addr), (uint16_t)(bits)) : \
+ _SDK_AtomicLocalClear4Byte((volatile uint32_t *)(volatile void *)(addr), (uint32_t)(bits))))
+
+#define SDK_ATOMIC_LOCAL_TOGGLE(addr, bits) \
+ ((1UL == sizeof(*(addr))) ? \
+ _SDK_AtomicLocalToggle1Byte((volatile uint8_t *)(volatile void *)(addr), (uint8_t)(bits)) : \
+ ((2UL == sizeof(*(addr))) ? \
+ _SDK_AtomicLocalToggle2Byte((volatile uint16_t *)(volatile void *)(addr), (uint16_t)(bits)) : \
+ _SDK_AtomicLocalToggle4Byte((volatile uint32_t *)(volatile void *)(addr), (uint32_t)(bits))))
+
+#define SDK_ATOMIC_LOCAL_CLEAR_AND_SET(addr, clearBits, setBits) \
+ ((1UL == sizeof(*(addr))) ? \
+ _SDK_AtomicLocalClearAndSet1Byte((volatile uint8_t *)(volatile void *)(addr), (uint8_t)(clearBits), (uint8_t)(setBits)) : \
+ ((2UL == sizeof(*(addr))) ? \
+ _SDK_AtomicLocalClearAndSet2Byte((volatile uint16_t *)(volatile void *)(addr), (uint16_t)(clearBits), (uint16_t)(setBits)) : \
+ _SDK_AtomicLocalClearAndSet4Byte((volatile uint32_t *)(volatile void *)(addr), (uint32_t)(clearBits), (uint32_t)(setBits))))
#else
-#define SDK_ATOMIC_LOCAL_ADD(addr, val) \
- do { \
- uint32_t s_atomicOldInt; \
- s_atomicOldInt = DisableGlobalIRQ(); \
- *(addr) += (val); \
- EnableGlobalIRQ(s_atomicOldInt); \
+#define SDK_ATOMIC_LOCAL_ADD(addr, val) \
+ do \
+ { \
+ uint32_t s_atomicOldInt; \
+ s_atomicOldInt = DisableGlobalIRQ(); \
+ *(addr) += (val); \
+ EnableGlobalIRQ(s_atomicOldInt); \
} while (0)
-#define SDK_ATOMIC_LOCAL_SET(addr, bits) \
- do { \
- uint32_t s_atomicOldInt; \
- s_atomicOldInt = DisableGlobalIRQ(); \
- *(addr) |= (bits); \
- EnableGlobalIRQ(s_atomicOldInt); \
+#define SDK_ATOMIC_LOCAL_SET(addr, bits) \
+ do \
+ { \
+ uint32_t s_atomicOldInt; \
+ s_atomicOldInt = DisableGlobalIRQ(); \
+ *(addr) |= (bits); \
+ EnableGlobalIRQ(s_atomicOldInt); \
} while (0)
-#define SDK_ATOMIC_LOCAL_CLEAR(addr, bits) \
- do { \
- uint32_t s_atomicOldInt; \
- s_atomicOldInt = DisableGlobalIRQ(); \
- *(addr) &= ~(bits); \
- EnableGlobalIRQ(s_atomicOldInt); \
+#define SDK_ATOMIC_LOCAL_CLEAR(addr, bits) \
+ do \
+ { \
+ uint32_t s_atomicOldInt; \
+ s_atomicOldInt = DisableGlobalIRQ(); \
+ *(addr) &= ~(bits); \
+ EnableGlobalIRQ(s_atomicOldInt); \
} while (0)
-#define SDK_ATOMIC_LOCAL_TOGGLE(addr, bits) \
- do { \
- uint32_t s_atomicOldInt; \
- s_atomicOldInt = DisableGlobalIRQ(); \
- *(addr) ^= (bits); \
- EnableGlobalIRQ(s_atomicOldInt); \
+#define SDK_ATOMIC_LOCAL_TOGGLE(addr, bits) \
+ do \
+ { \
+ uint32_t s_atomicOldInt; \
+ s_atomicOldInt = DisableGlobalIRQ(); \
+ *(addr) ^= (bits); \
+ EnableGlobalIRQ(s_atomicOldInt); \
} while (0)
#define SDK_ATOMIC_LOCAL_CLEAR_AND_SET(addr, clearBits, setBits) \
- do { \
+ do \
+ { \
uint32_t s_atomicOldInt; \
s_atomicOldInt = DisableGlobalIRQ(); \
- *(addr) = (*(addr) & ~(clearBits)) | (setBits); \
+ *(addr) = (*(addr) & ~(clearBits)) | (setBits); \
EnableGlobalIRQ(s_atomicOldInt); \
} while (0)
@@ -288,12 +301,12 @@ static inline void _SDK_AtomicLocalClearAndSet4Byte(volatile uint32_t *addr, uin
/*! Macro to convert a microsecond period to raw count value */
#define USEC_TO_COUNT(us, clockFreqInHz) (uint64_t)(((uint64_t)(us) * (clockFreqInHz)) / 1000000U)
/*! Macro to convert a raw count value to microsecond */
-#define COUNT_TO_USEC(count, clockFreqInHz) (uint64_t)((uint64_t)(count) * 1000000U / (clockFreqInHz))
+#define COUNT_TO_USEC(count, clockFreqInHz) (uint64_t)((uint64_t)(count)*1000000U / (clockFreqInHz))
/*! Macro to convert a millisecond period to raw count value */
#define MSEC_TO_COUNT(ms, clockFreqInHz) (uint64_t)((uint64_t)(ms) * (clockFreqInHz) / 1000U)
/*! Macro to convert a raw count value to millisecond */
-#define COUNT_TO_MSEC(count, clockFreqInHz) (uint64_t)((uint64_t)(count) * 1000U / (clockFreqInHz))
+#define COUNT_TO_MSEC(count, clockFreqInHz) (uint64_t)((uint64_t)(count)*1000U / (clockFreqInHz))
/* @} */
/*! @name ISR exit barrier
@@ -322,7 +335,7 @@ static inline void _SDK_AtomicLocalClearAndSet4Byte(volatile uint32_t *addr, uin
*/
_Pragma("diag_suppress=Pm120")
#define SDK_PRAGMA(x) _Pragma(#x)
-_Pragma("diag_error=Pm120")
+ _Pragma("diag_error=Pm120")
/*! Macro to define a variable with alignbytes alignment */
#define SDK_ALIGN(var, alignbytes) SDK_PRAGMA(data_alignment = alignbytes) var
#elif defined(__CC_ARM) || defined(__ARMCC_VERSION)
@@ -351,25 +364,27 @@ _Pragma("diag_error=Pm120")
/*! @name Non-cacheable region definition macros */
/* For initialized non-zero non-cacheable variables, please using "AT_NONCACHEABLE_SECTION_INIT(var) ={xx};" or
- * "AT_NONCACHEABLE_SECTION_ALIGN_INIT(var) ={xx};" in your projects to define them, for zero-inited non-cacheable variables,
- * please using "AT_NONCACHEABLE_SECTION(var);" or "AT_NONCACHEABLE_SECTION_ALIGN(var);" to define them, these zero-inited variables
- * will be initialized to zero in system startup.
+ * "AT_NONCACHEABLE_SECTION_ALIGN_INIT(var) ={xx};" in your projects to define them, for zero-inited non-cacheable
+ * variables, please using "AT_NONCACHEABLE_SECTION(var);" or "AT_NONCACHEABLE_SECTION_ALIGN(var);" to define them,
+ * these zero-inited variables will be initialized to zero in system startup.
*/
/* @{ */
-#if ((!(defined(FSL_FEATURE_HAS_NO_NONCACHEABLE_SECTION) && FSL_FEATURE_HAS_NO_NONCACHEABLE_SECTION)) && defined(FSL_FEATURE_L1ICACHE_LINESIZE_BYTE))
+#if ((!(defined(FSL_FEATURE_HAS_NO_NONCACHEABLE_SECTION) && FSL_FEATURE_HAS_NO_NONCACHEABLE_SECTION)) && \
+ defined(FSL_FEATURE_L1ICACHE_LINESIZE_BYTE))
#if (defined(__ICCARM__))
-#define AT_NONCACHEABLE_SECTION(var) var @"NonCacheable"
+#define AT_NONCACHEABLE_SECTION(var) var @"NonCacheable"
#define AT_NONCACHEABLE_SECTION_ALIGN(var, alignbytes) SDK_PRAGMA(data_alignment = alignbytes) var @"NonCacheable"
-#define AT_NONCACHEABLE_SECTION_INIT(var) var @"NonCacheable.init"
-#define AT_NONCACHEABLE_SECTION_ALIGN_INIT(var, alignbytes) SDK_PRAGMA(data_alignment = alignbytes) var @"NonCacheable.init"
+#define AT_NONCACHEABLE_SECTION_INIT(var) var @"NonCacheable.init"
+#define AT_NONCACHEABLE_SECTION_ALIGN_INIT(var, alignbytes) \
+ SDK_PRAGMA(data_alignment = alignbytes) var @"NonCacheable.init"
-#elif(defined(__CC_ARM) || defined(__ARMCC_VERSION))
+#elif (defined(__CC_ARM) || defined(__ARMCC_VERSION))
#define AT_NONCACHEABLE_SECTION_INIT(var) __attribute__((section("NonCacheable.init"))) var
#define AT_NONCACHEABLE_SECTION_ALIGN_INIT(var, alignbytes) \
__attribute__((section("NonCacheable.init"))) __attribute__((aligned(alignbytes))) var
-#if(defined(__CC_ARM))
+#if (defined(__CC_ARM))
#define AT_NONCACHEABLE_SECTION(var) __attribute__((section("NonCacheable"), zero_init)) var
#define AT_NONCACHEABLE_SECTION_ALIGN(var, alignbytes) \
__attribute__((section("NonCacheable"), zero_init)) __attribute__((aligned(alignbytes))) var
@@ -379,7 +394,7 @@ _Pragma("diag_error=Pm120")
__attribute__((section(".bss.NonCacheable"))) __attribute__((aligned(alignbytes))) var
#endif
-#elif(defined(__GNUC__))
+#elif (defined(__GNUC__))
/* For GCC, when the non-cacheable section is required, please define "__STARTUP_INITIALIZE_NONCACHEDATA"
* in your projects to make sure the non-cacheable section variables will be initialized in system startup.
*/
@@ -395,9 +410,9 @@ _Pragma("diag_error=Pm120")
#else
-#define AT_NONCACHEABLE_SECTION(var) var
-#define AT_NONCACHEABLE_SECTION_ALIGN(var, alignbytes) SDK_ALIGN(var, alignbytes)
-#define AT_NONCACHEABLE_SECTION_INIT(var) var
+#define AT_NONCACHEABLE_SECTION(var) var
+#define AT_NONCACHEABLE_SECTION_ALIGN(var, alignbytes) SDK_ALIGN(var, alignbytes)
+#define AT_NONCACHEABLE_SECTION_INIT(var) var
#define AT_NONCACHEABLE_SECTION_ALIGN_INIT(var, alignbytes) SDK_ALIGN(var, alignbytes)
#endif
@@ -408,43 +423,39 @@ _Pragma("diag_error=Pm120")
* @name Time sensitive region
* @{
*/
-#if (defined(FSL_SDK_DRIVER_QUICK_ACCESS_ENABLE) && FSL_SDK_DRIVER_QUICK_ACCESS_ENABLE)
-
#if (defined(__ICCARM__))
#define AT_QUICKACCESS_SECTION_CODE(func) func @"CodeQuickAccess"
-#define AT_QUICKACCESS_SECTION_DATA(func) func @"DataQuickAccess"
-#elif(defined(__CC_ARM) || defined(__ARMCC_VERSION))
+#define AT_QUICKACCESS_SECTION_DATA(var) var @"DataQuickAccess"
+#define AT_QUICKACCESS_SECTION_DATA_ALIGN(var, alignbytes) \
+ SDK_PRAGMA(data_alignment = alignbytes) var @"DataQuickAccess"
+#elif (defined(__CC_ARM) || defined(__ARMCC_VERSION))
#define AT_QUICKACCESS_SECTION_CODE(func) __attribute__((section("CodeQuickAccess"), __noinline__)) func
-#define AT_QUICKACCESS_SECTION_DATA(func) __attribute__((section("DataQuickAccess"))) func
-#elif(defined(__GNUC__))
+#define AT_QUICKACCESS_SECTION_DATA(var) __attribute__((section("DataQuickAccess"))) var
+#define AT_QUICKACCESS_SECTION_DATA_ALIGN(var, alignbytes) \
+ __attribute__((section("DataQuickAccess"))) __attribute__((aligned(alignbytes))) var
+#elif (defined(__GNUC__))
#define AT_QUICKACCESS_SECTION_CODE(func) __attribute__((section("CodeQuickAccess"), __noinline__)) func
-#define AT_QUICKACCESS_SECTION_DATA(func) __attribute__((section("DataQuickAccess"))) func
+#define AT_QUICKACCESS_SECTION_DATA(var) __attribute__((section("DataQuickAccess"))) var
+#define AT_QUICKACCESS_SECTION_DATA_ALIGN(var, alignbytes) \
+ __attribute__((section("DataQuickAccess"))) var __attribute__((aligned(alignbytes)))
#else
#error Toolchain not supported.
#endif /* defined(__ICCARM__) */
-#else /* __FSL_SDK_DRIVER_QUICK_ACCESS_ENABLE */
-
-#define AT_QUICKACCESS_SECTION_CODE(func) func
-#define AT_QUICKACCESS_SECTION_DATA(func) func
-
-#endif /* __FSL_SDK_DRIVER_QUICK_ACCESS_ENABLE */
-/* @} */
-
/*! @name Ram Function */
#if (defined(__ICCARM__))
#define RAMFUNCTION_SECTION_CODE(func) func @"RamFunction"
-#elif(defined(__CC_ARM) || defined(__ARMCC_VERSION))
+#elif (defined(__CC_ARM) || defined(__ARMCC_VERSION))
#define RAMFUNCTION_SECTION_CODE(func) __attribute__((section("RamFunction"))) func
-#elif(defined(__GNUC__))
+#elif (defined(__GNUC__))
#define RAMFUNCTION_SECTION_CODE(func) __attribute__((section("RamFunction"))) func
#else
#error Toolchain not supported.
#endif /* defined(__ICCARM__) */
/* @} */
-#if defined ( __ARMCC_VERSION ) && ( __ARMCC_VERSION >= 6010050 )
-void DefaultISR(void);
+#if defined(__ARMCC_VERSION) && (__ARMCC_VERSION >= 6010050)
+ void DefaultISR(void);
#endif
/*
@@ -558,6 +569,144 @@ static inline status_t DisableIRQ(IRQn_Type interrupt)
}
/*!
+ * @brief Enable the IRQ, and also set the interrupt priority.
+ *
+ * Only handle LEVEL1 interrupt. For some devices, there might be multiple interrupt
+ * levels. For example, there are NVIC and intmux. Here the interrupts connected
+ * to NVIC are the LEVEL1 interrupts, because they are routed to the core directly.
+ * The interrupts connected to intmux are the LEVEL2 interrupts, they are routed
+ * to NVIC first then routed to core.
+ *
+ * This function only handles the LEVEL1 interrupts. The number of LEVEL1 interrupts
+ * is indicated by the feature macro FSL_FEATURE_NUMBER_OF_LEVEL1_INT_VECTORS.
+ *
+ * @param interrupt The IRQ to Enable.
+ * @param priNum Priority number set to interrupt controller register.
+ * @retval kStatus_Success Interrupt priority set successfully
+ * @retval kStatus_Fail Failed to set the interrupt priority.
+ */
+static inline status_t EnableIRQWithPriority(IRQn_Type interrupt, uint8_t priNum)
+{
+ status_t status = kStatus_Success;
+
+ if (NotAvail_IRQn == interrupt)
+ {
+ status = kStatus_Fail;
+ }
+
+#if defined(FSL_FEATURE_NUMBER_OF_LEVEL1_INT_VECTORS) && (FSL_FEATURE_NUMBER_OF_LEVEL1_INT_VECTORS > 0)
+ else if ((int32_t)interrupt >= (int32_t)FSL_FEATURE_NUMBER_OF_LEVEL1_INT_VECTORS)
+ {
+ status = kStatus_Fail;
+ }
+#endif
+
+ else
+ {
+#if defined(__GIC_PRIO_BITS)
+ GIC_SetPriority(interrupt, priNum);
+ GIC_EnableIRQ(interrupt);
+#else
+ NVIC_SetPriority(interrupt, priNum);
+ NVIC_EnableIRQ(interrupt);
+#endif
+ }
+
+ return status;
+}
+
+/*!
+ * @brief Set the IRQ priority.
+ *
+ * Only handle LEVEL1 interrupt. For some devices, there might be multiple interrupt
+ * levels. For example, there are NVIC and intmux. Here the interrupts connected
+ * to NVIC are the LEVEL1 interrupts, because they are routed to the core directly.
+ * The interrupts connected to intmux are the LEVEL2 interrupts, they are routed
+ * to NVIC first then routed to core.
+ *
+ * This function only handles the LEVEL1 interrupts. The number of LEVEL1 interrupts
+ * is indicated by the feature macro FSL_FEATURE_NUMBER_OF_LEVEL1_INT_VECTORS.
+ *
+ * @param interrupt The IRQ to set.
+ * @param priNum Priority number set to interrupt controller register.
+ *
+ * @retval kStatus_Success Interrupt priority set successfully
+ * @retval kStatus_Fail Failed to set the interrupt priority.
+ */
+static inline status_t IRQ_SetPriority(IRQn_Type interrupt, uint8_t priNum)
+{
+ status_t status = kStatus_Success;
+
+ if (NotAvail_IRQn == interrupt)
+ {
+ status = kStatus_Fail;
+ }
+
+#if defined(FSL_FEATURE_NUMBER_OF_LEVEL1_INT_VECTORS) && (FSL_FEATURE_NUMBER_OF_LEVEL1_INT_VECTORS > 0)
+ else if ((int32_t)interrupt >= (int32_t)FSL_FEATURE_NUMBER_OF_LEVEL1_INT_VECTORS)
+ {
+ status = kStatus_Fail;
+ }
+#endif
+
+ else
+ {
+#if defined(__GIC_PRIO_BITS)
+ GIC_SetPriority(interrupt, priNum);
+#else
+ NVIC_SetPriority(interrupt, priNum);
+#endif
+ }
+
+ return status;
+}
+
+/*!
+ * @brief Clear the pending IRQ flag.
+ *
+ * Only handle LEVEL1 interrupt. For some devices, there might be multiple interrupt
+ * levels. For example, there are NVIC and intmux. Here the interrupts connected
+ * to NVIC are the LEVEL1 interrupts, because they are routed to the core directly.
+ * The interrupts connected to intmux are the LEVEL2 interrupts, they are routed
+ * to NVIC first then routed to core.
+ *
+ * This function only handles the LEVEL1 interrupts. The number of LEVEL1 interrupts
+ * is indicated by the feature macro FSL_FEATURE_NUMBER_OF_LEVEL1_INT_VECTORS.
+ *
+ * @param interrupt The flag which IRQ to clear.
+ *
+ * @retval kStatus_Success Interrupt priority set successfully
+ * @retval kStatus_Fail Failed to set the interrupt priority.
+ */
+static inline status_t IRQ_ClearPendingIRQ(IRQn_Type interrupt)
+{
+ status_t status = kStatus_Success;
+
+ if (NotAvail_IRQn == interrupt)
+ {
+ status = kStatus_Fail;
+ }
+
+#if defined(FSL_FEATURE_NUMBER_OF_LEVEL1_INT_VECTORS) && (FSL_FEATURE_NUMBER_OF_LEVEL1_INT_VECTORS > 0)
+ else if ((int32_t)interrupt >= (int32_t)FSL_FEATURE_NUMBER_OF_LEVEL1_INT_VECTORS)
+ {
+ status = kStatus_Fail;
+ }
+#endif
+
+ else
+ {
+#if defined(__GIC_PRIO_BITS)
+ GIC_ClearPendingIRQ(interrupt);
+#else
+ NVIC_ClearPendingIRQ(interrupt);
+#endif
+ }
+
+ return status;
+}
+
+/*!
* @brief Disable the global IRQ
*
* Disable the global interrupt and return the current primask register. User is required to provided the primask
@@ -567,19 +716,18 @@ static inline status_t DisableIRQ(IRQn_Type interrupt)
*/
static inline uint32_t DisableGlobalIRQ(void)
{
-#if defined(CPSR_I_Msk)
- uint32_t cpsr = __get_CPSR() & CPSR_I_Msk;
-
- __disable_irq();
+ uint32_t mask;
- return cpsr;
+#if defined(CPSR_I_Msk)
+ mask = __get_CPSR() & CPSR_I_Msk;
+#elif defined(DAIF_I_BIT)
+ mask = __get_DAIF() & DAIF_I_BIT;
#else
- uint32_t regPrimask = __get_PRIMASK();
-
+ mask = __get_PRIMASK();
+#endif
__disable_irq();
- return regPrimask;
-#endif
+ return mask;
}
/*!
@@ -596,6 +744,11 @@ static inline void EnableGlobalIRQ(uint32_t primask)
{
#if defined(CPSR_I_Msk)
__set_CPSR((__get_CPSR() & ~CPSR_I_Msk) | primask);
+#elif defined(DAIF_I_BIT)
+ if (0UL == primask)
+ {
+ __enable_irq();
+ }
#else
__set_PRIMASK(primask);
#endif
@@ -651,6 +804,20 @@ void DisableDeepSleepIRQ(IRQn_Type interrupt);
#endif /* FSL_FEATURE_POWERLIB_EXTEND */
#endif /* FSL_FEATURE_SOC_SYSCON_COUNT */
+#if defined(DWT)
+/*!
+ * @brief Enable the counter to get CPU cycles.
+ */
+void MSDK_EnableCpuCycleCounter(void);
+
+/*!
+ * @brief Get the current CPU cycle count.
+ *
+ * @return Current CPU cycle count.
+ */
+uint32_t MSDK_GetCpuCycleCount(void);
+#endif
+
#if defined(__cplusplus)
}
#endif /* __cplusplus*/
diff --git a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_power.c b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_power.c
index ccc1ad471..41561f4d6 100644
--- a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_power.c
+++ b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_power.c
@@ -13,7 +13,1819 @@
#endif
/*******************************************************************************
- * Code
+ * Variables
******************************************************************************/
-/* Empty file since implementation is in header file and power library */
+/*******************************************************************************
+ * Definitions
+ ******************************************************************************/
+/** @brief Low Power main structure */
+typedef enum
+{
+ VD_AON = 0x0, /*!< Digital Always On power domain */
+ VD_MEM = 0x1, /*!< Memories (SRAM) power domain */
+ VD_DCDC = 0x2, /*!< Core logic power domain */
+ VD_DEEPSLEEP = 0x3 /*!< Core logic power domain */
+} LPC_POWER_DOMAIN_T;
+
+/**
+ * @brief LDO_FLASH_NV & LDO_USB voltage settings
+ */
+typedef enum _v_flashnv
+{
+ V_LDOFLASHNV_1P650 = 0, /*!< 0.95 V */
+ V_LDOFLASHNV_1P700 = 1, /*!< 0.975 V */
+ V_LDOFLASHNV_1P750 = 2, /*!< 1 V */
+ V_LDOFLASHNV_0P800 = 3, /*!< 1.025 V */
+ V_LDOFLASHNV_1P850 = 4, /*!< 1.050 V */
+ V_LDOFLASHNV_1P900 = 5, /*!< 1.075 V */
+ V_LDOFLASHNV_1P950 = 6, /*!< 1.1 V */
+ V_LDOFLASHNV_2P000 = 7 /*!< 1.125 V */
+} v_flashnv_t;
+
+/** @brief Low Power main structure */
+typedef struct
+{ /* */
+ __IO uint32_t CFG; /*!< Low Power Mode Configuration, and miscallenous options */
+ __IO uint32_t PDCTRL0; /*!< Power Down control : controls power of various modules
+ in the different Low power modes, including ROM */
+ __IO uint32_t SRAMRETCTRL; /*!< Power Down control : controls power SRAM instances
+ in the different Low power modes */
+ __IO uint32_t CPURETCTRL; /*!< CPU0 retention control : controls CPU retention parameters in POWER DOWN modes */
+ __IO uint64_t VOLTAGE; /*!< Voltage control in Low Power Modes */
+ __IO uint64_t WAKEUPSRC; /*!< Wake up sources control for sleepcon */
+ __IO uint64_t WAKEUPINT; /*!< Wake up sources control for ARM */
+ __IO uint32_t HWWAKE; /*!< Interrupt that can postpone power down modes
+ in case an interrupt is pending when the processor request deepsleep */
+ __IO uint32_t WAKEUPIOSRC; /*!< Wake up I/O sources in DEEP POWER DOWN mode */
+ __IO uint32_t TIMERCFG; /*!< Wake up timers configuration */
+ __IO uint32_t TIMERCOUNT; /*!< Wake up Timer count*/
+ __IO uint32_t POWERCYCLE; /*!< Cancels entry in Low Power mode if set with 0xDEADABBA (might be used by some
+ interrupt handlers)*/
+} LPC_LOWPOWER_T;
+
+/* */
+#define LOWPOWER_POWERCYCLE_CANCELLED 0xDEADABBAUL /*!< */
+
+/**
+ * @brief SRAM Low Power Modes
+ */
+#define LOWPOWER_SRAM_LPMODE_MASK (0xFUL)
+#define LOWPOWER_SRAM_LPMODE_ACTIVE (0x6UL) /*!< SRAM functional mode */
+#define LOWPOWER_SRAM_LPMODE_SLEEP (0xFUL) /*!< SRAM Sleep mode (Data retention, fast wake up) */
+#define LOWPOWER_SRAM_LPMODE_DEEPSLEEP (0x8UL) /*!< SRAM Deep Sleep mode (Data retention, slow wake up) */
+#define LOWPOWER_SRAM_LPMODE_SHUTDOWN (0x9UL) /*!< SRAM Shut Down mode (no data retention) */
+#define LOWPOWER_SRAM_LPMODE_POWERUP (0xAUL) /*!< SRAM is powering up */
+
+/**
+ * @brief Wake up timers configuration in Low Power Modes
+ */
+#define LOWPOWER_TIMERCFG_CTRL_INDEX 0
+#define LOWPOWER_TIMERCFG_CTRL_MASK (0x1UL << LOWPOWER_TIMERCFG_CTRL_INDEX)
+#define LOWPOWER_TIMERCFG_TIMER_INDEX 1
+#define LOWPOWER_TIMERCFG_TIMER_MASK (0x7UL << LOWPOWER_TIMERCFG_TIMER_INDEX)
+#define LOWPOWER_TIMERCFG_OSC32K_INDEX 4
+#define LOWPOWER_TIMERCFG_OSC32K_MASK (0x1UL << LOWPOWER_TIMERCFG_OSC32K_INDEX)
+
+#define LOWPOWER_TIMERCFG_CTRL_DISABLE 0 /*!< Wake Timer Disable */
+#define LOWPOWER_TIMERCFG_CTRL_ENABLE 1 /*!< Wake Timer Enable */
+
+/**
+ * @brief Primary Wake up timers configuration in Low Power Modes
+ */
+#define LOWPOWER_TIMERCFG_TIMER_RTC1KHZ 0 /*!< 1 KHz Real Time Counter (RTC) used as wake up source */
+#define LOWPOWER_TIMERCFG_TIMER_RTC1HZ 1 /*!< 1 Hz Real Time Counter (RTC) used as wake up source */
+#define LOWPOWER_TIMERCFG_TIMER_OSTIMER 2 /*!< OS Event Timer used as wake up source */
+
+#define LOWPOWER_TIMERCFG_OSC32K_FRO32KHZ 0 /*!< Wake up Timers uses FRO 32 KHz as clock source */
+#define LOWPOWER_TIMERCFG_OSC32K_XTAL32KHZ 1 /*!< Wake up Timers uses Chrystal 32 KHz as clock source */
+
+//! @brief Interface for lowpower functions
+typedef struct LowpowerDriverInterface
+{
+ void (*power_cycle_cpu_and_flash)(void);
+ void (*set_lowpower_mode)(LPC_LOWPOWER_T *p_lowpower_cfg);
+} lowpower_driver_interface_t;
+
+/**< DCDC Power Profiles */
+typedef enum
+{
+ DCDC_POWER_PROFILE_LOW, /**< LOW (for CPU frequencies below DCDC_POWER_PROFILE_LOW_MAX_FREQ_HZ) */
+ DCDC_POWER_PROFILE_MEDIUM, /**< MEDIUM (for CPU frequencies between DCDC_POWER_PROFILE_LOW_MAX_FREQ_HZ and
+ DCDC_POWER_PROFILE_MEDIUM_MAX_FREQ_HZ) */
+ DCDC_POWER_PROFILE_HIGH, /**< HIGH (for CPU frequencies between DCDC_POWER_PROFILE_MEDIUM_MAX_FREQ_HZ and
+ DCDC_POWER_PROFILE_HIGH_MAX_FREQ_HZ) */
+} lowpower_dcdc_power_profile_enum;
+
+/**< Manufacturing Process Corners */
+typedef enum
+{
+ PROCESS_CORNER_SSS, /**< Slow Corner Process */
+ PROCESS_CORNER_NNN, /**< Nominal Corner Process */
+ PROCESS_CORNER_FFF, /**< Fast Corner Process */
+ PROCESS_CORNER_OTHERS, /**< SFN, SNF, NFS, Poly Res ... Corner Process */
+} lowpower_process_corner_enum;
+
+/**
+ * @brief DCDC voltage settings
+ */
+typedef enum _v_dcdc
+{
+ V_DCDC_0P950 = 0, /*!< 0.95 V */
+ V_DCDC_0P975 = 1, /*!< 0.975 V */
+ V_DCDC_1P000 = 2, /*!< 1 V */
+ V_DCDC_1P025 = 3, /*!< 1.025 V */
+ V_DCDC_1P050 = 4, /*!< 1.050 V */
+ V_DCDC_1P075 = 5, /*!< 1.075 V */
+ V_DCDC_1P100 = 6, /*!< 1.1 V */
+ V_DCDC_1P125 = 7, /*!< 1.125 V */
+ V_DCDC_1P150 = 8, /*!< 1.150 V */
+ V_DCDC_1P175 = 9, /*!< 1.175 V */
+ V_DCDC_1P200 = 10 /*!< 1.2 V */
+} v_dcdc_t;
+
+/**
+ * @brief Deep Sleep LDO voltage settings
+ */
+typedef enum _v_deepsleep
+{
+ V_DEEPSLEEP_0P900 = 0, /*!< 0.9 V */
+ V_DEEPSLEEP_0P925 = 1, /*!< 0.925 V */
+ V_DEEPSLEEP_0P950 = 2, /*!< 0.95 V */
+ V_DEEPSLEEP_0P975 = 3, /*!< 0.975 V */
+ V_DEEPSLEEP_1P000 = 4, /*!< 1.000 V */
+ V_DEEPSLEEP_1P025 = 5, /*!< 1.025 V */
+ V_DEEPSLEEP_1P050 = 6, /*!< 1.050 V */
+ V_DEEPSLEEP_1P075 = 7 /*!< 1.075 V */
+} v_deepsleep_t;
+
+/**
+ * @brief Always On and Memories LDO voltage settings
+ */
+typedef enum _v_ao
+{
+ V_AO_0P700 = 1, /*!< 0.7 V */
+ V_AO_0P725 = 2, /*!< 0.725 V */
+ V_AO_0P750 = 3, /*!< 0.75 V */
+ V_AO_0P775 = 4, /*!< 0.775 V */
+ V_AO_0P800 = 5, /*!< 0.8 V */
+ V_AO_0P825 = 6, /*!< 0.825 V */
+ V_AO_0P850 = 7, /*!< 0.85 V */
+ V_AO_0P875 = 8, /*!< 0.875 V */
+ V_AO_0P900 = 9, /*!< 0.9 V */
+ V_AO_0P960 = 10, /*!< 0.96 V */
+ V_AO_0P970 = 11, /*!< 0.97 V */
+ V_AO_0P980 = 12, /*!< 0.98 V */
+ V_AO_0P990 = 13, /*!< 0.99 V */
+ V_AO_1P000 = 14, /*!< 1 V */
+ V_AO_1P010 = 15, /*!< 1.01 V */
+ V_AO_1P020 = 16, /*!< 1.02 V */
+ V_AO_1P030 = 17, /*!< 1.03 V */
+ V_AO_1P040 = 18, /*!< 1.04 V */
+ V_AO_1P050 = 19, /*!< 1.05 V */
+ V_AO_1P060 = 20, /*!< 1.06 V */
+ V_AO_1P070 = 21, /*!< 1.07 V */
+ V_AO_1P080 = 22, /*!< 1.08 V */
+ V_AO_1P090 = 23, /*!< 1.09 V */
+ V_AO_1P100 = 24, /*!< 1.1 V */
+ V_AO_1P110 = 25, /*!< 1.11 V */
+ V_AO_1P120 = 26, /*!< 1.12 V */
+ V_AO_1P130 = 27, /*!< 1.13 V */
+ V_AO_1P140 = 28, /*!< 1.14 V */
+ V_AO_1P150 = 29, /*!< 1.15 V */
+ V_AO_1P160 = 30, /*!< 1.16 V */
+ V_AO_1P220 = 31 /*!< 1.22 V */
+} v_ao_t;
+
+/* Low Power modes */
+#define LOWPOWER_CFG_LPMODE_INDEX 0
+#define LOWPOWER_CFG_LPMODE_MASK (0x3UL << LOWPOWER_CFG_LPMODE_INDEX)
+#define LOWPOWER_CFG_SELCLOCK_INDEX 2
+#define LOWPOWER_CFG_SELCLOCK_MASK (0x1UL << LOWPOWER_CFG_SELCLOCK_INDEX)
+#define LOWPOWER_CFG_SELMEMSUPPLY_INDEX 3
+#define LOWPOWER_CFG_SELMEMSUPPLY_MASK (0x1UL << LOWPOWER_CFG_SELMEMSUPPLY_INDEX)
+#define LOWPOWER_CFG_MEMLOWPOWERMODE_INDEX 4
+#define LOWPOWER_CFG_MEMLOWPOWERMODE_MASK (0x1UL << LOWPOWER_CFG_MEMLOWPOWERMODE_INDEX)
+#define LOWPOWER_CFG_LDODEEPSLEEPREF_INDEX 5
+#define LOWPOWER_CFG_LDODEEPSLEEPREF_MASK (0x1UL << LOWPOWER_CFG_LDODEEPSLEEPREF_INDEX)
+
+#define LOWPOWER_CFG_LPMODE_ACTIVE 0 /*!< ACTIVE mode */
+#define LOWPOWER_CFG_LPMODE_DEEPSLEEP 1 /*!< DEEP SLEEP mode */
+#define LOWPOWER_CFG_LPMODE_POWERDOWN 2 /*!< POWER DOWN mode */
+#define LOWPOWER_CFG_LPMODE_DEEPPOWERDOWN 3 /*!< DEEP POWER DOWN mode */
+#define LOWPOWER_CFG_LPMODE_SLEEP 4 /*!< SLEEP mode */
+
+#define LOWPOWER_CFG_SELCLOCK_1MHZ 0 /*!< The 1 MHz clock is used during the configuration of the PMC */
+#define LOWPOWER_CFG_SELCLOCK_12MHZ \
+ 1 /*!< The 12 MHz clock is used during the configuration of the PMC (to speed up PMC configuration process)*/
+
+#define LOWPOWER_CFG_SELMEMSUPPLY_LDOMEM 0 /*!< In DEEP SLEEP power mode, the Memories are supplied by the LDO_MEM */
+#define LOWPOWER_CFG_SELMEMSUPPLY_LDODEEPSLEEP \
+ 1 /*!< In DEEP SLEEP power mode, the Memories are supplied by the LDO_DEEP_SLEEP (or DCDC) */
+
+#define LOWPOWER_CFG_MEMLOWPOWERMODE_SOURCEBIASING \
+ 0 /*!< All SRAM instances use "Source Biasing" as low power mode technic (it is recommended to set LDO_MEM as high \
+ as possible -- 1.1V typical -- during low power mode) */
+#define LOWPOWER_CFG_MEMLOWPOWERMODE_VOLTAGESCALING \
+ 1 /*!< All SRAM instances use "Voltage Scaling" as low power mode technic (it is recommended to set LDO_MEM as low \
+ as possible -- down to 0.7V -- during low power mode) */
+
+#define LOWPOWER_CFG_LDODEEPSLEEPREF_FLASHBUFFER 0 /*!< LDO DEEP SLEEP uses Flash Buffer as reference */
+#define LOWPOWER_CFG_LDODEEPSLEEPREF_BANDGAG0P8V 1 /*!< LDO DEEP SLEEP uses Band Gap 0.8V as reference */
+
+/* CPU Retention Control*/
+#define LOWPOWER_CPURETCTRL_ENA_INDEX 0
+#define LOWPOWER_CPURETCTRL_ENA_MASK (0x1UL << LOWPOWER_CPURETCTRL_ENA_INDEX)
+#define LOWPOWER_CPURETCTRL_MEMBASE_INDEX 1
+#define LOWPOWER_CPURETCTRL_MEMBASE_MASK (0x1FFFUL << LOWPOWER_CPURETCTRL_MEMBASE_INDEX)
+#define LOWPOWER_CPURETCTRL_RETDATALENGTH_INDEX 14
+#define LOWPOWER_CPURETCTRL_RETDATALENGTH_MASK (0x3FFUL << LOWPOWER_CPURETCTRL_RETDATALENGTH_INDEX)
+
+/* Voltgae setting*/
+#define DCDC_POWER_PROFILE_LOW_MAX_FREQ_HZ \
+ (100000000U) /* Maximum System Frequency allowed with DCDC Power Profile LOW */
+#define DCDC_POWER_PROFILE_MEDIUM_MAX_FREQ_HZ \
+ (130000000U) /* Maximum System Frequency allowed with DCDC Power Profile MEDIUM */
+#define DCDC_POWER_PROFILE_HIGH_MAX_FREQ_HZ \
+ (150000000U) /* Maximum System Frequency allowed with DCDC Power Profile HIGH */
+#define PROCESS_NNN_AVG_HZ (19300000U) /* Average Ring OScillator value for Nominal (NNN) Manufacturing Process */
+#define PROCESS_NNN_STD_HZ \
+ (400000U) /* Standard Deviation Ring OScillator value for Nominal (NNN) Manufacturing Process */
+#define PROCESS_NNN_LIMITS \
+ (6U) /* Nominal (NNN) Manufacturing Process Ring Oscillator values limit (with respect to the Average value) */
+#define PROCESS_NNN_MIN_HZ \
+ (PROCESS_NNN_AVG_HZ - \
+ (PROCESS_NNN_LIMITS * \
+ PROCESS_NNN_STD_HZ)) /* Minimum Ring OScillator value for Nominal (NNN) Manufacturing Process */
+#define PROCESS_NNN_MAX_HZ \
+ (PROCESS_NNN_AVG_HZ + \
+ (PROCESS_NNN_LIMITS * \
+ PROCESS_NNN_STD_HZ)) /* Maximum Ring OScillator value for Nominal (NNN) Manufacturing Process */
+#define VOLTAGE_SSS_LOW_MV (1075U) /* Voltage Settings for : Process=SSS, DCDC Power Profile=LOW */
+#define VOLTAGE_SSS_MED_MV (1150U) /* Voltage Settings for : Process=SSS, DCDC Power Profile=MEDIUM */
+#define VOLTAGE_SSS_HIG_MV (1200U) /* Voltage Settings for : Process=SSS, DCDC Power Profile=HIGH */
+#define VOLTAGE_NNN_LOW_MV (1000U) /* Voltage Settings for : Process=NNN, DCDC Power Profile=LOW */
+#define VOLTAGE_NNN_MED_MV (1100U) /* Voltage Settings for : Process=NNN, DCDC Power Profile=MEDIUM */
+#define VOLTAGE_NNN_HIG_MV (1150U) /* Voltage Settings for : Process=NNN, DCDC Power Profile=HIGH */
+#define VOLTAGE_FFF_LOW_MV (1000U) /* Voltage Settings for : Process=FFF, DCDC Power Profile=LOW */
+#define VOLTAGE_FFF_MED_MV (1025U) /* Voltage Settings for : Process=FFF, DCDC Power Profile=MEDIUM */
+#define VOLTAGE_FFF_HIG_MV (1050U) /* Voltage Settings for : Process=FFF, DCDC Power Profile=HIGH */
+
+/**
+ * @brief LDO Voltage control in Low Power Modes
+ */
+#define LOWPOWER_VOLTAGE_LDO_PMU_INDEX 0
+#define LOWPOWER_VOLTAGE_LDO_PMU_MASK (0x1FULL << LOWPOWER_VOLTAGE_LDO_PMU_INDEX)
+#define LOWPOWER_VOLTAGE_LDO_MEM_INDEX 5
+#define LOWPOWER_VOLTAGE_LDO_MEM_MASK (0x1FULL << LOWPOWER_VOLTAGE_LDO_MEM_INDEX)
+#define LOWPOWER_VOLTAGE_LDO_DEEP_SLEEP_INDEX 10
+#define LOWPOWER_VOLTAGE_LDO_DEEP_SLEEP_MASK (0x7ULL << LOWPOWER_VOLTAGE_LDO_DEEP_SLEEP_INDEX)
+#define LOWPOWER_VOLTAGE_LDO_PMU_BOOST_INDEX 19
+#define LOWPOWER_VOLTAGE_LDO_PMU_BOOST_MASK (0x1FULL << LOWPOWER_VOLTAGE_LDO_PMU_BOOST_INDEX)
+#define LOWPOWER_VOLTAGE_LDO_MEM_BOOST_INDEX 24
+#define LOWPOWER_VOLTAGE_LDO_MEM_BOOST_MASK (0x1FULL << LOWPOWER_VOLTAGE_LDO_MEM_BOOST_INDEX)
+#define LOWPOWER_VOLTAGE_DCDC_INDEX 29
+#define LOWPOWER_VOLTAGE_DCDC_MASK (0xFULL << LOWPOWER_VOLTAGE_DCDC_INDEX)
+
+/*! @brief set and clear bit MACRO's. */
+#define U32_SET_BITS(P, B) ((*(uint32_t *)P) |= (B))
+#define U32_CLR_BITS(P, B) ((*(uint32_t *)P) &= ~(B))
+/* Return values from Config (N-2) page of flash */
+#define GET_16MXO_TRIM() (*(uint32_t *)0x9FCC8)
+#define GET_32KXO_TRIM() (*(uint32_t *)0x9FCCC)
+
+#define CPU_RETENTION_RAMX_STORAGE_START_ADDR (0x04006000)
+
+#define XO_SLAVE_EN (1)
+/*******************************************************************************
+ * Codes
+ ******************************************************************************/
+
+/*******************************************************************************
+ * LOCAL FUNCTIONS PROTOTYPES
+ ******************************************************************************/
+static void lf_get_deepsleep_core_supply_cfg(uint32_t exclude_from_pd, uint32_t *dcdc_voltage);
+static uint32_t lf_set_ldo_ao_ldo_mem_voltage(uint32_t p_lp_mode, uint32_t p_dcdc_voltage);
+static uint32_t lf_wakeup_io_ctrl(uint32_t p_wakeup_io_ctrl);
+static uint8_t CLOCK_u8OscCapConvert(uint8_t u8OscCap, uint8_t u8CapBankDiscontinuity);
+
+static void lowpower_set_dcdc_power_profile(lowpower_dcdc_power_profile_enum dcdc_power_profile);
+static lowpower_process_corner_enum lowpower_get_part_process_corner(void);
+static void lowpower_set_voltage_for_process(lowpower_dcdc_power_profile_enum dcdc_power_profile);
+
+/**
+ * @brief Configures and enters in low power mode
+ * @param p_lowpower_cfg: pointer to a structure that contains all low power mode parameters
+ * @return Nothing
+ *
+ * !!! IMPORTANT NOTES :
+ * 1 - CPU Interrupt Enable registers are updated with p_lowpower_cfg->WAKEUPINT. They are NOT restored by the
+ * API.
+ * 2 - The Non Maskable Interrupt (NMI) should be disable before calling this API (otherwise, there is a risk
+ * of Dead Lock).
+ * 3 - The HARD FAULT handler should execute from SRAM. (The Hard fault handler should initiate a full chip
+ * reset)
+ */
+static void POWER_EnterLowPower(LPC_LOWPOWER_T *p_lowpower_cfg);
+
+/**
+ * @brief
+ * @param
+ * @return
+ */
+static void lf_set_dcdc_power_profile_low(void)
+{
+#define DCDC_POWER_PROFILE_LOW_0_ADDRS (0x9FCE0U)
+#define DCDC_POWER_PROFILE_LOW_1_ADDRS (0x9FCE4U)
+
+ uint32_t dcdcTrimValue0 = (*((volatile unsigned int *)(DCDC_POWER_PROFILE_LOW_0_ADDRS)));
+ uint32_t dcdcTrimValue1 = (*((volatile unsigned int *)(DCDC_POWER_PROFILE_LOW_1_ADDRS)));
+
+ if (0UL != (dcdcTrimValue0 & 0x1UL))
+ {
+ PMC->DCDC0 = dcdcTrimValue0 >> 1;
+ PMC->DCDC1 = dcdcTrimValue1;
+ }
+}
+
+/**
+ * @brief Configures and enters in low power mode
+ * @param : p_lowpower_cfg
+ * @return Nothing
+ */
+static void POWER_EnterLowPower(LPC_LOWPOWER_T *p_lowpower_cfg)
+{
+ lowpower_driver_interface_t *s_lowpowerDriver;
+ /* Judging the core and call the corresponding API base address*/
+ if (0UL == Chip_GetVersion())
+ {
+ s_lowpowerDriver = (lowpower_driver_interface_t *)(0x130010d4UL);
+ }
+ else
+ {
+ s_lowpowerDriver = (lowpower_driver_interface_t *)(0x13001204UL);
+ }
+ /* PMC clk set to 12 MHZ */
+ p_lowpower_cfg->CFG |= (uint32_t)LOWPOWER_CFG_SELCLOCK_12MHZ << LOWPOWER_CFG_SELCLOCK_INDEX;
+
+ /* Enable Analog References fast wake-up in case of wake-up from a low power mode (DEEP SLEEP, POWER DOWN and DEEP
+ * POWER DOWN) and Hardware Pin reset */
+ PMC->REFFASTWKUP = (PMC->REFFASTWKUP & (~PMC_REFFASTWKUP_LPWKUP_MASK) & (~PMC_REFFASTWKUP_HWWKUP_MASK)) |
+ PMC_REFFASTWKUP_LPWKUP(1) | PMC_REFFASTWKUP_HWWKUP(1);
+
+ /* SRAM uses Voltage Scaling in all Low Power modes */
+ PMC->SRAMCTRL = (PMC->SRAMCTRL & (~PMC_SRAMCTRL_SMB_MASK)) | PMC_SRAMCTRL_SMB(3);
+
+ /* CPU Retention configuration : preserve the value of FUNCRETENTIONCTRL.RET_LENTH which is a Hardware defined
+ * parameter. */
+ p_lowpower_cfg->CPURETCTRL = (SYSCON->FUNCRETENTIONCTRL & SYSCON_FUNCRETENTIONCTRL_RET_LENTH_MASK) |
+ (p_lowpower_cfg->CPURETCTRL & (~SYSCON_FUNCRETENTIONCTRL_RET_LENTH_MASK));
+
+ /* Switch System Clock to FRO12Mhz (the configuration before calling this function will not be restored back) */
+ CLOCK_AttachClk(kFRO12M_to_MAIN_CLK); /* Switch main clock to FRO12MHz */
+ CLOCK_SetClkDiv(kCLOCK_DivAhbClk, 1U, false); /* Main clock divided by 1 */
+ SYSCON->FMCCR = (SYSCON->FMCCR & 0xFFFF0000UL) | 0x201AUL; /* Adjust FMC waiting time cycles */
+ lf_set_dcdc_power_profile_low(); /* Align DCDC Power profile with the 12 MHz clock (DCDC Power Profile LOW) */
+
+ (*(s_lowpowerDriver->set_lowpower_mode))(p_lowpower_cfg);
+
+ /* Restore the configuration of the MISCCTRL Register : LOWPWR_FLASH_BUF = 0, LDOMEMBLEEDDSLP = 0, LDOMEMHIGHZMODE =
+ * 0 */
+ PMC->MISCCTRL &= (~PMC_MISCCTRL_LOWPWR_FLASH_BUF_MASK) & (~PMC_MISCCTRL_DISABLE_BLEED_MASK) &
+ (~PMC_MISCCTRL_LDOMEMHIGHZMODE_MASK);
+}
+
+/**
+ * @brief Shut off the Flash and execute the _WFI(), then power up the Flash after wake-up event
+ * @param None
+ * @return Nothing
+ */
+void POWER_CycleCpuAndFlash(void)
+{
+ /* Judging the core and call the corresponding API base address*/
+ lowpower_driver_interface_t *s_lowpowerDriver;
+ if (0UL == Chip_GetVersion())
+ {
+ s_lowpowerDriver = (lowpower_driver_interface_t *)(0x130010d4UL);
+ }
+ else
+ {
+ s_lowpowerDriver = (lowpower_driver_interface_t *)(0x13001204UL);
+ }
+ (*(s_lowpowerDriver->power_cycle_cpu_and_flash))();
+};
+
+/**
+ * brief PMC Deep Sleep function call
+ * return nothing
+ */
+void POWER_EnterDeepSleep(uint32_t exclude_from_pd,
+ uint32_t sram_retention_ctrl,
+ uint64_t wakeup_interrupts,
+ uint32_t hardware_wake_ctrl)
+{
+ LPC_LOWPOWER_T lv_low_power_mode_cfg; /* Low Power Mode configuration structure */
+ uint32_t cpu0_nmi_enable;
+ uint32_t cpu0_int_enable_0;
+ uint32_t cpu0_int_enable_1;
+ uint32_t dcdc_voltage;
+ uint32_t pmc_reset_ctrl;
+ /* Clear Low Power Mode configuration variable */
+ (void)memset(&lv_low_power_mode_cfg, 0x0, sizeof(LPC_LOWPOWER_T));
+
+ /* Configure Low Power Mode configuration variable */
+ lv_low_power_mode_cfg.CFG |= (uint32_t)LOWPOWER_CFG_LPMODE_DEEPSLEEP
+ << LOWPOWER_CFG_LPMODE_INDEX; /* DEEPSLEEP mode */
+
+ lf_get_deepsleep_core_supply_cfg(exclude_from_pd, &dcdc_voltage);
+
+ if (((exclude_from_pd & (uint32_t)kPDRUNCFG_PD_USB1_PHY) != 0UL) &&
+ ((exclude_from_pd & (uint32_t)kPDRUNCFG_PD_LDOUSBHS) != 0UL))
+ {
+ /* USB High Speed is required as wake-up source in Deep Sleep mode: make sure LDO FLASH NV stays powered during
+ * deep-sleep */
+ exclude_from_pd = exclude_from_pd | (uint32_t)kPDRUNCFG_PD_LDOFLASHNV;
+ }
+
+ /* DCDC will be always used during Deep Sleep (instead of LDO Deep Sleep); Make sure LDO MEM & Analog references
+ * will stay powered, Shut down ROM */
+ lv_low_power_mode_cfg.PDCTRL0 = (~exclude_from_pd & ~(uint32_t)kPDRUNCFG_PD_DCDC & ~(uint32_t)kPDRUNCFG_PD_LDOMEM &
+ ~(uint32_t)kPDRUNCFG_PD_BIAS) |
+ (uint32_t)kPDRUNCFG_PD_LDODEEPSLEEP | (uint32_t)kPDRUNCFG_PD_ROM;
+
+ /* Voltage control in DeepSleep Low Power Modes */
+ /* The Memories Voltage settings below are for voltage scaling */
+ lv_low_power_mode_cfg.VOLTAGE = lf_set_ldo_ao_ldo_mem_voltage(LOWPOWER_CFG_LPMODE_POWERDOWN, dcdc_voltage);
+
+ /* SRAM retention control during POWERDOWN */
+ lv_low_power_mode_cfg.SRAMRETCTRL = sram_retention_ctrl;
+
+ /* CPU Wake up & Interrupt sources control */
+ lv_low_power_mode_cfg.WAKEUPINT = wakeup_interrupts;
+ lv_low_power_mode_cfg.WAKEUPSRC = wakeup_interrupts;
+
+ /* Interrupts that allow DMA transfers with Flexcomm without waking up the Processor */
+ if (0UL != (hardware_wake_ctrl & (LOWPOWER_HWWAKE_PERIPHERALS | LOWPOWER_HWWAKE_SDMA0 | LOWPOWER_HWWAKE_SDMA1)))
+ {
+ lv_low_power_mode_cfg.HWWAKE = (hardware_wake_ctrl & ~LOWPOWER_HWWAKE_FORCED) | LOWPOWER_HWWAKE_ENABLE_FRO192M;
+ }
+
+ cpu0_nmi_enable = SYSCON->NMISRC & SYSCON_NMISRC_NMIENCPU0_MASK; /* Save the configuration of the NMI Register */
+ SYSCON->NMISRC &= ~SYSCON_NMISRC_NMIENCPU0_MASK; /* Disable NMI of CPU0 */
+
+ /* Save the configuration of the CPU interrupt enable Registers (because they are overwritten inside the low power
+ * API */
+ cpu0_int_enable_0 = NVIC->ISER[0];
+ cpu0_int_enable_1 = NVIC->ISER[1];
+
+ pmc_reset_ctrl = PMC->RESETCTRL;
+ if (0UL != (pmc_reset_ctrl & PMC_RESETCTRL_BODCORERESETENABLE_MASK))
+ {
+ /* BoD CORE reset is activated, so make sure BoD Core won't be shutdown */
+ lv_low_power_mode_cfg.PDCTRL0 &= ~(uint32_t)kPDRUNCFG_PD_BODCORE;
+ }
+ if (0UL != (pmc_reset_ctrl & PMC_RESETCTRL_BODVBATRESETENABLE_MASK))
+ {
+ /* BoD VBAT reset is activated, so make sure BoD VBAT won't be shutdown */
+ lv_low_power_mode_cfg.PDCTRL0 &= ~(uint32_t)kPDRUNCFG_PD_BODVBAT;
+ }
+
+ /* Enter low power mode */
+ POWER_EnterLowPower(&lv_low_power_mode_cfg);
+
+ /* Restore the configuration of the NMI Register */
+ SYSCON->NMISRC |= cpu0_nmi_enable;
+
+ /* Restore the configuration of the CPU interrupt enable Registers (because they have been overwritten inside the
+ * low power API */
+ NVIC->ISER[0] = cpu0_int_enable_0;
+ NVIC->ISER[1] = cpu0_int_enable_1;
+}
+
+/**
+ * brief PMC power Down function call
+ * return nothing
+ */
+void POWER_EnterPowerDown(uint32_t exclude_from_pd,
+ uint32_t sram_retention_ctrl,
+ uint64_t wakeup_interrupts,
+ uint32_t cpu_retention_ctrl)
+{
+ LPC_LOWPOWER_T lv_low_power_mode_cfg; /* Low Power Mode configuration structure */
+ uint32_t cpu0_nmi_enable;
+ uint32_t cpu0_int_enable_0;
+ uint32_t cpu0_int_enable_1;
+ uint64_t wakeup_src_int;
+ uint32_t pmc_reset_ctrl;
+
+ uint32_t analog_ctrl_regs[12]; /* To store Analog Controller Regristers */
+
+ /* Clear Low Power Mode configuration variable */
+ (void)memset(&lv_low_power_mode_cfg, 0x0, sizeof(LPC_LOWPOWER_T));
+
+ /* Configure Low Power Mode configuration variable */
+ lv_low_power_mode_cfg.CFG |= (uint32_t)LOWPOWER_CFG_LPMODE_POWERDOWN
+ << LOWPOWER_CFG_LPMODE_INDEX; /* POWER DOWN mode */
+
+ /* Only FRO32K, XTAL32K, COMP, BIAS and LDO_MEM can be stay powered during POWERDOWN (valid from application point
+ * of view; Hardware allows BODVBAT, LDODEEPSLEEP and FRO1M to stay powered, that's why they are excluded below) */
+ lv_low_power_mode_cfg.PDCTRL0 = (~exclude_from_pd) | (uint32_t)kPDRUNCFG_PD_BODVBAT | (uint32_t)kPDRUNCFG_PD_FRO1M |
+ (uint32_t)kPDRUNCFG_PD_LDODEEPSLEEP;
+
+ /* SRAM retention control during POWERDOWN */
+ lv_low_power_mode_cfg.SRAMRETCTRL = sram_retention_ctrl;
+
+ /* Sanity check: If retention is required for any of SRAM instances, make sure LDO MEM will stay powered */
+ if ((sram_retention_ctrl & 0x7FFFUL) != 0UL)
+ {
+ lv_low_power_mode_cfg.PDCTRL0 &= ~(uint32_t)kPDRUNCFG_PD_LDOMEM;
+ }
+
+ /* Voltage control in Low Power Modes */
+ /* The Memories Voltage settings below are for voltage scaling */
+ lv_low_power_mode_cfg.VOLTAGE = lf_set_ldo_ao_ldo_mem_voltage(LOWPOWER_CFG_LPMODE_POWERDOWN, 0);
+
+ /* CPU0 retention Ctrl.
+ * For the time being, we do not allow customer to relocate the CPU retention area in SRAMX, meaning that the
+ * retention area range is [0x0400_6000 - 0x0400_6600] (beginning of RAMX2) If required by customer,
+ * cpu_retention_ctrl[13:1] will be used for that to modify the default retention area
+ */
+ lv_low_power_mode_cfg.CPURETCTRL =
+ (cpu_retention_ctrl & LOWPOWER_CPURETCTRL_ENA_MASK) |
+ ((((uint32_t)CPU_RETENTION_RAMX_STORAGE_START_ADDR >> 2UL) << LOWPOWER_CPURETCTRL_MEMBASE_INDEX) &
+ LOWPOWER_CPURETCTRL_MEMBASE_MASK);
+ if (0UL != (cpu_retention_ctrl & 0x1UL))
+ {
+ /* CPU retention is required: store Analog Controller Registers */
+ analog_ctrl_regs[0] = ANACTRL->FRO192M_CTRL;
+ analog_ctrl_regs[1] = ANACTRL->ANALOG_CTRL_CFG;
+ analog_ctrl_regs[2] = ANACTRL->ADC_CTRL;
+ analog_ctrl_regs[3] = ANACTRL->XO32M_CTRL;
+ analog_ctrl_regs[4] = ANACTRL->BOD_DCDC_INT_CTRL;
+ analog_ctrl_regs[5] = ANACTRL->RINGO0_CTRL;
+ analog_ctrl_regs[6] = ANACTRL->RINGO1_CTRL;
+ analog_ctrl_regs[7] = ANACTRL->RINGO2_CTRL;
+ analog_ctrl_regs[8] = ANACTRL->LDO_XO32M;
+ analog_ctrl_regs[9] = ANACTRL->AUX_BIAS;
+ analog_ctrl_regs[10] = ANACTRL->USBHS_PHY_CTRL;
+ analog_ctrl_regs[11] = ANACTRL->USBHS_PHY_TRIM;
+ }
+
+ /* CPU Wake up & Interrupt sources control : only WAKEUP_GPIO_GLOBALINT0, WAKEUP_GPIO_GLOBALINT1, WAKEUP_FLEXCOMM3,
+ * WAKEUP_ACMP_CAPT, WAKEUP_RTC_LITE_ALARM_WAKEUP, WAKEUP_OS_EVENT_TIMER, WAKEUP_ALLWAKEUPIOS */
+ wakeup_src_int = (uint64_t)(WAKEUP_GPIO_GLOBALINT0 | WAKEUP_GPIO_GLOBALINT1 | WAKEUP_FLEXCOMM3 | WAKEUP_ACMP_CAPT |
+ WAKEUP_RTC_LITE_ALARM_WAKEUP | WAKEUP_OS_EVENT_TIMER | WAKEUP_ALLWAKEUPIOS);
+ lv_low_power_mode_cfg.WAKEUPINT = wakeup_interrupts & wakeup_src_int;
+ lv_low_power_mode_cfg.WAKEUPSRC = wakeup_interrupts & wakeup_src_int;
+
+ cpu0_nmi_enable = SYSCON->NMISRC & SYSCON_NMISRC_NMIENCPU0_MASK; /* Save the configuration of the NMI Register */
+ SYSCON->NMISRC &= ~SYSCON_NMISRC_NMIENCPU0_MASK; /* Disable NMI of CPU0 */
+
+ /* Save the configuration of the CPU interrupt enable Registers (because they are overwritten inside the low power
+ * API */
+ cpu0_int_enable_0 = NVIC->ISER[0];
+ cpu0_int_enable_1 = NVIC->ISER[1];
+
+ pmc_reset_ctrl = PMC->RESETCTRL;
+ /* Disable BoD VBAT and BoD Core resets */
+ PMC->RESETCTRL =
+ pmc_reset_ctrl & (~(PMC_RESETCTRL_BODVBATRESETENABLE_MASK | PMC_RESETCTRL_BODCORERESETENABLE_MASK));
+
+ /* Enter low power mode */
+ POWER_EnterLowPower(&lv_low_power_mode_cfg);
+
+ /*** We'll reach this point in case of POWERDOWN with CPU retention or if the POWERDOWN has not been taken (for
+ instance because an interrupt is pending). In case of CPU retention, assumption is that the SRAM containing the
+ stack used to call this function shall be preserved during low power ***/
+
+ /* Restore the configuration of the NMI Register */
+ SYSCON->NMISRC |= cpu0_nmi_enable;
+
+ /* Restore PMC RESETCTRL register */
+ PMC->RESETCTRL = pmc_reset_ctrl;
+
+ /* Restore the configuration of the CPU interrupt enable Registers (because they have been overwritten inside the
+ * low power API */
+ NVIC->ISER[0] = cpu0_int_enable_0;
+ NVIC->ISER[1] = cpu0_int_enable_1;
+
+ if (0UL != (cpu_retention_ctrl & 0x1UL))
+ {
+ /* Restore Analog Controller Registers */
+ ANACTRL->FRO192M_CTRL = analog_ctrl_regs[0] | ANACTRL_FRO192M_CTRL_WRTRIM_MASK;
+ ANACTRL->ANALOG_CTRL_CFG = analog_ctrl_regs[1];
+ ANACTRL->ADC_CTRL = analog_ctrl_regs[2];
+ ANACTRL->XO32M_CTRL = analog_ctrl_regs[3];
+ ANACTRL->BOD_DCDC_INT_CTRL = analog_ctrl_regs[4];
+ ANACTRL->RINGO0_CTRL = analog_ctrl_regs[5];
+ ANACTRL->RINGO1_CTRL = analog_ctrl_regs[6];
+ ANACTRL->RINGO2_CTRL = analog_ctrl_regs[7];
+ ANACTRL->LDO_XO32M = analog_ctrl_regs[8];
+ ANACTRL->AUX_BIAS = analog_ctrl_regs[9];
+ ANACTRL->USBHS_PHY_CTRL = analog_ctrl_regs[10];
+ ANACTRL->USBHS_PHY_TRIM = analog_ctrl_regs[11];
+ }
+}
+
+/**
+ * brief PMC Deep Sleep Power Down function call
+ * return nothing
+ */
+void POWER_EnterDeepPowerDown(uint32_t exclude_from_pd,
+ uint32_t sram_retention_ctrl,
+ uint64_t wakeup_interrupts,
+ uint32_t wakeup_io_ctrl)
+{
+ LPC_LOWPOWER_T lv_low_power_mode_cfg; /* Low Power Mode configuration structure */
+ uint32_t cpu0_nmi_enable;
+ uint32_t cpu0_int_enable_0;
+ uint32_t cpu0_int_enable_1;
+ uint32_t pmc_reset_ctrl;
+
+ /* Clear Low Power Mode configuration variable */
+ (void)memset(&lv_low_power_mode_cfg, 0x0, sizeof(LPC_LOWPOWER_T));
+
+ /* Configure Low Power Mode configuration variable */
+ lv_low_power_mode_cfg.CFG |= (uint32_t)LOWPOWER_CFG_LPMODE_DEEPPOWERDOWN
+ << LOWPOWER_CFG_LPMODE_INDEX; /* DEEP POWER DOWN mode */
+
+ /* Only FRO32K, XTAL32K and LDO_MEM can be stay powered during DEEPPOWERDOWN (valid from application point of view;
+ * Hardware allows BODVBAT, BIAS FRO1M and COMP to stay powered, that's why they are excluded below) */
+ lv_low_power_mode_cfg.PDCTRL0 = (~exclude_from_pd) | (uint32_t)kPDRUNCFG_PD_BIAS | (uint32_t)kPDRUNCFG_PD_BODVBAT |
+ (uint32_t)kPDRUNCFG_PD_FRO1M | (uint32_t)kPDRUNCFG_PD_COMP;
+
+ /* SRAM retention control during DEEPPOWERDOWN */
+ sram_retention_ctrl =
+ sram_retention_ctrl &
+ (~(LOWPOWER_SRAMRETCTRL_RETEN_RAMX0 | LOWPOWER_SRAMRETCTRL_RETEN_RAMX1 | LOWPOWER_SRAMRETCTRL_RETEN_RAM00));
+
+ /* SRAM retention control during DEEPPOWERDOWN */
+ lv_low_power_mode_cfg.SRAMRETCTRL = sram_retention_ctrl;
+
+ /* Sanity check: If retention is required for any of SRAM instances, make sure LDO MEM will stay powered */
+ if ((sram_retention_ctrl & 0x7FFFUL) != 0UL)
+ {
+ lv_low_power_mode_cfg.PDCTRL0 &= ~(uint32_t)kPDRUNCFG_PD_LDOMEM;
+ }
+
+ /* Voltage control in Low Power Modes */
+ /* The Memories Voltage settings below are for voltage scaling */
+ lv_low_power_mode_cfg.VOLTAGE = lf_set_ldo_ao_ldo_mem_voltage(LOWPOWER_CFG_LPMODE_DEEPPOWERDOWN, 0);
+
+ lv_low_power_mode_cfg.WAKEUPINT =
+ wakeup_interrupts & (WAKEUP_RTC_LITE_ALARM_WAKEUP |
+ WAKEUP_OS_EVENT_TIMER); /* CPU Wake up sources control : only WAKEUP_RTC_LITE_ALARM_WAKEUP,
+ WAKEUP_OS_EVENT_TIMER */
+ lv_low_power_mode_cfg.WAKEUPSRC =
+ wakeup_interrupts &
+ (WAKEUP_RTC_LITE_ALARM_WAKEUP | WAKEUP_OS_EVENT_TIMER |
+ WAKEUP_ALLWAKEUPIOS); /*!< Hardware Wake up sources control: : only WAKEUP_RTC_LITE_ALARM_WAKEUP,
+ WAKEUP_OS_EVENT_TIMER and WAKEUP_ALLWAKEUPIOS */
+
+ /* Wake up I/O sources */
+ lv_low_power_mode_cfg.WAKEUPIOSRC = lf_wakeup_io_ctrl(wakeup_io_ctrl);
+
+ cpu0_nmi_enable = SYSCON->NMISRC & SYSCON_NMISRC_NMIENCPU0_MASK; /* Save the configuration of the NMI Register */
+ SYSCON->NMISRC &= ~SYSCON_NMISRC_NMIENCPU0_MASK; /* Disable NMI of CPU0 */
+
+ /* Save the configuration of the CPU interrupt enable Registers */
+ cpu0_int_enable_0 = NVIC->ISER[0];
+ cpu0_int_enable_1 = NVIC->ISER[1];
+
+ /* Save the configuration of the PMC RESETCTRL register */
+ pmc_reset_ctrl = PMC->RESETCTRL;
+ /* Disable BoD VBAT and BoD Core resets */
+ PMC->RESETCTRL =
+ pmc_reset_ctrl & (~(PMC_RESETCTRL_BODVBATRESETENABLE_MASK | PMC_RESETCTRL_BODCORERESETENABLE_MASK));
+
+ /* Disable LDO MEM bleed current */
+ // PMC->MISCCTRL |= PMC_MISCCTRL_DISABLE_BLEED_MASK;
+
+ /* Enter low power mode */
+ POWER_EnterLowPower(&lv_low_power_mode_cfg);
+
+ /* Restore the configuration of the NMI Register */
+ SYSCON->NMISRC |= cpu0_nmi_enable;
+
+ /* Restore PMC RESETCTRL register */
+ PMC->RESETCTRL = pmc_reset_ctrl;
+
+ /* Restore the configuration of the CPU interrupt enable Registers */
+ NVIC->ISER[0] = cpu0_int_enable_0;
+ NVIC->ISER[1] = cpu0_int_enable_1;
+}
+
+/**
+ * brief PMC Sleep function call
+ * return nothing
+ */
+void POWER_EnterSleep(void)
+{
+ uint32_t pmsk;
+ pmsk = __get_PRIMASK();
+ __disable_irq();
+ SCB->SCR &= ~SCB_SCR_SLEEPDEEP_Msk;
+ __WFI();
+ __set_PRIMASK(pmsk);
+}
+
+/**
+ * @brief Get Digital Core logic supply source to be used during Deep Sleep.
+ * @param [in] exclude_from_pd: COmpoenents NOT to be powered down during Deep Sleep
+ * @param [out] core_supply: 0 = LDO DEEPSLEEP will be used / 1 = DCDC will be used
+ * @param [out] dcdc_voltage: as defined by V_DCDC_* in fsl_power.h
+
+ * @return Nothing
+ */
+static void lf_get_deepsleep_core_supply_cfg(uint32_t exclude_from_pd, uint32_t *dcdc_voltage)
+{
+ *dcdc_voltage = (uint32_t)V_DCDC_0P950; /* Default value */
+
+ if (((exclude_from_pd & (uint32_t)kPDRUNCFG_PD_USB1_PHY) != 0UL) &&
+ ((exclude_from_pd & (uint32_t)kPDRUNCFG_PD_LDOUSBHS) != 0UL))
+ {
+ /* USB High Speed is required as wake-up source in Deep Sleep mode */
+ PMC->MISCCTRL |= PMC_MISCCTRL_LOWPWR_FLASH_BUF_MASK; /* Force flash buffer in low power mode */
+ *dcdc_voltage =
+ (uint32_t)V_DCDC_1P000; /* Set DCDC voltage to be 1.000 V (USB HS IP cannot work below 0.990 V) */
+ }
+}
+
+/**
+ * @brief
+ * @param
+ * @return
+ */
+static uint32_t lf_set_ldo_ao_ldo_mem_voltage(uint32_t p_lp_mode, uint32_t p_dcdc_voltage)
+{
+#define FLASH_NMPA_LDO_AO_ADDRS (0x9FCF4U)
+#define FLASH_NMPA_LDO_AO_DSLP_TRIM_VALID_MASK (0x100U)
+#define FLASH_NMPA_LDO_AO_DSLP_TRIM_MASK (0x3E00U)
+#define FLASH_NMPA_LDO_AO_DSLP_TRIM_SHIFT (9U)
+#define FLASH_NMPA_LDO_AO_PDWN_TRIM_VALID_MASK (0x10000U)
+#define FLASH_NMPA_LDO_AO_PDWN_TRIM_MASK (0x3E0000U)
+#define FLASH_NMPA_LDO_AO_PDWN_TRIM_SHIFT (17U)
+#define FLASH_NMPA_LDO_AO_DPDW_TRIM_VALID_MASK (0x1000000U)
+#define FLASH_NMPA_LDO_AO_DPDW_TRIM_MASK (0x3E000000U)
+#define FLASH_NMPA_LDO_AO_DPDW_TRIM_SHIFT (25U)
+
+ uint32_t ldo_ao_trim, voltage;
+ uint32_t lv_v_ldo_pmu, lv_v_ldo_pmu_boost;
+
+ ldo_ao_trim = (*((volatile unsigned int *)(FLASH_NMPA_LDO_AO_ADDRS)));
+
+ switch (p_lp_mode)
+ {
+ case LOWPOWER_CFG_LPMODE_DEEPSLEEP:
+ {
+ if ((ldo_ao_trim & FLASH_NMPA_LDO_AO_DSLP_TRIM_VALID_MASK) != 0UL)
+ {
+ /* Apply settings coming from Flash */
+ lv_v_ldo_pmu = (ldo_ao_trim & FLASH_NMPA_LDO_AO_DSLP_TRIM_MASK) >> FLASH_NMPA_LDO_AO_DSLP_TRIM_SHIFT;
+ lv_v_ldo_pmu_boost = lv_v_ldo_pmu - 2UL; /* - 50 mV */
+ }
+ else
+ {
+ /* Apply default settings */
+ lv_v_ldo_pmu = (uint32_t)V_AO_0P900;
+ lv_v_ldo_pmu_boost = (uint32_t)V_AO_0P850;
+ }
+ }
+ break;
+
+ case LOWPOWER_CFG_LPMODE_POWERDOWN:
+ {
+ if ((ldo_ao_trim & FLASH_NMPA_LDO_AO_PDWN_TRIM_VALID_MASK) != 0UL)
+ {
+ /* Apply settings coming from Flash */
+ lv_v_ldo_pmu = (ldo_ao_trim & FLASH_NMPA_LDO_AO_PDWN_TRIM_MASK) >> FLASH_NMPA_LDO_AO_PDWN_TRIM_SHIFT;
+ lv_v_ldo_pmu_boost = lv_v_ldo_pmu - 2UL; /* - 50 mV */
+ }
+ else
+ {
+ /* Apply default settings */
+ lv_v_ldo_pmu = (uint32_t)V_AO_0P800;
+ lv_v_ldo_pmu_boost = (uint32_t)V_AO_0P750;
+ }
+ }
+ break;
+
+ case LOWPOWER_CFG_LPMODE_DEEPPOWERDOWN:
+ {
+ if ((ldo_ao_trim & FLASH_NMPA_LDO_AO_DPDW_TRIM_VALID_MASK) != 0UL)
+ {
+ /* Apply settings coming from Flash */
+ lv_v_ldo_pmu = (ldo_ao_trim & FLASH_NMPA_LDO_AO_DPDW_TRIM_MASK) >> FLASH_NMPA_LDO_AO_DPDW_TRIM_SHIFT;
+ lv_v_ldo_pmu_boost = lv_v_ldo_pmu - 2UL; /* - 50 mV */
+ }
+ else
+ {
+ /* Apply default settings */
+ lv_v_ldo_pmu = (uint32_t)V_AO_0P800;
+ lv_v_ldo_pmu_boost = (uint32_t)V_AO_0P750;
+ }
+ }
+ break;
+
+ default:
+ /* Should never reach this point */
+ lv_v_ldo_pmu = (uint32_t)V_AO_1P100;
+ lv_v_ldo_pmu_boost = (uint32_t)V_AO_1P050;
+ break;
+ }
+
+ /* The Memories Voltage settings below are for voltage scaling */
+ voltage =
+ (lv_v_ldo_pmu << LOWPOWER_VOLTAGE_LDO_PMU_INDEX) | /* */
+ (lv_v_ldo_pmu_boost << LOWPOWER_VOLTAGE_LDO_PMU_BOOST_INDEX) | /* */
+ ((uint32_t)V_AO_0P750 << LOWPOWER_VOLTAGE_LDO_MEM_INDEX) | /* Set to 0.75V (voltage Scaling) */
+ ((uint32_t)V_AO_0P700 << LOWPOWER_VOLTAGE_LDO_MEM_BOOST_INDEX) | /* Set to 0.7V (voltage Scaling) */
+ ((uint32_t)V_DEEPSLEEP_0P900
+ << LOWPOWER_VOLTAGE_LDO_DEEP_SLEEP_INDEX) | /* Set to 0.90 V (Not used because LDO_DEEP_SLEEP is disabled)*/
+ (p_dcdc_voltage << LOWPOWER_VOLTAGE_DCDC_INDEX) /* */
+ ;
+
+ return (voltage);
+}
+
+/**
+ * @brief
+ * @param
+ * @return
+ */
+static uint32_t lf_wakeup_io_ctrl(uint32_t p_wakeup_io_ctrl)
+{
+ uint32_t wake_up_type;
+ uint32_t misc_ctrl_reg;
+ uint8_t use_external_pullupdown = 0;
+
+ /* Configure Pull up & Pull down based on the required wake-up edge */
+ CLOCK_EnableClock(kCLOCK_Iocon);
+
+ misc_ctrl_reg = 0UL;
+
+ /* Wake-up I/O 0 */
+ wake_up_type = (p_wakeup_io_ctrl & 0x3UL) >> LOWPOWER_WAKEUPIOSRC_PIO0_INDEX;
+ use_external_pullupdown = (uint8_t)((p_wakeup_io_ctrl & LOWPOWER_WAKEUPIO_PIO0_USEEXTERNALPULLUPDOWN_MASK) >>
+ LOWPOWER_WAKEUPIO_PIO0_USEEXTERNALPULLUPDOWN_INDEX);
+
+ if (use_external_pullupdown == 0UL)
+ {
+ if ((wake_up_type == 1UL) || (wake_up_type == 3UL))
+ {
+ /* Rising edge and both rising and falling edges */
+ IOCON->PIO[1][1] = IOCON_PIO_DIGIMODE(1) | IOCON_PIO_MODE(1); /* Pull down */
+ misc_ctrl_reg |= LOWPOWER_WAKEUPIO_PIO0_PULLUPDOWN_MASK;
+ p_wakeup_io_ctrl &= ~LOWPOWER_WAKEUPIO_PIO0_PULLUPDOWN_MASK;
+ }
+ else
+ {
+ if (wake_up_type == 2UL)
+ {
+ /* Falling edge only */
+ IOCON->PIO[1][1] = IOCON_PIO_DIGIMODE(1) | IOCON_PIO_MODE(2); /* Pull up */
+ misc_ctrl_reg &= ~LOWPOWER_WAKEUPIO_PIO0_PULLUPDOWN_MASK;
+ p_wakeup_io_ctrl |= LOWPOWER_WAKEUPIO_PIO0_PULLUPDOWN_MASK;
+ }
+ else
+ {
+ /* Wake-up I/O is disabled : set it as required by the user */
+ if ((p_wakeup_io_ctrl & LOWPOWER_WAKEUPIO_PIO0_DISABLEPULLUPDOWN_MASK) != 0UL)
+ {
+ /* Wake-up I/O is configured as Plain Input */
+ p_wakeup_io_ctrl &= ~LOWPOWER_WAKEUPIO_PIO0_PULLUPDOWN_MASK;
+ }
+ else
+ {
+ /* Wake-up I/O is configured as pull-up or pull-down */
+ misc_ctrl_reg |= (~p_wakeup_io_ctrl) & LOWPOWER_WAKEUPIO_PIO0_PULLUPDOWN_MASK;
+ }
+ }
+ }
+ }
+ else
+ {
+ /* MISCCTRL[8]:WAKEUPIOCTRL[8]:00 -no pullup,pulldown, 10 - pulldown, 01 - pullup, 11 - reserved */
+ p_wakeup_io_ctrl &= ~LOWPOWER_WAKEUPIO_PIO0_PULLUPDOWN_MASK;
+ misc_ctrl_reg &= ~LOWPOWER_WAKEUPIO_PIO0_PULLUPDOWN_MASK;
+ }
+
+ /* Wake-up I/O 1 */
+ wake_up_type = (p_wakeup_io_ctrl & 0xCUL) >> LOWPOWER_WAKEUPIOSRC_PIO1_INDEX;
+ use_external_pullupdown = (uint8_t)((p_wakeup_io_ctrl & LOWPOWER_WAKEUPIO_PIO1_USEEXTERNALPULLUPDOWN_MASK) >>
+ LOWPOWER_WAKEUPIO_PIO1_USEEXTERNALPULLUPDOWN_INDEX);
+
+ if (use_external_pullupdown == 0UL)
+ {
+ if ((wake_up_type == 1UL) || (wake_up_type == 3UL))
+ {
+ /* Rising edge and both rising and falling edges */
+ IOCON->PIO[0][28] = IOCON_PIO_DIGIMODE(1) | IOCON_PIO_MODE(1); /* Pull down */
+ misc_ctrl_reg |= LOWPOWER_WAKEUPIO_PIO1_PULLUPDOWN_MASK;
+ p_wakeup_io_ctrl &= ~LOWPOWER_WAKEUPIO_PIO1_PULLUPDOWN_MASK;
+ }
+ else
+ {
+ if (wake_up_type == 2UL)
+ {
+ /* Falling edge only */
+ IOCON->PIO[0][28] = IOCON_PIO_DIGIMODE(1) | IOCON_PIO_MODE(2); /* Pull up */
+ misc_ctrl_reg &= ~LOWPOWER_WAKEUPIO_PIO1_PULLUPDOWN_MASK;
+ p_wakeup_io_ctrl |= LOWPOWER_WAKEUPIO_PIO1_PULLUPDOWN_MASK;
+ }
+ else
+ {
+ /* Wake-up I/O is disabled : set it as required by the user */
+ if ((p_wakeup_io_ctrl & LOWPOWER_WAKEUPIO_PIO1_DISABLEPULLUPDOWN_MASK) != 0UL)
+ {
+ /* Wake-up I/O is configured as Plain Input */
+ p_wakeup_io_ctrl &= ~LOWPOWER_WAKEUPIO_PIO1_PULLUPDOWN_MASK;
+ }
+ else
+ {
+ /* Wake-up I/O is configured as pull-up or pull-down */
+ misc_ctrl_reg |= (~p_wakeup_io_ctrl) & LOWPOWER_WAKEUPIO_PIO1_PULLUPDOWN_MASK;
+ }
+ }
+ }
+ }
+ else
+ {
+ /* MISCCTRL[9]:WAKEUPIOCTRL[9]:00 -no pullup,pulldown, 10 - pulldown, 01 - pullup, 11 - reserved */
+ p_wakeup_io_ctrl &= ~LOWPOWER_WAKEUPIO_PIO1_PULLUPDOWN_MASK;
+ misc_ctrl_reg &= ~LOWPOWER_WAKEUPIO_PIO1_PULLUPDOWN_MASK;
+ }
+
+ /* Wake-up I/O 2 */
+ wake_up_type = (p_wakeup_io_ctrl & 0x30UL) >> LOWPOWER_WAKEUPIOSRC_PIO2_INDEX;
+ use_external_pullupdown = (uint8_t)((p_wakeup_io_ctrl & LOWPOWER_WAKEUPIO_PIO2_USEEXTERNALPULLUPDOWN_MASK) >>
+ LOWPOWER_WAKEUPIO_PIO2_USEEXTERNALPULLUPDOWN_INDEX);
+
+ if (use_external_pullupdown == 0UL)
+ {
+ if ((wake_up_type == 1UL) || (wake_up_type == 3UL))
+ {
+ /* Rising edge and both rising and falling edges */
+ IOCON->PIO[1][18] = IOCON_PIO_DIGIMODE(1) | IOCON_PIO_MODE(1); /* Pull down */
+ misc_ctrl_reg |= LOWPOWER_WAKEUPIO_PIO2_PULLUPDOWN_MASK;
+ p_wakeup_io_ctrl &= ~LOWPOWER_WAKEUPIO_PIO2_PULLUPDOWN_MASK;
+ }
+ else
+ {
+ if (wake_up_type == 2UL)
+ {
+ /* Falling edge only */
+ IOCON->PIO[1][18] = IOCON_PIO_DIGIMODE(1) | IOCON_PIO_MODE(2); /* Pull up */
+ misc_ctrl_reg &= ~LOWPOWER_WAKEUPIO_PIO2_PULLUPDOWN_MASK;
+ p_wakeup_io_ctrl |= LOWPOWER_WAKEUPIO_PIO2_PULLUPDOWN_MASK;
+ }
+ else
+ {
+ /* Wake-up I/O is disabled : set it as required by the user */
+ if ((p_wakeup_io_ctrl & LOWPOWER_WAKEUPIO_PIO2_DISABLEPULLUPDOWN_MASK) != 0UL)
+ {
+ /* Wake-up I/O is configured as Plain Input */
+ p_wakeup_io_ctrl &= ~LOWPOWER_WAKEUPIO_PIO2_PULLUPDOWN_MASK;
+ }
+ else
+ {
+ /* Wake-up I/O is configured as pull-up or pull-down */
+ misc_ctrl_reg |= (~p_wakeup_io_ctrl) & LOWPOWER_WAKEUPIO_PIO2_PULLUPDOWN_MASK;
+ }
+ }
+ }
+ }
+ else
+ {
+ /* MISCCTRL[10]:WAKEUPIOCTRL[10]:00 -no pullup,pulldown, 10 - pulldown, 01 - pullup, 11 - reserved */
+ p_wakeup_io_ctrl &= ~LOWPOWER_WAKEUPIO_PIO2_PULLUPDOWN_MASK;
+ misc_ctrl_reg &= ~LOWPOWER_WAKEUPIO_PIO2_PULLUPDOWN_MASK;
+ }
+
+ /* Wake-up I/O 3 */
+ wake_up_type = (p_wakeup_io_ctrl & 0xC0UL) >> LOWPOWER_WAKEUPIOSRC_PIO3_INDEX;
+ use_external_pullupdown = (uint8_t)((p_wakeup_io_ctrl & LOWPOWER_WAKEUPIO_PIO3_USEEXTERNALPULLUPDOWN_MASK) >>
+ LOWPOWER_WAKEUPIO_PIO3_USEEXTERNALPULLUPDOWN_INDEX);
+
+ if (use_external_pullupdown == 0UL)
+ {
+ if ((wake_up_type == 1UL) || (wake_up_type == 3UL))
+ {
+ /* Rising edge and both rising and falling edges */
+ IOCON->PIO[1][30] = IOCON_PIO_DIGIMODE(1) | IOCON_PIO_MODE(1); /* Pull down */
+ misc_ctrl_reg |= LOWPOWER_WAKEUPIO_PIO3_PULLUPDOWN_MASK;
+ p_wakeup_io_ctrl &= ~LOWPOWER_WAKEUPIO_PIO3_PULLUPDOWN_MASK;
+ }
+ else
+ {
+ if (wake_up_type == 2UL)
+ {
+ /* Falling edge only */
+ IOCON->PIO[1][30] = IOCON_PIO_DIGIMODE(1) | IOCON_PIO_MODE(2); /* Pull up */
+ misc_ctrl_reg &= ~LOWPOWER_WAKEUPIO_PIO3_PULLUPDOWN_MASK;
+ p_wakeup_io_ctrl |= LOWPOWER_WAKEUPIO_PIO3_PULLUPDOWN_MASK;
+ }
+ else
+ {
+ /* Wake-up I/O is disabled : set it as required by the user */
+ if ((p_wakeup_io_ctrl & LOWPOWER_WAKEUPIO_PIO3_DISABLEPULLUPDOWN_MASK) != 0UL)
+ {
+ /* Wake-up I/O is configured as Plain Input */
+ p_wakeup_io_ctrl &= ~LOWPOWER_WAKEUPIO_PIO3_PULLUPDOWN_MASK;
+ }
+ else
+ {
+ /* Wake-up I/O is configured as pull-up or pull-down */
+ misc_ctrl_reg |= (~p_wakeup_io_ctrl) & LOWPOWER_WAKEUPIO_PIO3_PULLUPDOWN_MASK;
+ }
+ }
+ }
+ }
+ else
+ {
+ /* MISCCTRL[11]:WAKEUPIOCTRL[11]:00 -no pullup,pulldown, 10 - pulldown, 01 - pullup, 11 - reserved */
+ p_wakeup_io_ctrl &= ~LOWPOWER_WAKEUPIO_PIO3_PULLUPDOWN_MASK;
+ misc_ctrl_reg &= ~LOWPOWER_WAKEUPIO_PIO3_PULLUPDOWN_MASK;
+ }
+
+ PMC->MISCCTRL = (PMC->MISCCTRL & 0xFFFFF0FFUL) | misc_ctrl_reg;
+ PMC->WAKEUPIOCTRL = p_wakeup_io_ctrl & 0xFFFUL;
+
+ /*
+ * Defined according to :
+ * - LOWPOWER_WAKEUPIOSRC_<DISABLE,RISING,FALLING,RISING_FALLING> in fsl_power.h
+ * - LOWPOWER_WAKEUPIO_PIO0_PULLUPDOWN_<...> in fsl_power.h
+ */
+ return (p_wakeup_io_ctrl & 0xFFFUL);
+}
+
+/**
+ * @brief
+ * @param
+ * @return
+ */
+static uint8_t CLOCK_u8OscCapConvert(uint8_t u8OscCap, uint8_t u8CapBankDiscontinuity)
+{
+ /* Compensate for discontinuity in the capacitor banks */
+ if (u8OscCap < 64U)
+ {
+ if (u8OscCap >= u8CapBankDiscontinuity)
+ {
+ u8OscCap -= u8CapBankDiscontinuity;
+ }
+ else
+ {
+ u8OscCap = 0U;
+ }
+ }
+ else
+ {
+ if (u8OscCap <= (127U - u8CapBankDiscontinuity))
+ {
+ u8OscCap += u8CapBankDiscontinuity;
+ }
+ else
+ {
+ u8OscCap = 127U;
+ }
+ }
+ return u8OscCap;
+}
+
+/**
+ * @brief Described in fsl_common.h
+ * @param
+ * @return
+ */
+static void lowpower_set_system_voltage(uint32_t system_voltage_mv)
+{
+ /*
+ * Set system voltage
+ */
+ uint32_t lv_ldo_ao = (uint32_t)V_AO_1P100; /* <ldo_ao> */
+ uint32_t lv_ldo_ao_boost = (uint32_t)V_AO_1P150; /* <ldo_ao_boost> */
+ uint32_t lv_dcdc = (uint32_t)V_DCDC_1P100; /* <dcdc> */
+
+ if (system_voltage_mv <= 950UL)
+ {
+ lv_dcdc = (uint32_t)V_DCDC_0P950;
+ lv_ldo_ao = (uint32_t)V_AO_0P960;
+ lv_ldo_ao_boost = (uint32_t)V_AO_1P010;
+ }
+ else if (system_voltage_mv <= 975UL)
+ {
+ lv_dcdc = (uint32_t)V_DCDC_0P975;
+ lv_ldo_ao = (uint32_t)V_AO_0P980;
+ lv_ldo_ao_boost = (uint32_t)V_AO_1P030;
+ }
+ else if (system_voltage_mv <= 1000UL)
+ {
+ lv_dcdc = (uint32_t)V_DCDC_1P000;
+ lv_ldo_ao = (uint32_t)V_AO_1P000;
+ lv_ldo_ao_boost = (uint32_t)V_AO_1P050;
+ }
+ else if (system_voltage_mv <= 1025UL)
+ {
+ lv_dcdc = (uint32_t)V_DCDC_1P025;
+ lv_ldo_ao = (uint32_t)V_AO_1P030;
+ lv_ldo_ao_boost = (uint32_t)V_AO_1P080;
+ }
+ else if (system_voltage_mv <= 1050UL)
+ {
+ lv_dcdc = (uint32_t)V_DCDC_1P050;
+ lv_ldo_ao = (uint32_t)V_AO_1P060;
+ lv_ldo_ao_boost = (uint32_t)V_AO_1P110;
+ }
+ else if (system_voltage_mv <= 1075UL)
+ {
+ lv_dcdc = (uint32_t)V_DCDC_1P075;
+ lv_ldo_ao = (uint32_t)V_AO_1P080;
+ lv_ldo_ao_boost = (uint32_t)V_AO_1P130;
+ }
+ else if (system_voltage_mv <= 1100UL)
+ {
+ lv_dcdc = (uint32_t)V_DCDC_1P100;
+ lv_ldo_ao = (uint32_t)V_AO_1P100;
+ lv_ldo_ao_boost = (uint32_t)V_AO_1P150;
+ }
+ else if (system_voltage_mv <= 1125UL)
+ {
+ lv_dcdc = (uint32_t)V_DCDC_1P125;
+ lv_ldo_ao = (uint32_t)V_AO_1P130;
+ lv_ldo_ao_boost = (uint32_t)V_AO_1P160;
+ }
+ else if (system_voltage_mv <= 1150UL)
+ {
+ lv_dcdc = (uint32_t)V_DCDC_1P150;
+ lv_ldo_ao = (uint32_t)V_AO_1P160;
+ lv_ldo_ao_boost = (uint32_t)V_AO_1P220;
+ }
+ else if (system_voltage_mv <= 1175UL)
+ {
+ lv_dcdc = (uint32_t)V_DCDC_1P175;
+ lv_ldo_ao = (uint32_t)V_AO_1P160;
+ lv_ldo_ao_boost = (uint32_t)V_AO_1P220;
+ }
+ else
+ {
+ lv_dcdc = (uint32_t)V_DCDC_1P200;
+ lv_ldo_ao = (uint32_t)V_AO_1P160;
+ lv_ldo_ao_boost = (uint32_t)V_AO_1P220;
+ }
+
+ /* Set up LDO Always-On voltages */
+ PMC->LDOPMU = (PMC->LDOPMU & (~PMC_LDOPMU_VADJ_MASK) & (~PMC_LDOPMU_VADJ_BOOST_MASK)) | PMC_LDOPMU_VADJ(lv_ldo_ao) |
+ PMC_LDOPMU_VADJ_BOOST(lv_ldo_ao_boost);
+
+ /* Set up DCDC voltage */
+ PMC->DCDC0 = (PMC->DCDC0 & (~PMC_DCDC0_VOUT_MASK)) | PMC_DCDC0_VOUT(lv_dcdc);
+}
+
+/**
+ * @brief Described in fsl_common.h
+ * @param
+ * @return
+ */
+static void lowpower_set_dcdc_power_profile(lowpower_dcdc_power_profile_enum dcdc_power_profile)
+{
+#define FLASH_NMPA_BASE (0x9FC00u)
+#define FLASH_NMPA_DCDC_POWER_PROFILE_LOW_0_ADDRS (FLASH_NMPA_BASE + 0xE0U) // (0x9FCE0U)
+#define FLASH_NMPA_DCDC_POWER_PROFILE_LOW_1_ADDRS (FLASH_NMPA_BASE + 0xE4U) // (0x9FCE4U)
+#define FLASH_NMPA_DCDC_POWER_PROFILE_MEDIUM_0_ADDRS (FLASH_NMPA_BASE + 0xE8U) // (0x9FCE8U)
+#define FLASH_NMPA_DCDC_POWER_PROFILE_MEDIUM_1_ADDRS (FLASH_NMPA_BASE + 0xECU) // (0x9FCECU)
+#define FLASH_NMPA_DCDC_POWER_PROFILE_HIGH_0_ADDRS (FLASH_NMPA_BASE + 0xD8U) // (0x9FCD8U)
+#define FLASH_NMPA_DCDC_POWER_PROFILE_HIGH_1_ADDRS (FLASH_NMPA_BASE + 0xDCU) // (0x9FCDCU)
+
+ const uint32_t PMC_DCDC0_DEFAULT = 0x010C4E68;
+ const uint32_t PMC_DCDC1_DEFAULT = 0x01803A98;
+
+ uint32_t dcdcTrimValue0;
+ uint32_t dcdcTrimValue1;
+
+ switch (dcdc_power_profile)
+ {
+ case DCDC_POWER_PROFILE_LOW:
+ /* Low */
+ dcdcTrimValue0 = (*((volatile unsigned int *)(FLASH_NMPA_DCDC_POWER_PROFILE_LOW_0_ADDRS)));
+ dcdcTrimValue1 = (*((volatile unsigned int *)(FLASH_NMPA_DCDC_POWER_PROFILE_LOW_1_ADDRS)));
+
+ if (0UL != (dcdcTrimValue0 & 0x1UL))
+ {
+ dcdcTrimValue0 = dcdcTrimValue0 >> 1;
+
+ PMC->DCDC0 = dcdcTrimValue0;
+ PMC->DCDC1 = dcdcTrimValue1;
+#if (defined(NIOBE_DEBUG_LEVEL) && (NIOBE_DEBUG_LEVEL >= 1))
+ PRINTF(
+ "\nINFO : DCDC Power Profile set to "
+ "LOW"
+ "\n");
+#endif
+ }
+ break;
+
+ case DCDC_POWER_PROFILE_MEDIUM:
+ /* Medium */
+ dcdcTrimValue0 = (*((volatile unsigned int *)(FLASH_NMPA_DCDC_POWER_PROFILE_MEDIUM_0_ADDRS)));
+ dcdcTrimValue1 = (*((volatile unsigned int *)(FLASH_NMPA_DCDC_POWER_PROFILE_MEDIUM_1_ADDRS)));
+
+ if (0UL != (dcdcTrimValue0 & 0x1UL))
+ {
+ dcdcTrimValue0 = dcdcTrimValue0 >> 1;
+
+ PMC->DCDC0 = dcdcTrimValue0;
+ PMC->DCDC1 = dcdcTrimValue1;
+#if (defined(NIOBE_DEBUG_LEVEL) && (NIOBE_DEBUG_LEVEL >= 1))
+ PRINTF(
+ "\nINFO : DCDC Power Profile set to "
+ "MEDIUM"
+ "\n");
+#endif
+ }
+ break;
+
+ case DCDC_POWER_PROFILE_HIGH:
+ /* High */
+ dcdcTrimValue0 = (*((volatile unsigned int *)(FLASH_NMPA_DCDC_POWER_PROFILE_HIGH_0_ADDRS)));
+ dcdcTrimValue1 = (*((volatile unsigned int *)(FLASH_NMPA_DCDC_POWER_PROFILE_HIGH_1_ADDRS)));
+
+ if (0UL != (dcdcTrimValue0 & 0x1UL))
+ {
+ dcdcTrimValue0 = dcdcTrimValue0 >> 1;
+
+ PMC->DCDC0 = dcdcTrimValue0;
+ PMC->DCDC1 = dcdcTrimValue1;
+#if (defined(NIOBE_DEBUG_LEVEL) && (NIOBE_DEBUG_LEVEL >= 1))
+ PRINTF(
+ "\nINFO : DCDC Power Profile set to "
+ "HIGH"
+ "\n");
+#endif
+ }
+ break;
+
+ default:
+ /* Low */
+ PMC->DCDC0 = PMC_DCDC0_DEFAULT;
+ PMC->DCDC1 = PMC_DCDC1_DEFAULT;
+#if (defined(NIOBE_DEBUG_LEVEL) && (NIOBE_DEBUG_LEVEL >= 1))
+ PRINTF(
+ "\nINFO : DCDC Power Profile set to "
+ "LOW"
+ "\n");
+#endif
+ break;
+ }
+}
+
+/**
+ * @brief
+ * @param
+ * @return
+ */
+static lowpower_process_corner_enum lowpower_get_part_process_corner(void)
+{
+#define FLASH_NMPA_PVT_MONITOR_0_RINGO_ADDRS (FLASH_NMPA_BASE + 0x130U)
+#define FLASH_NMPA_PVT_MONITOR_1_RINGO_ADDRS (FLASH_NMPA_BASE + 0x140U)
+
+ lowpower_process_corner_enum part_process_corner;
+ uint32_t pvt_ringo_hz;
+ uint32_t pvt_ringo_0 = (*((volatile unsigned int *)(FLASH_NMPA_PVT_MONITOR_0_RINGO_ADDRS)));
+ uint32_t pvt_ringo_1 = (*((volatile unsigned int *)(FLASH_NMPA_PVT_MONITOR_1_RINGO_ADDRS)));
+
+ /*
+ * Check that the PVT Monitors Trimmings in flash are valid.
+ */
+ if (0UL != (pvt_ringo_0 & 0x1UL))
+ {
+ /* PVT Trimmings in Flash are valid */
+ pvt_ringo_0 = pvt_ringo_0 >> 1;
+ }
+ else
+ {
+ /* PVT Trimmings in Flash are NOT valid (average value assumed) */
+ pvt_ringo_0 = PROCESS_NNN_AVG_HZ;
+ }
+
+ if (0UL != (pvt_ringo_1 & 0x1UL))
+ {
+ /* PVT Trimmings in Flash are valid */
+ pvt_ringo_1 = pvt_ringo_1 >> 1;
+ }
+ else
+ {
+ /* PVT Trimmings in Flash are NOT valid (average value assumed) */
+ pvt_ringo_1 = PROCESS_NNN_AVG_HZ;
+ }
+
+ if (pvt_ringo_1 <= pvt_ringo_0)
+ {
+ pvt_ringo_hz = pvt_ringo_1;
+ }
+ else
+ {
+ pvt_ringo_hz = pvt_ringo_0;
+ }
+
+ /*
+ * Determine the process corner based on the value of the Ring Oscillator frequency
+ */
+ if (pvt_ringo_hz <= PROCESS_NNN_MIN_HZ)
+ {
+ /* SSS Process Corner */
+ part_process_corner = PROCESS_CORNER_SSS;
+#if (defined(NIOBE_DEBUG_LEVEL) && (NIOBE_DEBUG_LEVEL >= 1))
+ PRINTF(
+ "\nINFO : Process Corner : "
+ "SSS"
+ "\n");
+#endif
+ }
+ else
+ {
+ if (pvt_ringo_hz <= PROCESS_NNN_MAX_HZ)
+ {
+ /* NNN Process Corner */
+ part_process_corner = PROCESS_CORNER_NNN;
+#if (defined(NIOBE_DEBUG_LEVEL) && (NIOBE_DEBUG_LEVEL >= 1))
+ PRINTF(
+ "\nINFO : Process Corner : "
+ "NNN"
+ "\n");
+#endif
+ }
+ else
+ {
+ /* FFF Process Corner */
+ part_process_corner = PROCESS_CORNER_FFF;
+#if (defined(NIOBE_DEBUG_LEVEL) && (NIOBE_DEBUG_LEVEL >= 1))
+ PRINTF(
+ "\nINFO : Process Corner : "
+ "FFF"
+ "\n");
+#endif
+ }
+ }
+
+ return (part_process_corner);
+}
+
+/**
+ * @brief Described in fsl_common.h
+ * @param
+ * @return
+ */
+static void lowpower_set_voltage_for_process(lowpower_dcdc_power_profile_enum dcdc_power_profile)
+{
+ /* Get Sample Process Corner */
+ lowpower_process_corner_enum part_process_corner = lowpower_get_part_process_corner();
+
+ switch (part_process_corner)
+ {
+ case PROCESS_CORNER_SSS:
+ /* Slow Corner */
+ {
+ switch (dcdc_power_profile)
+ {
+ case DCDC_POWER_PROFILE_MEDIUM:
+ /* Medium */
+ lowpower_set_system_voltage(VOLTAGE_SSS_MED_MV);
+ break;
+
+ case DCDC_POWER_PROFILE_HIGH:
+ /* High */
+ lowpower_set_system_voltage(VOLTAGE_SSS_HIG_MV);
+ break;
+
+ default:
+ /* DCDC_POWER_PROFILE_LOW */
+ lowpower_set_system_voltage(VOLTAGE_SSS_LOW_MV);
+ break;
+ } // switch(dcdc_power_profile)
+ }
+ break;
+
+ case PROCESS_CORNER_FFF:
+ /* Fast Corner */
+ {
+ switch (dcdc_power_profile)
+ {
+ case DCDC_POWER_PROFILE_MEDIUM:
+ /* Medium */
+ lowpower_set_system_voltage(VOLTAGE_FFF_MED_MV);
+ break;
+
+ case DCDC_POWER_PROFILE_HIGH:
+ /* High */
+ lowpower_set_system_voltage(VOLTAGE_FFF_HIG_MV);
+ break;
+
+ default:
+ /* DCDC_POWER_PROFILE_LOW */
+ lowpower_set_system_voltage(VOLTAGE_FFF_LOW_MV);
+ break;
+ } // switch(dcdc_power_profile)
+ }
+ break;
+
+ default:
+ /* Nominal (NNN) and all others Process Corners : assume Nominal Corner */
+ {
+ switch (dcdc_power_profile)
+ {
+ case DCDC_POWER_PROFILE_MEDIUM:
+ /* Medium */
+ lowpower_set_system_voltage(VOLTAGE_NNN_MED_MV);
+ break;
+
+ case DCDC_POWER_PROFILE_HIGH:
+ /* High */
+ lowpower_set_system_voltage(VOLTAGE_NNN_HIG_MV);
+ break;
+
+ default:
+ /* DCDC_POWER_PROFILE_LOW */
+ lowpower_set_system_voltage(VOLTAGE_NNN_LOW_MV);
+ break;
+ } // switch(dcdc_power_profile)
+ break;
+ }
+ } // switch(part_process_corner)
+}
+
+/**
+ * @brief Described in fsl_common.h
+ * @param
+ * @return
+ */
+void POWER_SetVoltageForFreq(uint32_t system_freq_hz)
+{
+ if (system_freq_hz <= DCDC_POWER_PROFILE_LOW_MAX_FREQ_HZ)
+ {
+ /* [0 Hz - DCDC_POWER_PROFILE_LOW_MAX_FREQ_HZ Hz] */
+ lowpower_set_dcdc_power_profile(DCDC_POWER_PROFILE_LOW); /* DCDC VOUT = 1.05 V by default */
+ lowpower_set_voltage_for_process(DCDC_POWER_PROFILE_LOW);
+ }
+ else
+ {
+ if (system_freq_hz <= DCDC_POWER_PROFILE_MEDIUM_MAX_FREQ_HZ)
+ {
+ /* ]DCDC_POWER_PROFILE_LOW_MAX_FREQ_HZ Hz - DCDC_POWER_PROFILE_MEDIUM_MAX_FREQ_HZ Hz] */
+ lowpower_set_dcdc_power_profile(DCDC_POWER_PROFILE_MEDIUM); /* DCDC VOUT = 1.15 V by default */
+ lowpower_set_voltage_for_process(DCDC_POWER_PROFILE_MEDIUM);
+ }
+ else
+ {
+ /* > DCDC_POWER_PROFILE_MEDIUM_MAX_FREQ_HZ Hz */
+ lowpower_set_dcdc_power_profile(DCDC_POWER_PROFILE_HIGH); /* DCDC VOUT = 1.2 V by default */
+ lowpower_set_voltage_for_process(DCDC_POWER_PROFILE_HIGH);
+ }
+ }
+}
+
+void POWER_Xtal16mhzCapabankTrim(int32_t pi32_16MfXtalIecLoadpF_x100,
+ int32_t pi32_16MfXtalPPcbParCappF_x100,
+ int32_t pi32_16MfXtalNPcbParCappF_x100)
+{
+ uint32_t u32XOTrimValue;
+ uint8_t u8IECXinCapCal6pF, u8IECXinCapCal8pF, u8IECXoutCapCal6pF, u8IECXoutCapCal8pF, u8XOSlave;
+ int32_t iaXin_x4, ibXin, iaXout_x4, ibXout;
+ int32_t iXOCapInpF_x100, iXOCapOutpF_x100;
+ uint8_t u8XOCapInCtrl, u8XOCapOutCtrl;
+ uint32_t u32RegVal;
+ int32_t i32Tmp;
+
+ /* Enable and set LDO, if not already done */
+ POWER_SetXtal16mhzLdo();
+ /* Get Cal values from Flash */
+ u32XOTrimValue = GET_16MXO_TRIM();
+ /* Check validity and apply */
+ if ((0UL != (u32XOTrimValue & 1UL)) && (0UL != ((u32XOTrimValue >> 15UL) & 1UL)))
+ {
+ /* These fields are 7 bits, unsigned */
+ u8IECXinCapCal6pF = (uint8_t)((u32XOTrimValue >> 1UL) & 0x7fUL);
+ u8IECXinCapCal8pF = (uint8_t)((u32XOTrimValue >> 8UL) & 0x7fUL);
+ u8IECXoutCapCal6pF = (uint8_t)((u32XOTrimValue >> 16UL) & 0x7fUL);
+ u8IECXoutCapCal8pF = (uint8_t)((u32XOTrimValue >> 23UL) & 0x7fUL);
+ /* This field is 1 bit */
+ u8XOSlave = (uint8_t)((u32XOTrimValue >> 30UL) & 0x1UL);
+ /* Linear fit coefficients calculation */
+ iaXin_x4 = (int)u8IECXinCapCal8pF - (int)u8IECXinCapCal6pF;
+ ibXin = (int)u8IECXinCapCal6pF - iaXin_x4 * 3;
+ iaXout_x4 = (int)u8IECXoutCapCal8pF - (int)u8IECXoutCapCal6pF;
+ ibXout = (int)u8IECXoutCapCal6pF - iaXout_x4 * 3;
+ }
+ else
+ {
+ iaXin_x4 = 20; // gain in LSB/pF
+ ibXin = -9; // offset in LSB
+ iaXout_x4 = 20; // gain in LSB/pF
+ ibXout = -13; // offset in LSB
+ u8XOSlave = 0;
+ }
+ /* In & out load cap calculation with derating */
+ iXOCapInpF_x100 = 2 * pi32_16MfXtalIecLoadpF_x100 - pi32_16MfXtalNPcbParCappF_x100 +
+ 39 * ((int32_t)XO_SLAVE_EN - (int32_t)u8XOSlave) - 15;
+ iXOCapOutpF_x100 = 2 * pi32_16MfXtalIecLoadpF_x100 - pi32_16MfXtalPPcbParCappF_x100 - 21;
+ /* In & out XO_OSC_CAP_Code_CTRL calculation, with rounding */
+ i32Tmp = ((iXOCapInpF_x100 * iaXin_x4 + ibXin * 400) + 200) / 400;
+ u8XOCapInCtrl = (uint8_t)i32Tmp;
+ i32Tmp = ((iXOCapOutpF_x100 * iaXout_x4 + ibXout * 400) + 200) / 400;
+ u8XOCapOutCtrl = (uint8_t)i32Tmp;
+ /* Read register and clear fields to be written */
+ u32RegVal = ANACTRL->XO32M_CTRL;
+ u32RegVal &= ~(ANACTRL_XO32M_CTRL_OSC_CAP_IN_MASK | ANACTRL_XO32M_CTRL_OSC_CAP_OUT_MASK);
+ /* Configuration of 32 MHz XO output buffers */
+#if (XO_SLAVE_EN == 0)
+ u32RegVal &= ~(ANACTRL_XO32M_CTRL_SLAVE_MASK | ANACTRL_XO32M_CTRL_ACBUF_PASS_ENABLE_MASK);
+#else
+ u32RegVal |= ANACTRL_XO32M_CTRL_SLAVE_MASK | ANACTRL_XO32M_CTRL_ACBUF_PASS_ENABLE_MASK;
+#endif
+ /* XO_OSC_CAP_Code_CTRL to XO_OSC_CAP_Code conversion */
+ u32RegVal |= (uint32_t)CLOCK_u8OscCapConvert(u8XOCapInCtrl, 13) << ANACTRL_XO32M_CTRL_OSC_CAP_IN_SHIFT;
+ u32RegVal |= (uint32_t)CLOCK_u8OscCapConvert(u8XOCapOutCtrl, 13) << ANACTRL_XO32M_CTRL_OSC_CAP_OUT_SHIFT;
+ /* Write back to register */
+ ANACTRL->XO32M_CTRL = u32RegVal;
+}
+
+void POWER_Xtal32khzCapabankTrim(int32_t pi32_32kfXtalIecLoadpF_x100,
+ int32_t pi32_32kfXtalPPcbParCappF_x100,
+ int32_t pi32_32kfXtalNPcbParCappF_x100)
+{
+ uint32_t u32XOTrimValue;
+ uint8_t u8IECXinCapCal6pF, u8IECXinCapCal8pF, u8IECXoutCapCal6pF, u8IECXoutCapCal8pF;
+ int32_t iaXin_x4, ibXin, iaXout_x4, ibXout;
+ int32_t iXOCapInpF_x100, iXOCapOutpF_x100;
+ uint8_t u8XOCapInCtrl, u8XOCapOutCtrl;
+ uint32_t u32RegVal;
+ int32_t i32Tmp;
+ /* Get Cal values from Flash */
+ u32XOTrimValue = GET_32KXO_TRIM();
+ /* check validity and apply */
+ if ((0UL != (u32XOTrimValue & 1UL)) && (0UL != ((u32XOTrimValue >> 15UL) & 1UL)))
+ {
+ /* These fields are 7 bits, unsigned */
+ u8IECXinCapCal6pF = (uint8_t)((u32XOTrimValue >> 1UL) & 0x7fUL);
+ u8IECXinCapCal8pF = (uint8_t)((u32XOTrimValue >> 8UL) & 0x7fUL);
+ u8IECXoutCapCal6pF = (uint8_t)((u32XOTrimValue >> 16UL) & 0x7fUL);
+ u8IECXoutCapCal8pF = (uint8_t)((u32XOTrimValue >> 23UL) & 0x7fUL);
+ /* Linear fit coefficients calculation */
+ iaXin_x4 = (int)u8IECXinCapCal8pF - (int)u8IECXinCapCal6pF;
+ ibXin = (int)u8IECXinCapCal6pF - iaXin_x4 * 3;
+ iaXout_x4 = (int)u8IECXoutCapCal8pF - (int)u8IECXoutCapCal6pF;
+ ibXout = (int)u8IECXoutCapCal6pF - iaXout_x4 * 3;
+ }
+ else
+ {
+ iaXin_x4 = 16; // gain in LSB/pF
+ ibXin = 12; // offset in LSB
+ iaXout_x4 = 16; // gain in LSB/pF
+ ibXout = 11; // offset in LSB
+ }
+
+ /* In & out load cap calculation with derating */
+ iXOCapInpF_x100 = 2 * pi32_32kfXtalIecLoadpF_x100 - pi32_32kfXtalNPcbParCappF_x100 - 130;
+ iXOCapOutpF_x100 = 2 * pi32_32kfXtalIecLoadpF_x100 - pi32_32kfXtalPPcbParCappF_x100 - 41;
+
+ /* In & out XO_OSC_CAP_Code_CTRL calculation, with rounding */
+ i32Tmp = ((iXOCapInpF_x100 * iaXin_x4 + ibXin * 400) + 200) / 400;
+ u8XOCapInCtrl = (uint8_t)i32Tmp;
+ i32Tmp = ((iXOCapOutpF_x100 * iaXout_x4 + ibXout * 400) + 200) / 400;
+ u8XOCapOutCtrl = (uint8_t)i32Tmp;
+
+ /* Read register and clear fields to be written */
+ u32RegVal = PMC->XTAL32K;
+ u32RegVal &= ~(PMC_XTAL32K_CAPBANKIN_MASK | PMC_XTAL32K_CAPBANKOUT_MASK);
+
+ /* XO_OSC_CAP_Code_CTRL to XO_OSC_CAP_Code conversion */
+ u32RegVal |= (uint32_t)CLOCK_u8OscCapConvert(u8XOCapInCtrl, 23) << PMC_XTAL32K_CAPBANKIN_SHIFT;
+ u32RegVal |= (uint32_t)CLOCK_u8OscCapConvert(u8XOCapOutCtrl, 23) << PMC_XTAL32K_CAPBANKOUT_SHIFT;
+
+ /* Write back to register */
+ PMC->XTAL32K = u32RegVal;
+}
+
+void POWER_SetXtal16mhzLdo(void)
+{
+ uint32_t temp;
+ const uint32_t u32Mask =
+ (ANACTRL_LDO_XO32M_VOUT_MASK | ANACTRL_LDO_XO32M_IBIAS_MASK | ANACTRL_LDO_XO32M_STABMODE_MASK);
+
+ const uint32_t u32Value =
+ (ANACTRL_LDO_XO32M_VOUT(0x5) | ANACTRL_LDO_XO32M_IBIAS(0x2) | ANACTRL_LDO_XO32M_STABMODE(0x1));
+
+ /* Enable & set-up XTAL 32 MHz clock LDO */
+ temp = ANACTRL->LDO_XO32M;
+
+ if ((temp & u32Mask) != u32Value)
+ {
+ temp &= ~u32Mask;
+
+ /*
+ * Enable the XTAL32M LDO
+ * Adjust the output voltage level, 0x5 for 1.1V
+ * Adjust the biasing current, 0x2 value
+ * Stability configuration, 0x1 default mode
+ */
+ temp |= u32Value;
+
+ ANACTRL->LDO_XO32M = temp;
+
+ /* Delay for LDO to be up */
+ // CLOCK_uDelay(20);
+ }
+
+ /* Enable LDO XO32M */
+ PMC->PDRUNCFGCLR0 = PMC_PDRUNCFG0_PDEN_LDOXO32M_MASK;
+}
+
+/**
+ * @brief Return some key information related to the device reset causes / wake-up sources, for all power modes.
+ * @param p_reset_cause : the device reset cause, according to the definition of power_device_reset_cause_t type.
+ * @param p_boot_mode : the device boot mode, according to the definition of power_device_boot_mode_t type.
+ * @param p_wakeupio_cause: the wake-up pin sources, according to the definition of register PMC->WAKEIOCAUSE[3:0].
+
+ * @return Nothing
+ *
+ * !!! IMPORTANT ERRATA - IMPORTANT ERRATA - IMPORTANT ERRATA !!!
+ * !!! valid ONLY for LPC55S69 (not for LPC55S16 and LPC55S06) !!!
+ * !!! when FALLING EDGE DETECTION is enabled on wake-up pins: !!!
+ * - 1. p_wakeupio_cause is NOT ACCURATE
+ * - 2. Spurious kRESET_CAUSE_DPDRESET_WAKEUPIO* event is reported when
+ * several wake-up sources are enabled during DEEP-POWER-DOWN
+ * (like enabling wake-up on RTC and Falling edge wake-up pins)
+ *
+ */
+void POWER_GetWakeUpCause(power_device_reset_cause_t *p_reset_cause,
+ power_device_boot_mode_t *p_boot_mode,
+ uint32_t *p_wakeupio_cause)
+{
+ uint32_t reset_cause_reg;
+ uint32_t boot_mode_reg;
+
+#if (defined(LPC55S06_SERIES) || defined(LPC55S04_SERIES) || defined(LPC5506_SERIES) || defined(LPC5504_SERIES) || \
+ defined(LPC5502_SERIES) || defined(LPC55S16_SERIES) || defined(LPC55S14_SERIES) || defined(LPC5516_SERIES) || \
+ defined(LPC5514_SERIES) || defined(LPC5512_SERIES))
+ reset_cause_reg = (PMC->AOREG1) & 0x3FF0UL;
+#else /* LPC55S69/28 */
+ reset_cause_reg = (PMC->AOREG1) & 0x1FF0UL;
+#endif
+
+ /*
+ * Prioritize interrupts source with respect to their critical level
+ */
+#if (defined(LPC55S06_SERIES) || defined(LPC55S04_SERIES) || defined(LPC5506_SERIES) || defined(LPC5504_SERIES) || \
+ defined(LPC5502_SERIES) || defined(LPC55S16_SERIES) || defined(LPC55S14_SERIES) || defined(LPC5516_SERIES) || \
+ defined(LPC5514_SERIES) || defined(LPC5512_SERIES))
+ if (0UL != (reset_cause_reg & PMC_AOREG1_CDOGRESET_MASK))
+ { /* Code Watchdog Reset */
+ *p_reset_cause = kRESET_CAUSE_CDOGRESET;
+ *p_boot_mode = kBOOT_MODE_POWER_UP;
+ *p_wakeupio_cause = 0; /* Device has not been waked-up by any wake-up pins */
+ }
+ else
+#endif
+ {
+ if (0UL != (reset_cause_reg & PMC_AOREG1_WDTRESET_MASK))
+ { /* Watchdog Timer Reset */
+ *p_reset_cause = kRESET_CAUSE_WDTRESET;
+ *p_boot_mode = kBOOT_MODE_POWER_UP;
+ *p_wakeupio_cause = 0; /* Device has not been waked-up by any wake-up pins */
+ }
+ else
+ {
+ if (0UL != (reset_cause_reg & PMC_AOREG1_SYSTEMRESET_MASK))
+ { /* ARM System Reset */
+ *p_reset_cause = kRESET_CAUSE_ARMSYSTEMRESET;
+ *p_boot_mode = kBOOT_MODE_POWER_UP;
+ *p_wakeupio_cause = 0; /* Device has not been waked-up by any wake-up pins */
+ }
+ else
+ {
+ boot_mode_reg = (PMC->STATUS & PMC_STATUS_BOOTMODE_MASK) >> PMC_STATUS_BOOTMODE_SHIFT;
+
+ if (boot_mode_reg == 0UL) /* POWER-UP: Power On Reset, Pin reset, Brown Out Detectors, Software Reset */
+ {
+ *p_boot_mode = kBOOT_MODE_POWER_UP; /* All non wake-up from a Low Power mode */
+ *p_wakeupio_cause = 0; /* Device has not been waked-up by any wake-up pins */
+
+ /*
+ * Prioritise Reset causes, starting from the strongest (Power On Reset)
+ */
+ if (0UL != (reset_cause_reg & PMC_AOREG1_POR_MASK))
+ { /* Power On Reset */
+ *p_reset_cause = kRESET_CAUSE_POR;
+ }
+ else
+ {
+ if (0UL != (reset_cause_reg & PMC_AOREG1_BODRESET_MASK))
+ { /* Brown-out Detector reset (either BODVBAT or BODCORE) */
+ *p_reset_cause = kRESET_CAUSE_BODRESET;
+ }
+ else
+ {
+ if (0UL != (reset_cause_reg & PMC_AOREG1_PADRESET_MASK))
+ { /* Hardware Pin Reset */
+ *p_reset_cause = kRESET_CAUSE_PADRESET;
+ }
+ else
+ {
+ if (0UL != (reset_cause_reg & PMC_AOREG1_SWRRESET_MASK))
+ { /* Software triggered Reset */
+ *p_reset_cause = kRESET_CAUSE_SWRRESET;
+ }
+ else
+ { /* Unknown Reset Cause */
+ *p_reset_cause = kRESET_CAUSE_NOT_DETERMINISTIC;
+ }
+ }
+ }
+ }
+
+#if (defined(LPC55S06_SERIES) || defined(LPC55S04_SERIES) || defined(LPC5506_SERIES) || defined(LPC5504_SERIES) || \
+ defined(LPC5502_SERIES) || defined(LPC55S16_SERIES) || defined(LPC55S14_SERIES) || defined(LPC5516_SERIES) || \
+ defined(LPC5514_SERIES) || defined(LPC5512_SERIES))
+ /* Transfer the control of the 4 wake-up pins to IOCON (instead of the Power Management Controller
+ */
+ PMC->WAKEUPIOCTRL = PMC->WAKEUPIOCTRL & (~PMC_WAKEUPIOCTRL_WAKEUPIO_ENABLE_CTRL_MASK);
+#endif
+ }
+ else /* DEEP-SLEEP, POWER-DOWN and DEEP-POWER-DOWN */
+ {
+ /*
+ * 1- First, save wakeup_io_cause register ...
+ */
+ *p_wakeupio_cause = PMC->WAKEIOCAUSE;
+
+ if (boot_mode_reg == 3UL) /* DEEP-POWER-DOWN */
+ {
+ *p_boot_mode = kBOOT_MODE_LP_DEEP_POWER_DOWN;
+
+ switch (((reset_cause_reg >> PMC_AOREG1_DPDRESET_WAKEUPIO_SHIFT) & 0x7UL))
+ {
+ case 1:
+ *p_reset_cause = kRESET_CAUSE_DPDRESET_WAKEUPIO;
+ break;
+ case 2:
+ *p_reset_cause = kRESET_CAUSE_DPDRESET_RTC;
+ break;
+ case 3:
+ *p_reset_cause = kRESET_CAUSE_DPDRESET_WAKEUPIO_RTC;
+ break;
+ case 4:
+ *p_reset_cause = kRESET_CAUSE_DPDRESET_OSTIMER;
+ break;
+ case 5:
+ *p_reset_cause = kRESET_CAUSE_DPDRESET_WAKEUPIO_OSTIMER;
+ break;
+ case 6:
+ *p_reset_cause = kRESET_CAUSE_DPDRESET_RTC_OSTIMER;
+ break;
+ case 7:
+ *p_reset_cause = kRESET_CAUSE_DPDRESET_WAKEUPIO_RTC_OSTIMER;
+ break;
+ default:
+ /* Unknown Reset Cause */
+ *p_reset_cause = kRESET_CAUSE_NOT_DETERMINISTIC;
+ break;
+ }
+
+#if (defined(LPC55S06_SERIES) || defined(LPC55S04_SERIES) || defined(LPC5506_SERIES) || defined(LPC5504_SERIES) || \
+ defined(LPC5502_SERIES) || defined(LPC55S16_SERIES) || defined(LPC55S14_SERIES) || defined(LPC5516_SERIES) || \
+ defined(LPC5514_SERIES) || defined(LPC5512_SERIES))
+ /*
+ * 2- Next, transfer the control of the 4 wake-up pins
+ * to IOCON (instead of the Power Management Controller)
+ */
+ PMC->WAKEUPIOCTRL = PMC->WAKEUPIOCTRL & (~PMC_WAKEUPIOCTRL_WAKEUPIO_ENABLE_CTRL_MASK);
+#endif
+ }
+ else /* DEEP-SLEEP and POWER-DOWN */
+ {
+ *p_reset_cause = kRESET_CAUSE_NOT_RELEVANT;
+
+ /*
+ * The control of the 4 wake-up pins is already in IOCON,
+ * so there is nothing special to do.
+ */
+
+ if (boot_mode_reg == 1UL) /* DEEP-SLEEP */
+ {
+ *p_boot_mode = kBOOT_MODE_LP_DEEP_SLEEP;
+ }
+ else /* POWER-DOWN */
+ {
+ *p_boot_mode = kBOOT_MODE_LP_POWER_DOWN;
+
+ } /* if ( boot_mode_reg == 1 ) DEEP-SLEEP */
+
+ } /* if ( boot_mode == 3 ) DEEP-POWER-DOWN */
+
+ } /* if ( boot_mode == 0 ) POWER-UP */
+
+ } /* if ( reset_cause_reg & PMC_AOREG1_CDOGRESET_MASK ) */
+
+ } /* if ( reset_cause_reg & PMC_AOREG1_WDTRESET_MASK ) */
+
+ } /* if ( reset_cause_reg & PMC_AOREG1_SYSTEMRESET_MASK ) */
+}
diff --git a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_power.h b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_power.h
index f972918b9..c37cbcf49 100644
--- a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_power.h
+++ b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_power.h
@@ -540,13 +540,6 @@ void POWER_EnterSleep(void);
*/
void POWER_SetVoltageForFreq(uint32_t system_freq_hz);
-/*!
- * @brief Power Library API to return the library version.
- *
- * @return version number of the power library
- */
-uint32_t POWER_GetLibVersion(void);
-
/**
* @brief Sets board-specific trim values for 16MHz XTAL
* @param pi32_16MfXtalIecLoadpF_x100 Load capacitance, pF x 100. For example, 6pF becomes 600, 1.2pF becomes 120
@@ -588,14 +581,6 @@ extern void POWER_Xtal32khzCapabankTrim(int32_t pi32_32kfXtalIecLoadpF_x100,
extern void POWER_SetXtal16mhzLdo(void);
/**
- * @brief Set up 16-MHz XTAL Trimmings
- * @param amp Amplitude
- * @param gm Transconductance
- * @return none
- */
-extern void POWER_SetXtal16mhzTrim(uint32_t amp, uint32_t gm);
-
-/**
* @brief Return some key information related to the device reset causes / wake-up sources, for all power modes.
* @param p_reset_cause : the device reset cause, according to the definition of power_device_reset_cause_t type.
* @param p_boot_mode : the device boot mode, according to the definition of power_device_boot_mode_t type.
diff --git a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_reset.h b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_reset.h
index bd6b2da56..9bde6707f 100644
--- a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_reset.h
+++ b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_reset.h
@@ -26,8 +26,8 @@
/*! @name Driver version */
/*@{*/
-/*! @brief reset driver version 2.0.2. */
-#define FSL_RESET_DRIVER_VERSION (MAKE_VERSION(2, 0, 2))
+/*! @brief reset driver version 2.0.3. */
+#define FSL_RESET_DRIVER_VERSION (MAKE_VERSION(2, 0, 3))
/*@}*/
/*!
@@ -233,6 +233,22 @@ typedef enum _SYSCON_RSTn
{ \
kOSTIMER0_RST_SHIFT_RSTn \
} /* Reset bits for OSTIMER peripheral */
+#define POWERQUAD_RSTS \
+ { \
+ kPOWERQUAD_RST_SHIFT_RSTn \
+ } /* Reset bits for Powerquad peripheral */
+#define CASPER_RSTS \
+ { \
+ kCASPER_RST_SHIFT_RSTn \
+ } /* Reset bits for Casper peripheral */
+#define HASHCRYPT_RSTS \
+ { \
+ kHASHCRYPT_RST_SHIFT_RSTn \
+ } /* Reset bits for Hashcrypt peripheral */
+#define PUF_RSTS \
+ { \
+ kPUF_RST_SHIFT_RSTn \
+ } /* Reset bits for PUF peripheral */
typedef SYSCON_RSTn_t reset_ip_name_t;
/*******************************************************************************
diff --git a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_usart.c b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_usart.c
index e1b2fd2c4..7e84d0cb4 100644
--- a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_usart.c
+++ b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_usart.c
@@ -1,6 +1,6 @@
/*
* Copyright (c) 2016, Freescale Semiconductor, Inc.
- * Copyright 2016-2021 NXP
+ * Copyright 2016-2022 NXP
* All rights reserved.
*
* SPDX-License-Identifier: BSD-3-Clause
@@ -229,6 +229,9 @@ status_t USART_Init(USART_Type *base, const usart_config_t *config, uint32_t src
/* enable trigger interrupt */
base->FIFOTRIG |= USART_FIFOTRIG_RXLVLENA_MASK;
}
+#if defined(FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG) && FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG
+ USART_SetRxTimeoutConfig(base, (usart_rx_timeout_config *)&(config->rxTimeout));
+#endif
/* setup configuration and enable USART */
base->CFG = USART_CFG_PARITYSEL(config->parityMode) | USART_CFG_STOPLEN(config->stopBitCount) |
USART_CFG_DATALEN(config->bitCountPerChar) | USART_CFG_LOOP(config->loopback) |
@@ -281,6 +284,9 @@ void USART_Deinit(USART_Type *base)
USART_FIFOINTENCLR_RXLVL_MASK;
base->FIFOCFG &= ~(USART_FIFOCFG_DMATX_MASK | USART_FIFOCFG_DMARX_MASK);
base->CFG &= ~(USART_CFG_ENABLE_MASK);
+#if defined(FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG) && FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG
+ base->FIFORXTIMEOUTCFG = 0U;
+#endif
}
/*!
@@ -321,7 +327,84 @@ void USART_GetDefaultConfig(usart_config_t *config)
config->enableContinuousSCLK = false;
config->clockPolarity = kUSART_RxSampleOnFallingEdge;
config->enableHardwareFlowControl = false;
+#if defined(FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG) && FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG
+ config->rxTimeout.enable = false;
+ config->rxTimeout.resetCounterOnEmpty = true;
+ config->rxTimeout.resetCounterOnReceive = true;
+ config->rxTimeout.counter = 0U;
+ config->rxTimeout.prescaler = 0U;
+#endif
}
+#if defined(FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG) && FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG
+/*!
+ * brief Calculate the USART instance RX timeout prescaler and counter.
+ *
+ * This function for calculate the USART RXFIFO timeout config. This function is used to calculate
+ * suitable prescaler and counter for target_us.
+ * Example below shows how to use this API to configure USART.
+ * code
+ * usart_config_t config;
+ * config.rxWatermark = kUSART_RxFifo2;
+ * config.rxTimeout.enable = true;
+ * config.rxTimeout.resetCounterOnEmpty = true;
+ * config.rxTimeout.resetCounterOnReceive = true;
+ * USART_CalcTimeoutConfig(200, &config.rxTimeout.prescaler, &config.rxTimeout.counter,
+ * CLOCK_GetFreq(kCLOCK_BusClk));
+ * endcode
+ * param target_us Time for rx timeout unit us.
+ * param rxTimeoutPrescaler The prescaler to be setted after function.
+ * param rxTimeoutcounter The counter to be setted after function.
+ * param srcClock_Hz The clockSrc for rx timeout.
+ */
+void USART_CalcTimeoutConfig(uint32_t target_us,
+ uint8_t *rxTimeoutPrescaler,
+ uint32_t *rxTimeoutcounter,
+ uint32_t srcClock_Hz)
+{
+ uint16_t counter = 0U;
+ uint32_t perscalar = 0U, calculate_us = 0U, us_diff = 0U, min_diff = 0xffffffffUL;
+ /* find the suitable value */
+ for (perscalar = 0U; perscalar < 256U; perscalar++)
+ {
+ counter = target_us * (srcClock_Hz / 1000000UL) / (16U * (perscalar + 1U));
+ calculate_us = 16U * (perscalar + 1U) * counter / (srcClock_Hz / 1000000UL);
+ us_diff = (calculate_us > target_us) ? (calculate_us - target_us) : (target_us - calculate_us);
+ if (us_diff == 0U)
+ {
+ *rxTimeoutPrescaler = perscalar;
+ *rxTimeoutcounter = counter;
+ break;
+ }
+ else
+ {
+ if (min_diff > us_diff)
+ {
+ min_diff = us_diff;
+ *rxTimeoutPrescaler = perscalar;
+ *rxTimeoutcounter = counter;
+ }
+ }
+ }
+}
+/*!
+ * brief Sets the USART instance RX timeout config.
+ *
+ * This function configures the USART RXFIFO timeout config. This function is used to config
+ * the USART RXFIFO timeout config after the USART module is initialized by the USART_Init.
+ *
+ * param base USART peripheral base address.
+ * param config pointer to receive timeout configuration structure.
+ */
+void USART_SetRxTimeoutConfig(USART_Type *base, usart_rx_timeout_config *config)
+{
+ base->FIFORXTIMEOUTCFG = 0U;
+ base->FIFORXTIMEOUTCFG = USART_FIFORXTIMEOUTCFG_RXTIMEOUT_COW(~config->resetCounterOnReceive) |
+ USART_FIFORXTIMEOUTCFG_RXTIMEOUT_COE(~config->resetCounterOnEmpty) |
+ USART_FIFORXTIMEOUTCFG_RXTIMEOUT_EN(config->enable) |
+ USART_FIFORXTIMEOUTCFG_RXTIMEOUT_VALUE(config->counter) |
+ USART_FIFORXTIMEOUTCFG_RXTIMEOUT_PRESCALER(config->prescaler);
+}
+#endif
/*!
* brief Sets the USART instance baud rate.
@@ -342,7 +425,7 @@ void USART_GetDefaultConfig(usart_config_t *config)
status_t USART_SetBaudRate(USART_Type *base, uint32_t baudrate_Bps, uint32_t srcClock_Hz)
{
uint32_t best_diff = (uint32_t)-1, best_osrval = 0xf, best_brgval = (uint32_t)-1;
- uint32_t osrval, brgval, diff, baudrate;
+ uint32_t osrval, brgval, diff, baudrate, allowed_error;
/* check arguments */
assert(!((NULL == base) || (0U == baudrate_Bps) || (0U == srcClock_Hz)));
@@ -362,12 +445,21 @@ status_t USART_SetBaudRate(USART_Type *base, uint32_t baudrate_Bps, uint32_t src
}
else
{
+ /* Actual baud rate must be within 3% of desired baud rate based on the calculated OSR and BRG value */
+ allowed_error = ((baudrate_Bps / 100U) * 3U);
/*
* Smaller values of OSR can make the sampling position within a data bit less accurate and may
* potentially cause more noise errors or incorrect data.
*/
- for (osrval = best_osrval; osrval >= 8U; osrval--)
+ for (osrval = best_osrval; (osrval >= 4U); osrval--)
{
+ /* Break if the best baudrate's diff is in the allowed error range and the osrval is below 8,
+ only use lower osrval if the baudrate cannot be obtained with an osrval of 8 or above. */
+ if ((osrval <= 8U) && (best_diff <= allowed_error))
+ {
+ break;
+ }
+
brgval = (((srcClock_Hz * 10U) / ((osrval + 1U) * baudrate_Bps)) - 5U) / 10U;
if (brgval > 0xFFFFU)
{
@@ -387,7 +479,7 @@ status_t USART_SetBaudRate(USART_Type *base, uint32_t baudrate_Bps, uint32_t src
* based on the best calculated OSR and BRG value */
baudrate = srcClock_Hz / ((best_osrval + 1U) * (best_brgval + 1U));
diff = (baudrate_Bps < baudrate) ? (baudrate - baudrate_Bps) : (baudrate_Bps - baudrate);
- if (diff > ((baudrate_Bps / 100U) * 3U))
+ if (diff > allowed_error)
{
return kStatus_USART_BaudrateNotSupport;
}
@@ -708,13 +800,9 @@ status_t USART_TransferCreateHandle(USART_Type *base,
* all data is written to the TX register in the IRQ handler, the USART driver calls the callback
* function and passes the ref kStatus_USART_TxIdle as status parameter.
*
- * note The kStatus_USART_TxIdle is passed to the upper layer when all data is written
- * to the TX register. However it does not ensure that all data are sent out. Before disabling the TX,
- * check the kUSART_TransmissionCompleteFlag to ensure that the TX is finished.
- *
* param base USART peripheral base address.
* param handle USART handle pointer.
- * param xfer USART transfer structure. See #usart_transfer_t.
+ * param xfer USART transfer structure. See #usart_transfer_t.
* retval kStatus_Success Successfully start the data transmission.
* retval kStatus_USART_TxBusy Previous transmission still not finished, data not all written to TX register yet.
* retval kStatus_InvalidArgument Invalid argument.
@@ -1039,6 +1127,56 @@ void USART_TransferHandleIRQ(USART_Type *base, usart_handle_t *handle)
handle->callback(base, handle, kStatus_USART_RxError, handle->userData);
}
}
+ /* TX under run, happens when slave is in synchronous mode and the data is not written in tx register in time. */
+ if ((base->FIFOSTAT & USART_FIFOSTAT_TXERR_MASK) != 0U)
+ {
+ /* Clear tx error state. */
+ base->FIFOSTAT |= USART_FIFOSTAT_TXERR_MASK;
+ /* Trigger callback. */
+ if (handle->callback != NULL)
+ {
+ handle->callback(base, handle, kStatus_USART_TxError, handle->userData);
+ }
+ }
+ /* If noise error. */
+ if ((base->STAT & USART_STAT_RXNOISEINT_MASK) != 0U)
+ {
+ /* Clear rx error state. */
+ base->STAT |= USART_STAT_RXNOISEINT_MASK;
+ /* clear rxFIFO */
+ base->FIFOCFG |= USART_FIFOCFG_EMPTYRX_MASK;
+ /* Trigger callback. */
+ if (handle->callback != NULL)
+ {
+ handle->callback(base, handle, kStatus_USART_NoiseError, handle->userData);
+ }
+ }
+ /* If framing error. */
+ if ((base->STAT & USART_STAT_FRAMERRINT_MASK) != 0U)
+ {
+ /* Clear rx error state. */
+ base->STAT |= USART_STAT_FRAMERRINT_MASK;
+ /* clear rxFIFO */
+ base->FIFOCFG |= USART_FIFOCFG_EMPTYRX_MASK;
+ /* Trigger callback. */
+ if (handle->callback != NULL)
+ {
+ handle->callback(base, handle, kStatus_USART_FramingError, handle->userData);
+ }
+ }
+ /* If parity error. */
+ if ((base->STAT & USART_STAT_PARITYERRINT_MASK) != 0U)
+ {
+ /* Clear rx error state. */
+ base->STAT |= USART_STAT_PARITYERRINT_MASK;
+ /* clear rxFIFO */
+ base->FIFOCFG |= USART_FIFOCFG_EMPTYRX_MASK;
+ /* Trigger callback. */
+ if (handle->callback != NULL)
+ {
+ handle->callback(base, handle, kStatus_USART_ParityError, handle->userData);
+ }
+ }
while ((receiveEnabled && ((base->FIFOSTAT & USART_FIFOSTAT_RXNOTEMPTY_MASK) != 0U)) ||
(sendEnabled && ((base->FIFOSTAT & USART_FIFOSTAT_TXNOTFULL_MASK) != 0U)))
{
diff --git a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_usart.h b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_usart.h
index 726ed1c22..3aa3cae0f 100644
--- a/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_usart.h
+++ b/FreeRTOS/Demo/CORTEX_MPU_M33F_NXP_LPC55S69_MCUXpresso/NXP_Code/drivers/fsl_usart.h
@@ -1,6 +1,6 @@
/*
* Copyright (c) 2016, Freescale Semiconductor, Inc.
- * Copyright 2016-2021 NXP
+ * Copyright 2016-2022NXP
* All rights reserved.
*
* SPDX-License-Identifier: BSD-3-Clause
@@ -22,15 +22,22 @@
/*! @name Driver version */
/*@{*/
/*! @brief USART driver version. */
-#define FSL_USART_DRIVER_VERSION (MAKE_VERSION(2, 5, 1))
+#define FSL_USART_DRIVER_VERSION (MAKE_VERSION(2, 7, 0))
/*@}*/
#define USART_FIFOTRIG_TXLVL_GET(base) (((base)->FIFOTRIG & USART_FIFOTRIG_TXLVL_MASK) >> USART_FIFOTRIG_TXLVL_SHIFT)
#define USART_FIFOTRIG_RXLVL_GET(base) (((base)->FIFOTRIG & USART_FIFOTRIG_RXLVL_MASK) >> USART_FIFOTRIG_RXLVL_SHIFT)
-/*! @brief Retry times for waiting flag. */
+/*! @brief Retry times for waiting flag.
+ *
+ * Defining to zero means to keep waiting for the flag until it is assert/deassert in blocking transfer,
+ * otherwise the program will wait until the UART_RETRY_TIMES counts down to 0,
+ * if the flag still remains unchanged then program will return kStatus_USART_Timeout.
+ * It is not advised to use this macro in formal application to prevent any hardware error
+ * because the actual wait period is affected by the compiler and optimization.
+ */
#ifndef UART_RETRY_TIMES
-#define UART_RETRY_TIMES 0U /* Defining to zero means to keep waiting for the flag until it is assert/deassert. */
+#define UART_RETRY_TIMES 0U
#endif
/*! @brief Error codes for the USART driver. */
@@ -48,7 +55,9 @@ enum
kStatus_USART_ParityError = MAKE_STATUS(kStatusGroup_LPC_USART, 12), /*!< USART parity error. */
kStatus_USART_BaudrateNotSupport =
MAKE_STATUS(kStatusGroup_LPC_USART, 13), /*!< Baudrate is not support in current clock source */
+#if UART_RETRY_TIMES
kStatus_USART_Timeout = MAKE_STATUS(kStatusGroup_LPC_USART, 14), /*!< USART time out. */
+#endif
};
/*! @brief USART synchronous mode. */
@@ -123,6 +132,28 @@ enum _usart_interrupt_enable
kUSART_RxErrorInterruptEnable = (USART_FIFOINTENSET_RXERR_MASK),
kUSART_TxLevelInterruptEnable = (USART_FIFOINTENSET_TXLVL_MASK),
kUSART_RxLevelInterruptEnable = (USART_FIFOINTENSET_RXLVL_MASK),
+ kUSART_TxIdleInterruptEnable = (USART_INTENSET_TXIDLEEN_MASK << 16U), /*!< Transmitter idle. */
+ kUSART_CtsChangeInterruptEnable =
+ (USART_INTENSET_DELTACTSEN_MASK << 16U), /*!< Change in the state of the CTS input. */
+ kUSART_RxBreakChangeInterruptEnable =
+ (USART_INTENSET_DELTARXBRKEN_MASK), /*!< Break condition asserted or deasserted. */
+ kUSART_RxStartInterruptEnable = (USART_INTENSET_STARTEN_MASK), /*!< Rx start bit detected. */
+ kUSART_FramingErrorInterruptEnable = (USART_INTENSET_FRAMERREN_MASK), /*!< Framing error detected. */
+ kUSART_ParityErrorInterruptEnable = (USART_INTENSET_PARITYERREN_MASK), /*!< Parity error detected. */
+ kUSART_NoiseErrorInterruptEnable = (USART_INTENSET_RXNOISEEN_MASK), /*!< Noise error detected. */
+ kUSART_AutoBaudErrorInterruptEnable = (USART_INTENSET_ABERREN_MASK), /*!< Auto baudrate error detected. */
+#if defined(FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG) && FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG
+ kUSART_RxTimeoutInterruptEnable = (USART_FIFOINTENSET_RXTIMEOUT_MASK), /*!< Receive timeout detected. */
+#endif
+ kUSART_AllInterruptEnables =
+ kUSART_TxErrorInterruptEnable | kUSART_RxErrorInterruptEnable | kUSART_TxLevelInterruptEnable |
+ kUSART_RxLevelInterruptEnable | kUSART_TxIdleInterruptEnable | kUSART_CtsChangeInterruptEnable |
+ kUSART_RxBreakChangeInterruptEnable | kUSART_RxStartInterruptEnable | kUSART_FramingErrorInterruptEnable |
+ kUSART_ParityErrorInterruptEnable | kUSART_NoiseErrorInterruptEnable |
+#if defined(FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG) && FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG
+ kUSART_RxTimeoutInterruptEnable |
+#endif
+ kUSART_AutoBaudErrorInterruptEnable,
};
/*!
@@ -132,14 +163,49 @@ enum _usart_interrupt_enable
*/
enum _usart_flags
{
- kUSART_TxError = (USART_FIFOSTAT_TXERR_MASK), /*!< TEERR bit, sets if TX buffer is error */
- kUSART_RxError = (USART_FIFOSTAT_RXERR_MASK), /*!< RXERR bit, sets if RX buffer is error */
- kUSART_TxFifoEmptyFlag = (USART_FIFOSTAT_TXEMPTY_MASK), /*!< TXEMPTY bit, sets if TX buffer is empty */
- kUSART_TxFifoNotFullFlag = (USART_FIFOSTAT_TXNOTFULL_MASK), /*!< TXNOTFULL bit, sets if TX buffer is not full */
- kUSART_RxFifoNotEmptyFlag = (USART_FIFOSTAT_RXNOTEMPTY_MASK), /*!< RXNOEMPTY bit, sets if RX buffer is not empty */
- kUSART_RxFifoFullFlag = (USART_FIFOSTAT_RXFULL_MASK), /*!< RXFULL bit, sets if RX buffer is full */
+ kUSART_TxError = (USART_FIFOSTAT_TXERR_MASK), /*!< TEERR bit, sets if TX buffer is error */
+ kUSART_RxError = (USART_FIFOSTAT_RXERR_MASK), /*!< RXERR bit, sets if RX buffer is error */
+ kUSART_TxFifoEmptyFlag = (USART_FIFOSTAT_TXEMPTY_MASK), /*!< TXEMPTY bit, sets if TX buffer is empty */
+ kUSART_TxFifoNotFullFlag = (USART_FIFOSTAT_TXNOTFULL_MASK), /*!< TXNOTFULL bit, sets if TX buffer is not full */
+ kUSART_RxFifoNotEmptyFlag = (USART_FIFOSTAT_RXNOTEMPTY_MASK), /*!< RXNOEMPTY bit, sets if RX buffer is not empty */
+ kUSART_RxFifoFullFlag = (USART_FIFOSTAT_RXFULL_MASK), /*!< RXFULL bit, sets if RX buffer is full */
+ kUSART_RxIdleFlag = (USART_STAT_RXIDLE_MASK << 16U), /*!< Receiver idle. */
+ kUSART_TxIdleFlag = (USART_STAT_TXIDLE_MASK << 16U), /*!< Transmitter idle. */
+ kUSART_CtsAssertFlag = (USART_STAT_CTS_MASK << 16U), /*!< CTS signal high. */
+ kUSART_CtsChangeFlag = (USART_STAT_DELTACTS_MASK << 16U), /*!< CTS signal changed interrupt status. */
+ kUSART_BreakDetectFlag = (USART_STAT_RXBRK_MASK), /*!< Break detected. Self cleared when rx pin goes high again. */
+ kUSART_BreakDetectChangeFlag = (USART_STAT_DELTARXBRK_MASK), /*!< Break detect change interrupt flag. A change in
+ the state of receiver break detection. */
+ kUSART_RxStartFlag = (USART_STAT_START_MASK), /*!< Rx start bit detected interrupt flag. */
+ kUSART_FramingErrorFlag = (USART_STAT_FRAMERRINT_MASK), /*!< Framing error interrupt flag. */
+ kUSART_ParityErrorFlag = (USART_STAT_PARITYERRINT_MASK), /*!< parity error interrupt flag. */
+ kUSART_NoiseErrorFlag = (USART_STAT_RXNOISEINT_MASK), /*!< Noise error interrupt flag. */
+ kUSART_AutobaudErrorFlag = (USART_STAT_ABERR_MASK), /*!< Auto baudrate error interrupt flag, caused by the baudrate
+ counter timeout before the end of start bit. */
+#if defined(FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG) && FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG
+ kUSART_RxTimeoutFlag = (USART_FIFOSTAT_RXTIMEOUT_MASK), /*!< RXTIMEOUT bit, sets if RX FIFO Timeout. */
+#endif
+ kUSART_AllClearFlags = kUSART_TxError | kUSART_RxError | kUSART_CtsChangeFlag | kUSART_BreakDetectChangeFlag |
+ kUSART_RxStartFlag | kUSART_FramingErrorFlag | kUSART_ParityErrorFlag |
+#if defined(FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG) && FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG
+ kUSART_RxTimeoutFlag |
+#endif
+ kUSART_NoiseErrorFlag | kUSART_AutobaudErrorFlag,
};
+#if defined(FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG) && FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG
+/*! @brief USART receive timeout configuration structure. */
+typedef struct _usart_rx_timeout_config
+{
+ bool enable; /*!< Enable RX timeout */
+ bool resetCounterOnEmpty; /*!< Enable RX timeout counter reset when RX FIFO becames empty. */
+ bool resetCounterOnReceive; /*!< Enable RX timeout counter reset when RX FIFO receives data from the transmitter
+ side. */
+ uint32_t counter; /*!< RX timeout counter*/
+ uint8_t prescaler; /*!< RX timeout prescaler*/
+} usart_rx_timeout_config;
+#endif
+
/*! @brief USART configuration structure. */
typedef struct _usart_config
{
@@ -157,6 +223,9 @@ typedef struct _usart_config
usart_rxfifo_watermark_t rxWatermark; /*!< rxFIFO watermark */
usart_sync_mode_t syncMode; /*!< Transfer mode select - asynchronous, synchronous master, synchronous slave. */
usart_clock_polarity_t clockPolarity; /*!< Selects the clock polarity and sampling edge in synchronous mode. */
+#if defined(FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG) && FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG
+ usart_rx_timeout_config rxTimeout; /*!< rx timeout configuration */
+#endif
} usart_config_t;
/*! @brief USART transfer structure. */
@@ -247,7 +316,41 @@ uint32_t USART_GetInstance(USART_Type *base);
* @retval kStatus_Success Status USART initialize succeed
*/
status_t USART_Init(USART_Type *base, const usart_config_t *config, uint32_t srcClock_Hz);
-
+#if defined(FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG) && FSL_FEATURE_USART_HAS_FIFORXTIMEOUTCFG
+/*!
+ * @brief Calculate the USART instance RX timeout prescaler and counter.
+ *
+ * This function for calculate the USART RXFIFO timeout config. This function is used to calculate
+ * suitable prescaler and counter for target_us.
+ * @code
+ * usart_config_t config;
+ * config.rxWatermark = kUSART_RxFifo2;
+ * config.rxTimeout.enable = true;
+ * config.rxTimeout.resetCounterOnEmpty = true;
+ * config.rxTimeout.resetCounterOnReceive = true;
+ * USART_CalcTimeoutConfig(200U, &config.rxTimeout.prescaler, &config.rxTimeout.counter,
+ * CLOCK_GetFreq(kCLOCK_BusClk));
+ * @endcode
+ * @param target_us Time for rx timeout unit us.
+ * @param rxTimeoutPrescaler The prescaler to be setted after function.
+ * @param rxTimeoutcounter The counter to be setted after function.
+ * @param srcClock_Hz The clockSrc for rx timeout.
+ */
+void USART_CalcTimeoutConfig(uint32_t target_us,
+ uint8_t *rxTimeoutPrescaler,
+ uint32_t *rxTimeoutcounter,
+ uint32_t srcClock_Hz);
+/*!
+ * @brief Sets the USART instance RX timeout config.
+ *
+ * This function configures the USART RXFIFO timeout config. This function is used to config
+ * the USART RXFIFO timeout config after the USART module is initialized by the USART_Init.
+ *
+ * @param base USART peripheral base address.
+ * @param config pointer to receive timeout configuration structure.
+ */
+void USART_SetRxTimeoutConfig(USART_Type *base, usart_rx_timeout_config *config);
+#endif
/*!
* @brief Deinitializes a USART instance.
*
@@ -389,7 +492,7 @@ static inline void USART_EnableMatchAddress(USART_Type *base, bool match)
*/
static inline uint32_t USART_GetStatusFlags(USART_Type *base)
{
- return base->FIFOSTAT;
+ return (base->FIFOSTAT & 0xFF0000FFUL) | (base->STAT & 0xFFUL) << 16U | (base->STAT & 0xFFFF00UL);
}
/*!
@@ -409,6 +512,9 @@ static inline uint32_t USART_GetStatusFlags(USART_Type *base)
*/
static inline void USART_ClearStatusFlags(USART_Type *base, uint32_t mask)
{
+ mask &= (uint32_t)kUSART_AllClearFlags;
+ /* Clear the clearable status in STAT register. */
+ base->STAT = (mask & 0xFFFF00UL) | ((mask & 0xFF0000UL) >> 16U);
/* Only TXERR, RXERR fields support write. Remaining fields should be set to zero */
base->FIFOSTAT = mask & (USART_FIFOSTAT_TXERR_MASK | USART_FIFOSTAT_RXERR_MASK);
}
@@ -419,7 +525,6 @@ static inline void USART_ClearStatusFlags(USART_Type *base, uint32_t mask)
* @name Interrupts
* @{
*/
-
/*!
* @brief Enables USART interrupts according to the provided mask.
*
@@ -435,7 +540,9 @@ static inline void USART_ClearStatusFlags(USART_Type *base, uint32_t mask)
*/
static inline void USART_EnableInterrupts(USART_Type *base, uint32_t mask)
{
- base->FIFOINTENSET = mask & 0xFUL;
+ mask &= (uint32_t)kUSART_AllInterruptEnables;
+ base->INTENSET = (mask & 0x1FF00UL) | ((mask & 0xFF0000UL) >> 16U);
+ base->FIFOINTENSET = mask & 0xF00000FUL;
}
/*!
@@ -453,6 +560,8 @@ static inline void USART_EnableInterrupts(USART_Type *base, uint32_t mask)
*/
static inline void USART_DisableInterrupts(USART_Type *base, uint32_t mask)
{
+ mask &= (uint32_t)kUSART_AllInterruptEnables;
+ base->INTENCLR = (mask & 0x1FF00UL) | ((mask & 0xFF0000UL) >> 16U);
base->FIFOINTENCLR = mask & 0xFUL;
}
@@ -465,7 +574,7 @@ static inline void USART_DisableInterrupts(USART_Type *base, uint32_t mask)
*/
static inline uint32_t USART_GetEnabledInterrupts(USART_Type *base)
{
- return base->FIFOINTENSET;
+ return (base->INTENSET & 0x1FF00UL) | ((base->INTENSET & 0xFFUL) << 16UL) | (base->FIFOINTENSET & 0xFUL);
}
/*!
@@ -711,10 +820,6 @@ status_t USART_TransferCreateHandle(USART_Type *base,
* all data is written to the TX register in the IRQ handler, the USART driver calls the callback
* function and passes the @ref kStatus_USART_TxIdle as status parameter.
*
- * @note The kStatus_USART_TxIdle is passed to the upper layer when all data is written
- * to the TX register. However it does not ensure that all data are sent out. Before disabling the TX,
- * check the kUSART_TransmissionCompleteFlag to ensure that the TX is finished.
- *
* @param base USART peripheral base address.
* @param handle USART handle pointer.
* @param xfer USART transfer structure. See #usart_transfer_t.