OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 2013 Google Inc. All rights reserved. | 2 * Copyright (C) 2013 Google Inc. All rights reserved. |
3 * | 3 * |
4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
5 * modification, are permitted provided that the following conditions are | 5 * modification, are permitted provided that the following conditions are |
6 * met: | 6 * met: |
7 * | 7 * |
8 * * Redistributions of source code must retain the above copyright | 8 * * Redistributions of source code must retain the above copyright |
9 * notice, this list of conditions and the following disclaimer. | 9 * notice, this list of conditions and the following disclaimer. |
10 * * Redistributions in binary form must reproduce the above | 10 * * Redistributions in binary form must reproduce the above |
(...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
124 #if defined(LEAK_SANITIZER) | 124 #if defined(LEAK_SANITIZER) |
125 m_disabledStaticPersistentsRegistration(0), | 125 m_disabledStaticPersistentsRegistration(0), |
126 #endif | 126 #endif |
127 m_allocatedObjectSize(0), | 127 m_allocatedObjectSize(0), |
128 m_markedObjectSize(0), | 128 m_markedObjectSize(0), |
129 m_reportedMemoryToV8(0) { | 129 m_reportedMemoryToV8(0) { |
130 ASSERT(checkThread()); | 130 ASSERT(checkThread()); |
131 ASSERT(!**s_threadSpecific); | 131 ASSERT(!**s_threadSpecific); |
132 **s_threadSpecific = this; | 132 **s_threadSpecific = this; |
133 | 133 |
134 m_heap = new ThreadHeap(); | 134 m_heap = WTF::wrapUnique(new ThreadHeap(this)); |
135 ASSERT(m_heap); | |
136 m_heap->attach(this); | |
137 | 135 |
138 for (int arenaIndex = 0; arenaIndex < BlinkGC::LargeObjectArenaIndex; | 136 for (int arenaIndex = 0; arenaIndex < BlinkGC::LargeObjectArenaIndex; |
139 arenaIndex++) | 137 arenaIndex++) |
140 m_arenas[arenaIndex] = new NormalPageArena(this, arenaIndex); | 138 m_arenas[arenaIndex] = new NormalPageArena(this, arenaIndex); |
141 m_arenas[BlinkGC::LargeObjectArenaIndex] = | 139 m_arenas[BlinkGC::LargeObjectArenaIndex] = |
142 new LargeObjectArena(this, BlinkGC::LargeObjectArenaIndex); | 140 new LargeObjectArena(this, BlinkGC::LargeObjectArenaIndex); |
143 | 141 |
144 m_likelyToBePromptlyFreed = | 142 m_likelyToBePromptlyFreed = |
145 wrapArrayUnique(new int[likelyToBePromptlyFreedArraySize]); | 143 wrapArrayUnique(new int[likelyToBePromptlyFreedArraySize]); |
146 clearArenaAges(); | 144 clearArenaAges(); |
147 } | 145 } |
148 | 146 |
149 ThreadState::~ThreadState() { | 147 ThreadState::~ThreadState() { |
150 ASSERT(checkThread()); | 148 ASSERT(checkThread()); |
| 149 if (isMainThread()) |
| 150 DCHECK_EQ(heap().heapStats().allocatedSpace(), 0u); |
| 151 CHECK(gcState() == ThreadState::NoGCScheduled); |
| 152 |
151 for (int i = 0; i < BlinkGC::NumberOfArenas; ++i) | 153 for (int i = 0; i < BlinkGC::NumberOfArenas; ++i) |
152 delete m_arenas[i]; | 154 delete m_arenas[i]; |
153 | 155 |
154 **s_threadSpecific = nullptr; | 156 **s_threadSpecific = nullptr; |
155 } | 157 } |
156 | 158 |
157 void ThreadState::attachMainThread() { | 159 void ThreadState::attachMainThread() { |
158 s_threadSpecific = new WTF::ThreadSpecific<ThreadState*>(); | 160 s_threadSpecific = new WTF::ThreadSpecific<ThreadState*>(); |
159 new (s_mainThreadStateStorage) ThreadState(); | 161 new (s_mainThreadStateStorage) ThreadState(); |
160 } | 162 } |
161 | 163 |
162 void ThreadState::attachCurrentThread() { | 164 void ThreadState::attachCurrentThread() { |
163 new ThreadState(); | 165 new ThreadState(); |
164 } | 166 } |
165 | 167 |
| 168 void ThreadState::detachCurrentThread() { |
| 169 ThreadState* state = current(); |
| 170 state->runTerminationGC(); |
| 171 delete state; |
| 172 } |
| 173 |
166 void ThreadState::removeAllPages() { | 174 void ThreadState::removeAllPages() { |
167 ASSERT(checkThread()); | 175 ASSERT(checkThread()); |
168 for (int i = 0; i < BlinkGC::NumberOfArenas; ++i) | 176 for (int i = 0; i < BlinkGC::NumberOfArenas; ++i) |
169 m_arenas[i]->removeAllPages(); | 177 m_arenas[i]->removeAllPages(); |
170 } | 178 } |
171 | 179 |
172 void ThreadState::runTerminationGC() { | 180 void ThreadState::runTerminationGC() { |
173 if (isMainThread()) { | 181 if (isMainThread()) { |
174 removeAllPages(); | 182 removeAllPages(); |
175 return; | 183 return; |
(...skipping 25 matching lines...) Expand all Loading... |
201 // We should not have any persistents left when getting to this point, | 209 // We should not have any persistents left when getting to this point, |
202 // if we have it is probably a bug so adding a debug ASSERT to catch this. | 210 // if we have it is probably a bug so adding a debug ASSERT to catch this. |
203 ASSERT(!currentCount); | 211 ASSERT(!currentCount); |
204 // All of pre-finalizers should be consumed. | 212 // All of pre-finalizers should be consumed. |
205 ASSERT(m_orderedPreFinalizers.isEmpty()); | 213 ASSERT(m_orderedPreFinalizers.isEmpty()); |
206 RELEASE_ASSERT(gcState() == NoGCScheduled); | 214 RELEASE_ASSERT(gcState() == NoGCScheduled); |
207 | 215 |
208 removeAllPages(); | 216 removeAllPages(); |
209 } | 217 } |
210 | 218 |
211 void ThreadState::detachCurrentThread() { | |
212 ThreadState* state = current(); | |
213 state->heap().detach(state); | |
214 RELEASE_ASSERT(state->gcState() == ThreadState::NoGCScheduled); | |
215 delete state; | |
216 } | |
217 | |
218 NO_SANITIZE_ADDRESS | 219 NO_SANITIZE_ADDRESS |
219 void ThreadState::visitAsanFakeStackForPointer(Visitor* visitor, Address ptr) { | 220 void ThreadState::visitAsanFakeStackForPointer(Visitor* visitor, Address ptr) { |
220 #if defined(ADDRESS_SANITIZER) | 221 #if defined(ADDRESS_SANITIZER) |
221 Address* start = reinterpret_cast<Address*>(m_startOfStack); | 222 Address* start = reinterpret_cast<Address*>(m_startOfStack); |
222 Address* end = reinterpret_cast<Address*>(m_endOfStack); | 223 Address* end = reinterpret_cast<Address*>(m_endOfStack); |
223 Address* fakeFrameStart = nullptr; | 224 Address* fakeFrameStart = nullptr; |
224 Address* fakeFrameEnd = nullptr; | 225 Address* fakeFrameEnd = nullptr; |
225 Address* maybeFakeFrame = reinterpret_cast<Address*>(ptr); | 226 Address* maybeFakeFrame = reinterpret_cast<Address*>(ptr); |
226 Address* realFrameForFakeFrame = reinterpret_cast<Address*>( | 227 Address* realFrameForFakeFrame = reinterpret_cast<Address*>( |
227 __asan_addr_is_in_fake_stack(m_asanFakeStack, maybeFakeFrame, | 228 __asan_addr_is_in_fake_stack(m_asanFakeStack, maybeFakeFrame, |
(...skipping 1021 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1249 void ThreadState::enterStaticReferenceRegistrationDisabledScope() { | 1250 void ThreadState::enterStaticReferenceRegistrationDisabledScope() { |
1250 m_disabledStaticPersistentsRegistration++; | 1251 m_disabledStaticPersistentsRegistration++; |
1251 } | 1252 } |
1252 | 1253 |
1253 void ThreadState::leaveStaticReferenceRegistrationDisabledScope() { | 1254 void ThreadState::leaveStaticReferenceRegistrationDisabledScope() { |
1254 ASSERT(m_disabledStaticPersistentsRegistration); | 1255 ASSERT(m_disabledStaticPersistentsRegistration); |
1255 m_disabledStaticPersistentsRegistration--; | 1256 m_disabledStaticPersistentsRegistration--; |
1256 } | 1257 } |
1257 #endif | 1258 #endif |
1258 | 1259 |
1259 void ThreadState::lockThreadAttachMutex() { | |
1260 m_heap->threadAttachMutex().lock(); | |
1261 } | |
1262 | |
1263 void ThreadState::unlockThreadAttachMutex() { | |
1264 m_heap->threadAttachMutex().unlock(); | |
1265 } | |
1266 | |
1267 void ThreadState::invokePreFinalizers() { | 1260 void ThreadState::invokePreFinalizers() { |
1268 ASSERT(checkThread()); | 1261 ASSERT(checkThread()); |
1269 ASSERT(!sweepForbidden()); | 1262 ASSERT(!sweepForbidden()); |
1270 TRACE_EVENT0("blink_gc", "ThreadState::invokePreFinalizers"); | 1263 TRACE_EVENT0("blink_gc", "ThreadState::invokePreFinalizers"); |
1271 | 1264 |
1272 SweepForbiddenScope sweepForbidden(this); | 1265 SweepForbiddenScope sweepForbidden(this); |
1273 ScriptForbiddenIfMainThreadScope scriptForbidden; | 1266 ScriptForbiddenIfMainThreadScope scriptForbidden; |
1274 | 1267 |
1275 double startTime = WTF::currentTimeMS(); | 1268 double startTime = WTF::currentTimeMS(); |
1276 if (!m_orderedPreFinalizers.isEmpty()) { | 1269 if (!m_orderedPreFinalizers.isEmpty()) { |
(...skipping 279 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1556 collectGarbage(BlinkGC::NoHeapPointersOnStack, BlinkGC::GCWithSweep, | 1549 collectGarbage(BlinkGC::NoHeapPointersOnStack, BlinkGC::GCWithSweep, |
1557 BlinkGC::ForcedGC); | 1550 BlinkGC::ForcedGC); |
1558 size_t liveObjects = heap().heapStats().markedObjectSize(); | 1551 size_t liveObjects = heap().heapStats().markedObjectSize(); |
1559 if (liveObjects == previousLiveObjects) | 1552 if (liveObjects == previousLiveObjects) |
1560 break; | 1553 break; |
1561 previousLiveObjects = liveObjects; | 1554 previousLiveObjects = liveObjects; |
1562 } | 1555 } |
1563 } | 1556 } |
1564 | 1557 |
1565 } // namespace blink | 1558 } // namespace blink |
OLD | NEW |