event/DeferEvent: use class IntrusiveList instead of boost::intrusive::list

This commit is contained in:
Max Kellermann 2020-12-01 16:56:58 +01:00
parent 774b4313f2
commit 990f2dc1cf
4 changed files with 25 additions and 49 deletions

View File

@ -20,14 +20,11 @@
#include "DeferEvent.hxx"
#include "Loop.hxx"
void
DeferEvent::Cancel() noexcept
{
loop.RemoveDeferred(*this);
}
void
DeferEvent::Schedule() noexcept
{
loop.AddDeferred(*this);
if (!IsPending())
loop.AddDeferred(*this);
assert(IsPending());
}

View File

@ -21,8 +21,7 @@
#define MPD_DEFER_EVENT_HXX
#include "util/BindMethod.hxx"
#include <boost/intrusive/list_hook.hpp>
#include "util/IntrusiveList.hxx"
class EventLoop;
@ -34,10 +33,10 @@ class EventLoop;
* This class is not thread-safe, all methods must be called from the
* thread that runs the #EventLoop.
*/
class DeferEvent final
: public boost::intrusive::list_base_hook<>
class DeferEvent final : AutoUnlinkIntrusiveListHook
{
friend class EventLoop;
friend class IntrusiveList<DeferEvent>;
EventLoop &loop;
@ -51,23 +50,23 @@ public:
DeferEvent(const DeferEvent &) = delete;
DeferEvent &operator=(const DeferEvent &) = delete;
~DeferEvent() noexcept {
Cancel();
}
EventLoop &GetEventLoop() const noexcept {
auto &GetEventLoop() const noexcept {
return loop;
}
void Schedule() noexcept;
void Cancel() noexcept;
private:
bool IsPending() const noexcept {
return is_linked();
}
void RunDeferred() noexcept {
void Schedule() noexcept;
void Cancel() noexcept {
if (IsPending())
unlink();
}
private:
void Run() noexcept {
callback();
}
};

View File

@ -198,29 +198,17 @@ EventLoop::HandleTimers() noexcept
void
EventLoop::AddDeferred(DeferEvent &d) noexcept
{
if (d.IsPending())
return;
deferred.push_back(d);
defer.push_back(d);
again = true;
}
void
EventLoop::RemoveDeferred(DeferEvent &d) noexcept
{
if (d.IsPending())
deferred.erase(deferred.iterator_to(d));
}
void
EventLoop::RunDeferred() noexcept
{
while (!deferred.empty() && !quit) {
auto &m = deferred.front();
assert(m.IsPending());
deferred.pop_front();
m.RunDeferred();
while (!defer.empty() && !quit) {
defer.pop_front_and_dispose([](DeferEvent *e){
e->Run();
});
}
}

View File

@ -79,11 +79,9 @@ class EventLoop final
boost::intrusive::constant_time_size<false>>;
TimerSet timers;
using DeferList =
boost::intrusive::list<DeferEvent,
boost::intrusive::base_hook<boost::intrusive::list_base_hook<>>,
boost::intrusive::constant_time_size<false>>;
DeferList deferred;
using DeferList = IntrusiveList<DeferEvent>;
DeferList defer;
using IdleList = IntrusiveList<IdleEvent>;
IdleList idle;
@ -214,12 +212,6 @@ public:
*/
void AddDeferred(DeferEvent &d) noexcept;
/**
* Cancel a pending call to DeferEvent::RunDeferred().
* However after returning, the call may still be running.
*/
void RemoveDeferred(DeferEvent &d) noexcept;
#ifdef HAVE_THREADED_EVENT_LOOP
/**
* Schedule a call to the InjectEvent.