mirror of
https://github.com/corda/corda.git
synced 2025-06-11 20:01:46 +00:00
continuation bugfixes
This commit is contained in:
@ -18,7 +18,7 @@
|
|||||||
|
|
||||||
#define THREAD_CONTINUATION 168
|
#define THREAD_CONTINUATION 168
|
||||||
#define THREAD_EXCEPTION 64
|
#define THREAD_EXCEPTION 64
|
||||||
#define THREAD_EXCEPTION_STACK 176
|
#define THREAD_EXCEPTION_STACK_ADJUSTMENT 176
|
||||||
#define THREAD_EXCEPTION_OFFSET 184
|
#define THREAD_EXCEPTION_OFFSET 184
|
||||||
#define THREAD_EXCEPTION_HANDLER 192
|
#define THREAD_EXCEPTION_HANDLER 192
|
||||||
|
|
||||||
@ -124,7 +124,8 @@ LOCAL(vmInvoke_continuationTest):
|
|||||||
LOCAL(vmInvoke_handleException):
|
LOCAL(vmInvoke_handleException):
|
||||||
// we're handling an exception - call the exception handler instead
|
// we're handling an exception - call the exception handler instead
|
||||||
movq $0,THREAD_EXCEPTION(%rbx)
|
movq $0,THREAD_EXCEPTION(%rbx)
|
||||||
movq THREAD_EXCEPTION_STACK(%rbx),%rsp
|
movq THREAD_EXCEPTION_STACK_ADJUSTMENT(%rbx),%rdi
|
||||||
|
subq %rdi,%rsp
|
||||||
movq THREAD_EXCEPTION_OFFSET(%rbx),%rdi
|
movq THREAD_EXCEPTION_OFFSET(%rbx),%rdi
|
||||||
movq %rsi,(%rsp,%rdi,1)
|
movq %rsi,(%rsp,%rdi,1)
|
||||||
|
|
||||||
@ -182,7 +183,7 @@ LOCAL(vmJumpAndInvoke_argumentTest):
|
|||||||
|
|
||||||
#define THREAD_CONTINUATION 96
|
#define THREAD_CONTINUATION 96
|
||||||
#define THREAD_EXCEPTION 36
|
#define THREAD_EXCEPTION 36
|
||||||
#define THREAD_EXCEPTION_STACK 100
|
#define THREAD_EXCEPTION_STACK_ADJUSTMENT 100
|
||||||
#define THREAD_EXCEPTION_OFFSET 104
|
#define THREAD_EXCEPTION_OFFSET 104
|
||||||
#define THREAD_EXCEPTION_HANDLER 108
|
#define THREAD_EXCEPTION_HANDLER 108
|
||||||
|
|
||||||
@ -303,7 +304,8 @@ LOCAL(vmInvoke_continuationTest):
|
|||||||
LOCAL(vmInvoke_handleException):
|
LOCAL(vmInvoke_handleException):
|
||||||
// we're handling an exception - call the exception handler instead
|
// we're handling an exception - call the exception handler instead
|
||||||
movl $0,THREAD_EXCEPTION(%ebx)
|
movl $0,THREAD_EXCEPTION(%ebx)
|
||||||
movl THREAD_EXCEPTION_STACK(%ebx),%esp
|
movl THREAD_EXCEPTION_STACK_ADJUSTMENT(%ebx),%edi
|
||||||
|
subl %edi,%esp
|
||||||
movl THREAD_EXCEPTION_OFFSET(%ebx),%edi
|
movl THREAD_EXCEPTION_OFFSET(%ebx),%edi
|
||||||
movl %esi,(%esp,%edi,1)
|
movl %esi,(%esp,%edi,1)
|
||||||
|
|
||||||
|
@ -88,7 +88,7 @@ class MyThread: public Thread {
|
|||||||
base(0),
|
base(0),
|
||||||
stack(0),
|
stack(0),
|
||||||
continuation(0),
|
continuation(0),
|
||||||
exceptionStack(0),
|
exceptionStackAdjustment(0),
|
||||||
exceptionOffset(0),
|
exceptionOffset(0),
|
||||||
exceptionHandler(0),
|
exceptionHandler(0),
|
||||||
tailAddress(0),
|
tailAddress(0),
|
||||||
@ -105,7 +105,7 @@ class MyThread: public Thread {
|
|||||||
void* base;
|
void* base;
|
||||||
void* stack;
|
void* stack;
|
||||||
object continuation;
|
object continuation;
|
||||||
void* exceptionStack;
|
uintptr_t exceptionStackAdjustment;
|
||||||
uintptr_t exceptionOffset;
|
uintptr_t exceptionOffset;
|
||||||
void* exceptionHandler;
|
void* exceptionHandler;
|
||||||
void* tailAddress;
|
void* tailAddress;
|
||||||
@ -1426,43 +1426,43 @@ findUnwindTarget(MyThread* t, void** targetIp, void** targetBase,
|
|||||||
}
|
}
|
||||||
|
|
||||||
while (t->continuation) {
|
while (t->continuation) {
|
||||||
object method = continuationMethod(t, t->continuation);
|
object c = t->continuation;
|
||||||
|
|
||||||
|
object method = continuationMethod(t, c);
|
||||||
|
|
||||||
void* handler = findExceptionHandler
|
void* handler = findExceptionHandler
|
||||||
(t, method, continuationAddress(t, t->continuation));
|
(t, method, continuationAddress(t, c));
|
||||||
|
|
||||||
if (handler) {
|
if (handler) {
|
||||||
t->exceptionHandler = handler;
|
t->exceptionHandler = handler;
|
||||||
|
|
||||||
t->exceptionStack = static_cast<void**>(*targetStack)
|
t->exceptionStackAdjustment
|
||||||
+ t->arch->argumentFootprint(methodParameterFootprint(t, target))
|
= (stackOffsetFromFrame(t, method)
|
||||||
- t->arch->argumentFootprint(methodParameterFootprint(t, method))
|
- ((continuationFramePointerOffset(t, c) / BytesPerWord)
|
||||||
- stackOffsetFromFrame(t, method);
|
- t->arch->framePointerOffset()
|
||||||
|
+ t->arch->frameReturnAddressSize())) * BytesPerWord;
|
||||||
|
|
||||||
t->exceptionOffset
|
t->exceptionOffset
|
||||||
= localOffset(t, localSize(t, method), method) * BytesPerWord;
|
= localOffset(t, localSize(t, method), method) * BytesPerWord;
|
||||||
break;
|
break;
|
||||||
} else if (t->exception) {
|
} else if (t->exception) {
|
||||||
releaseLock(t, method,
|
releaseLock(t, method,
|
||||||
reinterpret_cast<uint8_t*>(t->continuation)
|
reinterpret_cast<uint8_t*>(c)
|
||||||
+ ContinuationBody
|
+ ContinuationBody
|
||||||
+ continuationReturnAddressOffset(t, t->continuation)
|
+ continuationReturnAddressOffset(t, c)
|
||||||
- t->arch->returnAddressOffset());
|
- t->arch->returnAddressOffset());
|
||||||
}
|
}
|
||||||
|
|
||||||
t->continuation = continuationNext(t, t->continuation);
|
t->continuation = continuationNext(t, c);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
object
|
object
|
||||||
makeCurrentContinuation(MyThread* t, object context, void** targetIp,
|
makeCurrentContinuation(MyThread* t, void** targetIp, void** targetBase,
|
||||||
void** targetBase, void** targetStack,
|
void** targetStack, unsigned* oldArgumentFootprint)
|
||||||
unsigned* oldArgumentFootprint)
|
|
||||||
{
|
{
|
||||||
PROTECT(t, context);
|
|
||||||
|
|
||||||
void* ip = t->ip;
|
void* ip = t->ip;
|
||||||
void* base = t->base;
|
void* base = t->base;
|
||||||
void* stack = t->stack;
|
void* stack = t->stack;
|
||||||
@ -1470,6 +1470,11 @@ makeCurrentContinuation(MyThread* t, object context, void** targetIp,
|
|||||||
ip = t->arch->frameIp(stack);
|
ip = t->arch->frameIp(stack);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
object context = t->continuation
|
||||||
|
? continuationContext(t, t->continuation)
|
||||||
|
: makeContinuationContext(t, 0, 0, 0, 0, t->trace->originalMethod);
|
||||||
|
PROTECT(t, context);
|
||||||
|
|
||||||
object target = t->trace->targetMethod;
|
object target = t->trace->targetMethod;
|
||||||
PROTECT(t, target);
|
PROTECT(t, target);
|
||||||
|
|
||||||
@ -5300,9 +5305,6 @@ callContinuation(MyThread* t, object continuation, object result,
|
|||||||
{
|
{
|
||||||
assert(t, t->exception == 0);
|
assert(t, t->exception == 0);
|
||||||
|
|
||||||
t->trace->nativeMethod = 0;
|
|
||||||
t->trace->targetMethod = 0;
|
|
||||||
|
|
||||||
t->continuation = continuation;
|
t->continuation = continuation;
|
||||||
|
|
||||||
if (exception) {
|
if (exception) {
|
||||||
@ -5313,8 +5315,13 @@ callContinuation(MyThread* t, object continuation, object result,
|
|||||||
t->stack = stack;
|
t->stack = stack;
|
||||||
|
|
||||||
findUnwindTarget(t, &ip, &base, &stack);
|
findUnwindTarget(t, &ip, &base, &stack);
|
||||||
|
|
||||||
|
t->ip = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
t->trace->nativeMethod = 0;
|
||||||
|
t->trace->targetMethod = 0;
|
||||||
|
|
||||||
vmJump(ip, base, stack, t, reinterpret_cast<uintptr_t>(result), 0);
|
vmJump(ip, base, stack, t, reinterpret_cast<uintptr_t>(result), 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -5371,8 +5378,7 @@ compatibleReturnType(MyThread* t, object oldMethod, object newMethod)
|
|||||||
|
|
||||||
void
|
void
|
||||||
jumpAndInvoke(MyThread* t, object method, void* base, void* stack,
|
jumpAndInvoke(MyThread* t, object method, void* base, void* stack,
|
||||||
unsigned oldArgumentFootprint, unsigned argumentCount,
|
unsigned oldArgumentFootprint, ...)
|
||||||
...)
|
|
||||||
{
|
{
|
||||||
t->trace->targetMethod = 0;
|
t->trace->targetMethod = 0;
|
||||||
|
|
||||||
@ -5382,8 +5388,9 @@ jumpAndInvoke(MyThread* t, object method, void* base, void* stack,
|
|||||||
t->trace->nativeMethod = 0;
|
t->trace->nativeMethod = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsigned argumentCount = methodParameterFootprint(t, method);
|
||||||
uintptr_t arguments[argumentCount];
|
uintptr_t arguments[argumentCount];
|
||||||
va_list a; va_start(a, argumentCount);
|
va_list a; va_start(a, oldArgumentFootprint);
|
||||||
for (unsigned i = 0; i < argumentCount; ++i) {
|
for (unsigned i = 0; i < argumentCount; ++i) {
|
||||||
arguments[i] = va_arg(a, uintptr_t);
|
arguments[i] = va_arg(a, uintptr_t);
|
||||||
}
|
}
|
||||||
@ -5394,7 +5401,7 @@ jumpAndInvoke(MyThread* t, object method, void* base, void* stack,
|
|||||||
base,
|
base,
|
||||||
static_cast<void**>(stack)
|
static_cast<void**>(stack)
|
||||||
+ oldArgumentFootprint
|
+ oldArgumentFootprint
|
||||||
- t->arch->argumentFootprint(methodParameterFootprint(t, method))
|
- t->arch->argumentFootprint(argumentCount)
|
||||||
- t->arch->frameFooterSize()
|
- t->arch->frameFooterSize()
|
||||||
- t->arch->frameReturnAddressSize(),
|
- t->arch->frameReturnAddressSize(),
|
||||||
argumentCount * BytesPerWord,
|
argumentCount * BytesPerWord,
|
||||||
@ -5517,9 +5524,9 @@ callContinuation(MyThread* t, object continuation, object result,
|
|||||||
|
|
||||||
case Rewind: {
|
case Rewind: {
|
||||||
jumpAndInvoke
|
jumpAndInvoke
|
||||||
(t, rewindMethod(t), base, stack, oldArgumentFootprint, 3,
|
(t, rewindMethod(t), base, stack, oldArgumentFootprint,
|
||||||
continuationContextBefore(t, nextContinuation), nextContinuation,
|
continuationContextBefore(t, continuationContext(t, nextContinuation)),
|
||||||
result, exception);
|
nextContinuation, result, exception);
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
case Throw: {
|
case Throw: {
|
||||||
@ -5803,7 +5810,7 @@ class MyProcessor: public Processor {
|
|||||||
if (false) {
|
if (false) {
|
||||||
fprintf(stderr, "%d\n", difference(&(t->continuation), t));
|
fprintf(stderr, "%d\n", difference(&(t->continuation), t));
|
||||||
fprintf(stderr, "%d\n", difference(&(t->exception), t));
|
fprintf(stderr, "%d\n", difference(&(t->exception), t));
|
||||||
fprintf(stderr, "%d\n", difference(&(t->exceptionStack), t));
|
fprintf(stderr, "%d\n", difference(&(t->exceptionStackAdjustment), t));
|
||||||
fprintf(stderr, "%d\n", difference(&(t->exceptionOffset), t));
|
fprintf(stderr, "%d\n", difference(&(t->exceptionOffset), t));
|
||||||
fprintf(stderr, "%d\n", difference(&(t->exceptionHandler), t));
|
fprintf(stderr, "%d\n", difference(&(t->exceptionHandler), t));
|
||||||
exit(0);
|
exit(0);
|
||||||
@ -6245,18 +6252,14 @@ class MyProcessor: public Processor {
|
|||||||
|
|
||||||
if (LIKELY(t->exception == 0)) {
|
if (LIKELY(t->exception == 0)) {
|
||||||
t->continuation = makeCurrentContinuation
|
t->continuation = makeCurrentContinuation
|
||||||
(t, t->continuation
|
(t, &ip, &base, &stack, &oldArgumentFootprint);
|
||||||
? continuationContext(t, t->continuation)
|
|
||||||
: makeContinuationContext
|
|
||||||
(t, 0, 0, 0, 0, t->trace->originalMethod),
|
|
||||||
&ip, &base, &stack, &oldArgumentFootprint);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (LIKELY(t->exception == 0)) {
|
if (LIKELY(t->exception == 0)) {
|
||||||
jumpAndInvoke
|
jumpAndInvoke
|
||||||
(t, method, base, stack, oldArgumentFootprint, 2, receiver,
|
(t, method, base, stack, oldArgumentFootprint, receiver,
|
||||||
t->continuation);
|
t->continuation);
|
||||||
} else {
|
} else {
|
||||||
unwind(t);
|
unwind(t);
|
||||||
@ -6296,25 +6299,20 @@ class MyProcessor: public Processor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (LIKELY(t->exception == 0)) {
|
if (LIKELY(t->exception == 0)) {
|
||||||
object oldContext
|
t->continuation = makeCurrentContinuation
|
||||||
= (t->continuation ? continuationContext(t, t->continuation) : 0);
|
(t, &ip, &base, &stack, &oldArgumentFootprint);
|
||||||
|
|
||||||
object context = makeContinuationContext
|
object newContext = makeContinuationContext
|
||||||
(t, oldContext, before, after, 0, t->trace->originalMethod);
|
(t, continuationContext(t, t->continuation), before, after,
|
||||||
|
t->continuation, t->trace->originalMethod);
|
||||||
|
|
||||||
object continuation = makeCurrentContinuation
|
set(t, t->continuation, ContinuationContext, newContext);
|
||||||
(t, context, &ip, &base, &stack, &oldArgumentFootprint);
|
|
||||||
|
|
||||||
set(t, continuationContext(t, continuation),
|
|
||||||
ContinuationContextContinuation, continuation);
|
|
||||||
|
|
||||||
t->continuation = continuation;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (LIKELY(t->exception == 0)) {
|
if (LIKELY(t->exception == 0)) {
|
||||||
jumpAndInvoke
|
jumpAndInvoke
|
||||||
(t, windMethod, base, stack, oldArgumentFootprint, 3, before, thunk,
|
(t, windMethod, base, stack, oldArgumentFootprint, before, thunk,
|
||||||
after);
|
after);
|
||||||
} else {
|
} else {
|
||||||
unwind(t);
|
unwind(t);
|
||||||
|
Reference in New Issue
Block a user