From e6c0633a9c386817017a97dac9e541a45f42fd7f Mon Sep 17 00:00:00 2001 From: Kent Hansen Date: Mon, 22 Aug 2011 13:15:52 +0200 Subject: [PATCH] Fix tst_qjsvalue::castToPointer test failure In order for casting the variant's data() to work, we need to get at the actual QVariant wrapped in the JS object; copying the variant caused a stale pointer to be returned. Task-number: QTBUG-21000 Change-Id: I1a32a70d5a043c94dbbd07ef2c8048e7df7fc7bf Reviewed-on: http://codereview.qt.nokia.com/3309 Reviewed-by: Qt Sanity Bot Reviewed-by: Simon Hausmann --- src/declarative/qml/v8/qv8engine.cpp | 9 ++++----- src/declarative/qml/v8/qv8engine_p.h | 2 +- src/declarative/qml/v8/qv8variantwrapper.cpp | 9 ++++++++- src/declarative/qml/v8/qv8variantwrapper_p.h | 1 + tests/auto/declarative/qjsvalue/tst_qjsvalue.cpp | 4 ---- 5 files changed, 14 insertions(+), 11 deletions(-) diff --git a/src/declarative/qml/v8/qv8engine.cpp b/src/declarative/qml/v8/qv8engine.cpp index 84892d7..4f5caa1 100644 --- a/src/declarative/qml/v8/qv8engine.cpp +++ b/src/declarative/qml/v8/qv8engine.cpp @@ -2107,14 +2107,14 @@ bool QV8Engine::metaTypeFromJS(v8::Handle value, int type, void *data } #endif - // Try to use magic. + // Try to use magic; for compatibility with qscriptvalue_cast. QByteArray name = QMetaType::typeName(type); if (convertToNativeQObject(value, name, reinterpret_cast(data))) return true; if (isVariant(value) && name.endsWith('*')) { int valueType = QMetaType::type(name.left(name.size()-1)); - QVariant var = variantValue(value); + QVariant &var = variantValue(value); if (valueType == var.userType()) { // We have T t, T* is requested, so return &t. *reinterpret_cast(data) = var.data(); @@ -2235,10 +2235,9 @@ QObject *QV8Engine::qtObjectFromJS(v8::Handle value) } -QVariant QV8Engine::variantValue(v8::Handle value) +QVariant &QV8Engine::variantValue(v8::Handle value) { - Q_ASSERT(isVariant(value)); - return QV8Engine::toVariant(value, -1 /*whateever magic hint is*/); + return variantWrapper()->variantValue(value); } // Creates a QVariant wrapper object. diff --git a/src/declarative/qml/v8/qv8engine_p.h b/src/declarative/qml/v8/qv8engine_p.h index f20d867..43ef982 100644 --- a/src/declarative/qml/v8/qv8engine_p.h +++ b/src/declarative/qml/v8/qv8engine_p.h @@ -387,7 +387,7 @@ public: const QByteArray &targetType, void **result); - QVariant variantValue(v8::Handle value); + QVariant &variantValue(v8::Handle value); QJSValue scriptValueFromInternal(v8::Handle) const; diff --git a/src/declarative/qml/v8/qv8variantwrapper.cpp b/src/declarative/qml/v8/qv8variantwrapper.cpp index 27d0b31..de4f0ce 100644 --- a/src/declarative/qml/v8/qv8variantwrapper.cpp +++ b/src/declarative/qml/v8/qv8variantwrapper.cpp @@ -159,7 +159,14 @@ QVariant QV8VariantWrapper::toVariant(QV8ObjectResource *r) return static_cast(r)->data; } -v8::Handle QV8VariantWrapper::Getter(v8::Local property, +QVariant &QV8VariantWrapper::variantValue(v8::Handle value) +{ + Q_ASSERT(isVariant(value)); + QV8VariantResource *r = v8_resource_cast(value->ToObject()); + return static_cast(r)->data; +} + +v8::Handle QV8VariantWrapper::Getter(v8::Local property, const v8::AccessorInfo &info) { return v8::Handle(); diff --git a/src/declarative/qml/v8/qv8variantwrapper_p.h b/src/declarative/qml/v8/qv8variantwrapper_p.h index de74bc9..7e9924b 100644 --- a/src/declarative/qml/v8/qv8variantwrapper_p.h +++ b/src/declarative/qml/v8/qv8variantwrapper_p.h @@ -74,6 +74,7 @@ public: bool isVariant(v8::Handle); QVariant toVariant(v8::Handle); QVariant toVariant(QV8ObjectResource *); + QVariant &variantValue(v8::Handle); private: static v8::Handle Getter(v8::Local property, diff --git a/tests/auto/declarative/qjsvalue/tst_qjsvalue.cpp b/tests/auto/declarative/qjsvalue/tst_qjsvalue.cpp index 4eef465..24330c9 100644 --- a/tests/auto/declarative/qjsvalue/tst_qjsvalue.cpp +++ b/tests/auto/declarative/qjsvalue/tst_qjsvalue.cpp @@ -3705,11 +3705,7 @@ void tst_QJSValue::castToPointer() QJSValue v = eng.newVariant(int(123)); int *ip = qjsvalue_cast(v); QVERIFY(ip != 0); -#ifdef Q_WS_QPA - QEXPECT_FAIL("", "QTBUG-21000 fails", Abort); -#endif QCOMPARE(*ip, 123); - QEXPECT_FAIL("", "Pointer magic for variants is currently not supported by QJSEngine", Abort); *ip = 456; QCOMPARE(qjsvalue_cast(v), 456); -- 2.7.4