1 /*
2  * SPDX-FileCopyrightText: 2010-2022 Espressif Systems (Shanghai) CO LTD
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  */
6 
7 #pragma once
8 
9 #include <stdint.h>
10 #include <stdbool.h>
11 #include "sdkconfig.h"
12 #include "esp_err.h"
13 #include "driver/timer_types_legacy.h"
14 
15 #if !CONFIG_GPTIMER_SUPPRESS_DEPRECATE_WARN
16 #warning "legacy timer group driver is deprecated, please migrate to driver/gptimer.h"
17 #endif
18 
19 #ifdef __cplusplus
20 extern "C" {
21 #endif
22 
23 /**
24  * @brief Read the counter value of hardware timer.
25  *
26  * @param group_num Timer group, 0 for TIMERG0 or 1 for TIMERG1
27  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
28  * @param timer_val Pointer to accept timer counter value.
29  *
30  * @return
31  *     - ESP_OK Success
32  *     - ESP_ERR_INVALID_ARG Parameter error
33  */
34 esp_err_t timer_get_counter_value(timer_group_t group_num, timer_idx_t timer_num, uint64_t *timer_val);
35 
36 /**
37  * @brief Read the counter value of hardware timer, in unit of a given scale.
38  *
39  * @param group_num Timer group, 0 for TIMERG0 or 1 for TIMERG1
40  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
41  * @param time Pointer, type of double*, to accept timer counter value, in seconds.
42  *
43  * @return
44  *     - ESP_OK Success
45  *     - ESP_ERR_INVALID_ARG Parameter error
46  */
47 esp_err_t timer_get_counter_time_sec(timer_group_t group_num, timer_idx_t timer_num, double *time);
48 
49 /**
50  * @brief Set counter value to hardware timer.
51  *
52  * @param group_num Timer group, 0 for TIMERG0 or 1 for TIMERG1
53  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
54  * @param load_val Counter value to write to the hardware timer.
55  *
56  * @return
57  *     - ESP_OK Success
58  *     - ESP_ERR_INVALID_ARG Parameter error
59  */
60 esp_err_t timer_set_counter_value(timer_group_t group_num, timer_idx_t timer_num, uint64_t load_val);
61 
62 /**
63  * @brief Start the counter of hardware timer.
64  *
65  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
66  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
67  *
68  * @return
69  *     - ESP_OK Success
70  *     - ESP_ERR_INVALID_ARG Parameter error
71  */
72 esp_err_t timer_start(timer_group_t group_num, timer_idx_t timer_num);
73 
74 /**
75  * @brief Pause the counter of hardware timer.
76  *
77  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
78  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
79  *
80  * @return
81  *     - ESP_OK Success
82  *     - ESP_ERR_INVALID_ARG Parameter error
83  */
84 esp_err_t timer_pause(timer_group_t group_num, timer_idx_t timer_num);
85 
86 /**
87  * @brief Set counting mode for hardware timer.
88  *
89  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
90  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
91  * @param counter_dir Counting direction of timer, count-up or count-down
92  *
93  * @return
94  *     - ESP_OK Success
95  *     - ESP_ERR_INVALID_ARG Parameter error
96  */
97 esp_err_t timer_set_counter_mode(timer_group_t group_num, timer_idx_t timer_num, timer_count_dir_t counter_dir);
98 
99 /**
100  * @brief Enable or disable counter reload function when alarm event occurs.
101  *
102  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
103  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
104  * @param reload Counter reload mode.
105  *
106  * @return
107  *     - ESP_OK Success
108  *     - ESP_ERR_INVALID_ARG Parameter error
109  */
110 esp_err_t timer_set_auto_reload(timer_group_t group_num, timer_idx_t timer_num, timer_autoreload_t reload);
111 
112 /**
113  * @brief Set hardware divider of the source clock to the timer group.
114  * By default, the source clock is APB clock running at 80 MHz.
115  * For more information, please check Chapter Reset and Clock in Chip Technical Reference Manual.
116  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
117  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
118  * @param divider Timer clock divider value. The divider's range is from from 2 to 65536.
119  *
120  * @return
121  *     - ESP_OK Success
122  *     - ESP_ERR_INVALID_ARG Parameter error
123  */
124 esp_err_t timer_set_divider(timer_group_t group_num, timer_idx_t timer_num, uint32_t divider);
125 
126 /**
127  * @brief Set timer alarm value.
128  *
129  * @param group_num Timer group, 0 for TIMERG0 or 1 for TIMERG1
130  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
131  * @param alarm_value A 64-bit value to set the alarm value.
132  *
133  * @return
134  *     - ESP_OK Success
135  *     - ESP_ERR_INVALID_ARG Parameter error
136  */
137 esp_err_t timer_set_alarm_value(timer_group_t group_num, timer_idx_t timer_num, uint64_t alarm_value);
138 
139 /**
140  * @brief Get timer alarm value.
141  *
142  * @param group_num Timer group, 0 for TIMERG0 or 1 for TIMERG1
143  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
144  * @param alarm_value Pointer of A 64-bit value to accept the alarm value.
145  *
146  * @return
147  *     - ESP_OK Success
148  *     - ESP_ERR_INVALID_ARG Parameter error
149  */
150 esp_err_t timer_get_alarm_value(timer_group_t group_num, timer_idx_t timer_num, uint64_t *alarm_value);
151 
152 /**
153  * @brief Enable or disable generation of timer alarm events.
154  *
155  * @param group_num Timer group, 0 for TIMERG0 or 1 for TIMERG1
156  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
157  * @param alarm_en To enable or disable timer alarm function.
158  *
159  * @return
160  *     - ESP_OK Success
161  *     - ESP_ERR_INVALID_ARG Parameter error
162  */
163 esp_err_t timer_set_alarm(timer_group_t group_num, timer_idx_t timer_num, timer_alarm_t alarm_en);
164 
165 /**
166  * @brief Add ISR handle callback for the corresponding timer.
167  *
168  * @param group_num Timer group number
169  * @param timer_num Timer index of timer group
170  * @param isr_handler Interrupt handler function, it is a callback function.
171  * @param arg Parameter for handler function
172  * @param intr_alloc_flags Flags used to allocate the interrupt. One or multiple (ORred)
173  *        ESP_INTR_FLAG_* values. See esp_intr_alloc.h for more info.
174  *
175  * @note This ISR handler will be called from an ISR.
176  *       This ISR handler do not need to handle interrupt status, and should be kept short.
177  *       If you want to realize some specific applications or write the whole ISR, you can
178  *       call timer_isr_register(...) to register ISR.
179  *
180  *       The callback should return a bool value to determine whether need to do YIELD at
181  *       the end of the ISR.
182  *
183  *       If the intr_alloc_flags value ESP_INTR_FLAG_IRAM is set,
184  *       the handler function must be declared with IRAM_ATTR attribute
185  *       and can only call functions in IRAM or ROM. It cannot call other timer APIs.
186  *
187  * @return
188  *     - ESP_OK Success
189  *     - ESP_ERR_INVALID_ARG Parameter error
190  */
191 esp_err_t timer_isr_callback_add(timer_group_t group_num, timer_idx_t timer_num, timer_isr_t isr_handler, void *arg, int intr_alloc_flags);
192 
193 /**
194  * @brief Remove ISR handle callback for the corresponding timer.
195  *
196  * @param group_num Timer group number
197  * @param timer_num Timer index of timer group
198  *
199  * @return
200  *     - ESP_OK Success
201  *     - ESP_ERR_INVALID_ARG Parameter error
202  */
203 esp_err_t timer_isr_callback_remove(timer_group_t group_num, timer_idx_t timer_num);
204 
205 /**
206  * @brief Register Timer interrupt handler, the handler is an ISR.
207  *        The handler will be attached to the same CPU core that this function is running on.
208  *
209  * @param group_num Timer group number
210  * @param timer_num Timer index of timer group
211  * @param fn Interrupt handler function.
212  * @param arg Parameter for handler function
213  * @param intr_alloc_flags Flags used to allocate the interrupt. One or multiple (ORred)
214  *        ESP_INTR_FLAG_* values. See esp_intr_alloc.h for more info.
215  * @param handle Pointer to return handle. If non-NULL, a handle for the interrupt will
216  *        be returned here.
217  *
218  * @note If use this function to reigster ISR, you need to write the whole ISR.
219  *       In the interrupt handler, you need to call timer_spinlock_take(..) before
220  *       your handling, and call timer_spinlock_give(...) after your handling.
221  *
222  *       If the intr_alloc_flags value ESP_INTR_FLAG_IRAM is set,
223  *       the handler function must be declared with IRAM_ATTR attribute
224  *       and can only call functions in IRAM or ROM. It cannot call other timer APIs.
225  *       Use direct register access to configure timers from inside the ISR in this case.
226  *
227  * @return
228  *     - ESP_OK Success
229  *     - ESP_ERR_INVALID_ARG Parameter error
230  */
231 esp_err_t timer_isr_register(timer_group_t group_num, timer_idx_t timer_num, void (*fn)(void *), void *arg, int intr_alloc_flags, timer_isr_handle_t *handle);
232 
233 /** @brief Initializes and configure the timer.
234  *
235  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
236  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
237  * @param config Pointer to timer initialization parameters.
238  *
239  * @return
240  *     - ESP_OK Success
241  *     - ESP_ERR_INVALID_ARG Parameter error
242  */
243 esp_err_t timer_init(timer_group_t group_num, timer_idx_t timer_num, const timer_config_t *config);
244 
245 /** @brief Deinitializes the timer.
246  *
247  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
248  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
249  *
250  * @return
251  *     - ESP_OK Success
252  *     - ESP_ERR_INVALID_ARG Parameter error
253  */
254 esp_err_t timer_deinit(timer_group_t group_num, timer_idx_t timer_num);
255 
256 /** @brief Get timer configure value.
257  *
258  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
259  * @param timer_num Timer index, 0 for hw_timer[0] & 1 for hw_timer[1]
260  * @param config Pointer of struct to accept timer parameters.
261  *
262  * @return
263  *     - ESP_OK Success
264  *     - ESP_ERR_INVALID_ARG Parameter error
265  */
266 esp_err_t timer_get_config(timer_group_t group_num, timer_idx_t timer_num, timer_config_t *config);
267 
268 /** @brief Enable timer group interrupt, by enable mask
269  *
270  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
271  * @param intr_mask Timer interrupt enable mask.
272  *          - TIMER_INTR_T0: t0 interrupt
273  *          - TIMER_INTR_T1: t1 interrupt
274  *          - TIMER_INTR_WDT: watchdog interrupt
275  *
276  * @return
277  *     - ESP_OK Success
278  *     - ESP_ERR_INVALID_ARG Parameter error
279  */
280 esp_err_t timer_group_intr_enable(timer_group_t group_num, timer_intr_t intr_mask);
281 
282 /** @brief Disable timer group interrupt, by disable mask
283  *
284  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
285  * @param intr_mask Timer interrupt disable mask.
286  *          - TIMER_INTR_T0: t0 interrupt
287  *          - TIMER_INTR_T1: t1 interrupt
288  *          - TIMER_INTR_WDT: watchdog interrupt
289  *
290  * @return
291  *     - ESP_OK Success
292  *     - ESP_ERR_INVALID_ARG Parameter error
293  */
294 esp_err_t timer_group_intr_disable(timer_group_t group_num, timer_intr_t intr_mask);
295 
296 /** @brief Enable timer interrupt
297  *
298  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
299  * @param timer_num Timer index.
300  *
301  * @return
302  *     - ESP_OK Success
303  *     - ESP_ERR_INVALID_ARG Parameter error
304  */
305 esp_err_t timer_enable_intr(timer_group_t group_num, timer_idx_t timer_num);
306 
307 /** @brief Disable timer interrupt
308  *
309  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
310  * @param timer_num Timer index.
311  *
312  * @return
313  *     - ESP_OK Success
314  *     - ESP_ERR_INVALID_ARG Parameter error
315  */
316 esp_err_t timer_disable_intr(timer_group_t group_num, timer_idx_t timer_num);
317 
318 /** @brief Clear timer interrupt status, just used in ISR
319  *
320  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
321  * @param timer_num Timer index.
322  *
323  */
324 void timer_group_clr_intr_status_in_isr(timer_group_t group_num, timer_idx_t timer_num);
325 
326 /** @brief Enable alarm interrupt, just used in ISR
327  *
328  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
329  * @param timer_num Timer index.
330  *
331  */
332 void timer_group_enable_alarm_in_isr(timer_group_t group_num, timer_idx_t timer_num);
333 
334 /** @brief Get the current counter value, just used in ISR
335  *
336  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
337  * @param timer_num Timer index.
338  *
339  * @return
340  *     - Counter value
341  */
342 uint64_t timer_group_get_counter_value_in_isr(timer_group_t group_num, timer_idx_t timer_num);
343 
344 /** @brief Set the alarm threshold for the timer, just used in ISR
345  *
346  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
347  * @param timer_num Timer index.
348  * @param alarm_val Alarm threshold.
349  *
350  */
351 void timer_group_set_alarm_value_in_isr(timer_group_t group_num, timer_idx_t timer_num, uint64_t alarm_val);
352 
353 /** @brief Enable/disable a counter, just used in ISR
354  *
355  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
356  * @param timer_num Timer index.
357  * @param counter_en Enable/disable.
358  *
359  */
360 void timer_group_set_counter_enable_in_isr(timer_group_t group_num, timer_idx_t timer_num, timer_start_t counter_en);
361 
362 
363 /** @brief Get interrupt status, just used in ISR
364  *
365  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
366  *
367  * @return
368  *     - Interrupt status
369  */
370 uint32_t timer_group_get_intr_status_in_isr(timer_group_t group_num);
371 /** @brief Get auto reload enable status, just used in ISR
372  *
373  * @param group_num Timer group number, 0 for TIMERG0 or 1 for TIMERG1
374  * @param timer_num Timer index
375  *
376  * @return
377  *     - True Auto reload enabled
378  *     - False Auto reload disabled
379  */
380 bool timer_group_get_auto_reload_in_isr(timer_group_t group_num, timer_idx_t timer_num);
381 
382 #ifdef __cplusplus
383 }
384 #endif
385