[dart2js] Use correct futureValueType.
Fixes: #54317
Change-Id: Id94b486df6a66ef6c77f2c578ab8d11a73189ff9
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/341328
Reviewed-by: Sigmund Cherem <sigmund@google.com>
Commit-Queue: Mayank Patke <fishythefish@google.com>
diff --git a/pkg/compiler/lib/src/common/elements.dart b/pkg/compiler/lib/src/common/elements.dart
index 34dbf15..8468322 100644
--- a/pkg/compiler/lib/src/common/elements.dart
+++ b/pkg/compiler/lib/src/common/elements.dart
@@ -1496,10 +1496,10 @@
/// argument is passed.
DartType getTypeVariableDefaultType(TypeVariableEntity typeVariable);
- /// Returns the 'element' type of a function with the async, async* or sync*
- /// marker [marker]. [returnType] is the return type marked function.
+ /// Returns the 'element' type of a [function] with the async, async* or sync*
+ /// marker. [returnType] is the return type of the marked function.
DartType getAsyncOrSyncStarElementType(
- AsyncMarker marker, DartType returnType);
+ FunctionEntity function, DartType returnType);
/// Returns the 'element' type of a function with an async, async* or sync*
/// marker. The return type of the method is inspected to determine the type
diff --git a/pkg/compiler/lib/src/js_model/element_map.dart b/pkg/compiler/lib/src/js_model/element_map.dart
index 4019f5c..0c4f6f7 100644
--- a/pkg/compiler/lib/src/js_model/element_map.dart
+++ b/pkg/compiler/lib/src/js_model/element_map.dart
@@ -235,12 +235,18 @@
case MemberKind.constructorBody:
ir.Member node = definition.node as ir.Member;
return node.function;
+ case MemberKind.generatorBody:
+ final node = definition.node;
+ if (node is ir.LocalFunction) return node.function;
+ return (node as ir.Member).function;
case MemberKind.closureCall:
ir.LocalFunction node = definition.node as ir.LocalFunction;
return node.function;
- default:
+ case MemberKind.closureField:
+ case MemberKind.signature:
+ case MemberKind.recordGetter:
+ return null;
}
- return null;
}
/// Returns the initializer for [field].
diff --git a/pkg/compiler/lib/src/js_model/element_map_impl.dart b/pkg/compiler/lib/src/js_model/element_map_impl.dart
index 5ea8aaa..bf0a945 100644
--- a/pkg/compiler/lib/src/js_model/element_map_impl.dart
+++ b/pkg/compiler/lib/src/js_model/element_map_impl.dart
@@ -2221,13 +2221,14 @@
DartType getFunctionAsyncOrSyncStarElementType(FunctionEntity function) {
// TODO(sra): Should be getting the DartType from the node.
DartType returnType = getFunctionType(function).returnType;
- return getAsyncOrSyncStarElementType(function.asyncMarker, returnType);
+ return getAsyncOrSyncStarElementType(function, returnType);
}
@override
DartType getAsyncOrSyncStarElementType(
- AsyncMarker asyncMarker, DartType returnType) {
- var returnTypeWithoutNullability = returnType.withoutNullability;
+ FunctionEntity function, DartType returnType) {
+ final asyncMarker = function.asyncMarker;
+ final returnTypeWithoutNullability = returnType.withoutNullability;
switch (asyncMarker) {
case AsyncMarker.SYNC:
return returnType;
@@ -2240,16 +2241,8 @@
}
return dynamicType;
case AsyncMarker.ASYNC:
- if (returnTypeWithoutNullability is FutureOrType) {
- return returnTypeWithoutNullability.typeArgument;
- }
- if (returnTypeWithoutNullability is InterfaceType) {
- if (returnTypeWithoutNullability.element ==
- elementMap.commonElements.futureClass) {
- return returnTypeWithoutNullability.typeArguments.first;
- }
- }
- return dynamicType;
+ return elementMap.getDartType(
+ getFunctionNode(elementMap, function)!.futureValueType!);
case AsyncMarker.ASYNC_STAR:
if (returnTypeWithoutNullability is InterfaceType) {
if (returnTypeWithoutNullability.element ==
diff --git a/pkg/compiler/lib/src/ssa/builder.dart b/pkg/compiler/lib/src/ssa/builder.dart
index c2c2186..9853b3b 100644
--- a/pkg/compiler/lib/src/ssa/builder.dart
+++ b/pkg/compiler/lib/src/ssa/builder.dart
@@ -1367,7 +1367,7 @@
// Add the type parameter for the generator's element type.
DartType elementType = _elementEnvironment.getAsyncOrSyncStarElementType(
- function.asyncMarker, _returnType!);
+ function, _returnType!);
// TODO(sra): [elementType] can contain free type variables that are erased
// due to no rtiNeed. We will get getter code if these type variables are
@@ -1454,7 +1454,7 @@
// Call `_makeSyncStarIterable<T>(body)`. This usually gets inlined.
final elementType = _elementEnvironment.getAsyncOrSyncStarElementType(
- function.asyncMarker, _returnType!);
+ function, _returnType!);
FunctionEntity method = _commonElements.syncStarIterableFactory;
List<HInstruction> arguments = [pop()];
List<DartType> typeArguments = const [];
diff --git a/tests/web/regress/issue/54317_test.dart b/tests/web/regress/issue/54317_test.dart
new file mode 100644
index 0000000..e4195f1
--- /dev/null
+++ b/tests/web/regress/issue/54317_test.dart
@@ -0,0 +1,13 @@
+// Copyright (c) 2023, the Dart project authors. Please see the AUTHORS file
+// for details. All rights reserved. Use of this source code is governed by a
+// BSD-style license that can be found in the LICENSE file.
+
+import 'dart:async';
+import 'package:expect/expect.dart';
+
+void main() async {
+ final value = await fn();
+ Expect.equals(42, value);
+}
+
+FutureOr<Object> fn() async => 42;