@@ -6,7 +6,7 @@ import 'package:kernel/ast.dart';
66import 'package:wasm_builder/wasm_builder.dart' as w;
77
88import 'class_info.dart' ;
9- import 'code_generator.dart' show MacroAssembler;
9+ import 'code_generator.dart' show CallTarget, CodeGenerator, MacroAssembler;
1010import 'dispatch_table.dart' ;
1111import 'reference_extensions.dart' ;
1212import 'translator.dart' ;
@@ -18,36 +18,61 @@ class DynamicForwarders {
1818 final Translator translator;
1919 final w.ModuleBuilder callingModule;
2020
21- final Map <String , Forwarder > _getterForwarderOfName = {};
22- final Map <String , Forwarder > _setterForwarderOfName = {};
23- final Map <String , Forwarder > _methodForwarderOfName = {};
21+ final Map <String , CallTarget > _getterForwarderOfName = {};
22+ final Map <String , CallTarget > _setterForwarderOfName = {};
23+ final Map <String , CallTarget > _methodForwarderOfName = {};
2424
2525 DynamicForwarders (this .translator, this .callingModule);
2626
27- Forwarder getDynamicGetForwarder (String memberName) =>
28- _getterForwarderOfName[memberName] ?? = Forwarder ._(
29- translator, _ForwarderKind .Getter , memberName, callingModule)
30- .._generateCode (translator);
27+ CallTarget getDynamicGetForwarder (String memberName) =>
28+ _getterForwarderOfName[memberName] ?? = _DynamicForwarderCallTarget (
29+ translator, _ForwarderKind .Getter , memberName, callingModule);
3130
32- Forwarder getDynamicSetForwarder (String memberName) =>
33- _setterForwarderOfName[memberName] ?? = Forwarder ._(
34- translator, _ForwarderKind .Setter , memberName, callingModule)
35- .._generateCode (translator);
31+ CallTarget getDynamicSetForwarder (String memberName) =>
32+ _setterForwarderOfName[memberName] ?? = _DynamicForwarderCallTarget (
33+ translator, _ForwarderKind .Setter , memberName, callingModule);
3634
37- Forwarder getDynamicInvocationForwarder (String memberName) {
35+ CallTarget getDynamicInvocationForwarder (String memberName) {
3836 // Add Wasm function to the map before generating the forwarder code, to
3937 // allow recursive calls in the "call" forwarder.
4038 var forwarder = _methodForwarderOfName[memberName];
4139 if (forwarder == null ) {
42- forwarder = Forwarder ._ (
40+ forwarder = _DynamicForwarderCallTarget (
4341 translator, _ForwarderKind .Method , memberName, callingModule);
4442 _methodForwarderOfName[memberName] = forwarder;
45- forwarder._generateCode (translator);
4643 }
4744 return forwarder;
4845 }
4946}
5047
48+ class _DynamicForwarderCallTarget extends CallTarget {
49+ final Translator translator;
50+ final _ForwarderKind _kind;
51+ final String memberName;
52+ final w.ModuleBuilder callingModule;
53+
54+ _DynamicForwarderCallTarget (
55+ this .translator, this ._kind, this .memberName, this .callingModule)
56+ : assert (! translator.isDynamicSubmodule ||
57+ (memberName == 'call' && _kind == _ForwarderKind .Getter )),
58+ super (_kind.functionType (translator));
59+
60+ @override
61+ String get name => 'Dynamic $_kind forwarder for "$memberName "' ;
62+
63+ @override
64+ bool get supportsInlining => false ;
65+
66+ @override
67+ late final w.BaseFunction function = (() {
68+ final function = callingModule.functions.define (signature, name);
69+ final forwarder =
70+ _DynamicForwarderCodeGenerator (translator, _kind, memberName, function);
71+ translator.compilationQueue.add (CompilationTask (function, forwarder));
72+ return function;
73+ })();
74+ }
75+
5176/// A function that "forwards" a dynamic get, set, or invocation to the right
5277/// type checking member.
5378///
@@ -67,21 +92,19 @@ class DynamicForwarders {
6792/// A forwarder calls `noSuchMethod` on the receiver when a matching member is
6893/// not found, or the passed arguments do not match the expected parameters of
6994/// the member.
70- class Forwarder {
95+ class _DynamicForwarderCodeGenerator extends CodeGenerator {
96+ final Translator translator;
7197 final _ForwarderKind _kind;
72-
7398 final String memberName;
74-
7599 final w.FunctionBuilder function;
76100
77- Forwarder ._(Translator translator, this ._kind, this .memberName,
78- w.ModuleBuilder module)
79- : function = module.functions.define (_kind.functionType (translator),
80- "$_kind forwarder for '$memberName '" ),
81- assert (! translator.isDynamicSubmodule ||
82- (memberName == 'call' && _kind == _ForwarderKind .Getter ));
101+ _DynamicForwarderCodeGenerator (
102+ this .translator, this ._kind, this .memberName, this .function);
83103
84- void _generateCode (Translator translator) {
104+ @override
105+ void generate (w.InstructionsBuilder b, List <w.Local > paramLocals,
106+ w.Label ? returnLabel) {
107+ assert (returnLabel == null ); // no inlining support atm.
85108 switch (_kind) {
86109 case _ForwarderKind .Getter :
87110 _generateGetterCode (translator);
0 commit comments