예제 #1
0
void WeakBlock::visit(HeapRootVisitor& heapRootVisitor)
{
    // If a block is completely empty, a visit won't have any effect.
    if (isEmpty())
        return;

    // If this WeakBlock doesn't belong to a MarkedBlock, we won't even be here.
    ASSERT(m_markedBlock);

    if (m_markedBlock->isAllocated())
        return;

    SlotVisitor& visitor = heapRootVisitor.visitor();

    for (size_t i = 0; i < weakImplCount(); ++i) {
        WeakImpl* weakImpl = &weakImpls()[i];
        if (weakImpl->state() != WeakImpl::Live)
            continue;

        const JSValue& jsValue = weakImpl->jsValue();
        if (m_markedBlock->isMarkedOrNewlyAllocated(jsValue.asCell()))
            continue;

        WeakHandleOwner* weakHandleOwner = weakImpl->weakHandleOwner();
        if (!weakHandleOwner)
            continue;

        if (!weakHandleOwner->isReachableFromOpaqueRoots(Handle<Unknown>::wrapSlot(&const_cast<JSValue&>(jsValue)), weakImpl->context(), visitor))
            continue;

        heapRootVisitor.visit(&const_cast<JSValue&>(jsValue));
    }
}
예제 #2
0
void WeakBlock::reap()
{
    // If a block is completely empty, a reaping won't have any effect.
    if (isEmpty())
        return;

    // If this WeakBlock doesn't belong to a MarkedBlock, we won't even be here.
    ASSERT(m_markedBlock);

    if (m_markedBlock->isAllocated())
        return;

    for (size_t i = 0; i < weakImplCount(); ++i) {
        WeakImpl* weakImpl = &weakImpls()[i];
        if (weakImpl->state() > WeakImpl::Dead)
            continue;

        if (m_markedBlock->isMarkedOrNewlyAllocated(weakImpl->jsValue().asCell())) {
            ASSERT(weakImpl->state() == WeakImpl::Live);
            continue;
        }

        weakImpl->setState(WeakImpl::Dead);
    }
}
예제 #3
0
void WeakBlock::specializedVisit(ContainerType& container, HeapRootVisitor& heapRootVisitor)
{
    SlotVisitor& visitor = heapRootVisitor.visitor();
    
    HeapVersion markingVersion = visitor.markingVersion();

    for (size_t i = 0; i < weakImplCount(); ++i) {
        WeakImpl* weakImpl = &weakImpls()[i];
        if (weakImpl->state() != WeakImpl::Live)
            continue;

        WeakHandleOwner* weakHandleOwner = weakImpl->weakHandleOwner();
        if (!weakHandleOwner)
            continue;

        const JSValue& jsValue = weakImpl->jsValue();
        if (container.isMarkedConcurrently(markingVersion, jsValue.asCell()))
            continue;
        
        if (!weakHandleOwner->isReachableFromOpaqueRoots(Handle<Unknown>::wrapSlot(&const_cast<JSValue&>(jsValue)), weakImpl->context(), visitor))
            continue;

        heapRootVisitor.visit(&const_cast<JSValue&>(jsValue));
    }
}
예제 #4
0
void WeakBlock::visitLiveWeakImpls(HeapRootVisitor& heapRootVisitor)
{
    // If a block is completely empty, a visit won't have any effect.
    if (!m_sweepResult.isNull() && m_sweepResult.blockIsFree)
        return;

    SlotVisitor& visitor = heapRootVisitor.visitor();

    for (size_t i = 0; i < weakImplCount(); ++i) {
        WeakImpl* weakImpl = &weakImpls()[i];
        if (weakImpl->state() != WeakImpl::Live)
            continue;

        const JSValue& jsValue = weakImpl->jsValue();
        if (Heap::isMarked(jsValue.asCell()))
            continue;

        WeakHandleOwner* weakHandleOwner = weakImpl->weakHandleOwner();
        if (!weakHandleOwner)
            continue;

        if (!weakHandleOwner->isReachableFromOpaqueRoots(Handle<Unknown>::wrapSlot(&const_cast<JSValue&>(jsValue)), weakImpl->context(), visitor))
            continue;

        heapRootVisitor.visit(&const_cast<JSValue&>(jsValue));
    }
}
예제 #5
0
void WeakBlock::lastChanceToFinalize()
{
    for (size_t i = 0; i < weakImplCount(); ++i) {
        WeakImpl* weakImpl = &weakImpls()[i];
        if (weakImpl->state() >= WeakImpl::Finalized)
            continue;
        weakImpl->setState(WeakImpl::Dead);
        finalize(weakImpl);
    }
}
예제 #6
0
WeakBlock::WeakBlock(PageAllocation& allocation)
    : m_allocation(allocation)
{
    for (size_t i = 0; i < weakImplCount(); ++i) {
        WeakImpl* weakImpl = &weakImpls()[i];
        new (NotNull, weakImpl) WeakImpl;
        addToFreeList(&m_sweepResult.freeList, weakImpl);
    }

    ASSERT(!m_sweepResult.isNull() && m_sweepResult.blockIsFree);
}
예제 #7
0
WeakBlock::WeakBlock(CellContainer container)
    : DoublyLinkedListNode<WeakBlock>()
    , m_container(container)
{
    for (size_t i = 0; i < weakImplCount(); ++i) {
        WeakImpl* weakImpl = &weakImpls()[i];
        new (NotNull, weakImpl) WeakImpl;
        addToFreeList(&m_sweepResult.freeList, weakImpl);
    }

    ASSERT(isEmpty());
}
예제 #8
0
void WeakBlock::visitDeadWeakImpls(HeapRootVisitor&)
{
    // If a block is completely empty, a visit won't have any effect.
    if (!m_sweepResult.isNull() && m_sweepResult.blockIsFree)
        return;

    for (size_t i = 0; i < weakImplCount(); ++i) {
        WeakImpl* weakImpl = &weakImpls()[i];
        if (weakImpl->state() > WeakImpl::Dead)
            continue;

        if (Heap::isMarked(weakImpl->jsValue().asCell()))
            continue;

        weakImpl->setState(WeakImpl::Dead);
    }
}
예제 #9
0
void WeakBlock::sweep()
{
    if (!m_sweepResult.isNull())
        return;

    SweepResult sweepResult;
    for (size_t i = 0; i < weakImplCount(); ++i) {
        WeakImpl* weakImpl = &weakImpls()[i];
        if (weakImpl->state() == WeakImpl::Dead)
            finalize(weakImpl);
        if (weakImpl->state() == WeakImpl::Deallocated)
            addToFreeList(&sweepResult.freeList, weakImpl);
        else
            sweepResult.blockIsFree = false;
    }

    m_sweepResult = sweepResult;
    ASSERT(!m_sweepResult.isNull());
}
예제 #10
0
void WeakBlock::sweep()
{
    // If a block is completely empty, a sweep won't have any effect.
    if (isEmpty())
        return;

    SweepResult sweepResult;
    for (size_t i = 0; i < weakImplCount(); ++i) {
        WeakImpl* weakImpl = &weakImpls()[i];
        if (weakImpl->state() == WeakImpl::Dead)
            finalize(weakImpl);
        if (weakImpl->state() == WeakImpl::Deallocated)
            addToFreeList(&sweepResult.freeList, weakImpl);
        else {
            sweepResult.blockIsFree = false;
            if (weakImpl->state() == WeakImpl::Live)
                sweepResult.blockIsLogicallyEmpty = false;
        }
    }

    m_sweepResult = sweepResult;
    ASSERT(!m_sweepResult.isNull());
}
예제 #11
0
void WeakBlock::reap()
{
    // If a block is completely empty, a reaping won't have any effect.
    if (isEmpty())
        return;

    // If this WeakBlock doesn't belong to a CellContainer, we won't even be here.
    ASSERT(m_container);

    HeapVersion markingVersion = m_container.heap()->objectSpace().markingVersion();

    for (size_t i = 0; i < weakImplCount(); ++i) {
        WeakImpl* weakImpl = &weakImpls()[i];
        if (weakImpl->state() > WeakImpl::Dead)
            continue;

        if (m_container.isMarked(markingVersion, weakImpl->jsValue().asCell())) {
            ASSERT(weakImpl->state() == WeakImpl::Live);
            continue;
        }

        weakImpl->setState(WeakImpl::Dead);
    }
}