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

Side by Side Diff: pkg/compiler/lib/src/world.dart

Issue 1413613010: Normalize type masks to use the least upper instantiated subclass/type. (Closed) Base URL: https://github.com/dart-lang/sdk.git@master
Patch Set: Created 5 years, 1 month 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) 2012, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2012, 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 library dart2js.world; 5 library dart2js.world;
6 6
7 import 'closure.dart' show 7 import 'closure.dart' show
8 SynthesizedCallMethodElementX; 8 SynthesizedCallMethodElementX;
9 import 'common.dart'; 9 import 'common.dart';
10 import 'common/backend_api.dart' show 10 import 'common/backend_api.dart' show
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
55 55
56 /// The [ClassElement] for the [int] class defined in 'dart:core'. 56 /// The [ClassElement] for the [int] class defined in 'dart:core'.
57 ClassElement get intClass; 57 ClassElement get intClass;
58 58
59 /// The [ClassElement] for the [double] class defined in 'dart:core'. 59 /// The [ClassElement] for the [double] class defined in 'dart:core'.
60 ClassElement get doubleClass; 60 ClassElement get doubleClass;
61 61
62 /// The [ClassElement] for the [String] class defined in 'dart:core'. 62 /// The [ClassElement] for the [String] class defined in 'dart:core'.
63 ClassElement get stringClass; 63 ClassElement get stringClass;
64 64
65 /// Returns `true` if [cls] is instantiated. 65 /// Returns `true` if [cls] is either directly or indirectly instantiated.
66 bool isInstantiated(ClassElement cls); 66 bool isInstantiated(ClassElement cls);
67 67
68 /// Returns `true` if [cls] is directly instantiated.
69 bool isDirectlyInstantiated(ClassElement cls);
70
71 /// Returns `true` if [cls] is indirectly instantiated, that is through a
72 /// subclass.
73 bool isIndirectlyInstantiated(ClassElement cls);
74
68 /// Returns `true` if [cls] is implemented by an instantiated class. 75 /// Returns `true` if [cls] is implemented by an instantiated class.
69 bool isImplemented(ClassElement cls); 76 bool isImplemented(ClassElement cls);
70 77
71 /// Returns `true` if the class world is closed. 78 /// Returns `true` if the class world is closed.
72 bool get isClosed; 79 bool get isClosed;
73 80
74 /// Return `true` if [x] is a subclass of [y]. 81 /// Return `true` if [x] is a subclass of [y].
75 bool isSubclassOf(ClassElement x, ClassElement y); 82 bool isSubclassOf(ClassElement x, ClassElement y);
76 83
77 /// Returns `true` if [x] is a subtype of [y], that is, if [x] implements an 84 /// Returns `true` if [x] is a subtype of [y], that is, if [x] implements an
(...skipping 21 matching lines...) Expand all
99 106
100 /// Returns `true` if any live class other than [cls] extends [cls]. 107 /// Returns `true` if any live class other than [cls] extends [cls].
101 bool hasAnyStrictSubclass(ClassElement cls); 108 bool hasAnyStrictSubclass(ClassElement cls);
102 109
103 /// Returns `true` if any live class other than [cls] implements [cls]. 110 /// Returns `true` if any live class other than [cls] implements [cls].
104 bool hasAnyStrictSubtype(ClassElement cls); 111 bool hasAnyStrictSubtype(ClassElement cls);
105 112
106 /// Returns `true` if all live classes that implement [cls] extend it. 113 /// Returns `true` if all live classes that implement [cls] extend it.
107 bool hasOnlySubclasses(ClassElement cls); 114 bool hasOnlySubclasses(ClassElement cls);
108 115
116 /// Returns the most specific subclass of [cls] (including [cls]) that is
117 /// directly instantiated or a superclass of all directly instantiated
118 /// subclasses. If [cls] is not instantiated, `null` is returned.
119 ClassElement getLeastUpperInstantiatedSubclass(ClassElement cls);
120
121 /// Returns the most specific subtype of [cls] (including [cls]) that is
122 /// directly instantiated or a superclass of all directly instantiated
123 /// subtypes. If no subtypes of [cls] are instantiated, `null` is returned.
124 ClassElement getLeastUpperInstantiatedSubtype(ClassElement cls);
125
109 /// Returns an iterable over the common supertypes of the [classes]. 126 /// Returns an iterable over the common supertypes of the [classes].
110 Iterable<ClassElement> commonSupertypesOf(Iterable<ClassElement> classes); 127 Iterable<ClassElement> commonSupertypesOf(Iterable<ClassElement> classes);
111 128
112 /// Returns an iterable over the live mixin applications that mixin [cls]. 129 /// Returns an iterable over the live mixin applications that mixin [cls].
113 Iterable<MixinApplicationElement> mixinUsesOf(ClassElement cls); 130 Iterable<MixinApplicationElement> mixinUsesOf(ClassElement cls);
114 131
115 /// Returns `true` if [cls] is mixed into a live class. 132 /// Returns `true` if [cls] is mixed into a live class.
116 bool isUsedAsMixin(ClassElement cls); 133 bool isUsedAsMixin(ClassElement cls);
117 134
118 /// Returns `true` if any live class that mixes in [cls] implements [type]. 135 /// Returns `true` if any live class that mixes in [cls] implements [type].
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after
183 200
184 if (y == objectClass) return true; 201 if (y == objectClass) return true;
185 if (x == objectClass) return false; 202 if (x == objectClass) return false;
186 while (x != null && x.hierarchyDepth >= y.hierarchyDepth) { 203 while (x != null && x.hierarchyDepth >= y.hierarchyDepth) {
187 if (x == y) return true; 204 if (x == y) return true;
188 x = x.superclass; 205 x = x.superclass;
189 } 206 }
190 return false; 207 return false;
191 } 208 }
192 209
193 /// Returns `true` if [cls] is instantiated either directly or through a 210 @override
194 /// subclass.
195 bool isInstantiated(ClassElement cls) { 211 bool isInstantiated(ClassElement cls) {
196 return compiler.resolverWorld.isInstantiated(cls); 212 ClassHierarchyNode node = _classHierarchyNodes[cls.declaration];
213 return node != null && node.isInstantiated;
214 }
215
216 @override
217 bool isDirectlyInstantiated(ClassElement cls) {
218 ClassHierarchyNode node = _classHierarchyNodes[cls.declaration];
219 return node != null && node.isDirectlyInstantiated;
220 }
221
222 @override
223 bool isIndirectlyInstantiated(ClassElement cls) {
224 ClassHierarchyNode node = _classHierarchyNodes[cls.declaration];
225 return node != null && node.isIndirectlyInstantiated;
197 } 226 }
198 227
199 /// Returns `true` if [cls] is implemented by an instantiated class. 228 /// Returns `true` if [cls] is implemented by an instantiated class.
200 bool isImplemented(ClassElement cls) { 229 bool isImplemented(ClassElement cls) {
201 return compiler.resolverWorld.isImplemented(cls); 230 return compiler.resolverWorld.isImplemented(cls);
202 } 231 }
203 232
204 /// Returns an iterable over the directly instantiated classes that extend 233 /// Returns an iterable over the directly instantiated classes that extend
205 /// [cls] possibly including [cls] itself, if it is live. 234 /// [cls] possibly including [cls] itself, if it is live.
206 Iterable<ClassElement> subclassesOf(ClassElement cls) { 235 Iterable<ClassElement> subclassesOf(ClassElement cls) {
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after
280 309
281 /// Returns `true` if all directly instantiated classes that implement [cls] 310 /// Returns `true` if all directly instantiated classes that implement [cls]
282 /// extend it. 311 /// extend it.
283 bool hasOnlySubclasses(ClassElement cls) { 312 bool hasOnlySubclasses(ClassElement cls) {
284 Iterable<ClassElement> subtypes = strictSubtypesOf(cls); 313 Iterable<ClassElement> subtypes = strictSubtypesOf(cls);
285 if (subtypes == null) return true; 314 if (subtypes == null) return true;
286 Iterable<ClassElement> subclasses = strictSubclassesOf(cls); 315 Iterable<ClassElement> subclasses = strictSubclassesOf(cls);
287 return subclasses != null && (subclasses.length == subtypes.length); 316 return subclasses != null && (subclasses.length == subtypes.length);
288 } 317 }
289 318
319 @override
320 ClassElement getLeastUpperInstantiatedSubclass(ClassElement cls) {
321 ClassHierarchyNode hierarchy = _classHierarchyNodes[cls.declaration];
322 return hierarchy != null
323 ? hierarchy.getLeastUpperInstantiatedSubclass() : null;
324 }
325
326 @override
327 ClassElement getLeastUpperInstantiatedSubtype(ClassElement cls) {
328 ClassSet classSet = _classSets[cls.declaration];
329 return classSet != null
330 ? classSet.getLeastUpperInstantiatedSubtype() : null;
331 }
332
290 /// Returns an iterable over the common supertypes of the [classes]. 333 /// Returns an iterable over the common supertypes of the [classes].
291 Iterable<ClassElement> commonSupertypesOf(Iterable<ClassElement> classes) { 334 Iterable<ClassElement> commonSupertypesOf(Iterable<ClassElement> classes) {
292 Iterator<ClassElement> iterator = classes.iterator; 335 Iterator<ClassElement> iterator = classes.iterator;
293 if (!iterator.moveNext()) return const <ClassElement>[]; 336 if (!iterator.moveNext()) return const <ClassElement>[];
294 337
295 ClassElement cls = iterator.current; 338 ClassElement cls = iterator.current;
296 assert(checkInvariants(cls)); 339 assert(checkInvariants(cls));
297 OrderedTypeSet typeSet = cls.allSupertypesAndSelf; 340 OrderedTypeSet typeSet = cls.allSupertypesAndSelf;
298 if (!iterator.moveNext()) return typeSet.types.map((type) => type.element); 341 if (!iterator.moveNext()) return typeSet.types.map((type) => type.element);
299 342
(...skipping 192 matching lines...) Expand 10 before | Expand all | Expand 10 after
492 }); 535 });
493 } 536 }
494 537
495 void populate() { 538 void populate() {
496 /// Updates the `isDirectlyInstantiated` and `isIndirectlyInstantiated` 539 /// Updates the `isDirectlyInstantiated` and `isIndirectlyInstantiated`
497 /// properties of the [ClassHierarchyNode] for [cls]. 540 /// properties of the [ClassHierarchyNode] for [cls].
498 void updateClassHierarchyNodeForClass( 541 void updateClassHierarchyNodeForClass(
499 ClassElement cls, 542 ClassElement cls,
500 {bool directlyInstantiated: false, 543 {bool directlyInstantiated: false,
501 bool indirectlyInstantiated: false}) { 544 bool indirectlyInstantiated: false}) {
502 assert(!directlyInstantiated || isInstantiated(cls));
503 ClassHierarchyNode node = getClassHierarchyNode(cls); 545 ClassHierarchyNode node = getClassHierarchyNode(cls);
504 bool changed = false; 546 bool changed = false;
505 if (directlyInstantiated && !node.isDirectlyInstantiated) { 547 if (directlyInstantiated && !node.isDirectlyInstantiated) {
506 node.isDirectlyInstantiated = true; 548 node.isDirectlyInstantiated = true;
507 changed = true; 549 changed = true;
508 } 550 }
509 if (indirectlyInstantiated && !node.isIndirectlyInstantiated) { 551 if (indirectlyInstantiated && !node.isIndirectlyInstantiated) {
510 node.isIndirectlyInstantiated = true; 552 node.isIndirectlyInstantiated = true;
511 changed = true; 553 changed = true;
512 } 554 }
513 if (changed && cls.superclass != null) { 555 if (changed && cls.superclass != null) {
514 updateClassHierarchyNodeForClass( 556 updateClassHierarchyNodeForClass(
515 cls.superclass, indirectlyInstantiated: true); 557 cls.superclass, indirectlyInstantiated: true);
516 } 558 }
559 // Ensure that classes implicitly implementing `Function` are in its
560 // subtype set.
561 if (cls != coreClasses.functionClass &&
562 cls.implementsFunction(compiler)) {
563 ClassSet subtypeSet = _ensureClassSet(coreClasses.functionClass);
564 subtypeSet.addSubtype(node);
565 }
517 } 566 }
518 567
519 void addSubtypes(ClassElement cls) { 568 void addSubtypes(ClassElement cls) {
520 if (compiler.hasIncrementalSupport && !alreadyPopulated.add(cls)) { 569 if (compiler.hasIncrementalSupport && !alreadyPopulated.add(cls)) {
521 return; 570 return;
522 } 571 }
523 assert(cls.isDeclaration); 572 assert(cls.isDeclaration);
524 if (!cls.isResolved) { 573 if (!cls.isResolved) {
525 reporter.internalError(cls, 'Class "${cls.name}" is not resolved.'); 574 reporter.internalError(cls, 'Class "${cls.name}" is not resolved.');
526 } 575 }
(...skipping 169 matching lines...) Expand 10 before | Expand all | Expand 10 after
696 // function expressions's element. 745 // function expressions's element.
697 // TODO(herhut): Generate classes for function expressions earlier. 746 // TODO(herhut): Generate classes for function expressions earlier.
698 if (element is SynthesizedCallMethodElementX) { 747 if (element is SynthesizedCallMethodElementX) {
699 return getMightBePassedToApply(element.expression); 748 return getMightBePassedToApply(element.expression);
700 } 749 }
701 return functionsThatMightBePassedToApply.contains(element); 750 return functionsThatMightBePassedToApply.contains(element);
702 } 751 }
703 752
704 bool get hasClosedWorldAssumption => !compiler.hasIncrementalSupport; 753 bool get hasClosedWorldAssumption => !compiler.hasIncrementalSupport;
705 } 754 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698