@@ -7,12 +7,14 @@ import 'package:analyzer/dart/ast/token.dart';
77import 'package:analyzer/dart/ast/visitor.dart' ;
88import 'package:analyzer/dart/element/element.dart' ;
99import 'package:analyzer/dart/element/type.dart' ;
10+ import 'package:analyzer/src/dart/element/inheritance_manager2.dart' ;
1011import 'package:analyzer/src/dart/element/member.dart' ;
1112import 'package:analyzer/src/generated/resolver.dart' ;
1213import 'package:analyzer/src/generated/source.dart' ;
1314import 'package:meta/meta.dart' ;
1415import 'package:nnbd_migration/nnbd_migration.dart' ;
1516import 'package:nnbd_migration/src/conditional_discard.dart' ;
17+ import 'package:nnbd_migration/src/decorated_class_hierarchy.dart' ;
1618import 'package:nnbd_migration/src/decorated_type.dart' ;
1719import 'package:nnbd_migration/src/edge_origin.dart' ;
1820import 'package:nnbd_migration/src/expression_checks.dart' ;
@@ -27,6 +29,8 @@ import 'package:nnbd_migration/src/nullability_node.dart';
2729/// variables that will determine its nullability. For `visit...` methods that
2830/// don't visit expressions, `null` will be returned.
2931class EdgeBuilder extends GeneralizingAstVisitor <DecoratedType > {
32+ final InheritanceManager2 _inheritanceManager;
33+
3034 /// The repository of constraint variables and decorated types (from a
3135 /// previous pass over the source code).
3236 final VariableRepository _variables;
@@ -38,6 +42,8 @@ class EdgeBuilder extends GeneralizingAstVisitor<DecoratedType> {
3842 /// The file being analyzed.
3943 final Source _source;
4044
45+ final DecoratedClassHierarchy _decoratedClassHierarchy;
46+
4147 /// For convenience, a [DecoratedType] representing non-nullable `Object` .
4248 final DecoratedType _notNullType;
4349
@@ -77,9 +83,11 @@ class EdgeBuilder extends GeneralizingAstVisitor<DecoratedType> {
7783
7884 NullabilityNode _lastConditionalNode;
7985
80- EdgeBuilder (TypeProvider typeProvider, this ._variables, this ._graph,
81- this ._source, this .listener)
82- : _notNullType = DecoratedType (typeProvider.objectType, _graph.never),
86+ EdgeBuilder (TypeProvider typeProvider, TypeSystem typeSystem, this ._variables,
87+ this ._graph, this ._source, this .listener)
88+ : _decoratedClassHierarchy = DecoratedClassHierarchy (_variables, _graph),
89+ _inheritanceManager = InheritanceManager2 (typeSystem),
90+ _notNullType = DecoratedType (typeProvider.objectType, _graph.never),
8391 _nonNullableBoolType =
8492 DecoratedType (typeProvider.boolType, _graph.never),
8593 _nonNullableTypeType =
@@ -490,11 +498,31 @@ class EdgeBuilder extends GeneralizingAstVisitor<DecoratedType> {
490498 DecoratedType visitMethodDeclaration (MethodDeclaration node) {
491499 node.parameters? .accept (this );
492500 assert (_currentFunctionType == null );
493- _currentFunctionType =
494- _variables.decoratedElementType (node. declaredElement);
501+ var declaredElement = node.declaredElement;
502+ _currentFunctionType = _variables.decoratedElementType (declaredElement);
495503 _inConditionalControlFlow = false ;
496504 try {
497505 node.body.accept (this );
506+ var classElement = declaredElement.enclosingElement as ClassElement ;
507+ for (var overridden in _inheritanceManager.getOverridden (
508+ classElement.type,
509+ Name (classElement.library.source.uri, declaredElement.name)) ??
510+ const []) {
511+ var overriddenElement = overridden.element as ExecutableElement ;
512+ assert (overriddenElement is ! ExecutableMember );
513+ var overriddenClass =
514+ overriddenElement.enclosingElement as ClassElement ;
515+ var decoratedOverriddenFunctionType =
516+ _variables.decoratedElementType (overriddenElement);
517+ var decoratedSupertype = _decoratedClassHierarchy.getDecoratedSupertype (
518+ classElement, overriddenClass);
519+ var substitution = decoratedSupertype.asSubstitution;
520+ _checkAssignment (null ,
521+ source: _currentFunctionType,
522+ destination:
523+ decoratedOverriddenFunctionType.substitute (substitution),
524+ hard: true );
525+ }
498526 } finally {
499527 _currentFunctionType = null ;
500528 }
0 commit comments