My Project
simple_state.hpp
Go to the documentation of this file.
1 #ifndef BOOST_STATECHART_SIMPLE_STATE_HPP_INCLUDED
2 #define BOOST_STATECHART_SIMPLE_STATE_HPP_INCLUDED
3 // Copyright 2002-2010 Andreas Huber Doenni
5 // Distributed under the Boost Software License, Version 1.0. (See accompany-
6 // ing file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
8 
9 
10 
12 
13 #include <boost/statechart/detail/leaf_state.hpp>
14 #include <boost/statechart/detail/node_state.hpp>
15 #include <boost/statechart/detail/constructor.hpp>
16 #include <boost/statechart/detail/memory.hpp>
17 
18 #include <boost/mpl/eval_if.hpp>
19 #include <boost/mpl/if.hpp>
20 #include <boost/mpl/identity.hpp>
21 #include <boost/mpl/is_sequence.hpp>
22 #include <boost/mpl/list.hpp>
23 #include <boost/mpl/empty.hpp>
24 #include <boost/mpl/size.hpp>
25 #include <boost/mpl/front.hpp>
26 #include <boost/mpl/at.hpp>
27 #include <boost/mpl/find.hpp>
28 #include <boost/mpl/find_if.hpp>
29 #include <boost/mpl/contains.hpp>
30 #include <boost/mpl/distance.hpp>
31 #include <boost/mpl/deref.hpp>
32 #include <boost/mpl/pop_front.hpp>
33 #include <boost/mpl/push_front.hpp>
34 #include <boost/mpl/clear.hpp>
35 #include <boost/mpl/placeholders.hpp>
36 #include <boost/mpl/bool.hpp>
37 #include <boost/mpl/integral_c.hpp>
38 #include <boost/mpl/less.hpp>
39 #include <boost/mpl/equal_to.hpp>
40 #include <boost/mpl/not.hpp>
41 #include <boost/mpl/or.hpp>
42 
43 #include <boost/mpl/plus.hpp>
44 #include <boost/mpl/max_element.hpp>
45 #include <boost/mpl/greater.hpp>
46 
47 #include <boost/get_pointer.hpp>
48 #include <boost/intrusive_ptr.hpp>
49 #include <boost/assert.hpp>
50 #include <boost/type_traits/is_base_of.hpp>
51 #include <boost/type_traits/is_same.hpp>
52 #include <boost/static_assert.hpp>
53 #include <boost/polymorphic_cast.hpp> // boost::polymorphic_downcast
54 
55 #include <cstddef> // std::size_t
56 
57 
58 
59 namespace boost
60 {
61 namespace statechart
62 {
63 namespace detail
64 {
65 
66 
67 
69 template< class T >
70 struct make_list : public mpl::eval_if<
71  mpl::is_sequence< T >,
72  mpl::identity< T >,
73  mpl::identity< mpl::list< T > > > {};
74 
76 template< class MostDerived, class Context, class InnerInitial >
78 {
79  private:
80  typedef typename Context::outermost_context_base_type::allocator_type
81  allocator_type;
82  typedef typename Context::outermost_context_base_type::rtti_policy_type
83  rtti_policy_type;
85  inner_initial_list;
86  typedef typename mpl::size< inner_initial_list >::type
87  inner_initial_list_size;
88 
89  public:
90  typedef typename mpl::eval_if<
91  mpl::empty< inner_initial_list >,
92  mpl::identity< typename rtti_policy_type::
93  template rtti_derived_type< MostDerived, leaf_state<
94  allocator_type,
95  rtti_policy_type > > >,
96  mpl::identity< typename rtti_policy_type::
97  template rtti_derived_type< MostDerived, node_state<
98  inner_initial_list_size,
99  allocator_type,
100  rtti_policy_type > > > >::type type;
101 };
102 
103 
106 {
107  template< class CommonContext >
108  void operator()( CommonContext & ) const {}
109 };
110 
111 template< class TransitionContext, class Event >
113 {
114  public:
116  void ( TransitionContext::*pTransitionAction )( const Event & ),
117  const Event & evt
118  ) :
119  pTransitionAction_( pTransitionAction ),
120  evt_( evt )
121  {
122  }
123 
124  template< class CommonContext >
125  void operator()( CommonContext & commonContext ) const
126  {
127  ( commonContext.template context< TransitionContext >()
128  .*pTransitionAction_ )( evt_ );
129  }
130 
131  private:
132  // avoids C4512 (assignment operator could not be generated)
133  transition_function & operator=( const transition_function & );
134 
135  void ( TransitionContext::*pTransitionAction_ )( const Event & );
136  const Event & evt_;
137 };
138 
139 
140 template< bool contextHasInheritedDeepHistory, bool contextHasDeepHistory >
142 {
143  template< class HistorizedState, class LeafState, class Context >
144  static void store_deep_history( Context & ) {}
145 };
146 
147 template<>
148 struct deep_history_storer< true, false >
149 {
150  template< class HistorizedState, class LeafState, class Context >
151  static void store_deep_history( Context & ctx )
152  {
153  ctx.template store_deep_history_impl< LeafState >();
154  }
155 };
156 
157 template<>
158 struct deep_history_storer< true, true >
159 {
160  template< class HistorizedState, class LeafState, class Context >
161  static void store_deep_history( Context & ctx )
162  {
163  ctx.outermost_context_base().template store_deep_history<
164  HistorizedState, LeafState >();
165  ctx.template store_deep_history_impl< LeafState >();
166  }
167 };
168 
169 
170 
171 } // namespace detail
172 
173 
174 
177 {
181  has_full_history // shallow & deep
182 };
183 
184 
185 
187 template< class MostDerived,
188  class Context,
189  class InnerInitial = mpl::list<>,
190  history_mode historyMode = has_no_history >
191 class simple_state : public detail::simple_state_base_type< MostDerived,
192  typename Context::inner_context_type, InnerInitial >::type
193 {
194  typedef typename detail::simple_state_base_type<
195  MostDerived, typename Context::inner_context_type,
196  InnerInitial >::type base_type;
197 
198  public:
200  typedef mpl::list<> reactions;
201 
202  typedef typename Context::inner_context_type context_type;
203 
204  template< detail::orthogonal_position_type innerOrthogonalPosition >
205  struct orthogonal
206  {
207  typedef mpl::integral_c<
208  detail::orthogonal_position_type,
209  innerOrthogonalPosition > inner_orthogonal_position;
210  typedef MostDerived inner_context_type;
211  };
212 
213  typedef typename context_type::outermost_context_type
215 
217  {
218  // This assert fails when an attempt is made to access the state machine
219  // from a constructor of a state that is *not* a subtype of state<>.
220  // To correct this, derive from state<> instead of simple_state<>.
221  BOOST_ASSERT( get_pointer( pContext_ ) != 0 );
222  return pContext_->outermost_context();
223  }
224 
226  {
227  // This assert fails when an attempt is made to access the state machine
228  // from a constructor of a state that is *not* a subtype of state<>.
229  // To correct this, derive from state<> instead of simple_state<>.
230  BOOST_ASSERT( get_pointer( pContext_ ) != 0 );
231  return pContext_->outermost_context();
232  }
233 
234  template< class OtherContext >
235  OtherContext & context()
236  {
237  typedef typename mpl::if_<
238  is_base_of< OtherContext, MostDerived >,
241  >::type impl;
242  return impl::template context_impl< OtherContext >( *this );
243  }
244 
245  template< class OtherContext >
246  const OtherContext & context() const
247  {
248  typedef typename mpl::if_<
249  is_base_of< OtherContext, MostDerived >,
252  >::type impl;
253  return impl::template context_impl< OtherContext >( *this );
254  }
255 
256  template< class Target >
257  Target state_cast() const
258  {
259  return outermost_context_base().template state_cast< Target >();
260  }
261 
262  template< class Target >
263  Target state_downcast() const
264  {
265  return outermost_context_base().template state_downcast< Target >();
266  }
267 
268  typedef typename context_type::state_base_type state_base_type;
269  typedef typename context_type::state_iterator state_iterator;
270 
272  {
273  return outermost_context_base().state_begin();
274  }
275 
277  {
278  return outermost_context_base().state_end();
279  }
280 
281 
282  typedef typename context_type::event_base_ptr_type event_base_ptr_type;
283 
284  void post_event( const event_base_ptr_type & pEvent )
285  {
286  outermost_context_base().post_event_impl( pEvent );
287  }
288 
289  void post_event( const event_base & evt )
290  {
291  outermost_context_base().post_event_impl( evt );
292  }
293 
295  {
297  }
298 
300  {
302  }
303 
305  {
306  this->state_base_type::defer_event();
308  }
309 
310  template< class DestinationState >
312  {
313  return transit_impl< DestinationState, outermost_context_type >(
315  }
316 
317  template< class DestinationState, class TransitionContext, class Event >
319  void ( TransitionContext::*pTransitionAction )( const Event & ),
320  const Event & evt )
321  {
322  return transit_impl< DestinationState, TransitionContext >(
324  pTransitionAction, evt ) );
325  }
326 
328  {
329  outermost_context_base().terminate_as_reaction( *this );
331  }
332 
333  template<
334  class HistoryContext,
335  detail::orthogonal_position_type orthogonalPosition >
337  {
339  HistoryContext, orthogonalPosition >();
340  }
341 
342  template<
343  class HistoryContext,
344  detail::orthogonal_position_type orthogonalPosition >
346  {
348  HistoryContext, orthogonalPosition >();
349  }
350 
351  const event_base * triggering_event() const
352  {
353  return outermost_context_base().triggering_event();
354  }
355 
356  protected:
358  simple_state() : pContext_( 0 ) {}
359 
361  {
362  // As a result of a throwing derived class constructor, this destructor
363  // can be called before the context is set.
364  if ( get_pointer( pContext_ ) != 0 )
365  {
366  if ( this->deferred_events() )
367  {
368  outermost_context_base().release_events();
369  }
370 
371  pContext_->remove_inner_state( orthogonal_position::value );
372  }
373  }
374 
375  public:
377  // The following declarations should be private.
378  // They are only public because many compilers lack template friends.
380  typedef typename Context::inner_orthogonal_position orthogonal_position;
381 
382  // If you receive a
383  // "use of undefined type 'boost::STATIC_ASSERTION_FAILURE<x>'" or similar
384  // compiler error here then either this state resides in a non-existent
385  // orthogonal region of the outer state or the outer state does not have
386  // inner states.
387  BOOST_STATIC_ASSERT( ( mpl::less<
389  typename context_type::no_of_orthogonal_regions >::value ) );
390 
391  typedef MostDerived inner_context_type;
392  typedef mpl::integral_c< detail::orthogonal_position_type, 0 >
394 
395  typedef typename context_type::event_base_type event_base_type;
396  typedef typename context_type::rtti_policy_type rtti_policy_type;
397 
398  typedef typename context_type::outermost_context_base_type
400  typedef typename context_type::inner_context_ptr_type context_ptr_type;
401  typedef typename context_type::state_list_type state_list_type;
402  typedef intrusive_ptr< inner_context_type > inner_context_ptr_type;
405  typedef typename mpl::size< inner_initial_list >::type
407  typedef mpl::integral_c<
408  detail::orthogonal_position_type,
409  inner_initial_list_size::value > no_of_orthogonal_regions;
410  typedef typename mpl::push_front<
411  typename context_type::context_type_list,
413 
414  // If you receive a
415  // "use of undefined type 'boost::STATIC_ASSERTION_FAILURE<x>'" or similar
416  // compiler error here then the direct or indirect context of this state
417  // has deep history _and_ this state has two or more orthogonal regions.
418  // Boost.Statechart does not currently support deep history in a state whose
419  // direct or indirect inner states have two or more orthogonal regions.
420  // Please consult the documentation on how to work around this limitation.
421  BOOST_STATIC_ASSERT( ( mpl::or_<
422  mpl::less<
424  mpl::integral_c< detail::orthogonal_position_type, 2 > >,
425  mpl::not_<
426  typename context_type::inherited_deep_history > >::value ) );
427 
428  typedef mpl::bool_< ( historyMode & has_shallow_history ) != 0 >
430  typedef typename context_type::shallow_history stores_shallow_history;
431 
432  typedef mpl::bool_< ( historyMode & has_deep_history ) != 0 >
434  typedef typename mpl::or_<
435  deep_history,
436  typename context_type::inherited_deep_history
438  typedef typename mpl::and_<
440  mpl::empty< inner_initial_list > >::type stores_deep_history;
441 
442  void * operator new( std::size_t size )
443  {
444  return detail::allocate< MostDerived,
445  typename outermost_context_type::allocator_type >( size );
446  }
447 
448  void operator delete( void * pState )
449  {
450  detail::deallocate< MostDerived,
451  typename outermost_context_type::allocator_type >( pState );
452  }
453 
455  {
456  // This assert fails when an attempt is made to access the state machine
457  // from a constructor of a state that is *not* a subtype of state<>.
458  // To correct this, derive from state<> instead of simple_state<>.
459  BOOST_ASSERT( get_pointer( pContext_ ) != 0 );
460  return pContext_->outermost_context_base();
461  }
462 
464  {
465  // This assert fails when an attempt is made to access the state machine
466  // from a constructor of a state that is *not* a subtype of state<>.
467  // To correct this, derive from state<> instead of simple_state<>.
468  BOOST_ASSERT( get_pointer( pContext_ ) != 0 );
469  return pContext_->outermost_context_base();
470  }
471 
472  virtual const state_base_type * outer_state_ptr() const
473  {
474  typedef typename mpl::if_<
475  is_same< outermost_context_type, context_type >,
476  outer_state_ptr_impl_outermost,
478  >::type impl;
479  return impl::outer_state_ptr_impl( *this );
480  }
481 
483  const event_base_type & evt,
484  typename rtti_policy_type::id_type eventType )
485  {
486  typedef typename detail::make_list<
487  typename MostDerived::reactions >::type reaction_list;
488  detail::reaction_result reactionResult =
489  local_react< reaction_list >( evt, eventType );
490 
491  // At this point we can only safely access pContext_ if the handler did
492  // not return do_discard_event!
493  if ( reactionResult == detail::do_forward_event )
494  {
495  // TODO: The following call to react_impl of our outer state should
496  // be made with a context_type:: prefix to call directly instead of
497  // virtually. For some reason the compiler complains...
498  reactionResult = pContext_->react_impl( evt, eventType );
499  }
500 
501  return reactionResult;
502  }
503 
504  virtual void exit_impl(
505  typename base_type::direct_state_base_ptr_type & pSelf,
506  typename state_base_type::node_state_base_ptr_type &
507  pOutermostUnstableState,
508  bool performFullExit )
509  {
510  inner_context_ptr_type pMostDerivedSelf =
511  polymorphic_downcast< MostDerived * >( this );
512  pSelf = 0;
513  exit_impl( pMostDerivedSelf, pOutermostUnstableState, performFullExit );
514  }
515 
516  void exit_impl(
517  inner_context_ptr_type & pSelf,
518  typename state_base_type::node_state_base_ptr_type &
519  pOutermostUnstableState,
520  bool performFullExit )
521  {
522  switch ( this->ref_count() )
523  {
524  case 2:
525  if ( get_pointer( pOutermostUnstableState ) ==
526  static_cast< state_base_type * >( this ) )
527  {
528  pContext_->set_outermost_unstable_state(
529  pOutermostUnstableState );
530  BOOST_FALLTHROUGH;
531  }
532  else
533  {
534  break;
535  }
536  case 1:
537  {
538  if ( get_pointer( pOutermostUnstableState ) == 0 )
539  {
540  pContext_->set_outermost_unstable_state(
541  pOutermostUnstableState );
542  }
543 
544  if ( performFullExit )
545  {
546  pSelf->exit();
547  check_store_shallow_history< stores_shallow_history >();
548  check_store_deep_history< stores_deep_history >();
549  }
550 
551  context_ptr_type pContext = pContext_;
552  pSelf = 0;
553  pContext->exit_impl(
554  pContext, pOutermostUnstableState, performFullExit );
555  break;
556  }
557  default:
558  break;
559  }
560  }
561 
563  typename state_base_type::node_state_base_ptr_type &
564  pOutermostUnstableState )
565  {
566  pOutermostUnstableState = this;
567  }
568 
569  template< class OtherContext >
570  const typename OtherContext::inner_context_ptr_type & context_ptr() const
571  {
572  typedef typename mpl::if_<
573  is_same< OtherContext, context_type >,
576  >::type impl;
577 
578  return impl::template context_ptr_impl< OtherContext >( *this );
579  }
580 
582  outermost_context_base_type & outermostContextBase )
583  {
584  deep_construct( &outermostContextBase, outermostContextBase );
585  }
586 
587  static void deep_construct(
588  const context_ptr_type & pContext,
589  outermost_context_base_type & outermostContextBase )
590  {
591  const inner_context_ptr_type pInnerContext(
592  shallow_construct( pContext, outermostContextBase ) );
593  deep_construct_inner< inner_initial_list >(
594  pInnerContext, outermostContextBase );
595  }
596 
598  const context_ptr_type & pContext,
599  outermost_context_base_type & outermostContextBase )
600  {
601  const inner_context_ptr_type pInnerContext( new MostDerived );
602  pInnerContext->set_context( pContext );
603  outermostContextBase.add( pInnerContext );
604  return pInnerContext;
605  }
606 
607  void set_context( const context_ptr_type & pContext )
608  {
609  BOOST_ASSERT( get_pointer( pContext ) != 0 );
610  pContext_ = pContext;
611  base_type::set_context(
612  orthogonal_position::value, get_pointer( pContext ) );
613  }
614 
615  template< class InnerList >
616  static void deep_construct_inner(
617  const inner_context_ptr_type & pInnerContext,
618  outermost_context_base_type & outermostContextBase )
619  {
620  typedef typename mpl::if_<
621  mpl::empty< InnerList >,
622  deep_construct_inner_impl_empty,
623  deep_construct_inner_impl_non_empty
624  >::type impl;
625  impl::template deep_construct_inner_impl< InnerList >(
626  pInnerContext, outermostContextBase );
627  }
628 
629  template< class LeafState >
631  {
633  context_type::inherited_deep_history::value,
634  context_type::deep_history::value
635  >::template store_deep_history< MostDerived, LeafState >(
636  *pContext_ );
637  }
638 
639  private:
642  {
643  template< class OtherContext, class State >
644  static const typename OtherContext::inner_context_ptr_type &
645  context_ptr_impl( const State & stt )
646  {
647  // This assert fails when an attempt is made to access an outer
648  // context from a constructor of a state that is *not* a subtype of
649  // state<>. To correct this, derive from state<> instead of
650  // simple_state<>.
651  BOOST_ASSERT( get_pointer( stt.pContext_ ) != 0 );
652  return stt.pContext_->template context_ptr< OtherContext >();
653  }
654  };
656 
658  {
659  template< class OtherContext, class State >
660  static const typename OtherContext::inner_context_ptr_type &
661  context_ptr_impl( const State & stt )
662  {
663  // This assert fails when an attempt is made to access an outer
664  // context from a constructor of a state that is *not* a subtype of
665  // state<>. To correct this, derive from state<> instead of
666  // simple_state<>.
667  BOOST_ASSERT( get_pointer( stt.pContext_ ) != 0 );
668  return stt.pContext_;
669  }
670  };
672 
674  {
675  template< class OtherContext, class State >
676  static OtherContext & context_impl( State & stt )
677  {
678  // This assert fails when an attempt is made to access an outer
679  // context from a constructor of a state that is *not* a subtype of
680  // state<>. To correct this, derive from state<> instead of
681  // simple_state<>.
682  BOOST_ASSERT( get_pointer( stt.pContext_ ) != 0 );
683  return stt.pContext_->template context< OtherContext >();
684  }
685  };
687 
689  {
690  template< class OtherContext, class State >
691  static OtherContext & context_impl( State & stt )
692  {
693  return *polymorphic_downcast< MostDerived * >( &stt );
694  }
695  };
697 
698  template< class DestinationState,
699  class TransitionContext,
700  class TransitionAction >
701  result transit_impl( const TransitionAction & transitionAction )
702  {
703  typedef typename mpl::find_if<
705  mpl::contains<
706  typename DestinationState::context_type_list,
707  mpl::placeholders::_ > >::type common_context_iter;
708  typedef typename mpl::deref< common_context_iter >::type
709  common_context_type;
710  typedef typename mpl::distance<
711  typename mpl::begin< context_type_list >::type,
712  common_context_iter >::type termination_state_position;
713  typedef typename mpl::push_front< context_type_list, MostDerived >::type
714  possible_transition_contexts;
715  typedef typename mpl::at<
716  possible_transition_contexts,
717  termination_state_position >::type termination_state_type;
718 
719  termination_state_type & terminationState(
720  context< termination_state_type >() );
721  const typename
722  common_context_type::inner_context_ptr_type pCommonContext(
723  terminationState.template context_ptr< common_context_type >() );
724  outermost_context_base_type & outermostContextBase(
725  pCommonContext->outermost_context_base() );
726 
727  #ifdef BOOST_STATECHART_RELAX_TRANSITION_CONTEXT
728  typedef typename mpl::distance<
729  typename mpl::begin< possible_transition_contexts >::type,
730  typename mpl::find<
731  possible_transition_contexts, TransitionContext >::type
732  >::type proposed_transition_context_position;
733 
734  typedef typename mpl::plus<
735  termination_state_position,
736  mpl::long_< 1 >
737  >::type uml_transition_context_position;
738 
739  typedef typename mpl::deref< typename mpl::max_element<
740  mpl::list<
741  proposed_transition_context_position,
742  uml_transition_context_position >,
743  mpl::greater< mpl::placeholders::_, mpl::placeholders::_ >
744  >::type >::type real_transition_context_position;
745 
746  typedef typename mpl::at<
747  possible_transition_contexts,
748  real_transition_context_position >::type real_transition_context_type;
749 
750  #ifdef BOOST_MSVC
751  # pragma warning( push )
752  # pragma warning( disable: 4127 ) // conditional expression is constant
753  #endif
754  if ( ( proposed_transition_context_position::value == 0 ) &&
755  ( inner_initial_list_size::value == 0 ) )
756  {
757  transitionAction( *polymorphic_downcast< MostDerived * >( this ) );
758  outermostContextBase.terminate_as_part_of_transit( terminationState );
759  }
760  else if ( proposed_transition_context_position::value >=
761  uml_transition_context_position::value )
762  {
763  real_transition_context_type & transitionContext =
764  context< real_transition_context_type >();
765  outermostContextBase.terminate_as_part_of_transit( terminationState );
766  transitionAction( transitionContext );
767  }
768  else
769  {
770  typename real_transition_context_type::inner_context_ptr_type
771  pTransitionContext = context_ptr< real_transition_context_type >();
772  outermostContextBase.terminate_as_part_of_transit(
773  *pTransitionContext );
774  transitionAction( *pTransitionContext );
775  pTransitionContext = 0;
776  outermostContextBase.terminate_as_part_of_transit( terminationState );
777  }
778  #ifdef BOOST_MSVC
779  # pragma warning( pop )
780  #endif
781  #else
782  outermostContextBase.terminate_as_part_of_transit( terminationState );
783  transitionAction( *pCommonContext );
784  #endif
785 
786  typedef typename detail::make_context_list<
787  common_context_type, DestinationState >::type context_list_type;
788 
789  // If you receive a
790  // "use of undefined type 'boost::STATIC_ASSERTION_FAILURE<x>'" or
791  // similar compiler error here then you tried to make an invalid
792  // transition between different orthogonal regions.
793  BOOST_STATIC_ASSERT( ( mpl::equal_to<
794  typename termination_state_type::orthogonal_position,
795  typename mpl::front< context_list_type >::type::orthogonal_position
796  >::value ) );
797 
798  detail::constructor<
799  context_list_type, outermost_context_base_type >::construct(
800  pCommonContext, outermostContextBase );
801 
803  }
804 
806  {
807  template< class ReactionList, class State >
808  static detail::reaction_result local_react_impl(
809  State & stt,
810  const event_base_type & evt,
811  typename rtti_policy_type::id_type eventType )
812  {
813  detail::reaction_result reactionResult =
814  mpl::front< ReactionList >::type::react(
815  *polymorphic_downcast< MostDerived * >( &stt ),
816  evt, eventType );
817 
818  if ( reactionResult == detail::no_reaction )
819  {
820  reactionResult = stt.template local_react<
821  typename mpl::pop_front< ReactionList >::type >(
822  evt, eventType );
823  }
824 
825  return reactionResult;
826  }
827  };
829 
830  struct local_react_impl_empty
831  {
832  template< class ReactionList, class State >
833  static detail::reaction_result local_react_impl(
834  State &, const event_base_type &, typename rtti_policy_type::id_type )
835  {
837  }
838  };
839 
840  template< class ReactionList >
841  detail::reaction_result local_react(
842  const event_base_type & evt,
843  typename rtti_policy_type::id_type eventType )
844  {
845  typedef typename mpl::if_<
846  mpl::empty< ReactionList >,
847  local_react_impl_empty,
849  >::type impl;
850  return impl::template local_react_impl< ReactionList >(
851  *this, evt, eventType );
852  }
853 
855  {
856  template< class State >
857  static const state_base_type * outer_state_ptr_impl( const State & stt )
858  {
859  return get_pointer( stt.pContext_ );
860  }
861  };
863 
864  struct outer_state_ptr_impl_outermost
865  {
866  template< class State >
867  static const state_base_type * outer_state_ptr_impl( const State & )
868  {
869  return 0;
870  }
871  };
872 
873  struct deep_construct_inner_impl_non_empty
874  {
875  template< class InnerList >
876  static void deep_construct_inner_impl(
877  const inner_context_ptr_type & pInnerContext,
878  outermost_context_base_type & outermostContextBase )
879  {
880  typedef typename mpl::front< InnerList >::type current_inner;
881 
882  // If you receive a
883  // "use of undefined type 'boost::STATIC_ASSERTION_FAILURE<x>'" or
884  // similar compiler error here then there is a mismatch between the
885  // orthogonal position of a state and its position in the inner
886  // initial list of its outer state.
887  BOOST_STATIC_ASSERT( ( is_same<
888  current_inner,
889  typename mpl::at<
890  typename current_inner::context_type::inner_initial_list,
891  typename current_inner::orthogonal_position >::type >::value ) );
892 
893  current_inner::deep_construct( pInnerContext, outermostContextBase );
894  deep_construct_inner< typename mpl::pop_front< InnerList >::type >(
895  pInnerContext, outermostContextBase );
896  }
897  };
898 
899  struct deep_construct_inner_impl_empty
900  {
901  template< class InnerList >
902  static void deep_construct_inner_impl(
904  };
905 
906  struct check_store_shallow_history_impl_no
907  {
908  template< class State >
909  static void check_store_shallow_history_impl( State & ) {}
910  };
911 
913  {
914  template< class State >
915  static void check_store_shallow_history_impl( State & stt )
916  {
917  stt.outermost_context_base().template store_shallow_history<
918  MostDerived >();
919  }
920  };
922 
923  template< class StoreShallowHistory >
924  void check_store_shallow_history()
925  {
926  typedef typename mpl::if_<
927  StoreShallowHistory,
929  check_store_shallow_history_impl_no
930  >::type impl;
931  impl::check_store_shallow_history_impl( *this );
932  }
933 
934  struct check_store_deep_history_impl_no
935  {
936  template< class State >
937  static void check_store_deep_history_impl( State & ) {}
938  };
939 
941  {
942  template< class State >
943  static void check_store_deep_history_impl( State & stt )
944  {
945  stt.template store_deep_history_impl< MostDerived >();
946  }
947  };
949 
950  template< class StoreDeepHistory >
951  void check_store_deep_history()
952  {
953  typedef typename mpl::if_<
954  StoreDeepHistory,
956  check_store_deep_history_impl_no
957  >::type impl;
958  impl::check_store_deep_history_impl( *this );
959  }
960 
961 
962  context_ptr_type pContext_;
963 };
964 
965 
966 
967 #ifdef BOOST_NO_ARGUMENT_DEPENDENT_LOOKUP
968 } // namespace statechart
969 #endif
970 
971 
972 
973 template< class MostDerived, class Context,
974  class InnerInitial, history_mode historyMode >
975 inline void intrusive_ptr_release( const ::boost::statechart::simple_state<
976  MostDerived, Context, InnerInitial, historyMode > * pBase )
977 {
978  if ( pBase->release() )
979  {
980  // The cast is necessary because the simple_state destructor is non-
981  // virtual (and inaccessible from this context)
982  delete polymorphic_downcast< const MostDerived * >( pBase );
983  }
984 }
985 
986 
987 
988 #ifndef BOOST_NO_ARGUMENT_DEPENDENT_LOOKUP
989 } // namespace statechart
990 #endif
991 
992 
993 
994 } // namespace boost
995 
996 
997 
998 #endif
boost::statechart::has_no_history
@ has_no_history
Definition: simple_state.hpp:178
boost::statechart::simple_state::inner_orthogonal_position
mpl::integral_c< detail::orthogonal_position_type, 0 > inner_orthogonal_position
Definition: simple_state.hpp:393
boost::statechart::simple_state::outer_state_ptr
virtual const state_base_type * outer_state_ptr() const
Definition: simple_state.hpp:472
boost::statechart::simple_state::BOOST_STATIC_ASSERT
BOOST_STATIC_ASSERT((mpl::or_< mpl::less< no_of_orthogonal_regions, mpl::integral_c< detail::orthogonal_position_type, 2 > >, mpl::not_< typename context_type::inherited_deep_history > >::value))
boost::statechart::simple_state::context_type_list
mpl::push_front< typename context_type::context_type_list, context_type >::type context_type_list
Definition: simple_state.hpp:412
boost::statechart::simple_state::post_event
void post_event(const event_base_ptr_type &pEvent)
Definition: simple_state.hpp:284
boost::statechart::simple_state::shallow_construct
static inner_context_ptr_type shallow_construct(const context_ptr_type &pContext, outermost_context_base_type &outermostContextBase)
Definition: simple_state.hpp:597
boost::statechart::simple_state::context_type
Context::inner_context_type context_type
Definition: simple_state.hpp:202
boost::statechart::has_shallow_history
@ has_shallow_history
Definition: simple_state.hpp:179
boost::statechart::simple_state::stores_deep_history
mpl::and_< inherited_deep_history, mpl::empty< inner_initial_list > >::type stores_deep_history
Definition: simple_state.hpp:440
boost::statechart::simple_state::stores_shallow_history
context_type::shallow_history stores_shallow_history
Definition: simple_state.hpp:430
boost::statechart::detail::do_defer_event
@ do_defer_event
Definition: result.hpp:30
boost::statechart::simple_state::event_base_type
context_type::event_base_type event_base_type
Definition: simple_state.hpp:395
boost::statechart::simple_state::orthogonal::inner_context_type
MostDerived inner_context_type
Definition: simple_state.hpp:210
boost::statechart::detail::make_list
Definition: simple_state.hpp:73
boost::statechart::simple_state::store_deep_history_impl
void store_deep_history_impl()
Definition: simple_state.hpp:630
boost::statechart::simple_state::outermost_context_base_type
context_type::outermost_context_base_type outermost_context_base_type
Definition: simple_state.hpp:399
boost::statechart::simple_state::triggering_event
const event_base * triggering_event() const
Definition: simple_state.hpp:351
boost::statechart::detail::simple_state_base_type
Definition: simple_state.hpp:78
boost::statechart::simple_state::context_ptr
const OtherContext::inner_context_ptr_type & context_ptr() const
Definition: simple_state.hpp:570
boost::statechart::detail::safe_reaction_result
Definition: result.hpp:38
boost::statechart::simple_state::outermost_context
const outermost_context_type & outermost_context() const
Definition: simple_state.hpp:225
boost::statechart::simple_state::outermost_context_base
const outermost_context_base_type & outermost_context_base() const
Definition: simple_state.hpp:463
event.hpp
boost::statechart::simple_state::outermost_context_type
context_type::outermost_context_type outermost_context_type
Definition: simple_state.hpp:214
boost::statechart::detail::transition_function
Definition: simple_state.hpp:113
boost::statechart::simple_state::transit
result transit()
Definition: simple_state.hpp:311
boost
Definition: asynchronous_state_machine.hpp:20
boost::statechart::simple_state::exit_impl
void exit_impl(inner_context_ptr_type &pSelf, typename state_base_type::node_state_base_ptr_type &pOutermostUnstableState, bool performFullExit)
Definition: simple_state.hpp:516
boost::statechart::simple_state::context_ptr_type
context_type::inner_context_ptr_type context_ptr_type
Definition: simple_state.hpp:400
boost::statechart::simple_state::discard_event
result discard_event()
Definition: simple_state.hpp:294
boost::statechart::simple_state< MostDerived, Context, mpl::list<>, has_no_history >::deep_history
mpl::bool_<(historyMode &has_deep_history) !=0 > deep_history
Definition: simple_state.hpp:433
boost::statechart::simple_state::context
OtherContext & context()
Definition: simple_state.hpp:235
boost::statechart::detail::deep_history_storer
Definition: simple_state.hpp:142
boost::statechart::simple_state::context_ptr_impl_other_context
friend struct context_ptr_impl_other_context
Definition: simple_state.hpp:655
boost::statechart::detail::transition_function::transition_function
transition_function(void(TransitionContext::*pTransitionAction)(const Event &), const Event &evt)
Definition: simple_state.hpp:115
boost::statechart::simple_state::simple_state
simple_state()
Definition: simple_state.hpp:358
boost::statechart::detail::reaction_result
reaction_result
Definition: result.hpp:26
boost::statechart::simple_state::set_outermost_unstable_state
void set_outermost_unstable_state(typename state_base_type::node_state_base_ptr_type &pOutermostUnstableState)
Definition: simple_state.hpp:562
boost::statechart::simple_state::inner_context_type
MostDerived inner_context_type
Definition: simple_state.hpp:391
boost::statechart::simple_state::inherited_deep_history
mpl::or_< deep_history, typename context_type::inherited_deep_history >::type inherited_deep_history
Definition: simple_state.hpp:437
boost::statechart::detail::deep_history_storer::store_deep_history
static void store_deep_history(Context &)
Definition: simple_state.hpp:144
boost::statechart::simple_state::context
const OtherContext & context() const
Definition: simple_state.hpp:246
boost::statechart::simple_state::transit
result transit(void(TransitionContext::*pTransitionAction)(const Event &), const Event &evt)
Definition: simple_state.hpp:318
boost::statechart::detail::transition_function::operator()
void operator()(CommonContext &commonContext) const
Definition: simple_state.hpp:125
boost::statechart::simple_state< MostDerived, Context, mpl::list<>, has_no_history >::shallow_history
mpl::bool_<(historyMode &has_shallow_history) !=0 > shallow_history
Definition: simple_state.hpp:429
boost::statechart::simple_state
Definition: simple_state.hpp:193
boost::statechart::simple_state::post_event
void post_event(const event_base &evt)
Definition: simple_state.hpp:289
boost::statechart::simple_state::check_store_shallow_history_impl_yes
friend struct check_store_shallow_history_impl_yes
Definition: simple_state.hpp:921
boost::statechart::detail::result_utility::make_result
::boost::statechart::result make_result(reaction_result value)
Definition: result.hpp:103
boost::statechart::simple_state::inner_initial_list
detail::make_list< InnerInitial >::type inner_initial_list
Definition: simple_state.hpp:404
boost::statechart::simple_state::set_context
void set_context(const context_ptr_type &pContext)
Definition: simple_state.hpp:607
boost::statechart::simple_state::BOOST_STATIC_ASSERT
BOOST_STATIC_ASSERT((mpl::less< orthogonal_position, typename context_type::no_of_orthogonal_regions >::value))
boost::statechart::simple_state::clear_deep_history
void clear_deep_history()
Definition: simple_state.hpp:345
boost::statechart::simple_state::~simple_state
~simple_state()
Definition: simple_state.hpp:360
boost::statechart::simple_state::exit_impl
virtual void exit_impl(typename base_type::direct_state_base_ptr_type &pSelf, typename state_base_type::node_state_base_ptr_type &pOutermostUnstableState, bool performFullExit)
Definition: simple_state.hpp:504
boost::statechart::simple_state::inner_context_ptr_type
intrusive_ptr< inner_context_type > inner_context_ptr_type
Definition: simple_state.hpp:402
boost::statechart::simple_state::context_ptr_impl_my_context
friend struct context_ptr_impl_my_context
Definition: simple_state.hpp:671
boost::statechart::simple_state::inner_initial_list_size
mpl::size< inner_initial_list >::type inner_initial_list_size
Definition: simple_state.hpp:406
boost::statechart::intrusive_ptr_release
void intrusive_ptr_release(const ::boost::statechart::simple_state< MostDerived, Context, InnerInitial, historyMode > *pBase)
Definition: simple_state.hpp:975
boost::statechart::simple_state::check_store_deep_history_impl_yes
friend struct check_store_deep_history_impl_yes
Definition: simple_state.hpp:948
boost::statechart::simple_state::clear_shallow_history
void clear_shallow_history()
Definition: simple_state.hpp:336
boost::statechart::simple_state::terminate
result terminate()
Definition: simple_state.hpp:327
boost::statechart::simple_state::orthogonal_position
Context::inner_orthogonal_position orthogonal_position
Definition: simple_state.hpp:380
boost::statechart::simple_state::context_impl_other_context
friend struct context_impl_other_context
Definition: simple_state.hpp:686
boost::statechart::simple_state::local_react_impl_non_empty
friend struct local_react_impl_non_empty
Definition: simple_state.hpp:828
boost::statechart::simple_state::no_of_orthogonal_regions
mpl::integral_c< detail::orthogonal_position_type, inner_initial_list_size::value > no_of_orthogonal_regions
Definition: simple_state.hpp:409
boost::statechart::simple_state::react_impl
virtual detail::reaction_result react_impl(const event_base_type &evt, typename rtti_policy_type::id_type eventType)
Definition: simple_state.hpp:482
boost::statechart::history_mode
history_mode
Definition: simple_state.hpp:177
boost::statechart::detail::no_reaction
@ no_reaction
Definition: result.hpp:27
boost::statechart::simple_state::event_base_ptr_type
context_type::event_base_ptr_type event_base_ptr_type
Definition: simple_state.hpp:282
boost::statechart::simple_state::state_iterator
context_type::state_iterator state_iterator
Definition: simple_state.hpp:269
boost::statechart::simple_state::orthogonal::inner_orthogonal_position
mpl::integral_c< detail::orthogonal_position_type, innerOrthogonalPosition > inner_orthogonal_position
Definition: simple_state.hpp:209
boost::statechart::simple_state::deep_construct
static void deep_construct(const context_ptr_type &pContext, outermost_context_base_type &outermostContextBase)
Definition: simple_state.hpp:587
boost::statechart::detail::deep_history_storer< true, false >::store_deep_history
static void store_deep_history(Context &ctx)
Definition: simple_state.hpp:151
boost::statechart::simple_state::state_cast
Target state_cast() const
Definition: simple_state.hpp:257
boost::statechart::simple_state::outermost_context_base
outermost_context_base_type & outermost_context_base()
Definition: simple_state.hpp:454
boost::statechart::simple_state::state_begin
state_iterator state_begin() const
Definition: simple_state.hpp:271
boost::statechart::detail::no_transition_function::operator()
void operator()(CommonContext &) const
Definition: simple_state.hpp:108
boost::statechart::simple_state::reactions
mpl::list reactions
Definition: simple_state.hpp:200
boost::statechart::simple_state::state_list_type
context_type::state_list_type state_list_type
Definition: simple_state.hpp:401
boost::statechart::event_base
Definition: event_base.hpp:51
boost::statechart::detail::no_transition_function
Definition: simple_state.hpp:106
boost::statechart::detail::do_forward_event
@ do_forward_event
Definition: result.hpp:28
boost::statechart::simple_state::orthogonal
Definition: simple_state.hpp:206
boost::statechart::simple_state::outer_state_ptr_impl_non_outermost
friend struct outer_state_ptr_impl_non_outermost
Definition: simple_state.hpp:862
boost::statechart::simple_state::state_end
state_iterator state_end() const
Definition: simple_state.hpp:276
boost::statechart::detail::deep_history_storer< true, true >::store_deep_history
static void store_deep_history(Context &ctx)
Definition: simple_state.hpp:161
boost::statechart::simple_state::context_impl_this_context
friend struct context_impl_this_context
Definition: simple_state.hpp:696
boost::statechart::has_full_history
@ has_full_history
Definition: simple_state.hpp:181
boost::statechart::has_deep_history
@ has_deep_history
Definition: simple_state.hpp:180
boost::statechart::simple_state::deep_construct_inner
static void deep_construct_inner(const inner_context_ptr_type &pInnerContext, outermost_context_base_type &outermostContextBase)
Definition: simple_state.hpp:616
boost::statechart::simple_state::state_downcast
Target state_downcast() const
Definition: simple_state.hpp:263
boost::statechart::simple_state::initial_deep_construct
static void initial_deep_construct(outermost_context_base_type &outermostContextBase)
Definition: simple_state.hpp:581
boost::statechart::simple_state::forward_event
result forward_event()
Definition: simple_state.hpp:299
boost::statechart::simple_state::state_base_type
context_type::state_base_type state_base_type
Definition: simple_state.hpp:268
boost::statechart::simple_state::defer_event
result defer_event()
Definition: simple_state.hpp:304
boost::statechart::detail::simple_state_base_type::type
mpl::eval_if< mpl::empty< inner_initial_list >, mpl::identity< typename rtti_policy_type::template rtti_derived_type< MostDerived, leaf_state< allocator_type, rtti_policy_type > > >, mpl::identity< typename rtti_policy_type::template rtti_derived_type< MostDerived, node_state< inner_initial_list_size, allocator_type, rtti_policy_type > > > >::type type
Definition: simple_state.hpp:100
boost::statechart::simple_state::outermost_context
outermost_context_type & outermost_context()
Definition: simple_state.hpp:216
boost::statechart::simple_state::rtti_policy_type
context_type::rtti_policy_type rtti_policy_type
Definition: simple_state.hpp:396
boost::statechart::detail::do_discard_event
@ do_discard_event
Definition: result.hpp:29