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

Unified Diff: pkg/analyzer/lib/src/generated/type_system.dart

Issue 2215873002: fix #26512, correct handling of fuzzy arrows in strong mode LUB (Closed) Base URL: git@github.com:dart-lang/sdk.git@master
Patch Set: rebase & fix pass through of arg Created 4 years, 4 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
« no previous file with comments | « no previous file | pkg/analyzer/test/generated/type_system_test.dart » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: pkg/analyzer/lib/src/generated/type_system.dart
diff --git a/pkg/analyzer/lib/src/generated/type_system.dart b/pkg/analyzer/lib/src/generated/type_system.dart
index fb823260619f025fdc3ea6a5a279041f352537e6..44e6eb02321adc1f76118de9e4a1fbe73752824c 100644
--- a/pkg/analyzer/lib/src/generated/type_system.dart
+++ b/pkg/analyzer/lib/src/generated/type_system.dart
@@ -91,26 +91,24 @@ class StrongTypeSystemImpl extends TypeSystem {
/// Computes the greatest lower bound of [type1] and [type2].
DartType getGreatestLowerBound(
- TypeProvider provider, DartType type1, DartType type2) {
+ TypeProvider provider, DartType type1, DartType type2,
+ {dynamicIsBottom: false}) {
// The greatest lower bound relation is reflexive.
if (identical(type1, type2)) {
return type1;
}
- // Treat dynamic as top. The GLB of dynamic and any type is just that type
- // since dynamic permits all values.
- if (type1.isDynamic) {
+ // The GLB of top and any type is just that type.
+ // Also GLB of bottom and any type is bottom.
+ if (_isTop(type1, dynamicIsBottom: dynamicIsBottom) ||
+ _isBottom(type2, dynamicIsBottom: dynamicIsBottom)) {
return type2;
}
- if (type2.isDynamic) {
+ if (_isTop(type2, dynamicIsBottom: dynamicIsBottom) ||
+ _isBottom(type1, dynamicIsBottom: dynamicIsBottom)) {
return type1;
}
- // You can't get any lower than bottom.
- if (type1.isBottom || type2.isBottom) {
- return provider.bottomType;
- }
-
// Treat void as top-like for GLB. This only comes into play with the
// return types of two functions whose GLB is being taken. We allow a
// non-void-returning function to subtype a void-returning one, so match
@@ -146,7 +144,8 @@ class StrongTypeSystemImpl extends TypeSystem {
*/
@override
DartType getLeastUpperBound(
- TypeProvider typeProvider, DartType type1, DartType type2) {
+ TypeProvider typeProvider, DartType type1, DartType type2,
+ {bool dynamicIsBottom: false}) {
if (isNullableType(type1) && isNonNullableType(type2)) {
assert(type2 is InterfaceType);
type2 = getLeastNullableSupertype(type2 as InterfaceType);
@@ -155,7 +154,8 @@ class StrongTypeSystemImpl extends TypeSystem {
assert(type1 is InterfaceType);
type1 = getLeastNullableSupertype(type1 as InterfaceType);
}
- return super.getLeastUpperBound(typeProvider, type1, type2);
+ return super.getLeastUpperBound(typeProvider, type1, type2,
+ dynamicIsBottom: dynamicIsBottom);
}
/**
@@ -476,7 +476,8 @@ class StrongTypeSystemImpl extends TypeSystem {
DartType paramType;
if (fType != null && gType != null) {
// If both functions have this parameter, include both of their types.
- paramType = getLeastUpperBound(provider, fType, gType);
+ paramType =
+ getLeastUpperBound(provider, fType, gType, dynamicIsBottom: true);
} else {
paramType = fType ?? gType;
}
@@ -560,7 +561,7 @@ class StrongTypeSystemImpl extends TypeSystem {
@override
DartType _functionParameterBound(
TypeProvider provider, DartType f, DartType g) =>
- getGreatestLowerBound(provider, f, g);
+ getGreatestLowerBound(provider, f, g, dynamicIsBottom: true);
/**
* Guard against loops in the class hierarchy
@@ -639,10 +640,6 @@ class StrongTypeSystemImpl extends TypeSystem {
provider.dynamicType;
}
- bool _isBottom(DartType t, {bool dynamicIsBottom: false}) {
- return (t.isDynamic && dynamicIsBottom) || t.isBottom;
- }
-
/**
* Check that [f1] is a subtype of [f2].
*
@@ -791,11 +788,6 @@ class StrongTypeSystemImpl extends TypeSystem {
return _isFunctionSubtypeOf(t1 as FunctionType, t2 as FunctionType);
}
- bool _isTop(DartType t, {bool dynamicIsBottom: false}) {
- // TODO(leafp): Document the rules in play here
- return (t.isDynamic && !dynamicIsBottom) || t.isObject;
- }
-
/// Check if [type] is in a set of preselected non-nullable types.
/// [FunctionType]s are always nullable.
bool isNonNullableType(DartType type) {
@@ -914,16 +906,20 @@ abstract class TypeSystem {
* Compute the least upper bound of two types.
*/
DartType getLeastUpperBound(
- TypeProvider typeProvider, DartType type1, DartType type2) {
+ TypeProvider typeProvider, DartType type1, DartType type2,
+ {dynamicIsBottom: false}) {
// The least upper bound relation is reflexive.
if (identical(type1, type2)) {
return type1;
}
- // The least upper bound of dynamic and any type T is dynamic.
- if (type1.isDynamic) {
+ // The least upper bound of top and any type T is top.
+ // The least upper bound of bottom and any type T is T.
+ if (_isTop(type1, dynamicIsBottom: dynamicIsBottom) ||
+ _isBottom(type2, dynamicIsBottom: dynamicIsBottom)) {
return type1;
}
- if (type2.isDynamic) {
+ if (_isTop(type2, dynamicIsBottom: dynamicIsBottom) ||
+ _isBottom(type1, dynamicIsBottom: dynamicIsBottom)) {
return type2;
}
// The least upper bound of void and any type T != dynamic is void.
@@ -933,13 +929,6 @@ abstract class TypeSystem {
if (type2.isVoid) {
return type2;
}
- // The least upper bound of bottom and any type T is T.
- if (type1.isBottom) {
- return type2;
- }
- if (type2.isBottom) {
- return type1;
- }
if (type1 is TypeParameterType || type2 is TypeParameterType) {
return _typeParameterLeastUpperBound(typeProvider, type1, type2);
@@ -1557,3 +1546,12 @@ class _TypeParameterVariance {
}
}
}
+
+bool _isBottom(DartType t, {bool dynamicIsBottom: false}) {
+ return (t.isDynamic && dynamicIsBottom) || t.isBottom;
+}
+
+bool _isTop(DartType t, {bool dynamicIsBottom: false}) {
+ // TODO(leafp): Document the rules in play here
+ return (t.isDynamic && !dynamicIsBottom) || t.isObject;
+}
« no previous file with comments | « no previous file | pkg/analyzer/test/generated/type_system_test.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698