1 /* 2 * Copyright (C) 1999-2000 Harri Porten (porten@kde.org) 3 * Copyright (C) 2001 Peter Kelly (pmk@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 globalData()68 JSGlobalData* globalData() const { return m_globalData; } markedSpace()69 MarkedSpace& markedSpace() { return m_markedSpace; } machineThreads()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 markListSet()98 HashSet<MarkedArgumentBuffer*>& markListSet() { if (!m_markListSet) m_markListSet = new HashSet<MarkedArgumentBuffer*>; return *m_markListSet; } 99 100 template <typename Functor> void forEach(Functor&); 101 allocateGlobalHandle()102 HandleSlot allocateGlobalHandle() { return m_handleHeap.allocate(); } allocateLocalHandle()103 HandleSlot allocateLocalHandle() { return m_handleStack.push(); } 104 handleStack()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 isMarked(const JSCell * cell)145 inline bool Heap::isMarked(const JSCell* cell) 146 { 147 return MarkedSpace::isMarked(cell); 148 } 149 testAndSetMarked(const JSCell * cell)150 inline bool Heap::testAndSetMarked(const JSCell* cell) 151 { 152 return MarkedSpace::testAndSetMarked(cell); 153 } 154 setMarked(JSCell * cell)155 inline void Heap::setMarked(JSCell* cell) 156 { 157 MarkedSpace::setMarked(cell); 158 } 159 contains(void * p)160 inline bool Heap::contains(void* p) 161 { 162 return m_markedSpace.contains(p); 163 } 164 reportExtraMemoryCost(size_t cost)165 inline void Heap::reportExtraMemoryCost(size_t cost) 166 { 167 if (cost > minExtraCost) 168 reportExtraMemoryCostSlowCase(cost); 169 } 170 forEach(Functor & functor)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