From 51a9926e09803966cf8400084106656e471f7025 Mon Sep 17 00:00:00 2001 From: "ggaren@apple.com" Date: Sat, 6 Apr 2013 18:24:37 +0000 Subject: [PATCH] Rolled out 147820 and 147818 because they caused plugins tests to ASSERT https://bugs.webkit.org/show_bug.cgi?id=114094 Reviewed by Anders Carlsson. Source/JavaScriptCore: * API/JSContextRef.cpp: (JSContextCreateBacktrace): * bytecompiler/BytecodeGenerator.cpp: (JSC::BytecodeGenerator::emitDebugHook): * interpreter/Interpreter.cpp: (JSC): (JSC::Interpreter::dumpRegisters): (JSC::Interpreter::unwindCallFrame): (JSC::getLineNumberForCallFrame): (JSC::getCallerInfo): (JSC::Interpreter::getStackTrace): (JSC::Interpreter::addStackTraceIfNecessary): (JSC::Interpreter::retrieveCallerFromVMCode): * interpreter/Interpreter.h: (StackFrame): (JSC::StackFrame::toString): (JSC::StackFrame::friendlyLineNumber): (Interpreter): * runtime/Error.cpp: (JSC::throwError): * runtime/JSGlobalData.h: (JSC): (JSGlobalData): * runtime/JSGlobalObject.cpp: (JSC::DynamicGlobalObjectScope::DynamicGlobalObjectScope): Source/WebCore: * bindings/js/ScriptCallStackFactory.cpp: (WebCore::createScriptCallStack): * inspector/ScriptCallFrame.cpp: (WebCore::ScriptCallFrame::isEqual): * inspector/ScriptCallFrame.h: (ScriptCallFrame): (WebCore::ScriptCallFrame::lineNumber): Tools: * Scripts/run-jsc: git-svn-id: http://svn.webkit.org/repository/webkit/trunk@147846 268f45cc-cd09-0410-ab3c-d52691b4dbfc --- Source/JavaScriptCore/API/JSContextRef.cpp | 48 +++++--- Source/JavaScriptCore/ChangeLog | 33 +++++ .../bytecompiler/BytecodeGenerator.cpp | 1 - .../interpreter/Interpreter.cpp | 114 ++++++------------ .../JavaScriptCore/interpreter/Interpreter.h | 35 ++++-- Source/JavaScriptCore/runtime/Error.cpp | 3 +- Source/JavaScriptCore/runtime/JSGlobalData.h | 3 - .../JavaScriptCore/runtime/JSGlobalObject.cpp | 2 - Source/WebCore/ChangeLog | 15 +++ .../bindings/js/ScriptCallStackFactory.cpp | 43 ++++--- Source/WebCore/inspector/ScriptCallFrame.cpp | 3 +- Source/WebCore/inspector/ScriptCallFrame.h | 3 +- Tools/ChangeLog | 9 ++ Tools/Scripts/run-jsc | 1 + 14 files changed, 180 insertions(+), 133 deletions(-) diff --git a/Source/JavaScriptCore/API/JSContextRef.cpp b/Source/JavaScriptCore/API/JSContextRef.cpp index bc2187671f3..2104ea32127 100644 --- a/Source/JavaScriptCore/API/JSContextRef.cpp +++ b/Source/JavaScriptCore/API/JSContextRef.cpp @@ -36,7 +36,6 @@ #include "JSGlobalObject.h" #include "JSObject.h" #include "Operations.h" -#include "SourceProvider.h" #include #include @@ -176,38 +175,51 @@ JSStringRef JSContextCreateBacktrace(JSContextRef ctx, unsigned maxStackSize) { ExecState* exec = toJS(ctx); JSLockHolder lock(exec); - StringBuilder builder; - Vector stackTrace; - Interpreter::getStackTrace(&exec->globalData(), stackTrace, maxStackSize); - for (size_t i = 0; i < stackTrace.size(); i++) { + unsigned count = 0; + StringBuilder builder; + CallFrame* callFrame = exec; + String functionName; + if (exec->callee()) { + if (asObject(exec->callee())->inherits(&InternalFunction::s_info)) { + functionName = asInternalFunction(exec->callee())->name(exec); + builder.appendLiteral("#0 "); + builder.append(functionName); + builder.appendLiteral("() "); + count++; + } + } + while (true) { + RELEASE_ASSERT(callFrame); + int signedLineNumber; + intptr_t sourceID; String urlString; - String functionName; - StackFrame& frame = stackTrace[i]; - JSValue function = frame.callee.get(); - if (frame.callee) - functionName = frame.friendlyFunctionName(exec); + JSValue function; + + exec->interpreter()->retrieveLastCaller(callFrame, signedLineNumber, sourceID, urlString, function); + + if (function) + functionName = jsCast(function)->name(exec); else { // Caller is unknown, but if frame is empty we should still add the frame, because // something called us, and gave us arguments. - if (i) + if (count) break; } - unsigned lineNumber = frame.line(); + unsigned lineNumber = signedLineNumber >= 0 ? signedLineNumber : 0; if (!builder.isEmpty()) builder.append('\n'); builder.append('#'); - builder.appendNumber(i); + builder.appendNumber(count); builder.append(' '); builder.append(functionName); builder.appendLiteral("() at "); builder.append(urlString); - if (frame.codeType != StackFrameNativeCode) { - builder.append(':'); - builder.appendNumber(lineNumber); - } - if (!function) + builder.append(':'); + builder.appendNumber(lineNumber); + if (!function || ++count == maxStackSize) break; + callFrame = callFrame->callerFrame(); } return OpaqueJSString::create(builder.toString()).leakRef(); } diff --git a/Source/JavaScriptCore/ChangeLog b/Source/JavaScriptCore/ChangeLog index 990d3141025..5adfad8c7e8 100644 --- a/Source/JavaScriptCore/ChangeLog +++ b/Source/JavaScriptCore/ChangeLog @@ -1,3 +1,36 @@ +2013-04-06 Geoffrey Garen + + Rolled out 147820 and 147818 because they caused plugins tests to ASSERT + https://bugs.webkit.org/show_bug.cgi?id=114094 + + Reviewed by Anders Carlsson. + + * API/JSContextRef.cpp: + (JSContextCreateBacktrace): + * bytecompiler/BytecodeGenerator.cpp: + (JSC::BytecodeGenerator::emitDebugHook): + * interpreter/Interpreter.cpp: + (JSC): + (JSC::Interpreter::dumpRegisters): + (JSC::Interpreter::unwindCallFrame): + (JSC::getLineNumberForCallFrame): + (JSC::getCallerInfo): + (JSC::Interpreter::getStackTrace): + (JSC::Interpreter::addStackTraceIfNecessary): + (JSC::Interpreter::retrieveCallerFromVMCode): + * interpreter/Interpreter.h: + (StackFrame): + (JSC::StackFrame::toString): + (JSC::StackFrame::friendlyLineNumber): + (Interpreter): + * runtime/Error.cpp: + (JSC::throwError): + * runtime/JSGlobalData.h: + (JSC): + (JSGlobalData): + * runtime/JSGlobalObject.cpp: + (JSC::DynamicGlobalObjectScope::DynamicGlobalObjectScope): + 2013-04-06 Patrick Gansterer Unreviewed build fix after r146932. diff --git a/Source/JavaScriptCore/bytecompiler/BytecodeGenerator.cpp b/Source/JavaScriptCore/bytecompiler/BytecodeGenerator.cpp index 4ae7fb2847f..7110f857d69 100644 --- a/Source/JavaScriptCore/bytecompiler/BytecodeGenerator.cpp +++ b/Source/JavaScriptCore/bytecompiler/BytecodeGenerator.cpp @@ -2055,7 +2055,6 @@ void BytecodeGenerator::emitDebugHook(DebugHookID debugHookID, int firstLine, in if (!m_shouldEmitDebugHooks) return; #endif - emitExpressionInfo(charPosition, 0, 0); emitOpcode(op_debug); instructions().append(debugHookID); instructions().append(firstLine); diff --git a/Source/JavaScriptCore/interpreter/Interpreter.cpp b/Source/JavaScriptCore/interpreter/Interpreter.cpp index 25e11e68937..e2c78ac23ea 100644 --- a/Source/JavaScriptCore/interpreter/Interpreter.cpp +++ b/Source/JavaScriptCore/interpreter/Interpreter.cpp @@ -199,7 +199,7 @@ Interpreter::StackPolicy::StackPolicy(Interpreter& interpreter, const StackBound } -static CallFrame* getCallerInfo(JSGlobalData*, CallFrame*, unsigned& bytecodeOffset, CodeBlock*& callerOut); +static CallFrame* getCallerInfo(JSGlobalData*, CallFrame*, int& lineNumber, unsigned& bytecodeOffset, CodeBlock*& callerOut); // Returns the depth of the scope chain within a given call frame. static int depth(CodeBlock* codeBlock, JSScope* sc) @@ -422,9 +422,8 @@ void Interpreter::dumpRegisters(CallFrame* callFrame) #endif unsigned bytecodeOffset = 0; int line = 0; - CodeBlock* callerCodeBlock = 0; - getCallerInfo(&callFrame->globalData(), callFrame, bytecodeOffset, callerCodeBlock); - line = callerCodeBlock->lineNumberForBytecodeOffset(bytecodeOffset); + CodeBlock* unusedCallerCodeBlock = 0; + getCallerInfo(&callFrame->globalData(), callFrame, line, bytecodeOffset, unusedCallerCodeBlock); dataLogF("[ReturnVPC] | %10p | %d (line %d)\n", it, bytecodeOffset, line); ++it; dataLogF("[CodeBlock] | %10p | %p \n", it, callFrame->codeBlock()); @@ -508,7 +507,8 @@ NEVER_INLINE bool Interpreter::unwindCallFrame(CallFrame*& callFrame, JSValue ex callFrame->globalData().topCallFrame = callerFrame; if (callerFrame->hasHostCallFrameFlag()) return false; - callFrame = getCallerInfo(&callFrame->globalData(), callFrame, bytecodeOffset, codeBlock); + int unusedLineNumber = 0; + callFrame = getCallerInfo(&callFrame->globalData(), callFrame, unusedLineNumber, bytecodeOffset, codeBlock); return true; } @@ -564,25 +564,27 @@ static void appendSourceToError(CallFrame* callFrame, ErrorInstance* exception, exception->putDirect(*globalData, globalData->propertyNames->message, jsString(globalData, message)); } -static unsigned getBytecodeOffsetForCallFrame(CallFrame* callFrame) +static int getLineNumberForCallFrame(JSGlobalData* globalData, CallFrame* callFrame) { + UNUSED_PARAM(globalData); callFrame = callFrame->removeHostCallFrameFlag(); CodeBlock* codeBlock = callFrame->codeBlock(); if (!codeBlock) - return 0; -#if ENABLE(JIT) + return -1; +#if ENABLE(JIT) || ENABLE(LLINT) #if ENABLE(DFG_JIT) if (codeBlock->getJITType() == JITCode::DFGJIT) - return codeBlock->codeOrigin(callFrame->codeOriginIndexForDFG()).bytecodeIndex; + return codeBlock->lineNumberForBytecodeOffset(codeBlock->codeOrigin(callFrame->codeOriginIndexForDFG()).bytecodeIndex); #endif - return callFrame->bytecodeOffsetForNonDFGCode(); + return codeBlock->lineNumberForBytecodeOffset(callFrame->bytecodeOffsetForNonDFGCode()); #endif } -static CallFrame* getCallerInfo(JSGlobalData* globalData, CallFrame* callFrame, unsigned& bytecodeOffset, CodeBlock*& caller) +static CallFrame* getCallerInfo(JSGlobalData* globalData, CallFrame* callFrame, int& lineNumber, unsigned& bytecodeOffset, CodeBlock*& caller) { ASSERT_UNUSED(globalData, globalData); bytecodeOffset = 0; + lineNumber = -1; ASSERT(!callFrame->hasHostCallFrameFlag()); CallFrame* callerFrame = callFrame->codeBlock() ? callFrame->trueCallerFrame() : callFrame->callerFrame()->removeHostCallFrameFlag(); bool callframeIsHost = callerFrame->addHostCallFrameFlag() == callFrame->callerFrame(); @@ -652,6 +654,7 @@ static CallFrame* getCallerInfo(JSGlobalData* globalData, CallFrame* callFrame, RELEASE_ASSERT(callerCodeBlock); caller = callerCodeBlock; + lineNumber = callerCodeBlock->lineNumberForBytecodeOffset(bytecodeOffset); return callerFrame; } @@ -677,97 +680,51 @@ static StackFrameCodeType getStackFrameCodeType(CallFrame* callFrame) return StackFrameGlobalCode; } -unsigned StackFrame::line() -{ - return codeBlock ? codeBlock->lineNumberForBytecodeOffset(bytecodeOffset) + lineOffset : 0; -} - -unsigned StackFrame::column() -{ - if (!code) - return 0; - int divot = 0; - int unusedStartOffset = 0; - int unusedEndOffset = 0; - expressionInfo(divot, unusedStartOffset, unusedEndOffset); - return code->charPositionToColumnNumber(divot); -} - -void StackFrame::expressionInfo(int& divot, int& startOffset, int& endOffset) -{ - codeBlock->expressionRangeForBytecodeOffset(bytecodeOffset, divot, startOffset, endOffset); - divot += startOffset; -} - -String StackFrame::toString(CallFrame* callFrame) -{ - StringBuilder traceBuild; - String functionName = friendlyFunctionName(callFrame); - String sourceURL = friendlySourceURL(); - traceBuild.append(functionName); - if (!sourceURL.isEmpty()) { - if (!functionName.isEmpty()) - traceBuild.append('@'); - traceBuild.append(sourceURL); - if (codeType != StackFrameNativeCode) { - traceBuild.append(':'); - traceBuild.appendNumber(line()); - } - } - return traceBuild.toString().impl(); -} - -void Interpreter::getStackTrace(JSGlobalData* globalData, Vector& results, size_t maxStackSize) +void Interpreter::getStackTrace(JSGlobalData* globalData, Vector& results) { CallFrame* callFrame = globalData->topCallFrame->removeHostCallFrameFlag(); if (!callFrame || callFrame == CallFrame::noCaller()) return; - unsigned bytecodeOffset = getBytecodeOffsetForCallFrame(callFrame); + int line = getLineNumberForCallFrame(globalData, callFrame); + callFrame = callFrame->trueCallFrameFromVMCode(); if (!callFrame) return; - CodeBlock* callerCodeBlock = callFrame->codeBlock(); - while (callFrame && callFrame != CallFrame::noCaller() && maxStackSize--) { + while (callFrame && callFrame != CallFrame::noCaller()) { String sourceURL; - if (callerCodeBlock) { + if (callFrame->codeBlock()) { sourceURL = getSourceURLFromCallFrame(callFrame); - StackFrame s = { - Strong(*globalData, callFrame->callee()), - getStackFrameCodeType(callFrame), - Strong(*globalData, callerCodeBlock->ownerExecutable()), - Strong(*globalData, callerCodeBlock->unlinkedCodeBlock()), - callerCodeBlock->source(), - callerCodeBlock->ownerExecutable()->lineNo(), - callerCodeBlock->sourceOffset(), - bytecodeOffset, - sourceURL - }; + StackFrame s = { Strong(*globalData, callFrame->callee()), getStackFrameCodeType(callFrame), Strong(*globalData, callFrame->codeBlock()->ownerExecutable()), line, sourceURL}; results.append(s); } else { - StackFrame s = { Strong(*globalData, callFrame->callee()), StackFrameNativeCode, Strong(), Strong(), 0, 0, 0, 0, String()}; + StackFrame s = { Strong(*globalData, callFrame->callee()), StackFrameNativeCode, Strong(), -1, String()}; results.append(s); } - callFrame = getCallerInfo(globalData, callFrame, bytecodeOffset, callerCodeBlock); + unsigned unusedBytecodeOffset = 0; + CodeBlock* unusedCallerCodeBlock = 0; + callFrame = getCallerInfo(globalData, callFrame, line, unusedBytecodeOffset, unusedCallerCodeBlock); } } -void Interpreter::addStackTraceIfNecessary(CallFrame* callFrame, JSValue error) +void Interpreter::addStackTraceIfNecessary(CallFrame* callFrame, JSObject* error) { JSGlobalData* globalData = &callFrame->globalData(); ASSERT(callFrame == globalData->topCallFrame || callFrame == callFrame->lexicalGlobalObject()->globalExec() || callFrame == callFrame->dynamicGlobalObject()->globalExec()); + if (error->hasProperty(callFrame, globalData->propertyNames->stack)) + return; Vector stackTrace; getStackTrace(&callFrame->globalData(), stackTrace); - if (stackTrace.isEmpty() || !error.isObject()) + if (stackTrace.isEmpty()) return; - JSObject* errorObject = asObject(error); + JSGlobalObject* globalObject = 0; if (isTerminatedExecutionException(error) || isInterruptedExecutionException(error)) globalObject = globalData->dynamicGlobalObject; else - globalObject = errorObject->globalObject(); + globalObject = error->globalObject(); // FIXME: JSStringJoiner could be more efficient than StringBuilder here. StringBuilder builder; @@ -776,10 +733,8 @@ void Interpreter::addStackTraceIfNecessary(CallFrame* callFrame, JSValue error) if (i != stackTrace.size() - 1) builder.append('\n'); } - - if (errorObject->hasProperty(callFrame, globalData->propertyNames->stack)) - return; - errorObject->putDirect(*globalData, globalData->propertyNames->stack, jsString(globalData, builder.toString()), ReadOnly | DontDelete); + + error->putDirect(*globalData, globalData->propertyNames->stack, jsString(globalData, builder.toString()), ReadOnly | DontDelete); } NEVER_INLINE HandlerInfo* Interpreter::throwException(CallFrame*& callFrame, JSValue& exceptionValue, unsigned bytecodeOffset) @@ -1422,9 +1377,10 @@ JSValue Interpreter::retrieveCallerFromVMCode(CallFrame* callFrame, JSFunction* if (!functionCallFrame) return jsNull(); + int lineNumber; unsigned bytecodeOffset; CodeBlock* unusedCallerCodeBlock = 0; - CallFrame* callerFrame = getCallerInfo(&callFrame->globalData(), functionCallFrame, bytecodeOffset, unusedCallerCodeBlock); + CallFrame* callerFrame = getCallerInfo(&callFrame->globalData(), functionCallFrame, lineNumber, bytecodeOffset, unusedCallerCodeBlock); if (!callerFrame) return jsNull(); JSValue caller = callerFrame->callee(); @@ -1434,7 +1390,7 @@ JSValue Interpreter::retrieveCallerFromVMCode(CallFrame* callFrame, JSFunction* // Skip over function bindings. ASSERT(caller.isObject()); while (asObject(caller)->inherits(&JSBoundFunction::s_info)) { - callerFrame = getCallerInfo(&callFrame->globalData(), callerFrame, bytecodeOffset, unusedCallerCodeBlock); + callerFrame = getCallerInfo(&callFrame->globalData(), callerFrame, lineNumber, bytecodeOffset, unusedCallerCodeBlock); if (!callerFrame) return jsNull(); caller = callerFrame->callee(); diff --git a/Source/JavaScriptCore/interpreter/Interpreter.h b/Source/JavaScriptCore/interpreter/Interpreter.h index ad3375e0070..7f938543bb4 100644 --- a/Source/JavaScriptCore/interpreter/Interpreter.h +++ b/Source/JavaScriptCore/interpreter/Interpreter.h @@ -79,13 +79,25 @@ namespace JSC { Strong callee; StackFrameCodeType codeType; Strong executable; - Strong codeBlock; - RefPtr code; - int lineOffset; - unsigned characterOffset; - unsigned bytecodeOffset; + int line; String sourceURL; - JS_EXPORT_PRIVATE String toString(CallFrame*); + String toString(CallFrame* callFrame) const + { + StringBuilder traceBuild; + String functionName = friendlyFunctionName(callFrame); + String sourceURL = friendlySourceURL(); + traceBuild.append(functionName); + if (!sourceURL.isEmpty()) { + if (!functionName.isEmpty()) + traceBuild.append('@'); + traceBuild.append(sourceURL); + if (line > -1) { + traceBuild.append(':'); + traceBuild.appendNumber(line); + } + } + return traceBuild.toString().impl(); + } String friendlySourceURL() const { String traceLine; @@ -125,9 +137,10 @@ namespace JSC { } return traceLine.isNull() ? emptyString() : traceLine; } - JS_EXPORT_PRIVATE unsigned line(); - JS_EXPORT_PRIVATE unsigned column(); - JS_EXPORT_PRIVATE void expressionInfo(int& divot, int& startOffset, int& endOffset); + unsigned friendlyLineNumber() const + { + return line > -1 ? line : 0; + } }; class TopCallFrameSetter { @@ -219,8 +232,8 @@ namespace JSC { NEVER_INLINE HandlerInfo* throwException(CallFrame*&, JSValue&, unsigned bytecodeOffset); NEVER_INLINE void debug(CallFrame*, DebugHookID, int firstLine, int lastLine, int column); static const String getTraceLine(CallFrame*, StackFrameCodeType, const String&, int); - JS_EXPORT_PRIVATE static void getStackTrace(JSGlobalData*, Vector& results, size_t maxStackSize = std::numeric_limits::max()); - static void addStackTraceIfNecessary(CallFrame*, JSValue error); + JS_EXPORT_PRIVATE static void getStackTrace(JSGlobalData*, Vector& results); + static void addStackTraceIfNecessary(CallFrame*, JSObject* error); void dumpSampleData(ExecState* exec); void startSampling(); diff --git a/Source/JavaScriptCore/runtime/Error.cpp b/Source/JavaScriptCore/runtime/Error.cpp index 7eb10109980..6855844f9ae 100644 --- a/Source/JavaScriptCore/runtime/Error.cpp +++ b/Source/JavaScriptCore/runtime/Error.cpp @@ -155,7 +155,8 @@ bool hasErrorInfo(ExecState* exec, JSObject* error) JSValue throwError(ExecState* exec, JSValue error) { - Interpreter::addStackTraceIfNecessary(exec, error); + if (error.isObject()) + return throwError(exec, asObject(error)); exec->globalData().exception = error; return error; } diff --git a/Source/JavaScriptCore/runtime/JSGlobalData.h b/Source/JavaScriptCore/runtime/JSGlobalData.h index d14a24ca286..337b0cb6e5d 100644 --- a/Source/JavaScriptCore/runtime/JSGlobalData.h +++ b/Source/JavaScriptCore/runtime/JSGlobalData.h @@ -54,7 +54,6 @@ #include #include #include -#include #include #include #include @@ -82,7 +81,6 @@ namespace JSC { class RegExpCache; class SourceProvider; class SourceProviderCache; - struct StackFrame; class Stringifier; class Structure; #if ENABLE(REGEXP_TRACING) @@ -330,7 +328,6 @@ namespace JSC { Terminator terminator; JSValue exception; - RefCountedArray exceptionStack; const ClassInfo* const jsArrayClassInfo; const ClassInfo* const jsFinalObjectClassInfo; diff --git a/Source/JavaScriptCore/runtime/JSGlobalObject.cpp b/Source/JavaScriptCore/runtime/JSGlobalObject.cpp index 632b1a7bc2b..485d88c1667 100644 --- a/Source/JavaScriptCore/runtime/JSGlobalObject.cpp +++ b/Source/JavaScriptCore/runtime/JSGlobalObject.cpp @@ -597,8 +597,6 @@ DynamicGlobalObjectScope::DynamicGlobalObjectScope(JSGlobalData& globalData, JSG // to observe time zone changes. globalData.resetDateCache(); } - // Clear the exception stack between entries - globalData.exceptionStack = RefCountedArray(); } void slowValidateCell(JSGlobalObject* globalObject) diff --git a/Source/WebCore/ChangeLog b/Source/WebCore/ChangeLog index 4521bd5e7d6..239477b5e99 100644 --- a/Source/WebCore/ChangeLog +++ b/Source/WebCore/ChangeLog @@ -1,3 +1,18 @@ +2013-04-06 Geoffrey Garen + + Rolled out 147820 and 147818 because they caused plugins tests to ASSERT + https://bugs.webkit.org/show_bug.cgi?id=114094 + + Reviewed by Anders Carlsson. + + * bindings/js/ScriptCallStackFactory.cpp: + (WebCore::createScriptCallStack): + * inspector/ScriptCallFrame.cpp: + (WebCore::ScriptCallFrame::isEqual): + * inspector/ScriptCallFrame.h: + (ScriptCallFrame): + (WebCore::ScriptCallFrame::lineNumber): + 2013-04-06 Anders Carlsson Remove VisitedLinks.{cpp|h} diff --git a/Source/WebCore/bindings/js/ScriptCallStackFactory.cpp b/Source/WebCore/bindings/js/ScriptCallStackFactory.cpp index a26ea63e2c8..2600c33103e 100644 --- a/Source/WebCore/bindings/js/ScriptCallStackFactory.cpp +++ b/Source/WebCore/bindings/js/ScriptCallStackFactory.cpp @@ -58,15 +58,18 @@ PassRefPtr createScriptCallStack(size_t maxStackSize, bool empt Vector frames; if (JSC::ExecState* exec = JSMainThreadExecState::currentState()) { Vector stackTrace; - Interpreter::getStackTrace(&exec->globalData(), stackTrace, maxStackSize); - for (size_t i = 0; i < stackTrace.size(); i++) - frames.append(ScriptCallFrame(stackTrace[i].friendlyFunctionName(exec), stackTrace[i].friendlySourceURL(), stackTrace[i].line(), stackTrace[i].column())); + Interpreter::getStackTrace(&exec->globalData(), stackTrace); + for (Vector::const_iterator iter = stackTrace.begin(); iter < stackTrace.end(); iter++) { + frames.append(ScriptCallFrame(iter->friendlyFunctionName(exec), iter->friendlySourceURL(), iter->friendlyLineNumber())); + if (frames.size() >= maxStackSize) + break; + } } if (frames.isEmpty() && !emptyIsAllowed) { // No frames found. It may happen in the case where // a bound function is called from native code for example. // Fallback to setting lineNumber to 0, and source and function name to "undefined". - frames.append(ScriptCallFrame("undefined", "undefined", 0, 0)); + frames.append(ScriptCallFrame("undefined", "undefined", 0)); } return ScriptCallStack::create(frames); } @@ -74,18 +77,30 @@ PassRefPtr createScriptCallStack(size_t maxStackSize, bool empt PassRefPtr createScriptCallStack(JSC::ExecState* exec, size_t maxStackSize) { Vector frames; - Vector stackTrace; - Interpreter::getStackTrace(&exec->globalData(), stackTrace, maxStackSize + 1); - for (size_t i = 1; i < stackTrace.size(); i++) { - // This early exit is necessary to maintain our old behaviour - // but the stack trace we produce now is complete and handles all - // ways in which code may be running - if (!stackTrace[i].callee && frames.size()) + CallFrame* callFrame = exec; + while (true) { + ASSERT(callFrame); + int signedLineNumber; + intptr_t sourceID; + String urlString; + JSValue function; + + exec->interpreter()->retrieveLastCaller(callFrame, signedLineNumber, sourceID, urlString, function); + String functionName; + if (function) + functionName = jsCast(function)->name(exec); + else { + // Caller is unknown, but if frames is empty we should still add the frame, because + // something called us, and gave us arguments. + if (!frames.isEmpty()) + break; + } + unsigned lineNumber = signedLineNumber >= 0 ? signedLineNumber : 0; + frames.append(ScriptCallFrame(functionName, urlString, lineNumber)); + if (!function || frames.size() == maxStackSize) break; - String functionName = stackTrace[i].friendlyFunctionName(exec); - frames.append(ScriptCallFrame(functionName, stackTrace[i].sourceURL, stackTrace[i].line(), stackTrace[i].column())); + callFrame = callFrame->callerFrame(); } - return ScriptCallStack::create(frames); } diff --git a/Source/WebCore/inspector/ScriptCallFrame.cpp b/Source/WebCore/inspector/ScriptCallFrame.cpp index 1abbd758bcc..114c24d9330 100644 --- a/Source/WebCore/inspector/ScriptCallFrame.cpp +++ b/Source/WebCore/inspector/ScriptCallFrame.cpp @@ -53,8 +53,7 @@ bool ScriptCallFrame::isEqual(const ScriptCallFrame& o) const { return m_functionName == o.m_functionName && m_scriptName == o.m_scriptName - && m_lineNumber == o.m_lineNumber - && m_column == o.m_column; + && m_lineNumber == o.m_lineNumber; } #if ENABLE(INSPECTOR) diff --git a/Source/WebCore/inspector/ScriptCallFrame.h b/Source/WebCore/inspector/ScriptCallFrame.h index 67f0d3611a1..9154104fc94 100644 --- a/Source/WebCore/inspector/ScriptCallFrame.h +++ b/Source/WebCore/inspector/ScriptCallFrame.h @@ -44,13 +44,12 @@ class InspectorObject; class ScriptCallFrame { public: - ScriptCallFrame(const String& functionName, const String& scriptName, unsigned lineNumber, unsigned column); + ScriptCallFrame(const String& functionName, const String& scriptName, unsigned lineNumber, unsigned column = 0); ~ScriptCallFrame(); const String& functionName() const { return m_functionName; } const String& sourceURL() const { return m_scriptName; } unsigned lineNumber() const { return m_lineNumber; } - unsigned columnNumber() const { return m_column; } bool isEqual(const ScriptCallFrame&) const; diff --git a/Tools/ChangeLog b/Tools/ChangeLog index 81b60557c89..d53ead66638 100644 --- a/Tools/ChangeLog +++ b/Tools/ChangeLog @@ -1,3 +1,12 @@ +2013-04-06 Geoffrey Garen + + Rolled out 147820 and 147818 because they caused plugins tests to ASSERT + https://bugs.webkit.org/show_bug.cgi?id=114094 + + Reviewed by Anders Carlsson. + + * Scripts/run-jsc: + 2013-04-05 Ojan Vafai Move the flakiness dashboard to the new instance at webkit-test-results.appspot.com diff --git a/Tools/Scripts/run-jsc b/Tools/Scripts/run-jsc index 82943c0a187..e5341c1d378 100755 --- a/Tools/Scripts/run-jsc +++ b/Tools/Scripts/run-jsc @@ -42,6 +42,7 @@ my $count = 1; my $verbose = 0; GetOptions("count|c=i" => \$count, "verbose|v" => \$verbose); +die "$usage\n" if (@ARGV < 1); my $jsc = jscProductDir() . "/jsc @ARGV"; $jsc .= " 2> " . File::Spec->devnull() unless $verbose; -- GitLab