00001 // -*- C++ -*- 00002 00003 /** 00004 * @file Refcountable.h 00005 * 00006 * $Id: Refcountable.h 81419 2008-04-24 11:35:22Z johnnyw $ 00007 * 00008 * @author Pradeep Gore <pradeep@oomworks.com> 00009 */ 00010 00011 #ifndef TAO_Notify_REFCOUNTABLE_H 00012 #define TAO_Notify_REFCOUNTABLE_H 00013 00014 #include /**/ "ace/pre.h" 00015 00016 #include "orbsvcs/Notify/notify_serv_export.h" 00017 #include "orbsvcs/Notify/Refcountable_Guard_T.h" 00018 00019 #if !defined (ACE_LACKS_PRAGMA_ONCE) 00020 # pragma once 00021 #endif /* ACE_LACKS_PRAGMA_ONCE */ 00022 00023 #include "tao/orbconf.h" 00024 #include "tao/Basic_Types.h" 00025 #include "ace/Synch_Traits.h" 00026 #include "ace/Thread_Mutex.h" 00027 #include "ace/Atomic_Op.h" 00028 00029 // Debugging macros 00030 #ifndef TAO_NOTIFY_REFCOUNT_DIAGNOSTICS 00031 #define TAO_NOTIFY_REFCOUNT_DIAGNOSTICS 0 00032 #endif 00033 00034 TAO_BEGIN_VERSIONED_NAMESPACE_DECL 00035 00036 /** 00037 * @class TAO_Notify_Refcountable 00038 * 00039 * @brief Thread-safe refounting, calls the <release> method when refcount falls to 0. 00040 * 00041 * The refcount is initialized to 0. When an instance of a 00042 * derived class becomes owned by a managed pointer 00043 * (Refcountable_Guard_T) the reference count becomes non-zero. 00044 * 00045 * Instances declared on the stack should always have a 00046 * refcount of zero. 00047 * 00048 * A method that creates or simply returns an instance of 00049 * Refcountable should not increment the reference count. It is 00050 * the responsibility of the client to increment the reference 00051 * count (take ownership or guard against deletion). The client 00052 * cannot know if the method will or will not incr the refcount 00053 * on its behalf. 00054 * 00055 * Use Refcountable_Guard_T or similar service to guarantee the 00056 * exception safe direct pairing of increments and decrements. Avoid 00057 * calling _incr_refcnt and _decr_refcnt. 00058 */ 00059 00060 class TAO_Notify_Serv_Export TAO_Notify_Refcountable 00061 { 00062 public: 00063 typedef TAO_Notify_Refcountable_Guard_T< TAO_Notify_Refcountable > Ptr; 00064 00065 /// Constructor 00066 TAO_Notify_Refcountable (void); 00067 00068 /// Destructor 00069 /// public for stack allocated instances 00070 virtual ~TAO_Notify_Refcountable (); 00071 00072 /// This method sigantures deliberately match the RefCounting methods required for ESF Proxy 00073 /// Public for bridge implementations and various guard classes 00074 CORBA::ULong _incr_refcnt (void); 00075 CORBA::ULong _decr_refcnt (void); 00076 00077 #if ( TAO_NOTIFY_REFCOUNT_DIAGNOSTICS != 0 ) 00078 static void diagnostic_dump( const char* title = 0 ); 00079 #endif 00080 00081 private: 00082 /// The release method is called when the refcount reaches 0. 00083 virtual void release (void) = 0; 00084 00085 /// Use a signed counter so that we can more easily detect 00086 /// boundary conditions such as too many _decr_refcnt() calls. 00087 ACE_Atomic_Op<TAO_SYNCH_MUTEX, CORBA::Long> refcount_; 00088 00089 #if ( TAO_NOTIFY_REFCOUNT_DIAGNOSTICS != 0 ) 00090 friend class TAO_Notify_Tracker; 00091 int ref_id_; 00092 #endif 00093 }; 00094 00095 TAO_END_VERSIONED_NAMESPACE_DECL 00096 00097 #include /**/ "ace/post.h" 00098 00099 #endif /* TAO_Notify_REFCOUNTABLE_H */