Commit 0924b63e authored by Max Kellermann's avatar Max Kellermann

event/TimerWheel: add `empty` flag to optimize a common case

parent ce6afe93
...@@ -54,6 +54,8 @@ TimerWheel::Insert(CoarseTimerEvent &t) noexcept ...@@ -54,6 +54,8 @@ TimerWheel::Insert(CoarseTimerEvent &t) noexcept
const auto due = std::max(t.GetDue(), last_time); const auto due = std::max(t.GetDue(), last_time);
buckets[BucketIndexAt(due)].push_back(t); buckets[BucketIndexAt(due)].push_back(t);
empty = false;
} }
void void
...@@ -99,10 +101,15 @@ TimerWheel::GetNextDue(const std::size_t bucket_index, ...@@ -99,10 +101,15 @@ TimerWheel::GetNextDue(const std::size_t bucket_index,
inline Event::Duration inline Event::Duration
TimerWheel::GetSleep(Event::TimePoint now) const noexcept TimerWheel::GetSleep(Event::TimePoint now) const noexcept
{ {
if (empty)
return Event::Duration(-1);
auto t = GetNextDue(BucketIndexAt(now), GetBucketStartTime(now)); auto t = GetNextDue(BucketIndexAt(now), GetBucketStartTime(now));
assert(t > now); assert(t > now);
if (t == Event::TimePoint::max()) if (t == Event::TimePoint::max()) {
empty = true;
return Event::Duration(-1); return Event::Duration(-1);
}
return t - now; return t - now;
} }
......
...@@ -72,6 +72,16 @@ class TimerWheel final { ...@@ -72,6 +72,16 @@ class TimerWheel final {
*/ */
Event::TimePoint last_time{}; Event::TimePoint last_time{};
/**
* If this flag is true, then all buckets are guaranteed to be
* empty. If it is false, the buckets may or may not be
* empty; if so, the next full scan will set it back to true.
*
* This field is "mutable" so the "const" method GetSleep()
* can update it.
*/
mutable bool empty = true;
public: public:
TimerWheel() noexcept; TimerWheel() noexcept;
~TimerWheel() noexcept; ~TimerWheel() noexcept;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment