1 /*
2 * Copyright (c) 2014-2018, 2021 The Linux Foundation. All rights reserved.
3 * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved.
4 *
5 * Permission to use, copy, modify, and/or distribute this software for
6 * any purpose with or without fee is hereby granted, provided that the
7 * above copyright notice and this permission notice appear in all
8 * copies.
9 *
10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
11 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
12 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
13 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
14 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
15 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
16 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
17 * PERFORMANCE OF THIS SOFTWARE.
18 */
19
20 /**
21 * DOC: qdf_hrtimer
22 * This file abstracts high resolution timers running in hardware context.
23 */
24
25 #ifndef _QDF_HRTIMER_H
26 #define _QDF_HRTIMER_H
27
28 #include <qdf_types.h>
29 #include <i_qdf_hrtimer.h>
30 #include <qdf_time.h>
31
32 /* Context independent hrtimer object */
33 typedef __qdf_hrtimer_data_t qdf_hrtimer_data_t;
34
35 /* Platform independent timer callback function */
36 typedef enum qdf_hrtimer_restart_status(*qdf_hrtimer_func_t)
37 (qdf_hrtimer_data_t *timer);
38
39 #ifdef ENHANCED_OS_ABSTRACTION
40 /**
41 * qdf_hrtimer_start() - Starts hrtimer in given context
42 * @timer: pointer to the qdf_hrtimer_data_t object
43 * @interval: interval to forward as qdf_ktime_t object
44 * @mode: mode of qdf_hrtimer_data_t
45 *
46 * Starts hrtimer in given context
47 *
48 * Return: void
49 */
50 void qdf_hrtimer_start(qdf_hrtimer_data_t *timer, qdf_ktime_t interval,
51 enum qdf_hrtimer_mode mode);
52
53 /**
54 * qdf_hrtimer_cancel() - Cancels hrtimer in given context
55 * @timer: pointer to the qdf_hrtimer_data_t object
56 *
57 * Cancels hrtimer in given context
58 *
59 * Return: int
60 */
61 int qdf_hrtimer_cancel(qdf_hrtimer_data_t *timer);
62
63 /**
64 * qdf_hrtimer_init() - init hrtimer based on context
65 * @timer: pointer to the qdf_hrtimer_data_t object
66 * @callback: callback function to be fired
67 * @clock: clock type
68 * @mode: mode of qdf_hrtimer_data_t
69 * @ctx: interrupt context mode
70 *
71 * starts hrtimer in a context passed as per qdf_context_mode
72 *
73 * Return: void
74 */
75 void qdf_hrtimer_init(qdf_hrtimer_data_t *timer,
76 qdf_hrtimer_func_t callback,
77 enum qdf_clock_id clock,
78 enum qdf_hrtimer_mode mode,
79 enum qdf_context_mode ctx);
80
81 /**
82 * qdf_time_ms_to_ktime() - Converts milliseconds to a qdf_ktime_t object
83 * @ms: time in milliseconds
84 *
85 * Return: milliseconds as ktime object
86 */
87 qdf_ktime_t qdf_time_ms_to_ktime(uint64_t ms);
88
89 /**
90 * qdf_hrtimer_kill() - kills hrtimer in given context
91 * @timer: pointer to the hrtimer object
92 *
93 * kills hrtimer in given context
94 *
95 * Return: void
96 */
97 void qdf_hrtimer_kill(__qdf_hrtimer_data_t *timer);
98
99 /**
100 * qdf_hrtimer_get_remaining() - check remaining time in the timer
101 * @timer: pointer to the qdf_hrtimer_data_t object
102 *
103 * check whether the timer is on one of the queues
104 *
105 * Return: remaining time as qdf_ktime_t object
106 */
107 qdf_ktime_t qdf_hrtimer_get_remaining(qdf_hrtimer_data_t *timer);
108
109 /**
110 * qdf_hrtimer_is_queued() - check whether the timer is on one of the queues
111 * @timer: pointer to the qdf_hrtimer_data_t object
112 *
113 * check whether the timer is on one of the queues
114 *
115 * Return: false when the timer was not in queue
116 * true when the timer was in queue
117 */
118 bool qdf_hrtimer_is_queued(qdf_hrtimer_data_t *timer);
119
120 /**
121 * qdf_hrtimer_callback_running() - check if callback is running
122 * @timer: pointer to the qdf_hrtimer_data_t object
123 *
124 * check whether the timer is running the callback function
125 *
126 * Return: false when callback is not running
127 * true when callback is running
128 */
129 bool qdf_hrtimer_callback_running(qdf_hrtimer_data_t *timer);
130
131 /**
132 * qdf_hrtimer_active() - check if timer is active
133 * @timer: pointer to the qdf_hrtimer_data_t object
134 *
135 * Check if timer is active. A timer is active, when it is enqueued into
136 * the rbtree or the callback function is running.
137 *
138 * Return: false if timer is not active
139 * true if timer is active
140 */
141 bool qdf_hrtimer_active(qdf_hrtimer_data_t *timer);
142
143 /**
144 * qdf_hrtimer_cb_get_time() - get remaining time in callback
145 * @timer: pointer to the qdf_hrtimer_data_t object
146 *
147 * Get remaining time in the hrtimer callback
148 *
149 * Return: time remaining as qdf_ktime_t object
150 */
151 qdf_ktime_t qdf_hrtimer_cb_get_time(qdf_hrtimer_data_t *timer);
152
153 /**
154 * qdf_hrtimer_forward() - forward the hrtimer
155 * @timer: pointer to the qdf_hrtimer_data_t object
156 * @now: current time as qdf_ktime_t object
157 * @interval: interval to forward as qdf_ktime_t object
158 *
159 * Forward the timer expiry so it will expire in the future
160 *
161 * Return: the number of overruns
162 */
163 uint64_t qdf_hrtimer_forward(qdf_hrtimer_data_t *timer,
164 qdf_ktime_t now,
165 qdf_ktime_t interval);
166
167 void qdf_hrtimer_add_expires(qdf_hrtimer_data_t *timer, qdf_ktime_t interval);
168 #else
169 /**
170 * qdf_hrtimer_start() - Starts hrtimer in given context
171 * @timer: pointer to the qdf_hrtimer_data_t object
172 * @interval: interval to forward as qdf_ktime_t object
173 * @mode: mode of qdf_hrtimer_data_t
174 *
175 * Starts hrtimer in given context
176 *
177 * Return: void
178 */
179 static inline
qdf_hrtimer_start(qdf_hrtimer_data_t * timer,qdf_ktime_t interval,enum qdf_hrtimer_mode mode)180 void qdf_hrtimer_start(qdf_hrtimer_data_t *timer, qdf_ktime_t interval,
181 enum qdf_hrtimer_mode mode)
182 {
183 __qdf_hrtimer_start(timer, interval, mode);
184 }
185
186 /**
187 * qdf_hrtimer_cancel() - Cancels hrtimer in given context
188 * @timer: pointer to the qdf_hrtimer_data_t object
189 *
190 * Cancels hrtimer in given context
191 *
192 * Return: int
193 */
194 static inline
qdf_hrtimer_cancel(qdf_hrtimer_data_t * timer)195 int qdf_hrtimer_cancel(qdf_hrtimer_data_t *timer)
196 {
197 return __qdf_hrtimer_cancel(timer);
198 }
199
200 /**
201 * qdf_hrtimer_init() - init hrtimer based on context
202 * @timer: pointer to the qdf_hrtimer_data_t object
203 * @callback: callback function to be fired
204 * @clock: clock type
205 * @mode: mode of qdf_hrtimer_data_t
206 * @ctx: interrupt context mode
207 *
208 * starts hrtimer in a context passed as per qdf_context_mode
209 *
210 * Return: void
211 */
qdf_hrtimer_init(qdf_hrtimer_data_t * timer,qdf_hrtimer_func_t callback,enum qdf_clock_id clock,enum qdf_hrtimer_mode mode,enum qdf_context_mode ctx)212 static inline void qdf_hrtimer_init(qdf_hrtimer_data_t *timer,
213 qdf_hrtimer_func_t callback,
214 enum qdf_clock_id clock,
215 enum qdf_hrtimer_mode mode,
216 enum qdf_context_mode ctx)
217 {
218 __qdf_hrtimer_init(timer, callback, clock, mode, ctx);
219 }
220
221 /**
222 * qdf_time_ms_to_ktime() - Converts milliseconds to a qdf_ktime_t object
223 * @ms: time in milliseconds
224 *
225 * Return: milliseconds as qdf_ktime_t object
226 */
qdf_time_ms_to_ktime(uint64_t ms)227 static inline qdf_ktime_t qdf_time_ms_to_ktime(uint64_t ms)
228 {
229 return __qdf_time_ms_to_ktime(ms);
230 }
231
232 /**
233 * qdf_hrtimer_kill() - kills hrtimer in given context
234 * @timer: pointer to the hrtimer object
235 *
236 * kills hrtimer in given context
237 *
238 * Return: void
239 */
240 static inline
qdf_hrtimer_kill(__qdf_hrtimer_data_t * timer)241 void qdf_hrtimer_kill(__qdf_hrtimer_data_t *timer)
242 {
243 __qdf_hrtimer_kill(timer);
244 }
245
246 /**
247 * qdf_hrtimer_get_remaining() - check remaining time in the timer
248 * @timer: pointer to the qdf_hrtimer_data_t object
249 *
250 * check whether the timer is on one of the queues
251 *
252 * Return: remaining time as qdf_ktime_t object
253 */
qdf_hrtimer_get_remaining(qdf_hrtimer_data_t * timer)254 static inline qdf_ktime_t qdf_hrtimer_get_remaining(qdf_hrtimer_data_t *timer)
255 {
256 return __qdf_hrtimer_get_remaining(timer);
257 }
258
259 /**
260 * qdf_hrtimer_is_queued() - check whether the timer is on one of the queues
261 * @timer: pointer to the qdf_hrtimer_data_t object
262 *
263 * check whether the timer is on one of the queues
264 *
265 * Return: false when the timer was not in queue
266 * true when the timer was in queue
267 */
qdf_hrtimer_is_queued(qdf_hrtimer_data_t * timer)268 static inline bool qdf_hrtimer_is_queued(qdf_hrtimer_data_t *timer)
269 {
270 return __qdf_hrtimer_is_queued(timer);
271 }
272
273 /**
274 * qdf_hrtimer_callback_running() - check if callback is running
275 * @timer: pointer to the qdf_hrtimer_data_t object
276 *
277 * check whether the timer is running the callback function
278 *
279 * Return: false when callback is not running
280 * true when callback is running
281 */
qdf_hrtimer_callback_running(qdf_hrtimer_data_t * timer)282 static inline bool qdf_hrtimer_callback_running(qdf_hrtimer_data_t *timer)
283 {
284 return __qdf_hrtimer_callback_running(timer);
285 }
286
287 /**
288 * qdf_hrtimer_active() - check if timer is active
289 * @timer: pointer to the qdf_hrtimer_data_t object
290 *
291 * Check if timer is active. A timer is active, when it is enqueued into
292 * the rbtree or the callback function is running.
293 *
294 * Return: false if timer is not active
295 * true if timer is active
296 */
qdf_hrtimer_active(qdf_hrtimer_data_t * timer)297 static inline bool qdf_hrtimer_active(qdf_hrtimer_data_t *timer)
298 {
299 return __qdf_hrtimer_active(timer);
300 }
301
302 /**
303 * qdf_hrtimer_cb_get_time() - get remaining time in callback
304 * @timer: pointer to the qdf_hrtimer_data_t object
305 *
306 * Get remaining time in the hrtimer callback
307 *
308 * Return: time remaining as qdf_ktime_t object
309 */
qdf_hrtimer_cb_get_time(qdf_hrtimer_data_t * timer)310 static inline qdf_ktime_t qdf_hrtimer_cb_get_time(qdf_hrtimer_data_t *timer)
311 {
312 return __qdf_hrtimer_cb_get_time(timer);
313 }
314
315 /**
316 * qdf_hrtimer_forward() - forward the hrtimer
317 * @timer: pointer to the qdf_hrtimer_data_t object
318 * @now: current time as qdf_ktime_t object
319 * @interval: interval to forward as qdf_ktime_t object
320 *
321 * Forward the timer expiry so it will expire in the future
322 *
323 * Return: the number of overruns
324 */
qdf_hrtimer_forward(qdf_hrtimer_data_t * timer,qdf_ktime_t now,qdf_ktime_t interval)325 static inline uint64_t qdf_hrtimer_forward(qdf_hrtimer_data_t *timer,
326 qdf_ktime_t now,
327 qdf_ktime_t interval)
328 {
329 return __qdf_hrtimer_forward(timer, now, interval);
330 }
331
332 /**
333 * qdf_hrtimer_add_expires() - Add expiry to hrtimer with given interval
334 * @timer: pointer to the qdf_hrtimer_data_t object
335 * @interval: interval to add as qdf_ktime_t object
336 *
337 * Add the timer expiry so it will expire in the future
338 *
339 * Return: None
340 */
341 static inline
qdf_hrtimer_add_expires(qdf_hrtimer_data_t * timer,qdf_ktime_t interval)342 void qdf_hrtimer_add_expires(qdf_hrtimer_data_t *timer, qdf_ktime_t interval)
343 {
344 return __qdf_hrtimer_add_expires(timer, interval);
345 }
346
347 #endif
348
349 #endif /* _QDF_HRTIMER_H */
350