1 /*
2  * Copyright (c) 2015, Freescale Semiconductor, Inc.
3  * Copyright 2016-2017 NXP
4  *
5  * Redistribution and use in source and binary forms, with or without modification,
6  * are permitted provided that the following conditions are met:
7  *
8  * o Redistributions of source code must retain the above copyright notice, this list
9  *   of conditions and the following disclaimer.
10  *
11  * o Redistributions in binary form must reproduce the above copyright notice, this
12  *   list of conditions and the following disclaimer in the documentation and/or
13  *   other materials provided with the distribution.
14  *
15  * o Neither the name of the copyright holder nor the names of its
16  *   contributors may be used to endorse or promote products derived from this
17  *   software without specific prior written permission.
18  *
19  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
20  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
21  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
22  * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
23  * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
24  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
25  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
26  * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
28  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29  */
30 
31 #include "fsl_lptmr.h"
32 
33 /*******************************************************************************
34  * Prototypes
35  ******************************************************************************/
36 /*!
37  * @brief Gets the instance from the base address to be used to gate or ungate the module clock
38  *
39  * @param base LPTMR peripheral base address
40  *
41  * @return The LPTMR instance
42  */
43 static uint32_t LPTMR_GetInstance(LPTMR_Type *base);
44 
45 /*******************************************************************************
46  * Variables
47  ******************************************************************************/
48 /*! @brief Pointers to LPTMR bases for each instance. */
49 static LPTMR_Type *const s_lptmrBases[] = LPTMR_BASE_PTRS;
50 
51 #if !(defined(FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL) && FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL)
52 /*! @brief Pointers to LPTMR clocks for each instance. */
53 static const clock_ip_name_t s_lptmrClocks[] = LPTMR_CLOCKS;
54 
55 #if defined(LPTMR_PERIPH_CLOCKS)
56 /* Array of LPTMR functional clock name. */
57 static const clock_ip_name_t s_lptmrPeriphClocks[] = LPTMR_PERIPH_CLOCKS;
58 #endif
59 
60 #endif /* FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL */
61 
62 /*******************************************************************************
63  * Code
64  ******************************************************************************/
LPTMR_GetInstance(LPTMR_Type * base)65 static uint32_t LPTMR_GetInstance(LPTMR_Type *base)
66 {
67     uint32_t instance;
68 
69     /* Find the instance index from base address mappings. */
70     for (instance = 0; instance < ARRAY_SIZE(s_lptmrBases); instance++)
71     {
72         if (s_lptmrBases[instance] == base)
73         {
74             break;
75         }
76     }
77 
78     assert(instance < ARRAY_SIZE(s_lptmrBases));
79 
80     return instance;
81 }
82 
LPTMR_Init(LPTMR_Type * base,const lptmr_config_t * config)83 void LPTMR_Init(LPTMR_Type *base, const lptmr_config_t *config)
84 {
85     assert(config);
86 
87 #if !(defined(FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL) && FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL)
88 
89     uint32_t instance = LPTMR_GetInstance(base);
90 
91     /* Ungate the LPTMR clock*/
92     CLOCK_EnableClock(s_lptmrClocks[instance]);
93 #if defined(LPTMR_PERIPH_CLOCKS)
94     CLOCK_EnableClock(s_lptmrPeriphClocks[instance]);
95 #endif
96 
97 #endif /* FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL */
98 
99     /* Configure the timers operation mode and input pin setup */
100     base->CSR = (LPTMR_CSR_TMS(config->timerMode) | LPTMR_CSR_TFC(config->enableFreeRunning) |
101                  LPTMR_CSR_TPP(config->pinPolarity) | LPTMR_CSR_TPS(config->pinSelect));
102 
103     /* Configure the prescale value and clock source */
104     base->PSR = (LPTMR_PSR_PRESCALE(config->value) | LPTMR_PSR_PBYP(config->bypassPrescaler) |
105                  LPTMR_PSR_PCS(config->prescalerClockSource));
106 }
107 
LPTMR_Deinit(LPTMR_Type * base)108 void LPTMR_Deinit(LPTMR_Type *base)
109 {
110     /* Disable the LPTMR and reset the internal logic */
111     base->CSR &= ~LPTMR_CSR_TEN_MASK;
112 #if !(defined(FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL) && FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL)
113 
114     uint32_t instance = LPTMR_GetInstance(base);
115 
116     /* Gate the LPTMR clock*/
117     CLOCK_DisableClock(s_lptmrClocks[instance]);
118 #if defined(LPTMR_PERIPH_CLOCKS)
119     CLOCK_DisableClock(s_lptmrPeriphClocks[instance]);
120 #endif
121 
122 #endif /* FSL_SDK_DISABLE_DRIVER_CLOCK_CONTROL */
123 }
124 
LPTMR_GetDefaultConfig(lptmr_config_t * config)125 void LPTMR_GetDefaultConfig(lptmr_config_t *config)
126 {
127     assert(config);
128 
129     /* Use time counter mode */
130     config->timerMode = kLPTMR_TimerModeTimeCounter;
131     /* Use input 0 as source in pulse counter mode */
132     config->pinSelect = kLPTMR_PinSelectInput_0;
133     /* Pulse input pin polarity is active-high */
134     config->pinPolarity = kLPTMR_PinPolarityActiveHigh;
135     /* Counter resets whenever TCF flag is set */
136     config->enableFreeRunning = false;
137     /* Bypass the prescaler */
138     config->bypassPrescaler = true;
139     /* LPTMR clock source */
140     config->prescalerClockSource = kLPTMR_PrescalerClock_1;
141     /* Divide the prescaler clock by 2 */
142     config->value = kLPTMR_Prescale_Glitch_0;
143 }
144