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

Side by Side Diff: pkg/compiler/lib/src/js_emitter/program_builder/collector.dart

Issue 2843283004: Use more entities in program_builder, collector and registry (Closed)
Patch Set: Updated cf. comments. Created 3 years, 7 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
OLDNEW
1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2015, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 part of dart2js.js_emitter.program_builder; 5 part of dart2js.js_emitter.program_builder;
6 6
7 /** 7 /**
8 * Generates the code for all used classes in the program. Static fields (even 8 * Generates the code for all used classes in the program. Static fields (even
9 * in classes) are ignored, since they can be treated as non-class elements. 9 * in classes) are ignored, since they can be treated as non-class elements.
10 * 10 *
11 * The code for the containing (used) methods must exist in the `universe`. 11 * The code for the containing (used) methods must exist in the `universe`.
12 */ 12 */
13 class Collector { 13 class Collector {
14 final CompilerOptions _options; 14 final CompilerOptions _options;
15 final CommonElements _commonElements; 15 final CommonElements _commonElements;
16 final DeferredLoadTask _deferredLoadTask; 16 final DeferredLoadTask _deferredLoadTask;
17 final CodegenWorldBuilder _worldBuilder; 17 final CodegenWorldBuilder _worldBuilder;
18 // TODO(floitsch): the code-emitter task should not need a namer. 18 // TODO(floitsch): the code-emitter task should not need a namer.
19 final Namer _namer; 19 final Namer _namer;
20 final Emitter _emitter; 20 final Emitter _emitter;
21 final JavaScriptConstantCompiler _constantHandler; 21 final JavaScriptConstantCompiler _constantHandler;
22 final NativeData _nativeData; 22 final NativeData _nativeData;
23 final InterceptorData _interceptorData; 23 final InterceptorData _interceptorData;
24 final OneShotInterceptorData _oneShotInterceptorData; 24 final OneShotInterceptorData _oneShotInterceptorData;
25 final MirrorsData _mirrorsData; 25 final MirrorsData _mirrorsData;
26 final ClosedWorld _closedWorld; 26 final ClosedWorld _closedWorld;
27 final Set<ClassElement> _rtiNeededClasses; 27 final Set<ClassEntity> _rtiNeededClasses;
28 final Map<MemberElement, js.Expression> _generatedCode; 28 final Map<MemberElement, js.Expression> _generatedCode;
29 final Sorter _sorter;
29 30
30 final Set<ClassElement> neededClasses = new Set<ClassElement>(); 31 final Set<ClassEntity> neededClasses = new Set<ClassEntity>();
31 // This field is set in [computeNeededDeclarations]. 32 // This field is set in [computeNeededDeclarations].
32 Set<ClassElement> classesOnlyNeededForRti; 33 Set<ClassEntity> classesOnlyNeededForRti;
33 final Map<OutputUnit, List<ClassElement>> outputClassLists = 34 final Map<OutputUnit, List<ClassEntity>> outputClassLists =
34 new Map<OutputUnit, List<ClassElement>>(); 35 new Map<OutputUnit, List<ClassEntity>>();
35 final Map<OutputUnit, List<ConstantValue>> outputConstantLists = 36 final Map<OutputUnit, List<ConstantValue>> outputConstantLists =
36 new Map<OutputUnit, List<ConstantValue>>(); 37 new Map<OutputUnit, List<ConstantValue>>();
37 final Map<OutputUnit, List<Element>> outputStaticLists = 38 final Map<OutputUnit, List<MemberEntity>> outputStaticLists =
38 new Map<OutputUnit, List<Element>>(); 39 new Map<OutputUnit, List<MemberEntity>>();
39 final Map<OutputUnit, List<VariableElement>> outputStaticNonFinalFieldLists = 40 final Map<OutputUnit, List<FieldEntity>> outputStaticNonFinalFieldLists =
40 new Map<OutputUnit, List<VariableElement>>(); 41 new Map<OutputUnit, List<FieldEntity>>();
41 final Map<OutputUnit, Set<LibraryElement>> outputLibraryLists = 42 final Map<OutputUnit, Set<LibraryEntity>> outputLibraryLists =
42 new Map<OutputUnit, Set<LibraryElement>>(); 43 new Map<OutputUnit, Set<LibraryEntity>>();
43 44
44 /// True, if the output contains a constant list. 45 /// True, if the output contains a constant list.
45 /// 46 ///
46 /// This flag is updated in [computeNeededConstants]. 47 /// This flag is updated in [computeNeededConstants].
47 bool outputContainsConstantList = false; 48 bool outputContainsConstantList = false;
48 49
49 final List<ClassElement> nativeClassesAndSubclasses = <ClassElement>[]; 50 final List<ClassElement> nativeClassesAndSubclasses = <ClassElement>[];
50 51
51 List<TypedefElement> typedefsNeededForReflection; 52 List<TypedefElement> typedefsNeededForReflection;
52 53
53 Collector( 54 Collector(
54 this._options, 55 this._options,
55 this._commonElements, 56 this._commonElements,
56 this._deferredLoadTask, 57 this._deferredLoadTask,
57 this._worldBuilder, 58 this._worldBuilder,
58 this._namer, 59 this._namer,
59 this._emitter, 60 this._emitter,
60 this._constantHandler, 61 this._constantHandler,
61 this._nativeData, 62 this._nativeData,
62 this._interceptorData, 63 this._interceptorData,
63 this._oneShotInterceptorData, 64 this._oneShotInterceptorData,
64 this._mirrorsData, 65 this._mirrorsData,
65 this._closedWorld, 66 this._closedWorld,
66 this._rtiNeededClasses, 67 this._rtiNeededClasses,
67 this._generatedCode); 68 this._generatedCode,
69 this._sorter);
68 70
69 Set<ClassElement> computeInterceptorsReferencedFromConstants() { 71 Set<ClassElement> computeInterceptorsReferencedFromConstants() {
70 Set<ClassElement> classes = new Set<ClassElement>(); 72 Set<ClassElement> classes = new Set<ClassElement>();
71 JavaScriptConstantCompiler handler = _constantHandler; 73 JavaScriptConstantCompiler handler = _constantHandler;
72 List<ConstantValue> constants = handler.getConstantsForEmission(); 74 List<ConstantValue> constants = handler.getConstantsForEmission();
73 for (ConstantValue constant in constants) { 75 for (ConstantValue constant in constants) {
74 if (constant is InterceptorConstantValue) { 76 if (constant is InterceptorConstantValue) {
75 InterceptorConstantValue interceptorConstant = constant; 77 InterceptorConstantValue interceptorConstant = constant;
76 classes.add(interceptorConstant.cls); 78 classes.add(interceptorConstant.cls);
77 } 79 }
(...skipping 186 matching lines...) Expand 10 before | Expand all | Expand 10 after
264 neededClasses.add(_commonElements.stringClass); 266 neededClasses.add(_commonElements.stringClass);
265 } 267 }
266 if (neededClasses.contains(_commonElements.jsBoolClass)) { 268 if (neededClasses.contains(_commonElements.jsBoolClass)) {
267 neededClasses.add(_commonElements.boolClass); 269 neededClasses.add(_commonElements.boolClass);
268 } 270 }
269 if (neededClasses.contains(_commonElements.jsArrayClass)) { 271 if (neededClasses.contains(_commonElements.jsArrayClass)) {
270 neededClasses.add(_commonElements.listClass); 272 neededClasses.add(_commonElements.listClass);
271 } 273 }
272 274
273 // 4. Finally, sort the classes. 275 // 4. Finally, sort the classes.
274 List<ClassElement> sortedClasses = Elements.sortedByPosition(neededClasses); 276 List<ClassEntity> sortedClasses = _sorter.sortClasses(neededClasses);
275 277
276 for (ClassElement element in sortedClasses) { 278 for (ClassEntity cls in sortedClasses) {
277 if (_nativeData.isNativeOrExtendsNative(element) && 279 if (_nativeData.isNativeOrExtendsNative(cls) &&
278 !classesOnlyNeededForRti.contains(element)) { 280 !classesOnlyNeededForRti.contains(cls)) {
279 // For now, native classes and related classes cannot be deferred. 281 // For now, native classes and related classes cannot be deferred.
280 nativeClassesAndSubclasses.add(element); 282 nativeClassesAndSubclasses.add(cls);
281 assert(invariant(element, !_deferredLoadTask.isDeferred(element))); 283 assert(invariant(cls, !_deferredLoadTask.isDeferredClass(cls)));
282 outputClassLists 284 outputClassLists
283 .putIfAbsent(_deferredLoadTask.mainOutputUnit, 285 .putIfAbsent(_deferredLoadTask.mainOutputUnit,
284 () => new List<ClassElement>()) 286 () => new List<ClassElement>())
285 .add(element); 287 .add(cls);
286 } else { 288 } else {
287 outputClassLists 289 outputClassLists
288 .putIfAbsent(_deferredLoadTask.outputUnitForElement(element), 290 .putIfAbsent(_deferredLoadTask.outputUnitForClass(cls),
289 () => new List<ClassElement>()) 291 () => new List<ClassElement>())
290 .add(element); 292 .add(cls);
291 } 293 }
292 } 294 }
293 } 295 }
294 296
295 void computeNeededStatics() { 297 void computeNeededStatics() {
296 bool isStaticFunction(MemberElement element) => 298 bool isStaticFunction(MemberEntity element) =>
297 !element.isInstanceMember && !element.isField; 299 !element.isInstanceMember && !element.isField;
298 300
299 Iterable<MemberElement> elements = 301 Iterable<MemberEntity> elements =
300 _generatedCode.keys.where(isStaticFunction); 302 _generatedCode.keys.where(isStaticFunction);
301 303
302 for (Element element in Elements.sortedByPosition(elements)) { 304 for (MemberEntity member in _sorter.sortMembers(elements)) {
303 List<Element> list = outputStaticLists.putIfAbsent( 305 List<MemberEntity> list = outputStaticLists.putIfAbsent(
304 _deferredLoadTask.outputUnitForElement(element), 306 _deferredLoadTask.outputUnitForMember(member),
305 () => new List<Element>()); 307 () => new List<MemberEntity>());
306 list.add(element); 308 list.add(member);
307 } 309 }
308 } 310 }
309 311
310 void computeNeededStaticNonFinalFields() { 312 void computeNeededStaticNonFinalFields() {
311 addToOutputUnit(Element element) { 313 addToOutputUnit(FieldEntity element) {
312 List<VariableElement> list = outputStaticNonFinalFieldLists.putIfAbsent( 314 List<FieldEntity> list = outputStaticNonFinalFieldLists.putIfAbsent(
313 _deferredLoadTask.outputUnitForElement(element), 315 // ignore: UNNECESSARY_CAST
314 () => new List<VariableElement>()); 316 _deferredLoadTask.outputUnitForMember(element as MemberEntity),
317 () => new List<FieldEntity>());
315 list.add(element); 318 list.add(element);
316 } 319 }
317 320
318 Iterable<FieldElement> fields = 321 Iterable<FieldEntity> fields =
319 // TODO(johnniwinther): This should be accessed from a codegen closed 322 // TODO(johnniwinther): This should be accessed from a codegen closed
320 // world. 323 // world.
321 _worldBuilder.allReferencedStaticFields.where((FieldElement field) { 324 _worldBuilder.allReferencedStaticFields.where((FieldElement field) {
322 if (!field.isConst) { 325 if (!field.isConst) {
323 return field.isField && 326 return field.isField &&
324 !field.isInstanceMember && 327 !field.isInstanceMember &&
325 !field.isFinal && 328 !field.isFinal &&
326 field.constant != null; 329 field.constant != null;
327 } else { 330 } else {
328 // We also need to emit static const fields if they are available for 331 // We also need to emit static const fields if they are available for
329 // reflection. 332 // reflection.
330 return _mirrorsData.isMemberAccessibleByReflection(field); 333 return _mirrorsData.isMemberAccessibleByReflection(field);
331 } 334 }
332 }); 335 });
333 336
334 Elements.sortedByPosition(fields).forEach(addToOutputUnit); 337 _sorter.sortMembers(fields).forEach(addToOutputUnit);
335 } 338 }
336 339
337 void computeNeededLibraries() { 340 void computeNeededLibraries() {
338 void addSurroundingLibraryToSet(Element element) { 341 _generatedCode.keys.forEach((MemberEntity element) {
339 OutputUnit unit = _deferredLoadTask.outputUnitForElement(element); 342 OutputUnit unit = _deferredLoadTask.outputUnitForMember(element);
340 LibraryElement library = element.library; 343 LibraryEntity library = element.library;
341 outputLibraryLists 344 outputLibraryLists
342 .putIfAbsent(unit, () => new Set<LibraryElement>()) 345 .putIfAbsent(unit, () => new Set<LibraryEntity>())
343 .add(library); 346 .add(library);
344 } 347 });
345 348 neededClasses.forEach((ClassEntity element) {
346 _generatedCode.keys.forEach(addSurroundingLibraryToSet); 349 OutputUnit unit = _deferredLoadTask.outputUnitForClass(element);
347 neededClasses.forEach(addSurroundingLibraryToSet); 350 LibraryEntity library = element.library;
351 outputLibraryLists
352 .putIfAbsent(unit, () => new Set<LibraryEntity>())
353 .add(library);
354 });
348 } 355 }
349 356
350 void collect() { 357 void collect() {
351 computeNeededDeclarations(); 358 computeNeededDeclarations();
352 computeNeededConstants(); 359 computeNeededConstants();
353 computeNeededStatics(); 360 computeNeededStatics();
354 computeNeededStaticNonFinalFields(); 361 computeNeededStaticNonFinalFields();
355 computeNeededLibraries(); 362 computeNeededLibraries();
356 } 363 }
357 } 364 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698