libzypp  10.5.0
ReferenceCounted.h
Go to the documentation of this file.
00001 /*---------------------------------------------------------------------\
00002 |                          ____ _   __ __ ___                          |
00003 |                         |__  / \ / / . \ . \                         |
00004 |                           / / \ V /|  _/  _/                         |
00005 |                          / /__ | | | | | |                           |
00006 |                         /_____||_| |_| |_|                           |
00007 |                                                                      |
00008 \---------------------------------------------------------------------*/
00012 #ifndef ZYPP_BASE_REFERENCECOUNTED_H
00013 #define ZYPP_BASE_REFERENCECOUNTED_H
00014 
00015 #include <iosfwd>
00016 
00017 #include "zypp/base/PtrTypes.h"
00018 
00020 namespace zypp
00021 { 
00022 
00023   namespace base
00024   { 
00025 
00027     //
00028     //  CLASS NAME : ReferenceCounted
00029     //
00033     class ReferenceCounted
00034     {
00036       friend std::ostream & operator<<( std::ostream & str, const ReferenceCounted & obj );
00037 
00038     public:
00042       ReferenceCounted();
00043 
00047       ReferenceCounted( const ReferenceCounted & rhs );
00048 
00052       virtual ~ReferenceCounted();
00053 
00057       ReferenceCounted & operator=( const ReferenceCounted & )
00058       { return *this; }
00059 
00060     public:
00062       unsigned refCount() const
00063       { return _counter; }
00064 
00066       void ref() const
00067       { ref_to( ++_counter ); }
00068 
00073       void unref() const
00074       {
00075         if ( !_counter )
00076           unrefException(); // will throw!
00077         if ( --_counter )
00078           unref_to( _counter );
00079         else
00080           delete this;
00081       }
00082 
00086       static void add_ref( const ReferenceCounted * ptr_r )
00087       { if( ptr_r ) ptr_r->ref(); }
00088 
00092       static void release( const ReferenceCounted * ptr_r )
00093       { if( ptr_r ) ptr_r->unref(); }
00094 
00095     protected:
00097       virtual std::ostream & dumpOn( std::ostream & str ) const;
00098 
00100       virtual void ref_to( unsigned /* rep_cnt_r */ ) const {}
00101 
00106       virtual void unref_to( unsigned /* rep_cnt_r */ ) const {}
00107 
00108     private:
00110       mutable unsigned _counter;
00111 
00113       void unrefException() const;
00114     };
00116 
00118     inline void intrusive_ptr_add_ref( const ReferenceCounted * ptr_r )
00119     { ReferenceCounted::add_ref( ptr_r ); }
00120 
00122     inline void intrusive_ptr_release( const ReferenceCounted * ptr_r )
00123     { ReferenceCounted::release( ptr_r ); }
00124 
00126     inline std::ostream & operator<<( std::ostream & str, const ReferenceCounted & obj )
00127     { return obj.dumpOn( str ); }
00128 
00130   } // namespace base
00133 } // namespace zypp
00135 
00136 #define IMPL_PTR_TYPE(NAME) \
00137 void intrusive_ptr_add_ref( const NAME * ptr_r )               \
00138 { zypp::base::ReferenceCounted::add_ref( ptr_r ); }                  \
00139 void intrusive_ptr_release( const NAME * ptr_r )               \
00140 { zypp::base::ReferenceCounted::release( ptr_r ); }
00141 
00143 #endif // ZYPP_BASE_REFERENCECOUNTED_H