00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #ifndef XAPIAN_INCLUDED_BASE_H
00026 #define XAPIAN_INCLUDED_BASE_H
00027
00032 namespace Xapian {
00033 namespace Internal {
00034 class RefCntBase {
00035 protected:
00043 RefCntBase(const RefCntBase &) : ref_count(0) { }
00044
00045 public:
00047 RefCntBase() : ref_count(0) { }
00048
00049 typedef unsigned int ref_count_t;
00050
00052 mutable ref_count_t ref_count;
00053 };
00054
00059 template <class T>
00060 class RefCntPtr {
00061 private:
00062 T *dest;
00063
00064 public:
00065 T *operator->() const;
00066 T &operator*() const;
00067 T *get() const;
00076 RefCntPtr(T *dest_);
00077 RefCntPtr();
00078 RefCntPtr(const RefCntPtr &other);
00079 void operator=(const RefCntPtr &other);
00080 ~RefCntPtr();
00081
00082 template <class U>
00083 RefCntPtr(const RefCntPtr<U> &other);
00084 };
00085
00086 template <class T>
00087 inline RefCntPtr<T>::RefCntPtr(T *dest_) : dest(dest_)
00088 {
00089 if (dest) ++dest->ref_count;
00090 }
00091
00092 template <class T>
00093 inline RefCntPtr<T>::RefCntPtr() : dest(0)
00094 {
00095 }
00096
00097 template <class T>
00098 inline RefCntPtr<T>::RefCntPtr(const RefCntPtr &other) : dest(other.dest)
00099 {
00100 if (dest) ++dest->ref_count;
00101 }
00102
00103 template <class T>
00104 inline void RefCntPtr<T>::operator=(const RefCntPtr &other) {
00105
00106 if (dest == other.dest) return;
00107
00108
00109
00110
00111 T *old_dest = dest;
00112 dest = other.dest;
00113 if (dest) ++dest->ref_count;
00114 if (old_dest && --old_dest->ref_count == 0) delete old_dest;
00115 }
00116
00117 template <class T>
00118 inline RefCntPtr<T>::~RefCntPtr()
00119 {
00120 if (dest && --dest->ref_count == 0) {
00121
00122
00123
00124 T * condemned = dest;
00125 dest = 0;
00126 delete condemned;
00127 }
00128 }
00129
00130 template <class T>
00131 template <class U>
00132 inline
00133 RefCntPtr<T>::RefCntPtr(const RefCntPtr<U> &other)
00134 : dest(other.get())
00135 {
00136 if (dest) ++dest->ref_count;
00137 }
00138
00139 template <class T>
00140 inline T *RefCntPtr<T>::operator->() const
00141 {
00142 return dest;
00143 }
00144
00145 template <class T>
00146 inline T &RefCntPtr<T>::operator*() const
00147 {
00148 return *dest;
00149 }
00150
00151 template <class T>
00152 inline T *RefCntPtr<T>::get() const
00153 {
00154 return dest;
00155 }
00156
00157 }
00158 }
00159
00160 #endif