blob: 88032d7fbcdab634c4f7371ebef435acfca6882e [file] [log] [blame]
The Android Open Source Project4f6e8d72008-10-21 07:00:00 -07001/*
2 * smartpointer.h
3 * Android
4 *
5 * Copyright 2005 The Android Open Source Project
6 *
7 */
8
9#ifndef ANDROID_SMART_POINTER_H
10#define ANDROID_SMART_POINTER_H
11
12#include <stdint.h>
13#include <sys/types.h>
14#include <stdlib.h>
15
16// ---------------------------------------------------------------------------
17namespace android {
18
19// ---------------------------------------------------------------------------
20
21#define COMPARE(_op_) \
22inline bool operator _op_ (const sp<T>& o) const { \
23 return m_ptr _op_ o.m_ptr; \
24} \
25inline bool operator _op_ (const T* o) const { \
26 return m_ptr _op_ o; \
27} \
28template<typename U> \
29inline bool operator _op_ (const sp<U>& o) const { \
30 return m_ptr _op_ o.m_ptr; \
31} \
32template<typename U> \
33inline bool operator _op_ (const U* o) const { \
34 return m_ptr _op_ o; \
35}
36
37// ---------------------------------------------------------------------------
38
39template <typename T>
40class sp
41{
42public:
43 inline sp() : m_ptr(0) { }
44
45 sp(T* other);
46 sp(const sp<T>& other);
47 template<typename U> sp(U* other);
48 template<typename U> sp(const sp<U>& other);
49
50 ~sp();
51
52 // Assignment
53
54 sp& operator = (T* other);
55 sp& operator = (const sp<T>& other);
56
57 template<typename U> sp& operator = (const sp<U>& other);
58 template<typename U> sp& operator = (U* other);
59
60 // Reset
61 void clear();
62
63 // Accessors
64
65 inline T& operator* () const { return *m_ptr; }
66 inline T* operator-> () const { return m_ptr; }
67 inline T* get() const { return m_ptr; }
68
69 // Operators
70
71 COMPARE(==)
72 COMPARE(!=)
73 COMPARE(>)
74 COMPARE(<)
75 COMPARE(<=)
76 COMPARE(>=)
77
78private:
79 template<typename Y> friend class sp;
80
81 T* m_ptr;
82};
83
84// ---------------------------------------------------------------------------
85// No user serviceable parts below here.
86
87template<typename T>
88sp<T>::sp(T* other)
89 : m_ptr(other)
90{
91 if (other) other->incStrong(this);
92}
93
94template<typename T>
95sp<T>::sp(const sp<T>& other)
96 : m_ptr(other.m_ptr)
97{
98 if (m_ptr) m_ptr->incStrong(this);
99}
100
101template<typename T> template<typename U>
102sp<T>::sp(U* other) : m_ptr(other)
103{
104 if (other) other->incStrong(this);
105}
106
107template<typename T> template<typename U>
108sp<T>::sp(const sp<U>& other)
109 : m_ptr(other.m_ptr)
110{
111 if (m_ptr) m_ptr->incStrong(this);
112}
113
114template<typename T>
115sp<T>::~sp()
116{
117 if (m_ptr) m_ptr->decStrong(this);
118}
119
120template<typename T>
121sp<T>& sp<T>::operator = (const sp<T>& other) {
122 if (other.m_ptr) other.m_ptr->incStrong(this);
123 if (m_ptr) m_ptr->decStrong(this);
124 m_ptr = other.m_ptr;
125 return *this;
126}
127
128template<typename T>
129sp<T>& sp<T>::operator = (T* other)
130{
131 if (other) other->incStrong(this);
132 if (m_ptr) m_ptr->decStrong(this);
133 m_ptr = other;
134 return *this;
135}
136
137template<typename T> template<typename U>
138sp<T>& sp<T>::operator = (const sp<U>& other)
139{
140 if (other.m_ptr) other.m_ptr->incStrong(this);
141 if (m_ptr) m_ptr->decStrong(this);
142 m_ptr = other.m_ptr;
143 return *this;
144}
145
146template<typename T> template<typename U>
147sp<T>& sp<T>::operator = (U* other)
148{
149 if (other) other->incStrong(this);
150 if (m_ptr) m_ptr->decStrong(this);
151 m_ptr = other;
152 return *this;
153}
154
155template<typename T>
156void sp<T>::clear()
157{
158 if (m_ptr) {
159 m_ptr->decStrong(this);
160 m_ptr = 0;
161 }
162}
163
164// ---------------------------------------------------------------------------
165
166}; // namespace android
167
168// ---------------------------------------------------------------------------
169
170#endif // ANDROID_SMART_POINTER_H