HashTableIterator hash_itr_next(HashTableIterator itr) { if (!itr) return 0; itr->list_itr = list_itr_next(itr->list_itr); if(itr->list_itr) { return itr; } else if(itr->index >= itr->hashtable->size-1) { itr->list_itr = 0; itr->index = 0; itr->hashtable = 0; return 0; } else { while((++itr->index < itr->hashtable->size) && list_empty(&itr->hashtable->hashbucket[itr->index].list)); if (itr->index >= itr->hashtable->size) { itr->list_itr = 0; itr->index = 0; itr->hashtable = 0; return 0; } else { itr->list_itr=list_itr_begin(&itr->hashtable->hashbucket[itr->index].list); return itr; } } }
/** Function triggers the timers which had timeouted (timer->ticks_rem == 0) and * rearm them in case they are auto reloaded */ static void OS_HOT os_timer_triger(void) { list_t *itr; os_timer_t* itr_timer; list_t list_autoreload; /* for auto reloaded timers use temporary list */ list_init(&list_autoreload); itr = list_itr_begin(&timers); while (false == list_itr_end(&timers, itr)) { itr_timer = os_container_of(itr, os_timer_t, list); /* the list will be modified, get pointer the next element before modification */ itr = itr->next; if ((itr_timer->ticks_rem -= timer_tick_unsynch) > 0) { /* current timer does not burn off yet, following timers wont trigger * either but we continue since w have to synchronize all of the timers */ continue; } /* in any case (auto reload or single shot) remove timer from active list */ list_unlink(&(itr_timer->list)); /* call the timer callback, from this callback it is allowed to call the * os_timer_destroy() */ itr_timer->clbck(itr_timer->param); /* check if it is marked as auto reload. * timer callback might destroy the timer but in tis case tick_reload will * be 0 */ if (itr_timer->ticks_reload > 0) { /* timer is auto reload, put the timer to temporary auto reload list */ list_append(&list_autoreload, &(itr_timer->list)); } } timer_tick_unsynch = 0; /* Now re-add all auto reload timers from temporary list. * We need a temporary list because we keep all timers sorted, and we cannot * figure out the position of timers which we auto reload until we finish * processing of previous trigger sequence */ while (NULL != (itr = list_detachfirst(&list_autoreload))) { itr_timer = os_container_of(itr, os_timer_t, list); itr_timer->ticks_rem = itr_timer->ticks_reload; os_timer_add(itr_timer); /* add timer at the proper place at the list */ } }
/** Function add the timer to the timer list. Function keeps the timer list * sorted by remaining burn off time of the timers. */ static void OS_HOT os_timer_add(os_timer_t *add_timer) { list_t *itr; os_timer_t* itr_timer; itr = list_itr_begin(&timers); while (false == list_itr_end(&timers, itr)) { itr_timer = os_container_of(itr, os_timer_t, list); if (itr_timer->ticks_rem > add_timer->ticks_rem) { break; } itr = itr->next; } list_put_before(itr, &(add_timer->list)); }
HashTableIterator hash_new_itr_begin(const HashTable *table) { int i=0; HashTableIterator hash_itr = 0; assert(table); while((i < table->size) && list_empty(&table->hashbucket[i].list)) i++; if (i >= table->size) { return 0; } else { hash_itr=calloc(1,sizeof(struct HashTableIterator_tag)); hash_itr->hashtable=(HashTable *)table; hash_itr->index=i; hash_itr->list_itr=list_itr_begin(&table->hashbucket[i].list); return hash_itr; } }