Commit 02039469 authored by oliver@apple.com's avatar oliver@apple.com

fourthTier: DFG tries to ref/deref StringImpls in a ton of places

https://bugs.webkit.org/show_bug.cgi?id=115300

Source/JavaScriptCore:

Reviewed by Geoffrey Garen.

Change any code transitively called from DFG compilation to use StringImpl*
directly instead of String, Identifier, or PropertyName. I use the convention
of passing "StringImpl* uid" instead of an Identifier or PropertyName.

Switch over any code transitively called from DFG compilation to use CStrings
whenever possible for all of its debug dumping.

This makes it possible to compile things without hitting the ref/deref
assertion in StringImpl.

* JavaScriptCore.xcodeproj/project.pbxproj:
* bytecode/CodeBlock.cpp:
(JSC::CodeBlock::inferredName):
(JSC::CodeBlock::sourceCodeForTools):
(JSC::CodeBlock::sourceCodeOnOneLine):
(JSC::constantName):
(JSC::idName):
(JSC::CodeBlock::registerName):
(JSC::regexpToSourceString):
(JSC::regexpName):
(JSC::pointerToSourceString):
(JSC::CodeBlock::printUnaryOp):
(JSC::CodeBlock::printBinaryOp):
(JSC::CodeBlock::printConditionalJump):
(JSC::CodeBlock::printGetByIdOp):
(JSC::dumpStructure):
(JSC::CodeBlock::printCallOp):
(JSC::CodeBlock::printPutByIdOp):
(JSC::CodeBlock::printStructure):
(JSC::CodeBlock::printStructures):
(JSC::CodeBlock::dumpBytecode):
* bytecode/CodeBlock.h:
(CodeBlock):
* bytecode/CodeBlockHash.cpp:
(JSC::CodeBlockHash::CodeBlockHash):
* bytecode/CodeOrigin.cpp:
(JSC::InlineCallFrame::inferredName):
* bytecode/CodeOrigin.h:
(InlineCallFrame):
* bytecode/GetByIdStatus.cpp:
(JSC::GetByIdStatus::computeFromLLInt):
(JSC::GetByIdStatus::computeForChain):
(JSC::GetByIdStatus::computeFor):
* bytecode/GetByIdStatus.h:
(JSC):
(GetByIdStatus):
* bytecode/PutByIdStatus.cpp:
(JSC::PutByIdStatus::computeFromLLInt):
(JSC::PutByIdStatus::computeFor):
* bytecode/PutByIdStatus.h:
(JSC):
(PutByIdStatus):
* bytecode/ReduceWhitespace.cpp:
(JSC::reduceWhitespace):
* bytecode/ReduceWhitespace.h:
(JSC):
* bytecode/ResolveGlobalStatus.cpp:
(JSC::computeForStructure):
(JSC::ResolveGlobalStatus::computeFor):
* bytecode/ResolveGlobalStatus.h:
(JSC):
(ResolveGlobalStatus):
* dfg/DFGAbstractState.cpp:
(JSC::DFG::AbstractState::executeEffects):
* dfg/DFGByteCodeParser.cpp:
(ByteCodeParser):
(JSC::DFG::ByteCodeParser::parseResolveOperations):
(JSC::DFG::ByteCodeParser::parseBlock):
(JSC::DFG::ByteCodeParser::InlineStackEntry::InlineStackEntry):
* dfg/DFGConstantFoldingPhase.cpp:
(JSC::DFG::ConstantFoldingPhase::foldConstants):
* dfg/DFGDesiredIdentifiers.cpp: Added.
(DFG):
(JSC::DFG::DesiredIdentifiers::DesiredIdentifiers):
(JSC::DFG::DesiredIdentifiers::~DesiredIdentifiers):
(JSC::DFG::DesiredIdentifiers::addLazily):
(JSC::DFG::DesiredIdentifiers::reallyAdd):
* dfg/DFGDesiredIdentifiers.h: Added.
(DFG):
(DesiredIdentifiers):
(JSC::DFG::DesiredIdentifiers::numberOfIdentifiers):
(JSC::DFG::DesiredIdentifiers::at):
(JSC::DFG::DesiredIdentifiers::operator[]):
* dfg/DFGFixupPhase.cpp:
(JSC::DFG::FixupPhase::fixupNode):
(JSC::DFG::FixupPhase::isStringPrototypeMethodSane):
(JSC::DFG::FixupPhase::canOptimizeStringObjectAccess):
* dfg/DFGGraph.cpp:
(JSC::DFG::Graph::Graph):
(JSC::DFG::Graph::dump):
* dfg/DFGGraph.h:
(Graph):
* dfg/DFGJITCompiler.cpp:
(JSC::DFG::JITCompiler::link):
* dfg/DFGOperations.cpp:
* dfg/DFGOperations.h:
* dfg/DFGRepatch.cpp:
(JSC::DFG::tryBuildGetByIDList):
* dfg/DFGSpeculativeJIT.h:
(JSC::DFG::SpeculativeJIT::identifierUID):
(JSC::DFG::SpeculativeJIT::callOperation):
* dfg/DFGSpeculativeJIT32_64.cpp:
(JSC::DFG::SpeculativeJIT::cachedGetById):
(JSC::DFG::SpeculativeJIT::cachedPutById):
(JSC::DFG::SpeculativeJIT::compile):
* dfg/DFGSpeculativeJIT64.cpp:
(JSC::DFG::SpeculativeJIT::cachedGetById):
(JSC::DFG::SpeculativeJIT::cachedPutById):
(JSC::DFG::SpeculativeJIT::compile):
* parser/SourceCode.cpp: Added.
(JSC):
(JSC::SourceCode::toUTF8):
* parser/SourceCode.h:
(SourceCode):
* profiler/ProfilerBytecodes.cpp:
(JSC::Profiler::Bytecodes::toJS):
* profiler/ProfilerBytecodes.h:
(JSC::Profiler::Bytecodes::inferredName):
(JSC::Profiler::Bytecodes::sourceCode):
(Bytecodes):
* runtime/Identifier.h:
(JSC::Identifier::utf8):
(JSC):
* runtime/Structure.cpp:
(JSC::Structure::addPropertyTransitionToExistingStructureImpl):
(JSC::Structure::addPropertyTransitionToExistingStructure):
(JSC::Structure::addPropertyTransitionToExistingStructureConcurrently):
(JSC::Structure::getConcurrently):
(JSC::Structure::prototypeChainMayInterceptStoreTo):
(JSC):
* runtime/Structure.h:
(Structure):
* runtime/StructureInlines.h:
(JSC::Structure::getConcurrently):

Source/WTF:

Reviewed by Geoffrey Garen.

Make it possible to do more things directly to StringImpl*'s, including being
able to directly do utf8 conversion on a substring without creating the
substring first.

Add assertions to StringImpl that it isn't being ref/deref'd from the
compilation thread.

* wtf/PrintStream.cpp:
(WTF::printInternal):
(WTF):
* wtf/PrintStream.h:
(WTF):
(WTF::printInternal):
* wtf/StringPrintStream.h:
(WTF):
(WTF::toCString):
* wtf/text/StringImpl.cpp:
(WTF::StringImpl::utf8ForRange):
(WTF::StringImpl::utf8):
(WTF):
* wtf/text/StringImpl.h:
(StringImpl):
(WTF::StringImpl::hasAtLeastOneRef):
(WTF::StringImpl::ref):
(WTF::StringImpl::deref):

git-svn-id: http://svn.webkit.org/repository/webkit/trunk@153142 268f45cc-cd09-0410-ab3c-d52691b4dbfc
parent 36e01a77
2013-05-02 Filip Pizlo <fpizlo@apple.com>
fourthTier: DFG tries to ref/deref StringImpls in a ton of places
https://bugs.webkit.org/show_bug.cgi?id=115300
Reviewed by Geoffrey Garen.
Change any code transitively called from DFG compilation to use StringImpl*
directly instead of String, Identifier, or PropertyName. I use the convention
of passing "StringImpl* uid" instead of an Identifier or PropertyName.
Switch over any code transitively called from DFG compilation to use CStrings
whenever possible for all of its debug dumping.
This makes it possible to compile things without hitting the ref/deref
assertion in StringImpl.
* JavaScriptCore.xcodeproj/project.pbxproj:
* bytecode/CodeBlock.cpp:
(JSC::CodeBlock::inferredName):
(JSC::CodeBlock::sourceCodeForTools):
(JSC::CodeBlock::sourceCodeOnOneLine):
(JSC::constantName):
(JSC::idName):
(JSC::CodeBlock::registerName):
(JSC::regexpToSourceString):
(JSC::regexpName):
(JSC::pointerToSourceString):
(JSC::CodeBlock::printUnaryOp):
(JSC::CodeBlock::printBinaryOp):
(JSC::CodeBlock::printConditionalJump):
(JSC::CodeBlock::printGetByIdOp):
(JSC::dumpStructure):
(JSC::CodeBlock::printCallOp):
(JSC::CodeBlock::printPutByIdOp):
(JSC::CodeBlock::printStructure):
(JSC::CodeBlock::printStructures):
(JSC::CodeBlock::dumpBytecode):
* bytecode/CodeBlock.h:
(CodeBlock):
* bytecode/CodeBlockHash.cpp:
(JSC::CodeBlockHash::CodeBlockHash):
* bytecode/CodeOrigin.cpp:
(JSC::InlineCallFrame::inferredName):
* bytecode/CodeOrigin.h:
(InlineCallFrame):
* bytecode/GetByIdStatus.cpp:
(JSC::GetByIdStatus::computeFromLLInt):
(JSC::GetByIdStatus::computeForChain):
(JSC::GetByIdStatus::computeFor):
* bytecode/GetByIdStatus.h:
(JSC):
(GetByIdStatus):
* bytecode/PutByIdStatus.cpp:
(JSC::PutByIdStatus::computeFromLLInt):
(JSC::PutByIdStatus::computeFor):
* bytecode/PutByIdStatus.h:
(JSC):
(PutByIdStatus):
* bytecode/ReduceWhitespace.cpp:
(JSC::reduceWhitespace):
* bytecode/ReduceWhitespace.h:
(JSC):
* bytecode/ResolveGlobalStatus.cpp:
(JSC::computeForStructure):
(JSC::ResolveGlobalStatus::computeFor):
* bytecode/ResolveGlobalStatus.h:
(JSC):
(ResolveGlobalStatus):
* dfg/DFGAbstractState.cpp:
(JSC::DFG::AbstractState::executeEffects):
* dfg/DFGByteCodeParser.cpp:
(ByteCodeParser):
(JSC::DFG::ByteCodeParser::parseResolveOperations):
(JSC::DFG::ByteCodeParser::parseBlock):
(JSC::DFG::ByteCodeParser::InlineStackEntry::InlineStackEntry):
* dfg/DFGConstantFoldingPhase.cpp:
(JSC::DFG::ConstantFoldingPhase::foldConstants):
* dfg/DFGDesiredIdentifiers.cpp: Added.
(DFG):
(JSC::DFG::DesiredIdentifiers::DesiredIdentifiers):
(JSC::DFG::DesiredIdentifiers::~DesiredIdentifiers):
(JSC::DFG::DesiredIdentifiers::addLazily):
(JSC::DFG::DesiredIdentifiers::reallyAdd):
* dfg/DFGDesiredIdentifiers.h: Added.
(DFG):
(DesiredIdentifiers):
(JSC::DFG::DesiredIdentifiers::numberOfIdentifiers):
(JSC::DFG::DesiredIdentifiers::at):
(JSC::DFG::DesiredIdentifiers::operator[]):
* dfg/DFGFixupPhase.cpp:
(JSC::DFG::FixupPhase::fixupNode):
(JSC::DFG::FixupPhase::isStringPrototypeMethodSane):
(JSC::DFG::FixupPhase::canOptimizeStringObjectAccess):
* dfg/DFGGraph.cpp:
(JSC::DFG::Graph::Graph):
(JSC::DFG::Graph::dump):
* dfg/DFGGraph.h:
(Graph):
* dfg/DFGJITCompiler.cpp:
(JSC::DFG::JITCompiler::link):
* dfg/DFGOperations.cpp:
* dfg/DFGOperations.h:
* dfg/DFGRepatch.cpp:
(JSC::DFG::tryBuildGetByIDList):
* dfg/DFGSpeculativeJIT.h:
(JSC::DFG::SpeculativeJIT::identifierUID):
(JSC::DFG::SpeculativeJIT::callOperation):
* dfg/DFGSpeculativeJIT32_64.cpp:
(JSC::DFG::SpeculativeJIT::cachedGetById):
(JSC::DFG::SpeculativeJIT::cachedPutById):
(JSC::DFG::SpeculativeJIT::compile):
* dfg/DFGSpeculativeJIT64.cpp:
(JSC::DFG::SpeculativeJIT::cachedGetById):
(JSC::DFG::SpeculativeJIT::cachedPutById):
(JSC::DFG::SpeculativeJIT::compile):
* parser/SourceCode.cpp: Added.
(JSC):
(JSC::SourceCode::toUTF8):
* parser/SourceCode.h:
(SourceCode):
* profiler/ProfilerBytecodes.cpp:
(JSC::Profiler::Bytecodes::toJS):
* profiler/ProfilerBytecodes.h:
(JSC::Profiler::Bytecodes::inferredName):
(JSC::Profiler::Bytecodes::sourceCode):
(Bytecodes):
* runtime/Identifier.h:
(JSC::Identifier::utf8):
(JSC):
* runtime/Structure.cpp:
(JSC::Structure::addPropertyTransitionToExistingStructureImpl):
(JSC::Structure::addPropertyTransitionToExistingStructure):
(JSC::Structure::addPropertyTransitionToExistingStructureConcurrently):
(JSC::Structure::getConcurrently):
(JSC::Structure::prototypeChainMayInterceptStoreTo):
(JSC):
* runtime/Structure.h:
(Structure):
* runtime/StructureInlines.h:
(JSC::Structure::getConcurrently):
2013-05-02 Filip Pizlo <fpizlo@apple.com>
fourthTier: Structure transition table keys don't have to ref their StringImpl's
......
......@@ -220,6 +220,9 @@
0F8364B7164B0C110053329A /* DFGBranchDirection.h in Headers */ = {isa = PBXBuildFile; fileRef = 0F8364B5164B0C0E0053329A /* DFGBranchDirection.h */; settings = {ATTRIBUTES = (Private, ); }; };
0F8F2B95172E04A0007DBDA5 /* FTLLink.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 0F8F2B93172E049E007DBDA5 /* FTLLink.cpp */; };
0F8F2B96172E04A3007DBDA5 /* FTLLink.h in Headers */ = {isa = PBXBuildFile; fileRef = 0F8F2B94172E049E007DBDA5 /* FTLLink.h */; settings = {ATTRIBUTES = (Private, ); }; };
0F8F2B99172F04FF007DBDA5 /* DFGDesiredIdentifiers.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 0F8F2B97172F04FD007DBDA5 /* DFGDesiredIdentifiers.cpp */; };
0F8F2B9A172F0501007DBDA5 /* DFGDesiredIdentifiers.h in Headers */ = {isa = PBXBuildFile; fileRef = 0F8F2B98172F04FD007DBDA5 /* DFGDesiredIdentifiers.h */; settings = {ATTRIBUTES = (Private, ); }; };
0F8F2B9E17306C8D007DBDA5 /* SourceCode.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 0F8F2B9D17306C8B007DBDA5 /* SourceCode.cpp */; };
0F8F943C1667631300D61971 /* CodeSpecializationKind.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 0F8F943A1667631100D61971 /* CodeSpecializationKind.cpp */; };
0F8F94401667633000D61971 /* CodeBlockHash.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 0F8F943D1667632D00D61971 /* CodeBlockHash.cpp */; };
0F8F94411667633200D61971 /* CodeBlockHash.h in Headers */ = {isa = PBXBuildFile; fileRef = 0F8F943E1667632D00D61971 /* CodeBlockHash.h */; settings = {ATTRIBUTES = (Private, ); }; };
......@@ -1196,6 +1199,9 @@
0F85A31E16AB76AE0077571E /* DFGVariadicFunction.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = DFGVariadicFunction.h; path = dfg/DFGVariadicFunction.h; sourceTree = "<group>"; };
0F8F2B93172E049E007DBDA5 /* FTLLink.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = FTLLink.cpp; path = ftl/FTLLink.cpp; sourceTree = "<group>"; };
0F8F2B94172E049E007DBDA5 /* FTLLink.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = FTLLink.h; path = ftl/FTLLink.h; sourceTree = "<group>"; };
0F8F2B97172F04FD007DBDA5 /* DFGDesiredIdentifiers.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = DFGDesiredIdentifiers.cpp; path = dfg/DFGDesiredIdentifiers.cpp; sourceTree = "<group>"; };
0F8F2B98172F04FD007DBDA5 /* DFGDesiredIdentifiers.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = DFGDesiredIdentifiers.h; path = dfg/DFGDesiredIdentifiers.h; sourceTree = "<group>"; };
0F8F2B9D17306C8B007DBDA5 /* SourceCode.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = SourceCode.cpp; sourceTree = "<group>"; };
0F8F943A1667631100D61971 /* CodeSpecializationKind.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = CodeSpecializationKind.cpp; sourceTree = "<group>"; };
0F8F943D1667632D00D61971 /* CodeBlockHash.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = CodeBlockHash.cpp; sourceTree = "<group>"; };
0F8F943E1667632D00D61971 /* CodeBlockHash.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = CodeBlockHash.h; sourceTree = "<group>"; };
......@@ -2559,6 +2565,7 @@
A77F18241641925400640A47 /* ParserModes.h */,
65303D631447B9E100D3F904 /* ParserTokens.h */,
869EBCB60E8C6D4A008722CC /* ResultType.h */,
0F8F2B9D17306C8B007DBDA5 /* SourceCode.cpp */,
65E866EE0DD59AFA00A2B2A1 /* SourceCode.h */,
0F493AF816D0CAD10084508B /* SourceProvider.cpp */,
65E866ED0DD59AFA00A2B2A1 /* SourceProvider.h */,
......@@ -2894,6 +2901,8 @@
0FFFC94E14EF909500C72532 /* DFGCSEPhase.h */,
0F2FC77016E12F6F0038D976 /* DFGDCEPhase.cpp */,
0F2FC77116E12F6F0038D976 /* DFGDCEPhase.h */,
0F8F2B97172F04FD007DBDA5 /* DFGDesiredIdentifiers.cpp */,
0F8F2B98172F04FD007DBDA5 /* DFGDesiredIdentifiers.h */,
0FE853491723CDA500B618F5 /* DFGDesiredWatchpoints.cpp */,
0FE8534A1723CDA500B618F5 /* DFGDesiredWatchpoints.h */,
0FF427611591A1C9004CB9FF /* DFGDisassembler.cpp */,
......@@ -3479,6 +3488,7 @@
86E3C612167BABD7006D760A /* JSValue.h in Headers */,
86E3C61B167BABEE006D760A /* JSValueInternal.h in Headers */,
BC18C42C0E16F5CD00B34460 /* JSValueRef.h in Headers */,
0F8F2B9A172F0501007DBDA5 /* DFGDesiredIdentifiers.h in Headers */,
BC18C42D0E16F5CD00B34460 /* JSVariableObject.h in Headers */,
86E3C615167BABD7006D760A /* JSVirtualMachine.h in Headers */,
86E3C61D167BABEE006D760A /* JSVirtualMachineInternal.h in Headers */,
......@@ -4123,6 +4133,7 @@
86EC9DD21328DF82002B2AD7 /* DFGSpeculativeJIT.cpp in Sources */,
86880F1F14328BB900B08D42 /* DFGSpeculativeJIT32_64.cpp in Sources */,
86880F4D14353B2100B08D42 /* DFGSpeculativeJIT64.cpp in Sources */,
0F8F2B9E17306C8D007DBDA5 /* SourceCode.cpp in Sources */,
0FC097A1146B28CA00CF2442 /* DFGThunks.cpp in Sources */,
0F63944015C75F1D006A597C /* DFGTypeCheckHoistingPhase.cpp in Sources */,
0FBE0F7616C1DB0F0082C5E8 /* DFGUnificationPhase.cpp in Sources */,
......@@ -4346,6 +4357,7 @@
BCCF0D0C0EF0B8A500413C8F /* StructureStubInfo.cpp in Sources */,
C2DF442F1707AC0100A5CA96 /* SuperRegion.cpp in Sources */,
0F919D2815856773004A4E7D /* SymbolTable.cpp in Sources */,
0F8F2B99172F04FF007DBDA5 /* DFGDesiredIdentifiers.cpp in Sources */,
A7386555118697B400540279 /* ThunkGenerators.cpp in Sources */,
0FF4274A158EBE91004CB9FF /* udis86.c in Sources */,
0FF42740158EBE8B004CB9FF /* udis86_decode.c in Sources */,
......
......@@ -109,10 +109,10 @@ namespace JSC {
UnlinkedCodeBlock* unlinkedCodeBlock() const { return m_unlinkedCode.get(); }
String inferredName() const;
CString inferredName() const;
CodeBlockHash hash() const;
String sourceCodeForTools() const; // Not quite the actual source we parsed; this will do things like prefix the source for a function with a reified signature.
String sourceCodeOnOneLine() const; // As sourceCodeForTools(), but replaces all whitespace runs with a single space.
CString sourceCodeForTools() const; // Not quite the actual source we parsed; this will do things like prefix the source for a function with a reified signature.
CString sourceCodeOnOneLine() const; // As sourceCodeForTools(), but replaces all whitespace runs with a single space.
void dumpAssumingJITType(PrintStream&, JITCode::JITType) const;
void dump(PrintStream&) const;
......@@ -983,7 +983,7 @@ namespace JSC {
void dumpBytecode(PrintStream&, ExecState*, const Instruction* begin, const Instruction*&);
CString registerName(ExecState*, int r) const;
CString registerName(int r) const;
void printUnaryOp(PrintStream&, ExecState*, int location, const Instruction*&, const char* op);
void printBinaryOp(PrintStream&, ExecState*, int location, const Instruction*&, const char* op);
void printConditionalJump(PrintStream&, ExecState*, const Instruction*, const Instruction*&, int location, const char* op);
......
......@@ -58,7 +58,7 @@ CodeBlockHash::CodeBlockHash(const SourceCode& sourceCode, CodeSpecializationKin
: m_hash(0)
{
SHA1 sha1;
sha1.addBytes(sourceCode.toString().utf8());
sha1.addBytes(sourceCode.toUTF8());
Vector<uint8_t, 20> digest;
sha1.computeHash(digest);
m_hash += digest[0] | (digest[1] << 8) | (digest[2] << 16) | (digest[3] << 24);
......
......@@ -87,9 +87,9 @@ CodeBlockHash InlineCallFrame::hash() const
return executable->hashFor(specializationKind());
}
String InlineCallFrame::inferredName() const
CString InlineCallFrame::inferredName() const
{
return jsCast<FunctionExecutable*>(executable.get())->inferredName().string();
return jsCast<FunctionExecutable*>(executable.get())->inferredName().utf8();
}
CodeBlock* InlineCallFrame::baselineCodeBlock() const
......
......@@ -114,7 +114,7 @@ struct InlineCallFrame {
// Get the callee given a machine call frame to which this InlineCallFrame belongs.
JSFunction* calleeForCallFrame(ExecState*) const;
String inferredName() const;
CString inferredName() const;
CodeBlockHash hash() const;
CodeBlock* baselineCodeBlock() const;
......
......@@ -34,11 +34,11 @@
namespace JSC {
GetByIdStatus GetByIdStatus::computeFromLLInt(CodeBlock* profiledBlock, unsigned bytecodeIndex, Identifier& ident)
GetByIdStatus GetByIdStatus::computeFromLLInt(CodeBlock* profiledBlock, unsigned bytecodeIndex, StringImpl* uid)
{
UNUSED_PARAM(profiledBlock);
UNUSED_PARAM(bytecodeIndex);
UNUSED_PARAM(ident);
UNUSED_PARAM(uid);
#if ENABLE(LLINT)
Instruction* instruction = profiledBlock->instructions().begin() + bytecodeIndex;
......@@ -52,7 +52,7 @@ GetByIdStatus GetByIdStatus::computeFromLLInt(CodeBlock* profiledBlock, unsigned
unsigned attributesIgnored;
JSCell* specificValue;
PropertyOffset offset = structure->getConcurrently(
*profiledBlock->vm(), ident, attributesIgnored, specificValue);
*profiledBlock->vm(), uid, attributesIgnored, specificValue);
if (structure->isDictionary())
specificValue = 0;
if (!isValidOffset(offset))
......@@ -64,7 +64,7 @@ GetByIdStatus GetByIdStatus::computeFromLLInt(CodeBlock* profiledBlock, unsigned
#endif
}
void GetByIdStatus::computeForChain(GetByIdStatus& result, CodeBlock* profiledBlock, Identifier& ident, Structure* structure)
void GetByIdStatus::computeForChain(GetByIdStatus& result, CodeBlock* profiledBlock, StringImpl* uid, Structure* structure)
{
#if ENABLE(JIT) && ENABLE(VALUE_PROFILER)
// Validate the chain. If the chain is invalid, then currently the best thing
......@@ -93,7 +93,7 @@ void GetByIdStatus::computeForChain(GetByIdStatus& result, CodeBlock* profiledBl
JSCell* specificValue;
result.m_offset = currentStructure->getConcurrently(
*profiledBlock->vm(), ident, attributesIgnored, specificValue);
*profiledBlock->vm(), uid, attributesIgnored, specificValue);
if (currentStructure->isDictionary())
specificValue = 0;
if (!isValidOffset(result.m_offset))
......@@ -104,28 +104,28 @@ void GetByIdStatus::computeForChain(GetByIdStatus& result, CodeBlock* profiledBl
#else
UNUSED_PARAM(result);
UNUSED_PARAM(profiledBlock);
UNUSED_PARAM(ident);
UNUSED_PARAM(uid);
UNUSED_PARAM(structure);
UNREACHABLE_FOR_PLATFORM();
#endif
}
GetByIdStatus GetByIdStatus::computeFor(CodeBlock* profiledBlock, unsigned bytecodeIndex, Identifier& ident)
GetByIdStatus GetByIdStatus::computeFor(CodeBlock* profiledBlock, unsigned bytecodeIndex, StringImpl* uid)
{
CodeBlockLocker locker(profiledBlock->m_lock);
UNUSED_PARAM(profiledBlock);
UNUSED_PARAM(bytecodeIndex);
UNUSED_PARAM(ident);
UNUSED_PARAM(uid);
#if ENABLE(JIT) && ENABLE(VALUE_PROFILER)
if (!profiledBlock->numberOfStructureStubInfos())
return computeFromLLInt(profiledBlock, bytecodeIndex, ident);
return computeFromLLInt(profiledBlock, bytecodeIndex, uid);
// First check if it makes either calls, in which case we want to be super careful, or
// if it's not set at all, in which case we punt.
StructureStubInfo& stubInfo = profiledBlock->getStubInfo(bytecodeIndex);
if (!stubInfo.seen)
return computeFromLLInt(profiledBlock, bytecodeIndex, ident);
return computeFromLLInt(profiledBlock, bytecodeIndex, uid);
if (stubInfo.resetByGC)
return GetByIdStatus(TakesSlowPath, true);
......@@ -160,14 +160,14 @@ GetByIdStatus GetByIdStatus::computeFor(CodeBlock* profiledBlock, unsigned bytec
result.m_wasSeenInJIT = true; // This is interesting for bytecode dumping only.
switch (stubInfo.accessType) {
case access_unset:
return computeFromLLInt(profiledBlock, bytecodeIndex, ident);
return computeFromLLInt(profiledBlock, bytecodeIndex, uid);
case access_get_by_id_self: {
Structure* structure = stubInfo.u.getByIdSelf.baseObjectStructure.get();
unsigned attributesIgnored;
JSCell* specificValue;
result.m_offset = structure->getConcurrently(
*profiledBlock->vm(), ident, attributesIgnored, specificValue);
*profiledBlock->vm(), uid, attributesIgnored, specificValue);
if (structure->isDictionary())
specificValue = 0;
......@@ -192,7 +192,7 @@ GetByIdStatus GetByIdStatus::computeFor(CodeBlock* profiledBlock, unsigned bytec
unsigned attributesIgnored;
JSCell* specificValue;
PropertyOffset myOffset = structure->getConcurrently(
*profiledBlock->vm(), ident, attributesIgnored, specificValue);
*profiledBlock->vm(), uid, attributesIgnored, specificValue);
if (structure->isDictionary())
specificValue = 0;
......@@ -223,7 +223,7 @@ GetByIdStatus GetByIdStatus::computeFor(CodeBlock* profiledBlock, unsigned bytec
return GetByIdStatus(MakesCalls, true);
result.m_chain.append(stubInfo.u.getByIdProto.prototypeStructure.get());
computeForChain(
result, profiledBlock, ident,
result, profiledBlock, uid,
stubInfo.u.getByIdProto.baseObjectStructure.get());
break;
}
......@@ -234,7 +234,7 @@ GetByIdStatus GetByIdStatus::computeFor(CodeBlock* profiledBlock, unsigned bytec
for (unsigned i = 0; i < stubInfo.u.getByIdChain.count; ++i)
result.m_chain.append(stubInfo.u.getByIdChain.chain->head()[i].get());
computeForChain(
result, profiledBlock, ident,
result, profiledBlock, uid,
stubInfo.u.getByIdChain.baseObjectStructure.get());
break;
}
......@@ -258,12 +258,12 @@ GetByIdStatus GetByIdStatus::computeFor(CodeBlock* profiledBlock, unsigned bytec
#endif // ENABLE(JIT)
}
GetByIdStatus GetByIdStatus::computeFor(VM& vm, Structure* structure, Identifier& ident)
GetByIdStatus GetByIdStatus::computeFor(VM& vm, Structure* structure, StringImpl* uid)
{
// For now we only handle the super simple self access case. We could handle the
// prototype case in the future.
if (PropertyName(ident).asIndex() != PropertyName::NotAnIndex)
if (toUInt32FromStringImpl(uid) != PropertyName::NotAnIndex)
return GetByIdStatus(TakesSlowPath);
if (structure->typeInfo().overridesGetOwnPropertySlot())
......@@ -273,10 +273,10 @@ GetByIdStatus GetByIdStatus::computeFor(VM& vm, Structure* structure, Identifier
return GetByIdStatus(TakesSlowPath);
GetByIdStatus result;
result.m_wasSeenInJIT = false; // To my knowledge nobody that uses computeFor(VM&, Structure*, Identifier&) reads this field, but I might as well be honest: no, it wasn't seen in the JIT, since I computed it statically.
result.m_wasSeenInJIT = false; // To my knowledge nobody that uses computeFor(VM&, Structure*, StringImpl*) reads this field, but I might as well be honest: no, it wasn't seen in the JIT, since I computed it statically.
unsigned attributes;
JSCell* specificValue;
result.m_offset = structure->getConcurrently(vm, ident, attributes, specificValue);
result.m_offset = structure->getConcurrently(vm, uid, attributes, specificValue);
if (!isValidOffset(result.m_offset))
return GetByIdStatus(TakesSlowPath); // It's probably a prototype lookup. Give up on life for now, even though we could totally be way smarter about it.
if (attributes & Accessor)
......
/*
* Copyright (C) 2012 Apple Inc. All rights reserved.
* Copyright (C) 2012, 2013 Apple Inc. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
......@@ -33,7 +33,6 @@
namespace JSC {
class CodeBlock;
class Identifier;
class GetByIdStatus {
public:
......@@ -71,8 +70,8 @@ public:
ASSERT((state == Simple) == (offset != invalidOffset));
}
static GetByIdStatus computeFor(CodeBlock*, unsigned bytecodeIndex, Identifier&);
static GetByIdStatus computeFor(VM&, Structure*, Identifier&);
static GetByIdStatus computeFor(CodeBlock*, unsigned bytecodeIndex, StringImpl* uid);
static GetByIdStatus computeFor(VM&, Structure*, StringImpl* uid);
State state() const { return m_state; }
......@@ -90,8 +89,8 @@ public:
bool wasSeenInJIT() const { return m_wasSeenInJIT; }
private:
static void computeForChain(GetByIdStatus& result, CodeBlock*, Identifier&, Structure*);
static GetByIdStatus computeFromLLInt(CodeBlock*, unsigned bytecodeIndex, Identifier&);
static void computeForChain(GetByIdStatus& result, CodeBlock*, StringImpl* uid, Structure*);
static GetByIdStatus computeFromLLInt(CodeBlock*, unsigned bytecodeIndex, StringImpl* uid);
State m_state;
StructureSet m_structureSet;
......
......@@ -35,11 +35,11 @@
namespace JSC {
PutByIdStatus PutByIdStatus::computeFromLLInt(CodeBlock* profiledBlock, unsigned bytecodeIndex, Identifier& ident)
PutByIdStatus PutByIdStatus::computeFromLLInt(CodeBlock* profiledBlock, unsigned bytecodeIndex, StringImpl* uid)
{
UNUSED_PARAM(profiledBlock);
UNUSED_PARAM(bytecodeIndex);
UNUSED_PARAM(ident);
UNUSED_PARAM(uid);
#if ENABLE(LLINT)
Instruction* instruction = profiledBlock->instructions().begin() + bytecodeIndex;
......@@ -49,7 +49,7 @@ PutByIdStatus PutByIdStatus::computeFromLLInt(CodeBlock* profiledBlock, unsigned
if (instruction[0].u.opcode == LLInt::getOpcode(llint_op_put_by_id)
|| instruction[0].u.opcode == LLInt::getOpcode(llint_op_put_by_id_out_of_line)) {
PropertyOffset offset = structure->getConcurrently(*profiledBlock->vm(), ident);
PropertyOffset offset = structure->getConcurrently(*profiledBlock->vm(), uid);
if (!isValidOffset(offset))
return PutByIdStatus(NoInformation, 0, 0, 0, invalidOffset);
......@@ -68,7 +68,7 @@ PutByIdStatus PutByIdStatus::computeFromLLInt(CodeBlock* profiledBlock, unsigned
ASSERT(newStructure);
ASSERT(chain);
PropertyOffset offset = newStructure->getConcurrently(*profiledBlock->vm(), ident);
PropertyOffset offset = newStructure->getConcurrently(*profiledBlock->vm(), uid);
if (!isValidOffset(offset))
return PutByIdStatus(NoInformation, 0, 0, 0, invalidOffset);
......@@ -78,23 +78,23 @@ PutByIdStatus PutByIdStatus::computeFromLLInt(CodeBlock* profiledBlock, unsigned
#endif
}
PutByIdStatus PutByIdStatus::computeFor(CodeBlock* profiledBlock, unsigned bytecodeIndex, Identifier& ident)
PutByIdStatus PutByIdStatus::computeFor(CodeBlock* profiledBlock, unsigned bytecodeIndex, StringImpl* uid)
{
CodeBlockLocker locker(profiledBlock->m_lock);
UNUSED_PARAM(profiledBlock);
UNUSED_PARAM(bytecodeIndex);
UNUSED_PARAM(ident);
UNUSED_PARAM(uid);
#if ENABLE(JIT) && ENABLE(VALUE_PROFILER)
if (!profiledBlock->numberOfStructureStubInfos())
return computeFromLLInt(profiledBlock, bytecodeIndex, ident);
return computeFromLLInt(profiledBlock, bytecodeIndex, uid);
if (profiledBlock->likelyToTakeSlowCase(bytecodeIndex))
return PutByIdStatus(TakesSlowPath, 0, 0, 0, invalidOffset);
StructureStubInfo& stubInfo = profiledBlock->getStubInfo(bytecodeIndex);
if (!stubInfo.seen)
return computeFromLLInt(profiledBlock, bytecodeIndex, ident);
return computeFromLLInt(profiledBlock, bytecodeIndex, uid);
if (stubInfo.resetByGC)
return PutByIdStatus(TakesSlowPath, 0, 0, 0, invalidOffset);
......@@ -107,7 +107,7 @@ PutByIdStatus PutByIdStatus::computeFor(CodeBlock* profiledBlock, unsigned bytec
case access_put_by_id_replace: {
PropertyOffset offset =
stubInfo.u.putByIdReplace.baseObjectStructure->getConcurrently(
*profiledBlock->vm(), ident);
*profiledBlock->vm(), uid);
if (isValidOffset(offset)) {
return PutByIdStatus(
SimpleReplace,
......@@ -123,7 +123,7 @@ PutByIdStatus PutByIdStatus::computeFor(CodeBlock* profiledBlock, unsigned bytec
ASSERT(stubInfo.u.putByIdTransition.previousStructure->transitionWatchpointSetHasBeenInvalidated());
PropertyOffset offset =
stubInfo.u.putByIdTransition.structure->getConcurrently(
*profiledBlock->vm(), ident);
*profiledBlock->vm(), uid);
if (isValidOffset(offset)) {
return PutByIdStatus(
SimpleTransition,
......@@ -143,9 +143,9 @@ PutByIdStatus PutByIdStatus::computeFor(CodeBlock* profiledBlock, unsigned bytec
#endif // ENABLE(JIT)
}
PutByIdStatus PutByIdStatus::computeFor(VM& vm, JSGlobalObject* globalObject, Structure* structure, Identifier& ident, bool isDirect)
PutByIdStatus PutByIdStatus::computeFor(VM& vm, JSGlobalObject* globalObject, Structure* structure, StringImpl* uid, bool isDirect)
{
if (PropertyName(ident).asIndex() != PropertyName::NotAnIndex)
if (toUInt32FromStringImpl(uid) != PropertyName::NotAnIndex)
return PutByIdStatus(TakesSlowPath);
if (structure->typeInfo().overridesGetOwnPropertySlot())
......@@ -157,7 +157,7 @@ PutByIdStatus PutByIdStatus::computeFor(VM& vm, JSGlobalObject* globalObject, St
unsigned attributes;
JSCell* specificValue;
PropertyOffset offset = structure->getConcurrently(
vm, ident, attributes, specificValue);
vm, uid, attributes, specificValue);
if (isValidOffset(offset)) {
if (attributes & (Accessor | ReadOnly))
return PutByIdStatus(TakesSlowPath);
......@@ -183,7 +183,7 @@ PutByIdStatus PutByIdStatus::computeFor(VM& vm, JSGlobalObject* globalObject, St
if (!isDirect) {
// If the prototype chain has setters or read-only properties, then give up.
if (structure->prototypeChainMayInterceptStoreTo(vm, ident))
if (structure->prototypeChainMayInterceptStoreTo(vm, uid))
return PutByIdStatus(TakesSlowPath);
// If the prototype chain hasn't been normalized (i.e. there are proxies or dictionaries)
......@@ -210,7 +210,7 @@ PutByIdStatus PutByIdStatus::computeFor(VM& vm, JSGlobalObject* globalObject, St
// - If we're not storing a value that could be specific: again, this would only be a
// problem if the existing transition did have a specific value, which we check for
// by passing 0 for the specificValue.
Structure* transition = Structure::addPropertyTransitionToExistingStructureConcurrently(structure, ident, 0, 0, offset);
Structure* transition = Structure::addPropertyTransitionToExistingStructureConcurrently(structure, uid, 0, 0, offset);
if (!transition)
return PutByIdStatus(TakesSlowPath); // This occurs in bizarre cases only. See above.
ASSERT(!transition->transitionDidInvolveSpecificValue());
......
/*
* Copyright (C) 2012 Apple Inc. All rights reserved.
* Copyright (C) 2012, 2013 Apple Inc. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
......@@ -28,11 +28,11 @@
#include "PropertyOffset.h"
#include <wtf/NotFound.h>
#include <wtf/text/StringImpl.h>
namespace JSC {
class CodeBlock;
class Identifier;
class VM;
class JSGlobalObject;
class Structure;
......@@ -90,8 +90,8 @@ public:
ASSERT((m_state == NoInformation || m_state == TakesSlowPath) == (m_offset == invalidOffset));
}
static PutByIdStatus computeFor(CodeBlock*, unsigned bytecodeIndex, Identifier&);
static PutByIdStatus computeFor(VM&, JSGlobalObject*, Structure*, Identifier&, bool isDirect);
static PutByIdStatus computeFor(CodeBlock*, unsigned bytecodeIndex, StringImpl* uid);
static PutByIdStatus computeFor(VM&, JSGlobalObject*, Structure*, StringImpl* uid, bool isDirect);
State state() const { return m_state; }
......@@ -107,7 +107,7 @@ public:
PropertyOffset offset() const { return m_offset; }
private:
static PutByIdStatus computeFromLLInt(CodeBlock*, unsigned bytecodeIndex, Identifier&);
static PutByIdStatus computeFromLLInt(CodeBlock*, unsigned bytecodeIndex, StringImpl* uid);
State m_state;
Structure* m_oldStructure;
......
/*
* Copyright (C) 2012 Apple Inc. All rights reserved.
* Copyright (C) 2012, 2013 Apple Inc. All rights reserved.
*