1 /* 2 * Copyright 2005 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef ANDROID_PIXELFLINGER_SMART_POINTER_H 18 #define ANDROID_PIXELFLINGER_SMART_POINTER_H 19 20 #include <stdint.h> 21 #include <sys/types.h> 22 #include <stdlib.h> 23 24 // --------------------------------------------------------------------------- 25 namespace android { 26 namespace tinyutils { 27 28 // --------------------------------------------------------------------------- 29 30 #define COMPARE(_op_) \ 31 inline bool operator _op_ (const sp<T>& o) const { \ 32 return m_ptr _op_ o.m_ptr; \ 33 } \ 34 inline bool operator _op_ (const T* o) const { \ 35 return m_ptr _op_ o; \ 36 } \ 37 template<typename U> \ 38 inline bool operator _op_ (const sp<U>& o) const { \ 39 return m_ptr _op_ o.m_ptr; \ 40 } \ 41 template<typename U> \ 42 inline bool operator _op_ (const U* o) const { \ 43 return m_ptr _op_ o; \ 44 } 45 46 // --------------------------------------------------------------------------- 47 48 template <typename T> 49 class sp 50 { 51 public: sp()52 inline sp() : m_ptr(0) { } 53 54 sp(T* other); // NOLINT, implicit 55 sp(const sp<T>& other); 56 template<typename U> sp(U* other); // NOLINT, implicit 57 template<typename U> sp(const sp<U>& other); // NOLINT, implicit 58 59 ~sp(); 60 61 // Assignment 62 63 sp& operator = (T* other); 64 sp& operator = (const sp<T>& other); 65 66 template<typename U> sp& operator = (const sp<U>& other); 67 template<typename U> sp& operator = (U* other); 68 69 // Reset 70 void clear(); 71 72 // Accessors 73 74 inline T& operator* () const { return *m_ptr; } 75 inline T* operator-> () const { return m_ptr; } get()76 inline T* get() const { return m_ptr; } 77 78 // Operators 79 80 COMPARE(==) 81 COMPARE(!=) 82 COMPARE(>) 83 COMPARE(<) 84 COMPARE(<=) 85 COMPARE(>=) 86 87 private: 88 template<typename Y> friend class sp; 89 90 T* m_ptr; 91 }; 92 93 // --------------------------------------------------------------------------- 94 // No user serviceable parts below here. 95 96 template<typename T> sp(T * other)97sp<T>::sp(T* other) 98 : m_ptr(other) 99 { 100 if (other) other->incStrong(this); 101 } 102 103 template<typename T> sp(const sp<T> & other)104sp<T>::sp(const sp<T>& other) 105 : m_ptr(other.m_ptr) 106 { 107 if (m_ptr) m_ptr->incStrong(this); 108 } 109 110 template<typename T> template<typename U> sp(U * other)111sp<T>::sp(U* other) : m_ptr(other) 112 { 113 if (other) other->incStrong(this); 114 } 115 116 template<typename T> template<typename U> sp(const sp<U> & other)117sp<T>::sp(const sp<U>& other) 118 : m_ptr(other.m_ptr) 119 { 120 if (m_ptr) m_ptr->incStrong(this); 121 } 122 123 template<typename T> ~sp()124sp<T>::~sp() 125 { 126 if (m_ptr) m_ptr->decStrong(this); 127 } 128 129 template<typename T> 130 sp<T>& sp<T>::operator = (const sp<T>& other) { 131 if (other.m_ptr) other.m_ptr->incStrong(this); 132 if (m_ptr) m_ptr->decStrong(this); 133 m_ptr = other.m_ptr; 134 return *this; 135 } 136 137 template<typename T> 138 sp<T>& sp<T>::operator = (T* other) 139 { 140 if (other) other->incStrong(this); 141 if (m_ptr) m_ptr->decStrong(this); 142 m_ptr = other; 143 return *this; 144 } 145 146 template<typename T> template<typename U> 147 sp<T>& sp<T>::operator = (const sp<U>& other) 148 { 149 if (other.m_ptr) other.m_ptr->incStrong(this); 150 if (m_ptr) m_ptr->decStrong(this); 151 m_ptr = other.m_ptr; 152 return *this; 153 } 154 155 template<typename T> template<typename U> 156 sp<T>& sp<T>::operator = (U* other) 157 { 158 if (other) other->incStrong(this); 159 if (m_ptr) m_ptr->decStrong(this); 160 m_ptr = other; 161 return *this; 162 } 163 164 template<typename T> clear()165void sp<T>::clear() 166 { 167 if (m_ptr) { 168 m_ptr->decStrong(this); 169 m_ptr = 0; 170 } 171 } 172 173 // --------------------------------------------------------------------------- 174 175 } // namespace tinyutils 176 } // namespace android 177 178 // --------------------------------------------------------------------------- 179 180 #endif // ANDROID_PIXELFLINGER_SMART_POINTER_H 181