mirror of
https://github.com/ParkerTenBroeck/coroutines.git
synced 2026-06-07 05:08:51 -04:00
generalization
This commit is contained in:
parent
9b0a9b7ad2
commit
95e7f6a59e
8 changed files with 174 additions and 104 deletions
|
|
@ -1,3 +1,4 @@
|
|||
import generator.future.Future;
|
||||
import generator.gen.Gen;
|
||||
|
||||
public class Examples {
|
||||
|
|
@ -65,25 +66,22 @@ public class Examples {
|
|||
// return Gen.ret();
|
||||
// }
|
||||
|
||||
public static Gen<Void, String> awaitTest2(int number){
|
||||
for(int i = 0; i < number; i ++)Gen.yield();
|
||||
return Gen.ret(number+"");
|
||||
}
|
||||
// public static Future<String> awaitTest2(int number){
|
||||
// for(int i = 0; i < number; i ++)Future.yield();
|
||||
// return Future.ret(number+"");
|
||||
// }
|
||||
|
||||
public static class Meow implements AutoCloseable{
|
||||
{
|
||||
System.out.println("Opened");
|
||||
}
|
||||
@Override
|
||||
public void close() {
|
||||
System.out.println("Closed");
|
||||
}
|
||||
}
|
||||
|
||||
public static Gen<Void, String> awaitTest(int number){
|
||||
try(var m = new Meow()){
|
||||
return Gen.ret(awaitTest2(number).await());
|
||||
}
|
||||
public static Future<String> awaitTest(int number){
|
||||
int i = 0;
|
||||
// Future.yield();
|
||||
// i = 1;
|
||||
// Future.yield();
|
||||
// i += i*12;
|
||||
// Future.yield();
|
||||
// return Future.ret(awaitTest2(number).await());
|
||||
for(; i < number; i++)
|
||||
Future.yield();
|
||||
return Future.ret("meow"+i);
|
||||
}
|
||||
|
||||
// public static Gen<Double, Void> test(double[] nyas){
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
import generator.RT;
|
||||
import generator.future.Future;
|
||||
import generator.gen.Gen;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
|
@ -10,47 +11,45 @@ public class Main implements Runnable {
|
|||
|
||||
@Override
|
||||
public void run() {
|
||||
// await();
|
||||
lexer();
|
||||
await();
|
||||
// lexer();
|
||||
// lambda();
|
||||
}
|
||||
|
||||
void lambda(){
|
||||
var gen = ((Supplier<Gen<Integer, String>>)() -> {
|
||||
Gen.yield(12);
|
||||
return Gen.ret("hello");
|
||||
}).get();
|
||||
|
||||
while(true) {
|
||||
var next = gen.next();
|
||||
if(next instanceof Gen.Yield(var e)) System.out.println(e);
|
||||
else if(next instanceof Gen.Ret(var ret)){
|
||||
System.out.println(ret);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
// void lambda(){
|
||||
// var gen = ((Supplier<Gen<Integer, String>>)() -> {
|
||||
// Gen.yield(12);
|
||||
// return Gen.ret("hello");
|
||||
// }).get();
|
||||
//
|
||||
// while(true) {
|
||||
// var next = gen.next();
|
||||
// if(next instanceof Gen.Yield(var e)) System.out.println(e);
|
||||
// else if(next instanceof Gen.Ret(var ret)){
|
||||
// System.out.println(ret);
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
|
||||
void await(){
|
||||
var gen = Examples.awaitTest(10);
|
||||
while(true) {
|
||||
var next = gen.next();
|
||||
if(next instanceof Gen.Yield(var e)) System.out.println(e);
|
||||
else if(next instanceof Gen.Ret(var ret)){
|
||||
System.out.println(ret);
|
||||
var next = (Object)gen.poll(() -> {});
|
||||
if(!(next instanceof Future.Pending)){
|
||||
System.out.println(next);
|
||||
break;
|
||||
}
|
||||
System.out.println("Pending");
|
||||
}
|
||||
|
||||
Runnable meow = () -> {};
|
||||
}
|
||||
|
||||
|
||||
void lexer(){
|
||||
var gen = Lexer.parse("f7(x,y,z,w, u,v, othersIg) = v-(x*y+y+ln(z)^2*sin(z*pi/2))/(w*u)+sqrt(othersIg*120e-1)");
|
||||
// var gen = Examples.test(new double[]{1,2,3,4});
|
||||
while(gen.next() instanceof Gen.Yield(var tok)) {
|
||||
System.out.println(tok);
|
||||
}
|
||||
}
|
||||
// void lexer(){
|
||||
// var gen = Lexer.parse("f7(x,y,z,w, u,v, othersIg) = v-(x*y+y+ln(z)^2*sin(z*pi/2))/(w*u)+sqrt(othersIg*120e-1)");
|
||||
//// var gen = Examples.test(new double[]{1,2,3,4});
|
||||
// while(gen.next() instanceof Gen.Yield(var tok)) {
|
||||
// System.out.println(tok);
|
||||
// }
|
||||
// }
|
||||
}
|
||||
|
|
@ -4,19 +4,23 @@ public interface Future<R> {
|
|||
|
||||
@SuppressWarnings("unchecked")
|
||||
default R poll(Waker waker){
|
||||
return (R) Pending.INSTANCE;
|
||||
return (R)Pending.INSTANCE;
|
||||
}
|
||||
|
||||
default R await(){
|
||||
throw new RuntimeException();
|
||||
throw new RuntimeException("NO!");
|
||||
}
|
||||
|
||||
static <R> Future<R> ret(R r){
|
||||
throw new RuntimeException();
|
||||
throw new RuntimeException("NO!");
|
||||
}
|
||||
|
||||
static void yield() {
|
||||
throw new RuntimeException("NO!");
|
||||
}
|
||||
|
||||
final class Pending{
|
||||
private static final Pending INSTANCE = new Pending();
|
||||
public static final Pending INSTANCE = new Pending();
|
||||
private Pending(){}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,6 +1,8 @@
|
|||
package generator.runtime;
|
||||
|
||||
import generator.future.Future;
|
||||
import generator.gen.Gen;
|
||||
import generator.runtime.future.FutureSMBuilder;
|
||||
import generator.runtime.gen.GenSMBuilder;
|
||||
|
||||
import java.io.IOException;
|
||||
|
|
@ -8,6 +10,7 @@ import java.lang.classfile.*;
|
|||
import java.lang.classfile.attribute.*;
|
||||
import java.lang.classfile.constantpool.ClassEntry;
|
||||
import java.lang.constant.ClassDesc;
|
||||
import java.lang.reflect.AccessFlag;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.Path;
|
||||
import java.util.*;
|
||||
|
|
@ -39,16 +42,17 @@ public class GeneratorClassLoader extends ClassLoader {
|
|||
var p = "/" + name.replace('.', '/') + ".class";
|
||||
try (var stream = GeneratorClassLoader.class.getResourceAsStream(p)) {
|
||||
var bytes = Objects.requireNonNull(stream).readAllBytes();
|
||||
add(name, searchForGenerators(bytes));
|
||||
add(name, searchReplaceMethods(bytes));
|
||||
return customClazzMap.get(name);
|
||||
} catch (IOException e) {
|
||||
throw new ClassNotFoundException(name, e);
|
||||
}
|
||||
}
|
||||
|
||||
public byte[] searchForGenerators(byte[] in) {
|
||||
public byte[] searchReplaceMethods(byte[] in) {
|
||||
var clm = ClassFile.of(ClassFile.AttributesProcessingOption.PASS_ALL_ATTRIBUTES).parse(in);
|
||||
var isGen = clm.thisClass().asSymbol().descriptorString().equals(Gen.class.descriptorString());
|
||||
var isFuture = clm.thisClass().asSymbol().descriptorString().equals(Future.class.descriptorString());
|
||||
|
||||
|
||||
var nestMem = new ArrayList<ClassDesc>();
|
||||
|
|
@ -58,14 +62,18 @@ public class GeneratorClassLoader extends ClassLoader {
|
|||
|
||||
return ClassFile.of(ClassFile.AttributesProcessingOption.PASS_ALL_ATTRIBUTES).build(clm.thisClass().asSymbol(), cb -> {
|
||||
for (var ce : clm) {
|
||||
if (ce instanceof MethodModel mem && !isGen) {
|
||||
var methodRetGen = mem.methodTypeSymbol().returnType().descriptorString().equals(Gen.class.descriptorString());
|
||||
if (!methodRetGen) {
|
||||
if (ce instanceof MethodModel mem && !isGen && !isFuture) {
|
||||
StateMachineBuilder builder = null;
|
||||
if(mem.methodTypeSymbol().returnType().descriptorString().equals(Gen.class.descriptorString())){
|
||||
builder = generatorMethod(cb, mem, clm);
|
||||
}else if(mem.methodTypeSymbol().returnType().descriptorString().equals(Future.class.descriptorString())){
|
||||
builder = futureMethod(cb, mem, clm);
|
||||
}else{
|
||||
cb.with(mem);
|
||||
} else{
|
||||
var gcd = generatorMethod(cb, mem, clm);
|
||||
// innerCl.add(InnerClassInfo.of(gcd, Optional.of(clm.thisClass().asSymbol()), Optional.of(gcd.displayName()), AccessFlag.PUBLIC, AccessFlag.FINAL, AccessFlag.STATIC));
|
||||
// nestMem.add(ClassDesc.of(gcd.displayName()));
|
||||
}
|
||||
if(builder != null && builder.shouldBeInnerClass()){
|
||||
innerCl.add(InnerClassInfo.of(builder.CD_this, Optional.of(clm.thisClass().asSymbol()), Optional.of(builder.CD_this.displayName()), AccessFlag.PUBLIC, AccessFlag.FINAL, AccessFlag.STATIC));
|
||||
nestMem.add(ClassDesc.of(builder.CD_this.displayName()));
|
||||
}
|
||||
}
|
||||
else if (ce instanceof Attribute<?> e){
|
||||
|
|
@ -81,13 +89,23 @@ public class GeneratorClassLoader extends ClassLoader {
|
|||
});
|
||||
}
|
||||
|
||||
private ClassDesc generatorMethod(ClassBuilder cb, MethodModel src_mem, ClassModel src_clm) {
|
||||
private StateMachineBuilder generatorMethod(ClassBuilder cb, MethodModel src_mem, ClassModel src_clm) {
|
||||
var com = src_mem.code().get();
|
||||
var gb = new GenSMBuilder(src_clm, src_mem, com);
|
||||
add(gb.CD_this.displayName(), gb.buildStateMachine());
|
||||
var smb = new GenSMBuilder(src_clm, src_mem, com);
|
||||
add(smb.CD_this.displayName(), smb.buildStateMachine());
|
||||
cb.withMethod(src_mem.methodName(), src_mem.methodType(), src_mem.flags().flagsMask(), mb -> {
|
||||
mb.withCode(gb::buildSourceMethodShim);
|
||||
mb.withCode(smb::buildSourceMethodShim);
|
||||
});
|
||||
return gb.CD_this;
|
||||
return smb;
|
||||
}
|
||||
|
||||
private StateMachineBuilder futureMethod(ClassBuilder cb, MethodModel src_mem, ClassModel src_clm) {
|
||||
var com = src_mem.code().get();
|
||||
var smb = new FutureSMBuilder(src_clm, src_mem, com);
|
||||
add(smb.CD_this.displayName(), smb.buildStateMachine());
|
||||
cb.withMethod(src_mem.methodName(), src_mem.methodType(), src_mem.flags().flagsMask(), mb -> {
|
||||
mb.withCode(smb::buildSourceMethodShim);
|
||||
});
|
||||
return smb;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -60,8 +60,8 @@ public class LocalTracker {
|
|||
name = StateMachineBuilder.LOCAL_PREFIX + localStore.size();
|
||||
localStore.add(new LocalStore(name, desc));
|
||||
}
|
||||
saved.add(new Saved(slot, name, desc));
|
||||
cob.aload(0).loadLocal(tk, slot).putfield(cd, name, desc);
|
||||
saved.add(new Saved(slot+1, name, desc));
|
||||
cob.aload(0).loadLocal(tk, slot+1).putfield(cd, name, desc);
|
||||
});
|
||||
run.run();
|
||||
|
||||
|
|
@ -98,7 +98,7 @@ public class LocalTracker {
|
|||
|
||||
public void currentLocals(LocalConsumer consumer) {
|
||||
var slot = 0;
|
||||
if (currentFrame != null)
|
||||
if (currentFrame != null && false)
|
||||
for (var kind : currentFrame.locals()) {
|
||||
switch (kind) {
|
||||
case StackMapFrameInfo.ObjectVerificationTypeInfo o -> {
|
||||
|
|
@ -129,10 +129,10 @@ public class LocalTracker {
|
|||
case StackMapFrameInfo.UninitializedVerificationTypeInfo _ -> throw new IllegalStateException();
|
||||
}
|
||||
}
|
||||
for (var entry : localVarTypes.entrySet()) {
|
||||
if (entry.getKey() < slot) continue;
|
||||
ClassDesc cd = entry.getValue().upperBound();
|
||||
consumer.consume(entry.getKey(), TypeKind.from(cd), cd);
|
||||
}
|
||||
// for (var entry : localVarTypes.entrySet()) {
|
||||
// if (entry.getKey() < slot) continue;
|
||||
// ClassDesc cd = entry.getValue().upperBound();
|
||||
// consumer.consume(entry.getKey(), TypeKind.from(cd), cd);
|
||||
// }
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -36,7 +36,7 @@ public abstract class StateMachineBuilder {
|
|||
|
||||
private final ArrayList<SwitchCase> stateSwitchCases = new ArrayList<>();
|
||||
|
||||
protected final String uniqueName(){
|
||||
protected String uniqueName(){
|
||||
return sequence+++"";
|
||||
}
|
||||
|
||||
|
|
@ -116,9 +116,9 @@ public abstract class StateMachineBuilder {
|
|||
|
||||
protected abstract void buildStateMachineMethod(ClassBuilder clb);
|
||||
|
||||
public void buildStateMachineMethodCode(ClassBuilder clb, CodeBuilder cob){
|
||||
public void buildStateMachineMethodCode(ClassBuilder clb, CodeBuilder cob, int loc_param_off){
|
||||
cob.trying(
|
||||
tcob -> buildStateMachineCode(clb, tcob),
|
||||
tcob -> buildStateMachineCode(clb, tcob, loc_param_off),
|
||||
// catch anything set our state to -1 and throw the exception
|
||||
ctb -> ctb.catchingAll(
|
||||
blc ->
|
||||
|
|
@ -132,7 +132,7 @@ public abstract class StateMachineBuilder {
|
|||
).aconst_null().areturn();
|
||||
}
|
||||
|
||||
public void buildStateMachineCode(ClassBuilder clb, CodeBuilder cob) {
|
||||
public void buildStateMachineCode(ClassBuilder clb, CodeBuilder cob, int loc_param_off) {
|
||||
boolean ignore_next_pop = false;
|
||||
|
||||
var invalidState = cob.newLabel();
|
||||
|
|
@ -187,25 +187,27 @@ public abstract class StateMachineBuilder {
|
|||
continue;
|
||||
}
|
||||
}
|
||||
if(coe instanceof LocalVariable lv) System.out.println(lv);
|
||||
|
||||
switch (coe) {
|
||||
// locals which were once function parameters can be ignored
|
||||
case LocalVariable lv when lv.slot() < paramSlotOff -> {
|
||||
}
|
||||
case LocalVariable lv ->
|
||||
cob.localVariable(lv.slot() - paramSlotOff + 1, lv.name(), lv.type(), lv.startScope(), lv.endScope());
|
||||
cob.localVariable(lv.slot() - paramSlotOff + loc_param_off, lv.name(), lv.type(), lv.startScope(), lv.endScope());
|
||||
|
||||
// increment indexes into the stack
|
||||
case IncrementInstruction ii when ii.slot() < paramSlotOff ->
|
||||
cob.aload(0).dup().getfield(CD_this, PARAM_PREFIX + ii.slot(), ConstantDescs.CD_int)
|
||||
.loadConstant(ii.constant()).iadd()
|
||||
.putfield(CD_this, PARAM_PREFIX + ii.slot(), ConstantDescs.CD_int);
|
||||
case IncrementInstruction ii -> cob.iinc(ii.slot() - paramSlotOff + 1, ii.constant());
|
||||
case IncrementInstruction ii -> cob.iinc(ii.slot() - paramSlotOff + loc_param_off, ii.constant());
|
||||
|
||||
// convert local function parameters to class fields and offset regular locals
|
||||
case LoadInstruction li when li.slot() < paramSlotOff ->
|
||||
cob.aload(0).getfield(CD_this, PARAM_PREFIX + li.slot(), lt.paramType(li.slot()));
|
||||
case LoadInstruction li -> cob.loadLocal(li.typeKind(), li.slot() - paramSlotOff + 1);
|
||||
case LoadInstruction li ->
|
||||
cob.loadLocal(li.typeKind(), li.slot() - paramSlotOff + loc_param_off);
|
||||
|
||||
// convert local function parameters to class fields and offset regular locals
|
||||
case StoreInstruction ls when ls.slot() < paramSlotOff && ls.typeKind().slotSize() == 2 ->
|
||||
|
|
@ -213,8 +215,8 @@ public abstract class StateMachineBuilder {
|
|||
case StoreInstruction ls when ls.slot() < paramSlotOff ->
|
||||
cob.aload(0).swap().putfield(CD_this, PARAM_PREFIX + ls.slot(), lt.paramType(ls.slot()));
|
||||
case StoreInstruction ls -> {
|
||||
lt.trackLocal(ls.slot() - paramSlotOff + 1, ls.typeKind());
|
||||
cob.storeLocal(ls.typeKind(), ls.slot() - paramSlotOff + 1);
|
||||
lt.trackLocal(ls.slot() - paramSlotOff + loc_param_off, ls.typeKind());
|
||||
cob.storeLocal(ls.typeKind(), ls.slot() - paramSlotOff + loc_param_off);
|
||||
}
|
||||
|
||||
default -> cob.with(coe);
|
||||
|
|
|
|||
|
|
@ -1,5 +1,7 @@
|
|||
package generator.runtime.future;
|
||||
|
||||
import generator.future.Future;
|
||||
import generator.future.Waker;
|
||||
import generator.gen.Gen;
|
||||
import generator.runtime.ReplacementKind;
|
||||
import generator.runtime.SpecialMethod;
|
||||
|
|
@ -14,13 +16,12 @@ import java.util.List;
|
|||
|
||||
public class FutureSMBuilder extends StateMachineBuilder {
|
||||
|
||||
public final static ClassDesc CD_Gen = ClassDesc.ofDescriptor(Gen.class.descriptorString());
|
||||
public final static ClassDesc CD_Res = ClassDesc.ofDescriptor(Gen.Res.class.descriptorString());
|
||||
public final static ClassDesc CD_Yield = ClassDesc.ofDescriptor(Gen.Yield.class.descriptorString());
|
||||
public final static ClassDesc CD_Ret = ClassDesc.ofDescriptor(Gen.Ret.class.descriptorString());
|
||||
public final static MethodTypeDesc MTD_Res = MethodTypeDesc.of(CD_Res);
|
||||
public final static MethodTypeDesc MTD_Gen_Obj = MethodTypeDesc.of(CD_Gen, ConstantDescs.CD_Object);
|
||||
public final static MethodTypeDesc MTD_Gen = MethodTypeDesc.of(CD_Gen);
|
||||
public final static ClassDesc CD_Future = ClassDesc.ofDescriptor(Future.class.descriptorString());
|
||||
public final static ClassDesc CD_Waker = ClassDesc.ofDescriptor(Waker.class.descriptorString());
|
||||
public final static ClassDesc CD_Pending = ClassDesc.ofDescriptor(Future.Pending.class.descriptorString());
|
||||
|
||||
public final static MethodTypeDesc MTD_Future_Obj = MethodTypeDesc.of(CD_Future, ConstantDescs.CD_Object);
|
||||
public final static MethodTypeDesc MTD_Object_Waker = MethodTypeDesc.of(ConstantDescs.CD_Object, CD_Waker);
|
||||
public final static MethodTypeDesc MTD_Obj = MethodTypeDesc.of(ConstantDescs.CD_Object);
|
||||
|
||||
static class AwaitHandler implements SpecialMethodHandler{
|
||||
|
|
@ -38,33 +39,76 @@ public class FutureSMBuilder extends StateMachineBuilder {
|
|||
cob.aload(0).loadConstant(yield_state).putfield(smb.CD_this, STATE_NAME, TypeKind.INT.upperBound());
|
||||
var start = cob.newBoundLabel();
|
||||
cob.dup().dup()
|
||||
.invokeinterface(CD_Gen, "next", MethodTypeDesc.of(CD_Res)).dup()
|
||||
.instanceOf(CD_Ret);
|
||||
.aload(1)
|
||||
.invokeinterface(CD_Future, "poll", MTD_Object_Waker).dup()
|
||||
.instanceOf(CD_Pending);
|
||||
cob.ifThenElse(bcb -> {
|
||||
bcb.checkcast(CD_Ret).invokevirtual(CD_Ret, "v", MethodTypeDesc.of(ConstantDescs.CD_Object)).swap().pop();
|
||||
}, bcb -> {
|
||||
smb.lt.savingLocals(smb.CD_this, bcb, () -> {
|
||||
bcb.swap().loadLocal(TypeKind.from(smb.CD_this), 0).swap().putfield(smb.CD_this, "meow", CD_Gen);
|
||||
bcb.swap().aload(0).swap().putfield(smb.CD_this, "meow", CD_Future);
|
||||
bcb.areturn().labelBinding(yield_label);
|
||||
bcb.loadLocal(TypeKind.from(smb.CD_this), 0).getfield(smb.CD_this, "meow", CD_Gen);
|
||||
bcb.aload(0).getfield(smb.CD_this, "meow", CD_Future);
|
||||
});
|
||||
bcb.goto_(start);
|
||||
}, bcb -> {
|
||||
bcb.swap().pop();
|
||||
});
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
static class YieldHandler implements SpecialMethodHandler {
|
||||
final int resume_state;
|
||||
final Label resume_label;
|
||||
|
||||
public YieldHandler(StateMachineBuilder smb, CodeBuilder cob) {
|
||||
resume_state = smb.add_state(resume_label = cob.newLabel());
|
||||
}
|
||||
|
||||
public ReplacementKind replacementKind(){return ReplacementKind.Immediate;}
|
||||
|
||||
@Override
|
||||
public void handle(StateMachineBuilder smb, CodeBuilder cob) {
|
||||
|
||||
smb.lt.savingLocals(smb.CD_this, cob, () -> {
|
||||
cob.aload(0).loadConstant(resume_state).putfield(smb.CD_this, STATE_NAME, TypeKind.INT.upperBound())
|
||||
.getstatic(CD_Pending, "INSTANCE", CD_Pending)
|
||||
.areturn();
|
||||
cob.labelBinding(resume_label);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
static class RetHandler implements SpecialMethodHandler{
|
||||
|
||||
public RetHandler() {}
|
||||
|
||||
public ReplacementKind replacementKind(){return ReplacementKind.ReplacingNextReturn;}
|
||||
|
||||
@Override
|
||||
public void handle(StateMachineBuilder smb, CodeBuilder cob) {
|
||||
cob.aload(0).loadConstant(-1).putfield(smb.CD_this, STATE_NAME, TypeKind.INT.upperBound()).areturn();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String uniqueName() {
|
||||
return "Fut"+super.uniqueName();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void buildStateMachineMethod(ClassBuilder clb){
|
||||
clb.withInterfaces(List.of(clb.constantPool().classEntry(CD_Gen)));
|
||||
clb.withMethod("next", MethodTypeDesc.of(CD_Res), ClassFile.ACC_PUBLIC, mb -> mb.withCode(cob -> {
|
||||
buildStateMachineMethodCode(clb, cob);
|
||||
clb.withInterfaces(List.of(clb.constantPool().classEntry(CD_Future)));
|
||||
clb.withMethod("poll", MTD_Object_Waker, ClassFile.ACC_PUBLIC, mb -> mb.withCode(cob -> {
|
||||
cob.localVariable(1, "waker", CD_Waker, cob.startLabel(), cob.endLabel());
|
||||
buildStateMachineMethodCode(clb, cob, 2);
|
||||
}));
|
||||
clb.withField("meow", CD_Gen, ClassFile.ACC_PRIVATE);
|
||||
clb.withField("meow", CD_Future, ClassFile.ACC_PRIVATE);
|
||||
}
|
||||
|
||||
public FutureSMBuilder(ClassModel src_clm, MethodModel src_mem, CodeModel src_com) {
|
||||
super(src_clm, src_mem, src_com);
|
||||
smmap.put(new SpecialMethod(CD_Gen, "await", MTD_Obj), AwaitHandler::new);
|
||||
smmap.put(new SpecialMethod(CD_Future, "await", MTD_Obj), AwaitHandler::new);
|
||||
smmap.put(new SpecialMethod(CD_Future, "ret", MTD_Future_Obj), (_, _) -> new RetHandler());
|
||||
smmap.put(new SpecialMethod(CD_Future, "yield", ConstantDescs.MTD_void), YieldHandler::new);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -81,11 +81,16 @@ public class GenSMBuilder extends StateMachineBuilder {
|
|||
smmap.put(new SpecialMethod(CD_Gen, "ret", MTD_Gen),(_, _) -> new RetHandler(true));
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String uniqueName() {
|
||||
return "Gen"+super.uniqueName();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void buildStateMachineMethod(ClassBuilder clb){
|
||||
clb.withInterfaces(List.of(clb.constantPool().classEntry(CD_Gen)));
|
||||
clb.withMethod("next", MethodTypeDesc.of(CD_Res), ClassFile.ACC_PUBLIC, mb -> mb.withCode(cob -> {
|
||||
buildStateMachineMethodCode(clb, cob);
|
||||
buildStateMachineMethodCode(clb, cob, 1);
|
||||
}));
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue