34#error THIS HEADER IS A GENERATOR. DO NOT INCLUDE.
63#ifndef ETL_FSM_INCLUDED
64#define ETL_FSM_INCLUDED
72#include "message_router.h"
86#if !defined(ETL_FSM_STATE_ID_TYPE)
95#if ETL_USING_CPP17 && !defined(ETL_FSM_FORCE_CPP03_IMPLEMENTATION)
121 fsm_exception(string_type reason_, string_type file_name_, numeric_type line_number_)
122 :
etl::exception(reason_, file_name_, line_number_)
134 fsm_null_state_exception(string_type file_name_, numeric_type line_number_)
135 :
etl::fsm_exception(ETL_ERROR_TEXT(
"fsm:null state", ETL_FSM_FILE_ID
"A"), file_name_, line_number_)
147 fsm_state_id_exception(string_type file_name_, numeric_type line_number_)
148 :
etl::fsm_exception(ETL_ERROR_TEXT(
"fsm:state id", ETL_FSM_FILE_ID
"B"), file_name_, line_number_)
160 fsm_state_list_exception(string_type file_name_, numeric_type line_number_)
161 :
etl::fsm_exception(ETL_ERROR_TEXT(
"fsm:state list", ETL_FSM_FILE_ID
"C"), file_name_, line_number_)
173 fsm_state_list_order_exception(string_type file_name_, numeric_type line_number_)
174 :
etl::fsm_exception(ETL_ERROR_TEXT(
"fsm:state list order", ETL_FSM_FILE_ID
"D"), file_name_, line_number_)
185 fsm_state_composite_state_change_forbidden(string_type file_name_, numeric_type line_number_)
186 :
etl::fsm_exception(ETL_ERROR_TEXT(
"fsm:change in composite state forbidden", ETL_FSM_FILE_ID
"E"), file_name_, line_number_)
197 fsm_not_started(string_type file_name_, numeric_type line_number_)
198 :
etl::fsm_exception(ETL_ERROR_TEXT(
"fsm:not started", ETL_FSM_FILE_ID
"F"), file_name_, line_number_)
203 namespace private_fsm
205 template <
typename T =
void>
206 class ifsm_state_helper
215 static ETL_CONSTANT
fsm_state_id_t Pass_To_Parent = No_State_Change - 1U;
218 static ETL_CONSTANT
fsm_state_id_t Self_Transition = No_State_Change - 2U;
221 template <
typename T>
222 ETL_CONSTANT
fsm_state_id_t ifsm_state_helper<T>::No_State_Change;
224 template <
typename T>
227 template <
typename T>
228 ETL_CONSTANT
fsm_state_id_t ifsm_state_helper<T>::Self_Transition;
234 class ifsm_state :
public private_fsm::ifsm_state_helper<>
242 using private_fsm::ifsm_state_helper<>::No_State_Change;
243 using private_fsm::ifsm_state_helper<>::Pass_To_Parent;
244 using private_fsm::ifsm_state_helper<>::Self_Transition;
246#if ETL_USING_CPP17 && !defined(ETL_FSM_FORCE_CPP03_IMPLEMENTATION)
248 friend class fsm_state;
280 state.p_parent =
this;
282 if (p_default_child == ETL_NULLPTR)
284 p_active_child = &state;
285 p_default_child = &state;
293 template <
typename TSize>
296 p_active_child = ETL_NULLPTR;
297 p_default_child = ETL_NULLPTR;
302 add_child_state(*state_list[
i]);
313 p_context(ETL_NULLPTR),
314 p_parent(ETL_NULLPTR),
315 p_active_child(ETL_NULLPTR),
316 p_default_child(ETL_NULLPTR)
337 virtual fsm_state_id_t on_enter_state() {
return No_State_Change; }
338 virtual void on_exit_state() {}
341 void set_fsm_context(
etl::fsm& context)
343 p_context = &context;
353 ifsm_state* p_parent;
356 ifsm_state* p_active_child;
359 ifsm_state* p_default_child;
362 ifsm_state(
const ifsm_state&);
363 ifsm_state& operator =(
const ifsm_state&);
374 using imessage_router::receive;
379 fsm(etl::message_router_id_t
id)
381 , p_state(ETL_NULLPTR)
382 , state_list(ETL_NULLPTR)
383 , number_of_states(0
U)
390 template <
typename TSize>
403 state_list[
i]->set_fsm_context(*
this);
416 if (p_state == ETL_NULLPTR)
418 p_state = state_list[0];
429 next_state_id = p_state->on_enter_state();
430 if (next_state_id != ifsm_state::No_State_Change)
433 p_state = state_list[next_state_id];
449 if (have_changed_state(next_state_id))
456 p_state->on_exit_state();
459 next_state_id = p_state->on_enter_state();
461 if (have_changed_state(next_state_id))
468 else if (is_self_transition(next_state_id))
470 p_state->on_exit_state();
471 p_state->on_enter_state();
480 using imessage_router::accepts;
497 return p_state->get_state_id();
523 return p_state != ETL_NULLPTR;
534 p_state->on_exit_state();
537 p_state = ETL_NULLPTR;
541 ETL_DEPRECATED
bool is_null_router()
const ETL_OVERRIDE
547 bool is_producer() const ETL_OVERRIDE
553 bool is_consumer() const ETL_OVERRIDE
563 return (next_state_id != p_state->get_state_id()) &&
564 (next_state_id != ifsm_state::No_State_Change) &&
565 (next_state_id != ifsm_state::Self_Transition);
571 return (next_state_id == ifsm_state::Self_Transition);
582#if ETL_USING_CPP17 && !defined(ETL_FSM_FORCE_CPP03_IMPLEMENTATION)
586 template <
typename TContext,
typename TDerived,
etl::fsm_state_id_t STATE_ID_,
typename... TMessageTypes>
587 class fsm_state :
public ifsm_state
604 TContext& get_fsm_context()
const
606 return static_cast<TContext&
>(ifsm_state::get_fsm_context());
623 const bool was_handled = (process_event_type<TMessageTypes>(message, new_state_id) || ...);
625 if (!was_handled || (new_state_id == Pass_To_Parent))
627 new_state_id = (p_parent !=
nullptr) ? p_parent->process_event(message) :
static_cast<TDerived*
>(
this)->on_event_unknown(message);
634 template <
typename TMessage>
637 if (TMessage::ID == msg.get_message_id())
639 new_state_id =
static_cast<TDerived*
>(
this)->on_event(
static_cast<const TMessage&
>(msg));
650 template <
typename TContext,
typename TDerived,
etl::fsm_state_id_t STATE_ID_,
typename... TMessageTypes>
651 ETL_CONSTANT
etl::fsm_state_id_t fsm_state<TContext, TDerived, STATE_ID_, TMessageTypes...>::STATE_ID;
Base exception class for FSM.
Definition fsm.h:99
Exception for message received but not started.
Definition fsm.h:176
Exception for null state pointer.
Definition fsm.h:112
Exception for invalid state id.
Definition fsm.h:125
Exception for incompatible state list.
Definition fsm.h:138
Exception for incompatible order state list.
Definition fsm.h:151
The FSM class.
Definition fsm.h:344
etl::fsm_state_id_t get_state_id() const
Gets the current state id.
Definition fsm_generator.h:494
void receive(const etl::imessage &message) ETL_OVERRIDE
Top level message handler for the FSM.
Definition fsm_generator.h:443
virtual void start(bool call_on_enter_state=true)
Starts the FSM. Can only be called once. Subsequent calls will do nothing.
Definition fsm_generator.h:413
fsm(etl::message_router_id_t id)
Constructor.
Definition fsm_generator.h:379
virtual void reset(bool call_on_exit_state=false)
Reset the FSM to pre-started state.
Definition fsm_generator.h:530
bool accepts(etl::message_id_t) const ETL_OVERRIDE
Does this FSM accept the message id? Yes, it accepts everything!
Definition fsm_generator.h:486
void set_states(etl::ifsm_state **p_states, TSize size)
Set the states for the FSM.
Definition fsm_generator.h:391
const ifsm_state & get_state() const
Gets a const reference to the current state interface.
Definition fsm_generator.h:512
ifsm_state & get_state()
Gets a reference to the current state interface.
Definition fsm_generator.h:503
bool is_started() const
Checks if the FSM has been started.
Definition fsm_generator.h:521
Interface class for FSM states.
Definition fsm.h:216
void add_child_state(etl::ifsm_state &state)
Adds a child to this state. Only of use when part of an HFSM.
Definition fsm_generator.h:277
void set_child_states(etl::ifsm_state **state_list, TSize size)
Adds a list of child states. Only of use when part of an HFSM.
Definition fsm_generator.h:294
etl::fsm_state_id_t get_state_id() const
Gets the id for this state.
Definition fsm_generator.h:268
ifsm_state(etl::fsm_state_id_t state_id_)
Constructor.
Definition fsm_generator.h:311
virtual ~ifsm_state()
Destructor.
Definition fsm_generator.h:323
This is the base of all message routers.
Definition message_router_generator.h:121
#define ETL_ASSERT(b, e)
Definition error_handler.h:356
Definition exception.h:47
Definition integral_limits.h:516
Defines a type that is as larger or larger than the specified type. Will return the specified type is...
Definition largest_generator.h:352
bitset_ext
Definition absolute.h:38
uint_least8_t message_id_t
Allow alternative type for message id.
Definition message_types.h:40
ETL_CONSTEXPR TContainer::size_type size(const TContainer &container)
Definition iterator.h:1187
uint_least8_t fsm_state_id_t
Allow alternative type for state id.
Definition fsm.h:75
pair holds two objects of arbitrary type
Definition utility.h:164