Diff
Modified: trunk/Source/_javascript_Core/ChangeLog (172866 => 172867)
--- trunk/Source/_javascript_Core/ChangeLog 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/ChangeLog 2014-08-22 19:54:30 UTC (rev 172867)
@@ -1,3 +1,79 @@
+2014-08-21 Michael Saboff <msab...@apple.com>
+
+ REGRESSION(r163179): Sporadic crash in js/dom/line-column-numbers.html test
+ https://bugs.webkit.org/show_bug.cgi?id=136111
+
+ Reviewed by Filip Pizlo.
+
+ The problem was that we weren't properly handling VM::topVMEntryFrame in two ways.
+
+ First in the case where we get an exception of a stack overflow during setup of the direct
+ callee frame of a VM entry frame, we need to throw the exception in the caller's frame.
+ This requires unrolling topVMEntryFrame while creating the exception object. This is
+ accomplished with the renamed NativeCallFrameTracerWithRestore object. As part of this,
+ split the JIT rollback exception handling to call a new helper,
+ callLookupExceptionHandlerFromCallerFrame, which will unroll the callFrame and VMEntryFrame.
+
+ Second, when we unwind to find a handler, we also need to unwind topVMCallFrame for the
+ case where we end up (re)throwing another exception after entering the catch block, but
+ before another vmEntry call. Added VM::vmEntryFrameForThrow as a way similar to
+ VM::callFrameForThrow to pass the appropriate VMENtryFrame to the catch block.
+
+
+ * dfg/DFGJITCompiler.cpp:
+ (JSC::DFG::JITCompiler::compileExceptionHandlers):
+ * ftl/FTLCompile.cpp:
+ (JSC::FTL::fixFunctionBasedOnStackMaps):
+ * jit/JIT.cpp:
+ (JSC::JIT::privateCompileExceptionHandlers):
+ Split out the unroll cases to use the new helper callLookupExceptionHandlerFromCallerFrame()
+ to unwind both the callFrame and topVMEntryFrame.
+
+ * interpreter/Interpreter.cpp:
+ (JSC::UnwindFunctor::UnwindFunctor):
+ (JSC::UnwindFunctor::operator()):
+ (JSC::Interpreter::unwind):
+ * jit/JITExceptions.cpp:
+ (JSC::genericUnwind):
+ Added VMEntryFrame as another component to unwind.
+
+ * interpreter/Interpreter.h:
+ (JSC::NativeCallFrameTracer::NativeCallFrameTracer):
+ (JSC::NativeCallFrameTracerWithRestore::NativeCallFrameTracerWithRestore):
+ (JSC::NativeCallFrameTracerWithRestore::~NativeCallFrameTracerWithRestore):
+ Renamed and changed to save and restore topCallFrame and topVMEntryFrame around the setting of
+ both values.
+
+ * interpreter/StackVisitor.cpp:
+ (JSC::StackVisitor::gotoNextFrame):
+ (JSC::StackVisitor::readNonInlinedFrame):
+ * interpreter/StackVisitor.h:
+ (JSC::StackVisitor::Frame::vmEntryFrame):
+ Added code to unwind the VMEntryFrame.
+
+ * jit/CCallHelpers.h:
+ (JSC::CCallHelpers::jumpToExceptionHandler): Updated comment to indicate that the value
+ the handler should use for VM::topEntryFrame is in VM::vmEntryFrameForThrow.
+
+ * jit/JITOpcodes.cpp:
+ (JSC::JIT::emit_op_catch):
+ * jit/JITOpcodes32_64.cpp:
+ (JSC::JIT::emit_op_catch):
+ * llint/LowLevelInterpreter32_64.asm:
+ * llint/LowLevelInterpreter64.asm:
+ Added code to update VM::topVMEntryFrame from VM::vmEntryFrameForThrowOffset.
+
+ * jit/JITOperations.cpp:
+ * jit/JITOperations.h:
+ (JSC::operationThrowStackOverflowError):
+ (JSC::operationCallArityCheck):
+ (JSC::operationConstructArityCheck):
+
+ * runtime/VM.h:
+ (JSC::VM::vmEntryFrameForThrowOffset):
+ (JSC::VM::topVMEntryFrameOffset):
+ Added as the side channel to return the topVMEntryFrame that the handler should use.
+
2014-08-22 Daniel Bates <daba...@apple.com>
[iOS] Disable ENABLE_IOS_{GESTURE, TOUCH}_EVENTS, and temporarily disable ENABLE_TOUCH_EVENTS
Modified: trunk/Source/_javascript_Core/dfg/DFGJITCompiler.cpp (172866 => 172867)
--- trunk/Source/_javascript_Core/dfg/DFGJITCompiler.cpp 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/dfg/DFGJITCompiler.cpp 2014-08-22 19:54:30 UTC (rev 172867)
@@ -116,35 +116,39 @@
void JITCompiler::compileExceptionHandlers()
{
- if (m_exceptionChecks.empty() && m_exceptionChecksWithCallFrameRollback.empty())
- return;
+ if (!m_exceptionChecksWithCallFrameRollback.empty()) {
+ m_exceptionChecksWithCallFrameRollback.link(this);
- Jump doLookup;
+ // lookupExceptionHandlerFromCallerFrame is passed two arguments, the VM and the exec (the CallFrame*).
+ move(TrustedImmPtr(vm()), GPRInfo::argumentGPR0);
+ move(GPRInfo::callFrameRegister, GPRInfo::argumentGPR1);
- if (!m_exceptionChecksWithCallFrameRollback.empty()) {
- m_exceptionChecksWithCallFrameRollback.link(this);
- emitGetCallerFrameFromCallFrameHeaderPtr(GPRInfo::argumentGPR1);
- doLookup = jump();
+#if CPU(X86)
+ // FIXME: should use the call abstraction, but this is currently in the SpeculativeJIT layer!
+ poke(GPRInfo::argumentGPR0);
+ poke(GPRInfo::argumentGPR1, 1);
+#endif
+ m_calls.append(CallLinkRecord(call(), lookupExceptionHandlerFromCallerFrame));
+
+ jumpToExceptionHandler();
}
- if (!m_exceptionChecks.empty())
+ if (!m_exceptionChecks.empty()) {
m_exceptionChecks.link(this);
- // lookupExceptionHandler is passed two arguments, the VM and the exec (the CallFrame*).
- move(GPRInfo::callFrameRegister, GPRInfo::argumentGPR1);
+ // lookupExceptionHandler is passed two arguments, the VM and the exec (the CallFrame*).
+ move(TrustedImmPtr(vm()), GPRInfo::argumentGPR0);
+ move(GPRInfo::callFrameRegister, GPRInfo::argumentGPR1);
- if (doLookup.isSet())
- doLookup.link(this);
-
- move(TrustedImmPtr(vm()), GPRInfo::argumentGPR0);
-
#if CPU(X86)
- // FIXME: should use the call abstraction, but this is currently in the SpeculativeJIT layer!
- poke(GPRInfo::argumentGPR0);
- poke(GPRInfo::argumentGPR1, 1);
+ // FIXME: should use the call abstraction, but this is currently in the SpeculativeJIT layer!
+ poke(GPRInfo::argumentGPR0);
+ poke(GPRInfo::argumentGPR1, 1);
#endif
- m_calls.append(CallLinkRecord(call(), lookupExceptionHandler));
- jumpToExceptionHandler();
+ m_calls.append(CallLinkRecord(call(), lookupExceptionHandler));
+
+ jumpToExceptionHandler();
+ }
}
void JITCompiler::link(LinkBuffer& linkBuffer)
Modified: trunk/Source/_javascript_Core/ftl/FTLCompile.cpp (172866 => 172867)
--- trunk/Source/_javascript_Core/ftl/FTLCompile.cpp 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/ftl/FTLCompile.cpp 2014-08-22 19:54:30 UTC (rev 172867)
@@ -285,24 +285,28 @@
// At this point it's perfectly fair to just blow away all state and restore the
// JS JIT view of the universe.
+ checkJIT.move(MacroAssembler::TrustedImm64(TagTypeNumber), GPRInfo::tagTypeNumberRegister);
+ checkJIT.move(MacroAssembler::TrustedImm64(TagMask), GPRInfo::tagMaskRegister);
+
+ checkJIT.move(MacroAssembler::TrustedImmPtr(&vm), GPRInfo::argumentGPR0);
checkJIT.move(GPRInfo::callFrameRegister, GPRInfo::argumentGPR1);
+ MacroAssembler::Call callLookupExceptionHandler = checkJIT.call();
+ checkJIT.jumpToExceptionHandler();
- MacroAssembler::Label exceptionContinueArg1Set = checkJIT.label();
+ stackOverflowException = checkJIT.label();
checkJIT.move(MacroAssembler::TrustedImm64(TagTypeNumber), GPRInfo::tagTypeNumberRegister);
checkJIT.move(MacroAssembler::TrustedImm64(TagMask), GPRInfo::tagMaskRegister);
checkJIT.move(MacroAssembler::TrustedImmPtr(&vm), GPRInfo::argumentGPR0);
- MacroAssembler::Call call = checkJIT.call();
+ checkJIT.move(GPRInfo::callFrameRegister, GPRInfo::argumentGPR1);
+ MacroAssembler::Call callLookupExceptionHandlerFromCallerFrame = checkJIT.call();
checkJIT.jumpToExceptionHandler();
- stackOverflowException = checkJIT.label();
- checkJIT.emitGetCallerFrameFromCallFrameHeaderPtr(GPRInfo::argumentGPR1);
- checkJIT.jump(exceptionContinueArg1Set);
-
OwnPtr<LinkBuffer> linkBuffer = adoptPtr(new LinkBuffer(
vm, checkJIT, codeBlock, JITCompilationMustSucceed));
- linkBuffer->link(call, FunctionPtr(lookupExceptionHandler));
-
+ linkBuffer->link(callLookupExceptionHandler, FunctionPtr(lookupExceptionHandler));
+ linkBuffer->link(callLookupExceptionHandlerFromCallerFrame, FunctionPtr(lookupExceptionHandlerFromCallerFrame));
+
state.finalizer->handleExceptionsLinkBuffer = linkBuffer.release();
}
Modified: trunk/Source/_javascript_Core/interpreter/Interpreter.cpp (172866 => 172867)
--- trunk/Source/_javascript_Core/interpreter/Interpreter.cpp 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/interpreter/Interpreter.cpp 2014-08-22 19:54:30 UTC (rev 172867)
@@ -645,8 +645,9 @@
class UnwindFunctor {
public:
- UnwindFunctor(CallFrame*& callFrame, bool isTermination, CodeBlock*& codeBlock, HandlerInfo*& handler)
- : m_callFrame(callFrame)
+ UnwindFunctor(VMEntryFrame*& vmEntryFrame, CallFrame*& callFrame, bool isTermination, CodeBlock*& codeBlock, HandlerInfo*& handler)
+ : m_vmEntryFrame(vmEntryFrame)
+ , m_callFrame(callFrame)
, m_isTermination(isTermination)
, m_codeBlock(codeBlock)
, m_handler(handler)
@@ -656,6 +657,7 @@
StackVisitor::Status operator()(StackVisitor& visitor)
{
VM& vm = m_callFrame->vm();
+ m_vmEntryFrame = visitor->vmEntryFrame();
m_callFrame = visitor->callFrame();
m_codeBlock = visitor->codeBlock();
unsigned bytecodeOffset = visitor->bytecodeOffset();
@@ -673,13 +675,14 @@
}
private:
+ VMEntryFrame*& m_vmEntryFrame;
CallFrame*& m_callFrame;
bool m_isTermination;
CodeBlock*& m_codeBlock;
HandlerInfo*& m_handler;
};
-NEVER_INLINE HandlerInfo* Interpreter::unwind(CallFrame*& callFrame, JSValue& exceptionValue)
+NEVER_INLINE HandlerInfo* Interpreter::unwind(VMEntryFrame*& vmEntryFrame, CallFrame*& callFrame, JSValue& exceptionValue)
{
CodeBlock* codeBlock = callFrame->codeBlock();
ASSERT(codeBlock);
@@ -724,7 +727,7 @@
HandlerInfo* handler = 0;
VM& vm = callFrame->vm();
ASSERT(callFrame == vm.topCallFrame);
- UnwindFunctor functor(callFrame, isTermination, codeBlock, handler);
+ UnwindFunctor functor(vmEntryFrame, callFrame, isTermination, codeBlock, handler);
callFrame->iterate(functor);
if (!handler)
return 0;
Modified: trunk/Source/_javascript_Core/interpreter/Interpreter.h (172866 => 172867)
--- trunk/Source/_javascript_Core/interpreter/Interpreter.h 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/interpreter/Interpreter.h 2014-08-22 19:54:30 UTC (rev 172867)
@@ -175,18 +175,33 @@
{
ASSERT(vm);
ASSERT(callFrame);
- ASSERT(callFrame < vm->topVMEntryFrame);
vm->topCallFrame = callFrame;
}
+ };
- ALWAYS_INLINE NativeCallFrameTracer(VM* vm, VMEntryFrame* vmEntryFrame, CallFrame* callFrame)
+ class NativeCallFrameTracerWithRestore {
+ public:
+ ALWAYS_INLINE NativeCallFrameTracerWithRestore(VM* vm, VMEntryFrame* vmEntryFrame, CallFrame* callFrame)
+ : m_vm(vm)
{
ASSERT(vm);
ASSERT(callFrame);
- ASSERT(callFrame < vmEntryFrame);
+ m_savedTopVMEntryFrame = vm->topVMEntryFrame;
+ m_savedTopCallFrame = vm->topCallFrame;
vm->topVMEntryFrame = vmEntryFrame;
vm->topCallFrame = callFrame;
}
+
+ ALWAYS_INLINE ~NativeCallFrameTracerWithRestore()
+ {
+ m_vm->topVMEntryFrame = m_savedTopVMEntryFrame;
+ m_vm->topCallFrame = m_savedTopCallFrame;
+ }
+
+ private:
+ VM* m_vm;
+ VMEntryFrame* m_savedTopVMEntryFrame;
+ CallFrame* m_savedTopCallFrame;
};
class Interpreter {
@@ -236,7 +251,7 @@
SamplingTool* sampler() { return m_sampler.get(); }
- NEVER_INLINE HandlerInfo* unwind(CallFrame*&, JSValue&);
+ NEVER_INLINE HandlerInfo* unwind(VMEntryFrame*&, CallFrame*&, JSValue&);
NEVER_INLINE void debug(CallFrame*, DebugHookID);
JSString* stackTraceAsString(ExecState*, Vector<StackFrame>);
Modified: trunk/Source/_javascript_Core/interpreter/StackVisitor.cpp (172866 => 172867)
--- trunk/Source/_javascript_Core/interpreter/StackVisitor.cpp 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/interpreter/StackVisitor.cpp 2014-08-22 19:54:30 UTC (rev 172867)
@@ -61,10 +61,11 @@
InlineCallFrame* inlineCallFrame = m_frame.inlineCallFrame();
CodeOrigin* callerCodeOrigin = &inlineCallFrame->caller;
readInlinedFrame(m_frame.callFrame(), callerCodeOrigin);
-
- } else
+ return;
+ }
#endif // ENABLE(DFG_JIT)
- readFrame(m_frame.callerFrame());
+ m_frame.m_VMEntryFrame = m_frame.m_CallerVMEntryFrame;
+ readFrame(m_frame.callerFrame());
}
void StackVisitor::readFrame(CallFrame* callFrame)
@@ -116,9 +117,9 @@
{
m_frame.m_callFrame = callFrame;
m_frame.m_argumentCountIncludingThis = callFrame->argumentCountIncludingThis();
- VMEntryFrame* currentVMEntryFrame = m_frame.m_VMEntryFrame;
- m_frame.m_callerFrame = callFrame->callerFrame(m_frame.m_VMEntryFrame);
- m_frame.m_callerIsVMEntryFrame = currentVMEntryFrame != m_frame.m_VMEntryFrame;
+ m_frame.m_CallerVMEntryFrame = m_frame.m_VMEntryFrame;
+ m_frame.m_callerFrame = callFrame->callerFrame(m_frame.m_CallerVMEntryFrame);
+ m_frame.m_callerIsVMEntryFrame = m_frame.m_CallerVMEntryFrame != m_frame.m_VMEntryFrame;
m_frame.m_callee = callFrame->callee();
m_frame.m_scope = callFrame->scope();
m_frame.m_codeBlock = callFrame->codeBlock();
Modified: trunk/Source/_javascript_Core/interpreter/StackVisitor.h (172866 => 172867)
--- trunk/Source/_javascript_Core/interpreter/StackVisitor.h 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/interpreter/StackVisitor.h 2014-08-22 19:54:30 UTC (rev 172867)
@@ -81,6 +81,7 @@
Arguments* createArguments();
Arguments* existingArguments();
+ VMEntryFrame* vmEntryFrame() const { return m_VMEntryFrame; }
CallFrame* callFrame() const { return m_callFrame; }
#ifndef NDEBUG
@@ -97,6 +98,7 @@
size_t m_index;
size_t m_argumentCountIncludingThis;
VMEntryFrame* m_VMEntryFrame;
+ VMEntryFrame* m_CallerVMEntryFrame;
CallFrame* m_callerFrame;
JSObject* m_callee;
JSScope* m_scope;
Modified: trunk/Source/_javascript_Core/jit/CCallHelpers.h (172866 => 172867)
--- trunk/Source/_javascript_Core/jit/CCallHelpers.h 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/jit/CCallHelpers.h 2014-08-22 19:54:30 UTC (rev 172867)
@@ -1700,6 +1700,7 @@
void jumpToExceptionHandler()
{
// genericUnwind() leaves the handler CallFrame* in vm->callFrameForThrow,
+ // the topVMEntryFrame for the handler in vm->vmEntryFrameForThrow,
// and the address of the handler in vm->targetMachinePCForThrow.
loadPtr(&vm()->targetMachinePCForThrow, GPRInfo::regT1);
jump(GPRInfo::regT1);
Modified: trunk/Source/_javascript_Core/jit/JIT.cpp (172866 => 172867)
--- trunk/Source/_javascript_Core/jit/JIT.cpp 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/jit/JIT.cpp 2014-08-22 19:54:30 UTC (rev 172867)
@@ -722,35 +722,38 @@
void JIT::privateCompileExceptionHandlers()
{
- if (m_exceptionChecks.empty() && m_exceptionChecksWithCallFrameRollback.empty())
- return;
+ if (!m_exceptionChecksWithCallFrameRollback.empty()) {
+ m_exceptionChecksWithCallFrameRollback.link(this);
- Jump doLookup;
+ // lookupExceptionHandlerFromCallerFrame is passed two arguments, the VM and the exec (the CallFrame*).
- if (!m_exceptionChecksWithCallFrameRollback.empty()) {
- m_exceptionChecksWithCallFrameRollback.link(this);
- emitGetCallerFrameFromCallFrameHeaderPtr(GPRInfo::argumentGPR1);
- doLookup = jump();
+ move(TrustedImmPtr(vm()), GPRInfo::argumentGPR0);
+ move(GPRInfo::callFrameRegister, GPRInfo::argumentGPR1);
+
+#if CPU(X86)
+ // FIXME: should use the call abstraction, but this is currently in the SpeculativeJIT layer!
+ poke(GPRInfo::argumentGPR0);
+ poke(GPRInfo::argumentGPR1, 1);
+#endif
+ m_calls.append(CallRecord(call(), (unsigned)-1, FunctionPtr(lookupExceptionHandlerFromCallerFrame).value()));
+ jumpToExceptionHandler();
}
- if (!m_exceptionChecks.empty())
+ if (!m_exceptionChecks.empty()) {
m_exceptionChecks.link(this);
-
- // lookupExceptionHandler is passed two arguments, the VM and the exec (the CallFrame*).
- move(GPRInfo::callFrameRegister, GPRInfo::argumentGPR1);
- if (doLookup.isSet())
- doLookup.link(this);
+ // lookupExceptionHandler is passed two arguments, the VM and the exec (the CallFrame*).
+ move(TrustedImmPtr(vm()), GPRInfo::argumentGPR0);
+ move(GPRInfo::callFrameRegister, GPRInfo::argumentGPR1);
- move(TrustedImmPtr(vm()), GPRInfo::argumentGPR0);
-
#if CPU(X86)
- // FIXME: should use the call abstraction, but this is currently in the SpeculativeJIT layer!
- poke(GPRInfo::argumentGPR0);
- poke(GPRInfo::argumentGPR1, 1);
+ // FIXME: should use the call abstraction, but this is currently in the SpeculativeJIT layer!
+ poke(GPRInfo::argumentGPR0);
+ poke(GPRInfo::argumentGPR1, 1);
#endif
- m_calls.append(CallRecord(call(), (unsigned)-1, FunctionPtr(lookupExceptionHandler).value()));
- jumpToExceptionHandler();
+ m_calls.append(CallRecord(call(), (unsigned)-1, FunctionPtr(lookupExceptionHandler).value()));
+ jumpToExceptionHandler();
+ }
}
unsigned JIT::frameRegisterCountFor(CodeBlock* codeBlock)
Modified: trunk/Source/_javascript_Core/jit/JITExceptions.cpp (172866 => 172867)
--- trunk/Source/_javascript_Core/jit/JITExceptions.cpp 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/jit/JITExceptions.cpp 2014-08-22 19:54:30 UTC (rev 172867)
@@ -48,7 +48,8 @@
}
RELEASE_ASSERT(exceptionValue);
- HandlerInfo* handler = vm->interpreter->unwind(callFrame, exceptionValue); // This may update callFrame.
+ VMEntryFrame* vmEntryFrame = vm->topVMEntryFrame;
+ HandlerInfo* handler = vm->interpreter->unwind(vmEntryFrame, callFrame, exceptionValue); // This may update vmEntryFrame and callFrame.
void* catchRoutine;
Instruction* catchPCForInterpreter = 0;
@@ -62,6 +63,7 @@
} else
catchRoutine = LLInt::getCodePtr(handleUncaughtException);
+ vm->vmEntryFrameForThrow = vmEntryFrame;
vm->callFrameForThrow = callFrame;
vm->targetMachinePCForThrow = catchRoutine;
vm->targetInterpreterPCForThrow = catchPCForInterpreter;
Modified: trunk/Source/_javascript_Core/jit/JITOpcodes.cpp (172866 => 172867)
--- trunk/Source/_javascript_Core/jit/JITOpcodes.cpp 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/jit/JITOpcodes.cpp 2014-08-22 19:54:30 UTC (rev 172867)
@@ -532,6 +532,8 @@
{
move(TrustedImmPtr(m_vm), regT3);
load64(Address(regT3, VM::callFrameForThrowOffset()), callFrameRegister);
+ load64(Address(regT3, VM::vmEntryFrameForThrowOffset()), regT0);
+ store64(regT0, Address(regT3, VM::topVMEntryFrameOffset()));
addPtr(TrustedImm32(stackPointerOffsetFor(codeBlock()) * sizeof(Register)), callFrameRegister, stackPointerRegister);
Modified: trunk/Source/_javascript_Core/jit/JITOpcodes32_64.cpp (172866 => 172867)
--- trunk/Source/_javascript_Core/jit/JITOpcodes32_64.cpp 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/jit/JITOpcodes32_64.cpp 2014-08-22 19:54:30 UTC (rev 172867)
@@ -813,6 +813,8 @@
move(TrustedImmPtr(m_vm), regT3);
// operationThrow returns the callFrame for the handler.
load32(Address(regT3, VM::callFrameForThrowOffset()), callFrameRegister);
+ load32(Address(regT3, VM::vmEntryFrameForThrowOffset()), regT0);
+ store32(regT0, Address(regT3, VM::topVMEntryFrameOffset()));
addPtr(TrustedImm32(stackPointerOffsetFor(codeBlock()) * sizeof(Register)), callFrameRegister, stackPointerRegister);
Modified: trunk/Source/_javascript_Core/jit/JITOperations.cpp (172866 => 172867)
--- trunk/Source/_javascript_Core/jit/JITOperations.cpp 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/jit/JITOperations.cpp 2014-08-22 19:54:30 UTC (rev 172867)
@@ -86,7 +86,7 @@
if (!callerFrame)
callerFrame = exec;
- NativeCallFrameTracer tracer(vm, vmEntryFrame, callerFrame);
+ NativeCallFrameTracerWithRestore tracer(vm, vmEntryFrame, callerFrame);
ErrorHandlingScope errorScope(*vm);
vm->throwException(callerFrame, createStackOverflowError(callerFrame));
}
@@ -101,7 +101,7 @@
int32_t missingArgCount = CommonSlowPaths::arityCheckFor(exec, &stack, CodeForCall);
if (missingArgCount < 0) {
- NativeCallFrameTracer tracer(vm, vmEntryFrame, callerFrame);
+ NativeCallFrameTracerWithRestore tracer(vm, vmEntryFrame, callerFrame);
throwStackOverflowError(callerFrame);
}
@@ -118,7 +118,7 @@
int32_t missingArgCount = CommonSlowPaths::arityCheckFor(exec, &stack, CodeForConstruct);
if (missingArgCount < 0) {
- NativeCallFrameTracer tracer(vm, vmEntryFrame, callerFrame);
+ NativeCallFrameTracerWithRestore tracer(vm, vmEntryFrame, callerFrame);
throwStackOverflowError(callerFrame);
}
@@ -1790,7 +1790,7 @@
JSValue exceptionValue = JSValue::decode(encodedExceptionValue);
vm->throwException(exec, exceptionValue);
- // Results stored out-of-band in vm.targetMachinePCForThrow & vm.callFrameForThrow
+ // Results stored out-of-band in vm.targetMachinePCForThrow, vm.callFrameForThrow & vm.vmEntryFrameForThrow
genericUnwind(vm, exec, exceptionValue);
}
@@ -1838,6 +1838,21 @@
ASSERT(vm->targetMachinePCForThrow);
}
+void JIT_OPERATION lookupExceptionHandlerFromCallerFrame(VM* vm, ExecState* exec)
+{
+ VMEntryFrame* vmEntryFrame = vm->topVMEntryFrame;
+ CallFrame* callerFrame = exec->callerFrame(vmEntryFrame);
+ ASSERT(callerFrame);
+
+ NativeCallFrameTracer tracer(vm, callerFrame);
+
+ JSValue exceptionValue = vm->exception();
+ ASSERT(exceptionValue);
+
+ genericUnwind(vm, callerFrame, exceptionValue);
+ ASSERT(vm->targetMachinePCForThrow);
+}
+
void JIT_OPERATION operationVMHandleException(ExecState* exec)
{
VM* vm = &exec->vm();
Modified: trunk/Source/_javascript_Core/jit/JITOperations.h (172866 => 172867)
--- trunk/Source/_javascript_Core/jit/JITOperations.h 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/jit/JITOperations.h 2014-08-22 19:54:30 UTC (rev 172867)
@@ -205,6 +205,7 @@
// the return location from one of the calls out to one of the helper operations above.
void JIT_OPERATION lookupExceptionHandler(VM*, ExecState*) WTF_INTERNAL;
+void JIT_OPERATION lookupExceptionHandlerFromCallerFrame(VM*, ExecState*) WTF_INTERNAL;
void JIT_OPERATION operationVMHandleException(ExecState*) WTF_INTERNAL;
void JIT_OPERATION operationThrowStackOverflowError(ExecState*, CodeBlock*) WTF_INTERNAL;
Modified: trunk/Source/_javascript_Core/llint/LowLevelInterpreter32_64.asm (172866 => 172867)
--- trunk/Source/_javascript_Core/llint/LowLevelInterpreter32_64.asm 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/llint/LowLevelInterpreter32_64.asm 2014-08-22 19:54:30 UTC (rev 172867)
@@ -2048,6 +2048,8 @@
andp MarkedBlockMask, t3
loadp MarkedBlock::m_weakSet + WeakSet::m_vm[t3], t3
loadp VM::callFrameForThrow[t3], cfr
+ loadp VM::vmEntryFrameForThrow[t3], t0
+ storep t0, VM::topVMEntryFrame[t3]
restoreStackPointerAfterCall()
loadi VM::targetInterpreterPCForThrow[t3], PC
Modified: trunk/Source/_javascript_Core/llint/LowLevelInterpreter64.asm (172866 => 172867)
--- trunk/Source/_javascript_Core/llint/LowLevelInterpreter64.asm 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/llint/LowLevelInterpreter64.asm 2014-08-22 19:54:30 UTC (rev 172867)
@@ -1903,6 +1903,8 @@
andp MarkedBlockMask, t3
loadp MarkedBlock::m_weakSet + WeakSet::m_vm[t3], t3
loadp VM::callFrameForThrow[t3], cfr
+ loadp VM::vmEntryFrameForThrow[t3], t0
+ storep t0, VM::topVMEntryFrame[t3]
restoreStackPointerAfterCall()
loadp CodeBlock[cfr], PB
Modified: trunk/Source/_javascript_Core/runtime/VM.h (172866 => 172867)
--- trunk/Source/_javascript_Core/runtime/VM.h 2014-08-22 19:39:51 UTC (rev 172866)
+++ trunk/Source/_javascript_Core/runtime/VM.h 2014-08-22 19:54:30 UTC (rev 172867)
@@ -346,6 +346,16 @@
return OBJECT_OFFSETOF(VM, m_exception);
}
+ static ptrdiff_t vmEntryFrameForThrowOffset()
+ {
+ return OBJECT_OFFSETOF(VM, vmEntryFrameForThrow);
+ }
+
+ static ptrdiff_t topVMEntryFrameOffset()
+ {
+ return OBJECT_OFFSETOF(VM, topVMEntryFrame);
+ }
+
static ptrdiff_t callFrameForThrowOffset()
{
return OBJECT_OFFSETOF(VM, callFrameForThrow);
@@ -401,6 +411,7 @@
JSValue hostCallReturnValue;
ExecState* newCallFrameReturnValue;
+ VMEntryFrame* vmEntryFrameForThrow;
ExecState* callFrameForThrow;
void* targetMachinePCForThrow;
Instruction* targetInterpreterPCForThrow;