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

Side by Side Diff: tools/clang/blink_gc_plugin/RecordInfo.cpp

Issue 197863003: Check consistency of manual trace and finalization dispatching. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: finalization and considered-abstract Created 6 years, 9 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
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "Config.h" 5 #include "Config.h"
6 #include "RecordInfo.h" 6 #include "RecordInfo.h"
7 7
8 #include "clang/AST/Attr.h" 8 #include "clang/AST/Attr.h"
9 9
10 using namespace clang; 10 using namespace clang;
(...skipping 176 matching lines...) Expand 10 before | Expand all | Expand 10 after
187 bool RecordInfo::InheritsNonPureTrace() { 187 bool RecordInfo::InheritsNonPureTrace() {
188 if (CXXMethodDecl* trace = GetTraceMethod()) 188 if (CXXMethodDecl* trace = GetTraceMethod())
189 return !trace->isPure(); 189 return !trace->isPure();
190 for (Bases::iterator it = GetBases().begin(); it != GetBases().end(); ++it) { 190 for (Bases::iterator it = GetBases().begin(); it != GetBases().end(); ++it) {
191 if (it->second.info()->InheritsNonPureTrace()) 191 if (it->second.info()->InheritsNonPureTrace())
192 return true; 192 return true;
193 } 193 }
194 return false; 194 return false;
195 } 195 }
196 196
197 CXXMethodDecl* RecordInfo::InheritsNonVirtualTrace() {
198 if (CXXMethodDecl* trace = GetTraceMethod())
199 return trace->isVirtual() ? 0 : trace;
200 for (Bases::iterator it = GetBases().begin(); it != GetBases().end(); ++it) {
201 if (CXXMethodDecl* trace = it->second.info()->InheritsNonVirtualTrace())
202 return trace;
203 }
204 return 0;
205 }
206
207 // A (non-virtual) class is considered abstract in Blink if it has
208 // no public constructors and no create methods.
209 bool RecordInfo::IsConsideredAbstract() {
210 for (CXXRecordDecl::ctor_iterator it = record_->ctor_begin();
211 it != record_->ctor_end();
212 ++it) {
213 if (!it->isCopyOrMoveConstructor() && it->getAccess() == AS_public)
214 return false;
215 }
216 for (CXXRecordDecl::method_iterator it = record_->method_begin();
217 it != record_->method_end();
218 ++it) {
219 if (it->getNameAsString() == kCreateName)
220 return false;
221 }
222 return true;
223 }
224
197 RecordInfo::Bases* RecordInfo::CollectBases() { 225 RecordInfo::Bases* RecordInfo::CollectBases() {
198 // Compute the collection locally to avoid inconsistent states. 226 // Compute the collection locally to avoid inconsistent states.
199 Bases* bases = new Bases; 227 Bases* bases = new Bases;
200 if (!record_->hasDefinition()) 228 if (!record_->hasDefinition())
201 return bases; 229 return bases;
202 for (CXXRecordDecl::base_class_iterator it = record_->bases_begin(); 230 for (CXXRecordDecl::base_class_iterator it = record_->bases_begin();
203 it != record_->bases_end(); 231 it != record_->bases_end();
204 ++it) { 232 ++it) {
205 const CXXBaseSpecifier& spec = *it; 233 const CXXBaseSpecifier& spec = *it;
206 RecordInfo* info = cache_->Lookup(spec.getType()); 234 RecordInfo* info = cache_->Lookup(spec.getType());
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
247 if (determined_trace_methods_) 275 if (determined_trace_methods_)
248 return; 276 return;
249 determined_trace_methods_ = true; 277 determined_trace_methods_ = true;
250 CXXMethodDecl* trace = 0; 278 CXXMethodDecl* trace = 0;
251 CXXMethodDecl* traceAfterDispatch = 0; 279 CXXMethodDecl* traceAfterDispatch = 0;
252 bool isTraceAfterDispatch; 280 bool isTraceAfterDispatch;
253 for (CXXRecordDecl::method_iterator it = record_->method_begin(); 281 for (CXXRecordDecl::method_iterator it = record_->method_begin();
254 it != record_->method_end(); 282 it != record_->method_end();
255 ++it) { 283 ++it) {
256 if (Config::IsTraceMethod(*it, &isTraceAfterDispatch)) { 284 if (Config::IsTraceMethod(*it, &isTraceAfterDispatch)) {
257 // TODO: Test that the formal parameter is of type Visitor*.
258 if (isTraceAfterDispatch) { 285 if (isTraceAfterDispatch) {
259 traceAfterDispatch = *it; 286 traceAfterDispatch = *it;
260 } else { 287 } else {
261 trace = *it; 288 trace = *it;
262 } 289 }
263 } 290 }
264 } 291 }
265 if (traceAfterDispatch) { 292 if (traceAfterDispatch) {
266 trace_method_ = traceAfterDispatch; 293 trace_method_ = traceAfterDispatch;
267 trace_dispatch_method_ = trace; 294 trace_dispatch_method_ = trace;
268 } else { 295 } else {
269 // TODO: Can we never have a dispatch method called trace without the same 296 // TODO: Can we never have a dispatch method called trace without the same
270 // class defining a traceAfterDispatch method? 297 // class defining a traceAfterDispatch method?
271 trace_method_ = trace; 298 trace_method_ = trace;
272 trace_dispatch_method_ = 0; 299 trace_dispatch_method_ = 0;
273 } 300 }
301 if (trace_dispatch_method_)
302 return;
Mads Ager (chromium) 2014/03/18 09:19:32 How about removing this and instead moving the bel
zerny-chromium 2014/03/18 10:03:41 The for loop might need to run in either branch si
303 // If this class does not define a trace dispatch method search inherit it.
Mads Ager (chromium) 2014/03/18 09:19:32 search the inheritance hierarchy for it?
zerny-chromium 2014/03/18 10:03:41 Yes. Thanks.
304 for (Bases::iterator it = GetBases().begin(); it != GetBases().end(); ++it) {
305 if (CXXMethodDecl* dispatch = it->second.info()->GetTraceDispatchMethod()) {
306 // TODO: Does it make sense to inherit multiple dispatch methods?
307 assert(!trace_dispatch_method_ && "Multiple trace dispatching methods");
308 trace_dispatch_method_ = dispatch;
309 }
310 }
274 } 311 }
275 312
276 // TODO: Add classes with a finalize() method that specialize FinalizerTrait. 313 // TODO: Add classes with a finalize() method that specialize FinalizerTrait.
277 bool RecordInfo::NeedsFinalization() { 314 bool RecordInfo::NeedsFinalization() {
278 return record_->hasNonTrivialDestructor(); 315 return record_->hasNonTrivialDestructor();
279 } 316 }
280 317
281 // A class needs tracing if: 318 // A class needs tracing if:
282 // - it is allocated on the managed heap, 319 // - it is allocated on the managed heap,
283 // - it is derived from a class that needs tracing, or 320 // - it is derived from a class that needs tracing, or
(...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after
380 // We failed to create an edge so abort the entire edge construction. 417 // We failed to create an edge so abort the entire edge construction.
381 delete edge; // Will delete the already allocated members. 418 delete edge; // Will delete the already allocated members.
382 return 0; 419 return 0;
383 } 420 }
384 } 421 }
385 return edge; 422 return edge;
386 } 423 }
387 424
388 return new Value(info); 425 return new Value(info);
389 } 426 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698