diff --git a/core/sip/wheeltimer.cpp b/core/sip/wheeltimer.cpp index 16635148..cafaf1d7 100644 --- a/core/sip/wheeltimer.cpp +++ b/core/sip/wheeltimer.cpp @@ -112,52 +112,48 @@ void _wheeltimer::process_current_timers(timer_list& list, std::unique_lockdisarm(); // removes it from list // safe to unlock now lock.unlock(); - t->list = NULL; - t->disarm(); - t->fire(); lock.lock(); } } -void _wheeltimer::place_timer(timer* t) +uint64_t _wheeltimer::get_timer_bucket(timer* t) { - t->arm(); - uint64_t exp = t->get_absolute_expiry(); // scale expiry based on resolution: this is the bucket index - exp = ((exp / resolution) + 1) * resolution; + uint64_t bucket = ((exp / resolution) + 1) * resolution; // if expiry is too soon or in the past, put the timer in the next bucket up auto now = gettimeofday_us(); - if (exp <= now) - exp = ((now / resolution) + 1) * resolution; + if (bucket <= now) + bucket = ((now / resolution) + 1) * resolution; + + return bucket; +} - add_timer_to_bucket(t, exp); +void _wheeltimer::place_timer(timer* t) +{ + t->arm(); + uint64_t bucket = get_timer_bucket(t); + add_timer_to_bucket(t, bucket); } void _wheeltimer::add_timer_to_bucket(timer* t, uint64_t bucket) { - auto& b = buckets[bucket]; - t->list = &b; - b.push_front(t); - t->pos = b.begin(); + t->link(buckets[bucket]); } void _wheeltimer::delete_timer(timer* t) { - if (t->list) { - t->list->erase(t->pos); - t->list = NULL; - } - + t->disarm(); delete t; } diff --git a/core/sip/wheeltimer.h b/core/sip/wheeltimer.h index 813c0af5..f28b9373 100644 --- a/core/sip/wheeltimer.h +++ b/core/sip/wheeltimer.h @@ -48,11 +48,11 @@ typedef std::map timer_buckets; class timer { -public: // for fast removal: timer_list::iterator pos; timer_list* list; +public: timer() : list(NULL), expires(0), expires_rel(0) {} @@ -69,19 +69,28 @@ public: virtual void fire()=0; - // returns true if timer was not armed before - // return false and does nothing otherwise - bool arm() + void arm() { if (expires) - return false; + return; expires = expires_rel + gettimeofday_us(); - return true; + } + + void link(timer_list& new_list) + { + list = &new_list; + list->push_front(this); + pos = list->begin(); } void disarm() { expires = 0; + + if (list) { + list->erase(pos); + list = NULL; + } } // microseconds @@ -120,6 +129,7 @@ class _wheeltimer: void place_timer(timer* t); void add_timer_to_bucket(timer* t, uint64_t); + uint64_t get_timer_bucket(timer* t); void delete_timer(timer* t); void process_current_timers(timer_list&, std::unique_lock&);