| 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 'src/heap.dart'; | 9 import 'src/heap.dart'; |
| 10 import 'type_algebra.dart'; | 10 import 'type_algebra.dart'; |
| (...skipping 98 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 109 /// | 109 /// |
| 110 /// This method will not report that a member overrides itself. A given pair | 110 /// This method will not report that a member overrides itself. A given pair |
| 111 /// may be reported multiple times when there are multiple inheritance paths | 111 /// may be reported multiple times when there are multiple inheritance paths |
| 112 /// to the overridden member. | 112 /// to the overridden member. |
| 113 /// | 113 /// |
| 114 /// It is possible for two methods to override one another in both directions. | 114 /// It is possible for two methods to override one another in both directions. |
| 115 /// | 115 /// |
| 116 /// Getters and setters are overridden separately. The [isSetter] callback | 116 /// Getters and setters are overridden separately. The [isSetter] callback |
| 117 /// parameter determines which type of access is being overridden. | 117 /// parameter determines which type of access is being overridden. |
| 118 void forEachOverridePair(Class class_, | 118 void forEachOverridePair(Class class_, |
| 119 callback(Member declaredMember, Member interfaceMember, bool isSetter)); | 119 callback(Member declaredMember, Member interfaceMember, bool isSetter), |
| 120 {bool crossGettersSetters: false}); |
| 120 | 121 |
| 121 /// This method is invoked by the client after it changed the [classes], and | 122 /// This method is invoked by the client after it changed the [classes], and |
| 122 /// some of the information that this hierarchy might have cached, is not | 123 /// some of the information that this hierarchy might have cached, is not |
| 123 /// valid anymore. The hierarchy may perform required updates and return the | 124 /// valid anymore. The hierarchy may perform required updates and return the |
| 124 /// same instance, or return a new instance. | 125 /// same instance, or return a new instance. |
| 125 ClassHierarchy applyChanges(Iterable<Class> classes); | 126 ClassHierarchy applyChanges(Iterable<Class> classes); |
| 126 } | 127 } |
| 127 | 128 |
| 128 /// Implementation of [ClassHierarchy] for closed world. | 129 /// Implementation of [ClassHierarchy] for closed world. |
| 129 class ClosedWorldClassHierarchy implements ClassHierarchy { | 130 class ClosedWorldClassHierarchy implements ClassHierarchy { |
| (...skipping 240 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 370 /// when members are inherited through different supertypes and not overridden | 371 /// when members are inherited through different supertypes and not overridden |
| 371 /// in the class. | 372 /// in the class. |
| 372 /// | 373 /// |
| 373 /// Also see [getInterfaceMember]. | 374 /// Also see [getInterfaceMember]. |
| 374 List<Member> getInterfaceMembers(Class class_, {bool setters: false}) { | 375 List<Member> getInterfaceMembers(Class class_, {bool setters: false}) { |
| 375 return _buildInterfaceMembers(class_, _infoFor[class_], setters: setters); | 376 return _buildInterfaceMembers(class_, _infoFor[class_], setters: setters); |
| 376 } | 377 } |
| 377 | 378 |
| 378 @override | 379 @override |
| 379 void forEachOverridePair(Class class_, | 380 void forEachOverridePair(Class class_, |
| 380 callback(Member declaredMember, Member interfaceMember, bool isSetter)) { | 381 callback(Member declaredMember, Member interfaceMember, bool isSetter), |
| 382 {bool crossGettersSetters: false}) { |
| 381 _ClassInfo info = _infoFor[class_]; | 383 _ClassInfo info = _infoFor[class_]; |
| 382 for (var supertype in class_.supers) { | 384 for (var supertype in class_.supers) { |
| 383 var superclass = supertype.classNode; | 385 var superclass = supertype.classNode; |
| 384 var superGetters = getInterfaceMembers(superclass); | 386 var superGetters = getInterfaceMembers(superclass); |
| 385 var superSetters = getInterfaceMembers(superclass, setters: true); | 387 var superSetters = getInterfaceMembers(superclass, setters: true); |
| 386 _reportOverrides(info.implementedGettersAndCalls, superGetters, callback); | 388 _reportOverrides(info.implementedGettersAndCalls, superGetters, callback); |
| 387 _reportOverrides(info.declaredGettersAndCalls, superGetters, callback, | 389 _reportOverrides(info.declaredGettersAndCalls, superGetters, callback, |
| 388 onlyAbstract: true); | 390 onlyAbstract: true); |
| 389 _reportOverrides(info.implementedSetters, superSetters, callback, | 391 _reportOverrides(info.implementedSetters, superSetters, callback, |
| 390 isSetter: true); | 392 isSetter: true); |
| 391 _reportOverrides(info.declaredSetters, superSetters, callback, | 393 _reportOverrides(info.declaredSetters, superSetters, callback, |
| 392 isSetter: true, onlyAbstract: true); | 394 isSetter: true, onlyAbstract: true); |
| 395 if (crossGettersSetters) { |
| 396 _reportOverrides(info.declaredGettersAndCalls, superSetters, callback); |
| 397 _reportOverrides(info.declaredSetters, superGetters, callback); |
| 398 } |
| 393 } | 399 } |
| 394 if (!class_.isAbstract) { | 400 if (!class_.isAbstract) { |
| 395 // If a non-abstract class declares an abstract method M whose | 401 // If a non-abstract class declares an abstract method M whose |
| 396 // implementation M' is inherited from the superclass, then the inherited | 402 // implementation M' is inherited from the superclass, then the inherited |
| 397 // method M' overrides the declared method M. | 403 // method M' overrides the declared method M. |
| 398 // This flies in the face of conventional override logic, but is necessary | 404 // This flies in the face of conventional override logic, but is necessary |
| 399 // because an instance of the class will contain the method M' which can | 405 // because an instance of the class will contain the method M' which can |
| 400 // be invoked through the interface of M. | 406 // be invoked through the interface of M. |
| 401 // Note that [_reportOverrides] does not report self-overrides, so in | 407 // Note that [_reportOverrides] does not report self-overrides, so in |
| 402 // most cases these calls will just scan both lists and report nothing. | 408 // most cases these calls will just scan both lists and report nothing. |
| (...skipping 727 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1130 class _LubHeap extends Heap<_ClassInfo> { | 1136 class _LubHeap extends Heap<_ClassInfo> { |
| 1131 @override | 1137 @override |
| 1132 bool sortsBefore(_ClassInfo a, _ClassInfo b) => sortsBeforeStatic(a, b); | 1138 bool sortsBefore(_ClassInfo a, _ClassInfo b) => sortsBeforeStatic(a, b); |
| 1133 | 1139 |
| 1134 static bool sortsBeforeStatic(_ClassInfo a, _ClassInfo b) { | 1140 static bool sortsBeforeStatic(_ClassInfo a, _ClassInfo b) { |
| 1135 if (a.depth > b.depth) return true; | 1141 if (a.depth > b.depth) return true; |
| 1136 if (a.depth < b.depth) return false; | 1142 if (a.depth < b.depth) return false; |
| 1137 return a.topologicalIndex < b.topologicalIndex; | 1143 return a.topologicalIndex < b.topologicalIndex; |
| 1138 } | 1144 } |
| 1139 } | 1145 } |
| OLD | NEW |