Handle exceptions inside QV8QObjectConnectionList::qt_metacall
Previously, exceptions were not handled in the connectionlist. This could cause v8 to assert under certain circumstances. Task-number: QTBUG-23375 Change-Id: Ie5f043b50bb6b02a77be464ca18ea8e3bbb0f501 Reviewed-by: Alan Alpert <alan.alpert@nokia.com>
This commit is contained in:
parent
7810092782
commit
8eec0518d6
|
@ -51,6 +51,7 @@
|
|||
#include <private/qjsvalue_p.h>
|
||||
#include <private/qscript_impl_p.h>
|
||||
#include <private/qdeclarativeaccessors_p.h>
|
||||
#include <private/qdeclarativeexpression_p.h>
|
||||
|
||||
#include <QtDeclarative/qjsvalue.h>
|
||||
#include <QtCore/qvarlengtharray.h>
|
||||
|
@ -1229,11 +1230,22 @@ int QV8QObjectConnectionList::qt_metacall(QMetaObject::Call method, int index, v
|
|||
Connection &connection = connections[ii];
|
||||
if (connection.needsDestroy)
|
||||
continue;
|
||||
|
||||
v8::TryCatch try_catch;
|
||||
if (connection.thisObject.IsEmpty()) {
|
||||
connection.function->Call(engine->global(), argCount, args.data());
|
||||
} else {
|
||||
connection.function->Call(connection.thisObject, argCount, args.data());
|
||||
}
|
||||
|
||||
if (try_catch.HasCaught()) {
|
||||
QDeclarativeError error;
|
||||
error.setDescription(QString(QLatin1String("Unknown exception occurred during evaluation of connected function: %1")).arg(engine->toString(connection.function->GetName())));
|
||||
v8::Local<v8::Message> message = try_catch.Message();
|
||||
if (!message.IsEmpty())
|
||||
QDeclarativeExpressionPrivate::exceptionToError(message, error);
|
||||
QDeclarativeEnginePrivate::get(engine->engine())->warning(error);
|
||||
}
|
||||
}
|
||||
|
||||
connectionList.connectionsInUse--;
|
||||
|
|
|
@ -0,0 +1,24 @@
|
|||
import QtQuick 2.0
|
||||
|
||||
Item {
|
||||
id: root
|
||||
property int first: 5
|
||||
property bool test: false
|
||||
|
||||
Item {
|
||||
id: exceptional
|
||||
function exceptionalFunction() {
|
||||
var obj = undefined;
|
||||
var prop = undefined;
|
||||
return obj[prop];
|
||||
}
|
||||
}
|
||||
|
||||
Component.onCompleted: {
|
||||
root["firstChanged"].connect(exceptional.exceptionalFunction);
|
||||
root["firstChanged"].connect(exceptional.exceptionalFunction);
|
||||
root["firstChanged"].connect(exceptional.exceptionalFunction);
|
||||
first = 6;
|
||||
test = true;
|
||||
}
|
||||
}
|
|
@ -199,6 +199,7 @@ private slots:
|
|||
void qtbug_11606();
|
||||
void qtbug_11600();
|
||||
void qtbug_21864();
|
||||
void qobjectConnectionListExceptionHandling();
|
||||
void nonscriptable();
|
||||
void deleteLater();
|
||||
void in();
|
||||
|
@ -5181,6 +5182,20 @@ void tst_qdeclarativeecmascript::qtbug_21864()
|
|||
delete o;
|
||||
}
|
||||
|
||||
void tst_qdeclarativeecmascript::qobjectConnectionListExceptionHandling()
|
||||
{
|
||||
// QTBUG-23375
|
||||
QDeclarativeComponent component(&engine, testFileUrl("qobjectConnectionListExceptionHandling.qml"));
|
||||
QString warning = component.url().toString() + QLatin1String(":13: TypeError: Cannot read property 'undefined' of undefined");
|
||||
QTest::ignoreMessage(QtWarningMsg, qPrintable(warning));
|
||||
QTest::ignoreMessage(QtWarningMsg, qPrintable(warning));
|
||||
QTest::ignoreMessage(QtWarningMsg, qPrintable(warning));
|
||||
QObject *o = component.create();
|
||||
QVERIFY(o != 0);
|
||||
QCOMPARE(o->property("test").toBool(), true);
|
||||
delete o;
|
||||
}
|
||||
|
||||
// Reading and writing non-scriptable properties should fail
|
||||
void tst_qdeclarativeecmascript::nonscriptable()
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue