Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(378)

Side by Side Diff: Source/platform/heap/Handle.h

Issue 1338573003: Restrict registered PersistentNodes to non-empty ones. (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: add back missing m_raw nullcheck that ps#3 incorrectly dropped Created 5 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « no previous file | Source/platform/heap/PersistentNode.cpp » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2014 Google Inc. All rights reserved. 2 * Copyright (C) 2014 Google Inc. All rights reserved.
3 * 3 *
4 * Redistribution and use in source and binary forms, with or without 4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are 5 * modification, are permitted provided that the following conditions are
6 * met: 6 * met:
7 * 7 *
8 * * Redistributions of source code must retain the above copyright 8 * * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer. 9 * notice, this list of conditions and the following disclaimer.
10 * * Redistributions in binary form must reproduce the above 10 * * Redistributions in binary form must reproduce the above
(...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after
130 if (weaknessConfiguration == WeakPersistentConfiguration) { 130 if (weaknessConfiguration == WeakPersistentConfiguration) {
131 visitor->registerWeakCell(&m_raw); 131 visitor->registerWeakCell(&m_raw);
132 } else { 132 } else {
133 visitor->mark(m_raw); 133 visitor->mark(m_raw);
134 } 134 }
135 } 135 }
136 136
137 RawPtr<T> release() 137 RawPtr<T> release()
138 { 138 {
139 RawPtr<T> result = m_raw; 139 RawPtr<T> result = m_raw;
140 m_raw = nullptr; 140 assign(nullptr);
141 return result; 141 return result;
142 } 142 }
143 143
144 void clear() { m_raw = nullptr; } 144 void clear() { assign(nullptr); }
145 T& operator*() const { return *m_raw; } 145 T& operator*() const { return *m_raw; }
146 bool operator!() const { return !m_raw; } 146 bool operator!() const { return !m_raw; }
147 operator T*() const { return m_raw; } 147 operator T*() const { return m_raw; }
148 operator RawPtr<T>() const { return m_raw; } 148 operator RawPtr<T>() const { return m_raw; }
149 T* operator->() const { return *this; } 149 T* operator->() const { return *this; }
150 T* get() const { return m_raw; } 150 T* get() const { return m_raw; }
151 151
152 template<typename U> 152 template<typename U>
153 PersistentBase& operator=(U* other) 153 PersistentBase& operator=(U* other)
154 { 154 {
155 m_raw = other; 155 assign(other);
156 checkPointer();
157 recordBacktrace();
158 return *this; 156 return *this;
159 } 157 }
160 158
161 PersistentBase& operator=(std::nullptr_t) 159 PersistentBase& operator=(std::nullptr_t)
162 { 160 {
163 m_raw = nullptr; 161 assign(nullptr);
164 return *this; 162 return *this;
165 } 163 }
166 164
167 PersistentBase& operator=(const PersistentBase& other) 165 PersistentBase& operator=(const PersistentBase& other)
168 { 166 {
169 m_raw = other; 167 assign(other);
170 checkPointer();
171 recordBacktrace();
172 return *this; 168 return *this;
173 } 169 }
174 170
175 template<typename U> 171 template<typename U>
176 PersistentBase& operator=(const PersistentBase<U, weaknessConfiguration, cro ssThreadnessConfiguration>& other) 172 PersistentBase& operator=(const PersistentBase<U, weaknessConfiguration, cro ssThreadnessConfiguration>& other)
177 { 173 {
178 m_raw = other; 174 assign(other);
179 checkPointer();
180 recordBacktrace();
181 return *this; 175 return *this;
182 } 176 }
183 177
184 template<typename U> 178 template<typename U>
185 PersistentBase& operator=(const Member<U>& other) 179 PersistentBase& operator=(const Member<U>& other)
186 { 180 {
187 m_raw = other; 181 assign(other);
188 checkPointer();
189 recordBacktrace();
190 return *this; 182 return *this;
191 } 183 }
192 184
193 template<typename U> 185 template<typename U>
194 PersistentBase& operator=(const RawPtr<U>& other) 186 PersistentBase& operator=(const RawPtr<U>& other)
195 { 187 {
196 m_raw = other; 188 assign(other);
197 checkPointer();
198 recordBacktrace();
199 return *this; 189 return *this;
200 } 190 }
201 191
202 192
203 private: 193 private:
204 NO_LAZY_SWEEP_SANITIZE_ADDRESS 194 NO_LAZY_SWEEP_SANITIZE_ADDRESS
195 void assign(T* ptr)
196 {
197 m_raw = ptr;
198 checkPointer();
199 recordBacktrace();
200 if (m_raw) {
201 if (!m_persistentNode)
202 initialize();
203 return;
204 }
205 if (m_persistentNode && crossThreadnessConfiguration != CrossThreadPersi stentConfiguration)
206 uninitialize();
207 }
208
209 NO_LAZY_SWEEP_SANITIZE_ADDRESS
205 void initialize() 210 void initialize()
206 { 211 {
212 ASSERT(!m_persistentNode);
213 if (!m_raw)
214 return;
215
207 TraceCallback traceCallback = TraceMethodDelegate<PersistentBase<T, weak nessConfiguration, crossThreadnessConfiguration>, &PersistentBase<T, weaknessCon figuration, crossThreadnessConfiguration>::trace>::trampoline; 216 TraceCallback traceCallback = TraceMethodDelegate<PersistentBase<T, weak nessConfiguration, crossThreadnessConfiguration>, &PersistentBase<T, weaknessCon figuration, crossThreadnessConfiguration>::trace>::trampoline;
208 if (crossThreadnessConfiguration == CrossThreadPersistentConfiguration) { 217 if (crossThreadnessConfiguration == CrossThreadPersistentConfiguration) {
209 m_persistentNode = ThreadState::crossThreadPersistentRegion().alloca tePersistentNode(this, traceCallback); 218 m_persistentNode = ThreadState::crossThreadPersistentRegion().alloca tePersistentNode(this, traceCallback);
210 } else { 219 } else {
211 ThreadState* state = ThreadStateFor<ThreadingTrait<T>::Affinity>::st ate(); 220 ThreadState* state = ThreadStateFor<ThreadingTrait<T>::Affinity>::st ate();
212 ASSERT(state->checkThread()); 221 ASSERT(state->checkThread());
213 m_persistentNode = state->persistentRegion()->allocatePersistentNode (this, traceCallback); 222 m_persistentNode = state->persistentRegion()->allocatePersistentNode (this, traceCallback);
214 #if ENABLE(ASSERT) 223 #if ENABLE(ASSERT)
215 m_state = state; 224 m_state = state;
216 #endif 225 #endif
217 } 226 }
218 } 227 }
219 228
220 void uninitialize() 229 void uninitialize()
221 { 230 {
231 if (!m_persistentNode)
232 return;
233
222 if (crossThreadnessConfiguration == CrossThreadPersistentConfiguration) { 234 if (crossThreadnessConfiguration == CrossThreadPersistentConfiguration) {
223 ThreadState::crossThreadPersistentRegion().freePersistentNode(m_pers istentNode); 235 ThreadState::crossThreadPersistentRegion().freePersistentNode(m_pers istentNode);
224 } else { 236 } else {
225 ThreadState* state = ThreadStateFor<ThreadingTrait<T>::Affinity>::st ate(); 237 ThreadState* state = ThreadStateFor<ThreadingTrait<T>::Affinity>::st ate();
226 ASSERT(state->checkThread()); 238 ASSERT(state->checkThread());
227 // Persistent handle must be created and destructed in the same thre ad. 239 // Persistent handle must be created and destructed in the same thre ad.
228 ASSERT(m_state == state); 240 ASSERT(m_state == state);
229 state->persistentRegion()->freePersistentNode(m_persistentNode); 241 state->persistentRegion()->freePersistentNode(m_persistentNode);
230 } 242 }
243 m_persistentNode = nullptr;
231 } 244 }
232 245
233 void checkPointer() 246 void checkPointer()
234 { 247 {
235 #if ENABLE(ASSERT) 248 #if ENABLE(ASSERT)
236 if (!m_raw) 249 if (!m_raw)
237 return; 250 return;
238 251
239 // Heap::isHeapObjectAlive(m_raw) checks that m_raw is a traceable 252 // Heap::isHeapObjectAlive(m_raw) checks that m_raw is a traceable
240 // object. In other words, it checks that the pointer is either of: 253 // object. In other words, it checks that the pointer is either of:
(...skipping 13 matching lines...) Expand all
254 if (m_raw) 267 if (m_raw)
255 m_tracingName = Heap::createBacktraceString(); 268 m_tracingName = Heap::createBacktraceString();
256 } 269 }
257 270
258 String m_tracingName; 271 String m_tracingName;
259 #else 272 #else
260 inline void recordBacktrace() const { } 273 inline void recordBacktrace() const { }
261 #endif 274 #endif
262 // m_raw is accessed most, so put it at the first field. 275 // m_raw is accessed most, so put it at the first field.
263 T* m_raw; 276 T* m_raw;
264 PersistentNode* m_persistentNode; 277 PersistentNode* m_persistentNode = nullptr;
265 #if ENABLE(ASSERT) 278 #if ENABLE(ASSERT)
266 ThreadState* m_state; 279 ThreadState* m_state = nullptr;
267 #endif 280 #endif
268 }; 281 };
269 282
270 // Persistent is a way to create a strong pointer from an off-heap object 283 // Persistent is a way to create a strong pointer from an off-heap object
271 // to another on-heap object. As long as the Persistent handle is alive 284 // to another on-heap object. As long as the Persistent handle is alive
272 // the GC will keep the object pointed to alive. The Persistent handle is 285 // the GC will keep the object pointed to alive. The Persistent handle is
273 // always a GC root from the point of view of the GC. 286 // always a GC root from the point of view of the GC.
274 // 287 //
275 // We have to construct and destruct Persistent in the same thread. 288 // We have to construct and destruct Persistent in the same thread.
276 template<typename T> 289 template<typename T>
(...skipping 1092 matching lines...) Expand 10 before | Expand all | Expand 10 after
1369 // TODO(sof): extend WTF::FunctionWrapper call overloading to also handle (C rossThread)WeakPersistent. 1382 // TODO(sof): extend WTF::FunctionWrapper call overloading to also handle (C rossThread)WeakPersistent.
1370 static T* unwrap(const StorageType& value) { return value.get(); } 1383 static T* unwrap(const StorageType& value) { return value.get(); }
1371 }; 1384 };
1372 1385
1373 template<typename T> 1386 template<typename T>
1374 PassRefPtr<T> adoptRef(blink::RefCountedGarbageCollected<T>*) = delete; 1387 PassRefPtr<T> adoptRef(blink::RefCountedGarbageCollected<T>*) = delete;
1375 1388
1376 } // namespace WTF 1389 } // namespace WTF
1377 1390
1378 #endif 1391 #endif
OLDNEW
« no previous file with comments | « no previous file | Source/platform/heap/PersistentNode.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698