|
Boost-Commit : |
Subject: [Boost-commit] svn:boost r63704 - trunk/boost/msm/back
From: christophe.j.henry_at_[hidden]
Date: 2010-07-06 15:08:01
Author: chenry
Date: 2010-07-06 15:07:59 EDT (Tue, 06 Jul 2010)
New Revision: 63704
URL: http://svn.boost.org/trac/boost/changeset/63704
Log:
fixed sporadic bug with explicit entries
Text files modified:
trunk/boost/msm/back/metafunctions.hpp | 22 ++++++++++++++-
trunk/boost/msm/back/state_machine.hpp | 55 +++++++++++++++++++--------------------
2 files changed, 47 insertions(+), 30 deletions(-)
Modified: trunk/boost/msm/back/metafunctions.hpp
==============================================================================
--- trunk/boost/msm/back/metafunctions.hpp (original)
+++ trunk/boost/msm/back/metafunctions.hpp 2010-07-06 15:07:59 EDT (Tue, 06 Jul 2010)
@@ -54,6 +54,7 @@
BOOST_MPL_HAS_XXX_TRAIT_DEF(no_exception_thrown)
BOOST_MPL_HAS_XXX_TRAIT_DEF(no_message_queue)
BOOST_MPL_HAS_XXX_TRAIT_DEF(activate_deferred_events)
+BOOST_MPL_HAS_XXX_TRAIT_DEF(wrapped_entry)
namespace boost { namespace msm { namespace back
{
@@ -340,6 +341,23 @@
typedef typename StateType::explicit_creation type;
};
+template <class StateType>
+struct get_wrapped_entry
+{
+ typedef typename StateType::wrapped_entry type;
+};
+// used for states created with explicit_creation
+// if the state is an explicit entry, we reach for the wrapped state
+// otherwise, this returns the state itself
+template <class StateType>
+struct get_wrapped_state
+{
+ typedef typename ::boost::mpl::eval_if<
+ typename has_wrapped_entry<StateType>::type,
+ get_wrapped_entry<StateType>,
+ ::boost::mpl::identity<StateType> >::type type;
+};
+
template <class Derived>
struct create_stt
{
@@ -357,7 +375,7 @@
::boost::mpl::has_key<states, ::boost::mpl::placeholders::_2>,
::boost::mpl::placeholders::_1,
::boost::mpl::insert< ::boost::mpl::placeholders::_1, ::boost::mpl::end<mpl::placeholders::_1>,
- not_a_row< ::boost::mpl::placeholders::_2 > >
+ not_a_row< get_wrapped_state< ::boost::mpl::placeholders::_2> > >
>
>::type with_init;
// do the same for states marked as explicitly created
@@ -379,7 +397,7 @@
::boost::mpl::has_key<states, ::boost::mpl::placeholders::_2>,
::boost::mpl::placeholders::_1,
::boost::mpl::insert< ::boost::mpl::placeholders::_1, ::boost::mpl::end<mpl::placeholders::_1>,
- not_a_row< ::boost::mpl::placeholders::_2 > >
+ not_a_row< get_wrapped_state< ::boost::mpl::placeholders::_2> > >
>
>::type type;
};
Modified: trunk/boost/msm/back/state_machine.hpp
==============================================================================
--- trunk/boost/msm/back/state_machine.hpp (original)
+++ trunk/boost/msm/back/state_machine.hpp 2010-07-06 15:07:59 EDT (Tue, 06 Jul 2010)
@@ -17,7 +17,6 @@
#include <functional>
#include <numeric>
#include <utility>
-
#include <boost/mpl/contains.hpp>
#include <boost/mpl/deref.hpp>
@@ -264,7 +263,7 @@
struct entry_pt : public EntryPoint
{
// tags
- typedef EntryPoint wrapped_exit;
+ typedef EntryPoint wrapped_entry;
typedef int pseudo_entry;
typedef library_sm owner;
typedef int no_automatic_create;
@@ -289,13 +288,13 @@
typedef typename make_entry<typename ROW::Source,library_sm>::type T1;
typedef typename make_exit<typename ROW::Target,library_sm>::type T2;
typedef typename ROW::Evt transition_event;
- // if the source has no automatic creation (i.e. is an exit pseudo state), then
+ // if the source is an exit pseudo state, then
// current_state_type becomes the result of get_owner
// meaning the containing SM from which the exit occurs
typedef typename ::boost::mpl::eval_if<
- typename has_no_automatic_create<T1>::type,
- get_owner<T1,library_sm>,
- ::boost::mpl::identity<T1> >::type current_state_type;
+ typename has_pseudo_exit<T1>::type,
+ get_owner<T1,library_sm>,
+ ::boost::mpl::identity<typename ROW::Source> >::type current_state_type;
// if Target is a sequence, then we have a fork and expect a sequence of explicit_entry
// else if Target is an explicit_entry, next_state_type becomes the result of get_owner
@@ -327,7 +326,7 @@
BOOST_STATIC_CONSTANT(int, next_state = (get_state_id<stt,next_state_type>::type::value));
BOOST_ASSERT(state == (current_state));
// if T1 is an exit pseudo state, then take the transition only if the pseudo exit state is active
- if (!::boost::is_same<T1,current_state_type>::value &&
+ if (has_pseudo_exit<T1>::type::value &&
!is_exit_state_active<T1,get_owner<T1,library_sm> >(fsm))
{
return HANDLED_FALSE;
@@ -366,13 +365,13 @@
typedef typename make_entry<typename ROW::Source,library_sm>::type T1;
typedef typename make_exit<typename ROW::Target,library_sm>::type T2;
typedef typename ROW::Evt transition_event;
- // if the source has no automatic creation (i.e. is an exit pseudo state), then
+ // if the source is an exit pseudo state, then
// current_state_type becomes the result of get_owner
// meaning the containing SM from which the exit occurs
typedef typename ::boost::mpl::eval_if<
- typename has_no_automatic_create<T1>::type,
- get_owner<T1,library_sm>,
- ::boost::mpl::identity<T1> >::type current_state_type;
+ typename has_pseudo_exit<T1>::type,
+ get_owner<T1,library_sm>,
+ ::boost::mpl::identity<typename ROW::Source> >::type current_state_type;
// if Target is a sequence, then we have a fork and expect a sequence of explicit_entry
// else if Target is an explicit_entry, next_state_type becomes the result of get_owner
@@ -403,7 +402,7 @@
BOOST_STATIC_CONSTANT(int, next_state = (get_state_id<stt,next_state_type>::type::value));
BOOST_ASSERT(state == (current_state));
// if T1 is an exit pseudo state, then take the transition only if the pseudo exit state is active
- if (!::boost::is_same<T1,current_state_type>::value &&
+ if (has_pseudo_exit<T1>::type::value &&
!is_exit_state_active<T1,get_owner<T1,library_sm> >(fsm))
{
return HANDLED_FALSE;
@@ -436,13 +435,13 @@
typedef typename make_entry<typename ROW::Source,library_sm>::type T1;
typedef typename make_exit<typename ROW::Target,library_sm>::type T2;
typedef typename ROW::Evt transition_event;
- // if the source has no automatic creation (i.e. is an exit pseudo state), then
+ // if the source is an exit pseudo state, then
// current_state_type becomes the result of get_owner
// meaning the containing SM from which the exit occurs
typedef typename ::boost::mpl::eval_if<
- typename has_no_automatic_create<T1>::type,
- get_owner<T1,library_sm>,
- ::boost::mpl::identity<T1> >::type current_state_type;
+ typename has_pseudo_exit<T1>::type,
+ get_owner<T1,library_sm>,
+ ::boost::mpl::identity<typename ROW::Source> >::type current_state_type;
// if Target is a sequence, then we have a fork and expect a sequence of explicit_entry
// else if Target is an explicit_entry, next_state_type becomes the result of get_owner
@@ -464,7 +463,7 @@
BOOST_ASSERT(state == (current_state));
// if T1 is an exit pseudo state, then take the transition only if the pseudo exit state is active
- if (!::boost::is_same<T1,current_state_type>::value &&
+ if (has_pseudo_exit<T1>::type::value &&
!is_exit_state_active<T1,get_owner<T1,library_sm> >(fsm))
{
return HANDLED_FALSE;
@@ -499,13 +498,13 @@
typedef typename make_entry<typename ROW::Source,library_sm>::type T1;
typedef typename make_exit<typename ROW::Target,library_sm>::type T2;
typedef typename ROW::Evt transition_event;
- // if the source has no automatic creation (i.e. is an exit pseudo state), then
+ // if the source is an exit pseudo state, then
// current_state_type becomes the result of get_owner
// meaning the containing SM from which the exit occurs
typedef typename ::boost::mpl::eval_if<
- typename has_no_automatic_create<T1>::type,
+ typename has_pseudo_exit<T1>::type,
get_owner<T1,library_sm>,
- ::boost::mpl::identity<T1> >::type current_state_type;
+ ::boost::mpl::identity<typename ROW::Source> >::type current_state_type;
// if Target is a sequence, then we have a fork and expect a sequence of explicit_entry
// else if Target is an explicit_entry, next_state_type becomes the result of get_owner
@@ -527,7 +526,7 @@
BOOST_ASSERT(state == (current_state));
// if T1 is an exit pseudo state, then take the transition only if the pseudo exit state is active
- if (!::boost::is_same<T1,current_state_type>::value &&
+ if (has_pseudo_exit<T1>::type::value &&
!is_exit_state_active<T1,get_owner<T1,library_sm> >(fsm))
{
return HANDLED_FALSE;
@@ -553,7 +552,7 @@
typedef typename make_entry<typename ROW::Source,library_sm>::type T1;
typedef typename make_exit<typename ROW::Target,library_sm>::type T2;
typedef typename ROW::Evt transition_event;
- typedef T1 current_state_type;
+ typedef typename ROW::Source current_state_type;
typedef T2 next_state_type;
// if a guard condition is here, call it to check that the event is accepted
@@ -596,7 +595,7 @@
typedef typename make_entry<typename ROW::Source,library_sm>::type T1;
typedef typename make_exit<typename ROW::Target,library_sm>::type T2;
typedef typename ROW::Evt transition_event;
- typedef T1 current_state_type;
+ typedef typename ROW::Source current_state_type;
typedef T2 next_state_type;
// if a guard condition is defined, call it to check that the event is accepted
@@ -633,7 +632,7 @@
typedef typename make_exit<typename ROW::Target,library_sm>::type T2;
typedef typename ROW::Evt transition_event;
- typedef T1 current_state_type;
+ typedef typename ROW::Source current_state_type;
typedef T2 next_state_type;
// Take the transition action and return the next state.
@@ -660,7 +659,7 @@
typedef typename make_entry<typename ROW::Source,library_sm>::type T1;
typedef typename make_exit<typename ROW::Target,library_sm>::type T2;
typedef typename ROW::Evt transition_event;
- typedef T1 current_state_type;
+ typedef typename ROW::Source current_state_type;
typedef T2 next_state_type;
// Take the transition action and return the next state.
@@ -1889,7 +1888,7 @@
operator()(EventType const& evt,FsmType& fsm, ::boost::msm::back::dummy<1> = 0)
{
(static_cast<Derived*>(self))->on_entry(evt,fsm);
- int state_id = get_state_id<stt,typename EventType::active_state>::value;
+ int state_id = get_state_id<stt,typename EventType::active_state::wrapped_entry>::value;
BOOST_STATIC_ASSERT(EventType::active_state::zone_index >= 0);
BOOST_STATIC_ASSERT(EventType::active_state::zone_index <= nr_regions::value);
// just set the correct zone, the others will be default/history initialized
@@ -1927,7 +1926,7 @@
{
// entry on the FSM
(static_cast<Derived*>(self))->on_entry(evt,fsm);
- int state_id = get_state_id<stt,typename EventType::active_state>::value;
+ int state_id = get_state_id<stt,typename EventType::active_state::wrapped_entry>::value;
// given region starts with the entry pseudo state as active state
self->m_states[EventType::active_state::zone_index] = state_id;
self->start(evt.m_event);
@@ -1946,7 +1945,7 @@
template <class StateType>
void operator()( ::boost::msm::wrap<StateType> const& )
{
- int state_id = get_state_id<stt,StateType>::value;
+ int state_id = get_state_id<stt,typename StateType::wrapped_entry>::value;
BOOST_STATIC_ASSERT(StateType::zone_index >= 0);
BOOST_STATIC_ASSERT(StateType::zone_index <= nr_regions::value);
helper_self->m_states[StateType::zone_index] = state_id;
Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk