From e9f7db9dbb2c5b9d1953c6643e1c38f82130f98b Mon Sep 17 00:00:00 2001 From: Dan Sinclair Date: Tue, 5 Jun 2018 18:24:12 +0000 Subject: [xfa] Make the event context available when calling back in XFA When calling into the XFA JS engine with a request for a non-XFA JS call which accesses the EventContext we would get a crash in XFA as we never set the context. This CL changes the XFA code to accept the CJS_Runtime instead of the CFXJS_Engine and then calls NewEventContext before executing JS scripts. This will correctly setup the event context as needed for any JS callbacks. Bug: pdfium:1003 Change-Id: Icf202252b2e6e56afdf0d1766a32a893935a2fd3 Reviewed-on: https://pdfium-review.googlesource.com/33930 Reviewed-by: Tom Sepez Commit-Queue: dsinclair --- fxjs/cfxjse_engine.cpp | 21 +++++++++++++-------- fxjs/cfxjse_engine.h | 6 +++--- fxjs/cjs_event.cpp | 22 ++++++++++++++++++++++ xfa/fxfa/parser/cxfa_document.cpp | 4 ++-- xfa/fxfa/parser/cxfa_document.h | 4 ++-- 5 files changed, 42 insertions(+), 15 deletions(-) diff --git a/fxjs/cfxjse_engine.cpp b/fxjs/cfxjse_engine.cpp index e894d51de4..90fcc312db 100644 --- a/fxjs/cfxjse_engine.cpp +++ b/fxjs/cfxjse_engine.cpp @@ -11,10 +11,10 @@ #include "core/fxcrt/autorestorer.h" #include "core/fxcrt/cfx_widetextbuf.h" #include "core/fxcrt/fx_extension.h" -#include "fxjs/cfxjs_engine.h" #include "fxjs/cfxjse_class.h" #include "fxjs/cfxjse_resolveprocessor.h" #include "fxjs/cfxjse_value.h" +#include "fxjs/cjs_runtime.h" #include "third_party/base/ptr_util.h" #include "third_party/base/stl_util.h" #include "xfa/fxfa/cxfa_eventparam.h" @@ -94,12 +94,12 @@ CXFA_Object* CFXJSE_Engine::ToObject(CFXJSE_Value* pValue, } CFXJSE_Engine::CFXJSE_Engine(CXFA_Document* pDocument, - CFXJS_Engine* fxjs_engine) - : CFX_V8(fxjs_engine->GetIsolate()), - m_pSubordinateEngine(fxjs_engine), + CJS_Runtime* fxjs_runtime) + : CFX_V8(fxjs_runtime->GetIsolate()), + m_pSubordinateRuntime(fxjs_runtime), m_pDocument(pDocument), - m_JsContext(CFXJSE_Context::Create(fxjs_engine->GetIsolate(), - fxjs_engine, + m_JsContext(CFXJSE_Context::Create(fxjs_runtime->GetIsolate(), + fxjs_runtime, &GlobalClassDescriptor, pDocument->GetRoot())), m_pJsClass(nullptr), @@ -146,7 +146,12 @@ bool CFXJSE_Engine::RunScript(CXFA_Script::Type eScriptType, AutoRestorer nodeRestorer(&m_pThisObject); m_pThisObject = pThisObject; CFXJSE_Value* pValue = pThisObject ? GetJSValueFromMap(pThisObject) : nullptr; - return m_JsContext->ExecuteScript(btScript.c_str(), hRetValue, pValue); + + IJS_EventContext* ctx = m_pSubordinateRuntime->NewEventContext(); + bool ret = m_JsContext->ExecuteScript(btScript.c_str(), hRetValue, pValue); + m_pSubordinateRuntime->ReleaseEventContext(ctx); + + return ret; } bool CFXJSE_Engine::QueryNodeByFlag(CXFA_Node* refNode, @@ -463,7 +468,7 @@ CFXJSE_Context* CFXJSE_Engine::CreateVariablesContext(CXFA_Node* pScriptNode, return nullptr; auto pNewContext = CFXJSE_Context::Create( - GetIsolate(), m_pSubordinateEngine.Get(), &VariablesClassDescriptor, + GetIsolate(), m_pSubordinateRuntime.Get(), &VariablesClassDescriptor, new CXFA_ThisProxy(pSubform, pScriptNode)); RemoveBuiltInObjs(pNewContext.get()); pNewContext->EnableCompatibleMode(); diff --git a/fxjs/cfxjse_engine.h b/fxjs/cfxjse_engine.h index dc05f0ddf8..62de0614c4 100644 --- a/fxjs/cfxjse_engine.h +++ b/fxjs/cfxjse_engine.h @@ -23,7 +23,7 @@ #define XFA_RESOLVENODE_TagName 0x0002 class CFXJSE_ResolveProcessor; -class CFXJS_Engine; +class CJS_Runtime; class CXFA_List; class CFXJSE_Engine : public CFX_V8 { @@ -52,7 +52,7 @@ class CFXJSE_Engine : public CFX_V8 { const ByteStringView& szPropName, bool bQueryIn); - CFXJSE_Engine(CXFA_Document* pDocument, CFXJS_Engine* fxjs_engine); + CFXJSE_Engine(CXFA_Document* pDocument, CJS_Runtime* fxjs_runtime); ~CFXJSE_Engine() override; void SetEventParam(CXFA_EventParam* param) { m_eventParam = param; } @@ -107,7 +107,7 @@ class CFXJSE_Engine : public CFX_V8 { bool bGetter); bool RunVariablesScript(CXFA_Node* pScriptNode); - UnownedPtr const m_pSubordinateEngine; + UnownedPtr const m_pSubordinateRuntime; UnownedPtr const m_pDocument; std::unique_ptr m_JsContext; CFXJSE_Class* m_pJsClass; diff --git a/fxjs/cjs_event.cpp b/fxjs/cjs_event.cpp index ca0671d3a9..de22ab8488 100644 --- a/fxjs/cjs_event.cpp +++ b/fxjs/cjs_event.cpp @@ -50,6 +50,8 @@ CJS_Event::CJS_Event(v8::Local pObject, CJS_Runtime* pRuntime) CJS_Event::~CJS_Event() = default; CJS_Return CJS_Event::get_change(CJS_Runtime* pRuntime) { + ASSERT(pRuntime->GetCurrentEventContext()); + CJS_EventHandler* pEvent = pRuntime->GetCurrentEventContext()->GetEventHandler(); return CJS_Return(pRuntime->NewString(pEvent->Change().c_str())); @@ -57,6 +59,8 @@ CJS_Return CJS_Event::get_change(CJS_Runtime* pRuntime) { CJS_Return CJS_Event::set_change(CJS_Runtime* pRuntime, v8::Local vp) { + ASSERT(pRuntime->GetCurrentEventContext()); + CJS_EventHandler* pEvent = pRuntime->GetCurrentEventContext()->GetEventHandler(); @@ -68,6 +72,8 @@ CJS_Return CJS_Event::set_change(CJS_Runtime* pRuntime, } CJS_Return CJS_Event::get_change_ex(CJS_Runtime* pRuntime) { + ASSERT(pRuntime->GetCurrentEventContext()); + CJS_EventHandler* pEvent = pRuntime->GetCurrentEventContext()->GetEventHandler(); @@ -80,6 +86,8 @@ CJS_Return CJS_Event::set_change_ex(CJS_Runtime* pRuntime, } CJS_Return CJS_Event::get_commit_key(CJS_Runtime* pRuntime) { + ASSERT(pRuntime->GetCurrentEventContext()); + CJS_EventHandler* pEvent = pRuntime->GetCurrentEventContext()->GetEventHandler(); @@ -92,6 +100,8 @@ CJS_Return CJS_Event::set_commit_key(CJS_Runtime* pRuntime, } CJS_Return CJS_Event::get_field_full(CJS_Runtime* pRuntime) { + ASSERT(pRuntime->GetCurrentEventContext()); + CJS_EventHandler* pEvent = pRuntime->GetCurrentEventContext()->GetEventHandler(); @@ -245,6 +255,8 @@ CJS_Return CJS_Event::set_source(CJS_Runtime* pRuntime, } CJS_Return CJS_Event::get_target(CJS_Runtime* pRuntime) { + ASSERT(pRuntime->GetCurrentEventContext()); + CJS_EventHandler* pEvent = pRuntime->GetCurrentEventContext()->GetEventHandler(); return CJS_Return(pEvent->Target_Field()->ToV8Object()); @@ -256,6 +268,8 @@ CJS_Return CJS_Event::set_target(CJS_Runtime* pRuntime, } CJS_Return CJS_Event::get_target_name(CJS_Runtime* pRuntime) { + ASSERT(pRuntime->GetCurrentEventContext()); + CJS_EventHandler* pEvent = pRuntime->GetCurrentEventContext()->GetEventHandler(); return CJS_Return(pRuntime->NewString(pEvent->TargetName().c_str())); @@ -267,6 +281,8 @@ CJS_Return CJS_Event::set_target_name(CJS_Runtime* pRuntime, } CJS_Return CJS_Event::get_type(CJS_Runtime* pRuntime) { + ASSERT(pRuntime->GetCurrentEventContext()); + CJS_EventHandler* pEvent = pRuntime->GetCurrentEventContext()->GetEventHandler(); return CJS_Return(pRuntime->NewString(pEvent->Type())); @@ -277,6 +293,8 @@ CJS_Return CJS_Event::set_type(CJS_Runtime* pRuntime, v8::Local vp) { } CJS_Return CJS_Event::get_value(CJS_Runtime* pRuntime) { + ASSERT(pRuntime->GetCurrentEventContext()); + CJS_EventHandler* pEvent = pRuntime->GetCurrentEventContext()->GetEventHandler(); @@ -291,6 +309,8 @@ CJS_Return CJS_Event::get_value(CJS_Runtime* pRuntime) { CJS_Return CJS_Event::set_value(CJS_Runtime* pRuntime, v8::Local vp) { + ASSERT(pRuntime->GetCurrentEventContext()); + CJS_EventHandler* pEvent = pRuntime->GetCurrentEventContext()->GetEventHandler(); @@ -305,6 +325,8 @@ CJS_Return CJS_Event::set_value(CJS_Runtime* pRuntime, } CJS_Return CJS_Event::get_will_commit(CJS_Runtime* pRuntime) { + ASSERT(pRuntime->GetCurrentEventContext()); + CJS_EventHandler* pEvent = pRuntime->GetCurrentEventContext()->GetEventHandler(); return CJS_Return(pRuntime->NewBoolean(pEvent->WillCommit())); diff --git a/xfa/fxfa/parser/cxfa_document.cpp b/xfa/fxfa/parser/cxfa_document.cpp index 5c4b55776a..a24bf2014f 100644 --- a/xfa/fxfa/parser/cxfa_document.cpp +++ b/xfa/fxfa/parser/cxfa_document.cpp @@ -1435,9 +1435,9 @@ CXFA_LocaleMgr* CXFA_Document::GetLocalMgr() { return m_pLocalMgr.get(); } -CFXJSE_Engine* CXFA_Document::InitScriptContext(CFXJS_Engine* fxjs_engine) { +CFXJSE_Engine* CXFA_Document::InitScriptContext(CJS_Runtime* fxjs_runtime) { ASSERT(!m_pScriptContext); - m_pScriptContext = pdfium::MakeUnique(this, fxjs_engine); + m_pScriptContext = pdfium::MakeUnique(this, fxjs_runtime); return m_pScriptContext.get(); } diff --git a/xfa/fxfa/parser/cxfa_document.h b/xfa/fxfa/parser/cxfa_document.h index f924abb989..795da004cc 100644 --- a/xfa/fxfa/parser/cxfa_document.h +++ b/xfa/fxfa/parser/cxfa_document.h @@ -41,7 +41,7 @@ enum XFA_DocFlag { }; class CFXJSE_Engine; -class CFXJS_Engine; +class CJS_Runtime; class CScript_DataWindow; class CScript_EventPseudoModel; class CScript_HostPseudoModel; @@ -58,7 +58,7 @@ class CXFA_Document : public CXFA_NodeOwner { explicit CXFA_Document(CXFA_FFNotify* notify); ~CXFA_Document() override; - CFXJSE_Engine* InitScriptContext(CFXJS_Engine* fxjs_engine); + CFXJSE_Engine* InitScriptContext(CJS_Runtime* fxjs_runtime); CXFA_Node* GetRoot() const { return m_pRootNode; } CXFA_FFNotify* GetNotify() const { return notify_.Get(); } -- cgit v1.2.3