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

2011-04-01 Oliver Hunt <oliver@apple.com>

        Reviewed by Geoffrey Garen.

        Make StructureChain GC allocated
        https://bugs.webkit.org/show_bug.cgi?id=56695

        Make StructureChain GC allocated, and make the various owners
        mark it correctly.

        * JavaScriptCore.exp:
        * bytecode/CodeBlock.cpp:
        (JSC::CodeBlock::dump):
        (JSC::CodeBlock::derefStructures):
        (JSC::CodeBlock::refStructures):
        (JSC::CodeBlock::markAggregate):
        * bytecode/Instruction.h:
        (JSC::PolymorphicAccessStructureList::PolymorphicStubInfo::set):
        (JSC::PolymorphicAccessStructureList::PolymorphicAccessStructureList):
        (JSC::PolymorphicAccessStructureList::derefStructures):
        (JSC::PolymorphicAccessStructureList::markAggregate):
        (JSC::Instruction::Instruction):
        * bytecode/StructureStubInfo.cpp:
        (JSC::StructureStubInfo::deref):
        (JSC::StructureStubInfo::markAggregate):
        * bytecode/StructureStubInfo.h:
        (JSC::StructureStubInfo::initGetByIdChain):
        (JSC::StructureStubInfo::initPutByIdTransition):
        * bytecompiler/BytecodeGenerator.cpp:
        (JSC::BytecodeGenerator::emitJumpIfNotFunctionCall):
        (JSC::BytecodeGenerator::emitJumpIfNotFunctionApply):
        * collector/handles/Handle.h:
        (JSC::HandleConverter::operator->):
        (JSC::HandleConverter::operator*):
        * interpreter/Interpreter.cpp:
        (JSC::Interpreter::privateExecute):
        * jit/JITOpcodes.cpp:
        (JSC::JIT::emit_op_jneq_ptr):
        * jit/JITOpcodes32_64.cpp:
        (JSC::JIT::emit_op_jneq_ptr):
        * jit/JITPropertyAccess.cpp:
        (JSC::JIT::privateCompileGetByIdChainList):
        * jit/JITPropertyAccess32_64.cpp:
        (JSC::JIT::privateCompileGetByIdChainList):
        * jit/JITStubs.cpp:
        (JSC::JITThunks::tryCachePutByID):
        (JSC::JITThunks::tryCacheGetByID):
        (JSC::getPolymorphicAccessStructureListSlot):
        (JSC::DEFINE_STUB_FUNCTION):
        * runtime/JSCell.h:
        * runtime/JSGlobalData.cpp:
        (JSC::JSGlobalData::JSGlobalData):
        * runtime/JSGlobalData.h:
        * runtime/JSGlobalObject.cpp:
        (JSC::markIfNeeded):
        * runtime/JSGlobalObject.h:
        (JSC::Structure::prototypeChain):
        * runtime/JSObject.h:
        (JSC::JSObject::putDirectInternal):
        (JSC::JSObject::markChildrenDirect):
        * runtime/JSPropertyNameIterator.cpp:
        (JSC::JSPropertyNameIterator::create):
        (JSC::JSPropertyNameIterator::get):
        (JSC::JSPropertyNameIterator::markChildren):
        * runtime/JSPropertyNameIterator.h:
        (JSC::JSPropertyNameIterator::setCachedPrototypeChain):
        * runtime/JSZombie.cpp:
        (JSC::JSZombie::leakedZombieStructure):
        * runtime/JSZombie.h:
        * runtime/MarkStack.h:
        (JSC::MarkStack::append):
        * runtime/MarkedBlock.cpp:
        (JSC::MarkedBlock::sweep):
        * runtime/Structure.cpp:
        (JSC::Structure::addPropertyTransition):
        * runtime/Structure.h:
        (JSC::Structure::markAggregate):
        * runtime/StructureChain.cpp:
        (JSC::StructureChain::StructureChain):
        (JSC::StructureChain::~StructureChain):
        (JSC::StructureChain::markChildren):
        * runtime/StructureChain.h:
        (JSC::StructureChain::create):
        (JSC::StructureChain::createStructure):
        * runtime/WriteBarrier.h:
        (JSC::WriteBarrierBase::get):
        (JSC::WriteBarrierBase::operator*):
        (JSC::WriteBarrierBase::operator->):
2011-04-01  Oliver Hunt  <oliver@apple.com>

        Reviewed by Geoffrey Garen.

        Make StructureChain GC allocated
        https://bugs.webkit.org/show_bug.cgi?id=56695

        Update for new Structure marking function

        * bindings/js/JSDOMGlobalObject.cpp:
        (WebCore::JSDOMGlobalObject::markChildren):

git-svn-id: http://svn.webkit.org/repository/webkit/trunk@82849 268f45cc-cd09-0410-ab3c-d52691b4dbfc
parent cb7a066b
2011-04-01 Oliver Hunt <oliver@apple.com>
Reviewed by Geoffrey Garen.
Make StructureChain GC allocated
https://bugs.webkit.org/show_bug.cgi?id=56695
Make StructureChain GC allocated, and make the various owners
mark it correctly.
* JavaScriptCore.exp:
* bytecode/CodeBlock.cpp:
(JSC::CodeBlock::dump):
(JSC::CodeBlock::derefStructures):
(JSC::CodeBlock::refStructures):
(JSC::CodeBlock::markAggregate):
* bytecode/Instruction.h:
(JSC::PolymorphicAccessStructureList::PolymorphicStubInfo::set):
(JSC::PolymorphicAccessStructureList::PolymorphicAccessStructureList):
(JSC::PolymorphicAccessStructureList::derefStructures):
(JSC::PolymorphicAccessStructureList::markAggregate):
(JSC::Instruction::Instruction):
* bytecode/StructureStubInfo.cpp:
(JSC::StructureStubInfo::deref):
(JSC::StructureStubInfo::markAggregate):
* bytecode/StructureStubInfo.h:
(JSC::StructureStubInfo::initGetByIdChain):
(JSC::StructureStubInfo::initPutByIdTransition):
* bytecompiler/BytecodeGenerator.cpp:
(JSC::BytecodeGenerator::emitJumpIfNotFunctionCall):
(JSC::BytecodeGenerator::emitJumpIfNotFunctionApply):
* collector/handles/Handle.h:
(JSC::HandleConverter::operator->):
(JSC::HandleConverter::operator*):
* interpreter/Interpreter.cpp:
(JSC::Interpreter::privateExecute):
* jit/JITOpcodes.cpp:
(JSC::JIT::emit_op_jneq_ptr):
* jit/JITOpcodes32_64.cpp:
(JSC::JIT::emit_op_jneq_ptr):
* jit/JITPropertyAccess.cpp:
(JSC::JIT::privateCompileGetByIdChainList):
* jit/JITPropertyAccess32_64.cpp:
(JSC::JIT::privateCompileGetByIdChainList):
* jit/JITStubs.cpp:
(JSC::JITThunks::tryCachePutByID):
(JSC::JITThunks::tryCacheGetByID):
(JSC::getPolymorphicAccessStructureListSlot):
(JSC::DEFINE_STUB_FUNCTION):
* runtime/JSCell.h:
* runtime/JSGlobalData.cpp:
(JSC::JSGlobalData::JSGlobalData):
* runtime/JSGlobalData.h:
* runtime/JSGlobalObject.cpp:
(JSC::markIfNeeded):
* runtime/JSGlobalObject.h:
(JSC::Structure::prototypeChain):
* runtime/JSObject.h:
(JSC::JSObject::putDirectInternal):
(JSC::JSObject::markChildrenDirect):
* runtime/JSPropertyNameIterator.cpp:
(JSC::JSPropertyNameIterator::create):
(JSC::JSPropertyNameIterator::get):
(JSC::JSPropertyNameIterator::markChildren):
* runtime/JSPropertyNameIterator.h:
(JSC::JSPropertyNameIterator::setCachedPrototypeChain):
* runtime/JSZombie.cpp:
(JSC::JSZombie::leakedZombieStructure):
* runtime/JSZombie.h:
* runtime/MarkStack.h:
(JSC::MarkStack::append):
* runtime/MarkedBlock.cpp:
(JSC::MarkedBlock::sweep):
* runtime/Structure.cpp:
(JSC::Structure::addPropertyTransition):
* runtime/Structure.h:
(JSC::Structure::markAggregate):
* runtime/StructureChain.cpp:
(JSC::StructureChain::StructureChain):
(JSC::StructureChain::~StructureChain):
(JSC::StructureChain::markChildren):
* runtime/StructureChain.h:
(JSC::StructureChain::create):
(JSC::StructureChain::createStructure):
* runtime/WriteBarrier.h:
(JSC::WriteBarrierBase::get):
(JSC::WriteBarrierBase::operator*):
(JSC::WriteBarrierBase::operator->):
2011-04-01 Geoffrey Garen <ggaren@apple.com> 2011-04-01 Geoffrey Garen <ggaren@apple.com>
Reviewed by Oliver Hunt. Reviewed by Oliver Hunt.
......
...@@ -314,7 +314,7 @@ __ZN3JSC9MarkStack10s_pageSizeE ...@@ -314,7 +314,7 @@ __ZN3JSC9MarkStack10s_pageSizeE
__ZN3JSC9MarkStack18initializePagesizeEv __ZN3JSC9MarkStack18initializePagesizeEv
__ZN3JSC9Structure17stopIgnoringLeaksEv __ZN3JSC9Structure17stopIgnoringLeaksEv
__ZN3JSC9Structure18startIgnoringLeaksEv __ZN3JSC9Structure18startIgnoringLeaksEv
__ZN3JSC9Structure21addPropertyTransitionEPS0_RKNS_10IdentifierEjPNS_6JSCellERm __ZN3JSC9Structure21addPropertyTransitionERNS_12JSGlobalDataEPS0_RKNS_10IdentifierEjPNS_6JSCellERm
__ZN3JSC9Structure22materializePropertyMapEv __ZN3JSC9Structure22materializePropertyMapEv
__ZN3JSC9Structure25changePrototypeTransitionEPS0_NS_7JSValueE __ZN3JSC9Structure25changePrototypeTransitionEPS0_NS_7JSValueE
__ZN3JSC9Structure27despecifyDictionaryFunctionERKNS_10IdentifierE __ZN3JSC9Structure27despecifyDictionaryFunctionERKNS_10IdentifierE
......
...@@ -51,7 +51,7 @@ EXPORTS ...@@ -51,7 +51,7 @@ EXPORTS
?addBytes@MD5@WTF@@QAEXPBEI@Z ?addBytes@MD5@WTF@@QAEXPBEI@Z
?addBytes@SHA1@WTF@@QAEXPBEI@Z ?addBytes@SHA1@WTF@@QAEXPBEI@Z
?addCurrentThread@MachineThreads@JSC@@QAEXXZ ?addCurrentThread@MachineThreads@JSC@@QAEXXZ
?addPropertyTransition@Structure@JSC@@SA?AV?$PassRefPtr@VStructure@JSC@@@WTF@@PAV12@ABVIdentifier@2@IPAVJSCell@2@AAI@Z ?addPropertyTransition@Structure@JSC@@SA?AV?$PassRefPtr@VStructure@JSC@@@WTF@@AAVJSGlobalData@2@PAV12@ABVIdentifier@2@IPAVJSCell@2@AAI@Z
?addPropertyTransitionToExistingStructure@Structure@JSC@@SA?AV?$PassRefPtr@VStructure@JSC@@@WTF@@PAV12@ABVIdentifier@2@IPAVJSCell@2@AAI@Z ?addPropertyTransitionToExistingStructure@Structure@JSC@@SA?AV?$PassRefPtr@VStructure@JSC@@@WTF@@PAV12@ABVIdentifier@2@IPAVJSCell@2@AAI@Z
?addPropertyWithoutTransition@Structure@JSC@@QAEIABVIdentifier@2@IPAVJSCell@2@@Z ?addPropertyWithoutTransition@Structure@JSC@@QAEIABVIdentifier@2@IPAVJSCell@2@@Z
?addSlowCase@Identifier@JSC@@CA?AV?$PassRefPtr@VStringImpl@WTF@@@WTF@@PAVExecState@2@PAVStringImpl@4@@Z ?addSlowCase@Identifier@JSC@@CA?AV?$PassRefPtr@VStringImpl@WTF@@@WTF@@PAVExecState@2@PAVStringImpl@4@@Z
......
...@@ -731,7 +731,7 @@ void CodeBlock::dump(ExecState* exec, const Vector<Instruction>::const_iterator& ...@@ -731,7 +731,7 @@ void CodeBlock::dump(ExecState* exec, const Vector<Instruction>::const_iterator&
case op_resolve_global_dynamic: { case op_resolve_global_dynamic: {
int r0 = (++it)->u.operand; int r0 = (++it)->u.operand;
int id0 = (++it)->u.operand; int id0 = (++it)->u.operand;
JSValue scope = JSValue((++it)->u.jsCell); JSValue scope = JSValue((++it)->u.jsCell.get());
++it; ++it;
int depth = (++it)->u.operand; int depth = (++it)->u.operand;
printf("[%4d] resolve_global_dynamic\t %s, %s, %s, %d\n", location, registerName(exec, r0).data(), valueToSourceString(exec, scope).utf8().data(), idName(id0, m_identifiers[id0]).data(), depth); printf("[%4d] resolve_global_dynamic\t %s, %s, %s, %d\n", location, registerName(exec, r0).data(), valueToSourceString(exec, scope).utf8().data(), idName(id0, m_identifiers[id0]).data(), depth);
...@@ -1437,13 +1437,11 @@ void CodeBlock::derefStructures(Instruction* vPC) const ...@@ -1437,13 +1437,11 @@ void CodeBlock::derefStructures(Instruction* vPC) const
} }
if (vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_chain) || vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_getter_chain) || vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_custom_chain)) { if (vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_chain) || vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_getter_chain) || vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_custom_chain)) {
vPC[4].u.structure->deref(); vPC[4].u.structure->deref();
vPC[5].u.structureChain->deref();
return; return;
} }
if (vPC[0].u.opcode == interpreter->getOpcode(op_put_by_id_transition)) { if (vPC[0].u.opcode == interpreter->getOpcode(op_put_by_id_transition)) {
vPC[4].u.structure->deref(); vPC[4].u.structure->deref();
vPC[5].u.structure->deref(); vPC[5].u.structure->deref();
vPC[6].u.structureChain->deref();
return; return;
} }
if (vPC[0].u.opcode == interpreter->getOpcode(op_put_by_id_replace)) { if (vPC[0].u.opcode == interpreter->getOpcode(op_put_by_id_replace)) {
...@@ -1486,13 +1484,11 @@ void CodeBlock::refStructures(Instruction* vPC) const ...@@ -1486,13 +1484,11 @@ void CodeBlock::refStructures(Instruction* vPC) const
} }
if (vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_chain) || vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_getter_chain) || vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_custom_chain)) { if (vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_chain) || vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_getter_chain) || vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_custom_chain)) {
vPC[4].u.structure->ref(); vPC[4].u.structure->ref();
vPC[5].u.structureChain->ref();
return; return;
} }
if (vPC[0].u.opcode == interpreter->getOpcode(op_put_by_id_transition)) { if (vPC[0].u.opcode == interpreter->getOpcode(op_put_by_id_transition)) {
vPC[4].u.structure->ref(); vPC[4].u.structure->ref();
vPC[5].u.structure->ref(); vPC[5].u.structure->ref();
vPC[6].u.structureChain->ref();
return; return;
} }
if (vPC[0].u.opcode == interpreter->getOpcode(op_put_by_id_replace)) { if (vPC[0].u.opcode == interpreter->getOpcode(op_put_by_id_replace)) {
...@@ -1527,6 +1523,34 @@ void CodeBlock::markAggregate(MarkStack& markStack) ...@@ -1527,6 +1523,34 @@ void CodeBlock::markAggregate(MarkStack& markStack)
if (callLinkInfo(i).isLinked()) if (callLinkInfo(i).isLinked())
markStack.append(&callLinkInfo(i).callee); markStack.append(&callLinkInfo(i).callee);
#endif #endif
#if ENABLE(INTERPRETER)
Interpreter* interpreter = m_globalData->interpreter;
for (size_t size = m_propertyAccessInstructions.size(), i = 0; i < size; ++i) {
Instruction* vPC = &m_instructions[m_propertyAccessInstructions[i]];
if (vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_chain) || vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_getter_chain) || vPC[0].u.opcode == interpreter->getOpcode(op_get_by_id_custom_chain))
markStack.append(&vPC[5].u.structureChain);
else if (vPC[0].u.opcode == interpreter->getOpcode(op_put_by_id_transition))
markStack.append(&vPC[6].u.structureChain);
}
#endif
#if ENABLE(JIT)
for (size_t size = m_globalResolveInfos.size(), i = 0; i < size; ++i) {
if (Structure* structure = m_globalResolveInfos[i].structure)
structure->markAggregate(markStack);
}
for (size_t size = m_structureStubInfos.size(), i = 0; i < size; ++i)
m_structureStubInfos[i].markAggregate(markStack);
for (size_t size = m_methodCallLinkInfos.size(), i = 0; i < size; ++i) {
if (Structure* structure = m_methodCallLinkInfos[i].cachedStructure) {
// Both members must be filled at the same time
structure->markAggregate(markStack);
ASSERT(!!m_methodCallLinkInfos[i].cachedPrototypeStructure);
m_methodCallLinkInfos[i].cachedPrototypeStructure->markAggregate(markStack);
}
}
#endif
} }
HandlerInfo* CodeBlock::handlerForBytecodeOffset(unsigned bytecodeOffset) HandlerInfo* CodeBlock::handlerForBytecodeOffset(unsigned bytecodeOffset)
......
...@@ -33,6 +33,7 @@ ...@@ -33,6 +33,7 @@
#include "Opcode.h" #include "Opcode.h"
#include "PropertySlot.h" #include "PropertySlot.h"
#include "Structure.h" #include "Structure.h"
#include "StructureChain.h"
#include <wtf/VectorTraits.h> #include <wtf/VectorTraits.h>
#define POLYMORPHIC_LIST_CACHE_SIZE 8 #define POLYMORPHIC_LIST_CACHE_SIZE 8
...@@ -63,7 +64,7 @@ namespace JSC { ...@@ -63,7 +64,7 @@ namespace JSC {
Structure* base; Structure* base;
union { union {
Structure* proto; Structure* proto;
StructureChain* chain; WriteBarrierBase<StructureChain> chain;
} u; } u;
void set(PolymorphicAccessStructureListStubRoutineType _stubRoutine, Structure* _base) void set(PolymorphicAccessStructureListStubRoutineType _stubRoutine, Structure* _base)
...@@ -82,11 +83,11 @@ namespace JSC { ...@@ -82,11 +83,11 @@ namespace JSC {
isChain = false; isChain = false;
} }
void set(PolymorphicAccessStructureListStubRoutineType _stubRoutine, Structure* _base, StructureChain* _chain) void set(JSGlobalData& globalData, JSCell* owner, PolymorphicAccessStructureListStubRoutineType _stubRoutine, Structure* _base, StructureChain* _chain)
{ {
stubRoutine = _stubRoutine; stubRoutine = _stubRoutine;
base = _base; base = _base;
u.chain = _chain; u.chain.set(globalData, owner, _chain);
isChain = true; isChain = true;
} }
} list[POLYMORPHIC_LIST_CACHE_SIZE]; } list[POLYMORPHIC_LIST_CACHE_SIZE];
...@@ -101,9 +102,9 @@ namespace JSC { ...@@ -101,9 +102,9 @@ namespace JSC {
list[0].set(stubRoutine, firstBase, firstProto); list[0].set(stubRoutine, firstBase, firstProto);
} }
PolymorphicAccessStructureList(PolymorphicAccessStructureListStubRoutineType stubRoutine, Structure* firstBase, StructureChain* firstChain) PolymorphicAccessStructureList(JSGlobalData& globalData, JSCell* owner, PolymorphicAccessStructureListStubRoutineType stubRoutine, Structure* firstBase, StructureChain* firstChain)
{ {
list[0].set(stubRoutine, firstBase, firstChain); list[0].set(globalData, owner, stubRoutine, firstBase, firstChain);
} }
void derefStructures(int count) void derefStructures(int count)
...@@ -115,13 +116,22 @@ namespace JSC { ...@@ -115,13 +116,22 @@ namespace JSC {
info.base->deref(); info.base->deref();
if (info.u.proto) { if (info.u.proto) {
if (info.isChain) if (!info.isChain)
info.u.chain->deref();
else
info.u.proto->deref(); info.u.proto->deref();
} }
} }
} }
void markAggregate(MarkStack& markStack, int count)
{
for (int i = 0; i < count; ++i) {
PolymorphicStubInfo& info = list[i];
ASSERT(info.base);
if (info.u.chain && info.isChain)
markStack.append(&info.u.chain);
}
}
}; };
struct Instruction { struct Instruction {
...@@ -130,7 +140,7 @@ namespace JSC { ...@@ -130,7 +140,7 @@ namespace JSC {
#if !ENABLE(COMPUTED_GOTO_INTERPRETER) #if !ENABLE(COMPUTED_GOTO_INTERPRETER)
// We have to initialize one of the pointer members to ensure that // We have to initialize one of the pointer members to ensure that
// the entire struct is initialized, when opcode is not a pointer. // the entire struct is initialized, when opcode is not a pointer.
u.jsCell = 0; u.jsCell.clear();
#endif #endif
u.opcode = opcode; u.opcode = opcode;
} }
...@@ -139,13 +149,21 @@ namespace JSC { ...@@ -139,13 +149,21 @@ namespace JSC {
{ {
// We have to initialize one of the pointer members to ensure that // We have to initialize one of the pointer members to ensure that
// the entire struct is initialized in 64-bit. // the entire struct is initialized in 64-bit.
u.jsCell = 0; u.jsCell.clear();
u.operand = operand; u.operand = operand;
} }
Instruction(Structure* structure) { u.structure = structure; } Instruction(Structure* structure) { u.structure = structure; }
Instruction(StructureChain* structureChain) { u.structureChain = structureChain; } Instruction(JSGlobalData& globalData, JSCell* owner, StructureChain* structureChain)
Instruction(JSCell* jsCell) { u.jsCell = jsCell; } {
u.structureChain.clear();
u.structureChain.set(globalData, owner, structureChain);
}
Instruction(JSGlobalData& globalData, JSCell* owner, JSCell* jsCell)
{
u.jsCell.clear();
u.jsCell.set(globalData, owner, jsCell);
}
Instruction(PolymorphicAccessStructureList* polymorphicStructures) { u.polymorphicStructures = polymorphicStructures; } Instruction(PolymorphicAccessStructureList* polymorphicStructures) { u.polymorphicStructures = polymorphicStructures; }
Instruction(PropertySlot::GetValueFunc getterFunc) { u.getterFunc = getterFunc; } Instruction(PropertySlot::GetValueFunc getterFunc) { u.getterFunc = getterFunc; }
...@@ -153,8 +171,8 @@ namespace JSC { ...@@ -153,8 +171,8 @@ namespace JSC {
Opcode opcode; Opcode opcode;
int operand; int operand;
Structure* structure; Structure* structure;
StructureChain* structureChain; WriteBarrierBase<StructureChain> structureChain;
JSCell* jsCell; WriteBarrierBase<JSCell> jsCell;
PolymorphicAccessStructureList* polymorphicStructures; PolymorphicAccessStructureList* polymorphicStructures;
PropertySlot::GetValueFunc getterFunc; PropertySlot::GetValueFunc getterFunc;
} u; } u;
......
...@@ -44,7 +44,6 @@ void StructureStubInfo::deref() ...@@ -44,7 +44,6 @@ void StructureStubInfo::deref()
return; return;
case access_get_by_id_chain: case access_get_by_id_chain:
u.getByIdChain.baseObjectStructure->deref(); u.getByIdChain.baseObjectStructure->deref();
u.getByIdChain.chain->deref();
return; return;
case access_get_by_id_self_list: { case access_get_by_id_self_list: {
PolymorphicAccessStructureList* polymorphicStructures = u.getByIdSelfList.structureList; PolymorphicAccessStructureList* polymorphicStructures = u.getByIdSelfList.structureList;
...@@ -60,8 +59,6 @@ void StructureStubInfo::deref() ...@@ -60,8 +59,6 @@ void StructureStubInfo::deref()
} }
case access_put_by_id_transition: case access_put_by_id_transition:
u.putByIdTransition.previousStructure->deref(); u.putByIdTransition.previousStructure->deref();
u.putByIdTransition.structure->deref();
u.putByIdTransition.chain->deref();
return; return;
case access_put_by_id_replace: case access_put_by_id_replace:
u.putByIdReplace.baseObjectStructure->deref(); u.putByIdReplace.baseObjectStructure->deref();
...@@ -78,6 +75,51 @@ void StructureStubInfo::deref() ...@@ -78,6 +75,51 @@ void StructureStubInfo::deref()
ASSERT_NOT_REACHED(); ASSERT_NOT_REACHED();
} }
} }
void StructureStubInfo::markAggregate(MarkStack& markStack)
{
switch (accessType) {
case access_get_by_id_self:
u.getByIdSelf.baseObjectStructure->markAggregate(markStack);
return;
case access_get_by_id_proto:
u.getByIdProto.baseObjectStructure->markAggregate(markStack);
u.getByIdProto.prototypeStructure->markAggregate(markStack);
return;
case access_get_by_id_chain:
u.getByIdChain.baseObjectStructure->markAggregate(markStack);
markStack.append(&u.getByIdChain.chain);
return;
case access_get_by_id_self_list: {
PolymorphicAccessStructureList* polymorphicStructures = u.getByIdSelfList.structureList;
polymorphicStructures->markAggregate(markStack, u.getByIdSelfList.listSize);
return;
}
case access_get_by_id_proto_list: {
PolymorphicAccessStructureList* polymorphicStructures = u.getByIdProtoList.structureList;
polymorphicStructures->markAggregate(markStack, u.getByIdProtoList.listSize);
return;
}
case access_put_by_id_transition:
u.putByIdTransition.previousStructure->markAggregate(markStack);
u.putByIdTransition.structure->markAggregate(markStack);
markStack.append(&u.putByIdTransition.chain);
return;
case access_put_by_id_replace:
u.putByIdReplace.baseObjectStructure->markAggregate(markStack);
return;
case access_get_by_id:
case access_put_by_id:
case access_get_by_id_generic:
case access_put_by_id_generic:
case access_get_array_length:
case access_get_string_length:
// These instructions don't ref their Structures.
return;
default:
ASSERT_NOT_REACHED();
}
}
#endif #endif
} // namespace JSC } // namespace JSC
...@@ -77,15 +77,14 @@ namespace JSC { ...@@ -77,15 +77,14 @@ namespace JSC {
prototypeStructure->ref(); prototypeStructure->ref();
} }
void initGetByIdChain(Structure* baseObjectStructure, StructureChain* chain) void initGetByIdChain(JSGlobalData& globalData, JSCell* owner, Structure* baseObjectStructure, StructureChain* chain)
{ {
accessType = access_get_by_id_chain; accessType = access_get_by_id_chain;
u.getByIdChain.baseObjectStructure = baseObjectStructure; u.getByIdChain.baseObjectStructure = baseObjectStructure;
baseObjectStructure->ref(); baseObjectStructure->ref();
u.getByIdChain.chain = chain; u.getByIdChain.chain.set(globalData, owner, chain);
chain->ref();
} }
void initGetByIdSelfList(PolymorphicAccessStructureList* structureList, int listSize) void initGetByIdSelfList(PolymorphicAccessStructureList* structureList, int listSize)
...@@ -106,7 +105,7 @@ namespace JSC { ...@@ -106,7 +105,7 @@ namespace JSC {
// PutById* // PutById*
void initPutByIdTransition(Structure* previousStructure, Structure* structure, StructureChain* chain) void initPutByIdTransition(JSGlobalData& globalData, JSCell* owner, Structure* previousStructure, Structure* structure, StructureChain* chain)
{ {
accessType = access_put_by_id_transition; accessType = access_put_by_id_transition;
...@@ -116,8 +115,7 @@ namespace JSC { ...@@ -116,8 +115,7 @@ namespace JSC {
u.putByIdTransition.structure = structure; u.putByIdTransition.structure = structure;
structure->ref(); structure->ref();
u.putByIdTransition.chain = chain; u.putByIdTransition.chain.set(globalData, owner, chain);
chain->ref();
} }
void initPutByIdReplace(Structure* baseObjectStructure) void initPutByIdReplace(Structure* baseObjectStructure)
...@@ -129,6 +127,7 @@ namespace JSC { ...@@ -129,6 +127,7 @@ namespace JSC {
} }
void deref(); void deref();
void markAggregate(MarkStack&);
bool seenOnce() bool seenOnce()
{ {
...@@ -153,7 +152,7 @@ namespace JSC { ...@@ -153,7 +152,7 @@ namespace JSC {
} getByIdProto; } getByIdProto;
struct { struct {
Structure* baseObjectStructure; Structure* baseObjectStructure;
StructureChain* chain; WriteBarrierBase<StructureChain> chain;
} getByIdChain; } getByIdChain;
struct { struct {
PolymorphicAccessStructureList* structureList; PolymorphicAccessStructureList* structureList;
...@@ -166,7 +165,7 @@ namespace JSC { ...@@ -166,7 +165,7 @@ namespace JSC {
struct { struct {
Structure* previousStructure; Structure* previousStructure;
Structure* structure; Structure* structure;
StructureChain* chain; WriteBarrierBase<StructureChain> chain;
} putByIdTransition; } putByIdTransition;
struct { struct {
Structure* baseObjectStructure; Structure* baseObjectStructure;
......
...@@ -925,7 +925,7 @@ PassRefPtr<Label> BytecodeGenerator::emitJumpIfNotFunctionCall(RegisterID* cond, ...@@ -925,7 +925,7 @@ PassRefPtr<Label> BytecodeGenerator::emitJumpIfNotFunctionCall(RegisterID* cond,
emitOpcode(op_jneq_ptr); emitOpcode(op_jneq_ptr);
instructions().append(cond->index()); instructions().append(cond->index());
instructions().append(m_scopeChain->globalObject->callFunction()); instructions().append(Instruction(*m_globalData, m_codeBlock->ownerExecutable(), m_scopeChain->globalObject->callFunction()));
instructions().append(target->bind(begin, instructions().size())); instructions().append(target->bind(begin, instructions().size()));
return target; return target;
} }
...@@ -936,7 +936,7 @@ PassRefPtr<Label> BytecodeGenerator::emitJumpIfNotFunctionApply(RegisterID* cond ...@@ -936,7 +936,7 @@ PassRefPtr<Label> BytecodeGenerator::emitJumpIfNotFunctionApply(RegisterID* cond
emitOpcode(op_jneq_ptr); emitOpcode(op_jneq_ptr);
instructions().append(cond->index()); instructions().append(cond->index());
instructions().append(m_scopeChain->globalObject->applyFunction()); instructions().append(Instruction(*m_globalData, m_codeBlock->ownerExecutable(), m_scopeChain->globalObject->applyFunction()));
instructions().append(target->bind(begin, instructions().size())); instructions().append(target->bind(begin, instructions().size()));
return target; return target;
} }
......
...@@ -104,10 +104,35 @@ template <> struct HandleTypes<Unknown> { ...@@ -104,10 +104,35 @@ template <> struct HandleTypes<Unknown> {
}; };
template <typename Base, typename T> struct HandleConverter { template <typename Base, typename T> struct HandleConverter {
T* operator->() { return static_cast<Base*>(this)->get(); } T* operator->()
const T* operator->() const { return static_cast<const Base*>(this)->get(); } {
T* operator*() { return static_cast<Base*>(this)->get(); } #if ENABLE(JSC_ZOMBIES)
const T* operator*() const { return static_cast<const Base*>(this)->get(); } ASSERT(!static_cast<const Base*>(this)->get() || !static_cast<const Base*>(this)->get()->isZombie());
#endif
return static_cast<Base*>(this)->get();
}
const T* operator->() const
{
#if ENABLE(JSC_ZOMBIES)
ASSERT(!static_cast<const Base*>(this)->get() || !static_cast<const Base*>(this)->get()->isZombie());
#endif
return static_cast<const Base*>(this)->get();
}
T* operator*()
{
#if ENABLE(JSC_ZOMBIES)
ASSERT(!static_cast<const Base*>(this)->get() || !static_cast<const Base*>(this)->get()->isZombie());
#endif
return static_cast<Base*>(this)->get();
}
const T* operator*() const
{
#if ENABLE(JSC_ZOMBIES)
ASSERT(!static_cast<const Base*>(this)->get() || !static_cast<const Base*>(this)->get()->isZombie());
#endif
return static_cast<const Base*>(this)->get();
}
}; };
template <typename Base> struct HandleConverter<Base, Unknown> { template <typename Base> struct HandleConverter<Base, Unknown> {
...@@ -118,7 +143,13 @@ template <typename Base> struct HandleConverter<Base, Unknown> { ...@@ -118,7 +143,13 @@ template <typename Base> struct HandleConverter<Base, Unknown> {
bool isUndefinedOrNull() const { return jsValue().isUndefinedOrNull(); } bool isUndefinedOrNull() const { return jsValue().isUndefinedOrNull(); }