mirror of
https://github.com/dart-lang/sdk
synced 2024-09-16 04:16:51 +00:00
[dart2wasm] Emit correct runtime type for tear-offs
The static type of a tear-off is the signature type of the method. The runtime type is the same with the types of all covariant parameters replaced by `Object?`. Change-Id: I9bb36a36ec04e27deab2b31c977fadac515ad561 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/273845 Reviewed-by: Joshua Litt <joshualitt@google.com>
This commit is contained in:
parent
ad06d73ace
commit
8c717be409
|
@ -197,8 +197,7 @@ class CodeGenerator extends ExpressionVisitor1<w.ValueType, w.ValueType>
|
||||||
|
|
||||||
void generateTearOffGetter(Procedure procedure) {
|
void generateTearOffGetter(Procedure procedure) {
|
||||||
_initializeThis(member);
|
_initializeThis(member);
|
||||||
DartType functionType =
|
DartType functionType = translator.getTearOffType(procedure);
|
||||||
procedure.function.computeFunctionType(Nullability.nonNullable);
|
|
||||||
ClosureImplementation closure = translator.getTearOffClosure(procedure);
|
ClosureImplementation closure = translator.getTearOffClosure(procedure);
|
||||||
w.StructType struct = closure.representation.closureStruct;
|
w.StructType struct = closure.representation.closureStruct;
|
||||||
|
|
||||||
|
@ -1842,7 +1841,7 @@ class CodeGenerator extends ExpressionVisitor1<w.ValueType, w.ValueType>
|
||||||
// Super tear-off
|
// Super tear-off
|
||||||
w.StructType closureStruct = _pushClosure(
|
w.StructType closureStruct = _pushClosure(
|
||||||
translator.getTearOffClosure(target),
|
translator.getTearOffClosure(target),
|
||||||
target.function.computeFunctionType(Nullability.nonNullable),
|
translator.getTearOffType(target),
|
||||||
() => visitThis(w.RefType.data(nullable: false)));
|
() => visitThis(w.RefType.data(nullable: false)));
|
||||||
return w.RefType.def(closureStruct, nullable: false);
|
return w.RefType.def(closureStruct, nullable: false);
|
||||||
}
|
}
|
||||||
|
|
|
@ -521,8 +521,8 @@ class ConstantCreator extends ConstantVisitor<ConstantInfo?> {
|
||||||
@override
|
@override
|
||||||
ConstantInfo? visitStaticTearOffConstant(StaticTearOffConstant constant) {
|
ConstantInfo? visitStaticTearOffConstant(StaticTearOffConstant constant) {
|
||||||
Procedure member = constant.targetReference.asProcedure;
|
Procedure member = constant.targetReference.asProcedure;
|
||||||
Constant functionTypeConstant = TypeLiteralConstant(
|
Constant functionTypeConstant =
|
||||||
member.function.computeFunctionType(Nullability.nonNullable));
|
TypeLiteralConstant(translator.getTearOffType(member));
|
||||||
ensureConstant(functionTypeConstant);
|
ensureConstant(functionTypeConstant);
|
||||||
ClosureImplementation closure = translator.getTearOffClosure(member);
|
ClosureImplementation closure = translator.getTearOffClosure(member);
|
||||||
w.StructType struct = closure.representation.closureStruct;
|
w.StructType struct = closure.representation.closureStruct;
|
||||||
|
@ -550,7 +550,7 @@ class ConstantCreator extends ConstantVisitor<ConstantInfo?> {
|
||||||
.toList();
|
.toList();
|
||||||
Procedure tearOffProcedure = tearOffConstant.targetReference.asProcedure;
|
Procedure tearOffProcedure = tearOffConstant.targetReference.asProcedure;
|
||||||
FunctionType tearOffFunctionType =
|
FunctionType tearOffFunctionType =
|
||||||
tearOffProcedure.function.computeFunctionType(Nullability.nonNullable);
|
translator.getTearOffType(tearOffProcedure);
|
||||||
FunctionType instantiatedFunctionType = Substitution.fromPairs(
|
FunctionType instantiatedFunctionType = Substitution.fromPairs(
|
||||||
tearOffFunctionType.typeParameters, constant.types)
|
tearOffFunctionType.typeParameters, constant.types)
|
||||||
.substituteType(tearOffFunctionType.withoutTypeParameters)
|
.substituteType(tearOffFunctionType.withoutTypeParameters)
|
||||||
|
|
|
@ -330,6 +330,40 @@ class Translator with KernelNodes {
|
||||||
: coreTypes.objectClass;
|
: coreTypes.objectClass;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Compute the runtime type of a tear-off. This is the signature of the
|
||||||
|
/// method with the types of all covariant parameters replaced by `Object?`.
|
||||||
|
FunctionType getTearOffType(Procedure method) {
|
||||||
|
assert(method.kind == ProcedureKind.Method);
|
||||||
|
final FunctionType staticType = method.getterType as FunctionType;
|
||||||
|
|
||||||
|
final positionalParameters = List.of(staticType.positionalParameters);
|
||||||
|
assert(positionalParameters.length ==
|
||||||
|
method.function.positionalParameters.length);
|
||||||
|
for (int i = 0; i < positionalParameters.length; i++) {
|
||||||
|
final param = method.function.positionalParameters[i];
|
||||||
|
if (param.isCovariantByDeclaration || param.isCovariantByClass) {
|
||||||
|
positionalParameters[i] = coreTypes.objectNullableRawType;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
final namedParameters = List.of(staticType.namedParameters);
|
||||||
|
assert(namedParameters.length == method.function.namedParameters.length);
|
||||||
|
for (int i = 0; i < namedParameters.length; i++) {
|
||||||
|
final param = method.function.namedParameters[i];
|
||||||
|
if (param.isCovariantByDeclaration || param.isCovariantByClass) {
|
||||||
|
namedParameters[i] = NamedType(
|
||||||
|
namedParameters[i].name, coreTypes.objectNullableRawType,
|
||||||
|
isRequired: namedParameters[i].isRequired);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return FunctionType(
|
||||||
|
positionalParameters, staticType.returnType, Nullability.nonNullable,
|
||||||
|
namedParameters: namedParameters,
|
||||||
|
typeParameters: staticType.typeParameters,
|
||||||
|
requiredParameterCount: staticType.requiredParameterCount);
|
||||||
|
}
|
||||||
|
|
||||||
/// Creates a [Tag] for a void [FunctionType] with two parameters,
|
/// Creates a [Tag] for a void [FunctionType] with two parameters,
|
||||||
/// a [topInfo.nonNullableType] parameter to hold an exception, and a
|
/// a [topInfo.nonNullableType] parameter to hold an exception, and a
|
||||||
/// [stackTraceInfo.nonNullableType] to hold a stack trace. This single
|
/// [stackTraceInfo.nonNullableType] to hold a stack trace. This single
|
||||||
|
|
Loading…
Reference in a new issue