Rietveld Code Review Tool
Help | Bug tracker | Discussion group | Source code

Side by Side Diff: compiled/intrusive_ptr.h

Issue 29333474: Issue 4125 - [emscripten] Convert filter classes to C++ (Closed)
Patch Set: Addressed comments from Patch Set 24 Created Dec. 6, 2016, 10:43 a.m.
Left:
Right:
Use n/p to move between diff chunks; N/P to move between comments.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 // Parts of this code have been copied from boost/smart_ptr/intrusive_ptr.hpp.
2 //
3 // Copyright (c) 2001, 2002 Peter Dimov
4 //
5 // Distributed under the Boost Software License, Version 1.0. (See
6 // accompanying file LICENSE_1_0.txt or copy at
7 // http://www.boost.org/LICENSE_1_0.txt)
8
9 #pragma once
10
11 #include <algorithm>
12 #include <type_traits>
13
14 #include "debug.h"
15
16 class ref_counted
17 {
18 public:
19 void AddRef()
20 {
21 mRefCount++;
22 }
23
24 void ReleaseRef()
25 {
26 assert(mRefCount > 0, u"Unexpected zero or negative reference count"_str);
27 if (--mRefCount == 0)
28 delete this;
29 }
30
31 protected:
32 ref_counted()
33 : mRefCount(1)
34 {
35 }
36
37 // We need this virtual destructor, otherwise the numerical value of
38 // a ref_counted pointer and the numerical value of a pointer to a derived
39 // class will no longer be identical - despite still pointing to the same
40 // object. So for example `(int)(Filter*)ptr - (int)(ref_counted*)ptr` will be
41 // four, something that presents an issue for our JavaScript bindings which
42 // don't know how to convert pointers between different types.
43 virtual ~ref_counted()
44 {
45 assert(mRefCount == 0, u"Destroying a ref-counted object with a non-zero ref erence count"_str);
46 }
47
48 private:
49 int mRefCount;
50 };
51
52 template<typename T,
53 class = typename std::enable_if<std::is_base_of<ref_counted,T>::value>::type >
54 class intrusive_ptr
55 {
56 public:
57 intrusive_ptr()
58 : mPointer(nullptr)
59 {
60 }
61
62 explicit intrusive_ptr(T* pointer)
63 : mPointer(pointer)
64 {
65 // Raw pointers always had their reference count increased by whatever gave
66 // us the pointer so we don't need to do it here.
67 }
68
69 intrusive_ptr(const intrusive_ptr& other)
70 : mPointer(other.mPointer)
71 {
72 if (mPointer)
73 mPointer->AddRef();
74 }
75
76 intrusive_ptr(intrusive_ptr&& other)
77 : mPointer(other.mPointer)
78 {
79 other.mPointer = nullptr;
80 }
81
82 ~intrusive_ptr()
83 {
84 if (mPointer)
85 mPointer->ReleaseRef();
86 }
87
88 intrusive_ptr& operator=(intrusive_ptr& other)
89 {
90 intrusive_ptr(other).swap(*this);
91 return *this;
92 }
93
94 intrusive_ptr& operator=(intrusive_ptr&& other)
95 {
96 intrusive_ptr(std::move(other)).swap(*this);
97 return *this;
98 }
99
100 intrusive_ptr& operator=(T* other)
101 {
102 intrusive_ptr(other).swap(*this);
103 return *this;
104 }
105
106 void reset()
107 {
108 intrusive_ptr().swap(*this);
109 }
110
111 void reset(T* other)
112 {
113 intrusive_ptr(other).swap(*this);
114 }
115
116 const T* get() const
117 {
118 return mPointer;
119 }
120
121 T* get()
122 {
123 return mPointer;
124 }
125
126 const T& operator*() const
127 {
128 return *mPointer;
129 }
130
131 T& operator*()
132 {
133 return *mPointer;
134 }
135
136 const T* operator->() const
137 {
138 return mPointer;
139 }
140
141 T* operator->()
142 {
143 return mPointer;
144 }
145
146 explicit operator bool() const
147 {
148 return mPointer != nullptr;
149 }
150
151 bool operator!() const
152 {
153 return mPointer == nullptr;
154 }
155
156 T* release()
157 {
158 T* result = mPointer;
159 mPointer = nullptr;
160 return result;
161 }
162
163 void swap(intrusive_ptr& other)
164 {
165 std::swap(mPointer, other.mPointer);
166 }
167
168 private:
169 T* mPointer;
170 };
171
172 template<typename T, typename U>
173 inline bool operator==(const intrusive_ptr<T>& a, const intrusive_ptr<U>& b)
174 {
175 return a.get() == b.get();
176 }
177
178 template<typename T, typename U>
179 inline bool operator!=(const intrusive_ptr<T>& a, const intrusive_ptr<U>& b)
180 {
181 return a.get() != b.get();
182 }
183
184 template<typename T, typename U>
185 inline bool operator==(const intrusive_ptr<T>& a, const U* b)
186 {
187 return a.get() == b;
188 }
189
190 template<typename T, typename U>
191 inline bool operator!=(const intrusive_ptr<T>& a, const U* b)
192 {
193 return a.get() != b;
194 }
195
196 template<typename T, typename U>
197 inline bool operator==(const T* a, const intrusive_ptr<U>& b)
198 {
199 return a == b.get();
200 }
201
202 template<typename T, typename U>
203 inline bool operator!=(const T* a, intrusive_ptr<U> const& b)
204 {
205 return a != b.get();
206 }
OLDNEW
« compiled/debug.h ('K') | « compiled/debug.h ('k') | compiled/shell.js » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld