| OLD | NEW |
| 1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2016, 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 library kernel.class_hierarchy; | 4 library kernel.class_hierarchy; |
| 5 | 5 |
| 6 import 'ast.dart'; | 6 import 'ast.dart'; |
| 7 import 'dart:math'; | 7 import 'dart:math'; |
| 8 import 'dart:typed_data'; | 8 import 'dart:typed_data'; |
| 9 import 'type_algebra.dart'; | 9 import 'type_algebra.dart'; |
| 10 | 10 |
| (...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 57 return _infoFor[class_].directMixers.isNotEmpty; | 57 return _infoFor[class_].directMixers.isNotEmpty; |
| 58 } | 58 } |
| 59 | 59 |
| 60 /// True if the given class is used in an `implements` clause. | 60 /// True if the given class is used in an `implements` clause. |
| 61 bool isUsedAsSuperInterface(Class class_) { | 61 bool isUsedAsSuperInterface(Class class_) { |
| 62 return _infoFor[class_].directImplementers.isNotEmpty; | 62 return _infoFor[class_].directImplementers.isNotEmpty; |
| 63 } | 63 } |
| 64 | 64 |
| 65 /// Returns the instantiation of [superclass] that is implemented by [class_], | 65 /// Returns the instantiation of [superclass] that is implemented by [class_], |
| 66 /// or `null` if [class_] does not implement [superclass] at all. | 66 /// or `null` if [class_] does not implement [superclass] at all. |
| 67 InterfaceType getClassAsInstanceOf(Class class_, Class superclass) { | 67 Supertype getClassAsInstanceOf(Class class_, Class superclass) { |
| 68 if (identical(class_, superclass)) return class_.thisType; | 68 if (identical(class_, superclass)) return class_.asThisSupertype; |
| 69 _ClassInfo info = _infoFor[class_]; | 69 _ClassInfo info = _infoFor[class_]; |
| 70 _ClassInfo superInfo = _infoFor[superclass]; | 70 _ClassInfo superInfo = _infoFor[superclass]; |
| 71 if (!info.isSubtypeOf(superInfo)) return null; | 71 if (!info.isSubtypeOf(superInfo)) return null; |
| 72 if (superclass.typeParameters.isEmpty) return superclass.rawType; | 72 if (superclass.typeParameters.isEmpty) return superclass.asRawSupertype; |
| 73 return info.genericSuperTypes[superclass]; | 73 return info.genericSuperTypes[superclass]; |
| 74 } | 74 } |
| 75 | 75 |
| 76 /// Returns the instantiation of [superclass] that is implemented by [type], | 76 /// Returns the instantiation of [superclass] that is implemented by [type], |
| 77 /// or `null` if [type] does not implement [superclass] at all. | 77 /// or `null` if [type] does not implement [superclass] at all. |
| 78 InterfaceType getTypeAsInstanceOf(InterfaceType type, Class superclass) { | 78 InterfaceType getTypeAsInstanceOf(InterfaceType type, Class superclass) { |
| 79 InterfaceType castedType = getClassAsInstanceOf(type.classNode, superclass); | 79 Supertype castedType = getClassAsInstanceOf(type.classNode, superclass); |
| 80 if (castedType == null) return null; | 80 if (castedType == null) return null; |
| 81 return substituteThisType(castedType, type); | 81 return Substitution |
| 82 .fromInterfaceType(type) |
| 83 .substituteType(castedType.asInterfaceType); |
| 82 } | 84 } |
| 83 | 85 |
| 84 /// Returns the instance member that would respond to a dynamic dispatch of | 86 /// Returns the instance member that would respond to a dynamic dispatch of |
| 85 /// [name] to an instance of [class_], or `null` if no such member exists. | 87 /// [name] to an instance of [class_], or `null` if no such member exists. |
| 86 /// | 88 /// |
| 87 /// If [setter] is `false`, the name is dispatched as a getter or call, | 89 /// If [setter] is `false`, the name is dispatched as a getter or call, |
| 88 /// and will return a field, getter, method, or operator (or null). | 90 /// and will return a field, getter, method, or operator (or null). |
| 89 /// | 91 /// |
| 90 /// If [setter] is `true`, the name is dispatched as a setter, roughly | 92 /// If [setter] is `true`, the name is dispatched as a setter, roughly |
| 91 /// corresponding to `name=` in the Dart specification, but note that the | 93 /// corresponding to `name=` in the Dart specification, but note that the |
| (...skipping 256 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 348 } | 350 } |
| 349 | 351 |
| 350 List<Member> _buildInterfaceMembers(Class classNode, _ClassInfo info, | 352 List<Member> _buildInterfaceMembers(Class classNode, _ClassInfo info, |
| 351 {bool setters}) { | 353 {bool setters}) { |
| 352 List<Member> members = | 354 List<Member> members = |
| 353 setters ? info.interfaceSetters : info.interfaceGettersAndCalls; | 355 setters ? info.interfaceSetters : info.interfaceGettersAndCalls; |
| 354 if (members != null) return members; | 356 if (members != null) return members; |
| 355 List<Member> allInheritedMembers = <Member>[]; | 357 List<Member> allInheritedMembers = <Member>[]; |
| 356 List<Member> declared = | 358 List<Member> declared = |
| 357 setters ? info.declaredSetters : info.declaredGettersAndCalls; | 359 setters ? info.declaredSetters : info.declaredGettersAndCalls; |
| 358 void inheritFrom(InterfaceType type) { | 360 void inheritFrom(Supertype type) { |
| 359 if (type == null) return; | 361 if (type == null) return; |
| 360 List<Member> inherited = _buildInterfaceMembers( | 362 List<Member> inherited = _buildInterfaceMembers( |
| 361 type.classNode, _infoFor[type.classNode], | 363 type.classNode, _infoFor[type.classNode], |
| 362 setters: setters); | 364 setters: setters); |
| 363 inherited = _getUnshadowedInheritedMembers(declared, inherited); | 365 inherited = _getUnshadowedInheritedMembers(declared, inherited); |
| 364 allInheritedMembers = _merge(allInheritedMembers, inherited); | 366 allInheritedMembers = _merge(allInheritedMembers, inherited); |
| 365 } | 367 } |
| 366 inheritFrom(classNode.supertype); | 368 inheritFrom(classNode.supertype); |
| 367 inheritFrom(classNode.mixedInType); | 369 inheritFrom(classNode.mixedInType); |
| 368 classNode.implementedTypes.forEach(inheritFrom); | 370 classNode.implementedTypes.forEach(inheritFrom); |
| (...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 484 while (i < first.length) { | 486 while (i < first.length) { |
| 485 result[storeIndex++] = first[i++]; | 487 result[storeIndex++] = first[i++]; |
| 486 } | 488 } |
| 487 while (j < second.length) { | 489 while (j < second.length) { |
| 488 result[storeIndex++] = second[j++]; | 490 result[storeIndex++] = second[j++]; |
| 489 } | 491 } |
| 490 result.length = storeIndex; | 492 result.length = storeIndex; |
| 491 return result; | 493 return result; |
| 492 } | 494 } |
| 493 | 495 |
| 494 void _recordSuperTypes(_ClassInfo subInfo, InterfaceType supertype) { | 496 void _recordSuperTypes(_ClassInfo subInfo, Supertype supertype) { |
| 495 _ClassInfo superInfo = _infoFor[supertype.classNode]; | 497 _ClassInfo superInfo = _infoFor[supertype.classNode]; |
| 496 if (supertype.typeArguments.isEmpty) { | 498 if (supertype.typeArguments.isEmpty) { |
| 497 if (superInfo.genericSuperTypes == null) return; | 499 if (superInfo.genericSuperTypes == null) return; |
| 498 // Since the immediate super type is not generic, all entries in its | 500 // Since the immediate super type is not generic, all entries in its |
| 499 // super type map are also valid entries for this class. | 501 // super type map are also valid entries for this class. |
| 500 if (subInfo.genericSuperTypes == null && | 502 if (subInfo.genericSuperTypes == null && |
| 501 superInfo.ownsGenericSuperTypeMap) { | 503 superInfo.ownsGenericSuperTypeMap) { |
| 502 // Instead of copying the map, take ownership of the map object. | 504 // Instead of copying the map, take ownership of the map object. |
| 503 // This may result in more entries being added to the map later. Those | 505 // This may result in more entries being added to the map later. Those |
| 504 // are not valid for the super type, but it works out because all | 506 // are not valid for the super type, but it works out because all |
| 505 // lookups in the map are guarded by a subtype check, so the super type | 507 // lookups in the map are guarded by a subtype check, so the super type |
| 506 // will not be bothered by the extra entries. | 508 // will not be bothered by the extra entries. |
| 507 subInfo.genericSuperTypes = superInfo.genericSuperTypes; | 509 subInfo.genericSuperTypes = superInfo.genericSuperTypes; |
| 508 superInfo.ownsGenericSuperTypeMap = false; | 510 superInfo.ownsGenericSuperTypeMap = false; |
| 509 } else { | 511 } else { |
| 510 // Copy over the super type entries. | 512 // Copy over the super type entries. |
| 511 subInfo.genericSuperTypes ??= <Class, InterfaceType>{}; | 513 subInfo.genericSuperTypes ??= <Class, Supertype>{}; |
| 512 subInfo.genericSuperTypes.addAll(superInfo.genericSuperTypes); | 514 subInfo.genericSuperTypes.addAll(superInfo.genericSuperTypes); |
| 513 } | 515 } |
| 514 } else { | 516 } else { |
| 515 // Copy over all transitive generic super types, and substitute the | 517 // Copy over all transitive generic super types, and substitute the |
| 516 // free variables with those provided in [supertype]. | 518 // free variables with those provided in [supertype]. |
| 517 Class superclass = supertype.classNode; | 519 Class superclass = supertype.classNode; |
| 518 var substitution = new Map<TypeParameter, DartType>.fromIterables( | 520 var substitution = Substitution.fromPairs( |
| 519 superclass.typeParameters, supertype.typeArguments); | 521 superclass.typeParameters, supertype.typeArguments); |
| 520 subInfo.genericSuperTypes ??= <Class, InterfaceType>{}; | 522 subInfo.genericSuperTypes ??= <Class, Supertype>{}; |
| 521 superInfo.genericSuperTypes?.forEach((Class key, InterfaceType type) { | 523 superInfo.genericSuperTypes?.forEach((Class key, Supertype type) { |
| 522 subInfo.genericSuperTypes[key] = substitute(type, substitution); | 524 subInfo.genericSuperTypes[key] = substitution.substituteSupertype(type); |
| 523 }); | 525 }); |
| 524 subInfo.genericSuperTypes[superclass] = supertype; | 526 subInfo.genericSuperTypes[superclass] = supertype; |
| 525 } | 527 } |
| 526 } | 528 } |
| 527 | 529 |
| 528 /// Downwards traversal of the class hierarchy that orders classes so local | 530 /// Downwards traversal of the class hierarchy that orders classes so local |
| 529 /// hierarchies have contiguous indices. | 531 /// hierarchies have contiguous indices. |
| 530 int _topDownSortIndex = 0; | 532 int _topDownSortIndex = 0; |
| 531 void _topDownSortVisit(_ClassInfo info) { | 533 void _topDownSortVisit(_ClassInfo info) { |
| 532 if (info.topDownIndex != -1) return; | 534 if (info.topDownIndex != -1) return; |
| (...skipping 280 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 813 /// For example: | 815 /// For example: |
| 814 /// | 816 /// |
| 815 /// class Q<T> | 817 /// class Q<T> |
| 816 /// class A<T> | 818 /// class A<T> |
| 817 /// | 819 /// |
| 818 /// class B extends A<String> | 820 /// class B extends A<String> |
| 819 /// class C extends B implements Q<int> | 821 /// class C extends B implements Q<int> |
| 820 /// | 822 /// |
| 821 /// In this case, a single map object `{A: A<String>, Q: Q<int>}` may be | 823 /// In this case, a single map object `{A: A<String>, Q: Q<int>}` may be |
| 822 /// shared by the classes `B` and `C`. | 824 /// shared by the classes `B` and `C`. |
| 823 Map<Class, InterfaceType> genericSuperTypes; | 825 Map<Class, Supertype> genericSuperTypes; |
| 824 | 826 |
| 825 /// If true, this is the current "owner" of [genericSuperTypes], meaning | 827 /// If true, this is the current "owner" of [genericSuperTypes], meaning |
| 826 /// we may add additional entries to the map or transfer ownership to another | 828 /// we may add additional entries to the map or transfer ownership to another |
| 827 /// class. | 829 /// class. |
| 828 bool ownsGenericSuperTypeMap = true; | 830 bool ownsGenericSuperTypeMap = true; |
| 829 | 831 |
| 830 /// Instance fields, getters, methods, and operators declared in this class | 832 /// Instance fields, getters, methods, and operators declared in this class |
| 831 /// or its mixed-in class, sorted according to [_compareMembers]. | 833 /// or its mixed-in class, sorted according to [_compareMembers]. |
| 832 List<Member> declaredGettersAndCalls; | 834 List<Member> declaredGettersAndCalls; |
| 833 | 835 |
| 834 /// Non-final instance fields and setters declared in this class or its | 836 /// Non-final instance fields and setters declared in this class or its |
| 835 /// mixed-in class, sorted according to [_compareMembers]. | 837 /// mixed-in class, sorted according to [_compareMembers]. |
| 836 List<Member> declaredSetters; | 838 List<Member> declaredSetters; |
| 837 | 839 |
| 838 /// Instance fields, getters, methods, and operators implemented by this class | 840 /// Instance fields, getters, methods, and operators implemented by this class |
| 839 /// (declared or inherited). | 841 /// (declared or inherited). |
| 840 List<Member> implementedGettersAndCalls; | 842 List<Member> implementedGettersAndCalls; |
| 841 | 843 |
| 842 /// Non-final instance fields and setters implemented by this class | 844 /// Non-final instance fields and setters implemented by this class |
| 843 /// (declared or inherited). | 845 /// (declared or inherited). |
| 844 List<Member> implementedSetters; | 846 List<Member> implementedSetters; |
| 845 | 847 |
| 846 List<Member> interfaceGettersAndCalls; | 848 List<Member> interfaceGettersAndCalls; |
| 847 List<Member> interfaceSetters; | 849 List<Member> interfaceSetters; |
| 848 | 850 |
| 849 _ClassInfo(this.classNode); | 851 _ClassInfo(this.classNode); |
| 850 } | 852 } |
| OLD | NEW |