static void keepAlive(v8::Local<v8::Array>& array,
                      uint32_t index,
                      const v8::Local<T>& value,
                      ScopedPersistent<T>& persistent,
                      ScriptState* scriptState) {
  if (value.IsEmpty())
    return;

  array->Set(scriptState->context(), index, value).ToChecked();

  persistent.set(scriptState->isolate(), value);
  persistent.setPhantom();
}
void V8CustomElementLifecycleCallbacks::call(const ScopedPersistent<v8::Function>& weakCallback, Element* element)
{
    // FIXME: callbacks while paused should be queued up for execution to
    // continue then be delivered in order rather than delivered immediately.
    // Bug 329665 tracks similar behavior for other synchronous events.
    if (!executionContext() || executionContext()->activeDOMObjectsAreStopped())
        return;

    if (!m_scriptState->contextIsValid())
        return;
    ScriptState::Scope scope(m_scriptState.get());
    v8::Isolate* isolate = m_scriptState->isolate();
    v8::Local<v8::Context> context = m_scriptState->context();
    v8::Local<v8::Function> callback = weakCallback.newLocal(isolate);
    if (callback.IsEmpty())
        return;

    v8::Local<v8::Value> receiver = toV8(element, context->Global(), isolate);
    if (receiver.IsEmpty())
        return;

    v8::TryCatch exceptionCatcher;
    exceptionCatcher.SetVerbose(true);
    ScriptController::callFunction(executionContext(), callback, receiver, 0, 0, isolate);
}
Exemple #3
0
void V8GCController::collectGarbage()
{
    v8::HandleScope handleScope;

    ScopedPersistent<v8::Context> context;

    context.adopt(v8::Context::New());
    if (context.isEmpty())
        return;

    {
        v8::Context::Scope scope(context.get());
        v8::Local<v8::String> source = v8::String::New("if (gc) gc();");
        v8::Local<v8::String> name = v8::String::New("gc");
        v8::Handle<v8::Script> script = v8::Script::Compile(source, name);
        if (!script.IsEmpty()) {
            V8RecursionScope::MicrotaskSuppression scope;
            script->Run();
        }
    }

    context.clear();
}
void V8CustomElementLifecycleCallbacks::call(const ScopedPersistent<v8::Function>& weakCallback, Element* element)
{
    if (!canInvokeCallback())
        return;

    v8::HandleScope handleScope(toIsolate(scriptExecutionContext()));
    v8::Handle<v8::Context> context = toV8Context(scriptExecutionContext(), m_world.get());
    if (context.IsEmpty())
        return;

    v8::Context::Scope scope(context);
    v8::Isolate* isolate = context->GetIsolate();

    v8::Handle<v8::Function> callback = weakCallback.newLocal(isolate);
    if (callback.IsEmpty())
        return;

    v8::Handle<v8::Object> receiver = toV8(element, context->Global(), isolate).As<v8::Object>();
    ASSERT(!receiver.IsEmpty());

    v8::TryCatch exceptionCatcher;
    exceptionCatcher.SetVerbose(true);
    ScriptController::callFunctionWithInstrumentation(scriptExecutionContext(), callback, receiver, 0, 0, isolate);
}
Exemple #5
0
TEST_F(PaintWorkletTest, GarbageCollectionOfCSSPaintDefinition) {
  PaintWorkletGlobalScope* globalScope =
      paintWorklet()->workletGlobalScopeProxy();
  globalScope->scriptController()->evaluate(
      ScriptSourceCode("registerPaint('foo', class { paint() { } });"));

  CSSPaintDefinition* definition = globalScope->findDefinition("foo");
  ASSERT(definition);

  v8::Isolate* isolate =
      globalScope->scriptController()->getScriptState()->isolate();
  ASSERT(isolate);

  // Set our ScopedPersistent to the paint function, and make weak.
  ScopedPersistent<v8::Function> handle;
  {
    v8::HandleScope handleScope(isolate);
    handle.set(isolate, definition->paintFunctionForTesting(isolate));
    handle.setPhantom();
  }
  ASSERT(!handle.isEmpty());
  ASSERT(handle.isWeak());

  // Run a GC, persistent shouldn't have been collected yet.
  ThreadState::current()->collectAllGarbage();
  V8GCController::collectAllGarbageForTesting(isolate);
  ASSERT(!handle.isEmpty());

  // Delete the page & associated objects.
  m_page.reset();

  // Run a GC, the persistent should have been collected.
  ThreadState::current()->collectAllGarbage();
  V8GCController::collectAllGarbageForTesting(isolate);
  ASSERT(handle.isEmpty());
}