1
#include "source/common/event/schedulable_cb_impl.h"
2

            
3
#include "source/common/common/assert.h"
4

            
5
#include "event2/event.h"
6

            
7
namespace Envoy {
8
namespace Event {
9

            
10
SchedulableCallbackImpl::SchedulableCallbackImpl(Libevent::BasePtr& libevent,
11
                                                 std::function<void()> cb)
12
427417
    : cb_(cb) {
13
427417
  ASSERT(cb_);
14
427417
  evtimer_assign(
15
427417
      &raw_event_, libevent.get(),
16
427417
      [](evutil_socket_t, short, void* arg) -> void {
17
427417
        SchedulableCallbackImpl* cb = static_cast<SchedulableCallbackImpl*>(arg);
18
427417
        cb->cb_();
19
427417
      },
20
427417
      this);
21
427417
}
22

            
23
797132
void SchedulableCallbackImpl::scheduleCallbackCurrentIteration() {
24
797132
  if (enabled()) {
25
17166
    return;
26
17166
  }
27
  // event_active directly adds the event to the end of the work queue so it executes in the current
28
  // iteration of the event loop.
29
779966
  event_active(&raw_event_, EV_TIMEOUT, 0);
30
779966
}
31

            
32
2236568
void SchedulableCallbackImpl::scheduleCallbackNextIteration() {
33
2236568
  if (enabled()) {
34
14311
    return;
35
14311
  }
36
  // libevent computes the list of timers to move to the work list after polling for fd events, but
37
  // iteration through the work list starts. Zero delay timers added while iterating through the
38
  // work list execute on the next iteration of the event loop.
39
2222257
  const timeval zero_tv{};
40
2222257
  event_add(&raw_event_, &zero_tv);
41
2222257
}
42

            
43
625461
void SchedulableCallbackImpl::cancel() { event_del(&raw_event_); }
44

            
45
4423914
bool SchedulableCallbackImpl::enabled() { return 0 != evtimer_pending(&raw_event_, nullptr); }
46

            
47
} // namespace Event
48
} // namespace Envoy