forked from boostorg/mpl
151 lines
4.0 KiB
C++
151 lines
4.0 KiB
C++
//-----------------------------------------------------------------------------
|
|
// boost fsm/handler.hpp header file
|
|
// See http://www.boost.org for updates, documentation, and revision history.
|
|
//-----------------------------------------------------------------------------
|
|
//
|
|
// Copyright (c) 2002
|
|
// Aleksey Gurtovoy
|
|
//
|
|
// Permission to use, copy, modify, distribute and sell this software
|
|
// and its documentation for any purpose is hereby granted without fee,
|
|
// provided that the above copyright notice appears in all copies and
|
|
// that both the copyright notice and this permission notice appear in
|
|
// supporting documentation. No representations are made about the
|
|
// suitability of this software for any purpose. It is provided "as is"
|
|
// without express or implied warranty.
|
|
|
|
#ifndef BOOST_FSM_HANDLER_INCLUDED
|
|
#define BOOST_FSM_HANDLER_INCLUDED
|
|
|
|
#include "boost/mpl/if.hpp"
|
|
#include "boost/mpl/fold.hpp"
|
|
#include "boost/mpl/front.hpp"
|
|
#include "boost/type_traits/is_same.hpp"
|
|
|
|
#include <typeinfo>
|
|
#include <cassert>
|
|
|
|
namespace fsm {
|
|
namespace aux {
|
|
|
|
namespace mpl = boost::mpl;
|
|
using namespace mpl::placeholders;
|
|
|
|
template< typename Transition >
|
|
struct STT_void_row_impl
|
|
{
|
|
typedef typename Transition::from_state_t state_t;
|
|
typedef typename Transition::fsm_t fsm_t;
|
|
typedef typename Transition::base_event_t base_event_t;
|
|
|
|
static long do_process_event(fsm_t&, long state, base_event_t const&)
|
|
{
|
|
assert(false);
|
|
return state;
|
|
}
|
|
|
|
static long do_transition(fsm_t&, long state, base_event_t const&)
|
|
{
|
|
assert(false);
|
|
return state;
|
|
}
|
|
};
|
|
|
|
|
|
template<
|
|
typename PrevRowImpl
|
|
, typename Transition
|
|
>
|
|
struct STT_event_row_impl
|
|
: PrevRowImpl
|
|
{
|
|
typedef typename Transition::from_state_t state_t;
|
|
typedef typename Transition::fsm_t fsm_t;
|
|
typedef typename Transition::base_event_t base_event_t;
|
|
|
|
static long do_process_event(fsm_t& fsm, long state, base_event_t const& evt)
|
|
{
|
|
if (typeid(typename Transition::event_t) == typeid(evt))
|
|
{
|
|
// typedefs are here to make GCC happy
|
|
typedef typename Transition::to_state_t to_state_;
|
|
typedef typename Transition::from_state_t from_state_;
|
|
|
|
return Transition::do_transition(fsm, evt)
|
|
? to_state_::do_check_invariant(fsm)
|
|
: from_state_::do_check_invariant(fsm)
|
|
;
|
|
}
|
|
|
|
return PrevRowImpl::do_process_event(fsm, state, evt);
|
|
}
|
|
};
|
|
|
|
template<
|
|
typename PrevRowImpl
|
|
, typename StateType
|
|
>
|
|
struct STT_state_row_impl
|
|
: PrevRowImpl
|
|
{
|
|
typedef typename PrevRowImpl::fsm_t fsm_t;
|
|
typedef typename PrevRowImpl::base_event_t base_event_t;
|
|
|
|
static long do_transition(fsm_t& fsm, long state, base_event_t const& evt)
|
|
{
|
|
return state == StateType::value
|
|
? PrevRowImpl::do_process_event(fsm, state, evt)
|
|
: PrevRowImpl::do_transition(fsm, state, evt)
|
|
;
|
|
}
|
|
|
|
static long do_process_event(fsm_t&, long state, base_event_t const&)
|
|
{
|
|
assert(false);
|
|
return state;
|
|
}
|
|
};
|
|
|
|
template<
|
|
typename PrevRowImpl
|
|
, typename Transition
|
|
>
|
|
struct STT_row_impl
|
|
{
|
|
typedef typename mpl::if_<
|
|
boost::is_same<
|
|
typename PrevRowImpl::state_t
|
|
, typename Transition::from_state_t
|
|
>
|
|
, STT_event_row_impl< PrevRowImpl,Transition >
|
|
, STT_event_row_impl<
|
|
STT_state_row_impl< PrevRowImpl,typename PrevRowImpl::state_t >
|
|
, Transition
|
|
>
|
|
>::type type;
|
|
};
|
|
|
|
|
|
template< typename Transitions >
|
|
struct STT_impl_gen
|
|
{
|
|
private:
|
|
typedef typename mpl::front<Transitions>::type first_;
|
|
typedef typename mpl::fold<
|
|
Transitions
|
|
, STT_void_row_impl<first_>
|
|
, STT_row_impl<_,_>
|
|
>::type STT_impl_;
|
|
|
|
public:
|
|
typedef STT_state_row_impl<
|
|
STT_impl_
|
|
, typename STT_impl_::state_t
|
|
> type;
|
|
};
|
|
|
|
} // namespace aux
|
|
} // namespace fsm
|
|
|
|
#endif // BOOST_FSM_HANDLER_INCLUDED
|