refcounted.h

Go to the documentation of this file.
00001 
00004 
00005 //
00006 // Copyright (c) 2000-2004 California Institute of Technology
00007 // Copyright (c) 2004-2007 University of Southern California
00008 // Rob Peters <rjpeters at usc dot edu>
00009 //
00010 // created: Sun Oct 22 14:40:19 2000
00011 // commit: $Id: refcounted.h 10065 2007-04-12 05:54:56Z rjpeters $
00012 // $HeadURL: file:///lab/rjpeters/svnrepo/code/trunk/groovx/src/nub/refcounted.h $
00013 //
00014 // --------------------------------------------------------------------
00015 //
00016 // This file is part of GroovX.
00017 //   [http://ilab.usc.edu/rjpeters/groovx/]
00018 //
00019 // GroovX is free software; you can redistribute it and/or modify it
00020 // under the terms of the GNU General Public License as published by
00021 // the Free Software Foundation; either version 2 of the License, or
00022 // (at your option) any later version.
00023 //
00024 // GroovX is distributed in the hope that it will be useful, but
00025 // WITHOUT ANY WARRANTY; without even the implied warranty of
00026 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00027 // General Public License for more details.
00028 //
00029 // You should have received a copy of the GNU General Public License
00030 // along with GroovX; if not, write to the Free Software Foundation,
00031 // Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
00032 //
00034 
00035 #ifndef GROOVX_NUB_REFCOUNTED_H_UTC20050626084018_DEFINED
00036 #define GROOVX_NUB_REFCOUNTED_H_UTC20050626084018_DEFINED
00037 
00038 #include "rutz/atomic.h"
00039 
00040 #include <cstdlib>
00041 
00042 namespace nub
00043 {
00044   class ref_counts;
00045   class ref_counted;
00046 }
00047 
00048 
00049 // If we want to enforce that destructors of objects derived form
00050 // nub::ref_counted (and nub::object) should have an empty throw-spec
00051 // (i.e. "throw()"), then need "#define GVX_DTOR_NOTHROW throw()",
00052 // otherwise we just define GVX_DTOR_NOTHROW to be empty
00053 #ifndef GVX_DTOR_NOTHROW
00054 #  define GVX_DTOR_NOTHROW
00055 #endif
00056 
00058 
00070 
00071 
00072 struct nub::ref_counts
00073 {
00074 public:
00075   friend class nub::ref_counted;
00076 
00077   void* operator new(size_t bytes);
00078   void operator delete(void* space, size_t bytes);
00079 
00080   ref_counts() throw();
00081 
00082 private:
00084   ~ref_counts() throw();
00085 
00086 public:
00087 
00088   bool is_owner_alive() const throw() { return m_owner_alive; }
00089 
00090   void acquire_weak() throw();
00091   int release_weak() throw();
00092 
00093   void debug_dump() const throw();
00094 
00095 private:
00096   ref_counts(const ref_counts&) throw();
00097   ref_counts& operator=(const ref_counts&) throw();
00098 
00099   void acquire_strong() throw();
00100   int release_strong() throw();
00101   void release_strong_no_delete() throw();
00102 
00103   rutz::atomic_int_t m_strong;
00104   rutz::atomic_int_t m_weak;
00105   bool m_owner_alive;
00106   bool m_volatile;
00107 };
00108 
00109 
00110 
00112 
00127 
00128 
00129 class nub::ref_counted
00130 {
00131 private:
00132   ref_counts* const m_ref_counts;
00133 
00134   // These are disallowed since ref_counted's should always be in
00135   // one-to-one correspondence with their pointee's.
00136   ref_counted(const ref_counted& other);
00137   ref_counted& operator=(const ref_counted& other);
00138 
00139   // If GVX_ENFORCE_FACTORY_FUNCTIONS, then we make operator new() and
00140   // delete() protected, as well as the default constructor and
00141   // destructor. This means that only derived classes can use operator
00142   // new() and delete(), and that thus derived classes are required to
00143   // define functions of the form "static nub::ref<derived_class>
00144   // make() { return nub::ref<derived_class>(new derived_class)."
00145   // While this is a bit of extra typing, it helps ensure that
00146   // ref_counted objects are not constructed on the stack, and are not
00147   // handled by the wrong type of smart pointer (such as a
00148   // shared_ptr).
00149 #ifdef GVX_ENFORCE_FACTORY_FUNCTIONS
00150 protected:
00151 #else
00152 public:
00153 #endif
00154 
00157   void* operator new(size_t bytes);
00158 
00161   void operator delete(void* space, size_t bytes);
00162 
00164   ref_counted();
00165 
00173   virtual ~ref_counted() GVX_DTOR_NOTHROW;
00174 
00176   void mark_as_volatile() throw();
00177 
00178 public:
00180 
00183   void incr_ref_count() const throw();
00184 
00186 
00191   void decr_ref_count() const throw();
00192 
00194 
00199   void decr_ref_count_no_delete() const throw();
00200 
00202 
00205   bool is_shared() const throw();
00206 
00208 
00210   bool is_unshared() const throw();
00211 
00217   bool is_not_shareable() const throw();
00218 
00220   ref_counts* get_counts() const throw();
00221 
00222 
00224   int dbg_ref_count() const throw();
00225 
00227   int dbg_weak_ref_count() const throw();
00228 };
00229 
00230 static const char __attribute__((used)) vcid_groovx_nub_refcounted_h_utc20050626084018[] = "$Id: refcounted.h 10065 2007-04-12 05:54:56Z rjpeters $ $HeadURL: file:
00231 #endif // !GROOVX_NUB_REFCOUNTED_H_UTC20050626084018_DEFINED

The software described here is Copyright (c) 1998-2005, Rob Peters.
This page was generated Wed Dec 3 06:49:40 2008 by Doxygen version 1.5.5.