more work on continuation support

This commit is contained in:
Joel Dice 2009-05-05 18:29:05 -06:00
parent eb3bd25aa1
commit 66c4867f18
9 changed files with 189 additions and 33 deletions

View File

@ -0,0 +1,16 @@
/* Copyright (c) 2009, Avian Contributors
Permission to use, copy, modify, and/or distribute this software
for any purpose with or without fee is hereby granted, provided
that the above copyright notice and this permission notice appear
in all copies.
There is NO WARRANTY for this software. See license.txt for
details. */
package avian;
public interface Callback<T> {
public void handleResult(T result);
public void handleException(Throwable exception);
}

View File

@ -0,0 +1,15 @@
/* Copyright (c) 2009, Avian Contributors
Permission to use, copy, modify, and/or distribute this software
for any purpose with or without fee is hereby granted, provided
that the above copyright notice and this permission notice appear
in all copies.
There is NO WARRANTY for this software. See license.txt for
details. */
package avian;
public interface CallbackReceiver<T> {
public T receive(Callback<T> callback) throws Exception;
}

View File

@ -0,0 +1,27 @@
/* Copyright (c) 2009, Avian Contributors
Permission to use, copy, modify, and/or distribute this software
for any purpose with or without fee is hereby granted, provided
that the above copyright notice and this permission notice appear
in all copies.
There is NO WARRANTY for this software. See license.txt for
details. */
package avian;
import java.util.concurrent.Callable;
public abstract class Continuations {
public static native <T> T callWithCurrentContinuation
(CallbackReceiver<T> receiver) throws Exception;
public static native <T> T dynamicWind(Runnable before,
Callable<T> thunk,
Runnable after) throws Exception;
private static class Continuation<T> implements Callback<T> {
public native void handleResult(T result);
public native void handleException(Throwable exception);
}
}

View File

@ -0,0 +1,15 @@
/* Copyright (c) 2009, Avian Contributors
Permission to use, copy, modify, and/or distribute this software
for any purpose with or without fee is hereby granted, provided
that the above copyright notice and this permission notice appear
in all copies.
There is NO WARRANTY for this software. See license.txt for
details. */
package java.util.concurrent;
public interface Callable<T> {
public T call() throws Exception;
}

View File

@ -847,3 +847,38 @@ Java_java_net_URL_00024ResourceInputStream_close(Thread*, jclass, jlong peer)
{
reinterpret_cast<System::Region*>(peer)->dispose();
}
extern "C" JNIEXPORT void JNICALL
Avian_avian_Continuations_callWithCurrentContinuation(Thread* t,
object,
uintptr_t* arguments)
{
t->m->processor->callWithCurrentContinuation
(t, reinterpret_cast<object>(*arguments));
abort(t);
}
extern "C" JNIEXPORT void JNICALL
Avian_avian_Continuation_handleResult(Thread* t,
object,
uintptr_t* arguments)
{
t->m->processor->feedResultToContinuation
(t, reinterpret_cast<object>(arguments[0]),
reinterpret_cast<object>(arguments[1]));
abort(t);
}
extern "C" JNIEXPORT void JNICALL
Avian_avian_Continuation_handleException(Thread* t,
object,
uintptr_t* arguments)
{
t->m->processor->feedExceptionToContinuation
(t, reinterpret_cast<object>(arguments[0]),
reinterpret_cast<object>(arguments[1]));
abort(t);
}

View File

@ -5553,6 +5553,7 @@ class MyProcessor: public Processor {
objectPools(0),
staticTableArray(0),
virtualThunks(0),
receiveMethod(0),
codeAllocator(s, 0, 0)
{ }
@ -5952,33 +5953,52 @@ class MyProcessor: public Processor {
(t->m->system->handleSegFault(&segFaultHandler)));
}
virtual void callWithCurrentContinuation(Thread* vmt, object method,
object this_)
{
virtual void callWithCurrentContinuation(Thread* vmt, object receiver) {
MyThread* t = static_cast<MyThread*>(vmt);
object method;
object continuation;
void* base;
void* stack;
{ PROTECT(t, method);
PROTECT(t, this_);
{ PROTECT(t, receiver);
compile(t, ::codeAllocator(t), 0, method);
if (receiveMethod == 0) {
const char* const className = "avian/CallbackReceiver";
const char* const methodName = "receive";
const char* const methodSpec = "(Lavian/Callback;)Ljava/lang/Object;";
receiveMethod = resolveMethod(t, className, methodName, methodSpec);
if (receiveMethod == 0) {
object message = makeString
(t, "%s %s not found in %s", methodName, methodSpec, className);
t->exception = makeNoSuchMethodError(t, message);
}
}
if (LIKELY(t->exception == 0)) {
void* ip;
continuation = makeCurrentContinuation(t, &ip, &base, &stack);
method = findInterfaceMethod
(t, receiveMethod, objectClass(t, receiver));
PROTECT(t, method);
compile(t, ::codeAllocator(t), 0, method);
if (LIKELY(t->exception == 0)) {
void* ip;
continuation = makeCurrentContinuation(t, &ip, &base, &stack);
}
}
}
if (LIKELY(t->exception == 0)) {
callWithContinuation(t, method, this_, continuation, base, stack);
callWithContinuation(t, method, receiver, continuation, base, stack);
} else {
unwind(t);
}
}
virtual void callContinuation(Thread* vmt, object continuation,
object result)
virtual void feedResultToContinuation(Thread* vmt, object continuation,
object result)
{
MyThread* t = static_cast<MyThread*>(vmt);
@ -5997,6 +6017,30 @@ class MyProcessor: public Processor {
vmJump(ip, base, stack, t, reinterpret_cast<uintptr_t>(result), 0);
}
virtual void feedExceptionToContinuation(Thread* vmt, object continuation,
object exception)
{
MyThread* t = static_cast<MyThread*>(vmt);
assert(t, t->exception == 0);
void* ip;
void* base;
void* stack;
findUnwindTarget(t, &ip, &base, &stack);
t->trace->nativeMethod = 0;
t->trace->targetMethod = 0;
t->continuation = continuation;
t->exception = exception;
findUnwindTarget(t, &ip, &base, &stack);
vmJump(ip, base, stack, t, 0, 0);
}
virtual void walkContinuationBody(Thread* t, Heap::Walker* w, object o,
unsigned start)
{
@ -6018,6 +6062,7 @@ class MyProcessor: public Processor {
object objectPools;
object staticTableArray;
object virtualThunks;
object receiveMethod;
SegFaultHandler segFaultHandler;
FixedAllocator codeAllocator;
};

View File

@ -134,10 +134,14 @@ class Processor {
boot(Thread* t, BootImage* image) = 0;
virtual void
callWithCurrentContinuation(Thread* t, object method, object this_) = 0;
callWithCurrentContinuation(Thread* t, object receiver) = 0;
virtual void
callContinuation(Thread* t, object continuation, object result) = 0;
feedResultToContinuation(Thread* t, object continuation, object result) = 0;
virtual void
feedExceptionToContinuation(Thread* t, object continuation,
object exception) = 0;
virtual void
walkContinuationBody(Thread* t, Heap::Walker* w, object o, unsigned start)

View File

@ -1323,12 +1323,6 @@ parseJavaClass(Object* type, Stream* s, Object* declarations)
}
}
if (equal(typeJavaName(type), "java/lang/Class")) {
// add inline vtable
addMember(type, Array::make
(type, 0, "void*", "vtable", sizeOf("void*", 0)));
}
if (typeSuper(type)) {
for (Object* p = typeMethods(typeSuper(type)); p; p = cdr(p)) {
addMethod(type, car(p));
@ -1372,23 +1366,25 @@ parseType(Object::ObjectType type, Object* p, Object* declarations,
Type* t = Type::make(type, name, javaName);
if (javaName and *javaName != '[') {
assert(cdr(p) == 0);
bool isJavaType = javaName and *javaName != '[';
if (isJavaType) {
const char* file = append(javaClassDirectory, "/", javaName, ".class");
Stream s(fopen(file, "rb"), true);
parseJavaClass(t, &s, declarations);
} else {
for (p = cdr(p); p; p = cdr(p)) {
if (type == Object::Type) {
parseSubdeclaration(t, car(p), declarations);
} else {
Object* member = parseMember(t, car(p), declarations);
assert(member->type == Object::Scalar);
addMember(t, member);
}
}
}
for (p = cdr(p); p; p = cdr(p)) {
if (type == Object::Type) {
parseSubdeclaration(t, car(p), declarations);
} else {
Object* member = parseMember(t, car(p), declarations);
assert(member->type == Object::Scalar);
addMember(t, member);
}
}
if (not isJavaType) {
if (type == Object::Type and typeSuper(t)) {
for (Object* p = typeMethods(typeSuper(t)); p; p = cdr(p)) {
addMethod(t, car(p));

View File

@ -1,6 +1,7 @@
(type jobject java/lang/Object)
(type class java/lang/Class)
(type class java/lang/Class
(array void* vtable))
(type singleton
(array uintptr_t body))
@ -103,7 +104,7 @@
(type array
(noassert array object body))
(type continuation
(type continuation avian/Continuations$Continuation
(object next)
(object method)
(void* address)
@ -111,6 +112,8 @@
(uintptr_t framePointerOffset)
(array uintptr_t body))
(type callbackReceiver avian/CallbackReceiver)
(type string java/lang/String)
(type thread java/lang/Thread)