Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | File List | Namespace Members | Class Members | File Members

smartptr.h

00001 #ifndef CRYPTOPP_SMARTPTR_H 00002 #define CRYPTOPP_SMARTPTR_H 00003 00004 #include "cryptopp_config.h" 00005 #include <algorithm> 00006 00007 NAMESPACE_BEGIN(CryptoPP) 00008 00009 template<class T> class member_ptr 00010 { 00011 public: 00012 explicit member_ptr(T *p = NULL) : m_p(p) {} 00013 00014 ~member_ptr(); 00015 00016 const T& operator*() const { return *m_p; } 00017 T& operator*() { return *m_p; } 00018 00019 const T* operator->() const { return m_p; } 00020 T* operator->() { return m_p; } 00021 00022 const T* get() const { return m_p; } 00023 T* get() { return m_p; } 00024 00025 T* release() 00026 { 00027 T *old_p = m_p; 00028 m_p = 0; 00029 return old_p; 00030 } 00031 00032 void reset(T *p = 0); 00033 00034 protected: 00035 member_ptr(const member_ptr<T>& rhs); // copy not allowed 00036 void operator=(const member_ptr<T>& rhs); // assignment not allowed 00037 00038 T *m_p; 00039 }; 00040 00041 template <class T> member_ptr<T>::~member_ptr() {delete m_p;} 00042 template <class T> void member_ptr<T>::reset(T *p) {delete m_p; m_p = p;} 00043 00044 // ******************************************************** 00045 00046 template<class T> class value_ptr : public member_ptr<T> 00047 { 00048 public: 00049 value_ptr(const T &obj) : member_ptr<T>(new T(obj)) {} 00050 value_ptr(T *p = NULL) : member_ptr<T>(p) {} 00051 value_ptr(const value_ptr<T>& rhs) 00052 : member_ptr<T>(rhs.m_p ? new T(*rhs.m_p) : NULL) {} 00053 00054 value_ptr<T>& operator=(const value_ptr<T>& rhs); 00055 bool operator==(const value_ptr<T>& rhs) 00056 { 00057 return (!m_p && !rhs.m_p) || (m_p && rhs.m_p && *m_p == *rhs.m_p); 00058 } 00059 }; 00060 00061 template <class T> value_ptr<T>& value_ptr<T>::operator=(const value_ptr<T>& rhs) 00062 { 00063 T *old_p = m_p; 00064 m_p = rhs.m_p ? new T(*rhs.m_p) : NULL; 00065 delete old_p; 00066 return *this; 00067 } 00068 00069 // ******************************************************** 00070 00071 template<class T> class clonable_ptr : public member_ptr<T> 00072 { 00073 public: 00074 clonable_ptr(const T &obj) : member_ptr<T>(obj.Clone()) {} 00075 clonable_ptr(T *p = NULL) : member_ptr<T>(p) {} 00076 clonable_ptr(const clonable_ptr<T>& rhs) 00077 : member_ptr<T>(rhs.m_p ? rhs.m_p->Clone() : NULL) {} 00078 00079 clonable_ptr<T>& operator=(const clonable_ptr<T>& rhs); 00080 }; 00081 00082 template <class T> clonable_ptr<T>& clonable_ptr<T>::operator=(const clonable_ptr<T>& rhs) 00083 { 00084 T *old_p = m_p; 00085 m_p = rhs.m_p ? rhs.m_p->Clone() : NULL; 00086 delete old_p; 00087 return *this; 00088 } 00089 00090 // ******************************************************** 00091 00092 template<class T> class counted_ptr 00093 { 00094 public: 00095 explicit counted_ptr(T *p = 0); 00096 counted_ptr(const T &r) : m_p(0) {attach(r);} 00097 counted_ptr(const counted_ptr<T>& rhs); 00098 00099 ~counted_ptr(); 00100 00101 const T& operator*() const { return *m_p; } 00102 T& operator*() { return *m_p; } 00103 00104 const T* operator->() const { return m_p; } 00105 T* operator->() { return get(); } 00106 00107 const T* get() const { return m_p; } 00108 T* get(); 00109 00110 void attach(const T &p); 00111 00112 counted_ptr<T> & operator=(const counted_ptr<T>& rhs); 00113 00114 private: 00115 T *m_p; 00116 }; 00117 00118 template <class T> counted_ptr<T>::counted_ptr(T *p) 00119 : m_p(p) 00120 { 00121 if (m_p) 00122 m_p->m_referenceCount = 1; 00123 } 00124 00125 template <class T> counted_ptr<T>::counted_ptr(const counted_ptr<T>& rhs) 00126 : m_p(rhs.m_p) 00127 { 00128 if (m_p) 00129 m_p->m_referenceCount++; 00130 } 00131 00132 template <class T> counted_ptr<T>::~counted_ptr() 00133 { 00134 if (m_p && --m_p->m_referenceCount == 0) 00135 delete m_p; 00136 } 00137 00138 template <class T> void counted_ptr<T>::attach(const T &r) 00139 { 00140 if (m_p && --m_p->m_referenceCount == 0) 00141 delete m_p; 00142 if (r.m_referenceCount == 0) 00143 { 00144 m_p = r.clone(); 00145 m_p->m_referenceCount = 1; 00146 } 00147 else 00148 { 00149 m_p = const_cast<T *>(&r); 00150 m_p->m_referenceCount++; 00151 } 00152 } 00153 00154 template <class T> T* counted_ptr<T>::get() 00155 { 00156 if (m_p && m_p->m_referenceCount > 1) 00157 { 00158 T *temp = m_p->clone(); 00159 m_p->m_referenceCount--; 00160 m_p = temp; 00161 m_p->m_referenceCount = 1; 00162 } 00163 return m_p; 00164 } 00165 00166 template <class T> counted_ptr<T> & counted_ptr<T>::operator=(const counted_ptr<T>& rhs) 00167 { 00168 if (m_p != rhs.m_p) 00169 { 00170 if (m_p && --m_p->m_referenceCount == 0) 00171 delete m_p; 00172 m_p = rhs.m_p; 00173 if (m_p) 00174 m_p->m_referenceCount++; 00175 } 00176 return *this; 00177 } 00178 00179 // ******************************************************** 00180 00181 template <class T> class vector_member_ptrs 00182 { 00183 public: 00184 vector_member_ptrs(unsigned int size=0) 00185 : _size(size) {ptr = new member_ptr<T>[_size];} 00186 ~vector_member_ptrs() 00187 {delete [] ptr;} 00188 00189 member_ptr<T>& operator[](unsigned int index) 00190 {assert(index<_size); return ptr[index];} 00191 const member_ptr<T>& operator[](unsigned int index) const 00192 {assert(index<_size); return ptr[index];} 00193 00194 unsigned int size() const {return _size;} 00195 void resize(unsigned int newSize) 00196 { 00197 member_ptr<T> *newPtr = new member_ptr<T>[newSize]; 00198 for (unsigned int i=0; i<STDMIN(_size, newSize); i++) 00199 newPtr[i].reset(ptr[i].release()); 00200 delete [] ptr; 00201 _size = newSize; 00202 ptr = newPtr; 00203 } 00204 00205 private: 00206 vector_member_ptrs(const vector_member_ptrs<T> &c); // copy not allowed 00207 void operator=(const vector_member_ptrs<T> &x); // assignment not allowed 00208 00209 unsigned int _size; 00210 member_ptr<T> *ptr; 00211 }; 00212 00213 NAMESPACE_END 00214 00215 #endif

Generated on Wed Jul 28 08:07:09 2004 for Crypto++ by doxygen 1.3.7