NO_SANITIZE_ADDRESS void OrphanedPagePool::decommitOrphanedPages() { ASSERT(ThreadState::current()->isInGC()); ASSERT(ThreadState::current()->heap().isAtSafePoint()); for (int index = 0; index < BlinkGC::NumberOfArenas; ++index) { PoolEntry* entry = m_pool[index]; PoolEntry** prevNext = &m_pool[index]; while (entry) { BasePage* page = entry->data; // Check if we should reuse the memory or just free it. // Large object memory is not reused but freed, normal blink heap // pages are reused. // NOTE: We call the destructor before freeing or adding to the // free page pool. PageMemory* memory = page->storage(); if (page->isLargeObjectPage()) { page->~BasePage(); delete memory; } else { page->~BasePage(); clearMemory(memory); ThreadHeap::mainThreadHeap()->getFreePagePool()->addFreePage(index, memory); } PoolEntry* deadEntry = entry; entry = entry->next; *prevNext = entry; delete deadEntry; } } }
bool OrphanedPagePool::contains(void* object) { for (int index = 0; index < BlinkGC::NumberOfArenas; ++index) { for (PoolEntry* entry = m_pool[index]; entry; entry = entry->next) { BasePage* page = entry->data; if (page->contains(reinterpret_cast<Address>(object))) return true; } } return false; }
void assertObjectHasGCInfo(const void* payload, size_t gcInfoIndex) { ASSERT(HeapObjectHeader::fromPayload(payload)->checkHeader()); #if !defined(COMPONENT_BUILD) // On component builds we cannot compare the gcInfos as they are statically // defined in each of the components and hence will not match. BasePage* page = pageFromObject(payload); ASSERT(!page->orphaned()); ASSERT(HeapObjectHeader::fromPayload(payload)->gcInfoIndex() == gcInfoIndex); #endif }
OrphanedPagePool::~OrphanedPagePool() { for (int index = 0; index < BlinkGC::NumberOfArenas; ++index) { while (PoolEntry* entry = m_pool[index]) { m_pool[index] = entry->next; BasePage* page = entry->data; delete entry; PageMemory* memory = page->storage(); ASSERT(memory); page->~BasePage(); delete memory; } } }
NO_SANITIZE_ADDRESS void OrphanedPagePool::decommitOrphanedPages() { ASSERT(ThreadState::current()->isInGC()); #if ENABLE(ASSERT) // No locking needed as all threads are at safepoints at this point in time. for (ThreadState* state : ThreadState::attachedThreads()) ASSERT(state->isAtSafePoint()); #endif for (int index = 0; index < BlinkGC::NumberOfHeaps; ++index) { PoolEntry* entry = m_pool[index]; PoolEntry** prevNext = &m_pool[index]; while (entry) { BasePage* page = entry->data; // Check if we should reuse the memory or just free it. // Large object memory is not reused but freed, normal blink heap // pages are reused. // NOTE: We call the destructor before freeing or adding to the // free page pool. PageMemory* memory = page->storage(); if (page->isLargeObjectPage()) { page->~BasePage(); delete memory; } else { page->~BasePage(); clearMemory(memory); Heap::freePagePool()->addFreePage(index, memory); } PoolEntry* deadEntry = entry; entry = entry->next; *prevNext = entry; delete deadEntry; } } }
httpStatus BasePage::Import(BasePage &p) { m_outstream << p(m_request, m_tagStack.size(), true); return p.getStatus(); }