[dart2bytecode] Throw exception instead of crashing when external member is called

TEST=ci

Change-Id: I60a598dd5f8ac05a4f5f3283d257c2c6a74490e1
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/384820
Reviewed-by: Slava Egorov <vegorov@google.com>
Commit-Queue: Alexander Markov <alexmarkov@google.com>
This commit is contained in:
Alexander Markov
2024-09-12 14:52:58 +00:00
committed by Commit Queue
parent b3e1eec36f
commit 80b092de04
2 changed files with 20 additions and 9 deletions
+20 -7
View File
@@ -808,7 +808,7 @@ class BytecodeGenerator extends RecursiveVisitor {
_genConstructorInitializers(node);
}
if (node.isExternal) {
_unimplemented(node, 'external member');
_genNoSuchMethodForExternal(node);
} else {
_generateNode(node.function?.body);
// BytecodeAssembler eliminates this bytecode if it is unreachable.
@@ -939,6 +939,9 @@ class BytecodeGenerator extends RecursiveVisitor {
late Procedure throwNewAssertionError =
libraryIndex.getProcedure('dart:core', '_AssertionError', '_throwNew');
late Procedure throwNewNoSuchMethodError =
libraryIndex.getProcedure('dart:core', 'NoSuchMethodError', '_throwNew');
late Procedure allocateInvocationMirror = libraryIndex.getProcedure(
'dart:core', '_InvocationMirror', '_allocateInvocationMirror');
@@ -2726,6 +2729,22 @@ class BytecodeGenerator extends RecursiveVisitor {
_genDirectCall(target, objectTable.getArgDescHandle(2), 2);
}
void _genNoSuchMethodForExternal(Member node) {
if (node.isInstanceMember) {
_genPushReceiver(); // receiver.
} else {
asm.emitPushNull();
}
asm.emitPushConstant(cp.addString(node.name.text)); // memberName.
asm.emitPushInt(0); // invocationType.
asm.emitPushInt(0); // typeArgumentsLength.
asm.emitPushNull(); // typeArguments.
asm.emitPushNull(); // arguments.
asm.emitPushNull(); // argumentNames.
_genDirectCall(
throwNewNoSuchMethodError, objectTable.getArgDescHandle(7), 7);
}
@override
void defaultTreeNode(Node node) => throw new UnsupportedOperationError(
'Unsupported node ${node.runtimeType}');
@@ -4433,12 +4452,6 @@ class BytecodeGenerator extends RecursiveVisitor {
throw 'Unexpected ${enclosingFunction!.dartAsyncMarker}';
}
}
void _unimplemented(TreeNode node, String what) {
print('Unimplemented $what at ${node.location}');
asm.emitTrap();
asm.isUnreachable = false;
}
}
class UnsupportedOperationError {
-2
View File
@@ -33,8 +33,6 @@ switch/case_warn_test: Skip # Analyzer only, see language_analyzer2.status
[ $compiler == dart2bytecode ]
class_modifiers/trans_legacy/legacy_superdeclaration_test: Crash
const/inference_test: Crash
constructor/external_constructor_test: Crash
external_abstract_fields/external_fields_test: Crash
final/syntax_test/08: Crash
regress/regress45763_test: Crash
vm/reflect_core_vm_test: Crash