00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #ifndef __CS_REF_H__
00021 #define __CS_REF_H__
00022
00023 #define CS_VOIDED_PTR 0xffffffff
00024
00025 template <class T> class csRef;
00026
00027 #if defined(CS_DEBUG)
00028 # define CS_TEST_VOIDPTRUSAGE
00029 #else
00030 # undef CS_TEST_VOIDPTRUSAGE
00031 #endif
00032
00043 template <class T>
00044 class csPtr
00045 {
00046 private:
00047 friend class csRef<T>;
00048 T* obj;
00049
00050 public:
00051 csPtr (T* p) : obj (p) { }
00052
00053 template <class T2>
00054 explicit csPtr (csRef<T2> const& r) : obj((T2*)r) { if (obj) obj->IncRef(); }
00055
00056 #ifdef CS_TEST_VOIDPTRUSAGE
00057 ~csPtr ()
00058 {
00059
00060
00061
00062
00063
00064 CS_ASSERT (obj == (T*)CS_VOIDED_PTR);
00065 }
00066 #endif
00067
00068 csPtr (const csPtr<T>& copy)
00069 {
00070 obj = copy.obj;
00071 #ifdef CS_TEST_VOIDPTRUSAGE
00072 ((csPtr<T>&)copy).obj = (T*)CS_VOIDED_PTR;
00073 #endif
00074 }
00075 };
00076
00083 template <class T>
00084 class csRef
00085 {
00086 private:
00087 T* obj;
00088
00089 public:
00095 csRef () : obj (0) {}
00096
00102 csRef (const csPtr<T>& newobj)
00103 {
00104 obj = newobj.obj;
00105 # ifdef CS_TEST_VOIDPTRUSAGE
00106 CS_ASSERT (newobj.obj != (T*)CS_VOIDED_PTR);
00107 # endif
00108
00109
00110 ((csPtr<T>&)newobj).obj = (T*)CS_VOIDED_PTR;
00111 }
00112
00117 csRef (T* newobj) : obj (newobj)
00118 {
00119 if (obj)
00120 obj->IncRef ();
00121 }
00122
00126 csRef (csRef const& other) : obj (other.obj)
00127 {
00128 if (obj)
00129 obj->IncRef ();
00130 }
00131
00135 ~csRef ()
00136 {
00137 if (obj)
00138 obj->DecRef ();
00139 }
00140
00150 csRef& operator = (const csPtr<T>& newobj)
00151 {
00152 T* oldobj = obj;
00153
00154 obj = newobj.obj;
00155 # ifdef CS_TEST_VOIDPTRUSAGE
00156 CS_ASSERT (newobj.obj != (T*)CS_VOIDED_PTR);
00157 # endif
00158
00159
00160 ((csPtr<T>&)newobj).obj = (T*)CS_VOIDED_PTR;
00161 if (oldobj)
00162 oldobj->DecRef ();
00163 return *this;
00164 }
00165
00178 csRef& operator = (T* newobj)
00179 {
00180 if (obj != newobj)
00181 {
00182 T* oldobj = obj;
00183
00184
00185
00186
00187 obj = newobj;
00188 if (newobj)
00189 newobj->IncRef ();
00190 if (oldobj)
00191 oldobj->DecRef ();
00192 }
00193 return *this;
00194 }
00195
00218 void AttachNew (csPtr<T> newObj)
00219 {
00220
00221
00222
00223
00224 *this = newObj;
00225 }
00226
00230 csRef& operator = (csRef const& other)
00231 {
00232 this->operator=(other.obj);
00233 return *this;
00234 }
00235
00237 inline friend bool operator == (const csRef& r1, const csRef& r2)
00238 {
00239 return r1.obj == r2.obj;
00240 }
00242 inline friend bool operator != (const csRef& r1, const csRef& r2)
00243 {
00244 return r1.obj != r2.obj;
00245 }
00247 inline friend bool operator == (const csRef& r1, T* obj)
00248 {
00249 return r1.obj == obj;
00250 }
00252 inline friend bool operator != (const csRef& r1, T* obj)
00253 {
00254 return r1.obj != obj;
00255 }
00257 inline friend bool operator == (T* obj, const csRef& r1)
00258 {
00259 return r1.obj == obj;
00260 }
00262 inline friend bool operator != (T* obj, const csRef& r1)
00263 {
00264 return r1.obj != obj;
00265 }
00266
00268 T* operator -> () const
00269 { return obj; }
00270
00272 operator T* () const
00273 { return obj; }
00274
00276 T& operator* () const
00277 { return *obj; }
00278
00283 bool IsValid () const
00284 { return (obj != 0); }
00285 };
00286
00287 #endif // __CS_REF_H__