1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/toolkit/crashreporter/google-breakpad/src/common/scoped_ptr.h Wed Dec 31 06:09:35 2014 +0100 1.3 @@ -0,0 +1,335 @@ 1.4 +// (C) Copyright Greg Colvin and Beman Dawes 1998, 1999. 1.5 +// Copyright (c) 2001, 2002 Peter Dimov 1.6 +// 1.7 +// Permission to copy, use, modify, sell and distribute this software 1.8 +// is granted provided this copyright notice appears in all copies. 1.9 +// This software is provided "as is" without express or implied 1.10 +// warranty, and with no claim as to its suitability for any purpose. 1.11 +// 1.12 +// See http://www.boost.org/libs/smart_ptr/scoped_ptr.htm for documentation. 1.13 +// 1.14 + 1.15 +// scoped_ptr mimics a built-in pointer except that it guarantees deletion 1.16 +// of the object pointed to, either on destruction of the scoped_ptr or via 1.17 +// an explicit reset(). scoped_ptr is a simple solution for simple needs; 1.18 +// use shared_ptr or std::auto_ptr if your needs are more complex. 1.19 + 1.20 +// *** NOTE *** 1.21 +// If your scoped_ptr is a class member of class FOO pointing to a 1.22 +// forward declared type BAR (as shown below), then you MUST use a non-inlined 1.23 +// version of the destructor. The destructor of a scoped_ptr (called from 1.24 +// FOO's destructor) must have a complete definition of BAR in order to 1.25 +// destroy it. Example: 1.26 +// 1.27 +// -- foo.h -- 1.28 +// class BAR; 1.29 +// 1.30 +// class FOO { 1.31 +// public: 1.32 +// FOO(); 1.33 +// ~FOO(); // Required for sources that instantiate class FOO to compile! 1.34 +// 1.35 +// private: 1.36 +// scoped_ptr<BAR> bar_; 1.37 +// }; 1.38 +// 1.39 +// -- foo.cc -- 1.40 +// #include "foo.h" 1.41 +// FOO::~FOO() {} // Empty, but must be non-inlined to FOO's class definition. 1.42 + 1.43 +// scoped_ptr_malloc added by Google 1.44 +// When one of these goes out of scope, instead of doing a delete or 1.45 +// delete[], it calls free(). scoped_ptr_malloc<char> is likely to see 1.46 +// much more use than any other specializations. 1.47 + 1.48 +// release() added by Google 1.49 +// Use this to conditionally transfer ownership of a heap-allocated object 1.50 +// to the caller, usually on method success. 1.51 + 1.52 +#ifndef COMMON_SCOPED_PTR_H_ 1.53 +#define COMMON_SCOPED_PTR_H_ 1.54 + 1.55 +#include <cstddef> // for std::ptrdiff_t 1.56 +#include <assert.h> // for assert 1.57 +#include <stdlib.h> // for free() decl 1.58 + 1.59 +namespace google_breakpad { 1.60 + 1.61 +template <typename T> 1.62 +class scoped_ptr { 1.63 + private: 1.64 + 1.65 + T* ptr; 1.66 + 1.67 + scoped_ptr(scoped_ptr const &); 1.68 + scoped_ptr & operator=(scoped_ptr const &); 1.69 + 1.70 + public: 1.71 + 1.72 + typedef T element_type; 1.73 + 1.74 + explicit scoped_ptr(T* p = 0): ptr(p) {} 1.75 + 1.76 + ~scoped_ptr() { 1.77 + typedef char type_must_be_complete[sizeof(T)]; 1.78 + delete ptr; 1.79 + } 1.80 + 1.81 + void reset(T* p = 0) { 1.82 + typedef char type_must_be_complete[sizeof(T)]; 1.83 + 1.84 + if (ptr != p) { 1.85 + delete ptr; 1.86 + ptr = p; 1.87 + } 1.88 + } 1.89 + 1.90 + T& operator*() const { 1.91 + assert(ptr != 0); 1.92 + return *ptr; 1.93 + } 1.94 + 1.95 + T* operator->() const { 1.96 + assert(ptr != 0); 1.97 + return ptr; 1.98 + } 1.99 + 1.100 + bool operator==(T* p) const { 1.101 + return ptr == p; 1.102 + } 1.103 + 1.104 + bool operator!=(T* p) const { 1.105 + return ptr != p; 1.106 + } 1.107 + 1.108 + T* get() const { 1.109 + return ptr; 1.110 + } 1.111 + 1.112 + void swap(scoped_ptr & b) { 1.113 + T* tmp = b.ptr; 1.114 + b.ptr = ptr; 1.115 + ptr = tmp; 1.116 + } 1.117 + 1.118 + T* release() { 1.119 + T* tmp = ptr; 1.120 + ptr = 0; 1.121 + return tmp; 1.122 + } 1.123 + 1.124 + private: 1.125 + 1.126 + // no reason to use these: each scoped_ptr should have its own object 1.127 + template <typename U> bool operator==(scoped_ptr<U> const& p) const; 1.128 + template <typename U> bool operator!=(scoped_ptr<U> const& p) const; 1.129 +}; 1.130 + 1.131 +template<typename T> inline 1.132 +void swap(scoped_ptr<T>& a, scoped_ptr<T>& b) { 1.133 + a.swap(b); 1.134 +} 1.135 + 1.136 +template<typename T> inline 1.137 +bool operator==(T* p, const scoped_ptr<T>& b) { 1.138 + return p == b.get(); 1.139 +} 1.140 + 1.141 +template<typename T> inline 1.142 +bool operator!=(T* p, const scoped_ptr<T>& b) { 1.143 + return p != b.get(); 1.144 +} 1.145 + 1.146 +// scoped_array extends scoped_ptr to arrays. Deletion of the array pointed to 1.147 +// is guaranteed, either on destruction of the scoped_array or via an explicit 1.148 +// reset(). Use shared_array or std::vector if your needs are more complex. 1.149 + 1.150 +template<typename T> 1.151 +class scoped_array { 1.152 + private: 1.153 + 1.154 + T* ptr; 1.155 + 1.156 + scoped_array(scoped_array const &); 1.157 + scoped_array & operator=(scoped_array const &); 1.158 + 1.159 + public: 1.160 + 1.161 + typedef T element_type; 1.162 + 1.163 + explicit scoped_array(T* p = 0) : ptr(p) {} 1.164 + 1.165 + ~scoped_array() { 1.166 + typedef char type_must_be_complete[sizeof(T)]; 1.167 + delete[] ptr; 1.168 + } 1.169 + 1.170 + void reset(T* p = 0) { 1.171 + typedef char type_must_be_complete[sizeof(T)]; 1.172 + 1.173 + if (ptr != p) { 1.174 + delete [] ptr; 1.175 + ptr = p; 1.176 + } 1.177 + } 1.178 + 1.179 + T& operator[](std::ptrdiff_t i) const { 1.180 + assert(ptr != 0); 1.181 + assert(i >= 0); 1.182 + return ptr[i]; 1.183 + } 1.184 + 1.185 + bool operator==(T* p) const { 1.186 + return ptr == p; 1.187 + } 1.188 + 1.189 + bool operator!=(T* p) const { 1.190 + return ptr != p; 1.191 + } 1.192 + 1.193 + T* get() const { 1.194 + return ptr; 1.195 + } 1.196 + 1.197 + void swap(scoped_array & b) { 1.198 + T* tmp = b.ptr; 1.199 + b.ptr = ptr; 1.200 + ptr = tmp; 1.201 + } 1.202 + 1.203 + T* release() { 1.204 + T* tmp = ptr; 1.205 + ptr = 0; 1.206 + return tmp; 1.207 + } 1.208 + 1.209 + private: 1.210 + 1.211 + // no reason to use these: each scoped_array should have its own object 1.212 + template <typename U> bool operator==(scoped_array<U> const& p) const; 1.213 + template <typename U> bool operator!=(scoped_array<U> const& p) const; 1.214 +}; 1.215 + 1.216 +template<class T> inline 1.217 +void swap(scoped_array<T>& a, scoped_array<T>& b) { 1.218 + a.swap(b); 1.219 +} 1.220 + 1.221 +template<typename T> inline 1.222 +bool operator==(T* p, const scoped_array<T>& b) { 1.223 + return p == b.get(); 1.224 +} 1.225 + 1.226 +template<typename T> inline 1.227 +bool operator!=(T* p, const scoped_array<T>& b) { 1.228 + return p != b.get(); 1.229 +} 1.230 + 1.231 + 1.232 +// This class wraps the c library function free() in a class that can be 1.233 +// passed as a template argument to scoped_ptr_malloc below. 1.234 +class ScopedPtrMallocFree { 1.235 + public: 1.236 + inline void operator()(void* x) const { 1.237 + free(x); 1.238 + } 1.239 +}; 1.240 + 1.241 +// scoped_ptr_malloc<> is similar to scoped_ptr<>, but it accepts a 1.242 +// second template argument, the functor used to free the object. 1.243 + 1.244 +template<typename T, typename FreeProc = ScopedPtrMallocFree> 1.245 +class scoped_ptr_malloc { 1.246 + private: 1.247 + 1.248 + T* ptr; 1.249 + 1.250 + scoped_ptr_malloc(scoped_ptr_malloc const &); 1.251 + scoped_ptr_malloc & operator=(scoped_ptr_malloc const &); 1.252 + 1.253 + public: 1.254 + 1.255 + typedef T element_type; 1.256 + 1.257 + explicit scoped_ptr_malloc(T* p = 0): ptr(p) {} 1.258 + 1.259 + ~scoped_ptr_malloc() { 1.260 + typedef char type_must_be_complete[sizeof(T)]; 1.261 + free_((void*) ptr); 1.262 + } 1.263 + 1.264 + void reset(T* p = 0) { 1.265 + typedef char type_must_be_complete[sizeof(T)]; 1.266 + 1.267 + if (ptr != p) { 1.268 + free_((void*) ptr); 1.269 + ptr = p; 1.270 + } 1.271 + } 1.272 + 1.273 + T& operator*() const { 1.274 + assert(ptr != 0); 1.275 + return *ptr; 1.276 + } 1.277 + 1.278 + T* operator->() const { 1.279 + assert(ptr != 0); 1.280 + return ptr; 1.281 + } 1.282 + 1.283 + bool operator==(T* p) const { 1.284 + return ptr == p; 1.285 + } 1.286 + 1.287 + bool operator!=(T* p) const { 1.288 + return ptr != p; 1.289 + } 1.290 + 1.291 + T* get() const { 1.292 + return ptr; 1.293 + } 1.294 + 1.295 + void swap(scoped_ptr_malloc & b) { 1.296 + T* tmp = b.ptr; 1.297 + b.ptr = ptr; 1.298 + ptr = tmp; 1.299 + } 1.300 + 1.301 + T* release() { 1.302 + T* tmp = ptr; 1.303 + ptr = 0; 1.304 + return tmp; 1.305 + } 1.306 + 1.307 + private: 1.308 + 1.309 + // no reason to use these: each scoped_ptr_malloc should have its own object 1.310 + template <typename U, typename GP> 1.311 + bool operator==(scoped_ptr_malloc<U, GP> const& p) const; 1.312 + template <typename U, typename GP> 1.313 + bool operator!=(scoped_ptr_malloc<U, GP> const& p) const; 1.314 + 1.315 + static FreeProc const free_; 1.316 +}; 1.317 + 1.318 +template<typename T, typename FP> 1.319 +FP const scoped_ptr_malloc<T,FP>::free_ = FP(); 1.320 + 1.321 +template<typename T, typename FP> inline 1.322 +void swap(scoped_ptr_malloc<T,FP>& a, scoped_ptr_malloc<T,FP>& b) { 1.323 + a.swap(b); 1.324 +} 1.325 + 1.326 +template<typename T, typename FP> inline 1.327 +bool operator==(T* p, const scoped_ptr_malloc<T,FP>& b) { 1.328 + return p == b.get(); 1.329 +} 1.330 + 1.331 +template<typename T, typename FP> inline 1.332 +bool operator!=(T* p, const scoped_ptr_malloc<T,FP>& b) { 1.333 + return p != b.get(); 1.334 +} 1.335 + 1.336 +} // namespace google_breakpad 1.337 + 1.338 +#endif // COMMON_SCOPED_PTR_H_