1 #ifndef BOOST_STATECHART_EVENT_BASE_HPP_INCLUDED 2 #define BOOST_STATECHART_EVENT_BASE_HPP_INCLUDED 3 ////////////////////////////////////////////////////////////////////////////// 4 // Copyright 2002-2006 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) 7 ////////////////////////////////////////////////////////////////////////////// 8 9 10 11 #include <boost/statechart/detail/rtti_policy.hpp> 12 #include <boost/statechart/detail/counted_base.hpp> 13 14 #include <boost/assert.hpp> 15 #include <boost/intrusive_ptr.hpp> 16 #include <boost/config.hpp> 17 18 19 20 namespace boost 21 { 22 namespace statechart 23 { 24 namespace detail 25 { 26 27 28 29 // This helper is necessary because there doesn't seem to be consensus among 30 // compilers on how a friend declaration for a function in another namespace 31 // has to look like. 32 class delete_helper 33 { 34 public: 35 template< class T > delete_object(const T * pObject)36 static void delete_object( const T * pObject ) 37 { 38 delete pObject; 39 } 40 }; 41 42 43 44 } // namespace detail 45 46 47 48 ////////////////////////////////////////////////////////////////////////////// 49 class event_base : public detail::rtti_policy::rtti_base_type< 50 detail::counted_base<> > 51 { 52 typedef detail::rtti_policy::rtti_base_type< 53 detail::counted_base<> > base_type; 54 public: 55 ////////////////////////////////////////////////////////////////////////// 56 intrusive_ptr< const event_base > intrusive_from_this() const; 57 58 protected: 59 ////////////////////////////////////////////////////////////////////////// event_base(detail::rtti_policy::id_provider_type idProvider)60 event_base( detail::rtti_policy::id_provider_type idProvider ) : 61 base_type( idProvider ) 62 { 63 } 64 ~event_base()65 virtual ~event_base() {} 66 67 private: 68 ////////////////////////////////////////////////////////////////////////// 69 virtual intrusive_ptr< const event_base > clone() const = 0; 70 71 friend class detail::delete_helper; 72 }; 73 74 75 76 #ifdef BOOST_NO_ARGUMENT_DEPENDENT_LOOKUP 77 } // namespace statechart 78 #endif 79 80 81 intrusive_ptr_add_ref(const::boost::statechart::event_base * pBase)82inline void intrusive_ptr_add_ref( const ::boost::statechart::event_base * pBase ) 83 { 84 pBase->add_ref(); 85 } 86 intrusive_ptr_release(const::boost::statechart::event_base * pBase)87inline void intrusive_ptr_release( const ::boost::statechart::event_base * pBase ) 88 { 89 if ( pBase->release() ) 90 { 91 ::boost::statechart::detail::delete_helper::delete_object( pBase ); 92 } 93 } 94 95 96 97 #ifndef BOOST_NO_ARGUMENT_DEPENDENT_LOOKUP 98 } // namespace statechart 99 #endif 100 namespace statechart 101 { 102 103 104 105 // We're implementing this here so that GCC3.4.2 can find 106 // intrusive_ptr_add_ref, which is indirectly called from the intrusive_ptr 107 // ctor. intrusive_from_this() const108inline intrusive_ptr< const event_base > event_base::intrusive_from_this() const 109 { 110 if ( base_type::ref_counted() ) 111 { 112 return intrusive_ptr< const event_base >( this ); 113 } 114 else 115 { 116 return clone(); 117 } 118 } 119 120 121 122 } // namespace statechart 123 } // namespace boost 124 125 126 127 #endif 128