Skip to content

Commit aece9de

Browse files
author
Dart CI
committed
Version 2.18.0-83.0.dev
Merge commit 'bf5690dd0cb13631c59fc6817833edc502cdea31' into 'dev'
2 parents b2b5788 + bf5690d commit aece9de

22 files changed

+937
-45
lines changed

pkg/compiler/test/dump_info/data/closures.dart

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,6 @@
6262
"id": "outputUnit/main",
6363
"kind": "outputUnit",
6464
"name": "main",
65-
"size": 107495,
6665
"filename": "out",
6766
"imports": []
6867
}]

pkg/compiler/test/dump_info/data/deferred/main.dart

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -114,7 +114,6 @@
114114
"id": "outputUnit/main",
115115
"kind": "outputUnit",
116116
"name": "main",
117-
"size": 183730,
118117
"filename": "out",
119118
"imports": []
120119
}]

pkg/compiler/test/dump_info/data/deferred_future/main.dart

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -120,7 +120,6 @@
120120
"id": "outputUnit/main",
121121
"kind": "outputUnit",
122122
"name": "main",
123-
"size": 190176,
124123
"filename": "out",
125124
"imports": []
126125
}]

pkg/compiler/test/dump_info/data/js_members.dart

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -138,7 +138,6 @@
138138
"id": "outputUnit/main",
139139
"kind": "outputUnit",
140140
"name": "main",
141-
"size": 112396,
142141
"filename": "out",
143142
"imports": []
144143
}]

pkg/compiler/test/dump_info/data/members.dart

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,6 @@
7777
"id": "outputUnit/main",
7878
"kind": "outputUnit",
7979
"name": "main",
80-
"size": 91101,
8180
"filename": "out",
8281
"imports": []
8382
}]

pkg/compiler/test/dump_info/dump_info_test.dart

Lines changed: 17 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -22,14 +22,23 @@ import '../equivalence/id_equivalence_helper.dart';
2222
final JsonEncoder encoder = const JsonEncoder();
2323
final JsonEncoder indentedEncoder = const JsonEncoder.withIndent(' ');
2424

25-
String jsonEncode(object, {bool indent = true}) {
25+
String jsonEncode(Map object, {bool indent = true}) {
2626
var jsonEncoder = indent ? indentedEncoder : encoder;
2727
// Filter block comments since they interfere with ID test comments.
2828
var json =
2929
jsonEncoder.convert(object).replaceAll('/*', '').replaceAll('*/', '');
3030
return json;
3131
}
3232

33+
Map filteredJsonObject(Map object, Set<String> filteredFields) {
34+
Map filteredObject = {};
35+
object.forEach((key, value) {
36+
if (filteredFields.contains(key)) return;
37+
filteredObject[key] = value;
38+
});
39+
return filteredObject;
40+
}
41+
3342
main(List<String> args) {
3443
asyncTest(() async {
3544
Directory dataDir = Directory.fromUri(Platform.script.resolve('data'));
@@ -85,8 +94,13 @@ class DumpInfoDataComputer extends DataComputer<Features> {
8594
features.addElement(
8695
Tags.dependencies, jsonEncode(dumpInfoState.info.dependencies));
8796
for (final outputUnit in dumpInfoState.info.outputUnits) {
88-
features.addElement(
89-
Tags.outputUnits, jsonEncode(outputUnit.accept(converter)));
97+
var outputUnitJsonObject = outputUnit.accept(converter);
98+
// Remove the size from the main output unit due to high noise ratio.
99+
if (outputUnit.name == 'main') {
100+
outputUnitJsonObject =
101+
filteredJsonObject(outputUnitJsonObject, {'size'});
102+
}
103+
features.addElement(Tags.outputUnits, jsonEncode(outputUnitJsonObject));
90104
}
91105
features.addElement(
92106
Tags.deferredFiles, jsonEncode(dumpInfoState.info.deferredFiles));

pkg/front_end/lib/src/fasta/kernel/inference_visitor.dart

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2037,7 +2037,7 @@ class InferenceVisitor
20372037
typeContext,
20382038
inferrer.libraryBuilder.library,
20392039
isConst: node.isConst);
2040-
inferrer.typeSchemaEnvironment.downwardsInfer(
2040+
inferrer.typeSchemaEnvironment.partialInfer(
20412041
gatherer,
20422042
listClass.typeParameters,
20432043
inferredTypes,
@@ -2722,7 +2722,7 @@ class InferenceVisitor
27222722
typeContext,
27232723
inferrer.libraryBuilder.library,
27242724
isConst: node.isConst);
2725-
inferrer.typeSchemaEnvironment.downwardsInfer(
2725+
inferrer.typeSchemaEnvironment.partialInfer(
27262726
gatherer,
27272727
mapClass.typeParameters,
27282728
inferredTypes,
@@ -2807,7 +2807,7 @@ class InferenceVisitor
28072807
typeContext,
28082808
inferrer.libraryBuilder.library,
28092809
isConst: node.isConst);
2810-
inferrer.typeSchemaEnvironment.downwardsInfer(
2810+
inferrer.typeSchemaEnvironment.partialInfer(
28112811
gatherer,
28122812
inferrer.coreTypes.setClass.typeParameters,
28132813
inferredTypesForSet,
@@ -5992,7 +5992,7 @@ class InferenceVisitor
59925992
typeContext,
59935993
inferrer.libraryBuilder.library,
59945994
isConst: node.isConst);
5995-
inferrer.typeSchemaEnvironment.downwardsInfer(
5995+
inferrer.typeSchemaEnvironment.partialInfer(
59965996
gatherer,
59975997
setClass.typeParameters,
59985998
inferredTypes,

pkg/front_end/lib/src/fasta/type_inference/type_inferrer.dart

Lines changed: 154 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
// for details. All rights reserved. Use of this source code is governed by a
33
// BSD-style license that can be found in the LICENSE.md file.
44

5+
import 'package:_fe_analyzer_shared/src/deferred_function_literal_heuristic.dart';
56
import 'package:_fe_analyzer_shared/src/flow_analysis/flow_analysis.dart';
67
import 'package:_fe_analyzer_shared/src/testing/id.dart';
78
import 'package:_fe_analyzer_shared/src/util/link.dart';
@@ -82,6 +83,59 @@ bool isOverloadableArithmeticOperator(String name) {
8283
identical(name, '%');
8384
}
8485

86+
/// Given a [FunctionExpression], computes a set whose elements consist of (a)
87+
/// an integer corresponding to the zero-based index of each positional
88+
/// parameter of the function expression that has an explicit type annotation,
89+
/// and (b) a string corresponding to the name of each named parameter of the
90+
/// function expression that has an explicit type annotation.
91+
Set<Object> _computeExplicitlyTypedParameterSet(
92+
FunctionExpression functionExpression) {
93+
Set<Object> result = {};
94+
int unnamedParameterIndex = 0;
95+
for (VariableDeclaration positionalParameter
96+
in functionExpression.function.positionalParameters) {
97+
int key = unnamedParameterIndex++;
98+
if (!(positionalParameter as VariableDeclarationImpl).isImplicitlyTyped) {
99+
result.add(key);
100+
}
101+
}
102+
for (VariableDeclaration namedParameter
103+
in functionExpression.function.namedParameters) {
104+
String key = namedParameter.name!;
105+
if (!(namedParameter as VariableDeclarationImpl).isImplicitlyTyped) {
106+
result.add(key);
107+
}
108+
}
109+
return result;
110+
}
111+
112+
/// Given an function type, computes a map based on the parameters whose keys
113+
/// are either the parameter name (for named parameters) or the zero-based
114+
/// integer index (for unnamed parameters), and whose values are the parameter
115+
/// types.
116+
Map<Object, DartType> _computeParameterMap(FunctionType functionType) => {
117+
for (int i = 0; i < functionType.positionalParameters.length; i++)
118+
i: functionType.positionalParameters[i],
119+
for (NamedType namedType in functionType.namedParameters)
120+
namedType.name: namedType.type
121+
};
122+
123+
/// Computes a list of [_ParamInfo] objects corresponding to the invocation
124+
/// parameters that were *not* deferred.
125+
List<_ParamInfo> _computeUndeferredParamInfo(List<DartType> formalTypes,
126+
List<_DeferredParamInfo> deferredFunctionLiterals) {
127+
// TODO(paulberry): test that the right thing happens when evaluation order differs from classic (positional/named) order.
128+
Set<int> evaluationOrderIndicesAlreadyCovered = {
129+
for (_DeferredParamInfo functionLiteral in deferredFunctionLiterals)
130+
functionLiteral.evaluationOrderIndex
131+
};
132+
return [
133+
for (int i = 0; i < formalTypes.length; i++)
134+
if (!evaluationOrderIndicesAlreadyCovered.contains(i))
135+
new _ParamInfo(formalTypes[i])
136+
];
137+
}
138+
85139
/// Enum denoting the kinds of contravariance check that might need to be
86140
/// inserted for a method call.
87141
enum MethodContravarianceCheckKind {
@@ -2290,7 +2344,8 @@ class TypeInferrerImpl implements TypeInferrer {
22902344
explicitTypeArguments == null &&
22912345
calleeTypeParameters.isNotEmpty;
22922346
bool typeChecksNeeded = !isTopLevel;
2293-
bool useFormalAndActualTypes = typeChecksNeeded ||
2347+
bool useFormalAndActualTypes = inferenceNeeded ||
2348+
typeChecksNeeded ||
22942349
isSpecialCasedBinaryOperator ||
22952350
isSpecialCasedTernaryOperator;
22962351

@@ -2331,7 +2386,7 @@ class TypeInferrerImpl implements TypeInferrer {
23312386
calleeTypeParameters,
23322387
typeContext,
23332388
libraryBuilder.library);
2334-
typeSchemaEnvironment.downwardsInfer(gatherer, calleeTypeParameters,
2389+
typeSchemaEnvironment.partialInfer(gatherer, calleeTypeParameters,
23352390
inferredTypes, libraryBuilder.library);
23362391
substitution =
23372392
Substitution.fromPairs(calleeTypeParameters, inferredTypes);
@@ -2471,6 +2526,7 @@ class TypeInferrerImpl implements TypeInferrer {
24712526
(deferredFunctionLiterals ??= []).add(new _DeferredParamInfo(
24722527
formalType: formalType,
24732528
argumentExpression: argumentExpression,
2529+
unparenthesizedExpression: unparenthesizedExpression,
24742530
isNamed: !isExpression,
24752531
evaluationOrderIndex: evaluationOrderIndex,
24762532
index: index));
@@ -2510,26 +2566,44 @@ class TypeInferrerImpl implements TypeInferrer {
25102566
}
25112567
}
25122568
if (deferredFunctionLiterals != null) {
2513-
for (_DeferredParamInfo deferredArgument in deferredFunctionLiterals) {
2514-
ExpressionInferenceResult result = inferArgument(
2515-
deferredArgument.formalType, deferredArgument.argumentExpression,
2516-
isNamed: deferredArgument.isNamed);
2517-
DartType inferredType = _computeInferredType(result);
2518-
Expression expression = result.expression;
2519-
identicalInfo?[deferredArgument.evaluationOrderIndex] =
2520-
flowAnalysis.equalityOperand_end(expression, inferredType);
2521-
if (deferredArgument.isNamed) {
2522-
NamedExpression namedArgument =
2523-
arguments.named[deferredArgument.index];
2524-
namedArgument.value = expression..parent = namedArgument;
2525-
} else {
2526-
arguments.positional[deferredArgument.index] = expression
2527-
..parent = arguments;
2569+
bool isFirstStage = true;
2570+
for (List<_DeferredParamInfo> stage in new _FunctionLiteralDependencies(
2571+
deferredFunctionLiterals,
2572+
calleeType.typeParameters.toSet(),
2573+
inferenceNeeded
2574+
? _computeUndeferredParamInfo(
2575+
formalTypes!, deferredFunctionLiterals)
2576+
: const [])
2577+
.planReconciliationStages()) {
2578+
if (gatherer != null && !isFirstStage) {
2579+
typeSchemaEnvironment.partialInfer(gatherer, calleeTypeParameters,
2580+
inferredTypes!, libraryBuilder.library);
2581+
substitution =
2582+
Substitution.fromPairs(calleeTypeParameters, inferredTypes);
25282583
}
2529-
gatherer?.tryConstrainLower(deferredArgument.formalType, inferredType);
2530-
if (useFormalAndActualTypes) {
2531-
actualTypes![deferredArgument.evaluationOrderIndex] = inferredType;
2584+
for (_DeferredParamInfo deferredArgument in stage) {
2585+
ExpressionInferenceResult result = inferArgument(
2586+
deferredArgument.formalType, deferredArgument.argumentExpression,
2587+
isNamed: deferredArgument.isNamed);
2588+
DartType inferredType = _computeInferredType(result);
2589+
Expression expression = result.expression;
2590+
identicalInfo?[deferredArgument.evaluationOrderIndex] =
2591+
flowAnalysis.equalityOperand_end(expression, inferredType);
2592+
if (deferredArgument.isNamed) {
2593+
NamedExpression namedArgument =
2594+
arguments.named[deferredArgument.index];
2595+
namedArgument.value = expression..parent = namedArgument;
2596+
} else {
2597+
arguments.positional[deferredArgument.index] = expression
2598+
..parent = arguments;
2599+
}
2600+
gatherer?.tryConstrainLower(
2601+
deferredArgument.formalType, inferredType);
2602+
if (useFormalAndActualTypes) {
2603+
actualTypes![deferredArgument.evaluationOrderIndex] = inferredType;
2604+
}
25322605
}
2606+
isFirstStage = false;
25332607
}
25342608
}
25352609
if (identicalInfo != null) {
@@ -5967,15 +6041,14 @@ class ImplicitInstantiation {
59676041
/// Information about an invocation argument that needs to be resolved later due
59686042
/// to the fact that it's a function literal and the `inference-update-1`
59696043
/// feature is enabled.
5970-
class _DeferredParamInfo {
5971-
/// The (unsubstituted) type of the formal parameter corresponding to this
5972-
/// argument.
5973-
final DartType formalType;
5974-
6044+
class _DeferredParamInfo extends _ParamInfo {
59756045
/// The argument expression (possibly wrapped in an arbitrary number of
59766046
/// ParenthesizedExpressions).
59776047
final Expression argumentExpression;
59786048

6049+
/// The unparenthesized argument expression.
6050+
final FunctionExpression unparenthesizedExpression;
6051+
59796052
/// Indicates whether this is a named argument.
59806053
final bool isNamed;
59816054

@@ -5988,9 +6061,63 @@ class _DeferredParamInfo {
59886061
final int index;
59896062

59906063
_DeferredParamInfo(
5991-
{required this.formalType,
6064+
{required DartType formalType,
59926065
required this.argumentExpression,
6066+
required this.unparenthesizedExpression,
59936067
required this.isNamed,
59946068
required this.evaluationOrderIndex,
5995-
required this.index});
6069+
required this.index})
6070+
: super(formalType);
6071+
}
6072+
6073+
/// Extension of the shared [FunctionLiteralDependencies] logic used by the
6074+
/// front end.
6075+
class _FunctionLiteralDependencies extends FunctionLiteralDependencies<
6076+
TypeParameter, _ParamInfo, _DeferredParamInfo> {
6077+
_FunctionLiteralDependencies(
6078+
Iterable<_DeferredParamInfo> deferredParamInfo,
6079+
Iterable<TypeParameter> typeVariables,
6080+
List<_ParamInfo> undeferredParamInfo)
6081+
: super(deferredParamInfo, typeVariables, undeferredParamInfo);
6082+
6083+
@override
6084+
Iterable<TypeParameter> typeVarsFreeInParamParams(
6085+
_DeferredParamInfo paramInfo) {
6086+
DartType type = paramInfo.formalType;
6087+
if (type is FunctionType) {
6088+
Map<Object, DartType> parameterMap = _computeParameterMap(type);
6089+
Set<Object> explicitlyTypedParameters =
6090+
_computeExplicitlyTypedParameterSet(
6091+
paramInfo.unparenthesizedExpression);
6092+
Set<TypeParameter> result = {};
6093+
for (MapEntry<Object, DartType> entry in parameterMap.entries) {
6094+
if (explicitlyTypedParameters.contains(entry.key)) continue;
6095+
result.addAll(allFreeTypeVariables(entry.value));
6096+
}
6097+
return result;
6098+
} else {
6099+
return const [];
6100+
}
6101+
}
6102+
6103+
@override
6104+
Iterable<TypeParameter> typeVarsFreeInParamReturns(_ParamInfo paramInfo) {
6105+
DartType type = paramInfo.formalType;
6106+
if (type is FunctionType) {
6107+
return allFreeTypeVariables(type.returnType);
6108+
} else {
6109+
return allFreeTypeVariables(type);
6110+
}
6111+
}
6112+
}
6113+
6114+
/// Information about an invocation argument that may or may not have already
6115+
/// been resolved, as part of the deferred resolution mechanism for the
6116+
/// `inference-update-1` feature.
6117+
class _ParamInfo {
6118+
/// The (unsubstituted) type of the formal parameter corresponding to this
6119+
/// argument.
6120+
final DartType formalType;
6121+
6122+
_ParamInfo(this.formalType);
59966123
}

pkg/front_end/lib/src/fasta/type_inference/type_schema_environment.dart

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -128,9 +128,9 @@ class TypeSchemaEnvironment extends HierarchyBasedTypeEnvironment
128128
getStandardLowerBound(constraint.upper, upper, clientLibrary);
129129
}
130130

131-
/// Performs downwards inference, producing a set of inferred types that may
132-
/// contain references to the "unknown type".
133-
void downwardsInfer(
131+
/// Performs partial (either downwards or horizontal) inference, producing a
132+
/// set of inferred types that may contain references to the "unknown type".
133+
void partialInfer(
134134
TypeConstraintGatherer gatherer,
135135
List<TypeParameter> typeParametersToInfer,
136136
List<DartType> inferredTypes,

pkg/front_end/test/fasta/type_inference/type_schema_environment_test_base.dart

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -171,8 +171,8 @@ abstract class TypeSchemaEnvironmentTestBase {
171171
returnContextTypeNode,
172172
testLibrary);
173173
if (formalTypeNodes == null) {
174-
typeSchemaEnvironment.downwardsInfer(gatherer,
175-
typeParameterNodesToInfer, inferredTypeNodes, testLibrary);
174+
typeSchemaEnvironment.partialInfer(gatherer, typeParameterNodesToInfer,
175+
inferredTypeNodes, testLibrary);
176176
} else {
177177
gatherer.constrainArguments(formalTypeNodes, actualTypeNodes!);
178178
typeSchemaEnvironment.upwardsInfer(gatherer, typeParameterNodesToInfer,

0 commit comments

Comments
 (0)