removed some useless spaces; not very important, I know :)
[senf.git] / Utils / intrusive_refcount.hh
index 0fb690a..8ce5785 100644 (file)
@@ -1,9 +1,9 @@
 // $Id$
 //
 // Copyright (C) 2006
-// Fraunhofer Institut fuer offene Kommunikationssysteme (FOKUS)
-// Kompetenzzentrum fuer Satelitenkommunikation (SatCom)
-//     Stefan Bund <stefan.bund@fokus.fraunhofer.de>
+// Fraunhofer Institute for Open Communication Systems (FOKUS)
+// Competence Center NETwork research (NET), St. Augustin, GERMANY
+//     Stefan Bund <g0dil@berlios.de>
 //
 // This program is free software; you can redistribute it and/or modify
 // it under the terms of the GNU General Public License as published by
 
 namespace senf {
 
-    /** \brief Reference count mixin for intrusive_ptr
+    template <class Self> class intrusive_refcount_t;
 
-        This class provides a simple internally managed refcount and supplies the <a
-        href="http://www.boost.org/libs/smart_ptr/intrusive_ptr.html">boost::intrusive_ptr</a>
-        required interface. To make a class compatible with \c boost::intrusive_ptr, just derive
-        publicly from intrusive_refcount.
+    /** \brief Reference count mixin interface baseclass
 
-        Two additional benefits of using intrusive_refcount are
-        \li The object can access it's own refcount
-        \li It is valid and safe to convert a plain object pointer to an intrusive_ptr at any time
-            (not only after new)
+        This class is the baseclass of all intrusive refcount mixins. See \ref intrusive_refcount_t
+        and \ref intrusive_refcount for more information.
      */
-    class intrusive_refcount
+    class intrusive_refcount_base
         : public boost::noncopyable
     {
     public:
         typedef unsigned refcount_t;    ///< reference count type
 
-        virtual ~intrusive_refcount();
+        virtual ~intrusive_refcount_base();
 
         refcount_t refcount();          ///< current refcount
         bool is_shared();               ///< return \c true if refcount() > 1
 
     protected:
-        intrusive_refcount();
+        intrusive_refcount_base();
 
-    private:
         void add_ref();
         bool release();
 
+    private:
         refcount_t refcount_;
+        
+    };
+
+    /** \brief Customizable reference count mixin for intrusive_ptr
+
+        This class provides a simple internally managed refcount and supplies the <a
+        href="http://www.boost.org/libs/smart_ptr/intrusive_ptr.html">boost::intrusive_ptr</a>
+        required interface. To make a class compatible with \c boost::intrusive_ptr, just derive
+        publicly from intrusive_refcount_t.
+
+        \code
+        class SomeClass 
+            : public intrusive_refcount_t<SomeClass>
+        {
+            // ...
+
+        private:
+            typedef intrusive_refcount_t<SomeClass> intrusive_base;
+
+            void add_ref()
+            {
+                // somehow call intrusive_base::add_ref()
+            }
+
+            bool release()
+            {
+                // Call intrusive_base::release() to decrement the
+                // refcount. This call will return 'true' when the refcount reaches 0.
+        
+                // Return 'true', if the instance shall be deleted
+            }
+
+            // Needed to give intrusive_base access to 'add_ref' and 'release'
+            friend class intrusive_base;
+        };
+        \endcode
+       
+        Two additional benefits of using intrusive_refcount are
+        \li The object can access it's own refcount
+        \li It is valid and safe to convert a plain object pointer to an intrusive_ptr at any time
+            (not only after new)
+
+        This class allows to customize the reference counting strategy (e.g. additional refcounting
+        within another object or checking some additional condition before deleting the object when
+        the refcount reaches 0).
+
+        The interface of this class is defined in \ref intrusive_refcount_base (which you should not
+        use directly).
+     */
+    template <class Self>
+    class intrusive_refcount_t
+        : public intrusive_refcount_base
+    {
+    protected:
+        intrusive_refcount_t();
+
+    private:
+        void intrusive_ptr_add_ref();
+        void intrusive_ptr_release();
+
+        template <class S>
+        friend void senf::intrusive_ptr_add_ref(intrusive_refcount_t<S> * p);
+        template <class S>
+        friend void senf::intrusive_ptr_release(intrusive_refcount_t<S> * p);
+    };
+
+    /** \brief Reference count mixin for intrusive_ptr
+
+        This class provides a simple internally managed refcount and supplies the <a
+        href="http://www.boost.org/libs/smart_ptr/intrusive_ptr.html">boost::intrusive_ptr</a>
+        required interface. To make a class compatible with \c boost::intrusive_ptr, just derive
+        publicly from intrusive_refcount.
 
-        friend void senf::intrusive_ptr_add_ref(intrusive_refcount* p);
-        friend void senf::intrusive_ptr_release(intrusive_refcount* p);
+        \code
+        class SomeClass
+            : public intrusive_refcount
+        {
+            // ...
+        };
+        \endcode
+
+        Two additional benefits of using intrusive_refcount are
+        \li The object can access it's own refcount
+        \li It is valid and safe to convert a plain object pointer to an intrusive_ptr at any time
+            (not only after new)
+
+        This mixin class directly uses the default allocation strategy. If you want to customize the
+        reference couting, use \ref intrusive_refcount_t.
+
+        The interface of this class is defined in \ref intrusive_refcount_t and \ref
+        intrusive_refcount_base (the latter of which you should not use directly).
+     */
+    class intrusive_refcount
+        : public intrusive_refcount_t<intrusive_refcount>
+    {
+    protected:
+        intrusive_refcount();
     };
 
-    void intrusive_ptr_add_ref(intrusive_refcount* p);
-    void intrusive_ptr_release(intrusive_refcount* p);
+    template <class Self>
+    void intrusive_ptr_add_ref(intrusive_refcount_t<Self> * p);
+    template <class Self>
+    void intrusive_ptr_release(intrusive_refcount_t<Self> * p);
+
 }
 
 ///////////////////////////////hh.e////////////////////////////////////////
 #include "intrusive_refcount.cci"
 //#include "intrusive_refcount.ct"
-//#include "intrusive_refcount.cti"
+#include "intrusive_refcount.cti"
 #endif
 
 \f