diff options
author | Allan Sandfeld Jensen <allan.jensen@digia.com> | 2013-05-15 13:32:50 +0200 |
---|---|---|
committer | The Qt Project <gerrit-noreply@qt-project.org> | 2013-05-21 11:15:15 +0200 |
commit | d7fff220c897ab0eebcd6ca8087efd4b9477beb9 (patch) | |
tree | d69a29a321af42e7bf8d26ed5f57bec7a7744d70 | |
parent | 49cede6e71305d56c3cd30962559d6b1f39365e7 (diff) | |
download | qtwebkit-d7fff220c897ab0eebcd6ca8087efd4b9477beb9.tar.gz |
Crash when calling QWebFrame::evaluateJavaScript
https://bugs.webkit.org/show_bug.cgi?id=113434
Reviewed by Simon Hausmann.
Ensure we hold the JSLock when converting JSValue to JSValueRef.
* Api/qwebelement.cpp:
(setupScriptContext):
(QWebElement::evaluateJavaScript):
* WebCoreSupport/QWebFrameAdapter.cpp:
(QWebFrameAdapter::evaluateJavaScript):
Change-Id: I1bcab3ec31d1fbbb55246982a2c69e72ae9d0948
git-svn-id: http://svn.webkit.org/repository/webkit/trunk@149671 268f45cc-cd09-0410-ab3c-d52691b4dbfc
Reviewed-by: Jocelyn Turcotte <jocelyn.turcotte@digia.com>
-rw-r--r-- | Source/WebKit/qt/Api/qwebelement.cpp | 25 | ||||
-rw-r--r-- | Source/WebKit/qt/WebCoreSupport/QWebFrameAdapter.cpp | 13 |
2 files changed, 23 insertions, 15 deletions
diff --git a/Source/WebKit/qt/Api/qwebelement.cpp b/Source/WebKit/qt/Api/qwebelement.cpp index 82f579d95..96278333b 100644 --- a/Source/WebKit/qt/Api/qwebelement.cpp +++ b/Source/WebKit/qt/Api/qwebelement.cpp @@ -44,6 +44,7 @@ #include "qt_runtime.h" #include "NodeList.h" #include "RenderImage.h" +#include "ScriptSourceCode.h" #include "ScriptState.h" #include "StaticNodeList.h" #include "StyleResolver.h" @@ -709,7 +710,7 @@ QWebFrame *QWebElement::webFrame() const return frameAdapter->apiHandle(); } -static bool setupScriptContext(WebCore::Element* element, JSC::JSValue& thisValue, ScriptState*& state, ScriptController*& scriptController) +static bool setupScriptContext(WebCore::Element* element, ScriptState*& state, ScriptController*& scriptController) { if (!element) return false; @@ -730,10 +731,6 @@ static bool setupScriptContext(WebCore::Element* element, JSC::JSValue& thisValu if (!state) return false; - thisValue = toJS(state, deprecatedGlobalObjectForPrototype(state), element); - if (!thisValue) - return false; - return true; } @@ -746,21 +743,29 @@ QVariant QWebElement::evaluateJavaScript(const QString& scriptSource) return QVariant(); ScriptState* state = 0; - JSC::JSValue thisValue; ScriptController* scriptController = 0; - if (!setupScriptContext(m_element, thisValue, state, scriptController)) + if (!setupScriptContext(m_element, state, scriptController)) + return QVariant(); + + JSC::JSLockHolder lock(state); + RefPtr<Element> protect = m_element; + + JSC::JSValue thisValue = toJS(state, toJSDOMGlobalObject(m_element->document(), state), m_element); + if (!thisValue) return QVariant(); - String script(reinterpret_cast_ptr<const UChar*>(scriptSource.data()), scriptSource.length()); + + ScriptSourceCode sourceCode(scriptSource); JSC::JSValue evaluationException; - JSC::JSValue evaluationResult = JSC::evaluate(state, JSC::makeSource(script), thisValue, &evaluationException); + JSC::JSValue evaluationResult = JSC::evaluate(state, sourceCode.jsSourceCode(), thisValue, &evaluationException); if (evaluationException) return QVariant(); + JSValueRef evaluationResultRef = toRef(state, evaluationResult); int distance = 0; JSValueRef* ignoredException = 0; - return JSC::Bindings::convertValueToQVariant(toRef(state), toRef(state, evaluationResult), QMetaType::Void, &distance, ignoredException); + return JSC::Bindings::convertValueToQVariant(toRef(state), evaluationResultRef, QMetaType::Void, &distance, ignoredException); } /*! diff --git a/Source/WebKit/qt/WebCoreSupport/QWebFrameAdapter.cpp b/Source/WebKit/qt/WebCoreSupport/QWebFrameAdapter.cpp index 7f55da362..595d758b4 100644 --- a/Source/WebKit/qt/WebCoreSupport/QWebFrameAdapter.cpp +++ b/Source/WebKit/qt/WebCoreSupport/QWebFrameAdapter.cpp @@ -194,14 +194,17 @@ void QWebFrameAdapter::handleGestureEvent(QGestureEventFacade* gestureEvent) QVariant QWebFrameAdapter::evaluateJavaScript(const QString &scriptSource) { - ScriptController* proxy = frame->script(); + ScriptController* scriptController = frame->script(); QVariant rc; - if (proxy) { + if (scriptController) { int distance = 0; - JSC::JSValue v = frame->script()->executeScript(ScriptSourceCode(scriptSource)).jsValue(); - JSC::ExecState* exec = proxy->globalObject(mainThreadNormalWorld())->globalExec(); + ScriptValue value = scriptController->executeScript(ScriptSourceCode(scriptSource)); + JSC::ExecState* exec = scriptController->globalObject(mainThreadNormalWorld())->globalExec(); JSValueRef* ignoredException = 0; - rc = JSC::Bindings::convertValueToQVariant(toRef(exec), toRef(exec, v), QMetaType::Void, &distance, ignoredException); + JSC::JSLock::lock(exec); + JSValueRef valueRef = toRef(exec, value.jsValue()); + JSC::JSLock::unlock(exec); + rc = JSC::Bindings::convertValueToQVariant(toRef(exec), valueRef, QMetaType::Void, &distance, ignoredException); } return rc; } |