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

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

Issue 2280023004: fix #27155, do not push down dynamic as context type (Closed)
Patch Set: add test 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
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 1abf232d518fffbe778f29b558fdeb9853f5e3e3..5fe01809c919444f19301184009e7854ca4b0681 100644
--- a/pkg/analyzer/lib/src/generated/type_system.dart
+++ b/pkg/analyzer/lib/src/generated/type_system.dart
@@ -1607,21 +1607,14 @@ class FutureUnionType extends TypeImpl {
final List<DartType> _types;
/**
- * Creates a union of `Future< flatten(T) > | flatten(T)`.
+ * Creates a union of `Future<T> | T`.
*/
- factory FutureUnionType(
- DartType type, TypeProvider provider, TypeSystem system) {
- type = type.flattenFutures(system);
-
- // The order of these types is important: T could be a type variable, so
- // we want to try and match `Future<T>` before we try and match `T`.
- return new FutureUnionType._([
- provider.futureType.instantiate([type]),
- type
- ]);
- }
-
- FutureUnionType._(this._types) : super(null, null);
+ FutureUnionType._(DartType type, TypeProvider provider, TypeSystem system)
+ : _types = [
+ provider.futureType.instantiate([type]),
+ type
+ ],
+ super(null, null);
DartType get futureOfType => _types[0];
@@ -1676,15 +1669,39 @@ class FutureUnionType extends TypeImpl {
throw new UnsupportedError('Future unions are not used in typedefs');
/**
- * Creates a union of `flatten(T) | Future<flatten(T)>`, unless `T` is
- * already a future-union, in which case it simply returns `T`
+ * Creates a union of `T | Future<T>`, unless `T` is already a future or a
+ * future-union, in which case it simply returns `T`.
+ *
+ * Conceptually this is used as the inverse of the `flatten(T)` operation,
+ * defined as:
+ *
+ * - `flatten(Future<T>) -> T`
+ * - `flatten(T) -> T`
+ *
+ * Thus the inverse will give us `T | Future<T>`.
+ *
+ * If [type] is top (dynamic or Object) then the resulting union type is
+ * equivalent to top, so we simply return it.
+ *
+ * For a similar reason `Future<T> | Future<Future<T>>` is equivalent to just
+ * `Future<T>`, so we return it. Note that it is not possible to get a
+ * `Future<T>` as a result of `flatten`, so a this case likely indicates a
+ * type error in the code, but it will be reported elsewhere.
*/
static DartType from(
DartType type, TypeProvider provider, TypeSystem system) {
+ if (_isTop(type)) {
+ return type;
+ }
+ if (!identical(type, type.flattenFutures(system))) {
+ // As noted above, this most likely represents erroneous input.
+ return type;
+ }
+
if (type is FutureUnionType) {
return type;
}
- return new FutureUnionType(type, provider, system);
+ return new FutureUnionType._(type, provider, system);
}
}
« no previous file with comments | « pkg/analyzer/lib/src/generated/resolver.dart ('k') | pkg/analyzer/test/src/task/strong/inferred_type_test.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698