diff --git a/server/robotserver/comgr.cc b/server/robotserver/comgr.cc index 8d83d118..f66d4e04 100644 --- a/server/robotserver/comgr.cc +++ b/server/robotserver/comgr.cc @@ -6,6 +6,7 @@ void CoMgr::Init() { INIT_LIST_HEAD(&co_list_); + INIT_LIST_HEAD(&exec_list_); } void CoMgr::UnInit() @@ -17,11 +18,15 @@ void CoMgr::Update() { Coroutine *co = nullptr, *tmp = nullptr; list_for_each_entry_safe(co, tmp, &co_list_, entry) { - co->Exec(); + if (!co->Exec()) { + co->hold_self_ = nullptr; + } } } std::weak_ptr CoMgr::CreateCoroutine(std::function cb) { - return std::make_shared(cb); + auto co = std::make_shared(cb); + co->hold_self_ = co; + return co; } diff --git a/server/robotserver/comgr.h b/server/robotserver/comgr.h index ca879688..fd8c7bc2 100644 --- a/server/robotserver/comgr.h +++ b/server/robotserver/comgr.h @@ -22,5 +22,7 @@ class CoMgr : public a8::Singleton list_head co_list_; + list_head exec_list_; + friend class Coroutine; }; diff --git a/server/robotserver/coroutine.cc b/server/robotserver/coroutine.cc index 5f4f7e53..a5cf55e3 100644 --- a/server/robotserver/coroutine.cc +++ b/server/robotserver/coroutine.cc @@ -17,20 +17,23 @@ Coroutine::Coroutine(std::function cb) cb_(this); CallExit(sink); }); + list_add_tail(&entry, &CoMgr::Instance()->co_list_); Attach(); } Coroutine::~Coroutine() { Deatch(); + list_del_init(&entry); } -void Coroutine::Exec() +bool Coroutine::Exec() { if (*source_) { (*source_)(); + return true; } else { - Deatch(); + return false; } } @@ -61,7 +64,7 @@ void Coroutine::CoAwait(Awaiter* awaiter) void Coroutine::Attach() { - list_add_tail(&entry, &CoMgr::Instance()->co_list_); + list_add_tail(&entry, &CoMgr::Instance()->exec_list_); } void Coroutine::Deatch() diff --git a/server/robotserver/coroutine.h b/server/robotserver/coroutine.h index 940e5551..d6ccdbac 100644 --- a/server/robotserver/coroutine.h +++ b/server/robotserver/coroutine.h @@ -12,7 +12,7 @@ class Promise : public Awaiter }; -class Coroutine : public Awaiter +class Coroutine : public Awaiter, public std::enable_shared_from_this { public: list_head entry; @@ -20,7 +20,7 @@ class Coroutine : public Awaiter Coroutine(std::function cb); ~Coroutine(); - void Exec(); + bool Exec(); void CoSuspend(); void CoResume(); void CoYield(); @@ -35,8 +35,10 @@ class Coroutine : public Awaiter void CallExit(boost::coroutines2::coroutine::push_type& sink); private: + std::shared_ptr hold_self_; std::shared_ptr::pull_type> source_; std::function cb_; boost::coroutines2::coroutine::push_type* sink_ = nullptr; + friend class CoMgr; };