Chromium Code Reviews| Index: lib/src/checker/checker.dart |
| diff --git a/lib/src/checker/checker.dart b/lib/src/checker/checker.dart |
| index 3c44e81204eee129dcaa8d7bce8b9a05bfb72128..ee6a78685a0a83b780f376dd421c3ad7e3254c32 100644 |
| --- a/lib/src/checker/checker.dart |
| +++ b/lib/src/checker/checker.dart |
| @@ -545,15 +545,22 @@ class CodeChecker extends RecursiveAstVisitor { |
| if (_rules.isDynamicCall(f)) { |
| // If f is Function and this is a method invocation, we should have |
| // gotten an analyzer error, so no need to issue another error. |
| - _recordDynamicInvoke(node); |
| + _recordDynamicInvoke(node, f); |
| } else { |
| checkArgumentList(list, _rules.getTypeAsCaller(f)); |
| } |
| } |
| @override |
| - void visitMethodInvocation(MethodInvocation node) { |
| - checkFunctionApplication(node, node.methodName, node.argumentList); |
| + visitMethodInvocation(MethodInvocation node) { |
| + var target = node.realTarget; |
| + if (_rules.isDynamicTarget(target)) { |
| + _recordDynamicInvoke(node, target); |
| + // Mark the call as being dynamic as well. |
| + DynamicInvoke.set(node.methodName, true); |
|
Jennifer Messerly
2015/06/12 18:18:09
we are interesting both in whether the method call
Leaf
2015/06/12 20:13:23
This is a little obscure, maybe worth a bit more e
Jennifer Messerly
2015/06/12 20:22:28
sure. will add. For your info, what happens is we
|
| + } else { |
| + checkFunctionApplication(node, node.methodName, node.argumentList); |
| + } |
| node.visitChildren(this); |
| } |
| @@ -622,8 +629,9 @@ class CodeChecker extends RecursiveAstVisitor { |
| @override |
| void visitPropertyAccess(PropertyAccess node) { |
| - if (node.staticType.isDynamic && _rules.isDynamicTarget(node.realTarget)) { |
| - _recordDynamicInvoke(node); |
| + var target = node.realTarget; |
|
Jennifer Messerly
2015/06/12 18:18:09
bug fix: cascade dinvoke not reported
|
| + if (_rules.isDynamicTarget(target)) { |
| + _recordDynamicInvoke(node, target); |
| } |
| node.visitChildren(this); |
| } |
| @@ -632,7 +640,7 @@ class CodeChecker extends RecursiveAstVisitor { |
| void visitPrefixedIdentifier(PrefixedIdentifier node) { |
| final target = node.prefix; |
| if (_rules.isDynamicTarget(target)) { |
| - _recordDynamicInvoke(node); |
| + _recordDynamicInvoke(node, target); |
| } |
| node.visitChildren(this); |
| } |
| @@ -774,7 +782,7 @@ class CodeChecker extends RecursiveAstVisitor { |
| op.type == TokenType.PLUS_PLUS || |
| op.type == TokenType.MINUS_MINUS) { |
| if (_rules.isDynamicTarget(node.operand)) { |
| - _recordDynamicInvoke(node); |
| + _recordDynamicInvoke(node, node.operand); |
| } |
| // For ++ and --, even if it is not dynamic, we still need to check |
| // that the user defined method accepts an `int` as the RHS. |
| @@ -790,7 +798,7 @@ class CodeChecker extends RecursiveAstVisitor { |
| // Dynamic invocation |
| // TODO(vsm): Move this logic to the resolver? |
| if (op.type != TokenType.EQ_EQ && op.type != TokenType.BANG_EQ) { |
| - _recordDynamicInvoke(node); |
| + _recordDynamicInvoke(node, node.leftOperand); |
| } |
| } else { |
| var element = node.staticElement; |
| @@ -831,8 +839,9 @@ class CodeChecker extends RecursiveAstVisitor { |
| @override |
| void visitIndexExpression(IndexExpression node) { |
| - if (_rules.isDynamicTarget(node.target)) { |
| - _recordDynamicInvoke(node); |
| + var target = node.realTarget; |
|
Jennifer Messerly
2015/06/12 18:18:09
bug fix: cascade dinvoke not reported
|
| + if (_rules.isDynamicTarget(target)) { |
| + _recordDynamicInvoke(node, target); |
| } else { |
| var element = node.staticElement; |
| if (element is MethodElement) { |
| @@ -897,7 +906,7 @@ class CodeChecker extends RecursiveAstVisitor { |
| var methodElement = expr.staticElement; |
| if (methodElement == null) { |
| // Dynamic invocation |
| - _recordDynamicInvoke(expr); |
| + _recordDynamicInvoke(expr, expr.leftHandSide); |
| } else { |
| // Sanity check the operator |
| assert(methodElement.isOperator); |
| @@ -941,8 +950,13 @@ class CodeChecker extends RecursiveAstVisitor { |
| } |
| } |
| - void _recordDynamicInvoke(AstNode node) { |
| - _reporter.log(new DynamicInvoke(_rules, node)); |
| + void _recordDynamicInvoke(AstNode node, AstNode target) { |
| + var dinvoke = new DynamicInvoke(_rules, node); |
| + _reporter.log(dinvoke); |
| + // TODO(jmesserly): we may eventually want to record if the whole operation |
| + // (node) was dynamic, rather than the target, but this is an easier fit |
| + // with what we used to do. |
| + DynamicInvoke.set(target, true); |
| } |
| void _recordMessage(StaticInfo info) { |