Changeset 95559 in webkit


Ignore:
Timestamp:
Sep 20, 2011 11:31:37 AM (13 years ago)
Author:
oliver@apple.com
Message:

Refactor Heap allocation logic into separate AllocationSpace class
https://bugs.webkit.org/show_bug.cgi?id=68409

Reviewed by Gavin Barraclough.

../../../../Volumes/Data/git/WebKit/OpenSource/Source/JavaScriptCore:

This patch hoists direct manipulation of the MarkedSpace and related
data out of Heap and into a separate class. This will allow us to
have multiple allocation spaces in future, so easing the way towards
having GC'd backing stores for objects.

(JSC::Debugger::recompileAllJSFunctions):

  • heap/AllocationSpace.cpp: Added.

(JSC::AllocationSpace::tryAllocate):
(JSC::AllocationSpace::allocateSlowCase):
(JSC::AllocationSpace::allocateBlock):
(JSC::AllocationSpace::freeBlocks):
(JSC::TakeIfEmpty::TakeIfEmpty):
(JSC::TakeIfEmpty::operator()):
(JSC::TakeIfEmpty::returnValue):
(JSC::AllocationSpace::shrink):

  • heap/AllocationSpace.h: Added.

(JSC::AllocationSpace::AllocationSpace):
(JSC::AllocationSpace::blocks):
(JSC::AllocationSpace::sizeClassFor):
(JSC::AllocationSpace::setHighWaterMark):
(JSC::AllocationSpace::highWaterMark):
(JSC::AllocationSpace::canonicalizeBlocks):
(JSC::AllocationSpace::resetAllocator):
(JSC::AllocationSpace::forEachCell):
(JSC::AllocationSpace::forEachBlock):
(JSC::AllocationSpace::allocate):

  • heap/Heap.cpp:

(JSC::Heap::Heap):
(JSC::Heap::reportExtraMemoryCostSlowCase):
(JSC::Heap::getConservativeRegisterRoots):
(JSC::Heap::markRoots):
(JSC::Heap::clearMarks):
(JSC::Heap::sweep):
(JSC::Heap::objectCount):
(JSC::Heap::size):
(JSC::Heap::capacity):
(JSC::Heap::globalObjectCount):
(JSC::Heap::objectTypeCounts):
(JSC::Heap::collect):
(JSC::Heap::canonicalizeBlocks):
(JSC::Heap::resetAllocator):
(JSC::Heap::freeBlocks):
(JSC::Heap::shrink):

  • heap/Heap.h:

(JSC::Heap::objectSpace):
(JSC::Heap::sizeClassForObject):
(JSC::Heap::allocate):

  • jit/JITInlineMethods.h:

(JSC::JIT::emitAllocateBasicJSObject):

  • runtime/JSGlobalData.cpp:

(JSC::JSGlobalData::recompileAllJSFunctions):
(JSC::JSGlobalData::releaseExecutableMemory):

../../../../Volumes/Data/git/WebKit/OpenSource/Source/WebCore:

Adding a forwarding header.

  • ForwardingHeaders/heap/AllocationSpace.h: Added.
Location:
trunk/Source
Files:
3 added
15 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/JavaScriptCore/CMakeLists.txt

    r95507 r95559  
    4646    bytecompiler/NodesCodegen.cpp
    4747
     48    heap/AllocationSpace.cpp
    4849    heap/Heap.cpp
    4950    heap/HandleHeap.cpp
  • trunk/Source/JavaScriptCore/ChangeLog

    r95555 r95559  
     12011-09-19  Oliver Hunt  <oliver@apple.com>
     2
     3        Refactor Heap allocation logic into separate AllocationSpace class
     4        https://bugs.webkit.org/show_bug.cgi?id=68409
     5
     6        Reviewed by Gavin Barraclough.
     7
     8        This patch hoists direct manipulation of the MarkedSpace and related
     9        data out of Heap and into a separate class.  This will allow us to
     10        have multiple allocation spaces in future, so easing the way towards
     11        having GC'd backing stores for objects.
     12
     13        * CMakeLists.txt:
     14        * GNUmakefile.list.am:
     15        * JavaScriptCore.exp:
     16        * JavaScriptCore.gypi:
     17        * JavaScriptCore.pro:
     18        * JavaScriptCore.vcproj/JavaScriptCore/JavaScriptCore.def:
     19        * JavaScriptCore.vcproj/JavaScriptCore/JavaScriptCore.vcproj:
     20        * JavaScriptCore.xcodeproj/project.pbxproj:
     21        * debugger/Debugger.cpp:
     22        (JSC::Debugger::recompileAllJSFunctions):
     23        * heap/AllocationSpace.cpp: Added.
     24        (JSC::AllocationSpace::tryAllocate):
     25        (JSC::AllocationSpace::allocateSlowCase):
     26        (JSC::AllocationSpace::allocateBlock):
     27        (JSC::AllocationSpace::freeBlocks):
     28        (JSC::TakeIfEmpty::TakeIfEmpty):
     29        (JSC::TakeIfEmpty::operator()):
     30        (JSC::TakeIfEmpty::returnValue):
     31        (JSC::AllocationSpace::shrink):
     32        * heap/AllocationSpace.h: Added.
     33        (JSC::AllocationSpace::AllocationSpace):
     34        (JSC::AllocationSpace::blocks):
     35        (JSC::AllocationSpace::sizeClassFor):
     36        (JSC::AllocationSpace::setHighWaterMark):
     37        (JSC::AllocationSpace::highWaterMark):
     38        (JSC::AllocationSpace::canonicalizeBlocks):
     39        (JSC::AllocationSpace::resetAllocator):
     40        (JSC::AllocationSpace::forEachCell):
     41        (JSC::AllocationSpace::forEachBlock):
     42        (JSC::AllocationSpace::allocate):
     43        * heap/Heap.cpp:
     44        (JSC::Heap::Heap):
     45        (JSC::Heap::reportExtraMemoryCostSlowCase):
     46        (JSC::Heap::getConservativeRegisterRoots):
     47        (JSC::Heap::markRoots):
     48        (JSC::Heap::clearMarks):
     49        (JSC::Heap::sweep):
     50        (JSC::Heap::objectCount):
     51        (JSC::Heap::size):
     52        (JSC::Heap::capacity):
     53        (JSC::Heap::globalObjectCount):
     54        (JSC::Heap::objectTypeCounts):
     55        (JSC::Heap::collect):
     56        (JSC::Heap::canonicalizeBlocks):
     57        (JSC::Heap::resetAllocator):
     58        (JSC::Heap::freeBlocks):
     59        (JSC::Heap::shrink):
     60        * heap/Heap.h:
     61        (JSC::Heap::objectSpace):
     62        (JSC::Heap::sizeClassForObject):
     63        (JSC::Heap::allocate):
     64        * jit/JITInlineMethods.h:
     65        (JSC::JIT::emitAllocateBasicJSObject):
     66        * runtime/JSGlobalData.cpp:
     67        (JSC::JSGlobalData::recompileAllJSFunctions):
     68        (JSC::JSGlobalData::releaseExecutableMemory):
     69
    1702011-09-19  Geoffrey Garen  <ggaren@apple.com>
    271
  • trunk/Source/JavaScriptCore/GNUmakefile.list.am

    r95507 r95559  
    134134        Source/JavaScriptCore/dfg/DFGSpeculativeJIT.cpp \
    135135        Source/JavaScriptCore/dfg/DFGSpeculativeJIT.h \
     136        Source/JavaScriptCore/heap/AllocationSpace.cpp \
     137        Source/JavaScriptCore/heap/AllocationSpace.h \
    136138        Source/JavaScriptCore/heap/ConservativeRoots.cpp \
    137139        Source/JavaScriptCore/heap/ConservativeRoots.h \
  • trunk/Source/JavaScriptCore/JavaScriptCore.exp

    r95507 r95559  
    119119__ZN3JSC11JSByteArray15createStructureERNS_12JSGlobalDataEPNS_14JSGlobalObjectENS_7JSValueEPKNS_9ClassInfoE
    120120__ZN3JSC11JSByteArrayC1EPNS_9ExecStateEPNS_9StructureEPN3WTF9ByteArrayE
     121__ZN3JSC15AllocationSpace16allocateSlowCaseERNS_11MarkedSpace9SizeClassE
    121122__ZN3JSC11ParserArena5resetEv
    122123__ZN3JSC11checkSyntaxEPNS_9ExecStateERKNS_10SourceCodeEPNS_7JSValueE
     
    234235__ZN3JSC4Heap11objectCountEv
    235236__ZN3JSC4Heap16activityCallbackEv
    236 __ZN3JSC4Heap16allocateSlowCaseERNS_11MarkedSpace9SizeClassE
    237237__ZN3JSC4Heap16objectTypeCountsEv
    238238__ZN3JSC4Heap17collectAllGarbageEv
  • trunk/Source/JavaScriptCore/JavaScriptCore.gypi

    r95507 r95559  
    2828            'assembler/MacroAssemblerCodeRef.h',
    2929            'bytecode/Opcode.h',
     30            'heap/AllocationSpace.h',
    3031            'heap/ConservativeRoots.h',
    3132            'heap/Handle.h',
     
    325326            'bytecompiler/NodesCodegen.cpp',
    326327            'bytecompiler/RegisterID.h',
     328            'heap/AllocationSpace.cpp',
    327329            'heap/ConservativeRoots.cpp',
    328330            'heap/HandleHeap.cpp',
  • trunk/Source/JavaScriptCore/JavaScriptCore.pro

    r95507 r95559  
    7373    bytecompiler/BytecodeGenerator.cpp \
    7474    bytecompiler/NodesCodegen.cpp \
     75    heap/AllocationSpace.cpp \
    7576    heap/ConservativeRoots.cpp \
    7677    heap/HandleHeap.cpp \
  • trunk/Source/JavaScriptCore/JavaScriptCore.vcproj/JavaScriptCore/JavaScriptCore.def

    r95516 r95559  
    6060    ?addSlowCase@Identifier@JSC@@CA?AV?$PassRefPtr@VStringImpl@WTF@@@WTF@@PAVExecState@2@PAVStringImpl@4@@Z
    6161    ?addStaticGlobals@JSGlobalObject@JSC@@IAEXPAUGlobalPropertyInfo@12@H@Z
    62     ?allocate@Heap@JSC@@QAEPAXAAUSizeClass@MarkedSpace@2@@Z
    6362    ?allocatePropertyStorage@JSObject@JSC@@QAEXAAVJSGlobalData@2@II@Z
    64     ?allocateSlowCase@Heap@JSC@@AAEPAXAAUSizeClass@MarkedSpace@2@@Z
     63    ?allocateSlowCase@AllocationSpace@JSC@@AAEPAXAAUSizeClass@MarkedSpace@2@@Z
    6564    ?append@StringBuilder@WTF@@QAEXPBDI@Z
    6665    ?append@StringBuilder@WTF@@QAEXPB_WI@Z
  • trunk/Source/JavaScriptCore/JavaScriptCore.vcproj/JavaScriptCore/JavaScriptCore.vcproj

    r95507 r95559  
    18911891                        >
    18921892                            <File
     1893                                    RelativePath="..\..\heap\AllocationSpace.cpp"
     1894                                    >
     1895                            </File>
     1896                            <File
     1897                                    RelativePath="..\..\heap\AllocationSpace.h"
     1898                                    >
     1899                            </File>
     1900                            <File
    18931901                                    RelativePath="..\..\heap\ConservativeRoots.cpp"
    18941902                                    >
  • trunk/Source/JavaScriptCore/JavaScriptCore.xcodeproj/project.pbxproj

    r95507 r95559  
    407407                A1712B4111C7B235007A5315 /* RegExpKey.h in Headers */ = {isa = PBXBuildFile; fileRef = A1712B4011C7B235007A5315 /* RegExpKey.h */; settings = {ATTRIBUTES = (Private, ); }; };
    408408                A1D764521354448B00C5C7C0 /* Alignment.h in Headers */ = {isa = PBXBuildFile; fileRef = A1D764511354448B00C5C7C0 /* Alignment.h */; settings = {ATTRIBUTES = (Private, ); }; };
     409                A70456B01427FB910037DA68 /* AllocationSpace.h in Headers */ = {isa = PBXBuildFile; fileRef = A70456AF1427FB150037DA68 /* AllocationSpace.h */; settings = {ATTRIBUTES = (Private, ); }; };
     410                A70456B11427FB950037DA68 /* AllocationSpace.cpp in Sources */ = {isa = PBXBuildFile; fileRef = A70456AE1427FB030037DA68 /* AllocationSpace.cpp */; };
    409411                A71236E51195F33C00BD2174 /* JITOpcodes32_64.cpp in Sources */ = {isa = PBXBuildFile; fileRef = A71236E41195F33C00BD2174 /* JITOpcodes32_64.cpp */; };
    410412                A72700900DAC6BBC00E548D7 /* JSNotAnObject.cpp in Sources */ = {isa = PBXBuildFile; fileRef = A72700780DAC605600E548D7 /* JSNotAnObject.cpp */; };
     
    11831185                A1712B4011C7B235007A5315 /* RegExpKey.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RegExpKey.h; sourceTree = "<group>"; };
    11841186                A1D764511354448B00C5C7C0 /* Alignment.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Alignment.h; sourceTree = "<group>"; };
     1187                A70456AE1427FB030037DA68 /* AllocationSpace.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = AllocationSpace.cpp; sourceTree = "<group>"; };
     1188                A70456AF1427FB150037DA68 /* AllocationSpace.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AllocationSpace.h; sourceTree = "<group>"; };
    11851189                A71236E41195F33C00BD2174 /* JITOpcodes32_64.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = JITOpcodes32_64.cpp; sourceTree = "<group>"; };
    11861190                A718F61A11754A21002465A7 /* RegExpJitTables.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = RegExpJitTables.h; sourceTree = "<group>"; };
     
    16181622                        isa = PBXGroup;
    16191623                        children = (
     1624                                A70456AF1427FB150037DA68 /* AllocationSpace.h */,
     1625                                A70456AE1427FB030037DA68 /* AllocationSpace.cpp */,
    16201626                                0F242DA513F3B1BB007ADD4C /* WeakReferenceHarvester.h */,
    16211627                                0FC815141405118D00CFA603 /* VTableSpectrum.h */,
     
    27942800                                A781E359141970C700094D90 /* StorageBarrier.h in Headers */,
    27952801                                1A08277A142168D70090CCAC /* BinarySemaphore.h in Headers */,
     2802                                A70456B01427FB910037DA68 /* AllocationSpace.h in Headers */,
    27962803                        );
    27972804                        runOnlyForDeploymentPostprocessing = 0;
     
    32993306                                C22C531313FAF6EF00B7DC0D /* strtod.cc in Sources */,
    33003307                                1A082779142168D70090CCAC /* BinarySemaphore.cpp in Sources */,
     3308                                A70456B11427FB950037DA68 /* AllocationSpace.cpp in Sources */,
    33013309                        );
    33023310                        runOnlyForDeploymentPostprocessing = 0;
  • trunk/Source/JavaScriptCore/debugger/Debugger.cpp

    r95507 r95559  
    119119
    120120    Recompiler recompiler(this);
    121     globalData->heap.forEachCell(recompiler);
     121    globalData->heap.objectSpace().forEachCell(recompiler);
    122122}
    123123
  • trunk/Source/JavaScriptCore/heap/Heap.cpp

    r95512 r95559  
    3434#include <algorithm>
    3535
    36 #define COLLECT_ON_EVERY_ALLOCATION 0
    3736
    3837using namespace std;
     
    176175}
    177176
    178 class TakeIfEmpty {
    179 public:
    180     typedef MarkedBlock* ReturnType;
    181 
    182     TakeIfEmpty(MarkedSpace*);
    183     void operator()(MarkedBlock*);
    184     ReturnType returnValue();
    185 
    186 private:
    187     MarkedSpace* m_markedSpace;
    188     DoublyLinkedList<MarkedBlock> m_empties;
    189 };
    190 
    191 inline TakeIfEmpty::TakeIfEmpty(MarkedSpace* newSpace)
    192     : m_markedSpace(newSpace)
    193 {
    194 }
    195 
    196 inline void TakeIfEmpty::operator()(MarkedBlock* block)
    197 {
    198     if (!block->isEmpty())
    199         return;
    200 
    201     m_markedSpace->removeBlock(block);
    202     m_empties.append(block);
    203 }
    204 
    205 inline TakeIfEmpty::ReturnType TakeIfEmpty::returnValue()
    206 {
    207     return m_empties.head();
    208 }
    209 
    210177class RecordType {
    211178public:
     
    250217    , m_minBytesPerCycle(heapSizeForHint(heapSize))
    251218    , m_operationInProgress(NoOperation)
    252     , m_markedSpace(this)
     219    , m_objectSpace(this)
    253220    , m_extraCost(0)
    254221    , m_markListSet(0)
     
    260227    , m_globalData(globalData)
    261228{
    262     m_markedSpace.setHighWaterMark(m_minBytesPerCycle);
     229    m_objectSpace.setHighWaterMark(m_minBytesPerCycle);
    263230    (*m_activityCallback)();
    264231    m_numberOfFreeBlocks = 0;
     
    394361    // collecting more frequently as long as it stays alive.
    395362
    396     if (m_extraCost > maxExtraCost && m_extraCost > m_markedSpace.highWaterMark() / 2)
     363    if (m_extraCost > maxExtraCost && m_extraCost > m_objectSpace.highWaterMark() / 2)
    397364        collectAllGarbage();
    398365    m_extraCost += cost;
    399 }
    400 
    401 inline void* Heap::tryAllocate(MarkedSpace::SizeClass& sizeClass)
    402 {
    403     m_operationInProgress = Allocation;
    404     void* result = m_markedSpace.allocate(sizeClass);
    405     m_operationInProgress = NoOperation;
    406     return result;
    407 }
    408 
    409 void* Heap::allocateSlowCase(MarkedSpace::SizeClass& sizeClass)
    410 {
    411 #if COLLECT_ON_EVERY_ALLOCATION
    412     collectAllGarbage();
    413     ASSERT(m_operationInProgress == NoOperation);
    414 #endif
    415 
    416     void* result = tryAllocate(sizeClass);
    417 
    418     if (LIKELY(result != 0))
    419         return result;
    420 
    421     AllocationEffort allocationEffort;
    422    
    423     if (m_markedSpace.waterMark() < m_markedSpace.highWaterMark() || !m_isSafeToCollect)
    424         allocationEffort = AllocationMustSucceed;
    425     else
    426         allocationEffort = AllocationCanFail;
    427    
    428     MarkedBlock* block = allocateBlock(sizeClass.cellSize, allocationEffort);
    429     if (block) {
    430         m_markedSpace.addBlock(sizeClass, block);
    431         void* result = tryAllocate(sizeClass);
    432         ASSERT(result);
    433         return result;
    434     }
    435 
    436     collect(DoNotSweep);
    437    
    438     result = tryAllocate(sizeClass);
    439    
    440     if (result)
    441         return result;
    442    
    443     ASSERT(m_markedSpace.waterMark() < m_markedSpace.highWaterMark());
    444    
    445     m_markedSpace.addBlock(sizeClass, allocateBlock(sizeClass.cellSize, AllocationMustSucceed));
    446    
    447     result = tryAllocate(sizeClass);
    448     ASSERT(result);
    449     return result;
    450366}
    451367
     
    522438        CRASH();
    523439    m_operationInProgress = Collection;
    524     ConservativeRoots registerFileRoots(&m_blocks);
     440    ConservativeRoots registerFileRoots(&m_objectSpace.blocks());
    525441    registerFile().gatherConservativeRoots(registerFileRoots);
    526442    size_t registerFileRootCount = registerFileRoots.size();
     
    544460    // We gather conservative roots before clearing mark bits because conservative
    545461    // gathering uses the mark bits to determine whether a reference is valid.
    546     ConservativeRoots machineThreadRoots(&m_blocks);
     462    ConservativeRoots machineThreadRoots(&m_objectSpace.blocks());
    547463    m_machineThreads.gatherConservativeRoots(machineThreadRoots, &dummy);
    548464
    549     ConservativeRoots registerFileRoots(&m_blocks);
     465    ConservativeRoots registerFileRoots(&m_objectSpace.blocks());
    550466    registerFile().gatherConservativeRoots(registerFileRoots);
    551467
     
    600516void Heap::clearMarks()
    601517{
    602     forEachBlock<ClearMarks>();
     518    m_objectSpace.forEachBlock<ClearMarks>();
    603519}
    604520
    605521void Heap::sweep()
    606522{
    607     forEachBlock<Sweep>();
     523    m_objectSpace.forEachBlock<Sweep>();
    608524}
    609525
    610526size_t Heap::objectCount()
    611527{
    612     return forEachBlock<MarkCount>();
     528    return m_objectSpace.forEachBlock<MarkCount>();
    613529}
    614530
    615531size_t Heap::size()
    616532{
    617     return forEachBlock<Size>();
     533    return m_objectSpace.forEachBlock<Size>();
    618534}
    619535
    620536size_t Heap::capacity()
    621537{
    622     return forEachBlock<Capacity>();
     538    return m_objectSpace.forEachBlock<Capacity>();
    623539}
    624540
     
    630546size_t Heap::globalObjectCount()
    631547{
    632     return forEachCell<CountIfGlobalObject>();
     548    return m_objectSpace.forEachCell<CountIfGlobalObject>();
    633549}
    634550
     
    645561PassOwnPtr<TypeCountSet> Heap::objectTypeCounts()
    646562{
    647     return forEachCell<RecordType>();
     563    return m_objectSpace.forEachCell<RecordType>();
    648564}
    649565
     
    684600    // new bytes allocated) proportion, and seems to work well in benchmarks.
    685601    size_t proportionalBytes = 2 * size();
    686     m_markedSpace.setHighWaterMark(max(proportionalBytes, m_minBytesPerCycle));
     602    m_objectSpace.setHighWaterMark(max(proportionalBytes, m_minBytesPerCycle));
    687603    JAVASCRIPTCORE_GC_END();
    688604
     
    692608void Heap::canonicalizeBlocks()
    693609{
    694     m_markedSpace.canonicalizeBlocks();
     610    m_objectSpace.canonicalizeBlocks();
    695611}
    696612
     
    698614{
    699615    m_extraCost = 0;
    700     m_markedSpace.resetAllocator();
     616    m_objectSpace.resetAllocator();
    701617}
    702618
     
    725641}
    726642
    727 MarkedBlock* Heap::allocateBlock(size_t cellSize, Heap::AllocationEffort allocationEffort)
    728 {
    729     MarkedBlock* block;
    730    
    731     {
    732         MutexLocker locker(m_freeBlockLock);
    733         if (m_numberOfFreeBlocks) {
    734             block = m_freeBlocks.removeHead();
    735             ASSERT(block);
    736             m_numberOfFreeBlocks--;
    737         } else
    738             block = 0;
    739     }
    740     if (block)
    741         block->initForCellSize(cellSize);
    742     else if (allocationEffort == AllocationCanFail)
    743         return 0;
    744     else
    745         block = MarkedBlock::create(this, cellSize);
    746    
    747     m_blocks.add(block);
    748 
    749     return block;
    750 }
    751 
    752643void Heap::freeBlocks(MarkedBlock* head)
    753644{
    754     MarkedBlock* next;
    755     for (MarkedBlock* block = head; block; block = next) {
    756         next = block->next();
    757 
    758         m_blocks.remove(block);
    759         block->reset();
    760         MutexLocker locker(m_freeBlockLock);
    761         m_freeBlocks.append(block);
    762         m_numberOfFreeBlocks++;
    763     }
     645    m_objectSpace.freeBlocks(head);
    764646}
    765647
    766648void Heap::shrink()
    767649{
    768     // We record a temporary list of empties to avoid modifying m_blocks while iterating it.
    769     TakeIfEmpty takeIfEmpty(&m_markedSpace);
    770     freeBlocks(forEachBlock(takeIfEmpty));
     650    m_objectSpace.shrink();
    771651}
    772652
  • trunk/Source/JavaScriptCore/heap/Heap.h

    r95512 r95559  
    2323#define Heap_h
    2424
     25#include "AllocationSpace.h"
    2526#include "HandleHeap.h"
    2627#include "HandleStack.h"
     
    3839    class GCActivityCallback;
    3940    class GlobalCodeBlock;
     41    class Heap;
    4042    class HeapRootVisitor;
    4143    class JSCell;
     
    5759    // Heap size hint.
    5860    enum HeapSize { SmallHeap, LargeHeap };
    59    
     61
    6062    class Heap {
    6163        WTF_MAKE_NONCOPYABLE(Heap);
    6264    public:
     65        friend class JIT;
    6366        static Heap* heap(JSValue); // 0 for immediate values
    6467        static Heap* heap(JSCell*);
     
    7780
    7881        JSGlobalData* globalData() const { return m_globalData; }
    79         MarkedSpace& markedSpace() { return m_markedSpace; }
     82        AllocationSpace& objectSpace() { return m_objectSpace; }
    8083        MachineThreads& machineThreads() { return m_machineThreads; }
    8184
     
    8588        // true if an allocation or collection is in progress
    8689        inline bool isBusy();
    87 
     90       
     91        MarkedSpace::SizeClass& sizeClassForObject(size_t bytes) { return m_objectSpace.sizeClassFor(bytes); }
    8892        void* allocate(size_t);
    89         MarkedSpace::SizeClass& sizeClassFor(size_t);
    90         void* allocate(MarkedSpace::SizeClass&);
     93
    9194        void notifyIsSafeToCollect() { m_isSafeToCollect = true; }
    9295        void collectAllGarbage();
     
    113116        template<typename Functor> typename Functor::ReturnType forEachProtectedCell(Functor&);
    114117        template<typename Functor> typename Functor::ReturnType forEachProtectedCell();
    115         template<typename Functor> typename Functor::ReturnType forEachCell(Functor&);
    116         template<typename Functor> typename Functor::ReturnType forEachCell();
    117         template<typename Functor> typename Functor::ReturnType forEachBlock(Functor&);
    118         template<typename Functor> typename Functor::ReturnType forEachBlock();
    119118       
    120119        HandleSlot allocateGlobalHandle() { return m_handleHeap.allocate(); }
     
    126125    private:
    127126        friend class MarkedBlock;
    128        
    129         typedef HashSet<MarkedBlock*>::iterator BlockIterator;
     127        friend class AllocationSpace;
    130128
    131129        static const size_t minExtraCost = 256;
    132130        static const size_t maxExtraCost = 1024 * 1024;
    133        
    134         enum AllocationEffort { AllocationMustSucceed, AllocationCanFail };
    135131       
    136132#if ENABLE(GGC)
     
    143139        void resetAllocator();
    144140
    145         MarkedBlock* allocateBlock(size_t cellSize, AllocationEffort);
    146141        void freeBlocks(MarkedBlock*);
    147142
     
    151146        void markTempSortVectors(HeapRootVisitor&);
    152147        void harvestWeakReferences();
    153 
    154         void* tryAllocate(MarkedSpace::SizeClass&);
    155         void* allocateSlowCase(MarkedSpace::SizeClass&);
    156148       
    157149        enum SweepToggle { DoNotSweep, DoSweep };
     
    174166       
    175167        OperationInProgress m_operationInProgress;
    176         MarkedSpace m_markedSpace;
    177         MarkedBlockSet m_blocks;
     168        AllocationSpace m_objectSpace;
    178169
    179170        DoublyLinkedList<MarkedBlock> m_freeBlocks;
     
    303294    }
    304295
    305     template<typename Functor> inline typename Functor::ReturnType Heap::forEachCell(Functor& functor)
    306     {
    307         canonicalizeBlocks();
    308         BlockIterator end = m_blocks.set().end();
    309         for (BlockIterator it = m_blocks.set().begin(); it != end; ++it)
    310             (*it)->forEachCell(functor);
    311         return functor.returnValue();
    312     }
    313 
    314     template<typename Functor> inline typename Functor::ReturnType Heap::forEachCell()
    315     {
    316         Functor functor;
    317         return forEachCell(functor);
    318     }
    319 
    320     template<typename Functor> inline typename Functor::ReturnType Heap::forEachBlock(Functor& functor)
    321     {
    322         canonicalizeBlocks();
    323         BlockIterator end = m_blocks.set().end();
    324         for (BlockIterator it = m_blocks.set().begin(); it != end; ++it)
    325             functor(*it);
    326         return functor.returnValue();
    327     }
    328 
    329     template<typename Functor> inline typename Functor::ReturnType Heap::forEachBlock()
    330     {
    331         Functor functor;
    332         return forEachBlock(functor);
    333     }
    334    
    335     inline MarkedSpace::SizeClass& Heap::sizeClassFor(size_t bytes)
    336     {
    337         return m_markedSpace.sizeClassFor(bytes);
    338     }
    339    
    340     inline void* Heap::allocate(MarkedSpace::SizeClass& sizeClass)
    341     {
    342         // This is a light-weight fast path to cover the most common case.
    343         MarkedBlock::FreeCell* firstFreeCell = sizeClass.firstFreeCell;
    344         if (UNLIKELY(!firstFreeCell))
    345             return allocateSlowCase(sizeClass);
    346        
    347         sizeClass.firstFreeCell = firstFreeCell->next;
    348         return firstFreeCell;
    349     }
    350 
    351296    inline void* Heap::allocate(size_t bytes)
    352297    {
    353298        ASSERT(isValidAllocation(bytes));
    354         MarkedSpace::SizeClass& sizeClass = sizeClassFor(bytes);
    355         return allocate(sizeClass);
     299        return m_objectSpace.allocate(bytes);
    356300    }
    357301
  • trunk/Source/JavaScriptCore/jit/JITInlineMethods.h

    r95507 r95559  
    395395template <typename ClassType, typename StructureType> inline void JIT::emitAllocateBasicJSObject(StructureType structure, void* vtable, RegisterID result, RegisterID storagePtr)
    396396{
    397     MarkedSpace::SizeClass* sizeClass = &m_globalData->heap.sizeClassFor(sizeof(ClassType));
     397    MarkedSpace::SizeClass* sizeClass = &m_globalData->heap.sizeClassForObject(sizeof(ClassType));
    398398    loadPtr(&sizeClass->firstFreeCell, result);
    399399    addSlowCase(branchTestPtr(Zero, result));
  • trunk/Source/JavaScriptCore/runtime/JSGlobalData.cpp

    r95510 r95559  
    448448    ASSERT(!dynamicGlobalObject);
    449449   
    450     heap.forEachCell<Recompiler>();
     450    heap.objectSpace().forEachCell<Recompiler>();
    451451}
    452452
     
    489489               
    490490        }
    491         heap.forEachCell<StackPreservingRecompiler>(recompiler);
     491        heap.objectSpace().forEachCell<StackPreservingRecompiler>(recompiler);
    492492    }
    493493    m_regExpCache->invalidateCode();
  • trunk/Source/WebCore/ChangeLog

    r95558 r95559  
     12011-09-19  Oliver Hunt  <oliver@apple.com>
     2
     3        Refactor Heap allocation logic into separate AllocationSpace class
     4        https://bugs.webkit.org/show_bug.cgi?id=68409
     5
     6        Reviewed by Gavin Barraclough.
     7
     8        Adding a forwarding header.
     9
     10        * ForwardingHeaders/heap/AllocationSpace.h: Added.
     11
    1122011-09-20  Geoffrey Garen  <ggaren@apple.com>
    213
Note: See TracChangeset for help on using the changeset viewer.