Home | History | Annotate | Download | only in heap
      1 /*
      2  *  Copyright (C) 1999-2000 Harri Porten (porten (at) kde.org)
      3  *  Copyright (C) 2001 Peter Kelly (pmk (at) post.com)
      4  *  Copyright (C) 2003, 2004, 2005, 2006, 2007, 2008, 2009 Apple Inc. All rights reserved.
      5  *
      6  *  This library is free software; you can redistribute it and/or
      7  *  modify it under the terms of the GNU Lesser General Public
      8  *  License as published by the Free Software Foundation; either
      9  *  version 2 of the License, or (at your option) any later version.
     10  *
     11  *  This library is distributed in the hope that it will be useful,
     12  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
     13  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
     14  *  Lesser General Public License for more details.
     15  *
     16  *  You should have received a copy of the GNU Lesser General Public
     17  *  License along with this library; if not, write to the Free Software
     18  *  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
     19  *
     20  */
     21 
     22 #ifndef Heap_h
     23 #define Heap_h
     24 
     25 #include "HandleHeap.h"
     26 #include "HandleStack.h"
     27 #include "MarkStack.h"
     28 #include "MarkedSpace.h"
     29 #include <wtf/Forward.h>
     30 #include <wtf/HashCountedSet.h>
     31 #include <wtf/HashSet.h>
     32 
     33 namespace JSC {
     34 
     35     class GCActivityCallback;
     36     class GlobalCodeBlock;
     37     class HeapRootMarker;
     38     class JSCell;
     39     class JSGlobalData;
     40     class JSValue;
     41     class LiveObjectIterator;
     42     class MarkStack;
     43     class MarkedArgumentBuffer;
     44     class RegisterFile;
     45     class UString;
     46     class WeakGCHandlePool;
     47 
     48     typedef std::pair<JSValue, UString> ValueStringPair;
     49     typedef HashCountedSet<JSCell*> ProtectCountSet;
     50     typedef HashCountedSet<const char*> TypeCountSet;
     51 
     52     enum OperationInProgress { NoOperation, Allocation, Collection };
     53 
     54     class Heap {
     55         WTF_MAKE_NONCOPYABLE(Heap);
     56     public:
     57         static Heap* heap(JSValue); // 0 for immediate values
     58         static Heap* heap(JSCell*);
     59 
     60         static bool isMarked(const JSCell*);
     61         static bool testAndSetMarked(const JSCell*);
     62         static void setMarked(JSCell*);
     63 
     64         Heap(JSGlobalData*);
     65         ~Heap();
     66         void destroy(); // JSGlobalData must call destroy() before ~Heap().
     67 
     68         JSGlobalData* globalData() const { return m_globalData; }
     69         MarkedSpace& markedSpace() { return m_markedSpace; }
     70         MachineThreads& machineThreads() { return m_machineThreads; }
     71 
     72         GCActivityCallback* activityCallback();
     73         void setActivityCallback(PassOwnPtr<GCActivityCallback>);
     74 
     75         bool isBusy(); // true if an allocation or collection is in progress
     76         void* allocate(size_t);
     77         void collectAllGarbage();
     78 
     79         void reportExtraMemoryCost(size_t cost);
     80 
     81         void protect(JSValue);
     82         bool unprotect(JSValue); // True when the protect count drops to 0.
     83 
     84         bool contains(void*);
     85 
     86         size_t size() const;
     87         size_t capacity() const;
     88         size_t objectCount() const;
     89         size_t globalObjectCount();
     90         size_t protectedObjectCount();
     91         size_t protectedGlobalObjectCount();
     92         PassOwnPtr<TypeCountSet> protectedObjectTypeCounts();
     93         PassOwnPtr<TypeCountSet> objectTypeCounts();
     94 
     95         void pushTempSortVector(Vector<ValueStringPair>*);
     96         void popTempSortVector(Vector<ValueStringPair>*);
     97 
     98         HashSet<MarkedArgumentBuffer*>& markListSet() { if (!m_markListSet) m_markListSet = new HashSet<MarkedArgumentBuffer*>; return *m_markListSet; }
     99 
    100         template <typename Functor> void forEach(Functor&);
    101 
    102         HandleSlot allocateGlobalHandle() { return m_handleHeap.allocate(); }
    103         HandleSlot allocateLocalHandle() { return m_handleStack.push(); }
    104 
    105         HandleStack* handleStack() { return &m_handleStack; }
    106 
    107     private:
    108         friend class JSGlobalData;
    109 
    110         static const size_t minExtraCost = 256;
    111         static const size_t maxExtraCost = 1024 * 1024;
    112 
    113         void* allocateSlowCase(size_t);
    114         void reportExtraMemoryCostSlowCase(size_t);
    115 
    116         void markRoots();
    117         void markProtectedObjects(HeapRootMarker&);
    118         void markTempSortVectors(HeapRootMarker&);
    119 
    120         enum SweepToggle { DoNotSweep, DoSweep };
    121         void reset(SweepToggle);
    122 
    123         RegisterFile& registerFile();
    124 
    125         OperationInProgress m_operationInProgress;
    126         MarkedSpace m_markedSpace;
    127 
    128         ProtectCountSet m_protectedValues;
    129         Vector<Vector<ValueStringPair>* > m_tempSortingVectors;
    130 
    131         HashSet<MarkedArgumentBuffer*>* m_markListSet;
    132 
    133         OwnPtr<GCActivityCallback> m_activityCallback;
    134 
    135         JSGlobalData* m_globalData;
    136 
    137         MachineThreads m_machineThreads;
    138         MarkStack m_markStack;
    139         HandleHeap m_handleHeap;
    140         HandleStack m_handleStack;
    141 
    142         size_t m_extraCost;
    143     };
    144 
    145     inline bool Heap::isMarked(const JSCell* cell)
    146     {
    147         return MarkedSpace::isMarked(cell);
    148     }
    149 
    150     inline bool Heap::testAndSetMarked(const JSCell* cell)
    151     {
    152         return MarkedSpace::testAndSetMarked(cell);
    153     }
    154 
    155     inline void Heap::setMarked(JSCell* cell)
    156     {
    157         MarkedSpace::setMarked(cell);
    158     }
    159 
    160     inline bool Heap::contains(void* p)
    161     {
    162         return m_markedSpace.contains(p);
    163     }
    164 
    165     inline void Heap::reportExtraMemoryCost(size_t cost)
    166     {
    167         if (cost > minExtraCost)
    168             reportExtraMemoryCostSlowCase(cost);
    169     }
    170 
    171     template <typename Functor> inline void Heap::forEach(Functor& functor)
    172     {
    173         m_markedSpace.forEach(functor);
    174     }
    175 
    176 } // namespace JSC
    177 
    178 #endif // Heap_h
    179