fix compilation of unusual exception handlers

As described in commit 36aa0d6, apps such as jython which generate
bytecode dynamically can produce patterns of bytecode for which the
VM's compiler could not handle properly.  However, that commit
introduced a regression and had to be partially reverted.

It turns out the real problem was the call to Compiler::restoreState
which we made before checking whether we were actually ready to
compile the exception handler (we delay compiling an exception handler
until and unless the try/catch block it serves has been compiled so we
can calculate the stack maps properly).  That confused the compiler in
rare cases, so we now only call restoreState once we're actually ready
to compile the handler.
This commit is contained in:
Joel Dice 2011-04-09 12:44:28 -06:00
parent c0f39fbe0c
commit 239fd98781

View File

@ -6952,8 +6952,6 @@ compile(MyThread* t, Context* context)
progress = false;
for (unsigned i = 0; i < exceptionHandlerTableLength(t, eht); ++i) {
c->restoreState(state);
ExceptionHandler* eh = exceptionHandlerTableBody(t, eht, i);
int start = resolveIpForwards
(context, exceptionHandlerStart(eh), exceptionHandlerEnd(eh));
@ -6965,36 +6963,36 @@ compile(MyThread* t, Context* context)
RUNTIME_ARRAY_BODY(visited)[i] = true;
progress = true;
if (true) {//context->visitTable[exceptionHandlerIp(eh)] == 0) {
THREAD_RUNTIME_ARRAY
(t, uint8_t, stackMap,
codeMaxStack(t, methodCode(t, context->method)));
Frame frame2(&frame, RUNTIME_ARRAY_BODY(stackMap));
c->restoreState(state);
unsigned end = exceptionHandlerEnd(eh);
if (exceptionHandlerIp(eh) >= start
and exceptionHandlerIp(eh) < end)
{
end = exceptionHandlerIp(eh);
}
THREAD_RUNTIME_ARRAY
(t, uint8_t, stackMap,
codeMaxStack(t, methodCode(t, context->method)));
Frame frame2(&frame, RUNTIME_ARRAY_BODY(stackMap));
context->eventLog.append(PushExceptionHandlerEvent);
context->eventLog.append2(start);
context->eventLog.append2(end);
for (unsigned i = 1;
i < codeMaxStack(t, methodCode(t, context->method));
++i)
{
frame2.set(localSize(t, context->method) + i, Frame::Integer);
}
compile(t, &frame2, exceptionHandlerIp(eh), start);
context->eventLog.append(PopContextEvent);
eventIndex = calculateFrameMaps(t, context, 0, eventIndex);
unsigned end = exceptionHandlerEnd(eh);
if (exceptionHandlerIp(eh) >= start
and exceptionHandlerIp(eh) < end)
{
end = exceptionHandlerIp(eh);
}
context->eventLog.append(PushExceptionHandlerEvent);
context->eventLog.append2(start);
context->eventLog.append2(end);
for (unsigned i = 1;
i < codeMaxStack(t, methodCode(t, context->method));
++i)
{
frame2.set(localSize(t, context->method) + i, Frame::Integer);
}
compile(t, &frame2, exceptionHandlerIp(eh), start);
context->eventLog.append(PopContextEvent);
eventIndex = calculateFrameMaps(t, context, 0, eventIndex);
}
}
}