1 /*
2  * Copyright (c) 2015, Freescale Semiconductor, Inc.
3  * Copyright 2016-2017, 2020 NXP
4  * All rights reserved.
5  *
6  * SPDX-License-Identifier: BSD-3-Clause
7  */
8 
9 #include "fsl_ewm.h"
10 
11 /* Component ID definition, used by tools. */
12 #ifndef FSL_COMPONENT_ID
13 #define FSL_COMPONENT_ID "platform.drivers.ewm"
14 #endif
15 
16 /*******************************************************************************
17  * Code
18  ******************************************************************************/
19 
20 /*!
21  * brief Initializes the EWM peripheral.
22  *
23  * This function is used to initialize the EWM. After calling, the EWM
24  * runs immediately according to the configuration.
25  * Note that, except for the interrupt enable control bit, other control bits and registers are write once after a
26  * CPU reset. Modifying them more than once generates a bus transfer error.
27  *
28  * This is an example.
29  * code
30  *   ewm_config_t config;
31  *   EWM_GetDefaultConfig(&config);
32  *   config.compareHighValue = 0xAAU;
33  *   EWM_Init(ewm_base,&config);
34  * endcode
35  *
36  * param base EWM peripheral base address
37  * param config The configuration of the EWM
38  */
EWM_Init(EWM_Type * base,const ewm_config_t * config)39 void EWM_Init(EWM_Type *base, const ewm_config_t *config)
40 {
41     assert(NULL != config);
42 
43     uint8_t value = 0U;
44 
45 #if !((defined(FSL_FEATURE_SOC_PCC_COUNT) && FSL_FEATURE_SOC_PCC_COUNT) && \
46       (defined(FSL_FEATURE_PCC_SUPPORT_EWM_CLOCK_REMOVE) && FSL_FEATURE_PCC_SUPPORT_EWM_CLOCK_REMOVE))
47 #if !(defined(FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL) && FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL)
48     CLOCK_EnableClock(kCLOCK_Ewm0);
49 #endif /* FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL */
50 #endif
51     value = EWM_CTRL_EWMEN(config->enableEwm) | EWM_CTRL_ASSIN(config->setInputAssertLogic) |
52             EWM_CTRL_INEN(config->enableEwmInput) | EWM_CTRL_INTEN(config->enableInterrupt);
53 #if defined(FSL_FEATURE_EWM_HAS_PRESCALER) && FSL_FEATURE_EWM_HAS_PRESCALER
54     base->CLKPRESCALER = config->prescaler;
55 #endif /* FSL_FEATURE_EWM_HAS_PRESCALER */
56 
57 #if defined(FSL_FEATURE_EWM_HAS_CLOCK_SELECT) && FSL_FEATURE_EWM_HAS_CLOCK_SELECT
58     base->CLKCTRL = (uint8_t)config->clockSource;
59 #endif /* FSL_FEATURE_EWM_HAS_CLOCK_SELECT*/
60 
61     base->CMPL = config->compareLowValue;
62     base->CMPH = config->compareHighValue;
63     base->CTRL = value;
64 }
65 
66 /*!
67  * brief Deinitializes the EWM peripheral.
68  *
69  * This function is used to shut down the EWM.
70  *
71  * param base EWM peripheral base address
72  */
EWM_Deinit(EWM_Type * base)73 void EWM_Deinit(EWM_Type *base)
74 {
75     EWM_DisableInterrupts(base, (uint32_t)kEWM_InterruptEnable);
76 #if !((defined(FSL_FEATURE_SOC_PCC_COUNT) && FSL_FEATURE_SOC_PCC_COUNT) && \
77       (defined(FSL_FEATURE_PCC_SUPPORT_EWM_CLOCK_REMOVE) && FSL_FEATURE_PCC_SUPPORT_EWM_CLOCK_REMOVE))
78 #if !(defined(FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL) && FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL)
79     CLOCK_DisableClock(kCLOCK_Ewm0);
80 #endif /* FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL */
81 #endif /* FSL_FEATURE_PCC_SUPPORT_EWM_CLOCK_REMOVE */
82 }
83 
84 /*!
85  * brief Initializes the EWM configuration structure.
86  *
87  * This function initializes the EWM configuration structure to default values. The default
88  * values are as follows.
89  * code
90  *   ewmConfig->enableEwm = true;
91  *   ewmConfig->enableEwmInput = false;
92  *   ewmConfig->setInputAssertLogic = false;
93  *   ewmConfig->enableInterrupt = false;
94  *   ewmConfig->ewm_lpo_clock_source_t = kEWM_LpoClockSource0;
95  *   ewmConfig->prescaler = 0;
96  *   ewmConfig->compareLowValue = 0;
97  *   ewmConfig->compareHighValue = 0xFEU;
98  * endcode
99  *
100  * param config Pointer to the EWM configuration structure.
101  * see ewm_config_t
102  */
EWM_GetDefaultConfig(ewm_config_t * config)103 void EWM_GetDefaultConfig(ewm_config_t *config)
104 {
105     assert(NULL != config);
106 
107     /* Initializes the configure structure to zero. */
108     (void)memset(config, 0, sizeof(*config));
109 
110     config->enableEwm           = true;
111     config->enableEwmInput      = false;
112     config->setInputAssertLogic = false;
113     config->enableInterrupt     = false;
114 #if defined(FSL_FEATURE_EWM_HAS_CLOCK_SELECT) && FSL_FEATURE_EWM_HAS_CLOCK_SELECT
115     config->clockSource = kEWM_LpoClockSource0;
116 #endif /* FSL_FEATURE_EWM_HAS_CLOCK_SELECT*/
117 #if defined(FSL_FEATURE_EWM_HAS_PRESCALER) && FSL_FEATURE_EWM_HAS_PRESCALER
118     config->prescaler = 0U;
119 #endif /* FSL_FEATURE_EWM_HAS_PRESCALER */
120     config->compareLowValue  = 0U;
121     config->compareHighValue = 0xFEU;
122 }
123 
124 /*!
125  * brief Services the EWM.
126  *
127  * This function resets the EWM counter to zero.
128  *
129  * param base EWM peripheral base address
130  */
EWM_Refresh(EWM_Type * base)131 void EWM_Refresh(EWM_Type *base)
132 {
133     uint32_t primaskValue = 0U;
134 
135     /* Disable the global interrupt to protect refresh sequence */
136     primaskValue = DisableGlobalIRQ();
137     base->SERV   = (uint8_t)0xB4U;
138     base->SERV   = (uint8_t)0x2CU;
139     EnableGlobalIRQ(primaskValue);
140 }
141