Skip to content

Commit

Permalink
Type inference should always infer the return type of operator []= as…
Browse files Browse the repository at this point in the history
… void.

R=brianwilkerson@google.com, paulberry@google.com

Bug: #31779
Change-Id: I1c396cce3f148585218e02ff4e41bc2f85cc924a
     #31638
Reviewed-on: https://dart-review.googlesource.com/32687
Reviewed-by: Paul Berry <paulberry@google.com>
Reviewed-by: Brian Wilkerson <brianwilkerson@google.com>
Commit-Queue: Konstantin Shcheglov <scheglov@google.com>
  • Loading branch information
scheglov authored and commit-bot@chromium.org committed Jan 9, 2018
1 parent b264dc6 commit bb52d1a
Show file tree
Hide file tree
Showing 3 changed files with 53 additions and 4 deletions.
9 changes: 6 additions & 3 deletions pkg/analyzer/lib/src/summary/link.dart
Original file line number Diff line number Diff line change
Expand Up @@ -1982,10 +1982,13 @@ abstract class ExecutableElementForLink extends Object
* better return type).
*/
DartType _computeDefaultReturnType() {
if (_unlinkedExecutable.kind == UnlinkedExecutableKind.setter &&
var kind = _unlinkedExecutable.kind;
var isMethod = kind == UnlinkedExecutableKind.functionOrMethod;
var isSetter = kind == UnlinkedExecutableKind.setter;
if ((isSetter || isMethod && _unlinkedExecutable.name == '[]=') &&
(library as LibraryElementForLink)._linker.strongMode) {
// In strong mode, setters without an explicit return type are
// considered to return `void`.
// In strong mode, setters and `[]=` operators without an explicit
// return type are considered to return `void`.
return VoidTypeImpl.instance;
} else {
return DynamicTypeImpl.instance;
Expand Down
2 changes: 1 addition & 1 deletion pkg/analyzer/lib/src/task/strong_mode.dart
Original file line number Diff line number Diff line change
Expand Up @@ -363,7 +363,7 @@ class InstanceMemberInferrer {
//
// Infer the return type.
//
if (element.hasImplicitReturnType) {
if (element.hasImplicitReturnType && element.displayName != '[]=') {
(element as ExecutableElementImpl).returnType =
_computeReturnType(overriddenTypes.map((t) => t.returnType));
if (element is PropertyAccessorElement) {
Expand Down
46 changes: 46 additions & 0 deletions pkg/analyzer/test/src/task/strong/dart2_inference_test.dart
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import 'package:analyzer/dart/ast/ast.dart';
import 'package:analyzer/dart/ast/token.dart';
import 'package:analyzer/dart/ast/visitor.dart';
import 'package:analyzer/dart/element/element.dart';
import 'package:analyzer/src/dart/element/type.dart';
import 'package:analyzer/src/generated/engine.dart';
import 'package:test/test.dart';
import 'package:test_reflective_loader/test_reflective_loader.dart';
Expand Down Expand Up @@ -654,6 +655,51 @@ class C {
assertType('f()) {} // top setter');
}

test_implicitVoidReturnType_default() async {
var code = r'''
class C {
set x(_) {}
operator []=(int index, double value) => null;
}
''';
var source = addSource(code);
var analysisResult = await computeAnalysisResult(source);
var unit = analysisResult.unit;

ClassElement c = unit.element.getType('C');

PropertyAccessorElement x = c.accessors[0];
expect(x.returnType, VoidTypeImpl.instance);

MethodElement operator = c.methods[0];
expect(operator.displayName, '[]=');
expect(operator.returnType, VoidTypeImpl.instance);
}

test_implicitVoidReturnType_derived() async {
var code = r'''
class Base {
dynamic set x(_) {}
dynamic operator[]=(int x, int y) => null;
}
class Derived extends Base {
set x(_) {}
operator[]=(int x, int y) {}
}''';
var source = addSource(code);
var analysisResult = await computeAnalysisResult(source);
var unit = analysisResult.unit;

ClassElement c = unit.element.getType('Derived');

PropertyAccessorElement x = c.accessors[0];
expect(x.returnType, VoidTypeImpl.instance);

MethodElement operator = c.methods[0];
expect(operator.displayName, '[]=');
expect(operator.returnType, VoidTypeImpl.instance);
}

test_inferObject_whenDownwardNull() async {
var code = r'''
int f(void Function(Null) f2) {}
Expand Down

0 comments on commit bb52d1a

Please sign in to comment.