Panda3D
 All Classes Functions Variables Enumerations
referenceCount.h
1 // Filename: referenceCount.h
2 // Created by: drose (23Oct98)
3 //
4 ////////////////////////////////////////////////////////////////////
5 //
6 // PANDA 3D SOFTWARE
7 // Copyright (c) Carnegie Mellon University. All rights reserved.
8 //
9 // All use of this software is subject to the terms of the revised BSD
10 // license. You should have received a copy of this license along
11 // with this source code in a file named "LICENSE."
12 //
13 ////////////////////////////////////////////////////////////////////
14 
15 #ifndef REFERENCECOUNT_H
16 #define REFERENCECOUNT_H
17 
18 #include "pandabase.h"
19 #include "weakReferenceList.h"
20 #include "typedObject.h"
21 #include "memoryUsage.h"
22 #include "memoryBase.h"
23 #include "config_express.h"
24 #include "atomicAdjust.h"
25 #include "numeric_types.h"
26 #include "deletedChain.h"
27 
28 #include <stdlib.h>
29 
30 #ifdef HAVE_RTTI
31 #include <typeinfo>
32 #endif
33 
34 ////////////////////////////////////////////////////////////////////
35 // Class : ReferenceCount
36 // Description : A base class for all things that want to be
37 // reference-counted. ReferenceCount works in
38 // conjunction with PointerTo to automatically delete
39 // objects when the last pointer to them goes away.
40 ////////////////////////////////////////////////////////////////////
41 class EXPCL_PANDAEXPRESS ReferenceCount : public MemoryBase {
42 protected:
43  INLINE ReferenceCount();
44  INLINE ReferenceCount(const ReferenceCount &);
45  INLINE void operator = (const ReferenceCount &);
46 
47 public:
48  virtual INLINE ~ReferenceCount();
49 
50 PUBLISHED:
51  INLINE int get_ref_count() const;
52  INLINE void ref() const;
53  virtual INLINE bool unref() const;
54 
55  INLINE bool test_ref_count_integrity() const;
56  INLINE bool test_ref_count_nonzero() const;
57 
58 public:
59  INLINE void local_object();
60  INLINE bool has_weak_list() const;
61  INLINE WeakReferenceList *get_weak_list() const;
62 
63  INLINE void weak_ref(WeakPointerToVoid *ptv);
64  INLINE void weak_unref(WeakPointerToVoid *ptv);
65 
66 protected:
67  bool do_test_ref_count_integrity() const;
68  bool do_test_ref_count_nonzero() const;
69 
70 private:
71  void create_weak_list();
72 
73 private:
74  enum {
75  // We use this value as a flag to indicate an object has been
76  // indicated as a local object, and should not be deleted except
77  // by its own destructor. Really, any nonzero value would do, but
78  // having a large specific number makes the sanity checks easier.
79  local_ref_count = 10000000,
80 
81  // This value is used as a flag to indicate that an object has
82  // just been deleted, and you're looking at deallocated memory.
83  // It's not guaranteed to stick around, of course (since the
84  // deleted memory might be repurposed for anything else, including
85  // a new object), but if you ever do encounter this value in a
86  // reference count field, you screwed up.
87  deleted_ref_count = -100,
88  };
89 
90  mutable AtomicAdjust::Integer _ref_count;
91  AtomicAdjust::Pointer _weak_list; // WeakReferenceList *
92 
93 public:
94  static TypeHandle get_class_type() {
95  return _type_handle;
96  }
97  static void init_type() {
98  register_type(_type_handle, "ReferenceCount");
99  }
100 
101 private:
102  static TypeHandle _type_handle;
103 };
104 
105 template<class RefCountType>
106 INLINE void unref_delete(RefCountType *ptr);
107 
108 ////////////////////////////////////////////////////////////////////
109 // Class : RefCountProxy
110 // Description : A "proxy" to use to make a reference-countable object
111 // whenever the object cannot inherit from
112 // ReferenceCount for some reason. RefCountPr<MyClass>
113 // can be treated as an instance of MyClass directly,
114 // for the most part, except that it can be reference
115 // counted.
116 //
117 // If you want to declare a RefCountProxy to something
118 // that does not have get_class_type(), you will have to
119 // define a template specialization on
120 // _get_type_handle() and _do_init_type(), as in
121 // typedObject.h.
122 ////////////////////////////////////////////////////////////////////
123 template<class Base>
125 public:
126  INLINE RefCountProxy();
127  INLINE RefCountProxy(const Base &copy);
128 
129  INLINE operator Base &();
130  INLINE operator const Base &() const;
131 
132  static TypeHandle get_class_type() {
133  return _type_handle;
134  }
135  static void init_type();
136 
137 private:
138  Base _base;
139  static TypeHandle _type_handle;
140 };
141 
142 
143 ////////////////////////////////////////////////////////////////////
144 // Class : RefCountObj
145 // Description : Another kind of proxy, similar to RefCountProxy.
146 // This one works by inheriting from the indicated base
147 // type, giving it an is-a relation instead of a has-a
148 // relation. As such, it's a little more robust, but
149 // only works when the base type is, in fact, a class.
150 ////////////////////////////////////////////////////////////////////
151 template<class Base>
152 class RefCountObj : public ReferenceCount, public Base {
153 public:
154  INLINE RefCountObj();
155  INLINE RefCountObj(const Base &copy);
156  ALLOC_DELETED_CHAIN(RefCountObj<Base>);
157 
158  static TypeHandle get_class_type() {
159  return _type_handle;
160  }
161  static void init_type();
162 
163 private:
164  static TypeHandle _type_handle;
165 };
166 
167 #include "referenceCount.I"
168 
169 #endif
This is the specialization of PointerToVoid for weak pointers.
This is a list of WeakPointerTo&#39;s that share a reference to a given ReferenceCount object...
This class is intended to be the base class of all objects in Panda that might be allocated and delet...
Definition: memoryBase.h:73
A base class for all things that want to be reference-counted.
Another kind of proxy, similar to RefCountProxy.
TypeHandle is the identifier used to differentiate C++ class types.
Definition: typeHandle.h:85
A &quot;proxy&quot; to use to make a reference-countable object whenever the object cannot inherit from Referen...