| 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 253 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 264 page->countObjectsToSweep(classAgeCounts); | 264 page->countObjectsToSweep(classAgeCounts); |
| 265 } | 265 } |
| 266 | 266 |
| 267 void BaseHeap::incrementMarkedObjectsAge() | 267 void BaseHeap::incrementMarkedObjectsAge() |
| 268 { | 268 { |
| 269 for (BasePage* page = m_firstPage; page; page = page->next()) | 269 for (BasePage* page = m_firstPage; page; page = page->next()) |
| 270 page->incrementMarkedObjectsAge(); | 270 page->incrementMarkedObjectsAge(); |
| 271 } | 271 } |
| 272 #endif | 272 #endif |
| 273 | 273 |
| 274 void BaseHeap::makeConsistentForSweeping() | 274 void BaseHeap::makeConsistentForSweeping(ThreadState::GCType gcType) |
| 275 { | 275 { |
| 276 clearFreeLists(); | 276 // We don't want to clear free lists when taking a snapshot. |
| 277 ASSERT(isConsistentForSweeping()); | 277 // This is fine because we don't sweep anything when taking a snapshot. |
| 278 if (gcType != ThreadState::TakeSnapshot) { |
| 279 clearFreeLists(); |
| 280 ASSERT(isConsistentForSweeping()); |
| 281 } |
| 282 |
| 278 for (BasePage* page = m_firstPage; page; page = page->next()) | 283 for (BasePage* page = m_firstPage; page; page = page->next()) |
| 279 page->markAsUnswept(); | 284 page->markAsUnswept(); |
| 280 | 285 |
| 281 // If a new GC is requested before this thread got around to sweep, | 286 // If a new GC is requested before this thread got around to sweep, |
| 282 // ie. due to the thread doing a long running operation, we clear | 287 // ie. due to the thread doing a long running operation, we clear |
| 283 // the mark bits and mark any of the dead objects as dead. The latter | 288 // the mark bits and mark any of the dead objects as dead. The latter |
| 284 // is used to ensure the next GC marking does not trace already dead | 289 // is used to ensure the next GC marking does not trace already dead |
| 285 // objects. If we trace a dead object we could end up tracing into | 290 // objects. If we trace a dead object we could end up tracing into |
| 286 // garbage or the middle of another object via the newly conservatively | 291 // garbage or the middle of another object via the newly conservatively |
| 287 // found object. | 292 // found object. |
| (...skipping 25 matching lines...) Expand all Loading... |
| 313 void BaseHeap::prepareHeapForTermination() | 318 void BaseHeap::prepareHeapForTermination() |
| 314 { | 319 { |
| 315 ASSERT(!m_firstUnsweptPage); | 320 ASSERT(!m_firstUnsweptPage); |
| 316 for (BasePage* page = m_firstPage; page; page = page->next()) { | 321 for (BasePage* page = m_firstPage; page; page = page->next()) { |
| 317 page->setTerminating(); | 322 page->setTerminating(); |
| 318 } | 323 } |
| 319 } | 324 } |
| 320 | 325 |
| 321 void BaseHeap::prepareForSweep() | 326 void BaseHeap::prepareForSweep() |
| 322 { | 327 { |
| 323 ASSERT(!threadState()->isInGC()); | 328 ASSERT(threadState()->isInGC()); |
| 324 ASSERT(!m_firstUnsweptPage); | 329 ASSERT(!m_firstUnsweptPage); |
| 325 | 330 |
| 326 // Move all pages to a list of unswept pages. | 331 // Move all pages to a list of unswept pages. |
| 327 m_firstUnsweptPage = m_firstPage; | 332 m_firstUnsweptPage = m_firstPage; |
| 328 m_firstPage = nullptr; | 333 m_firstPage = nullptr; |
| 329 } | 334 } |
| 330 | 335 |
| 331 #if defined(ADDRESS_SANITIZER) | 336 #if defined(ADDRESS_SANITIZER) |
| 332 void BaseHeap::poisonUnmarkedObjects() | 337 void BaseHeap::poisonUnmarkedObjects() |
| 333 { | 338 { |
| (...skipping 1500 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1834 } | 1839 } |
| 1835 | 1840 |
| 1836 #if ENABLE(ASSERT) | 1841 #if ENABLE(ASSERT) |
| 1837 bool Heap::weakTableRegistered(const void* table) | 1842 bool Heap::weakTableRegistered(const void* table) |
| 1838 { | 1843 { |
| 1839 ASSERT(s_ephemeronStack); | 1844 ASSERT(s_ephemeronStack); |
| 1840 return s_ephemeronStack->hasCallbackForObject(table); | 1845 return s_ephemeronStack->hasCallbackForObject(table); |
| 1841 } | 1846 } |
| 1842 #endif | 1847 #endif |
| 1843 | 1848 |
| 1844 void Heap::preGC() | 1849 void Heap::preGC(ThreadState::GCType gcType) |
| 1845 { | 1850 { |
| 1846 ASSERT(!ThreadState::current()->isInGC()); | 1851 ASSERT(!ThreadState::current()->isInGC()); |
| 1847 for (ThreadState* state : ThreadState::attachedThreads()) | 1852 for (ThreadState* state : ThreadState::attachedThreads()) |
| 1848 state->preGC(); | 1853 state->preGC(gcType); |
| 1849 } | 1854 } |
| 1850 | 1855 |
| 1851 void Heap::postGC(ThreadState::GCType gcType) | 1856 void Heap::postGC(ThreadState::GCType gcType) |
| 1852 { | 1857 { |
| 1853 ASSERT(ThreadState::current()->isInGC()); | 1858 ASSERT(ThreadState::current()->isInGC()); |
| 1854 for (ThreadState* state : ThreadState::attachedThreads()) | 1859 for (ThreadState* state : ThreadState::attachedThreads()) |
| 1855 state->postGC(gcType); | 1860 state->postGC(gcType); |
| 1856 } | 1861 } |
| 1857 | 1862 |
| 1858 const char* Heap::gcReasonString(GCReason reason) | 1863 const char* Heap::gcReasonString(GCReason reason) |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1897 TRACE_EVENT_SCOPED_SAMPLING_STATE("blink_gc", "BlinkGC"); | 1902 TRACE_EVENT_SCOPED_SAMPLING_STATE("blink_gc", "BlinkGC"); |
| 1898 double timeStamp = WTF::currentTimeMS(); | 1903 double timeStamp = WTF::currentTimeMS(); |
| 1899 #if ENABLE(GC_PROFILING) | 1904 #if ENABLE(GC_PROFILING) |
| 1900 static_cast<MarkingVisitor<Visitor::GlobalMarking>*>(s_markingVisitor)->obje
ctGraph().clear(); | 1905 static_cast<MarkingVisitor<Visitor::GlobalMarking>*>(s_markingVisitor)->obje
ctGraph().clear(); |
| 1901 #endif | 1906 #endif |
| 1902 | 1907 |
| 1903 // Disallow allocation during garbage collection (but not during the | 1908 // Disallow allocation during garbage collection (but not during the |
| 1904 // finalization that happens when the gcScope is torn down). | 1909 // finalization that happens when the gcScope is torn down). |
| 1905 ThreadState::NoAllocationScope noAllocationScope(state); | 1910 ThreadState::NoAllocationScope noAllocationScope(state); |
| 1906 | 1911 |
| 1907 preGC(); | 1912 preGC(gcType); |
| 1908 | 1913 |
| 1909 StackFrameDepthScope stackDepthScope; | 1914 StackFrameDepthScope stackDepthScope; |
| 1910 | 1915 |
| 1911 size_t totalObjectSize = Heap::allocatedObjectSize() + Heap::markedObjectSiz
e(); | 1916 size_t totalObjectSize = Heap::allocatedObjectSize() + Heap::markedObjectSiz
e(); |
| 1912 Heap::resetHeapCounters(); | 1917 Heap::resetHeapCounters(); |
| 1913 | 1918 |
| 1914 // 1. Trace persistent roots. | 1919 // 1. Trace persistent roots. |
| 1915 ThreadState::visitPersistentRoots(s_markingVisitor); | 1920 ThreadState::visitPersistentRoots(s_markingVisitor); |
| 1916 | 1921 |
| 1917 // 2. Trace objects reachable from the persistent roots including | 1922 // 2. Trace objects reachable from the persistent roots including |
| (...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1958 | 1963 |
| 1959 void Heap::collectGarbageForTerminatingThread(ThreadState* state) | 1964 void Heap::collectGarbageForTerminatingThread(ThreadState* state) |
| 1960 { | 1965 { |
| 1961 // We explicitly do not enter a safepoint while doing thread specific | 1966 // We explicitly do not enter a safepoint while doing thread specific |
| 1962 // garbage collection since we don't want to allow a global GC at the | 1967 // garbage collection since we don't want to allow a global GC at the |
| 1963 // same time as a thread local GC. | 1968 // same time as a thread local GC. |
| 1964 { | 1969 { |
| 1965 MarkingVisitor<Visitor::ThreadLocalMarking> markingVisitor; | 1970 MarkingVisitor<Visitor::ThreadLocalMarking> markingVisitor; |
| 1966 ThreadState::NoAllocationScope noAllocationScope(state); | 1971 ThreadState::NoAllocationScope noAllocationScope(state); |
| 1967 | 1972 |
| 1968 state->preGC(); | 1973 state->preGC(ThreadState::GCWithSweep); |
| 1969 StackFrameDepthScope stackDepthScope; | 1974 StackFrameDepthScope stackDepthScope; |
| 1970 | 1975 |
| 1971 // 1. Trace the thread local persistent roots. For thread local GCs we | 1976 // 1. Trace the thread local persistent roots. For thread local GCs we |
| 1972 // don't trace the stack (ie. no conservative scanning) since this is | 1977 // don't trace the stack (ie. no conservative scanning) since this is |
| 1973 // only called during thread shutdown where there should be no objects | 1978 // only called during thread shutdown where there should be no objects |
| 1974 // on the stack. | 1979 // on the stack. |
| 1975 // We also assume that orphaned pages have no objects reachable from | 1980 // We also assume that orphaned pages have no objects reachable from |
| 1976 // persistent handles on other threads or CrossThreadPersistents. The | 1981 // persistent handles on other threads or CrossThreadPersistents. The |
| 1977 // only cases where this could happen is if a subsequent conservative | 1982 // only cases where this could happen is if a subsequent conservative |
| 1978 // global GC finds a "pointer" on the stack or due to a programming | 1983 // global GC finds a "pointer" on the stack or due to a programming |
| (...skipping 114 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2093 Platform::current()->histogramEnumeration("BlinkGC.CommittedSize", sizeI
nMB, supportedMaxSizeInMB); | 2098 Platform::current()->histogramEnumeration("BlinkGC.CommittedSize", sizeI
nMB, supportedMaxSizeInMB); |
| 2094 observedMaxSizeInMB = sizeInMB; | 2099 observedMaxSizeInMB = sizeInMB; |
| 2095 } | 2100 } |
| 2096 } | 2101 } |
| 2097 | 2102 |
| 2098 size_t Heap::objectPayloadSizeForTesting() | 2103 size_t Heap::objectPayloadSizeForTesting() |
| 2099 { | 2104 { |
| 2100 size_t objectPayloadSize = 0; | 2105 size_t objectPayloadSize = 0; |
| 2101 for (ThreadState* state : ThreadState::attachedThreads()) { | 2106 for (ThreadState* state : ThreadState::attachedThreads()) { |
| 2102 state->setGCState(ThreadState::GCRunning); | 2107 state->setGCState(ThreadState::GCRunning); |
| 2103 state->makeConsistentForSweeping(); | 2108 state->makeConsistentForSweeping(ThreadState::GCWithSweep); |
| 2104 objectPayloadSize += state->objectPayloadSizeForTesting(); | 2109 objectPayloadSize += state->objectPayloadSizeForTesting(); |
| 2105 state->setGCState(ThreadState::EagerSweepScheduled); | 2110 state->setGCState(ThreadState::EagerSweepScheduled); |
| 2106 state->setGCState(ThreadState::Sweeping); | 2111 state->setGCState(ThreadState::Sweeping); |
| 2107 state->setGCState(ThreadState::NoGCScheduled); | 2112 state->setGCState(ThreadState::NoGCScheduled); |
| 2108 } | 2113 } |
| 2109 return objectPayloadSize; | 2114 return objectPayloadSize; |
| 2110 } | 2115 } |
| 2111 | 2116 |
| 2112 BasePage* Heap::lookup(Address address) | 2117 BasePage* Heap::lookup(Address address) |
| 2113 { | 2118 { |
| (...skipping 109 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2223 size_t Heap::s_allocatedObjectSize = 0; | 2228 size_t Heap::s_allocatedObjectSize = 0; |
| 2224 size_t Heap::s_allocatedSpace = 0; | 2229 size_t Heap::s_allocatedSpace = 0; |
| 2225 size_t Heap::s_markedObjectSize = 0; | 2230 size_t Heap::s_markedObjectSize = 0; |
| 2226 // We don't want to use 0 KB for the initial value because it may end up | 2231 // We don't want to use 0 KB for the initial value because it may end up |
| 2227 // triggering the first GC of some thread too prematurely. | 2232 // triggering the first GC of some thread too prematurely. |
| 2228 size_t Heap::s_estimatedLiveObjectSize = 512 * 1024; | 2233 size_t Heap::s_estimatedLiveObjectSize = 512 * 1024; |
| 2229 size_t Heap::s_externalObjectSizeAtLastGC = 0; | 2234 size_t Heap::s_externalObjectSizeAtLastGC = 0; |
| 2230 double Heap::s_estimatedMarkingTimePerByte = 0.0; | 2235 double Heap::s_estimatedMarkingTimePerByte = 0.0; |
| 2231 | 2236 |
| 2232 } // namespace blink | 2237 } // namespace blink |
| OLD | NEW |