diff --git a/lib/include/srslte/common/fsm.h b/lib/include/srslte/common/fsm.h index 8e4537b67..b2cfe2313 100644 --- a/lib/include/srslte/common/fsm.h +++ b/lib/include/srslte/common/fsm.h @@ -23,10 +23,11 @@ #define SRSLTE_FSM_H #include "srslte/common/logmap.h" +#include "srslte/common/move_callback.h" #include "type_utils.h" #include -#include #include +#include #include #include @@ -370,6 +371,8 @@ public: &get_unchecked()); } } + state_list(state_list&&) noexcept = default; + state_list& operator=(state_list&&) noexcept = default; template bool is() const @@ -414,19 +417,21 @@ public: }; explicit fsm_t(srslte::log_ref log_) : log_h(log_) {} + fsm_t(fsm_t&&) noexcept = default; + fsm_t& operator=(fsm_t&&) noexcept = default; // Push Events to FSM template bool trigger(Ev&& e) { if (trigger_locked) { - pending_events.emplace_back([e](fsm_t* d) { d->process_event(e); }); + scheduled_event(std::forward(e), typename std::is_lvalue_reference::type{}); return false; } trigger_locked = true; bool ret = process_event(std::forward(e)); while (not pending_events.empty()) { - pending_events.front()(this); + pending_events.front()(); pending_events.pop_front(); } trigger_locked = false; @@ -511,10 +516,21 @@ protected: return visitor.result; } - srslte::log_ref log_h; - srslte::LOG_LEVEL_ENUM fsm_event_log_level = LOG_LEVEL_INFO; - bool trigger_locked = false; - std::deque*)> > pending_events; + template + void scheduled_event(Ev&& e, std::true_type) + { + pending_events.emplace_back([this, e]() { process_event(e); }); + } + template + void scheduled_event(Ev&& e, std::false_type) + { + pending_events.emplace_back(std::bind([this](Ev& e) { process_event(std::move(e)); }, std::move(e))); + } + + srslte::log_ref log_h; + srslte::LOG_LEVEL_ENUM fsm_event_log_level = LOG_LEVEL_INFO; + bool trigger_locked = false; + std::list > pending_events; }; template @@ -526,6 +542,8 @@ public: static const bool is_nested = true; explicit nested_fsm_t(ParentFSM* parent_fsm_) : fsm_t(parent_fsm_->get_log()), fsm_ptr(parent_fsm_) {} + nested_fsm_t(nested_fsm_t&&) noexcept = default; + nested_fsm_t& operator=(nested_fsm_t&&) noexcept = default; // Get pointer to outer FSM in case of HSM const parent_t* parent_fsm() const { return fsm_ptr; } diff --git a/lib/test/common/fsm_test.cc b/lib/test/common/fsm_test.cc index 8d416dd22..08e6aaaff 100644 --- a/lib/test/common/fsm_test.cc +++ b/lib/test/common/fsm_test.cc @@ -63,6 +63,8 @@ public: }; explicit fsm2(fsm1* f_) : nested_fsm_t(f_) {} + fsm2(fsm2&&) noexcept = default; + fsm2& operator=(fsm2&&) noexcept = default; ~fsm2() { log_h->info("%s being destroyed!", get_type_name(*this).c_str()); } private: diff --git a/srsenb/src/stack/rrc/rrc_mobility.cc b/srsenb/src/stack/rrc/rrc_mobility.cc index 65ce19e18..641e0bac5 100644 --- a/srsenb/src/stack/rrc/rrc_mobility.cc +++ b/srsenb/src/stack/rrc/rrc_mobility.cc @@ -709,7 +709,7 @@ void rrc::ue::rrc_mobility::handle_ho_preparation_complete(bool is_success, srsl trigger(srslte::failure_ev{}); return; } - trigger(container); + trigger(std::move(container)); } bool rrc::ue::rrc_mobility::update_ue_var_meas_cfg(const asn1::rrc::meas_cfg_s& source_meas_cfg,