Diff
Modified: trunk/Source/_javascript_Core/ChangeLog (137246 => 137247)
--- trunk/Source/_javascript_Core/ChangeLog 2012-12-11 05:17:49 UTC (rev 137246)
+++ trunk/Source/_javascript_Core/ChangeLog 2012-12-11 05:22:49 UTC (rev 137247)
@@ -1,3 +1,28 @@
+2012-12-10 Filip Pizlo <[email protected]>
+
+ Don't OSR exit just because a string is a rope
+ https://bugs.webkit.org/show_bug.cgi?id=104621
+
+ Reviewed by Michael Saboff.
+
+ Slight SunSpider speed-up at around the 0.7% level. This patch does the obvious
+ thing of calling a slow path to resolve ropes rather than OSR exiting if the
+ string is a rope.
+
+ * dfg/DFGAbstractState.cpp:
+ (JSC::DFG::AbstractState::execute):
+ * dfg/DFGArrayMode.h:
+ (JSC::DFG::ArrayMode::getIndexedPropertyStorageMayTriggerGC):
+ (ArrayMode):
+ * dfg/DFGCSEPhase.cpp:
+ (JSC::DFG::CSEPhase::putStructureStoreElimination):
+ * dfg/DFGOperations.cpp:
+ * dfg/DFGOperations.h:
+ * dfg/DFGSpeculativeJIT.cpp:
+ (JSC::DFG::SpeculativeJIT::compileGetIndexedPropertyStorage):
+ * dfg/DFGSpeculativeJIT.h:
+ (JSC::DFG::SpeculativeJIT::callOperation):
+
2012-12-10 Gustavo Noronha Silva <[email protected]>
Unreviewed distcheck fix.
Modified: trunk/Source/_javascript_Core/dfg/DFGAbstractState.cpp (137246 => 137247)
--- trunk/Source/_javascript_Core/dfg/DFGAbstractState.cpp 2012-12-11 05:17:49 UTC (rev 137246)
+++ trunk/Source/_javascript_Core/dfg/DFGAbstractState.cpp 2012-12-11 05:22:49 UTC (rev 137247)
@@ -1598,16 +1598,7 @@
break;
}
case GetIndexedPropertyStorage: {
- switch (node.arrayMode().type()) {
- case Array::String:
- // Strings are weird - we may spec fail if the string was a rope. That is of course
- // stupid, and we should fix that, but for now let's at least be honest about it.
- node.setCanExit(true);
- break;
- default:
- node.setCanExit(false);
- break;
- }
+ node.setCanExit(false);
forNode(nodeIndex).clear();
break;
}
Modified: trunk/Source/_javascript_Core/dfg/DFGArrayMode.h (137246 => 137247)
--- trunk/Source/_javascript_Core/dfg/DFGArrayMode.h 2012-12-11 05:17:49 UTC (rev 137246)
+++ trunk/Source/_javascript_Core/dfg/DFGArrayMode.h 2012-12-11 05:22:49 UTC (rev 137247)
@@ -383,6 +383,11 @@
}
}
+ bool getIndexedPropertyStorageMayTriggerGC() const
+ {
+ return type() == Array::String;
+ }
+
bool operator==(const ArrayMode& other) const
{
return type() == other.type()
Modified: trunk/Source/_javascript_Core/dfg/DFGCSEPhase.cpp (137246 => 137247)
--- trunk/Source/_javascript_Core/dfg/DFGCSEPhase.cpp 2012-12-11 05:17:49 UTC (rev 137246)
+++ trunk/Source/_javascript_Core/dfg/DFGCSEPhase.cpp 2012-12-11 05:22:49 UTC (rev 137247)
@@ -564,6 +564,11 @@
case ReallocatePropertyStorage:
return NoNode;
+ case GetIndexedPropertyStorage:
+ if (node.arrayMode().getIndexedPropertyStorageMayTriggerGC())
+ return NoNode;
+ break;
+
default:
break;
}
Modified: trunk/Source/_javascript_Core/dfg/DFGOperations.cpp (137246 => 137247)
--- trunk/Source/_javascript_Core/dfg/DFGOperations.cpp 2012-12-11 05:17:49 UTC (rev 137246)
+++ trunk/Source/_javascript_Core/dfg/DFGOperations.cpp 2012-12-11 05:22:49 UTC (rev 137247)
@@ -1460,6 +1460,14 @@
return reinterpret_cast<char*>(object->ensureArrayStorage(globalData));
}
+StringImpl* DFG_OPERATION operationResolveRope(ExecState* exec, JSString* string)
+{
+ JSGlobalData& globalData = exec->globalData();
+ NativeCallFrameTracer tracer(&globalData, exec);
+
+ return string->value(exec).impl();
+}
+
double DFG_OPERATION operationFModOnInts(int32_t a, int32_t b)
{
return fmod(a, b);
Modified: trunk/Source/_javascript_Core/dfg/DFGOperations.h (137246 => 137247)
--- trunk/Source/_javascript_Core/dfg/DFGOperations.h 2012-12-11 05:17:49 UTC (rev 137246)
+++ trunk/Source/_javascript_Core/dfg/DFGOperations.h 2012-12-11 05:22:49 UTC (rev 137247)
@@ -117,6 +117,7 @@
typedef char* DFG_OPERATION (*P_DFGOperation_EStPS)(ExecState*, Structure*, void*, size_t);
typedef char* DFG_OPERATION (*P_DFGOperation_EStSS)(ExecState*, Structure*, size_t, size_t);
typedef char* DFG_OPERATION (*P_DFGOperation_EStZ)(ExecState*, Structure*, int32_t);
+typedef StringImpl* DFG_OPERATION (*Str_DFGOperation_EJss)(ExecState*, JSString*);
// These routines are provide callbacks out to C++ implementations of operations too complex to JIT.
JSCell* DFG_OPERATION operationNewObject(ExecState*, Structure*) WTF_INTERNAL;
@@ -207,6 +208,7 @@
char* DFG_OPERATION operationEnsureContiguous(ExecState*, JSObject*);
char* DFG_OPERATION operationRageEnsureContiguous(ExecState*, JSObject*);
char* DFG_OPERATION operationEnsureArrayStorage(ExecState*, JSObject*);
+StringImpl* DFG_OPERATION operationResolveRope(ExecState*, JSString*);
// This method is used to lookup an exception hander, keyed by faultLocation, which is
// the return location from one of the calls out to one of the helper operations above.
Modified: trunk/Source/_javascript_Core/dfg/DFGSpeculativeJIT.cpp (137246 => 137247)
--- trunk/Source/_javascript_Core/dfg/DFGSpeculativeJIT.cpp 2012-12-11 05:17:49 UTC (rev 137246)
+++ trunk/Source/_javascript_Core/dfg/DFGSpeculativeJIT.cpp 2012-12-11 05:22:49 UTC (rev 137247)
@@ -3365,8 +3365,10 @@
case Array::String:
m_jit.loadPtr(MacroAssembler::Address(baseReg, JSString::offsetOfValue()), storageReg);
- // Speculate that we're not accessing a rope
- speculationCheck(Uncountable, JSValueRegs(), NoNode, m_jit.branchTest32(MacroAssembler::Zero, storageReg));
+ addSlowPathGenerator(
+ slowPathCall(
+ m_jit.branchTest32(MacroAssembler::Zero, storageReg),
+ this, operationResolveRope, storageReg, baseReg));
m_jit.loadPtr(MacroAssembler::Address(storageReg, StringImpl::dataOffset()), storageReg);
break;
Modified: trunk/Source/_javascript_Core/dfg/DFGSpeculativeJIT.h (137246 => 137247)
--- trunk/Source/_javascript_Core/dfg/DFGSpeculativeJIT.h 2012-12-11 05:17:49 UTC (rev 137246)
+++ trunk/Source/_javascript_Core/dfg/DFGSpeculativeJIT.h 2012-12-11 05:22:49 UTC (rev 137247)
@@ -1524,6 +1524,11 @@
m_jit.setupArguments(arg1, arg2);
return appendCallSetResult(operation, result);
}
+ JITCompiler::Call callOperation(Str_DFGOperation_EJss operation, GPRReg result, GPRReg arg1)
+ {
+ m_jit.setupArgumentsWithExecState(arg1);
+ return appendCallWithExceptionCheckSetResult(operation, result);
+ }
#else
// EncodedJSValue in JSVALUE32_64 is a 64-bit integer. When being compiled in ARM EABI, it must be aligned even-numbered register (r0, r2 or [sp]).
@@ -1912,6 +1917,11 @@
m_jit.setupArguments(arg1, arg2);
return appendCallSetResult(operation, result);
}
+ JITCompiler::Call callOperation(Str_DFGOperation_EJss operation, GPRReg result, GPRReg arg1)
+ {
+ m_jit.setupArgumentsWithExecState(arg1);
+ return appendCallWithExceptionCheckSetResult(operation, result);
+ }
#undef EABI_32BIT_DUMMY_ARG