1 /*
2  * Copyright 2018-2019, 2023 NXP
3  * All rights reserved.
4  *
5  *
6  * SPDX-License-Identifier: BSD-3-Clause
7  */
8 
9 #include "fsl_common.h"
10 #include "fsl_device_registers.h"
11 #include "fsl_adapter_timer.h"
12 #include "fsl_pit.h"
13 
14 typedef struct _hal_timer_handle_struct_t
15 {
16     uint32_t timeout;
17     uint32_t timerClock_Hz;
18     hal_timer_callback_t callback;
19     void *callbackParam;
20     uint8_t instance;
21 } hal_timer_handle_struct_t;
22 
23 /*******************************************************************************
24  * Variables
25  ******************************************************************************/
26 
27 static PIT_Type *const s_PitBase[] = PIT_BASE_PTRS;
28 
29 static hal_timer_handle_t s_timerHandle[sizeof(s_PitBase) / sizeof(PIT_Type *)];
30 /************************************************************************************
31 *************************************************************************************
32 * Private prototypes
33 *************************************************************************************
34 ************************************************************************************/
35 
36 /************************************************************************************
37 *************************************************************************************
38 * Private memory declarations
39 *************************************************************************************
40 ************************************************************************************/
HAL_TimerInterruptHandle(uint8_t instance)41 static void HAL_TimerInterruptHandle(uint8_t instance)
42 {
43     hal_timer_handle_struct_t *halTimerState = (hal_timer_handle_struct_t *)s_timerHandle[instance];
44 
45     PIT_ClearStatusFlags(s_PitBase[halTimerState->instance], kPIT_Chnl_0, PIT_TFLG_TIF_MASK);
46     if (halTimerState->callback != NULL)
47     {
48         halTimerState->callback(halTimerState->callbackParam);
49     }
50 }
51 
52 #if (defined(FSL_FEATURE_SOC_PIT_COUNT) && (FSL_FEATURE_SOC_PIT_COUNT > 0U))
53 void PIT_IRQHandler(void);
PIT_IRQHandler(void)54 void PIT_IRQHandler(void)
55 {
56     HAL_TimerInterruptHandle(0);
57     SDK_ISR_EXIT_BARRIER;
58 }
59 void PIT0_IRQHandler(void);
PIT0_IRQHandler(void)60 void PIT0_IRQHandler(void)
61 {
62     HAL_TimerInterruptHandle(0);
63     SDK_ISR_EXIT_BARRIER;
64 }
65 #endif /* FSL_FEATURE_SOC_PIT_COUNT */
66 
67 #if (defined(FSL_FEATURE_SOC_PIT_COUNT) && (FSL_FEATURE_SOC_PIT_COUNT > 1U))
68 void PIT1_IRQHandler(void);
PIT1_IRQHandler(void)69 void PIT1_IRQHandler(void)
70 {
71     HAL_TimerInterruptHandle(1);
72     SDK_ISR_EXIT_BARRIER;
73 }
74 #endif /* FSL_FEATURE_SOC_PIT_COUNT */
75 
76 #if (defined(FSL_FEATURE_SOC_PIT_COUNT) && (FSL_FEATURE_SOC_PIT_COUNT > 2U))
PIT2_IRQHandler(void)77 void PIT2_IRQHandler(void)
78 {
79     HAL_TimerInterruptHandle(2);
80     SDK_ISR_EXIT_BARRIER;
81 }
82 #endif /* FSL_FEATURE_SOC_PIT_COUNT */
83 
84 #if (defined(FSL_FEATURE_SOC_PIT_COUNT) && (FSL_FEATURE_SOC_PIT_COUNT > 3U))
PIT3_IRQHandler(void)85 void PIT3_IRQHandler(void)
86 {
87     HAL_TimerInterruptHandle(3);
88     SDK_ISR_EXIT_BARRIER;
89 }
90 #endif /* FSL_FEATURE_SOC_PIT_COUNT */
91 /************************************************************************************
92 *************************************************************************************
93 * Public functions
94 *************************************************************************************
95 ************************************************************************************/
HAL_TimerInit(hal_timer_handle_t halTimerHandle,hal_timer_config_t * halTimerConfig)96 hal_timer_status_t HAL_TimerInit(hal_timer_handle_t halTimerHandle, hal_timer_config_t *halTimerConfig)
97 {
98     IRQn_Type instanceIrq[][FSL_FEATURE_PIT_TIMER_COUNT] = PIT_IRQS;
99     IRQn_Type irqId;
100     hal_timer_handle_struct_t *halTimerState = halTimerHandle;
101     /* Structure of initialize PIT */
102     pit_config_t pitConfig;
103 
104     assert(sizeof(hal_timer_handle_struct_t) == HAL_TIMER_HANDLE_SIZE);
105     assert(halTimerConfig);
106     assert(halTimerHandle);
107     assert(halTimerConfig->instance < (sizeof(s_PitBase) / sizeof(PIT_Type *)));
108 
109     halTimerState->timeout  = halTimerConfig->timeout;
110     halTimerState->instance = halTimerConfig->instance;
111     irqId                   = instanceIrq[halTimerState->instance][0];
112     /*
113      * pitConfig.enableRunInDebug = false;
114      */
115     PIT_GetDefaultConfig(&pitConfig);
116     assert(s_PitBase[halTimerState->instance]);
117     /* Init pit module */
118     PIT_Init(s_PitBase[halTimerState->instance], &pitConfig);
119     halTimerState->timerClock_Hz = halTimerConfig->srcClock_Hz;
120     /* Set timer period for channel 0 */
121     PIT_SetTimerPeriod(s_PitBase[halTimerState->instance], kPIT_Chnl_0,
122                        (uint32_t)USEC_TO_COUNT(halTimerState->timeout, halTimerState->timerClock_Hz));
123     /* Enable timer interrupts for channel 0 */
124     PIT_EnableInterrupts(s_PitBase[halTimerState->instance], kPIT_Chnl_0, (uint32_t)kPIT_TimerInterruptEnable);
125     s_timerHandle[halTimerState->instance] = halTimerHandle;
126 
127     NVIC_SetPriority((IRQn_Type)irqId, HAL_TIMER_ISR_PRIORITY);
128     (void)EnableIRQ(irqId);
129     return kStatus_HAL_TimerSuccess;
130 }
131 
132 /*************************************************************************************/
HAL_TimerDeinit(hal_timer_handle_t halTimerHandle)133 void HAL_TimerDeinit(hal_timer_handle_t halTimerHandle)
134 {
135     assert(halTimerHandle);
136     hal_timer_handle_struct_t *halTimerState = halTimerHandle;
137     s_timerHandle[halTimerState->instance]   = NULL;
138     PIT_Deinit(s_PitBase[halTimerState->instance]);
139 }
140 /*************************************************************************************/
HAL_TimerEnable(hal_timer_handle_t halTimerHandle)141 void HAL_TimerEnable(hal_timer_handle_t halTimerHandle)
142 {
143     assert(halTimerHandle);
144     hal_timer_handle_struct_t *halTimerState = halTimerHandle;
145     PIT_StartTimer(s_PitBase[halTimerState->instance], kPIT_Chnl_0);
146 }
147 
148 /*************************************************************************************/
HAL_TimerDisable(hal_timer_handle_t halTimerHandle)149 void HAL_TimerDisable(hal_timer_handle_t halTimerHandle)
150 {
151     assert(halTimerHandle);
152     hal_timer_handle_struct_t *halTimerState = halTimerHandle;
153     PIT_StopTimer(s_PitBase[halTimerState->instance], kPIT_Chnl_0);
154 }
155 
156 /*************************************************************************************/
HAL_TimerInstallCallback(hal_timer_handle_t halTimerHandle,hal_timer_callback_t callback,void * callbackParam)157 void HAL_TimerInstallCallback(hal_timer_handle_t halTimerHandle, hal_timer_callback_t callback, void *callbackParam)
158 {
159     assert(halTimerHandle);
160     hal_timer_handle_struct_t *halTimerState = halTimerHandle;
161     halTimerState->callback                  = callback;
162     halTimerState->callbackParam             = callbackParam;
163 }
164 
HAL_TimerGetMaxTimeout(hal_timer_handle_t halTimerHandle)165 uint32_t HAL_TimerGetMaxTimeout(hal_timer_handle_t halTimerHandle)
166 {
167     uint64_t reserveCount;
168     uint64_t retValue;
169     uint32_t reserveMs = 4U;
170     assert(halTimerHandle);
171     hal_timer_handle_struct_t *halTimerState = halTimerHandle;
172     reserveCount                             = (uint32_t)MSEC_TO_COUNT((reserveMs), (halTimerState->timerClock_Hz));
173 
174     retValue = COUNT_TO_USEC(((uint64_t)0xFFFFFFFF - (uint64_t)reserveCount), (uint64_t)halTimerState->timerClock_Hz);
175     return (uint32_t)((retValue > 0xFFFFFFFFU) ? (0xFFFFFFFFU - reserveMs * 1000U) : (uint32_t)retValue);
176 }
177 /* return micro us */
HAL_TimerGetCurrentTimerCount(hal_timer_handle_t halTimerHandle)178 uint32_t HAL_TimerGetCurrentTimerCount(hal_timer_handle_t halTimerHandle)
179 {
180     assert(halTimerHandle);
181     hal_timer_handle_struct_t *halTimerState = halTimerHandle;
182     return (uint32_t)COUNT_TO_USEC((uint64_t)PIT_GetCurrentTimerCount(s_PitBase[halTimerState->instance], kPIT_Chnl_0),
183                                    halTimerState->timerClock_Hz);
184 }
185 
HAL_TimerUpdateTimeout(hal_timer_handle_t halTimerHandle,uint32_t timeout)186 hal_timer_status_t HAL_TimerUpdateTimeout(hal_timer_handle_t halTimerHandle, uint32_t timeout)
187 {
188     uint32_t tickCount;
189     assert(halTimerHandle);
190     hal_timer_handle_struct_t *halTimerState = halTimerHandle;
191     halTimerState->timeout                   = timeout;
192     tickCount = (uint32_t)USEC_TO_COUNT(halTimerState->timeout, halTimerState->timerClock_Hz);
193     if ((tickCount < 1U) || (tickCount > 0xfffffff0U))
194     {
195         return kStatus_HAL_TimerOutOfRanger;
196     }
197     PIT_SetTimerPeriod(s_PitBase[halTimerState->instance], kPIT_Chnl_0, tickCount);
198     return kStatus_HAL_TimerSuccess;
199 }
200 
HAL_TimerExitLowpower(hal_timer_handle_t halTimerHandle)201 void HAL_TimerExitLowpower(hal_timer_handle_t halTimerHandle)
202 {
203     assert(halTimerHandle);
204 }
205 
HAL_TimerEnterLowpower(hal_timer_handle_t halTimerHandle)206 void HAL_TimerEnterLowpower(hal_timer_handle_t halTimerHandle)
207 {
208     assert(halTimerHandle);
209 }
210