@@ -2353,6 +2353,60 @@ QAST::OperationsJAST.map_classlib_core_op('compunitmainline', $TYPE_OPS, 'compun
2353
2353
QAST ::OperationsJAST. map_classlib_core_op(' compunitcodes' , $ TYPE_OPS , ' compunitcodes' , [$ RT_OBJ ], $ RT_OBJ , : tc);
2354
2354
QAST ::OperationsJAST. map_classlib_core_op(' jvmclasspaths' , $ TYPE_OPS , ' jvmclasspaths' , [], $ RT_OBJ , : tc);
2355
2355
2356
+ # JVM-specific ops for continuation handling
2357
+ # The three main continuation ops are fudgy because they need to be called partially like subs
2358
+ sub contop ($ name , @ params ) {
2359
+ my int $ expected_args := + @ params ;
2360
+ my @ jtypes_in ;
2361
+ for @ params {
2362
+ nqp :: push (@ jtypes_in , jtype($ _ ));
2363
+ }
2364
+ QAST ::OperationsJAST. add_core_op($ name , -> $ qastcomp , $ node {
2365
+ if + @ ($ node ) != $ expected_args {
2366
+ nqp ::die(" Operation '$ name ' requires $ expected_args operands" );
2367
+ }
2368
+
2369
+ # Emit operands.
2370
+ my $ il := JAST::InstructionList. new ();
2371
+ my int $ i := 0 ;
2372
+ my @ arg_res ;
2373
+ while $ i < $ expected_args {
2374
+ my $ type := @ params [$ i ];
2375
+ my $ operand := $ node [$ i ];
2376
+ my $ operand_res := $ qastcomp . as_jast($ node [$ i ], : want($ type ));
2377
+ $ il . append ($ operand_res . jast);
2378
+ $ i ++ ;
2379
+ nqp :: push (@ arg_res , $ operand_res );
2380
+ }
2381
+
2382
+ # Emit operation.
2383
+ $ * STACK . spill_to_locals($ il );
2384
+ $ * STACK . obtain($ il , | @ arg_res ) if @ arg_res ;
2385
+ $ il . append ($ ALOAD_1 );
2386
+ $ il . append ($ ACONST_NULL );
2387
+ $ il . append (savesite(JAST::Instruction. new (
2388
+ : op(' invokestatic' ), $ TYPE_OPS , $ name , ' Void' , | @ jtypes_in , $ TYPE_TC , $ TYPE_RESUME
2389
+ )));
2390
+
2391
+ # Load result onto the stack, unless in void context.
2392
+ if $ * WANT != $ RT_VOID {
2393
+ my $ rtype := rttype_from_typeobj($ node . returns );
2394
+ $ il . append (JAST::Instruction. new ( : op(' aload' ), ' cf' ));
2395
+ $ il . append (JAST::Instruction. new ( : op(' invokestatic' ), $ TYPE_OPS ,
2396
+ ' result_' ~ typechar($ rtype ), jtype($ rtype ), $ TYPE_CF ));
2397
+ result($ il , $ rtype )
2398
+ }
2399
+ else {
2400
+ result($ il , $ RT_VOID )
2401
+ }
2402
+ });
2403
+ }
2404
+ QAST ::OperationsJAST. map_classlib_core_op(' continuationclone' , $ TYPE_OPS , ' continuationclone' , [$ RT_OBJ ], $ RT_OBJ , : tc);
2405
+ contop(' continuationreset' , [$ RT_OBJ , $ RT_OBJ ]);
2406
+ contop(' continuationshift' , [$ RT_OBJ , $ RT_OBJ ]);
2407
+ contop(' continuationinvoke' , [$ RT_OBJ ]);
2408
+
2409
+
2356
2410
class QAST::CompilerJAST {
2357
2411
# Responsible for handling issues around code references, building the
2358
2412
# switch statement dispatcher, etc.
0 commit comments