void CopiedSpace::didStartFullCollection() { ASSERT(heap()->operationInProgress() == FullCollection); ASSERT(m_oldGen.fromSpace->isEmpty()); ASSERT(m_newGen.fromSpace->isEmpty()); #ifndef NDEBUG for (CopiedBlock* block = m_newGen.toSpace->head(); block; block = block->next()) ASSERT(!block->liveBytes()); for (CopiedBlock* block = m_newGen.oversizeBlocks.head(); block; block = block->next()) ASSERT(!block->liveBytes()); #endif for (CopiedBlock* block = m_oldGen.toSpace->head(); block; block = block->next()) block->didSurviveGC(); for (CopiedBlock* block = m_oldGen.oversizeBlocks.head(); block; block = block->next()) block->didSurviveGC(); }
void CopiedSpace::startedCopying() { std::swap(m_fromSpace, m_toSpace); m_blockFilter.reset(); m_allocator.resetCurrentBlock(); CopiedBlock* next = 0; size_t totalLiveBytes = 0; size_t totalUsableBytes = 0; for (CopiedBlock* block = m_fromSpace->head(); block; block = next) { next = block->next(); if (!block->isPinned() && block->canBeRecycled()) { recycleEvacuatedBlock(block); continue; } totalLiveBytes += block->liveBytes(); totalUsableBytes += block->payloadCapacity(); } CopiedBlock* block = m_oversizeBlocks.head(); while (block) { CopiedBlock* next = block->next(); if (block->isPinned()) { m_blockFilter.add(reinterpret_cast<Bits>(block)); totalLiveBytes += block->payloadCapacity(); totalUsableBytes += block->payloadCapacity(); block->didSurviveGC(); } else { m_oversizeBlocks.remove(block); m_blockSet.remove(block); m_heap->blockAllocator().deallocateCustomSize(CopiedBlock::destroy(block)); } block = next; } double markedSpaceBytes = m_heap->objectSpace().capacity(); double totalFragmentation = ((double)totalLiveBytes + markedSpaceBytes) / ((double)totalUsableBytes + markedSpaceBytes); m_shouldDoCopyPhase = totalFragmentation <= Options::minHeapUtilization(); if (!m_shouldDoCopyPhase) return; ASSERT(m_shouldDoCopyPhase); ASSERT(!m_inCopyingPhase); ASSERT(!m_numberOfLoanedBlocks); m_inCopyingPhase = true; }