mirror of
https://github.com/corda/corda.git
synced 2025-01-19 11:16:54 +00:00
fix stack unwinding and GC root scan for new calling convention
This commit is contained in:
parent
605ddffa31
commit
03653d2dd8
@ -413,7 +413,7 @@ localOffset(MyThread* t, int v, object method)
|
|||||||
return offset;
|
return offset;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline object*
|
object*
|
||||||
localObject(MyThread* t, void* stack, object method, unsigned index)
|
localObject(MyThread* t, void* stack, object method, unsigned index)
|
||||||
{
|
{
|
||||||
return reinterpret_cast<object*>
|
return reinterpret_cast<object*>
|
||||||
@ -422,6 +422,14 @@ localObject(MyThread* t, void* stack, object method, unsigned index)
|
|||||||
+ (t->arch->frameReturnAddressSize() * BytesPerWord));
|
+ (t->arch->frameReturnAddressSize() * BytesPerWord));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void*
|
||||||
|
stackForFrame(MyThread* t, void* frame, object method)
|
||||||
|
{
|
||||||
|
return static_cast<void**>(frame)
|
||||||
|
- alignedFrameSize(t, method)
|
||||||
|
- t->arch->frameHeaderSize();
|
||||||
|
}
|
||||||
|
|
||||||
class PoolElement: public Promise {
|
class PoolElement: public Promise {
|
||||||
public:
|
public:
|
||||||
PoolElement(Thread* t, object target, PoolElement* next):
|
PoolElement(Thread* t, object target, PoolElement* next):
|
||||||
@ -1306,8 +1314,12 @@ findUnwindTarget(MyThread* t, void** targetIp, void** targetBase,
|
|||||||
|
|
||||||
void* handler = findExceptionHandler(t, method, ip);
|
void* handler = findExceptionHandler(t, method, ip);
|
||||||
|
|
||||||
|
t->arch->nextFrame(&stack, &base);
|
||||||
|
|
||||||
|
void* canonicalStack = stackForFrame(t, stack, method);
|
||||||
|
|
||||||
if (handler) {
|
if (handler) {
|
||||||
void** sp = static_cast<void**>(stack)
|
void** sp = static_cast<void**>(canonicalStack)
|
||||||
+ t->arch->frameReturnAddressSize();
|
+ t->arch->frameReturnAddressSize();
|
||||||
|
|
||||||
sp[localOffset(t, localSize(t, method), method) / BytesPerWord]
|
sp[localOffset(t, localSize(t, method), method) / BytesPerWord]
|
||||||
@ -1324,13 +1336,13 @@ findUnwindTarget(MyThread* t, void** targetIp, void** targetBase,
|
|||||||
if (methodFlags(t, method) & ACC_STATIC) {
|
if (methodFlags(t, method) & ACC_STATIC) {
|
||||||
lock = methodClass(t, method);
|
lock = methodClass(t, method);
|
||||||
} else {
|
} else {
|
||||||
lock = *localObject(t, stack, method, savedTargetIndex(t, method));
|
lock = *localObject
|
||||||
|
(t, canonicalStack, method, savedTargetIndex(t, method));
|
||||||
}
|
}
|
||||||
|
|
||||||
release(t, lock);
|
release(t, lock);
|
||||||
}
|
}
|
||||||
|
|
||||||
t->arch->nextFrame(&stack, &base);
|
|
||||||
ip = t->arch->frameIp(stack);
|
ip = t->arch->frameIp(stack);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@ -4445,15 +4457,15 @@ finish(MyThread* t, Allocator* allocator, Context* context)
|
|||||||
(&byteArrayBody(t, methodSpec(t, context->method), 0)));
|
(&byteArrayBody(t, methodSpec(t, context->method), 0)));
|
||||||
|
|
||||||
// for debugging:
|
// for debugging:
|
||||||
if (false and
|
if (//false and
|
||||||
strcmp
|
strcmp
|
||||||
(reinterpret_cast<const char*>
|
(reinterpret_cast<const char*>
|
||||||
(&byteArrayBody(t, className(t, methodClass(t, context->method)), 0)),
|
(&byteArrayBody(t, className(t, methodClass(t, context->method)), 0)),
|
||||||
"java/lang/Throwable") == 0 and
|
"java/lang/Long") == 0 and
|
||||||
strcmp
|
strcmp
|
||||||
(reinterpret_cast<const char*>
|
(reinterpret_cast<const char*>
|
||||||
(&byteArrayBody(t, methodName(t, context->method), 0)),
|
(&byteArrayBody(t, methodName(t, context->method), 0)),
|
||||||
"printStackTrace") == 0)
|
"toString") == 0)
|
||||||
{
|
{
|
||||||
trap();
|
trap();
|
||||||
}
|
}
|
||||||
@ -4937,22 +4949,24 @@ frameMapIndex(MyThread* t, object method, int32_t offset)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
visitStackAndLocals(MyThread* t, Heap::Visitor* v, void* stack, object method,
|
visitStackAndLocals(MyThread* t, Heap::Visitor* v, void* frame, object method,
|
||||||
void* ip, void* calleeStack, unsigned argumentFootprint)
|
void* ip, bool skipArguments, unsigned argumentFootprint)
|
||||||
{
|
{
|
||||||
unsigned count;
|
unsigned count;
|
||||||
if (calleeStack) {
|
if (skipArguments) {
|
||||||
count = usableFrameSizeWithParameters(t, method) - argumentFootprint;
|
count = usableFrameSizeWithParameters(t, method) - argumentFootprint;
|
||||||
} else {
|
} else {
|
||||||
count = usableFrameSizeWithParameters(t, method);
|
count = usableFrameSizeWithParameters(t, method);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (count) {
|
if (count) {
|
||||||
object map = codePool(t, methodCode(t, method));
|
object map = codePool(t, methodCode(t, method));
|
||||||
int index = frameMapIndex
|
int index = frameMapIndex
|
||||||
(t, method, difference
|
(t, method, difference
|
||||||
(ip, reinterpret_cast<void*>(methodAddress(t, method))));
|
(ip, reinterpret_cast<void*>(methodAddress(t, method))));
|
||||||
|
|
||||||
|
void* stack = stackForFrame(t, frame, method);
|
||||||
|
|
||||||
for (unsigned i = 0; i < count; ++i) {
|
for (unsigned i = 0; i < count; ++i) {
|
||||||
int j = index + i;
|
int j = index + i;
|
||||||
if ((intArrayBody(t, map, j / 32)
|
if ((intArrayBody(t, map, j / 32)
|
||||||
@ -4975,7 +4989,7 @@ visitStack(MyThread* t, Heap::Visitor* v)
|
|||||||
}
|
}
|
||||||
|
|
||||||
MyThread::CallTrace* trace = t->trace;
|
MyThread::CallTrace* trace = t->trace;
|
||||||
void* calleeStack = 0;
|
bool skipArguments = false;
|
||||||
unsigned argumentFootprint = 0;
|
unsigned argumentFootprint = 0;
|
||||||
|
|
||||||
while (stack) {
|
while (stack) {
|
||||||
@ -4983,16 +4997,17 @@ visitStack(MyThread* t, Heap::Visitor* v)
|
|||||||
if (method) {
|
if (method) {
|
||||||
PROTECT(t, method);
|
PROTECT(t, method);
|
||||||
|
|
||||||
visitStackAndLocals
|
t->arch->nextFrame(&stack, &base);
|
||||||
(t, v, stack, method, ip, calleeStack, argumentFootprint);
|
|
||||||
|
|
||||||
calleeStack = stack;
|
visitStackAndLocals
|
||||||
|
(t, v, stack, method, ip, skipArguments, argumentFootprint);
|
||||||
|
|
||||||
|
skipArguments = true;
|
||||||
argumentFootprint = methodParameterFootprint(t, method);
|
argumentFootprint = methodParameterFootprint(t, method);
|
||||||
|
|
||||||
t->arch->nextFrame(&stack, &base);
|
|
||||||
ip = t->arch->frameIp(stack);
|
ip = t->arch->frameIp(stack);
|
||||||
} else if (trace) {
|
} else if (trace) {
|
||||||
calleeStack = 0;
|
skipArguments = false;
|
||||||
argumentFootprint = 0;
|
argumentFootprint = 0;
|
||||||
stack = trace->stack;
|
stack = trace->stack;
|
||||||
base = trace->base;
|
base = trace->base;
|
||||||
|
Loading…
Reference in New Issue
Block a user