bool HostRecord::limitsRequests(ResourceLoadPriority priority, SchedulableLoader* loader) const
{
    ASSERT(loader);
    ASSERT(loader->connectionToWebProcess());

    if (priority == ResourceLoadPriorityVeryLow && !m_loadersInProgress.isEmpty())
        return true;

    if (loader->connectionToWebProcess()->isSerialLoadingEnabled() && m_loadersInProgress.size() >= 1)
        return true;

    // If we're exactly at the limit for requests in flight, and this loader is asynchronous, then we're done serving new requests.
    // The synchronous loader exception handles the case where a sync XHR is made while 6 other requests are already in flight.
    if (m_loadersInProgress.size() == m_maxRequestsInFlight && !loader->isSynchronous())
        return true;

    // If we're already past the limit of the number of loaders in flight, we won't even serve new synchronous requests right now.
    if (m_loadersInProgress.size() > m_maxRequestsInFlight) {
#ifndef NDEBUG
        // If we have more loaders in progress than we should, at least one of them had better be synchronous.
        SchedulableLoaderSet::iterator i = m_loadersInProgress.begin();
        SchedulableLoaderSet::iterator end = m_loadersInProgress.end();
        for (; i != end; ++i) {
            if (i->get()->isSynchronous())
                break;
        }
        ASSERT(i != end);
#endif
        return true;
    }
    return false;
}
예제 #2
0
void HostRecord::removeLoader(SchedulableLoader* loader)
{
    ASSERT(isMainThread());

    // FIXME (NetworkProcess): Due to IPC race conditions, it's possible this HostRecord will be asked to remove the same loader twice.
    // It would be nice to know the loader has already been removed and treat it as a no-op.

    SchedulableLoaderSet::iterator i = m_loadersInProgress.find(loader);
    if (i != m_loadersInProgress.end()) {
        i->get()->setHostRecord(0);
        m_loadersInProgress.remove(i);
        return;
    }
    
    for (int priority = ResourceLoadPriorityHighest; priority >= ResourceLoadPriorityLowest; --priority) {  
        LoaderQueue::iterator end = m_loadersPending[priority].end();
        for (LoaderQueue::iterator it = m_loadersPending[priority].begin(); it != end; ++it) {
            if (it->get() == loader) {
                it->get()->setHostRecord(0);
                m_loadersPending[priority].remove(it);
                return;
            }
        }
    }
}