V8DOMWindowShell* ScriptController::windowShell(DOMWrapperWorld* world)
{
    ASSERT(world);

    V8DOMWindowShell* shell = 0;
    if (world->isMainWorld())
        shell = m_windowShell.get();
    else {
        IsolatedWorldMap::iterator iter = m_isolatedWorlds.find(world->worldId());
        if (iter != m_isolatedWorlds.end())
            shell = iter->value.get();
        else {
            OwnPtr<V8DOMWindowShell> isolatedWorldShell = V8DOMWindowShell::create(m_frame, world, m_isolate);
            shell = isolatedWorldShell.get();
            m_isolatedWorlds.set(world->worldId(), isolatedWorldShell.release());
        }
    }
    if (!shell->isContextInitialized() && shell->initializeIfNeeded()) {
        if (world->isMainWorld()) {
            // FIXME: Remove this if clause. See comment with existingWindowShellWorkaroundWorld().
            m_frame->loader()->dispatchDidClearWindowObjectInWorld(existingWindowShellWorkaroundWorld());
        } else
            m_frame->loader()->dispatchDidClearWindowObjectInWorld(world);
    }
    return shell;
}
void ScriptController::evaluateInIsolatedWorld(int worldID, const Vector<ScriptSourceCode>& sources, int extensionGroup, Vector<ScriptValue>* results)
{
    ASSERT(worldID > 0);

    v8::HandleScope handleScope;
    v8::Local<v8::Array> v8Results;
    {
        v8::HandleScope evaluateHandleScope;
        RefPtr<DOMWrapperWorld> world = DOMWrapperWorld::ensureIsolatedWorld(worldID, extensionGroup);
        V8DOMWindowShell* isolatedWorldShell = windowShell(world.get());

        if (!isolatedWorldShell->isContextInitialized())
            return;

        v8::Local<v8::Context> context = isolatedWorldShell->context();
        v8::Context::Scope contextScope(context);
        v8::Local<v8::Array> resultArray = v8::Array::New(sources.size());

        for (size_t i = 0; i < sources.size(); ++i) {
            v8::Local<v8::Value> evaluationResult = compileAndRunScript(sources[i]);
            if (evaluationResult.IsEmpty())
                evaluationResult = v8::Local<v8::Value>::New(v8::Undefined());
            resultArray->Set(i, evaluationResult);
        }

        v8Results = evaluateHandleScope.Close(resultArray);
    }

    if (results && !v8Results.IsEmpty()) {
        for (size_t i = 0; i < v8Results->Length(); ++i)
            results->append(ScriptValue(v8Results->Get(i)));
    }
}
예제 #3
0
void ScriptController::evaluateInIsolatedWorld(int worldID, const Vector<ScriptSourceCode>& sources, int extensionGroup, Vector<ScriptValue>* results)
{
    // Except in the test runner, worldID should be non 0 as it conflicts with the mainWorldId.
    // FIXME: Change the test runner to perform this swap and make this an ASSERT.
    if (UNLIKELY(!worldID))
        worldID = DOMWrapperWorld::uninitializedWorldId;

    v8::HandleScope handleScope;
    v8::Local<v8::Array> v8Results;
    {
        v8::HandleScope evaluateHandleScope;
        RefPtr<DOMWrapperWorld> world = DOMWrapperWorld::ensureIsolatedWorld(worldID, extensionGroup);
        V8DOMWindowShell* isolatedWorldShell = windowShell(world.get());

        if (!isolatedWorldShell->isContextInitialized())
            return;

        v8::Local<v8::Context> context = v8::Local<v8::Context>::New(isolatedWorldShell->context());
        v8::Context::Scope contextScope(context);
        v8::Local<v8::Array> resultArray = v8::Array::New(sources.size());

        for (size_t i = 0; i < sources.size(); ++i) {
            v8::Local<v8::Value> evaluationResult = compileAndRunScript(sources[i]);
            if (evaluationResult.IsEmpty())
                evaluationResult = v8::Local<v8::Value>::New(v8::Undefined());
            resultArray->Set(i, evaluationResult);
        }

        // Mark temporary shell for weak destruction.
        if (worldID == DOMWrapperWorld::uninitializedWorldId) {
            isolatedWorldShell->destroyIsolatedShell();
            m_isolatedWorlds.remove(world->worldId());
        }

        v8Results = evaluateHandleScope.Close(resultArray);
    }

    if (results && !v8Results.IsEmpty()) {
        for (size_t i = 0; i < v8Results->Length(); ++i)
            results->append(ScriptValue(v8Results->Get(i)));
    }
}