
2. Is is somehow possible to reuse state definitions as substates of different "higher-level" states?
In boost/libs/statechart/doc/tutorial.html#TransitionActions it says, "With Boost.Statechart, a transition action can be a member of any common outer context" and goes on to give some examples. If I've understood your question correctly then the answer is "Yes".
Actually, I'm inclined to say "No" considering the following (partially duplicated from your part later in the posting):
Top Remote Idle Executing Local Idle Executing
This I cannot do, right? Idle and Executing would ideally be the same, but as they are statically associated with their outer states (and vice versa) it doesn't look like it's possible.
OK, I've miss understood. Does this help? boost/libs/statechart/doc/tutorial.html#SubmachinesAndParametrizedStates It describes how to use templates to implement submachines. In the above example you'd use Executing<Remote> and Executing<Local>.
- I've got an application that can be either in remote or locally controlled mode (this is the highest-level states). - Certain events are allowed both in remote and local, while some are not. As an example, the "CommandEvent" event should be handled both in remote and local - resulting in the "ExecutingCommandState" being entered. - I'd like to be able to reuse the definition of ExecutingCommandState regardless of the enclosing state being Remote or Local - Possible?
Could you implement this with orthogonal regions?
Top Remote Local ------ Idle Executing
Sorry for my ignorance, but what then happens if there would be an additional substate, that should only be possible when in e.g. the Remote state.
Then it would go in the remote state. If you want a state only available in Remote and Executing that can't be done. But then you are not simply reusing Executing submachine because it's different in Remote and Local.
Top Remote RIdle RExecuting Local LIdle LExecuting
This is more similar to what I've got. There isn't really any other code duplication that having to define the e.g. RIdle, LIdle, RExecuting, LExecuting, as the state machine itself holds a reference to the domain object responsible for executing the actions. Within the different states I simply get this object using context<StateMachine> and delegate - so the state machine is in this case only used for discriminating the disallowed events according to the current state.
So what is it you want to reuse? Is it a common list of reactions, to which each of L & RExecuting add the reactions specific to Local and Remote?
UML provides "Do Activities" that can be used for this purpose. The statechart docs suggest simulating this "with a separate thread that is started in the entry action and canceled (!) in the exit action of a particular state". I quite like that approach.
I considered executing the commands in a worker thread similar to that approach; when receiving a command the FSM would enter the ExecutingCommand state, kick off a new thread (or using a previously existing worker thread) to execute the command. The problem I ran into that I wanted the command-executing thread _itself_ being able to signal the completion of the command (and thus trigger exiting the ExecutingCommand state to the previous state). It should never be possible to exit the state unless the command has run to an end, e.g. by unconditionally joining the worker thread in the state's destructor.
I couldn't really find a clean, thread-safe way to implement this. Did you actually try to implement anything like this?
Not yet. Can the worker thread, after processing the command push a Finished event onto the queue. When the statemachine thread receives this event it exits the Executing state.