Hi,
I've been working for a while with the MSM and I'm very impressed about it... congratulations for your work!! Thanks :)
I've to say that I'm not an expert on UML nor state machines and I think that my needs are a very common user-case... so I'm probably >missing something!
Basically what I need is a (reusable) Timer that, after a number of Clocks, it sends a TimeOut to the state machine, and when the Timer receives a Reset it restarts the counting of clocks. (I want to also add a Pause or similar but this doesn't matter right now...)
Yes, you could also use a region with 1 state and internal transitions but it's about the same.
So, the goal is that any (or all) of my states could be controlled by the Timer and if no events are received for a while a TimeOut will be (always) received/processed.
AFAIK there is no concept of timer/timeout in the MSM, but I found very straightforward to implement my idea with an Orthogonal Region with a single state Timer that receives Clock and Reset events and sends a TimeOut. And it worked like a charm!!
But I found a problem with one of my states become a submachine... The Timer::Reset action executes a fsm.process_event(Timer::Reset()), but this event is not processed. I realized that "fsm" is the submachine and AFAIK there is no way to access to the parent(est) fsm...
Yes it's something which has been requested a few times, it will be done, but I didn't come to it yet. In the meantime you have 2 solutions: - exit the submachine using an exit pseudo state, it's UML conform and visible in your diagram. - keep a pointer to the parent-est machine. Not very beautiful but it'll work.
So, is there a better or more standard way to implement a Timer/Timeout in UML/MSM?
There is no timer in MSM for 2 reasons: - it's out of the scope of the library and I'm probably not the ideal person for this (too system-dependent). - it would have to be done in another thread generating tick events => possible race condition. The only solution is outside the fsm. You can use asio, which will cost you a thread and you'll have to prevent the race condition. You can use a posix function to this aim too. To my knowledge, there is no other timer in boost (I looked but I might have missed it).
And, although "fsm" is the submachine, why the no_transition function is not executed (this last seems a bug to me...).
I don't think so. If the submachine doesn't handle the event, the upper one could, so it gets a chance to do it, etc. until the top-level fsm. If no fsm including the top-level fsm brings a no_transition, then it's a bug.
Albert
PD: Do you think that has meaning that the MSM could have an "on_timeout" function for the states (like on_entry/exit?), or to have a timeout event like "none"... ok may be this sounds huge to implement and not so generic...
And system-dependent. I have the hope someone in boost will provide this one day. Then I'd be happy to use it in MSM. HTH, Christophe