| OLD | NEW |
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "core/events/PromiseRejectionEvent.h" | 5 #include "core/events/PromiseRejectionEvent.h" |
| 6 | 6 |
| 7 #include "bindings/core/v8/DOMWrapperWorld.h" | 7 #include "bindings/core/v8/DOMWrapperWorld.h" |
| 8 | 8 |
| 9 namespace blink { | 9 namespace blink { |
| 10 | 10 |
| 11 PromiseRejectionEvent::PromiseRejectionEvent( | 11 PromiseRejectionEvent::PromiseRejectionEvent( |
| 12 ScriptState* state, | 12 ScriptState* state, |
| 13 const AtomicString& type, | 13 const AtomicString& type, |
| 14 const PromiseRejectionEventInit& initializer) | 14 const PromiseRejectionEventInit& initializer) |
| 15 : Event(type, initializer), | 15 : Event(type, initializer), |
| 16 m_scriptState(state), | 16 m_world(state->world()), |
| 17 m_promise(this), | 17 m_promise(this), |
| 18 m_reason(this) { | 18 m_reason(this) { |
| 19 ThreadState::current()->registerPreFinalizer(this); | 19 ThreadState::current()->registerPreFinalizer(this); |
| 20 DCHECK(initializer.hasPromise()); | 20 DCHECK(initializer.hasPromise()); |
| 21 m_promise.set(initializer.promise().isolate(), | 21 m_promise.set(initializer.promise().isolate(), |
| 22 initializer.promise().v8Value()); | 22 initializer.promise().v8Value()); |
| 23 if (initializer.hasReason()) { | 23 if (initializer.hasReason()) { |
| 24 m_reason.set(initializer.reason().isolate(), | 24 m_reason.set(initializer.reason().isolate(), |
| 25 initializer.reason().v8Value()); | 25 initializer.reason().v8Value()); |
| 26 } | 26 } |
| 27 } | 27 } |
| 28 | 28 |
| 29 PromiseRejectionEvent::~PromiseRejectionEvent() {} | 29 PromiseRejectionEvent::~PromiseRejectionEvent() {} |
| 30 | 30 |
| 31 void PromiseRejectionEvent::dispose() { | 31 void PromiseRejectionEvent::dispose() { |
| 32 // Clear ScopedPersistents so that V8 doesn't call phantom callbacks | 32 // Clear ScopedPersistents so that V8 doesn't call phantom callbacks |
| 33 // (and touch the ScopedPersistents) after Oilpan starts lazy sweeping. | 33 // (and touch the ScopedPersistents) after Oilpan starts lazy sweeping. |
| 34 m_promise.clear(); | 34 m_promise.clear(); |
| 35 m_reason.clear(); | 35 m_reason.clear(); |
| 36 m_scriptState.clear(); | 36 m_world.clear(); |
| 37 } | 37 } |
| 38 | 38 |
| 39 ScriptPromise PromiseRejectionEvent::promise(ScriptState* state) const { | 39 ScriptPromise PromiseRejectionEvent::promise(ScriptState* scriptState) const { |
| 40 // Return null when the promise is accessed by a different world than the | 40 // Return null when the promise is accessed by a different world than the |
| 41 // world that created the promise. | 41 // world that created the promise. |
| 42 if (!m_scriptState || !m_scriptState->contextIsValid() || | 42 if (!canBeDispatchedInWorld(scriptState->world())) |
| 43 m_scriptState->world().worldId() != state->world().worldId()) | |
| 44 return ScriptPromise(); | 43 return ScriptPromise(); |
| 45 return ScriptPromise(m_scriptState.get(), | 44 return ScriptPromise(scriptState, m_promise.newLocal(scriptState->isolate())); |
| 46 m_promise.newLocal(m_scriptState->isolate())); | |
| 47 } | 45 } |
| 48 | 46 |
| 49 ScriptValue PromiseRejectionEvent::reason(ScriptState* state) const { | 47 ScriptValue PromiseRejectionEvent::reason(ScriptState* scriptState) const { |
| 50 // Return null when the value is accessed by a different world than the world | 48 // Return null when the value is accessed by a different world than the world |
| 51 // that created the value. | 49 // that created the value. |
| 52 if (m_reason.isEmpty() || !m_scriptState || | 50 if (m_reason.isEmpty() || !canBeDispatchedInWorld(scriptState->world())) |
| 53 !m_scriptState->contextIsValid() || | 51 return ScriptValue(scriptState, v8::Undefined(scriptState->isolate())); |
| 54 m_scriptState->world().worldId() != state->world().worldId()) | 52 return ScriptValue(scriptState, m_reason.newLocal(scriptState->isolate())); |
| 55 return ScriptValue(state, v8::Undefined(state->isolate())); | |
| 56 return ScriptValue(m_scriptState.get(), | |
| 57 m_reason.newLocal(m_scriptState->isolate())); | |
| 58 } | 53 } |
| 59 | 54 |
| 60 void PromiseRejectionEvent::setWrapperReference( | 55 void PromiseRejectionEvent::setWrapperReference( |
| 61 v8::Isolate* isolate, | 56 v8::Isolate* isolate, |
| 62 const v8::Persistent<v8::Object>& wrapper) { | 57 const v8::Persistent<v8::Object>& wrapper) { |
| 63 // This might create cross world references. However, the regular code path | 58 // This might create cross world references. However, the regular code path |
| 64 // will not create them, and if we get a cross world reference here, the | 59 // will not create them, and if we get a cross world reference here, the |
| 65 // worst thing is that the lifetime is too long (similar to what happens | 60 // worst thing is that the lifetime is too long (similar to what happens |
| 66 // for DOM trees). | 61 // for DOM trees). |
| 67 if (!m_promise.isEmpty()) | 62 if (!m_promise.isEmpty()) |
| 68 m_promise.setReference(wrapper, isolate); | 63 m_promise.setReference(wrapper, isolate); |
| 69 if (!m_reason.isEmpty()) | 64 if (!m_reason.isEmpty()) |
| 70 m_reason.setReference(wrapper, isolate); | 65 m_reason.setReference(wrapper, isolate); |
| 71 } | 66 } |
| 72 | 67 |
| 73 const AtomicString& PromiseRejectionEvent::interfaceName() const { | 68 const AtomicString& PromiseRejectionEvent::interfaceName() const { |
| 74 return EventNames::PromiseRejectionEvent; | 69 return EventNames::PromiseRejectionEvent; |
| 75 } | 70 } |
| 76 | 71 |
| 77 bool PromiseRejectionEvent::canBeDispatchedInWorld( | 72 bool PromiseRejectionEvent::canBeDispatchedInWorld( |
| 78 const DOMWrapperWorld& world) const { | 73 const DOMWrapperWorld& world) const { |
| 79 return m_scriptState && m_scriptState->contextIsValid() && | 74 return m_world && m_world->worldId() == world.worldId(); |
| 80 m_scriptState->world().worldId() == world.worldId(); | |
| 81 } | 75 } |
| 82 | 76 |
| 83 DEFINE_TRACE(PromiseRejectionEvent) { | 77 DEFINE_TRACE(PromiseRejectionEvent) { |
| 84 Event::trace(visitor); | 78 Event::trace(visitor); |
| 85 } | 79 } |
| 86 | 80 |
| 87 DEFINE_TRACE_WRAPPERS(PromiseRejectionEvent) { | 81 DEFINE_TRACE_WRAPPERS(PromiseRejectionEvent) { |
| 88 visitor->traceWrappers(m_promise); | 82 visitor->traceWrappers(m_promise); |
| 89 visitor->traceWrappers(m_reason); | 83 visitor->traceWrappers(m_reason); |
| 90 } | 84 } |
| 91 | 85 |
| 92 } // namespace blink | 86 } // namespace blink |
| OLD | NEW |