mirror of
https://github.com/corda/corda.git
synced 2025-01-05 20:54:13 +00:00
sketch of windows access violation handling; posix segv handling bugfixes
This commit is contained in:
parent
f151d85f4e
commit
100fc304ad
@ -75,23 +75,21 @@ resolveTarget(MyThread* t, void* stack, object method)
|
||||
if (method and methodVirtual(t, method)) {
|
||||
unsigned parameterFootprint = methodParameterFootprint(t, method);
|
||||
|
||||
if (reinterpret_cast<object*>(stack)[parameterFootprint]) {
|
||||
object class_ = objectClass
|
||||
(t, reinterpret_cast<object*>(stack)[parameterFootprint]);
|
||||
object class_ = objectClass
|
||||
(t, reinterpret_cast<object*>(stack)[parameterFootprint]);
|
||||
|
||||
if (classVmFlags(t, class_) & BootstrapFlag) {
|
||||
PROTECT(t, method);
|
||||
PROTECT(t, class_);
|
||||
if (classVmFlags(t, class_) & BootstrapFlag) {
|
||||
PROTECT(t, method);
|
||||
PROTECT(t, class_);
|
||||
|
||||
resolveClass(t, className(t, class_));
|
||||
if (UNLIKELY(t->exception)) return 0;
|
||||
}
|
||||
resolveClass(t, className(t, class_));
|
||||
if (UNLIKELY(t->exception)) return 0;
|
||||
}
|
||||
|
||||
if (classFlags(t, methodClass(t, method)) & ACC_INTERFACE) {
|
||||
return findInterfaceMethod(t, method, class_);
|
||||
} else {
|
||||
return findMethod(t, method, class_);
|
||||
}
|
||||
if (classFlags(t, methodClass(t, method)) & ACC_INTERFACE) {
|
||||
return findInterfaceMethod(t, method, class_);
|
||||
} else {
|
||||
return findMethod(t, method, class_);
|
||||
}
|
||||
}
|
||||
|
||||
@ -2512,7 +2510,7 @@ compile(MyThread* t, Frame* initialFrame, unsigned ip)
|
||||
c->indirectCall
|
||||
(c->constant
|
||||
(reinterpret_cast<intptr_t>(findInterfaceMethodFromInstance)),
|
||||
frame->trace(target, true),
|
||||
frame->trace(0, false),
|
||||
3, c->thread(), frame->append(target),
|
||||
c->stack(frame->stack, instance));
|
||||
|
||||
@ -3999,7 +3997,7 @@ class SegFaultHandler: public System::SignalHandler {
|
||||
public:
|
||||
SegFaultHandler(): m(0) { }
|
||||
|
||||
virtual bool handleSignal(void* ip, void* base, void* stack) {
|
||||
virtual void handleSignal(void* ip, void* base, void* stack) {
|
||||
MyThread* t = static_cast<MyThread*>(m->localThread->get());
|
||||
object node = findTraceNode(t, ip);
|
||||
if (node) {
|
||||
@ -4008,8 +4006,6 @@ class SegFaultHandler: public System::SignalHandler {
|
||||
t->stack = stack;
|
||||
t->exception = makeNullPointerException(t);
|
||||
unwind(t);
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -64,19 +64,17 @@ handleSignal(int signal, siginfo_t* info, void* context)
|
||||
greg_t* registers
|
||||
= static_cast<ucontext_t*>(context)->uc_mcontext.gregs;
|
||||
|
||||
bool handled = segFaultHandler->handleSignal
|
||||
segFaultHandler->handleSignal
|
||||
(reinterpret_cast<void*>(registers[IpRegister]),
|
||||
reinterpret_cast<void*>(registers[BaseRegister]),
|
||||
reinterpret_cast<void*>(registers[StackRegister]));
|
||||
|
||||
if (not handled) {
|
||||
if (oldSegFaultHandler.sa_flags & SA_SIGINFO) {
|
||||
oldSegFaultHandler.sa_sigaction(signal, info, context);
|
||||
} else if (oldSegFaultHandler.sa_handler) {
|
||||
oldSegFaultHandler.sa_handler(signal);
|
||||
} else {
|
||||
abort();
|
||||
}
|
||||
if (oldSegFaultHandler.sa_flags & SA_SIGINFO) {
|
||||
oldSegFaultHandler.sa_sigaction(signal, info, context);
|
||||
} else if (oldSegFaultHandler.sa_handler) {
|
||||
oldSegFaultHandler.sa_handler(signal);
|
||||
} else {
|
||||
abort();
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -532,6 +530,7 @@ class MySystem: public System {
|
||||
|
||||
return sigaction(SIGSEGV, &sa, &oldSegFaultHandler);
|
||||
} else if (segFaultHandler) {
|
||||
segFaultHandler = 0;
|
||||
return sigaction(SIGSEGV, &oldSegFaultHandler, 0);
|
||||
} else {
|
||||
return 1;
|
||||
|
@ -84,7 +84,7 @@ class System: public Allocator {
|
||||
public:
|
||||
virtual ~SignalHandler() { }
|
||||
|
||||
virtual bool handleSignal(void* ip, void* base, void* stack) = 0;
|
||||
virtual void handleSignal(void* ip, void* base, void* stack) = 0;
|
||||
};
|
||||
|
||||
virtual ~System() { }
|
||||
|
@ -13,6 +13,21 @@ using namespace vm;
|
||||
|
||||
namespace {
|
||||
|
||||
System::SignalHandler* segFaultHandler = 0;
|
||||
LPTOP_LEVEL_EXCEPTION_FILTER oldSegFaultHandler = 0;
|
||||
|
||||
LONG CALLBACK
|
||||
handleException(LPEXCEPTION_POINTERS e)
|
||||
{
|
||||
if (e->ExceptionRecord->ExceptionCode == EXCEPTION_ACCESS_VIOLATION) {
|
||||
segFaultHandler->handleSignal
|
||||
(reinterpret_cast<void*>(e->ContextRecord->Eip),
|
||||
reinterpret_cast<void*>(e->ContextRecord->Ebp),
|
||||
reinterpret_cast<void*>(e->ContextRecord->Esp));
|
||||
}
|
||||
return EXCEPTION_CONTINUE_SEARCH;
|
||||
}
|
||||
|
||||
class MutexResource {
|
||||
public:
|
||||
MutexResource(System* s, HANDLE m): s(s), m(m) {
|
||||
@ -500,6 +515,21 @@ class MySystem: public System {
|
||||
return 0;
|
||||
}
|
||||
|
||||
virtual Status handleSegFault(SignalHandler* handler) {
|
||||
if (handler) {
|
||||
segFaultHandler = handler;
|
||||
|
||||
oldSegFaultHandler = SetUnhandledExceptionFilter(handleException);
|
||||
return 0;
|
||||
} else if (segFaultHandler) {
|
||||
segFaultHandler = 0;
|
||||
SetUnhandledExceptionFilter(oldSegFaultHandler);
|
||||
return 0;
|
||||
} else {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
virtual uint64_t call(void* function, uintptr_t* arguments, uint8_t* types,
|
||||
unsigned count, unsigned size, unsigned returnType)
|
||||
{
|
||||
|
Loading…
Reference in New Issue
Block a user