1 /*
2  * Copyright (c) 2014 - 2021, Nordic Semiconductor ASA
3  * All rights reserved.
4  *
5  * SPDX-License-Identifier: BSD-3-Clause
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions are met:
9  *
10  * 1. Redistributions of source code must retain the above copyright notice, this
11  *    list of conditions and the following disclaimer.
12  *
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in the
15  *    documentation and/or other materials provided with the distribution.
16  *
17  * 3. Neither the name of the copyright holder nor the names of its
18  *    contributors may be used to endorse or promote products derived from this
19  *    software without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
22  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
25  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
26  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
27  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
28  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
29  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31  * POSSIBILITY OF SUCH DAMAGE.
32  */
33 
34 #ifndef NRF_TIMER_H__
35 #define NRF_TIMER_H__
36 
37 #include <nrfx.h>
38 
39 #ifdef __cplusplus
40 extern "C" {
41 #endif
42 
43 /**
44  * @defgroup nrf_timer_hal TIMER HAL
45  * @{
46  * @ingroup nrf_timer
47  * @brief   Hardware access layer for managing the TIMER peripheral.
48  */
49 
50 /**
51  * @brief Macro for getting the maximum bit resolution of the specified timer instance.
52  *
53  * @param[in] id Index of the specified timer instance.
54  *
55  * @retval Maximum bit resolution of the specified timer instance.
56  */
57 #define TIMER_MAX_SIZE(id)  NRFX_CONCAT_3(TIMER, id, _MAX_SIZE)
58 
59 /**
60  * @brief Macro for validating the correctness of the bit width resolution setting.
61  *
62  * @param[in] id        Index of the specified timer instance.
63  * @param[in] bit_width Bit width resolution value to be checked.
64  *
65  * @retval true  Timer instance supports the specified bit width resolution value.
66  * @retval false Timer instance does not support the specified bit width resolution value.
67  */
68 #define TIMER_BIT_WIDTH_MAX(id, bit_width) \
69     (TIMER_MAX_SIZE(id) == 8   ? (bit_width == NRF_TIMER_BIT_WIDTH_8)  :  \
70     (TIMER_MAX_SIZE(id) == 16  ? (bit_width == NRF_TIMER_BIT_WIDTH_8)  || \
71                                  (bit_width == NRF_TIMER_BIT_WIDTH_16)  : \
72     (TIMER_MAX_SIZE(id) == 24  ? (bit_width == NRF_TIMER_BIT_WIDTH_8)  || \
73                                  (bit_width == NRF_TIMER_BIT_WIDTH_16) || \
74                                  (bit_width == NRF_TIMER_BIT_WIDTH_24) :  \
75     (TIMER_MAX_SIZE(id) == 32  ? (bit_width == NRF_TIMER_BIT_WIDTH_8)  || \
76                                  (bit_width == NRF_TIMER_BIT_WIDTH_16) || \
77                                  (bit_width == NRF_TIMER_BIT_WIDTH_24) || \
78                                  (bit_width == NRF_TIMER_BIT_WIDTH_32) :  \
79     false))))
80 
81 /**
82  * @brief Macro for checking correctness of bit width configuration for the specified timer.
83  *
84  * @param[in] p_reg     Timer instance register.
85  * @param[in] bit_width Bit width resolution value to be checked.
86  *
87  * @retval true  Timer instance supports the specified bit width resolution value.
88  * @retval false Timer instance does not support the specified bit width resolution value.
89  */
90 #if (TIMER_COUNT == 3) || defined(__NRFX_DOXYGEN__)
91     #define NRF_TIMER_IS_BIT_WIDTH_VALID(p_reg, bit_width) (              \
92            ((p_reg == NRF_TIMER0) && TIMER_BIT_WIDTH_MAX(0, bit_width))   \
93         || ((p_reg == NRF_TIMER1) && TIMER_BIT_WIDTH_MAX(1, bit_width))   \
94         || ((p_reg == NRF_TIMER2) && TIMER_BIT_WIDTH_MAX(2, bit_width)))
95 #elif (TIMER_COUNT == 4)
96     #define NRF_TIMER_IS_BIT_WIDTH_VALID(p_reg, bit_width) (              \
97            ((p_reg == NRF_TIMER0) && TIMER_BIT_WIDTH_MAX(0, bit_width))   \
98         || ((p_reg == NRF_TIMER1) && TIMER_BIT_WIDTH_MAX(1, bit_width))   \
99         || ((p_reg == NRF_TIMER2) && TIMER_BIT_WIDTH_MAX(2, bit_width))   \
100         || ((p_reg == NRF_TIMER3) && TIMER_BIT_WIDTH_MAX(3, bit_width)))
101 #elif (TIMER_COUNT == 5)
102     #define NRF_TIMER_IS_BIT_WIDTH_VALID(p_reg, bit_width) (              \
103            ((p_reg == NRF_TIMER0) && TIMER_BIT_WIDTH_MAX(0, bit_width))   \
104         || ((p_reg == NRF_TIMER1) && TIMER_BIT_WIDTH_MAX(1, bit_width))   \
105         || ((p_reg == NRF_TIMER2) && TIMER_BIT_WIDTH_MAX(2, bit_width))   \
106         || ((p_reg == NRF_TIMER3) && TIMER_BIT_WIDTH_MAX(3, bit_width))   \
107         || ((p_reg == NRF_TIMER4) && TIMER_BIT_WIDTH_MAX(4, bit_width)))
108 #else
109     #error "Not supported timer count"
110 #endif
111 
112 /**
113  * @brief Macro for getting the number of capture/compare channels available
114  *        in a given timer instance.
115  *
116  * @param[in] id Index of the specified timer instance.
117  */
118 #define NRF_TIMER_CC_CHANNEL_COUNT(id)  NRFX_CONCAT_3(TIMER, id, _CC_NUM)
119 
120 
121 /** @brief Timer tasks. */
122 typedef enum
123 {
124     NRF_TIMER_TASK_START    = offsetof(NRF_TIMER_Type, TASKS_START),      ///< Task for starting the timer.
125     NRF_TIMER_TASK_STOP     = offsetof(NRF_TIMER_Type, TASKS_STOP),       ///< Task for stopping the timer.
126     NRF_TIMER_TASK_COUNT    = offsetof(NRF_TIMER_Type, TASKS_COUNT),      ///< Task for incrementing the timer (in counter mode).
127     NRF_TIMER_TASK_CLEAR    = offsetof(NRF_TIMER_Type, TASKS_CLEAR),      ///< Task for resetting the timer value.
128     NRF_TIMER_TASK_SHUTDOWN = offsetof(NRF_TIMER_Type, TASKS_SHUTDOWN),   ///< Task for powering off the timer.
129     NRF_TIMER_TASK_CAPTURE0 = offsetof(NRF_TIMER_Type, TASKS_CAPTURE[0]), ///< Task for capturing the timer value on channel 0.
130     NRF_TIMER_TASK_CAPTURE1 = offsetof(NRF_TIMER_Type, TASKS_CAPTURE[1]), ///< Task for capturing the timer value on channel 1.
131     NRF_TIMER_TASK_CAPTURE2 = offsetof(NRF_TIMER_Type, TASKS_CAPTURE[2]), ///< Task for capturing the timer value on channel 2.
132     NRF_TIMER_TASK_CAPTURE3 = offsetof(NRF_TIMER_Type, TASKS_CAPTURE[3]), ///< Task for capturing the timer value on channel 3.
133 #if defined(TIMER_INTENSET_COMPARE4_Msk) || defined(__NRFX_DOXYGEN__)
134     NRF_TIMER_TASK_CAPTURE4 = offsetof(NRF_TIMER_Type, TASKS_CAPTURE[4]), ///< Task for capturing the timer value on channel 4.
135 #endif
136 #if defined(TIMER_INTENSET_COMPARE5_Msk) || defined(__NRFX_DOXYGEN__)
137     NRF_TIMER_TASK_CAPTURE5 = offsetof(NRF_TIMER_Type, TASKS_CAPTURE[5]), ///< Task for capturing the timer value on channel 5.
138 #endif
139 #if defined(TIMER_INTENSET_COMPARE6_Msk) || defined(__NRFX_DOXYGEN__)
140     NRF_TIMER_TASK_CAPTURE6 = offsetof(NRF_TIMER_Type, TASKS_CAPTURE[6]), ///< Task for capturing the timer value on channel 6.
141 #endif
142 #if defined(TIMER_INTENSET_COMPARE7_Msk) || defined(__NRFX_DOXYGEN__)
143     NRF_TIMER_TASK_CAPTURE7 = offsetof(NRF_TIMER_Type, TASKS_CAPTURE[7]), ///< Task for capturing the timer value on channel 7.
144 #endif
145 } nrf_timer_task_t;
146 
147 /** @brief Timer events. */
148 typedef enum
149 {
150     NRF_TIMER_EVENT_COMPARE0 = offsetof(NRF_TIMER_Type, EVENTS_COMPARE[0]), ///< Event from compare channel 0.
151     NRF_TIMER_EVENT_COMPARE1 = offsetof(NRF_TIMER_Type, EVENTS_COMPARE[1]), ///< Event from compare channel 1.
152     NRF_TIMER_EVENT_COMPARE2 = offsetof(NRF_TIMER_Type, EVENTS_COMPARE[2]), ///< Event from compare channel 2.
153     NRF_TIMER_EVENT_COMPARE3 = offsetof(NRF_TIMER_Type, EVENTS_COMPARE[3]), ///< Event from compare channel 3.
154 #if defined(TIMER_INTENSET_COMPARE4_Msk) || defined(__NRFX_DOXYGEN__)
155     NRF_TIMER_EVENT_COMPARE4 = offsetof(NRF_TIMER_Type, EVENTS_COMPARE[4]), ///< Event from compare channel 4.
156 #endif
157 #if defined(TIMER_INTENSET_COMPARE5_Msk) || defined(__NRFX_DOXYGEN__)
158     NRF_TIMER_EVENT_COMPARE5 = offsetof(NRF_TIMER_Type, EVENTS_COMPARE[5]), ///< Event from compare channel 5.
159 #endif
160 #if defined(TIMER_INTENSET_COMPARE6_Msk) || defined(__NRFX_DOXYGEN__)
161     NRF_TIMER_EVENT_COMPARE6 = offsetof(NRF_TIMER_Type, EVENTS_COMPARE[6]), ///< Event from compare channel 6.
162 #endif
163 #if defined(TIMER_INTENSET_COMPARE7_Msk) || defined(__NRFX_DOXYGEN__)
164     NRF_TIMER_EVENT_COMPARE7 = offsetof(NRF_TIMER_Type, EVENTS_COMPARE[7]), ///< Event from compare channel 7.
165 #endif
166 } nrf_timer_event_t;
167 
168 /** @brief Types of timer shortcuts. */
169 typedef enum
170 {
171     NRF_TIMER_SHORT_COMPARE0_STOP_MASK = TIMER_SHORTS_COMPARE0_STOP_Msk,   ///< Shortcut for stopping the timer based on compare 0.
172     NRF_TIMER_SHORT_COMPARE1_STOP_MASK = TIMER_SHORTS_COMPARE1_STOP_Msk,   ///< Shortcut for stopping the timer based on compare 1.
173     NRF_TIMER_SHORT_COMPARE2_STOP_MASK = TIMER_SHORTS_COMPARE2_STOP_Msk,   ///< Shortcut for stopping the timer based on compare 2.
174     NRF_TIMER_SHORT_COMPARE3_STOP_MASK = TIMER_SHORTS_COMPARE3_STOP_Msk,   ///< Shortcut for stopping the timer based on compare 3.
175 #if defined(TIMER_INTENSET_COMPARE4_Msk) || defined(__NRFX_DOXYGEN__)
176     NRF_TIMER_SHORT_COMPARE4_STOP_MASK = TIMER_SHORTS_COMPARE4_STOP_Msk,   ///< Shortcut for stopping the timer based on compare 4.
177 #endif
178 #if defined(TIMER_INTENSET_COMPARE5_Msk) || defined(__NRFX_DOXYGEN__)
179     NRF_TIMER_SHORT_COMPARE5_STOP_MASK = TIMER_SHORTS_COMPARE5_STOP_Msk,   ///< Shortcut for stopping the timer based on compare 5.
180 #endif
181     NRF_TIMER_SHORT_COMPARE0_CLEAR_MASK = TIMER_SHORTS_COMPARE0_CLEAR_Msk, ///< Shortcut for clearing the timer based on compare 0.
182     NRF_TIMER_SHORT_COMPARE1_CLEAR_MASK = TIMER_SHORTS_COMPARE1_CLEAR_Msk, ///< Shortcut for clearing the timer based on compare 1.
183     NRF_TIMER_SHORT_COMPARE2_CLEAR_MASK = TIMER_SHORTS_COMPARE2_CLEAR_Msk, ///< Shortcut for clearing the timer based on compare 2.
184     NRF_TIMER_SHORT_COMPARE3_CLEAR_MASK = TIMER_SHORTS_COMPARE3_CLEAR_Msk, ///< Shortcut for clearing the timer based on compare 3.
185 #if defined(TIMER_INTENSET_COMPARE4_Msk) || defined(__NRFX_DOXYGEN__)
186     NRF_TIMER_SHORT_COMPARE4_CLEAR_MASK = TIMER_SHORTS_COMPARE4_CLEAR_Msk, ///< Shortcut for clearing the timer based on compare 4.
187 #endif
188 #if defined(TIMER_INTENSET_COMPARE5_Msk) || defined(__NRFX_DOXYGEN__)
189     NRF_TIMER_SHORT_COMPARE5_CLEAR_MASK = TIMER_SHORTS_COMPARE5_CLEAR_Msk, ///< Shortcut for clearing the timer based on compare 5.
190 #endif
191 } nrf_timer_short_mask_t;
192 
193 /** @brief Timer modes. */
194 typedef enum
195 {
196     NRF_TIMER_MODE_TIMER             = TIMER_MODE_MODE_Timer,           ///< Timer mode: timer.
197     NRF_TIMER_MODE_COUNTER           = TIMER_MODE_MODE_Counter,         ///< Timer mode: counter.
198 #if defined(TIMER_MODE_MODE_LowPowerCounter) || defined(__NRFX_DOXYGEN__)
199     NRF_TIMER_MODE_LOW_POWER_COUNTER = TIMER_MODE_MODE_LowPowerCounter, ///< Timer mode: low-power counter.
200 #endif
201 } nrf_timer_mode_t;
202 
203 /** @brief Timer bit width. */
204 typedef enum
205 {
206     NRF_TIMER_BIT_WIDTH_8  = TIMER_BITMODE_BITMODE_08Bit, ///< Timer bit width 8 bit.
207     NRF_TIMER_BIT_WIDTH_16 = TIMER_BITMODE_BITMODE_16Bit, ///< Timer bit width 16 bit.
208     NRF_TIMER_BIT_WIDTH_24 = TIMER_BITMODE_BITMODE_24Bit, ///< Timer bit width 24 bit.
209     NRF_TIMER_BIT_WIDTH_32 = TIMER_BITMODE_BITMODE_32Bit  ///< Timer bit width 32 bit.
210 } nrf_timer_bit_width_t;
211 
212 /** @brief Timer prescalers. */
213 typedef enum
214 {
215     NRF_TIMER_FREQ_16MHz = 0, ///< Timer frequency 16 MHz.
216     NRF_TIMER_FREQ_8MHz,      ///< Timer frequency 8 MHz.
217     NRF_TIMER_FREQ_4MHz,      ///< Timer frequency 4 MHz.
218     NRF_TIMER_FREQ_2MHz,      ///< Timer frequency 2 MHz.
219     NRF_TIMER_FREQ_1MHz,      ///< Timer frequency 1 MHz.
220     NRF_TIMER_FREQ_500kHz,    ///< Timer frequency 500 kHz.
221     NRF_TIMER_FREQ_250kHz,    ///< Timer frequency 250 kHz.
222     NRF_TIMER_FREQ_125kHz,    ///< Timer frequency 125 kHz.
223     NRF_TIMER_FREQ_62500Hz,   ///< Timer frequency 62500 Hz.
224     NRF_TIMER_FREQ_31250Hz    ///< Timer frequency 31250 Hz.
225 } nrf_timer_frequency_t;
226 
227 /** @brief Timer capture/compare channels. */
228 typedef enum
229 {
230     NRF_TIMER_CC_CHANNEL0 = 0, ///< Timer capture/compare channel 0.
231     NRF_TIMER_CC_CHANNEL1,     ///< Timer capture/compare channel 1.
232     NRF_TIMER_CC_CHANNEL2,     ///< Timer capture/compare channel 2.
233     NRF_TIMER_CC_CHANNEL3,     ///< Timer capture/compare channel 3.
234 #if defined(TIMER_INTENSET_COMPARE4_Msk) || defined(__NRFX_DOXYGEN__)
235     NRF_TIMER_CC_CHANNEL4,     ///< Timer capture/compare channel 4.
236 #endif
237 #if defined(TIMER_INTENSET_COMPARE5_Msk) || defined(__NRFX_DOXYGEN__)
238     NRF_TIMER_CC_CHANNEL5,     ///< Timer capture/compare channel 5.
239 #endif
240 } nrf_timer_cc_channel_t;
241 
242 /** @brief Timer interrupts. */
243 typedef enum
244 {
245     NRF_TIMER_INT_COMPARE0_MASK = TIMER_INTENSET_COMPARE0_Msk, ///< Timer interrupt from compare event on channel 0.
246     NRF_TIMER_INT_COMPARE1_MASK = TIMER_INTENSET_COMPARE1_Msk, ///< Timer interrupt from compare event on channel 1.
247     NRF_TIMER_INT_COMPARE2_MASK = TIMER_INTENSET_COMPARE2_Msk, ///< Timer interrupt from compare event on channel 2.
248     NRF_TIMER_INT_COMPARE3_MASK = TIMER_INTENSET_COMPARE3_Msk, ///< Timer interrupt from compare event on channel 3.
249 #if defined(TIMER_INTENSET_COMPARE4_Msk) || defined(__NRFX_DOXYGEN__)
250     NRF_TIMER_INT_COMPARE4_MASK = TIMER_INTENSET_COMPARE4_Msk, ///< Timer interrupt from compare event on channel 4.
251 #endif
252 #if defined(TIMER_INTENSET_COMPARE5_Msk) || defined(__NRFX_DOXYGEN__)
253     NRF_TIMER_INT_COMPARE5_MASK = TIMER_INTENSET_COMPARE5_Msk, ///< Timer interrupt from compare event on channel 5.
254 #endif
255 } nrf_timer_int_mask_t;
256 
257 
258 /**
259  * @brief Function for activating the specified timer task.
260  *
261  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
262  * @param[in] task  Task to be activated.
263  */
264 NRF_STATIC_INLINE void nrf_timer_task_trigger(NRF_TIMER_Type * p_reg,
265                                               nrf_timer_task_t task);
266 
267 /**
268  * @brief Function for getting the address of the specified timer task register.
269  *
270  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
271  * @param[in] task  The specified task.
272  *
273  * @return Address of the specified task register.
274  */
275 NRF_STATIC_INLINE uint32_t nrf_timer_task_address_get(NRF_TIMER_Type const * p_reg,
276                                                       nrf_timer_task_t       task);
277 
278 /**
279  * @brief Function for clearing the specified timer event.
280  *
281  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
282  * @param[in] event Event to clear.
283  */
284 NRF_STATIC_INLINE void nrf_timer_event_clear(NRF_TIMER_Type *  p_reg,
285                                              nrf_timer_event_t event);
286 
287 /**
288  * @brief Function for retrieving the state of the TIMER event.
289  *
290  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
291  * @param[in] event Event to be checked.
292  *
293  * @retval true  The event has been generated.
294  * @retval false The event has not been generated.
295  */
296 NRF_STATIC_INLINE bool nrf_timer_event_check(NRF_TIMER_Type const * p_reg,
297                                              nrf_timer_event_t      event);
298 
299 /**
300  * @brief Function for getting the address of the specified timer event register.
301  *
302  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
303  * @param[in] event The specified event.
304  *
305  * @return Address of the specified event register.
306  */
307 NRF_STATIC_INLINE uint32_t nrf_timer_event_address_get(NRF_TIMER_Type const * p_reg,
308                                                        nrf_timer_event_t      event);
309 
310 /**
311  * @brief Function for enabling the specified shortcuts.
312  *
313  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
314  * @param[in] mask  Shortcuts to be enabled.
315  */
316 NRF_STATIC_INLINE void nrf_timer_shorts_enable(NRF_TIMER_Type * p_reg,
317                                                uint32_t         mask);
318 
319 /**
320  * @brief Function for disabling the specified shortcuts.
321  *
322  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
323  * @param[in] mask  Shortcuts to be disabled.
324  */
325 NRF_STATIC_INLINE void nrf_timer_shorts_disable(NRF_TIMER_Type * p_reg,
326                                                 uint32_t         mask);
327 
328 /**
329  * @brief Function for setting the specified shortcuts.
330  *
331  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
332  * @param[in] mask  Shortcuts to be set.
333  */
334 NRF_STATIC_INLINE void nrf_timer_shorts_set(NRF_TIMER_Type * p_reg,
335                                             uint32_t         mask);
336 
337 /**
338  * @brief Function for enabling the specified interrupts.
339  *
340  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
341  * @param[in] mask  Mask of interrupts to be enabled.
342  */
343 NRF_STATIC_INLINE void nrf_timer_int_enable(NRF_TIMER_Type * p_reg,
344                                             uint32_t         mask);
345 
346 /**
347  * @brief Function for disabling the specified interrupts.
348  *
349  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
350  * @param[in] mask  Mask of interrupts to be disabled.
351  */
352 NRF_STATIC_INLINE void nrf_timer_int_disable(NRF_TIMER_Type * p_reg,
353                                              uint32_t         mask);
354 
355 /**
356  * @brief Function for checking if the specified interrupts are enabled.
357  *
358  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
359  * @param[in] mask  Mask of interrupts to be checked.
360  *
361  * @return Mask of enabled interrupts.
362  */
363 NRF_STATIC_INLINE uint32_t nrf_timer_int_enable_check(NRF_TIMER_Type const * p_reg, uint32_t mask);
364 
365 #if defined(DPPI_PRESENT) || defined(__NRFX_DOXYGEN__)
366 /**
367  * @brief Function for setting the subscribe configuration for a given
368  *        TIMER task.
369  *
370  * @param[in] p_reg   Pointer to the structure of registers of the peripheral.
371  * @param[in] task    Task for which to set the configuration.
372  * @param[in] channel Channel through which to subscribe events.
373  */
374 NRF_STATIC_INLINE void nrf_timer_subscribe_set(NRF_TIMER_Type * p_reg,
375                                                nrf_timer_task_t task,
376                                                uint8_t          channel);
377 
378 /**
379  * @brief Function for clearing the subscribe configuration for a given
380  *        TIMER task.
381  *
382  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
383  * @param[in] task  Task for which to clear the configuration.
384  */
385 NRF_STATIC_INLINE void nrf_timer_subscribe_clear(NRF_TIMER_Type * p_reg,
386                                                  nrf_timer_task_t task);
387 
388 /**
389  * @brief Function for setting the publish configuration for a given
390  *        TIMER event.
391  *
392  * @param[in] p_reg   Pointer to the structure of registers of the peripheral.
393  * @param[in] event   Event for which to set the configuration.
394  * @param[in] channel Channel through which to publish the event.
395  */
396 NRF_STATIC_INLINE void nrf_timer_publish_set(NRF_TIMER_Type *  p_reg,
397                                              nrf_timer_event_t event,
398                                              uint8_t           channel);
399 
400 /**
401  * @brief Function for clearing the publish configuration for a given
402  *        TIMER event.
403  *
404  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
405  * @param[in] event Event for which to clear the configuration.
406  */
407 NRF_STATIC_INLINE void nrf_timer_publish_clear(NRF_TIMER_Type *  p_reg,
408                                                nrf_timer_event_t event);
409 #endif // defined(DPPI_PRESENT) || defined(__NRFX_DOXYGEN__)
410 
411 /**
412  * @brief Function for setting the timer mode.
413  *
414  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
415  * @param[in] mode  Timer mode.
416  */
417 NRF_STATIC_INLINE void nrf_timer_mode_set(NRF_TIMER_Type * p_reg,
418                                           nrf_timer_mode_t mode);
419 
420 /**
421  * @brief Function for retrieving the timer mode.
422  *
423  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
424  *
425  * @return Timer mode.
426  */
427 NRF_STATIC_INLINE nrf_timer_mode_t nrf_timer_mode_get(NRF_TIMER_Type const * p_reg);
428 
429 /**
430  * @brief Function for setting the timer bit width.
431  *
432  * @param[in] p_reg     Pointer to the structure of registers of the peripheral.
433  * @param[in] bit_width Timer bit width.
434  */
435 NRF_STATIC_INLINE void nrf_timer_bit_width_set(NRF_TIMER_Type *      p_reg,
436                                                nrf_timer_bit_width_t bit_width);
437 
438 /**
439  * @brief Function for retrieving the timer bit width.
440  *
441  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
442  *
443  * @return Timer bit width.
444  */
445 NRF_STATIC_INLINE nrf_timer_bit_width_t nrf_timer_bit_width_get(NRF_TIMER_Type const * p_reg);
446 
447 /**
448  * @brief Function for setting the timer frequency.
449  *
450  * @param[in] p_reg     Pointer to the structure of registers of the peripheral.
451  * @param[in] frequency Timer frequency.
452  */
453 NRF_STATIC_INLINE void nrf_timer_frequency_set(NRF_TIMER_Type *      p_reg,
454                                                nrf_timer_frequency_t frequency);
455 
456 /**
457  * @brief Function for retrieving the timer frequency.
458  *
459  * @param[in] p_reg Pointer to the structure of registers of the peripheral.
460  *
461  * @return Timer frequency.
462  */
463 NRF_STATIC_INLINE nrf_timer_frequency_t nrf_timer_frequency_get(NRF_TIMER_Type const * p_reg);
464 
465 /**
466  * @brief Function for setting the capture/compare register for the specified channel.
467  *
468  * @param[in] p_reg      Pointer to the structure of registers of the peripheral.
469  * @param[in] cc_channel The specified capture/compare channel.
470  * @param[in] cc_value   Value to write to the capture/compare register.
471  */
472 NRF_STATIC_INLINE void nrf_timer_cc_set(NRF_TIMER_Type *       p_reg,
473                                         nrf_timer_cc_channel_t cc_channel,
474                                         uint32_t               cc_value);
475 
476 /**
477  * @brief Function for retrieving the capture/compare value for a specified channel.
478  *
479  * @param[in] p_reg      Pointer to the structure of registers of the peripheral.
480  * @param[in] cc_channel The specified capture/compare channel.
481  *
482  * @return Value from the specified capture/compare register.
483  */
484 NRF_STATIC_INLINE uint32_t nrf_timer_cc_get(NRF_TIMER_Type const * p_reg,
485                                             nrf_timer_cc_channel_t cc_channel);
486 
487 /**
488  * @brief Function for getting the specified timer capture task.
489  *
490  * @param[in] channel Capture channel.
491  *
492  * @return Capture task.
493  */
494 NRF_STATIC_INLINE nrf_timer_task_t nrf_timer_capture_task_get(uint32_t channel);
495 
496 /**
497  * @brief Function for getting the specified timer compare event.
498  *
499  * @param[in] channel Compare channel.
500  *
501  * @return Compare event.
502  */
503 NRF_STATIC_INLINE nrf_timer_event_t nrf_timer_compare_event_get(uint32_t channel);
504 
505 /**
506  * @brief Function for getting the specified timer compare interrupt.
507  *
508  * @param[in] channel Compare channel.
509  *
510  * @return Compare interrupt.
511  */
512 NRF_STATIC_INLINE nrf_timer_int_mask_t nrf_timer_compare_int_get(uint32_t channel);
513 
514 /**
515  * @brief Function for calculating the number of timer ticks for a given time
516  *        (in microseconds) and timer frequency.
517  *
518  * @param[in] time_us   Time in microseconds.
519  * @param[in] frequency Timer frequency.
520  *
521  * @return Number of timer ticks.
522  */
523 NRF_STATIC_INLINE uint32_t nrf_timer_us_to_ticks(uint32_t              time_us,
524                                                  nrf_timer_frequency_t frequency);
525 
526 /**
527  * @brief Function for calculating the number of timer ticks for a given time
528  *        (in milliseconds) and timer frequency.
529  *
530  * @param[in] time_ms   Time in milliseconds.
531  * @param[in] frequency Timer frequency.
532  *
533  * @return Number of timer ticks.
534  */
535 NRF_STATIC_INLINE uint32_t nrf_timer_ms_to_ticks(uint32_t              time_ms,
536                                                  nrf_timer_frequency_t frequency);
537 
538 #if defined(TIMER_ONESHOTEN_ONESHOTEN_Msk) || defined(__NRFX_DOXYGEN__)
539 /**
540  * @brief Function for enabling one-shot operation for the specified capture/compare channel.
541  *
542  * @param[in] p_reg      Pointer to the structure of registers of the peripheral.
543  * @param[in] cc_channel Capture/compare channel.
544  */
545 NRF_STATIC_INLINE void nrf_timer_one_shot_enable(NRF_TIMER_Type *       p_reg,
546                                                  nrf_timer_cc_channel_t cc_channel);
547 
548 /**
549  * @brief Function for disabling one-shot operation for the specified capture/compare channel.
550  *
551  * @param[in] p_reg      Pointer to the structure of registers of the peripheral.
552  * @param[in] cc_channel Capture/compare channel.
553  */
554 NRF_STATIC_INLINE void nrf_timer_one_shot_disable(NRF_TIMER_Type *       p_reg,
555                                                   nrf_timer_cc_channel_t cc_channel);
556 
557 #endif // defined(TIMER_ONESHOTEN_ONESHOTEN_Msk) || defined(__NRFX_DOXYGEN__)
558 
559 #ifndef NRF_DECLARE_ONLY
560 
nrf_timer_task_trigger(NRF_TIMER_Type * p_reg,nrf_timer_task_t task)561 NRF_STATIC_INLINE void nrf_timer_task_trigger(NRF_TIMER_Type * p_reg,
562                                               nrf_timer_task_t task)
563 {
564     *((volatile uint32_t *)((uint8_t *)p_reg + (uint32_t)task)) = 0x1UL;
565 }
566 
nrf_timer_task_address_get(NRF_TIMER_Type const * p_reg,nrf_timer_task_t task)567 NRF_STATIC_INLINE uint32_t nrf_timer_task_address_get(NRF_TIMER_Type const * p_reg,
568                                                       nrf_timer_task_t       task)
569 {
570     return (uint32_t)((uint8_t *)p_reg + (uint32_t)task);
571 }
572 
nrf_timer_event_clear(NRF_TIMER_Type * p_reg,nrf_timer_event_t event)573 NRF_STATIC_INLINE void nrf_timer_event_clear(NRF_TIMER_Type *  p_reg,
574                                              nrf_timer_event_t event)
575 {
576     *((volatile uint32_t *)((uint8_t *)p_reg + (uint32_t)event)) = 0x0UL;
577     nrf_event_readback((uint8_t *)p_reg + (uint32_t)event);
578 }
579 
nrf_timer_event_check(NRF_TIMER_Type const * p_reg,nrf_timer_event_t event)580 NRF_STATIC_INLINE bool nrf_timer_event_check(NRF_TIMER_Type const * p_reg,
581                                              nrf_timer_event_t      event)
582 {
583     return (bool)*(volatile uint32_t *)((uint8_t *)p_reg + (uint32_t)event);
584 }
585 
nrf_timer_event_address_get(NRF_TIMER_Type const * p_reg,nrf_timer_event_t event)586 NRF_STATIC_INLINE uint32_t nrf_timer_event_address_get(NRF_TIMER_Type const * p_reg,
587                                                        nrf_timer_event_t      event)
588 {
589     return (uint32_t)((uint8_t *)p_reg + (uint32_t)event);
590 }
591 
nrf_timer_shorts_enable(NRF_TIMER_Type * p_reg,uint32_t mask)592 NRF_STATIC_INLINE void nrf_timer_shorts_enable(NRF_TIMER_Type * p_reg,
593                                                uint32_t         mask)
594 {
595     p_reg->SHORTS |= mask;
596 }
597 
nrf_timer_shorts_disable(NRF_TIMER_Type * p_reg,uint32_t mask)598 NRF_STATIC_INLINE void nrf_timer_shorts_disable(NRF_TIMER_Type * p_reg,
599                                                 uint32_t         mask)
600 {
601     p_reg->SHORTS &= ~(mask);
602 }
603 
nrf_timer_shorts_set(NRF_TIMER_Type * p_reg,uint32_t mask)604 NRF_STATIC_INLINE void nrf_timer_shorts_set(NRF_TIMER_Type * p_reg,
605                                             uint32_t         mask)
606 {
607     p_reg->SHORTS = mask;
608 }
609 
nrf_timer_int_enable(NRF_TIMER_Type * p_reg,uint32_t mask)610 NRF_STATIC_INLINE void nrf_timer_int_enable(NRF_TIMER_Type * p_reg,
611                                             uint32_t         mask)
612 {
613     p_reg->INTENSET = mask;
614 }
615 
nrf_timer_int_disable(NRF_TIMER_Type * p_reg,uint32_t mask)616 NRF_STATIC_INLINE void nrf_timer_int_disable(NRF_TIMER_Type * p_reg,
617                                              uint32_t         mask)
618 {
619     p_reg->INTENCLR = mask;
620 }
621 
nrf_timer_int_enable_check(NRF_TIMER_Type const * p_reg,uint32_t mask)622 NRF_STATIC_INLINE uint32_t nrf_timer_int_enable_check(NRF_TIMER_Type const * p_reg, uint32_t mask)
623 {
624     return p_reg->INTENSET & mask;
625 }
626 
627 #if defined(DPPI_PRESENT)
nrf_timer_subscribe_set(NRF_TIMER_Type * p_reg,nrf_timer_task_t task,uint8_t channel)628 NRF_STATIC_INLINE void nrf_timer_subscribe_set(NRF_TIMER_Type * p_reg,
629                                                nrf_timer_task_t task,
630                                                uint8_t          channel)
631 {
632     *((volatile uint32_t *) ((uint8_t *) p_reg + (uint32_t) task + 0x80uL)) =
633             ((uint32_t)channel | TIMER_SUBSCRIBE_START_EN_Msk);
634 }
635 
nrf_timer_subscribe_clear(NRF_TIMER_Type * p_reg,nrf_timer_task_t task)636 NRF_STATIC_INLINE void nrf_timer_subscribe_clear(NRF_TIMER_Type * p_reg,
637                                                  nrf_timer_task_t task)
638 {
639     *((volatile uint32_t *) ((uint8_t *) p_reg + (uint32_t) task + 0x80uL)) = 0;
640 }
641 
nrf_timer_publish_set(NRF_TIMER_Type * p_reg,nrf_timer_event_t event,uint8_t channel)642 NRF_STATIC_INLINE void nrf_timer_publish_set(NRF_TIMER_Type *  p_reg,
643                                              nrf_timer_event_t event,
644                                              uint8_t           channel)
645 {
646     *((volatile uint32_t *) ((uint8_t *) p_reg + (uint32_t) event + 0x80uL)) =
647             ((uint32_t)channel | TIMER_PUBLISH_COMPARE_EN_Msk);
648 }
649 
nrf_timer_publish_clear(NRF_TIMER_Type * p_reg,nrf_timer_event_t event)650 NRF_STATIC_INLINE void nrf_timer_publish_clear(NRF_TIMER_Type *  p_reg,
651                                                nrf_timer_event_t event)
652 {
653     *((volatile uint32_t *) ((uint8_t *) p_reg + (uint32_t) event + 0x80uL)) = 0;
654 }
655 #endif // defined(DPPI_PRESENT)
656 
nrf_timer_mode_set(NRF_TIMER_Type * p_reg,nrf_timer_mode_t mode)657 NRF_STATIC_INLINE void nrf_timer_mode_set(NRF_TIMER_Type * p_reg,
658                                           nrf_timer_mode_t mode)
659 {
660     p_reg->MODE = (p_reg->MODE & ~TIMER_MODE_MODE_Msk) |
661                     ((mode << TIMER_MODE_MODE_Pos) & TIMER_MODE_MODE_Msk);
662 }
663 
nrf_timer_mode_get(NRF_TIMER_Type const * p_reg)664 NRF_STATIC_INLINE nrf_timer_mode_t nrf_timer_mode_get(NRF_TIMER_Type const * p_reg)
665 {
666     return (nrf_timer_mode_t)(p_reg->MODE);
667 }
668 
nrf_timer_bit_width_set(NRF_TIMER_Type * p_reg,nrf_timer_bit_width_t bit_width)669 NRF_STATIC_INLINE void nrf_timer_bit_width_set(NRF_TIMER_Type *      p_reg,
670                                                nrf_timer_bit_width_t bit_width)
671 {
672     p_reg->BITMODE = (p_reg->BITMODE & ~TIMER_BITMODE_BITMODE_Msk) |
673                        ((bit_width << TIMER_BITMODE_BITMODE_Pos) &
674                             TIMER_BITMODE_BITMODE_Msk);
675 }
676 
nrf_timer_bit_width_get(NRF_TIMER_Type const * p_reg)677 NRF_STATIC_INLINE nrf_timer_bit_width_t nrf_timer_bit_width_get(NRF_TIMER_Type const * p_reg)
678 {
679     return (nrf_timer_bit_width_t)(p_reg->BITMODE);
680 }
681 
nrf_timer_frequency_set(NRF_TIMER_Type * p_reg,nrf_timer_frequency_t frequency)682 NRF_STATIC_INLINE void nrf_timer_frequency_set(NRF_TIMER_Type *      p_reg,
683                                                nrf_timer_frequency_t frequency)
684 {
685     p_reg->PRESCALER = (p_reg->PRESCALER & ~TIMER_PRESCALER_PRESCALER_Msk) |
686                          ((frequency << TIMER_PRESCALER_PRESCALER_Pos) &
687                               TIMER_PRESCALER_PRESCALER_Msk);
688 }
689 
nrf_timer_frequency_get(NRF_TIMER_Type const * p_reg)690 NRF_STATIC_INLINE nrf_timer_frequency_t nrf_timer_frequency_get(NRF_TIMER_Type const * p_reg)
691 {
692     return (nrf_timer_frequency_t)(p_reg->PRESCALER);
693 }
694 
nrf_timer_cc_set(NRF_TIMER_Type * p_reg,nrf_timer_cc_channel_t cc_channel,uint32_t cc_value)695 NRF_STATIC_INLINE void nrf_timer_cc_set(NRF_TIMER_Type *       p_reg,
696                                         nrf_timer_cc_channel_t cc_channel,
697                                         uint32_t               cc_value)
698 {
699     p_reg->CC[cc_channel] = cc_value;
700 }
701 
nrf_timer_cc_get(NRF_TIMER_Type const * p_reg,nrf_timer_cc_channel_t cc_channel)702 NRF_STATIC_INLINE uint32_t nrf_timer_cc_get(NRF_TIMER_Type const * p_reg,
703                                             nrf_timer_cc_channel_t cc_channel)
704 {
705     return (uint32_t)p_reg->CC[cc_channel];
706 }
707 
nrf_timer_capture_task_get(uint32_t channel)708 NRF_STATIC_INLINE nrf_timer_task_t nrf_timer_capture_task_get(uint32_t channel)
709 {
710     return (nrf_timer_task_t)NRFX_OFFSETOF(NRF_TIMER_Type, TASKS_CAPTURE[channel]);
711 }
712 
nrf_timer_compare_event_get(uint32_t channel)713 NRF_STATIC_INLINE nrf_timer_event_t nrf_timer_compare_event_get(uint32_t channel)
714 {
715     return (nrf_timer_event_t)NRFX_OFFSETOF(NRF_TIMER_Type, EVENTS_COMPARE[channel]);
716 }
717 
nrf_timer_compare_int_get(uint32_t channel)718 NRF_STATIC_INLINE nrf_timer_int_mask_t nrf_timer_compare_int_get(uint32_t channel)
719 {
720     return (nrf_timer_int_mask_t)
721         ((uint32_t)NRF_TIMER_INT_COMPARE0_MASK << channel);
722 }
723 
nrf_timer_us_to_ticks(uint32_t time_us,nrf_timer_frequency_t frequency)724 NRF_STATIC_INLINE uint32_t nrf_timer_us_to_ticks(uint32_t              time_us,
725                                                  nrf_timer_frequency_t frequency)
726 {
727     // The "frequency" parameter here is actually the prescaler value, and the
728     // timer runs at the following frequency: f = 16 MHz / 2^prescaler.
729     uint32_t prescaler = (uint32_t)frequency;
730     uint64_t ticks = ((time_us * 16ULL) >> prescaler);
731     NRFX_ASSERT(ticks <= UINT32_MAX);
732     return (uint32_t)ticks;
733 }
734 
nrf_timer_ms_to_ticks(uint32_t time_ms,nrf_timer_frequency_t frequency)735 NRF_STATIC_INLINE uint32_t nrf_timer_ms_to_ticks(uint32_t              time_ms,
736                                                  nrf_timer_frequency_t frequency)
737 {
738     // The "frequency" parameter here is actually the prescaler value, and the
739     // timer runs at the following frequency: f = 16000 kHz / 2^prescaler.
740     uint32_t prescaler = (uint32_t)frequency;
741     uint64_t ticks = ((time_ms * 16000ULL) >> prescaler);
742     NRFX_ASSERT(ticks <= UINT32_MAX);
743     return (uint32_t)ticks;
744 }
745 
746 #if defined(TIMER_ONESHOTEN_ONESHOTEN_Msk)
nrf_timer_one_shot_enable(NRF_TIMER_Type * p_reg,nrf_timer_cc_channel_t cc_channel)747 NRF_STATIC_INLINE void nrf_timer_one_shot_enable(NRF_TIMER_Type *       p_reg,
748                                                  nrf_timer_cc_channel_t cc_channel)
749 {
750     p_reg->ONESHOTEN[cc_channel] = TIMER_ONESHOTEN_ONESHOTEN_Msk;
751 }
752 
nrf_timer_one_shot_disable(NRF_TIMER_Type * p_reg,nrf_timer_cc_channel_t cc_channel)753 NRF_STATIC_INLINE void nrf_timer_one_shot_disable(NRF_TIMER_Type *       p_reg,
754                                                   nrf_timer_cc_channel_t cc_channel)
755 {
756     p_reg->ONESHOTEN[cc_channel] = 0;
757 }
758 #endif // defined(TIMER_ONESHOTEN_ONESHOTEN_Msk)
759 
760 #endif // NRF_DECLARE_ONLY
761 
762 /** @} */
763 
764 #ifdef __cplusplus
765 }
766 #endif
767 
768 #endif // NRF_TIMER_H__
769