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

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

Issue 1859343004: dartfmt pkg/compiler (Closed) Base URL: git@github.com:dart-lang/sdk.git@master
Patch Set: Created 4 years, 8 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) 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 SynthesizedCallMethodElementX;
8 SynthesizedCallMethodElementX;
9 import 'common.dart'; 8 import 'common.dart';
10 import 'common/backend_api.dart' show 9 import 'common/backend_api.dart' show Backend;
11 Backend; 10 import 'compiler.dart' show Compiler;
12 import 'compiler.dart' show 11 import 'core_types.dart' show CoreClasses;
13 Compiler;
14 import 'core_types.dart' show
15 CoreClasses;
16 import 'dart_types.dart'; 12 import 'dart_types.dart';
17 import 'elements/elements.dart' show 13 import 'elements/elements.dart'
18 ClassElement, 14 show
19 Element, 15 ClassElement,
20 FunctionElement, 16 Element,
21 MixinApplicationElement, 17 FunctionElement,
22 TypedefElement, 18 MixinApplicationElement,
23 VariableElement; 19 TypedefElement,
20 VariableElement;
24 import 'ordered_typeset.dart'; 21 import 'ordered_typeset.dart';
25 import 'types/types.dart' as ti; 22 import 'types/types.dart' as ti;
26 import 'universe/class_set.dart'; 23 import 'universe/class_set.dart';
27 import 'universe/function_set.dart' show 24 import 'universe/function_set.dart' show FunctionSet;
28 FunctionSet; 25 import 'universe/selector.dart' show Selector;
29 import 'universe/selector.dart' show 26 import 'universe/side_effects.dart' show SideEffects;
30 Selector; 27 import 'util/util.dart' show Link;
31 import 'universe/side_effects.dart' show
32 SideEffects;
33 import 'util/util.dart' show
34 Link;
35 28
36 abstract class ClassWorld { 29 abstract class ClassWorld {
37 // TODO(johnniwinther): Refine this into a `BackendClasses` interface. 30 // TODO(johnniwinther): Refine this into a `BackendClasses` interface.
38 Backend get backend; 31 Backend get backend;
39 32
40 // TODO(johnniwinther): Remove the need for this getter. 33 // TODO(johnniwinther): Remove the need for this getter.
41 @deprecated 34 @deprecated
42 Compiler get compiler; 35 Compiler get compiler;
43 36
44 /// The [ClassElement] for the [Object] class defined in 'dart:core'. 37 /// The [ClassElement] for the [Object] class defined in 'dart:core'.
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after
92 /// Returns an iterable over the live classes that extend [cls] _not_ 85 /// Returns an iterable over the live classes that extend [cls] _not_
93 /// including [cls] itself. 86 /// including [cls] itself.
94 Iterable<ClassElement> strictSubclassesOf(ClassElement cls); 87 Iterable<ClassElement> strictSubclassesOf(ClassElement cls);
95 88
96 /// Returns the number of live classes that extend [cls] _not_ 89 /// Returns the number of live classes that extend [cls] _not_
97 /// including [cls] itself. 90 /// including [cls] itself.
98 int strictSubclassCount(ClassElement cls); 91 int strictSubclassCount(ClassElement cls);
99 92
100 /// Applies [f] to each live class that extend [cls] _not_ including [cls] 93 /// Applies [f] to each live class that extend [cls] _not_ including [cls]
101 /// itself. 94 /// itself.
102 void forEachStrictSubclassOf(ClassElement cls, 95 void forEachStrictSubclassOf(
103 IterationStep f(ClassElement cls)); 96 ClassElement cls, IterationStep f(ClassElement cls));
104 97
105 /// Returns `true` if [predicate] applies to any live class that extend [cls] 98 /// Returns `true` if [predicate] applies to any live class that extend [cls]
106 /// _not_ including [cls] itself. 99 /// _not_ including [cls] itself.
107 bool anyStrictSubclassOf(ClassElement cls, bool predicate(ClassElement cls)); 100 bool anyStrictSubclassOf(ClassElement cls, bool predicate(ClassElement cls));
108 101
109 /// Returns an iterable over the directly instantiated that implement [cls] 102 /// Returns an iterable over the directly instantiated that implement [cls]
110 /// possibly including [cls] itself, if it is live. 103 /// possibly including [cls] itself, if it is live.
111 Iterable<ClassElement> subtypesOf(ClassElement cls); 104 Iterable<ClassElement> subtypesOf(ClassElement cls);
112 105
113 /// Returns an iterable over the live classes that implement [cls] _not_ 106 /// Returns an iterable over the live classes that implement [cls] _not_
114 /// including [cls] if it is live. 107 /// including [cls] if it is live.
115 Iterable<ClassElement> strictSubtypesOf(ClassElement cls); 108 Iterable<ClassElement> strictSubtypesOf(ClassElement cls);
116 109
117 /// Returns the number of live classes that implement [cls] _not_ 110 /// Returns the number of live classes that implement [cls] _not_
118 /// including [cls] itself. 111 /// including [cls] itself.
119 int strictSubtypeCount(ClassElement cls); 112 int strictSubtypeCount(ClassElement cls);
120 113
121 /// Applies [f] to each live class that implements [cls] _not_ including [cls] 114 /// Applies [f] to each live class that implements [cls] _not_ including [cls]
122 /// itself. 115 /// itself.
123 void forEachStrictSubtypeOf(ClassElement cls, 116 void forEachStrictSubtypeOf(
124 IterationStep f(ClassElement cls)); 117 ClassElement cls, IterationStep f(ClassElement cls));
125 118
126 /// Returns `true` if [predicate] applies to any live class that implements 119 /// Returns `true` if [predicate] applies to any live class that implements
127 /// [cls] _not_ including [cls] itself. 120 /// [cls] _not_ including [cls] itself.
128 bool anyStrictSubtypeOf(ClassElement cls, bool predicate(ClassElement cls)); 121 bool anyStrictSubtypeOf(ClassElement cls, bool predicate(ClassElement cls));
129 122
130 /// Returns `true` if [a] and [b] have any known common subtypes. 123 /// Returns `true` if [a] and [b] have any known common subtypes.
131 bool haveAnyCommonSubtypes(ClassElement a, ClassElement b); 124 bool haveAnyCommonSubtypes(ClassElement a, ClassElement b);
132 125
133 /// Returns `true` if any live class other than [cls] extends [cls]. 126 /// Returns `true` if any live class other than [cls] extends [cls].
134 bool hasAnyStrictSubclass(ClassElement cls); 127 bool hasAnyStrictSubclass(ClassElement cls);
(...skipping 17 matching lines...) Expand all
152 /// Returns an iterable over the common supertypes of the [classes]. 145 /// Returns an iterable over the common supertypes of the [classes].
153 Iterable<ClassElement> commonSupertypesOf(Iterable<ClassElement> classes); 146 Iterable<ClassElement> commonSupertypesOf(Iterable<ClassElement> classes);
154 147
155 /// Returns an iterable over the live mixin applications that mixin [cls]. 148 /// Returns an iterable over the live mixin applications that mixin [cls].
156 Iterable<MixinApplicationElement> mixinUsesOf(ClassElement cls); 149 Iterable<MixinApplicationElement> mixinUsesOf(ClassElement cls);
157 150
158 /// Returns `true` if [cls] is mixed into a live class. 151 /// Returns `true` if [cls] is mixed into a live class.
159 bool isUsedAsMixin(ClassElement cls); 152 bool isUsedAsMixin(ClassElement cls);
160 153
161 /// Returns `true` if any live class that mixes in [cls] implements [type]. 154 /// Returns `true` if any live class that mixes in [cls] implements [type].
162 bool hasAnySubclassOfMixinUseThatImplements(ClassElement cls, 155 bool hasAnySubclassOfMixinUseThatImplements(
163 ClassElement type); 156 ClassElement cls, ClassElement type);
164 157
165 /// Returns `true` if any live class that mixes in [mixin] is also a subclass 158 /// Returns `true` if any live class that mixes in [mixin] is also a subclass
166 /// of [superclass]. 159 /// of [superclass].
167 bool hasAnySubclassThatMixes(ClassElement superclass, ClassElement mixin); 160 bool hasAnySubclassThatMixes(ClassElement superclass, ClassElement mixin);
168 161
169 /// Returns `true` if any subclass of [superclass] implements [type]. 162 /// Returns `true` if any subclass of [superclass] implements [type].
170 bool hasAnySubclassThatImplements(ClassElement superclass, ClassElement type); 163 bool hasAnySubclassThatImplements(ClassElement superclass, ClassElement type);
171 164
172 /// Returns `true` if closed-world assumptions can be made, that is, 165 /// Returns `true` if closed-world assumptions can be made, that is,
173 /// incremental compilation isn't enabled. 166 /// incremental compilation isn't enabled.
(...skipping 14 matching lines...) Expand all
188 ClassElement get doubleClass => coreClasses.doubleClass; 181 ClassElement get doubleClass => coreClasses.doubleClass;
189 ClassElement get stringClass => coreClasses.stringClass; 182 ClassElement get stringClass => coreClasses.stringClass;
190 ClassElement get nullClass => coreClasses.nullClass; 183 ClassElement get nullClass => coreClasses.nullClass;
191 184
192 /// Cache of [ti.FlatTypeMask]s grouped by the 8 possible values of the 185 /// Cache of [ti.FlatTypeMask]s grouped by the 8 possible values of the
193 /// [ti.FlatTypeMask.flags] property. 186 /// [ti.FlatTypeMask.flags] property.
194 List<Map<ClassElement, ti.TypeMask>> canonicalizedTypeMasks = 187 List<Map<ClassElement, ti.TypeMask>> canonicalizedTypeMasks =
195 new List<Map<ClassElement, ti.TypeMask>>.filled(8, null); 188 new List<Map<ClassElement, ti.TypeMask>>.filled(8, null);
196 189
197 bool checkInvariants(ClassElement cls, {bool mustBeInstantiated: true}) { 190 bool checkInvariants(ClassElement cls, {bool mustBeInstantiated: true}) {
198 return 191 return invariant(cls, cls.isDeclaration,
199 invariant(cls, cls.isDeclaration,
200 message: '$cls must be the declaration.') && 192 message: '$cls must be the declaration.') &&
201 invariant(cls, cls.isResolved, 193 invariant(cls, cls.isResolved,
202 message: '$cls must be resolved.')/* && 194 message:
195 '$cls must be resolved.') /* &&
203 // TODO(johnniwinther): Reinsert this or similar invariant. 196 // TODO(johnniwinther): Reinsert this or similar invariant.
204 (!mustBeInstantiated || 197 (!mustBeInstantiated ||
205 invariant(cls, isInstantiated(cls), 198 invariant(cls, isInstantiated(cls),
206 message: '$cls is not instantiated.'))*/; 199 message: '$cls is not instantiated.'))*/
207 } 200 ;
201 }
208 202
209 /// Returns `true` if [x] is a subtype of [y], that is, if [x] implements an 203 /// Returns `true` if [x] is a subtype of [y], that is, if [x] implements an
210 /// instance of [y]. 204 /// instance of [y].
211 bool isSubtypeOf(ClassElement x, ClassElement y) { 205 bool isSubtypeOf(ClassElement x, ClassElement y) {
212 assert(checkInvariants(x)); 206 assert(checkInvariants(x));
213 assert(checkInvariants(y, mustBeInstantiated: false)); 207 assert(checkInvariants(y, mustBeInstantiated: false));
214 208
215 if (y == objectClass) return true; 209 if (y == objectClass) return true;
216 if (x == objectClass) return false; 210 if (x == objectClass) return false;
217 if (x.asInstanceOf(y) != null) return true; 211 if (x.asInstanceOf(y) != null) return true;
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
254 /// Returns `true` if [cls] is implemented by an instantiated class. 248 /// Returns `true` if [cls] is implemented by an instantiated class.
255 bool isImplemented(ClassElement cls) { 249 bool isImplemented(ClassElement cls) {
256 return compiler.resolverWorld.isImplemented(cls); 250 return compiler.resolverWorld.isImplemented(cls);
257 } 251 }
258 252
259 /// Returns an iterable over the directly instantiated classes that extend 253 /// Returns an iterable over the directly instantiated classes that extend
260 /// [cls] possibly including [cls] itself, if it is live. 254 /// [cls] possibly including [cls] itself, if it is live.
261 Iterable<ClassElement> subclassesOf(ClassElement cls) { 255 Iterable<ClassElement> subclassesOf(ClassElement cls) {
262 ClassHierarchyNode hierarchy = _classHierarchyNodes[cls.declaration]; 256 ClassHierarchyNode hierarchy = _classHierarchyNodes[cls.declaration];
263 if (hierarchy == null) return const <ClassElement>[]; 257 if (hierarchy == null) return const <ClassElement>[];
264 return hierarchy.subclassesByMask( 258 return hierarchy.subclassesByMask(ClassHierarchyNode.DIRECTLY_INSTANTIATED);
265 ClassHierarchyNode.DIRECTLY_INSTANTIATED);
266 } 259 }
267 260
268 /// Returns an iterable over the directly instantiated classes that extend 261 /// Returns an iterable over the directly instantiated classes that extend
269 /// [cls] _not_ including [cls] itself. 262 /// [cls] _not_ including [cls] itself.
270 Iterable<ClassElement> strictSubclassesOf(ClassElement cls) { 263 Iterable<ClassElement> strictSubclassesOf(ClassElement cls) {
271 ClassHierarchyNode subclasses = _classHierarchyNodes[cls.declaration]; 264 ClassHierarchyNode subclasses = _classHierarchyNodes[cls.declaration];
272 if (subclasses == null) return const <ClassElement>[]; 265 if (subclasses == null) return const <ClassElement>[];
273 return subclasses.subclassesByMask( 266 return subclasses.subclassesByMask(ClassHierarchyNode.DIRECTLY_INSTANTIATED,
274 ClassHierarchyNode.DIRECTLY_INSTANTIATED, strict: true); 267 strict: true);
275 } 268 }
276 269
277 /// Returns the number of live classes that extend [cls] _not_ 270 /// Returns the number of live classes that extend [cls] _not_
278 /// including [cls] itself. 271 /// including [cls] itself.
279 int strictSubclassCount(ClassElement cls) { 272 int strictSubclassCount(ClassElement cls) {
280 ClassHierarchyNode subclasses = _classHierarchyNodes[cls.declaration]; 273 ClassHierarchyNode subclasses = _classHierarchyNodes[cls.declaration];
281 if (subclasses == null) return 0; 274 if (subclasses == null) return 0;
282 return subclasses.instantiatedSubclassCount; 275 return subclasses.instantiatedSubclassCount;
283 } 276 }
284 277
285 /// Applies [f] to each live class that extend [cls] _not_ including [cls] 278 /// Applies [f] to each live class that extend [cls] _not_ including [cls]
286 /// itself. 279 /// itself.
287 void forEachStrictSubclassOf(ClassElement cls, 280 void forEachStrictSubclassOf(
288 IterationStep f(ClassElement cls)) { 281 ClassElement cls, IterationStep f(ClassElement cls)) {
289 ClassHierarchyNode subclasses = _classHierarchyNodes[cls.declaration]; 282 ClassHierarchyNode subclasses = _classHierarchyNodes[cls.declaration];
290 if (subclasses == null) return; 283 if (subclasses == null) return;
291 subclasses.forEachSubclass( 284 subclasses.forEachSubclass(f, ClassHierarchyNode.DIRECTLY_INSTANTIATED,
292 f,
293 ClassHierarchyNode.DIRECTLY_INSTANTIATED,
294 strict: true); 285 strict: true);
295 } 286 }
296 287
297 /// Returns `true` if [predicate] applies to any live class that extend [cls] 288 /// Returns `true` if [predicate] applies to any live class that extend [cls]
298 /// _not_ including [cls] itself. 289 /// _not_ including [cls] itself.
299 bool anyStrictSubclassOf(ClassElement cls, bool predicate(ClassElement cls)) { 290 bool anyStrictSubclassOf(ClassElement cls, bool predicate(ClassElement cls)) {
300 ClassHierarchyNode subclasses = _classHierarchyNodes[cls.declaration]; 291 ClassHierarchyNode subclasses = _classHierarchyNodes[cls.declaration];
301 if (subclasses == null) return false; 292 if (subclasses == null) return false;
302 return subclasses.anySubclass( 293 return subclasses.anySubclass(
303 predicate, 294 predicate, ClassHierarchyNode.DIRECTLY_INSTANTIATED,
304 ClassHierarchyNode.DIRECTLY_INSTANTIATED,
305 strict: true); 295 strict: true);
306 } 296 }
307 297
308 /// Returns an iterable over the directly instantiated that implement [cls] 298 /// Returns an iterable over the directly instantiated that implement [cls]
309 /// possibly including [cls] itself, if it is live. 299 /// possibly including [cls] itself, if it is live.
310 Iterable<ClassElement> subtypesOf(ClassElement cls) { 300 Iterable<ClassElement> subtypesOf(ClassElement cls) {
311 ClassSet classSet = _classSets[cls.declaration]; 301 ClassSet classSet = _classSets[cls.declaration];
312 if (classSet == null) { 302 if (classSet == null) {
313 return const <ClassElement>[]; 303 return const <ClassElement>[];
314 } else { 304 } else {
315 return classSet.subtypesByMask(ClassHierarchyNode.DIRECTLY_INSTANTIATED); 305 return classSet.subtypesByMask(ClassHierarchyNode.DIRECTLY_INSTANTIATED);
316 } 306 }
317 } 307 }
318 308
319 /// Returns an iterable over the directly instantiated that implement [cls] 309 /// Returns an iterable over the directly instantiated that implement [cls]
320 /// _not_ including [cls]. 310 /// _not_ including [cls].
321 Iterable<ClassElement> strictSubtypesOf(ClassElement cls) { 311 Iterable<ClassElement> strictSubtypesOf(ClassElement cls) {
322 ClassSet classSet = _classSets[cls.declaration]; 312 ClassSet classSet = _classSets[cls.declaration];
323 if (classSet == null) { 313 if (classSet == null) {
324 return const <ClassElement>[]; 314 return const <ClassElement>[];
325 } else { 315 } else {
326 return classSet.subtypesByMask( 316 return classSet.subtypesByMask(ClassHierarchyNode.DIRECTLY_INSTANTIATED,
327 ClassHierarchyNode.DIRECTLY_INSTANTIATED,
328 strict: true); 317 strict: true);
329 } 318 }
330 } 319 }
331 320
332 /// Returns the number of live classes that implement [cls] _not_ 321 /// Returns the number of live classes that implement [cls] _not_
333 /// including [cls] itself. 322 /// including [cls] itself.
334 int strictSubtypeCount(ClassElement cls) { 323 int strictSubtypeCount(ClassElement cls) {
335 ClassSet classSet = _classSets[cls.declaration]; 324 ClassSet classSet = _classSets[cls.declaration];
336 if (classSet == null) return 0; 325 if (classSet == null) return 0;
337 return classSet.instantiatedSubtypeCount; 326 return classSet.instantiatedSubtypeCount;
338 } 327 }
339 328
340 /// Applies [f] to each live class that implements [cls] _not_ including [cls] 329 /// Applies [f] to each live class that implements [cls] _not_ including [cls]
341 /// itself. 330 /// itself.
342 void forEachStrictSubtypeOf(ClassElement cls, 331 void forEachStrictSubtypeOf(
343 IterationStep f(ClassElement cls)) { 332 ClassElement cls, IterationStep f(ClassElement cls)) {
344 ClassSet classSet = _classSets[cls.declaration]; 333 ClassSet classSet = _classSets[cls.declaration];
345 if (classSet == null) return; 334 if (classSet == null) return;
346 classSet.forEachSubtype( 335 classSet.forEachSubtype(f, ClassHierarchyNode.DIRECTLY_INSTANTIATED,
347 f,
348 ClassHierarchyNode.DIRECTLY_INSTANTIATED,
349 strict: true); 336 strict: true);
350 } 337 }
351 338
352 /// Returns `true` if [predicate] applies to any live class that extend [cls] 339 /// Returns `true` if [predicate] applies to any live class that extend [cls]
353 /// _not_ including [cls] itself. 340 /// _not_ including [cls] itself.
354 bool anyStrictSubtypeOf(ClassElement cls, bool predicate(ClassElement cls)) { 341 bool anyStrictSubtypeOf(ClassElement cls, bool predicate(ClassElement cls)) {
355 ClassSet classSet = _classSets[cls.declaration]; 342 ClassSet classSet = _classSets[cls.declaration];
356 if (classSet == null) return false; 343 if (classSet == null) return false;
357 return classSet.anySubtype( 344 return classSet.anySubtype(
358 predicate, 345 predicate, ClassHierarchyNode.DIRECTLY_INSTANTIATED,
359 ClassHierarchyNode.DIRECTLY_INSTANTIATED,
360 strict: true); 346 strict: true);
361 } 347 }
362 348
363 /// Returns `true` if [a] and [b] have any known common subtypes. 349 /// Returns `true` if [a] and [b] have any known common subtypes.
364 bool haveAnyCommonSubtypes(ClassElement a, ClassElement b) { 350 bool haveAnyCommonSubtypes(ClassElement a, ClassElement b) {
365 ClassSet classSetA = _classSets[a.declaration]; 351 ClassSet classSetA = _classSets[a.declaration];
366 ClassSet classSetB = _classSets[b.declaration]; 352 ClassSet classSetB = _classSets[b.declaration];
367 if (classSetA == null || classSetB == null) return false; 353 if (classSetA == null || classSetB == null) return false;
368 // TODO(johnniwinther): Implement an optimized query on [ClassSet]. 354 // TODO(johnniwinther): Implement an optimized query on [ClassSet].
369 Set<ClassElement> subtypesOfB = classSetB.subtypes().toSet(); 355 Set<ClassElement> subtypesOfB = classSetB.subtypes().toSet();
(...skipping 29 matching lines...) Expand all
399 // Vacuously true. 385 // Vacuously true.
400 return true; 386 return true;
401 } 387 }
402 return classSet.hasOnlyInstantiatedSubclasses; 388 return classSet.hasOnlyInstantiatedSubclasses;
403 } 389 }
404 390
405 @override 391 @override
406 ClassElement getLubOfInstantiatedSubclasses(ClassElement cls) { 392 ClassElement getLubOfInstantiatedSubclasses(ClassElement cls) {
407 ClassHierarchyNode hierarchy = _classHierarchyNodes[cls.declaration]; 393 ClassHierarchyNode hierarchy = _classHierarchyNodes[cls.declaration];
408 return hierarchy != null 394 return hierarchy != null
409 ? hierarchy.getLubOfInstantiatedSubclasses() : null; 395 ? hierarchy.getLubOfInstantiatedSubclasses()
396 : null;
410 } 397 }
411 398
412 @override 399 @override
413 ClassElement getLubOfInstantiatedSubtypes(ClassElement cls) { 400 ClassElement getLubOfInstantiatedSubtypes(ClassElement cls) {
414 ClassSet classSet = _classSets[cls.declaration]; 401 ClassSet classSet = _classSets[cls.declaration];
415 return classSet != null 402 return classSet != null ? classSet.getLubOfInstantiatedSubtypes() : null;
416 ? classSet.getLubOfInstantiatedSubtypes() : null;
417 } 403 }
418 404
419 /// Returns an iterable over the common supertypes of the [classes]. 405 /// Returns an iterable over the common supertypes of the [classes].
420 Iterable<ClassElement> commonSupertypesOf(Iterable<ClassElement> classes) { 406 Iterable<ClassElement> commonSupertypesOf(Iterable<ClassElement> classes) {
421 Iterator<ClassElement> iterator = classes.iterator; 407 Iterator<ClassElement> iterator = classes.iterator;
422 if (!iterator.moveNext()) return const <ClassElement>[]; 408 if (!iterator.moveNext()) return const <ClassElement>[];
423 409
424 ClassElement cls = iterator.current; 410 ClassElement cls = iterator.current;
425 assert(checkInvariants(cls)); 411 assert(checkInvariants(cls));
426 OrderedTypeSet typeSet = cls.allSupertypesAndSelf; 412 OrderedTypeSet typeSet = cls.allSupertypesAndSelf;
427 if (!iterator.moveNext()) return typeSet.types.map((type) => type.element); 413 if (!iterator.moveNext()) return typeSet.types.map((type) => type.element);
428 414
429 int depth = typeSet.maxDepth; 415 int depth = typeSet.maxDepth;
430 Link<OrderedTypeSet> otherTypeSets = const Link<OrderedTypeSet>(); 416 Link<OrderedTypeSet> otherTypeSets = const Link<OrderedTypeSet>();
431 do { 417 do {
432 ClassElement otherClass = iterator.current; 418 ClassElement otherClass = iterator.current;
433 assert(checkInvariants(otherClass)); 419 assert(checkInvariants(otherClass));
434 OrderedTypeSet otherTypeSet = otherClass.allSupertypesAndSelf; 420 OrderedTypeSet otherTypeSet = otherClass.allSupertypesAndSelf;
435 otherTypeSets = otherTypeSets.prepend(otherTypeSet); 421 otherTypeSets = otherTypeSets.prepend(otherTypeSet);
436 if (otherTypeSet.maxDepth < depth) { 422 if (otherTypeSet.maxDepth < depth) {
437 depth = otherTypeSet.maxDepth; 423 depth = otherTypeSet.maxDepth;
438 } 424 }
439 } while (iterator.moveNext()); 425 } while (iterator.moveNext());
440 426
441 List<ClassElement> commonSupertypes = <ClassElement>[]; 427 List<ClassElement> commonSupertypes = <ClassElement>[];
442 OUTER: for (Link<DartType> link = typeSet[depth]; 428 OUTER: for (Link<DartType> link = typeSet[depth];
443 link.head.element != objectClass; 429 link.head.element != objectClass;
444 link = link.tail) { 430 link = link.tail) {
445 ClassElement cls = link.head.element; 431 ClassElement cls = link.head.element;
446 for (Link<OrderedTypeSet> link = otherTypeSets; 432 for (Link<OrderedTypeSet> link = otherTypeSets;
447 !link.isEmpty; 433 !link.isEmpty;
448 link = link.tail) { 434 link = link.tail) {
449 if (link.head.asInstanceOf(cls) == null) { 435 if (link.head.asInstanceOf(cls) == null) {
450 continue OUTER; 436 continue OUTER;
451 } 437 }
452 } 438 }
453 commonSupertypes.add(cls); 439 commonSupertypes.add(cls);
454 } 440 }
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
490 Iterable<MixinApplicationElement> uses = _liveMixinUses[cls]; 476 Iterable<MixinApplicationElement> uses = _liveMixinUses[cls];
491 return uses != null ? uses : const <MixinApplicationElement>[]; 477 return uses != null ? uses : const <MixinApplicationElement>[];
492 } 478 }
493 479
494 /// Returns `true` if [cls] is mixed into a live class. 480 /// Returns `true` if [cls] is mixed into a live class.
495 bool isUsedAsMixin(ClassElement cls) { 481 bool isUsedAsMixin(ClassElement cls) {
496 return !mixinUsesOf(cls).isEmpty; 482 return !mixinUsesOf(cls).isEmpty;
497 } 483 }
498 484
499 /// Returns `true` if any live class that mixes in [cls] implements [type]. 485 /// Returns `true` if any live class that mixes in [cls] implements [type].
500 bool hasAnySubclassOfMixinUseThatImplements(ClassElement cls, 486 bool hasAnySubclassOfMixinUseThatImplements(
501 ClassElement type) { 487 ClassElement cls, ClassElement type) {
502 return mixinUsesOf(cls).any( 488 return mixinUsesOf(cls)
503 (use) => hasAnySubclassThatImplements(use, type)); 489 .any((use) => hasAnySubclassThatImplements(use, type));
504 } 490 }
505 491
506 /// Returns `true` if any live class that mixes in [mixin] is also a subclass 492 /// Returns `true` if any live class that mixes in [mixin] is also a subclass
507 /// of [superclass]. 493 /// of [superclass].
508 bool hasAnySubclassThatMixes(ClassElement superclass, ClassElement mixin) { 494 bool hasAnySubclassThatMixes(ClassElement superclass, ClassElement mixin) {
509 return mixinUsesOf(mixin).any((each) => each.isSubclassOf(superclass)); 495 return mixinUsesOf(mixin).any((each) => each.isSubclassOf(superclass));
510 } 496 }
511 497
512 /// Returns `true` if any subclass of [superclass] implements [type]. 498 /// Returns `true` if any subclass of [superclass] implements [type].
513 bool hasAnySubclassThatImplements(ClassElement superclass, 499 bool hasAnySubclassThatImplements(
514 ClassElement type) { 500 ClassElement superclass, ClassElement type) {
515 Set<ClassElement> subclasses = typesImplementedBySubclassesOf(superclass); 501 Set<ClassElement> subclasses = typesImplementedBySubclassesOf(superclass);
516 if (subclasses == null) return false; 502 if (subclasses == null) return false;
517 return subclasses.contains(type); 503 return subclasses.contains(type);
518 } 504 }
519 505
520 final Compiler compiler; 506 final Compiler compiler;
521 Backend get backend => compiler.backend; 507 Backend get backend => compiler.backend;
522 final FunctionSet allFunctions; 508 final FunctionSet allFunctions;
523 final Set<Element> functionsCalledInLoop = new Set<Element>(); 509 final Set<Element> functionsCalledInLoop = new Set<Element>();
524 final Map<Element, SideEffects> sideEffects = new Map<Element, SideEffects>(); 510 final Map<Element, SideEffects> sideEffects = new Map<Element, SideEffects>();
525 511
526 final Set<TypedefElement> allTypedefs = new Set<TypedefElement>(); 512 final Set<TypedefElement> allTypedefs = new Set<TypedefElement>();
527 513
528 final Map<ClassElement, List<MixinApplicationElement>> _mixinUses = 514 final Map<ClassElement, List<MixinApplicationElement>> _mixinUses =
529 new Map<ClassElement, List<MixinApplicationElement>>(); 515 new Map<ClassElement, List<MixinApplicationElement>>();
530 Map<ClassElement, List<MixinApplicationElement>> _liveMixinUses; 516 Map<ClassElement, List<MixinApplicationElement>> _liveMixinUses;
531 517
532 final Map<ClassElement, Set<ClassElement>> _typesImplementedBySubclasses = 518 final Map<ClassElement, Set<ClassElement>> _typesImplementedBySubclasses =
533 new Map<ClassElement, Set<ClassElement>>(); 519 new Map<ClassElement, Set<ClassElement>>();
534 520
535 // We keep track of subtype and subclass relationships in four 521 // We keep track of subtype and subclass relationships in four
536 // distinct sets to make class hierarchy analysis faster. 522 // distinct sets to make class hierarchy analysis faster.
537 final Map<ClassElement, ClassHierarchyNode> _classHierarchyNodes = 523 final Map<ClassElement, ClassHierarchyNode> _classHierarchyNodes =
538 <ClassElement, ClassHierarchyNode>{}; 524 <ClassElement, ClassHierarchyNode>{};
539 final Map<ClassElement, ClassSet> _classSets = 525 final Map<ClassElement, ClassSet> _classSets = <ClassElement, ClassSet>{};
540 <ClassElement, ClassSet>{};
541 526
542 final Set<Element> sideEffectsFreeElements = new Set<Element>(); 527 final Set<Element> sideEffectsFreeElements = new Set<Element>();
543 528
544 final Set<Element> elementsThatCannotThrow = new Set<Element>(); 529 final Set<Element> elementsThatCannotThrow = new Set<Element>();
545 530
546 final Set<Element> functionsThatMightBePassedToApply = 531 final Set<Element> functionsThatMightBePassedToApply =
547 new Set<FunctionElement>(); 532 new Set<FunctionElement>();
548 533
549 final Set<Element> alreadyPopulated; 534 final Set<Element> alreadyPopulated;
550 535
(...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after
631 if (cls != coreClasses.functionClass && 616 if (cls != coreClasses.functionClass &&
632 cls.implementsFunction(coreClasses)) { 617 cls.implementsFunction(coreClasses)) {
633 ClassSet subtypeSet = _ensureClassSet(coreClasses.functionClass); 618 ClassSet subtypeSet = _ensureClassSet(coreClasses.functionClass);
634 subtypeSet.addSubtype(node); 619 subtypeSet.addSubtype(node);
635 } 620 }
636 if (!node.isInstantiated && node.parentNode != null) { 621 if (!node.isInstantiated && node.parentNode != null) {
637 _updateSuperClassHierarchyNodeForClass(node.parentNode); 622 _updateSuperClassHierarchyNodeForClass(node.parentNode);
638 } 623 }
639 } 624 }
640 625
641 void _updateClassHierarchyNodeForClass( 626 void _updateClassHierarchyNodeForClass(ClassElement cls,
642 ClassElement cls,
643 {bool directlyInstantiated: false}) { 627 {bool directlyInstantiated: false}) {
644 ClassHierarchyNode node = getClassHierarchyNode(cls); 628 ClassHierarchyNode node = getClassHierarchyNode(cls);
645 _updateSuperClassHierarchyNodeForClass(node); 629 _updateSuperClassHierarchyNodeForClass(node);
646 if (directlyInstantiated) { 630 if (directlyInstantiated) {
647 node.isDirectlyInstantiated = true; 631 node.isDirectlyInstantiated = true;
648 } 632 }
649 } 633 }
650 634
651 void populate() { 635 void populate() {
652 /// Updates the `isDirectlyInstantiated` and `isIndirectlyInstantiated` 636 /// Updates the `isDirectlyInstantiated` and `isIndirectlyInstantiated`
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
691 if (cls != null) { 675 if (cls != null) {
692 sb.write("Classes in the closed world related to $cls:\n"); 676 sb.write("Classes in the closed world related to $cls:\n");
693 } else { 677 } else {
694 sb.write("Instantiated classes in the closed world:\n"); 678 sb.write("Instantiated classes in the closed world:\n");
695 } 679 }
696 getClassHierarchyNode(coreClasses.objectClass) 680 getClassHierarchyNode(coreClasses.objectClass)
697 .printOn(sb, ' ', instantiatedOnly: cls == null, withRespectTo: cls); 681 .printOn(sb, ' ', instantiatedOnly: cls == null, withRespectTo: cls);
698 return sb.toString(); 682 return sb.toString();
699 } 683 }
700 684
701 void registerMixinUse(MixinApplicationElement mixinApplication, 685 void registerMixinUse(
702 ClassElement mixin) { 686 MixinApplicationElement mixinApplication, ClassElement mixin) {
703 // TODO(johnniwinther): Add map restricted to live classes. 687 // TODO(johnniwinther): Add map restricted to live classes.
704 // We don't support patch classes as mixin. 688 // We don't support patch classes as mixin.
705 assert(mixin.isDeclaration); 689 assert(mixin.isDeclaration);
706 List<MixinApplicationElement> users = 690 List<MixinApplicationElement> users = _mixinUses.putIfAbsent(
707 _mixinUses.putIfAbsent(mixin, () => 691 mixin, () => new List<MixinApplicationElement>());
708 new List<MixinApplicationElement>());
709 users.add(mixinApplication); 692 users.add(mixinApplication);
710 } 693 }
711 694
712 bool hasAnyUserDefinedGetter(Selector selector, ti.TypeMask mask) { 695 bool hasAnyUserDefinedGetter(Selector selector, ti.TypeMask mask) {
713 return allFunctions.filter(selector, mask).any((each) => each.isGetter); 696 return allFunctions.filter(selector, mask).any((each) => each.isGetter);
714 } 697 }
715 698
716 void registerUsedElement(Element element) { 699 void registerUsedElement(Element element) {
717 if (element.isInstanceMember && !element.isAbstract) { 700 if (element.isInstanceMember && !element.isAbstract) {
718 allFunctions.add(element); 701 allFunctions.add(element);
719 } 702 }
720 } 703 }
721 704
722 VariableElement locateSingleField(Selector selector, ti.TypeMask mask) { 705 VariableElement locateSingleField(Selector selector, ti.TypeMask mask) {
723 Element result = locateSingleElement(selector, mask); 706 Element result = locateSingleElement(selector, mask);
724 return (result != null && result.isField) ? result : null; 707 return (result != null && result.isField) ? result : null;
725 } 708 }
726 709
727 Element locateSingleElement(Selector selector, ti.TypeMask mask) { 710 Element locateSingleElement(Selector selector, ti.TypeMask mask) {
728 mask = mask == null 711 mask = mask == null ? compiler.typesTask.dynamicType : mask;
729 ? compiler.typesTask.dynamicType
730 : mask;
731 return mask.locateSingleElement(selector, mask, compiler); 712 return mask.locateSingleElement(selector, mask, compiler);
732 } 713 }
733 714
734 ti.TypeMask extendMaskIfReachesAll(Selector selector, ti.TypeMask mask) { 715 ti.TypeMask extendMaskIfReachesAll(Selector selector, ti.TypeMask mask) {
735 bool canReachAll = true; 716 bool canReachAll = true;
736 if (mask != null) { 717 if (mask != null) {
737 canReachAll = 718 canReachAll = compiler.enabledInvokeOn &&
738 compiler.enabledInvokeOn &&
739 mask.needsNoSuchMethodHandling(selector, this); 719 mask.needsNoSuchMethodHandling(selector, this);
740 } 720 }
741 return canReachAll ? compiler.typesTask.dynamicType : mask; 721 return canReachAll ? compiler.typesTask.dynamicType : mask;
742 } 722 }
743 723
744 void addFunctionCalledInLoop(Element element) { 724 void addFunctionCalledInLoop(Element element) {
745 functionsCalledInLoop.add(element.declaration); 725 functionsCalledInLoop.add(element.declaration);
746 } 726 }
747 727
748 bool isCalledInLoop(Element element) { 728 bool isCalledInLoop(Element element) {
749 return functionsCalledInLoop.contains(element.declaration); 729 return functionsCalledInLoop.contains(element.declaration);
750 } 730 }
751 731
752 bool fieldNeverChanges(Element element) { 732 bool fieldNeverChanges(Element element) {
753 if (!element.isField) return false; 733 if (!element.isField) return false;
754 if (backend.isNative(element)) { 734 if (backend.isNative(element)) {
755 // Some native fields are views of data that may be changed by operations. 735 // Some native fields are views of data that may be changed by operations.
756 // E.g. node.firstChild depends on parentNode.removeBefore(n1, n2). 736 // E.g. node.firstChild depends on parentNode.removeBefore(n1, n2).
757 // TODO(sra): Refine the effect classification so that native effects are 737 // TODO(sra): Refine the effect classification so that native effects are
758 // distinct from ordinary Dart effects. 738 // distinct from ordinary Dart effects.
759 return false; 739 return false;
760 } 740 }
761 741
762 if (element.isFinal || element.isConst) { 742 if (element.isFinal || element.isConst) {
763 return true; 743 return true;
764 } 744 }
765 if (element.isInstanceMember) { 745 if (element.isInstanceMember) {
766 return !compiler.resolverWorld.hasInvokedSetter(element, this) && 746 return !compiler.resolverWorld.hasInvokedSetter(element, this) &&
767 !compiler.resolverWorld.fieldSetters.contains(element); 747 !compiler.resolverWorld.fieldSetters.contains(element);
768 } 748 }
769 return false; 749 return false;
770 } 750 }
771 751
772 SideEffects getSideEffectsOfElement(Element element) { 752 SideEffects getSideEffectsOfElement(Element element) {
773 // The type inferrer (where the side effects are being computed), 753 // The type inferrer (where the side effects are being computed),
774 // does not see generative constructor bodies because they are 754 // does not see generative constructor bodies because they are
775 // created by the backend. Also, it does not make any distinction 755 // created by the backend. Also, it does not make any distinction
776 // between a constructor and its body for side effects. This 756 // between a constructor and its body for side effects. This
777 // implies that currently, the side effects of a constructor body 757 // implies that currently, the side effects of a constructor body
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after
837 // function expressions's element. 817 // function expressions's element.
838 // TODO(herhut): Generate classes for function expressions earlier. 818 // TODO(herhut): Generate classes for function expressions earlier.
839 if (element is SynthesizedCallMethodElementX) { 819 if (element is SynthesizedCallMethodElementX) {
840 return getMightBePassedToApply(element.expression); 820 return getMightBePassedToApply(element.expression);
841 } 821 }
842 return functionsThatMightBePassedToApply.contains(element); 822 return functionsThatMightBePassedToApply.contains(element);
843 } 823 }
844 824
845 bool get hasClosedWorldAssumption => !compiler.options.hasIncrementalSupport; 825 bool get hasClosedWorldAssumption => !compiler.options.hasIncrementalSupport;
846 } 826 }
OLDNEW
« no previous file with comments | « pkg/compiler/lib/src/util/util.dart ('k') | pkg/compiler/samples/compile_loop/compile_loop.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698