Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1385)

Unified Diff: lib/src/checker/rules.dart

Issue 1050703002: Downwards closure inference (Closed) Base URL: git@github.com:dart-lang/dart-dev-compiler.git@master
Patch Set: Created 5 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: lib/src/checker/rules.dart
diff --git a/lib/src/checker/rules.dart b/lib/src/checker/rules.dart
index 5fe33e6f811ca1fba3e9cb48f4be27fde31d851c..cfa9d74ed93b8b5ff62e644257c3f751128a8d14 100644
--- a/lib/src/checker/rules.dart
+++ b/lib/src/checker/rules.dart
@@ -570,6 +570,7 @@ class DownwardsInference {
bool inferExpression(Expression e, DartType t) {
if (e is Conversion) return inferExpression(e.node, t);
if (rules.isSubTypeOf(rules.getStaticType(e), t)) return true;
+ if (e is FunctionExpression) return _inferFunctionExpression(e, t);
if (e is ListLiteral) return _inferListLiteral(e, t);
if (e is MapLiteral) return _inferMapLiteral(e, t);
if (e is NamedExpression) return _inferNamedExpression(e, t);
@@ -723,6 +724,29 @@ class DownwardsInference {
return inferExpression(e.expression, t);
}
+ bool _inferFunctionExpression(FunctionExpression e, DartType t) {
+ if (t is! FunctionType) return false;
+ var returnT = (t as FunctionType).returnType;
+ if (returnT.isDynamic) return false;
vsm 2015/04/01 00:14:19 Why do we disallow this? In this case, typedef F
Leaf 2015/04/03 00:51:55 Eventually, yes. As it stands, no. I don't impro
+ var eType = e.staticType;
+ if (eType is! FunctionType) return false;
+ if (e.body is! ExpressionFunctionBody) return false;
+ var body = (e.body as ExpressionFunctionBody).expression;
+ if (!inferExpression(body, returnT)) return false;
+ // TODO(leafp): Try narrowing the argument types if possible
+ // to get better code in the function body. This requires checking
+ // that the body is well-typed at the more specific type.
+ (e.element as ExecutableElementImpl).returnType = returnT;
+ // Work around dynamic as bottom for now by handling function literals
+ // with dynamic arguments specially. We already know the body is typable
+ // at the chosen type, and if all args are dynamic, then function must be
+ // typeable.
+ if ((eType as FunctionType).parameters.every((x) => x.type.isDynamic)) {
+ return true;
+ }
+ return rules.isSubTypeOf(e.staticType, t);
vsm 2015/04/01 00:14:19 Should we have changed e.element.returnType if the
Leaf 2015/04/03 00:51:55 Probably not. Probably doesn't matter, but still
+ }
+
bool _inferListLiteral(ListLiteral e, DartType t) {
var dyn = rules.provider.dynamicType;
var listT = rules.provider.listType.substitute4([dyn]);

Powered by Google App Engine
This is Rietveld 408576698