blob: ac5d6117f2eb2d1060344a2545f8ef3542d7d888 [file] [log] [blame]
The Android Open Source Project5738f832012-12-12 16:00:35 -08001/******************************************************************************
2 *
3 * Copyright (C) 1999-2012 Broadcom Corporation
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 ******************************************************************************/
18
Sharvil Nanavati9bce2262014-05-28 17:09:46 -070019#include <utils/Log.h>
The Android Open Source Project5738f832012-12-12 16:00:35 -080020#include "gki_int.h"
21
22#ifndef BT_ERROR_TRACE_0
23#define BT_ERROR_TRACE_0(l,m)
24#endif
25
26/* Make sure that this has been defined in target.h */
27#ifndef GKI_NUM_TIMERS
28#error NO TIMERS: Must define at least 1 timer in the system!
29#endif
30
31
32#define GKI_NO_NEW_TMRS_STARTED (0x7fffffffL) /* Largest signed positive timer count */
33#define GKI_UNUSED_LIST_ENTRY (0x80000000L) /* Marks an unused timer list entry (initial value) */
The Android Open Source Project5738f832012-12-12 16:00:35 -080034
Sharvil Nanavati9bce2262014-05-28 17:09:46 -070035#define GKI_ERROR(fmt, ...) ALOGE ("ERROR : %s: " fmt, __FUNCTION__, ## __VA_ARGS__)
36
37// Used for controlling alarms from AlarmService.
38extern void alarm_service_reschedule(void);
39
The Android Open Source Project5738f832012-12-12 16:00:35 -080040/*******************************************************************************
41**
42** Function gki_timers_init
43**
44** Description This internal function is called once at startup to initialize
45** all the timer structures.
46**
47** Returns void
48**
49*******************************************************************************/
50void gki_timers_init(void)
51{
52 UINT8 tt;
53
54 gki_cb.com.OSTicksTilExp = 0; /* Remaining time (of OSTimeCurTimeout) before next timer expires */
55 gki_cb.com.OSNumOrigTicks = 0;
56#if (defined(GKI_DELAY_STOP_SYS_TICK) && (GKI_DELAY_STOP_SYS_TICK > 0))
57 gki_cb.com.OSTicksTilStop = 0; /* clear inactivity delay timer */
58#endif
59
60 for (tt = 0; tt < GKI_MAX_TASKS; tt++)
61 {
62 gki_cb.com.OSWaitTmr [tt] = 0;
63
64#if (GKI_NUM_TIMERS > 0)
65 gki_cb.com.OSTaskTmr0 [tt] = 0;
66 gki_cb.com.OSTaskTmr0R [tt] = 0;
67#endif
68
69#if (GKI_NUM_TIMERS > 1)
70 gki_cb.com.OSTaskTmr1 [tt] = 0;
71 gki_cb.com.OSTaskTmr1R [tt] = 0;
72#endif
73
74#if (GKI_NUM_TIMERS > 2)
75 gki_cb.com.OSTaskTmr2 [tt] = 0;
76 gki_cb.com.OSTaskTmr2R [tt] = 0;
77#endif
78
79#if (GKI_NUM_TIMERS > 3)
80 gki_cb.com.OSTaskTmr3 [tt] = 0;
81 gki_cb.com.OSTaskTmr3R [tt] = 0;
82#endif
83 }
84
85 for (tt = 0; tt < GKI_MAX_TIMER_QUEUES; tt++)
86 {
87 gki_cb.com.timer_queues[tt] = NULL;
88 }
89
90 gki_cb.com.p_tick_cb = NULL;
91 gki_cb.com.system_tick_running = FALSE;
92
93 return;
94}
95
96/*******************************************************************************
97**
98** Function gki_timers_is_timer_running
99**
100** Description This internal function is called to test if any gki timer are running
101**
102**
103** Returns TRUE if at least one time is running in the system, FALSE else.
104**
105*******************************************************************************/
106BOOLEAN gki_timers_is_timer_running(void)
107{
108 UINT8 tt;
109 for (tt = 0; tt < GKI_MAX_TASKS; tt++)
110 {
111
112#if (GKI_NUM_TIMERS > 0)
113 if(gki_cb.com.OSTaskTmr0 [tt])
114 {
115 return TRUE;
116 }
117#endif
118
119#if (GKI_NUM_TIMERS > 1)
120 if(gki_cb.com.OSTaskTmr1 [tt] )
121 {
122 return TRUE;
123 }
124#endif
125
126#if (GKI_NUM_TIMERS > 2)
127 if(gki_cb.com.OSTaskTmr2 [tt] )
128 {
129 return TRUE;
130 }
131#endif
132
133#if (GKI_NUM_TIMERS > 3)
134 if(gki_cb.com.OSTaskTmr3 [tt] )
135 {
136 return TRUE;
137 }
138#endif
139 }
140
141 return FALSE;
142
143}
144
145/*******************************************************************************
146**
147** Function GKI_get_tick_count
148**
149** Description This function returns the current system ticks
150**
151** Returns The current number of system ticks
152**
153*******************************************************************************/
154UINT32 GKI_get_tick_count(void)
155{
156 return gki_cb.com.OSTicks;
157}
158
159
160/*******************************************************************************
161**
162** Function GKI_ready_to_sleep
163**
164** Description This function returns the number of system ticks until the
165** next timer will expire. It is typically called by a power
166** savings manager to find out how long it can have the system
167** sleep before it needs to service the next entry.
168**
169** Parameters: None
170**
171** Returns Number of ticks til the next timer expires
172** Note: the value is a signed value. This value should be
173** compared to x > 0, to avoid misinterpreting negative tick
174** values.
175**
176*******************************************************************************/
177INT32 GKI_ready_to_sleep (void)
178{
179 return (gki_cb.com.OSTicksTilExp);
180}
181
182
183/*******************************************************************************
184**
185** Function GKI_start_timer
186**
187** Description An application can call this function to start one of
188** it's four general purpose timers. Any of the four timers
189** can be 1-shot or continuous. If a timer is already running,
190** it will be reset to the new parameters.
191**
192** Parameters tnum - (input) timer number to be started (TIMER_0,
193** TIMER_1, TIMER_2, or TIMER_3)
194** ticks - (input) the number of system ticks til the
195** timer expires.
196** is_continuous - (input) TRUE if timer restarts automatically,
197** else FALSE if it is a 'one-shot'.
198**
199** Returns void
200**
201*******************************************************************************/
202void GKI_start_timer (UINT8 tnum, INT32 ticks, BOOLEAN is_continuous)
203{
204 INT32 reload;
205 INT32 orig_ticks;
206 UINT8 task_id = GKI_get_taskid();
207 BOOLEAN bad_timer = FALSE;
208
209 if (ticks <= 0)
210 ticks = 1;
211
212 orig_ticks = ticks; /* save the ticks in case adjustment is necessary */
213
214
215 /* If continuous timer, set reload, else set it to 0 */
216 if (is_continuous)
217 reload = ticks;
218 else
219 reload = 0;
220
221 GKI_disable();
222
223 if(gki_timers_is_timer_running() == FALSE)
224 {
225#if (defined(GKI_DELAY_STOP_SYS_TICK) && (GKI_DELAY_STOP_SYS_TICK > 0))
226 /* if inactivity delay timer is not running, start system tick */
227 if(gki_cb.com.OSTicksTilStop == 0)
228 {
229#endif
230 if(gki_cb.com.p_tick_cb)
231 {
232 /* start system tick */
233 gki_cb.com.system_tick_running = TRUE;
234 (gki_cb.com.p_tick_cb) (TRUE);
235 }
236#if (defined(GKI_DELAY_STOP_SYS_TICK) && (GKI_DELAY_STOP_SYS_TICK > 0))
237 }
238 else
239 {
240 /* clear inactivity delay timer */
241 gki_cb.com.OSTicksTilStop = 0;
242 }
243#endif
244 }
245 /* Add the time since the last task timer update.
246 ** Note that this works when no timers are active since
247 ** both OSNumOrigTicks and OSTicksTilExp are 0.
248 */
Sharvil Nanavati6449e492014-06-06 01:26:23 -0700249 if (INT32_MAX - (gki_cb.com.OSNumOrigTicks - gki_cb.com.OSTicksTilExp) > ticks)
The Android Open Source Project5738f832012-12-12 16:00:35 -0800250 {
251 ticks += gki_cb.com.OSNumOrigTicks - gki_cb.com.OSTicksTilExp;
252 }
253 else
Sharvil Nanavati6449e492014-06-06 01:26:23 -0700254 ticks = INT32_MAX;
The Android Open Source Project5738f832012-12-12 16:00:35 -0800255
256 switch (tnum)
257 {
258#if (GKI_NUM_TIMERS > 0)
259 case TIMER_0:
260 gki_cb.com.OSTaskTmr0R[task_id] = reload;
261 gki_cb.com.OSTaskTmr0 [task_id] = ticks;
262 break;
263#endif
264
265#if (GKI_NUM_TIMERS > 1)
266 case TIMER_1:
267 gki_cb.com.OSTaskTmr1R[task_id] = reload;
268 gki_cb.com.OSTaskTmr1 [task_id] = ticks;
269 break;
270#endif
271
272#if (GKI_NUM_TIMERS > 2)
273 case TIMER_2:
274 gki_cb.com.OSTaskTmr2R[task_id] = reload;
275 gki_cb.com.OSTaskTmr2 [task_id] = ticks;
276 break;
277#endif
278
279#if (GKI_NUM_TIMERS > 3)
280 case TIMER_3:
281 gki_cb.com.OSTaskTmr3R[task_id] = reload;
282 gki_cb.com.OSTaskTmr3 [task_id] = ticks;
283 break;
284#endif
285 default:
286 bad_timer = TRUE; /* Timer number is bad, so do not use */
287 }
288
289 /* Update the expiration timeout if a legitimate timer */
290 if (!bad_timer)
291 {
292 /* Only update the timeout value if it is less than any other newly started timers */
293 gki_adjust_timer_count (orig_ticks);
294 }
295
296 GKI_enable();
297
298}
299
300/*******************************************************************************
301**
302** Function GKI_stop_timer
303**
304** Description An application can call this function to stop one of
305** it's four general purpose timers. There is no harm in
306** stopping a timer that is already stopped.
307**
308** Parameters tnum - (input) timer number to be started (TIMER_0,
309** TIMER_1, TIMER_2, or TIMER_3)
310** Returns void
311**
312*******************************************************************************/
313void GKI_stop_timer (UINT8 tnum)
314{
315 UINT8 task_id = GKI_get_taskid();
316
317 switch (tnum)
318 {
319#if (GKI_NUM_TIMERS > 0)
320 case TIMER_0:
321 gki_cb.com.OSTaskTmr0R[task_id] = 0;
322 gki_cb.com.OSTaskTmr0 [task_id] = 0;
323 break;
324#endif
325
326#if (GKI_NUM_TIMERS > 1)
327 case TIMER_1:
328 gki_cb.com.OSTaskTmr1R[task_id] = 0;
329 gki_cb.com.OSTaskTmr1 [task_id] = 0;
330 break;
331#endif
332
333#if (GKI_NUM_TIMERS > 2)
334 case TIMER_2:
335 gki_cb.com.OSTaskTmr2R[task_id] = 0;
336 gki_cb.com.OSTaskTmr2 [task_id] = 0;
337 break;
338#endif
339
340#if (GKI_NUM_TIMERS > 3)
341 case TIMER_3:
342 gki_cb.com.OSTaskTmr3R[task_id] = 0;
343 gki_cb.com.OSTaskTmr3 [task_id] = 0;
344 break;
345#endif
346 }
347
348 GKI_disable();
349
350 if (gki_timers_is_timer_running() == FALSE)
351 {
352 if (gki_cb.com.p_tick_cb)
353 {
354#if (defined(GKI_DELAY_STOP_SYS_TICK) && (GKI_DELAY_STOP_SYS_TICK > 0))
355 /* if inactivity delay timer is not running */
356 if ((gki_cb.com.system_tick_running)&&(gki_cb.com.OSTicksTilStop == 0))
357 {
358 /* set inactivity delay timer */
359 /* when timer expires, system tick will be stopped */
360 gki_cb.com.OSTicksTilStop = GKI_DELAY_STOP_SYS_TICK;
361 }
362#else
363 gki_cb.com.system_tick_running = FALSE;
364 gki_cb.com.p_tick_cb(FALSE); /* stop system tick */
365#endif
366 }
367 }
368
369 GKI_enable();
370
371
372}
373
374
375/*******************************************************************************
376**
377** Function GKI_timer_update
378**
379** Description This function is called by an OS to drive the GKI's timers.
380** It is typically called at every system tick to
381** update the timers for all tasks, and check for timeouts.
382**
383** Note: It has been designed to also allow for variable tick updates
384** so that systems with strict power savings requirements can
385** have the update occur at variable intervals.
386**
387** Parameters: ticks_since_last_update - (input) This is the number of TICKS that have
388** occurred since the last time GKI_timer_update was called.
389**
390** Returns void
391**
392*******************************************************************************/
393void GKI_timer_update (INT32 ticks_since_last_update)
394{
395 UINT8 task_id;
396 long next_expiration; /* Holds the next soonest expiration time after this update */
397
398 /* Increment the number of ticks used for time stamps */
399 gki_cb.com.OSTicks += ticks_since_last_update;
400
401 /* If any timers are running in any tasks, decrement the remaining time til
402 * the timer updates need to take place (next expiration occurs)
403 */
404 gki_cb.com.OSTicksTilExp -= ticks_since_last_update;
405
406 /* Don't allow timer interrupt nesting */
407 if (gki_cb.com.timer_nesting)
408 return;
409
410 gki_cb.com.timer_nesting = 1;
411
412#if (defined(GKI_DELAY_STOP_SYS_TICK) && (GKI_DELAY_STOP_SYS_TICK > 0))
413 /* if inactivity delay timer is set and expired */
414 if (gki_cb.com.OSTicksTilStop)
415 {
416 if( gki_cb.com.OSTicksTilStop <= (UINT32)ticks_since_last_update )
417 {
418 if(gki_cb.com.p_tick_cb)
419 {
420 gki_cb.com.system_tick_running = FALSE;
421 (gki_cb.com.p_tick_cb) (FALSE); /* stop system tick */
422 }
423 gki_cb.com.OSTicksTilStop = 0; /* clear inactivity delay timer */
424 gki_cb.com.timer_nesting = 0;
425 return;
426 }
427 else
428 gki_cb.com.OSTicksTilStop -= ticks_since_last_update;
429 }
430#endif
431
432 /* No need to update the ticks if no timeout has occurred */
433 if (gki_cb.com.OSTicksTilExp > 0)
434 {
Sharvil Nanavati9bce2262014-05-28 17:09:46 -0700435 // When using alarms from AlarmService we should
436 // always have work to be done here.
437 GKI_ERROR("No work to be done when expected work\n");
The Android Open Source Project5738f832012-12-12 16:00:35 -0800438 gki_cb.com.timer_nesting = 0;
439 return;
440 }
441
442 next_expiration = GKI_NO_NEW_TMRS_STARTED;
443
444 /* If here then gki_cb.com.OSTicksTilExp <= 0. If negative, then increase gki_cb.com.OSNumOrigTicks
445 to account for the difference so timer updates below are decremented by the full number
446 of ticks. gki_cb.com.OSNumOrigTicks is reset at the bottom of this function so changing this
447 value only affects the timer updates below
448 */
449 gki_cb.com.OSNumOrigTicks -= gki_cb.com.OSTicksTilExp;
450
451#if GKI_TIMER_LIST_NOPREEMPT == TRUE
452 /* Protect this section because if a GKI_timer_stop happens between:
453 * - gki_cb.com.OSTaskTmr0[task_id] -= gki_cb.com.OSNumOrigTicks;
454 * - gki_cb.com.OSTaskTmr0[task_id] = gki_cb.com.OSTaskTmr0R[task_id];
455 * then the timer may appear stopped while it is about to be reloaded.
456 * Note: Not needed if this function cannot be preempted (typical).
457 */
458 GKI_disable();
459#endif
460
461 /* Check for OS Task Timers */
462 for (task_id = 0; task_id < GKI_MAX_TASKS; task_id++)
463 {
464 if (gki_cb.com.OSWaitTmr[task_id] > 0) /* If timer is running */
465 {
466 gki_cb.com.OSWaitTmr[task_id] -= gki_cb.com.OSNumOrigTicks;
467 if (gki_cb.com.OSWaitTmr[task_id] <= 0)
468 {
469 /* Timer Expired */
470 gki_cb.com.OSRdyTbl[task_id] = TASK_READY;
471 }
472 }
473
474#if (GKI_NUM_TIMERS > 0)
475 /* If any timer is running, decrement */
476 if (gki_cb.com.OSTaskTmr0[task_id] > 0)
477 {
478 gki_cb.com.OSTaskTmr0[task_id] -= gki_cb.com.OSNumOrigTicks;
479
480 if (gki_cb.com.OSTaskTmr0[task_id] <= 0)
481 {
482 /* Reload timer and set Timer 0 Expired event mask */
483 gki_cb.com.OSTaskTmr0[task_id] = gki_cb.com.OSTaskTmr0R[task_id];
484
485#if (defined(GKI_TIMER_UPDATES_FROM_ISR) && GKI_TIMER_UPDATES_FROM_ISR == TRUE)
486 GKI_isend_event (task_id, TIMER_0_EVT_MASK);
487#else
488 GKI_send_event (task_id, TIMER_0_EVT_MASK);
489#endif
490 }
491 }
492
493 /* Check to see if this timer is the next one to expire */
494 if (gki_cb.com.OSTaskTmr0[task_id] > 0 && gki_cb.com.OSTaskTmr0[task_id] < next_expiration)
495 next_expiration = gki_cb.com.OSTaskTmr0[task_id];
496#endif
497
498#if (GKI_NUM_TIMERS > 1)
499 /* If any timer is running, decrement */
500 if (gki_cb.com.OSTaskTmr1[task_id] > 0)
501 {
502 gki_cb.com.OSTaskTmr1[task_id] -= gki_cb.com.OSNumOrigTicks;
503
504 if (gki_cb.com.OSTaskTmr1[task_id] <= 0)
505 {
506 /* Reload timer and set Timer 1 Expired event mask */
507 gki_cb.com.OSTaskTmr1[task_id] = gki_cb.com.OSTaskTmr1R[task_id];
508
509#if (defined(GKI_TIMER_UPDATES_FROM_ISR) && GKI_TIMER_UPDATES_FROM_ISR == TRUE)
510 GKI_isend_event (task_id, TIMER_1_EVT_MASK);
511#else
512 GKI_send_event (task_id, TIMER_1_EVT_MASK);
513#endif
514 }
515 }
516
517 /* Check to see if this timer is the next one to expire */
518 if (gki_cb.com.OSTaskTmr1[task_id] > 0 && gki_cb.com.OSTaskTmr1[task_id] < next_expiration)
519 next_expiration = gki_cb.com.OSTaskTmr1[task_id];
520#endif
521
522#if (GKI_NUM_TIMERS > 2)
523 /* If any timer is running, decrement */
524 if (gki_cb.com.OSTaskTmr2[task_id] > 0)
525 {
526 gki_cb.com.OSTaskTmr2[task_id] -= gki_cb.com.OSNumOrigTicks;
527
528 if (gki_cb.com.OSTaskTmr2[task_id] <= 0)
529 {
530 /* Reload timer and set Timer 2 Expired event mask */
531 gki_cb.com.OSTaskTmr2[task_id] = gki_cb.com.OSTaskTmr2R[task_id];
532
533#if (defined(GKI_TIMER_UPDATES_FROM_ISR) && GKI_TIMER_UPDATES_FROM_ISR == TRUE)
534 GKI_isend_event (task_id, TIMER_2_EVT_MASK);
535#else
536 GKI_send_event (task_id, TIMER_2_EVT_MASK);
537#endif
538 }
539 }
540
541 /* Check to see if this timer is the next one to expire */
542 if (gki_cb.com.OSTaskTmr2[task_id] > 0 && gki_cb.com.OSTaskTmr2[task_id] < next_expiration)
543 next_expiration = gki_cb.com.OSTaskTmr2[task_id];
544#endif
545
546#if (GKI_NUM_TIMERS > 3)
547 /* If any timer is running, decrement */
548 if (gki_cb.com.OSTaskTmr3[task_id] > 0)
549 {
550 gki_cb.com.OSTaskTmr3[task_id] -= gki_cb.com.OSNumOrigTicks;
551
552 if (gki_cb.com.OSTaskTmr3[task_id] <= 0)
553 {
554 /* Reload timer and set Timer 3 Expired event mask */
555 gki_cb.com.OSTaskTmr3[task_id] = gki_cb.com.OSTaskTmr3R[task_id];
556
557#if (defined(GKI_TIMER_UPDATES_FROM_ISR) && GKI_TIMER_UPDATES_FROM_ISR == TRUE)
558 GKI_isend_event (task_id, TIMER_3_EVT_MASK);
559#else
560 GKI_send_event (task_id, TIMER_3_EVT_MASK);
561#endif
562 }
563 }
564
565 /* Check to see if this timer is the next one to expire */
566 if (gki_cb.com.OSTaskTmr3[task_id] > 0 && gki_cb.com.OSTaskTmr3[task_id] < next_expiration)
567 next_expiration = gki_cb.com.OSTaskTmr3[task_id];
568#endif
569
570 }
The Android Open Source Project5738f832012-12-12 16:00:35 -0800571 /* Set the next timer experation value if there is one to start */
572 if (next_expiration < GKI_NO_NEW_TMRS_STARTED)
573 {
574 gki_cb.com.OSTicksTilExp = gki_cb.com.OSNumOrigTicks = next_expiration;
575 }
576 else
577 {
578 gki_cb.com.OSTicksTilExp = gki_cb.com.OSNumOrigTicks = 0;
579 }
580
Sharvil Nanavati9bce2262014-05-28 17:09:46 -0700581 // Set alarm service for next alarm.
582 alarm_service_reschedule();
583
584#if GKI_TIMER_LIST_NOPREEMPT == TRUE
585 /* End the critical section */
586 GKI_enable();
587#endif
588
589// GKI_ERROR("Timer expired - next expiration ticks:%ld\n", next_expiration);
590
The Android Open Source Project5738f832012-12-12 16:00:35 -0800591 gki_cb.com.timer_nesting = 0;
592
593 return;
594}
595
596
597/*******************************************************************************
598**
599** Function GKI_timer_queue_empty
600**
601** Description This function is called by applications to see whether the timer
602** queue is empty
603**
604** Parameters
605**
606** Returns BOOLEAN
607**
608*******************************************************************************/
609BOOLEAN GKI_timer_queue_empty (void)
610{
611 UINT8 tt;
612
613 for (tt = 0; tt < GKI_MAX_TIMER_QUEUES; tt++)
614 {
615 if (gki_cb.com.timer_queues[tt])
616 return FALSE;
617 }
618
619 return TRUE;
620}
621
622/*******************************************************************************
623**
624** Function GKI_timer_queue_register_callback
625**
626** Description This function is called by applications to register system tick
627** start/stop callback for time queues
628**
629**
630** Parameters p_callback - (input) pointer to the system tick callback
631**
632** Returns BOOLEAN
633**
634*******************************************************************************/
635void GKI_timer_queue_register_callback (SYSTEM_TICK_CBACK *p_callback)
636{
637 gki_cb.com.p_tick_cb = p_callback;
638
639 return;
640}
641
642/*******************************************************************************
643**
644** Function GKI_init_timer_list
645**
646** Description This function is called by applications when they
647** want to initialize a timer list.
648**
649** Parameters p_timer_listq - (input) pointer to the timer list queue object
650**
651** Returns void
652**
653*******************************************************************************/
654void GKI_init_timer_list (TIMER_LIST_Q *p_timer_listq)
655{
656 p_timer_listq->p_first = NULL;
657 p_timer_listq->p_last = NULL;
658 p_timer_listq->last_ticks = 0;
659
660 return;
661}
662
663/*******************************************************************************
664**
665** Function GKI_init_timer_list_entry
666**
667** Description This function is called by the applications when they
668** want to initialize a timer list entry. This must be
669** done prior to first use of the entry.
670**
671** Parameters p_tle - (input) pointer to a timer list queue entry
672**
673** Returns void
674**
675*******************************************************************************/
676void GKI_init_timer_list_entry (TIMER_LIST_ENT *p_tle)
677{
678 p_tle->p_next = NULL;
679 p_tle->p_prev = NULL;
680 p_tle->ticks = GKI_UNUSED_LIST_ENTRY;
681 p_tle->in_use = FALSE;
682}
683
684
685/*******************************************************************************
686**
687** Function GKI_update_timer_list
688**
689** Description This function is called by the applications when they
690** want to update a timer list. This should be at every
691** timer list unit tick, e.g. once per sec, once per minute etc.
692**
693** Parameters p_timer_listq - (input) pointer to the timer list queue object
694** num_units_since_last_update - (input) number of units since the last update
695** (allows for variable unit update)
696**
697** NOTE: The following timer list update routines should not be used for exact time
698** critical purposes. The timer tasks should be used when exact timing is needed.
699**
700** Returns the number of timers that have expired
701**
702*******************************************************************************/
703UINT16 GKI_update_timer_list (TIMER_LIST_Q *p_timer_listq, INT32 num_units_since_last_update)
704{
705 TIMER_LIST_ENT *p_tle;
706 UINT16 num_time_out = 0;
707 INT32 rem_ticks;
708 INT32 temp_ticks;
709
710 p_tle = p_timer_listq->p_first;
711
712 /* First, get the guys who have previously timed out */
713 /* Note that the tick value of the timers should always be '0' */
714 while ((p_tle) && (p_tle->ticks <= 0))
715 {
716 num_time_out++;
717 p_tle = p_tle->p_next;
718 }
719
720 /* Timer entriy tick values are relative to the preceeding entry */
721 rem_ticks = num_units_since_last_update;
722
723 /* Now, adjust remaining timer entries */
724 while ((p_tle != NULL) && (rem_ticks > 0))
725 {
726 temp_ticks = p_tle->ticks;
727 p_tle->ticks -= rem_ticks;
728
729 /* See if this timer has just timed out */
730 if (p_tle->ticks <= 0)
731 {
732 /* We set the number of ticks to '0' so that the legacy code
733 * that assumes a '0' or nonzero value will still work as coded. */
734 p_tle->ticks = 0;
735
736 num_time_out++;
737 }
738
739 rem_ticks -= temp_ticks; /* Decrement the remaining ticks to process */
740 p_tle = p_tle->p_next;
741 }
742
743 if (p_timer_listq->last_ticks > 0)
744 {
745 p_timer_listq->last_ticks -= num_units_since_last_update;
746
747 /* If the last timer has expired set last_ticks to 0 so that other list update
748 * functions will calculate correctly
749 */
750 if (p_timer_listq->last_ticks < 0)
751 p_timer_listq->last_ticks = 0;
752 }
753
754 return (num_time_out);
755}
756
757/*******************************************************************************
758**
759** Function GKI_get_remaining_ticks
760**
761** Description This function is called by an application to get remaining
762** ticks to expire
763**
764** Parameters p_timer_listq - (input) pointer to the timer list queue object
765** p_target_tle - (input) pointer to a timer list queue entry
766**
767** Returns 0 if timer is not used or timer is not in the list
768** remaining ticks if success
769**
770*******************************************************************************/
771UINT32 GKI_get_remaining_ticks (TIMER_LIST_Q *p_timer_listq, TIMER_LIST_ENT *p_target_tle)
772{
773 TIMER_LIST_ENT *p_tle;
774 UINT32 rem_ticks = 0;
775
776 if (p_target_tle->in_use)
777 {
778 p_tle = p_timer_listq->p_first;
779
780 /* adding up all of ticks in previous entries */
781 while ((p_tle)&&(p_tle != p_target_tle))
782 {
783 rem_ticks += p_tle->ticks;
784 p_tle = p_tle->p_next;
785 }
786
787 /* if found target entry */
788 if (p_tle == p_target_tle)
789 {
790 rem_ticks += p_tle->ticks;
791 }
792 else
793 {
794 BT_ERROR_TRACE_0(TRACE_LAYER_GKI, "GKI_get_remaining_ticks: No timer entry in the list");
795 return(0);
796 }
797 }
798 else
799 {
800 BT_ERROR_TRACE_0(TRACE_LAYER_GKI, "GKI_get_remaining_ticks: timer entry is not active");
801 }
802
803 return (rem_ticks);
804}
805
806/*******************************************************************************
807**
808** Function GKI_add_to_timer_list
809**
810** Description This function is called by an application to add a timer
811** entry to a timer list.
812**
813** Note: A timer value of '0' will effectively insert an already
814** expired event. Negative tick values will be ignored.
815**
816** Parameters p_timer_listq - (input) pointer to the timer list queue object
817** p_tle - (input) pointer to a timer list queue entry
818**
819** Returns void
820**
821*******************************************************************************/
822void GKI_add_to_timer_list (TIMER_LIST_Q *p_timer_listq, TIMER_LIST_ENT *p_tle)
823{
824 UINT32 nr_ticks_total;
825 UINT8 tt;
826 TIMER_LIST_ENT *p_temp;
827
828 /* Only process valid tick values */
829 if (p_tle->ticks >= 0)
830 {
831 /* If this entry is the last in the list */
832 if (p_tle->ticks >= p_timer_listq->last_ticks)
833 {
834 /* If this entry is the only entry in the list */
835 if (p_timer_listq->p_first == NULL)
836 p_timer_listq->p_first = p_tle;
837 else
838 {
839 /* Insert the entry onto the end of the list */
840 if (p_timer_listq->p_last != NULL)
841 p_timer_listq->p_last->p_next = p_tle;
842
843 p_tle->p_prev = p_timer_listq->p_last;
844 }
845
846 p_tle->p_next = NULL;
847 p_timer_listq->p_last = p_tle;
848 nr_ticks_total = p_tle->ticks;
849 p_tle->ticks -= p_timer_listq->last_ticks;
850
851 p_timer_listq->last_ticks = nr_ticks_total;
852 }
853 else /* This entry needs to be inserted before the last entry */
854 {
The Android Open Source Project5738f832012-12-12 16:00:35 -0800855 p_temp = p_timer_listq->p_first;
Ganesh Ganapathi Batta6fd2e4d2014-04-28 16:21:04 -0700856
857 if (p_temp == NULL)
858 {
859 /* list is corrupted, exit to avoid crash */
860 GKI_TRACE_ERROR_0("GKI_add_to_timer_list : Timerlist Q is empty");
861 GKI_exception(GKI_ERROR_TIMER_LIST_CORRUPTED, "*** "
862 "GKI_add_to_timer_list(): timer list corrupted! ***");
863 return;
864 }
865 /* Find the entry that the new one needs to be inserted in front of
866 * as last_ticks is the expiry value of p_last, it should be inserted
867 * BEFORE p_last. otherwise list is probably corrupted! */
The Android Open Source Project5738f832012-12-12 16:00:35 -0800868 while (p_tle->ticks > p_temp->ticks)
869 {
870 /* Update the tick value if looking at an unexpired entry */
871 if (p_temp->ticks > 0)
872 p_tle->ticks -= p_temp->ticks;
873
874 p_temp = p_temp->p_next;
875 }
876
877 /* The new entry is the first in the list */
878 if (p_temp == p_timer_listq->p_first)
879 {
880 p_tle->p_next = p_timer_listq->p_first;
881 p_timer_listq->p_first->p_prev = p_tle;
882 p_timer_listq->p_first = p_tle;
883 }
884 else
885 {
886 p_temp->p_prev->p_next = p_tle;
887 p_tle->p_prev = p_temp->p_prev;
888 p_temp->p_prev = p_tle;
889 p_tle->p_next = p_temp;
890 }
891 p_temp->ticks -= p_tle->ticks;
892 }
893
894 p_tle->in_use = TRUE;
895
896 /* if we already add this timer queue to the array */
897 for (tt = 0; tt < GKI_MAX_TIMER_QUEUES; tt++)
898 {
899 if (gki_cb.com.timer_queues[tt] == p_timer_listq)
900 return;
901 }
902 /* add this timer queue to the array */
903 for (tt = 0; tt < GKI_MAX_TIMER_QUEUES; tt++)
904 {
905 if (gki_cb.com.timer_queues[tt] == NULL)
906 break;
907 }
908 if (tt < GKI_MAX_TIMER_QUEUES)
909 {
910 gki_cb.com.timer_queues[tt] = p_timer_listq;
911 }
912 }
913
914 return;
915}
916
917
918/*******************************************************************************
919**
920** Function GKI_remove_from_timer_list
921**
922** Description This function is called by an application to remove a timer
923** entry from a timer list.
924**
925** Parameters p_timer_listq - (input) pointer to the timer list queue object
926** p_tle - (input) pointer to a timer list queue entry
927**
928** Returns void
929**
930*******************************************************************************/
931void GKI_remove_from_timer_list (TIMER_LIST_Q *p_timer_listq, TIMER_LIST_ENT *p_tle)
932{
933 UINT8 tt;
934
935 /* Verify that the entry is valid */
936 if (p_tle == NULL || p_tle->in_use == FALSE || p_timer_listq->p_first == NULL)
937 {
938 return;
939 }
940
941 /* Add the ticks remaining in this timer (if any) to the next guy in the list.
942 ** Note: Expired timers have a tick value of '0'.
943 */
944 if (p_tle->p_next != NULL)
945 {
946 p_tle->p_next->ticks += p_tle->ticks;
947 }
948 else
949 {
950 p_timer_listq->last_ticks -= p_tle->ticks;
951 }
952
953 /* Unlink timer from the list.
954 */
955 if (p_timer_listq->p_first == p_tle)
956 {
957 p_timer_listq->p_first = p_tle->p_next;
958
959 if (p_timer_listq->p_first != NULL)
960 p_timer_listq->p_first->p_prev = NULL;
961
962 if (p_timer_listq->p_last == p_tle)
963 p_timer_listq->p_last = NULL;
964 }
965 else
966 {
967 if (p_timer_listq->p_last == p_tle)
968 {
969 p_timer_listq->p_last = p_tle->p_prev;
970
971 if (p_timer_listq->p_last != NULL)
972 p_timer_listq->p_last->p_next = NULL;
973 }
974 else
975 {
976 if (p_tle->p_next != NULL && p_tle->p_next->p_prev == p_tle)
977 p_tle->p_next->p_prev = p_tle->p_prev;
978 else
979 {
980 /* Error case - chain messed up ?? */
981 return;
982 }
983
984 if (p_tle->p_prev != NULL && p_tle->p_prev->p_next == p_tle)
985 p_tle->p_prev->p_next = p_tle->p_next;
986 else
987 {
988 /* Error case - chain messed up ?? */
989 return;
990 }
991 }
992 }
993
994 p_tle->p_next = p_tle->p_prev = NULL;
995 p_tle->ticks = GKI_UNUSED_LIST_ENTRY;
996 p_tle->in_use = FALSE;
997
998 /* if timer queue is empty */
999 if (p_timer_listq->p_first == NULL && p_timer_listq->p_last == NULL)
1000 {
1001 for (tt = 0; tt < GKI_MAX_TIMER_QUEUES; tt++)
1002 {
1003 if (gki_cb.com.timer_queues[tt] == p_timer_listq)
1004 {
1005 gki_cb.com.timer_queues[tt] = NULL;
1006 break;
1007 }
1008 }
1009 }
1010
1011 return;
1012}
1013
1014
1015/*******************************************************************************
1016**
1017** Function gki_adjust_timer_count
1018**
1019** Description This function is called whenever a new timer or GKI_wait occurs
1020** to adjust (if necessary) the current time til the first expiration.
1021** This only needs to make an adjustment if the new timer (in ticks) is
1022** less than the number of ticks remaining on the current timer.
1023**
1024** Parameters: ticks - (input) number of system ticks of the new timer entry
1025**
1026** NOTE: This routine MUST be called while interrupts are disabled to
1027** avoid updates while adjusting the timer variables.
1028**
1029** Returns void
1030**
1031*******************************************************************************/
1032void gki_adjust_timer_count (INT32 ticks)
1033{
1034 if (ticks > 0)
1035 {
1036 /* See if the new timer expires before the current first expiration */
1037 if (gki_cb.com.OSNumOrigTicks == 0 || (ticks < gki_cb.com.OSTicksTilExp && gki_cb.com.OSTicksTilExp > 0))
1038 {
1039 gki_cb.com.OSNumOrigTicks = (gki_cb.com.OSNumOrigTicks - gki_cb.com.OSTicksTilExp) + ticks;
1040 gki_cb.com.OSTicksTilExp = ticks;
Sharvil Nanavati9bce2262014-05-28 17:09:46 -07001041 alarm_service_reschedule();
The Android Open Source Project5738f832012-12-12 16:00:35 -08001042 }
1043 }
1044
1045 return;
1046}