diff options
-rw-r--r-- | src/imports/localstorage/plugin.cpp | 12 | ||||
-rw-r--r-- | src/qml/jsapi/qjsengine.cpp | 4 | ||||
-rw-r--r-- | src/qml/jsapi/qjsvalue.cpp | 4 | ||||
-rw-r--r-- | src/qml/jsruntime/qv4jsonobject.cpp | 28 | ||||
-rw-r--r-- | src/qml/jsruntime/qv4jsonobject_p.h | 4 | ||||
-rw-r--r-- | src/qml/jsruntime/qv4mm.cpp | 6 | ||||
-rw-r--r-- | src/qml/jsruntime/qv4qobjectwrapper.cpp | 91 | ||||
-rw-r--r-- | src/qml/jsruntime/qv4sequenceobject.cpp | 9 | ||||
-rw-r--r-- | src/qml/jsruntime/qv4sequenceobject_p.h | 2 | ||||
-rw-r--r-- | src/qml/jsruntime/qv4serialize.cpp | 2 | ||||
-rw-r--r-- | src/qml/jsruntime/qv4value_p.h | 2 | ||||
-rw-r--r-- | src/qml/jsruntime/qv4variantobject.cpp | 27 | ||||
-rw-r--r-- | src/qml/jsruntime/qv4variantobject_p.h | 2 | ||||
-rw-r--r-- | src/qml/qml/qqmlproperty.cpp | 6 | ||||
-rw-r--r-- | src/qml/qml/qqmlvaluetypewrapper.cpp | 4 | ||||
-rw-r--r-- | src/qml/qml/qqmlvmemetaobject.cpp | 4 | ||||
-rw-r--r-- | src/qml/qml/v8/qv8engine.cpp | 173 | ||||
-rw-r--r-- | src/qml/qml/v8/qv8engine_p.h | 14 | ||||
-rw-r--r-- | src/qml/types/qqmldelegatemodel.cpp | 3 | ||||
-rw-r--r-- | tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp | 12 |
20 files changed, 207 insertions, 202 deletions
diff --git a/src/imports/localstorage/plugin.cpp b/src/imports/localstorage/plugin.cpp index d4966da9c8..739d37bb39 100644 --- a/src/imports/localstorage/plugin.cpp +++ b/src/imports/localstorage/plugin.cpp @@ -270,12 +270,13 @@ static ReturnedValue qmlsqldatabase_executeSql(SimpleCallContext *ctx) if (query.prepare(sql)) { if (ctx->argumentCount > 1) { - Value values = ctx->arguments[1]; - if (ArrayObject *array = values.asArrayObject()) { + ScopedValue values(scope, ctx->arguments[1]); + if (ArrayObject *array = values->asArrayObject()) { quint32 size = array->arrayLength(); + QV4::ScopedValue v(scope); for (quint32 ii = 0; ii < size; ++ii) - query.bindValue(ii, engine->toVariant(QV4::Value::fromReturnedValue(array->getIndexed(ii)), -1)); - } else if (Object *object = values.asObject()) { + query.bindValue(ii, engine->toVariant((v = array->getIndexed(ii)), -1)); + } else if (Object *object = values->asObject()) { ObjectIterator it(object, ObjectIterator::WithProtoChain|ObjectIterator::EnumerableOnly); ScopedValue key(scope); while (1) { @@ -283,7 +284,8 @@ static ReturnedValue qmlsqldatabase_executeSql(SimpleCallContext *ctx) key = it.nextPropertyName(&value); if (key->isNull()) break; - QVariant v = engine->toVariant(value, -1); + QV4::ScopedValue val(scope, value); + QVariant v = engine->toVariant(val, -1); if (key->isString()) { query.bindValue(key->stringValue()->toQString(), v); } else { diff --git a/src/qml/jsapi/qjsengine.cpp b/src/qml/jsapi/qjsengine.cpp index 59a6a14e81..57647a49d3 100644 --- a/src/qml/jsapi/qjsengine.cpp +++ b/src/qml/jsapi/qjsengine.cpp @@ -375,7 +375,9 @@ bool QJSEngine::convertV2(const QJSValue &value, int type, void *ptr) QJSValuePrivate *vp = QJSValuePrivate::get(value); QV8Engine *engine = vp->engine ? vp->engine->v8Engine : 0; if (engine) { - return engine->metaTypeFromJS(QV4::Value::fromReturnedValue(vp->getValue(engine->m_v4Engine)), type, ptr); + QV4::Scope scope(engine->m_v4Engine); + QV4::ScopedValue v(scope, vp->getValue(engine->m_v4Engine)); + return engine->metaTypeFromJS(v, type, ptr); } else { switch (type) { case QMetaType::Bool: diff --git a/src/qml/jsapi/qjsvalue.cpp b/src/qml/jsapi/qjsvalue.cpp index 9c06f403b5..a22f77b2b0 100644 --- a/src/qml/jsapi/qjsvalue.cpp +++ b/src/qml/jsapi/qjsvalue.cpp @@ -1021,11 +1021,11 @@ bool QJSValue::hasOwnProperty(const QString &name) const */ QObject *QJSValue::toQObject() const { - QV4::QObjectWrapper *o = d->value.as<QV4::QObjectWrapper>(); + Returned<QV4::QObjectWrapper> *o = d->value.as<QV4::QObjectWrapper>(); if (!o) return 0; - return o->object(); + return o->getPointer()->object(); } /*! diff --git a/src/qml/jsruntime/qv4jsonobject.cpp b/src/qml/jsruntime/qv4jsonobject.cpp index 5d1669dd8b..c6a0554d40 100644 --- a/src/qml/jsruntime/qv4jsonobject.cpp +++ b/src/qml/jsruntime/qv4jsonobject.cpp @@ -963,20 +963,20 @@ ReturnedValue JsonObject::fromJsonValue(ExecutionEngine *engine, const QJsonValu return Encode::undefined(); } -QJsonValue JsonObject::toJsonValue(const QV4::Value &value, +QJsonValue JsonObject::toJsonValue(const ValueRef value, V4ObjectSet &visitedObjects) { - if (String *s = value.asString()) + if (String *s = value->asString()) return QJsonValue(s->toQString()); - else if (value.isNumber()) - return QJsonValue(value.toNumber()); - else if (value.isBoolean()) - return QJsonValue((bool)value.booleanValue()); - else if (ArrayObject *a = value.asArrayObject()) + else if (value->isNumber()) + return QJsonValue(value->toNumber()); + else if (value->isBoolean()) + return QJsonValue((bool)value->booleanValue()); + else if (ArrayObject *a = value->asArrayObject()) return toJsonArray(a, visitedObjects); - else if (Object *o = value.asObject()) + else if (Object *o = value->asObject()) return toJsonObject(o, visitedObjects); - else if (value.isNull()) + else if (value->isNull()) return QJsonValue(QJsonValue::Null); else return QJsonValue(QJsonValue::Undefined); @@ -1020,9 +1020,11 @@ QJsonObject JsonObject::toJsonObject(QV4::Object *o, V4ObjectSet &visitedObjects if (name->isNull()) break; + QV4::ScopedValue val(scope, v); + QString key = name->toQStringNoThrow(); - if (!v.asFunctionObject()) - result.insert(key, toJsonValue(v, visitedObjects)); + if (!val->asFunctionObject()) + result.insert(key, toJsonValue(val, visitedObjects)); } visitedObjects.remove(o); @@ -1065,7 +1067,9 @@ QJsonArray JsonObject::toJsonArray(ArrayObject *a, V4ObjectSet &visitedObjects) quint32 length = a->arrayLength(); for (quint32 i = 0; i < length; ++i) { v = a->getIndexed(i); - result.append(toJsonValue(v->asFunctionObject() ? QV4::Value::nullValue() : v, visitedObjects)); + if (v->asFunctionObject()) + v = Encode::null(); + result.append(toJsonValue(v, visitedObjects)); } visitedObjects.remove(a); diff --git a/src/qml/jsruntime/qv4jsonobject_p.h b/src/qml/jsruntime/qv4jsonobject_p.h index 1dae5bbb40..eb661f7f56 100644 --- a/src/qml/jsruntime/qv4jsonobject_p.h +++ b/src/qml/jsruntime/qv4jsonobject_p.h @@ -63,7 +63,7 @@ public: static ReturnedValue fromJsonObject(ExecutionEngine *engine, const QJsonObject &object); static ReturnedValue fromJsonArray(ExecutionEngine *engine, const QJsonArray &array); - static inline QJsonValue toJsonValue(const QV4::Value &value) + static inline QJsonValue toJsonValue(const QV4::ValueRef value) { V4ObjectSet visitedObjects; return toJsonValue(value, visitedObjects); } static inline QJsonObject toJsonObject(QV4::Object *o) { V4ObjectSet visitedObjects; return toJsonObject(o, visitedObjects); } @@ -71,7 +71,7 @@ public: { V4ObjectSet visitedObjects; return toJsonArray(a, visitedObjects); } private: - static QJsonValue toJsonValue(const QV4::Value &value, V4ObjectSet &visitedObjects); + static QJsonValue toJsonValue(const QV4::ValueRef value, V4ObjectSet &visitedObjects); static QJsonObject toJsonObject(QV4::Object *o, V4ObjectSet &visitedObjects); static QJsonArray toJsonArray(QV4::ArrayObject *a, V4ObjectSet &visitedObjects); diff --git a/src/qml/jsruntime/qv4mm.cpp b/src/qml/jsruntime/qv4mm.cpp index b7a206abdf..d82968345b 100644 --- a/src/qml/jsruntime/qv4mm.cpp +++ b/src/qml/jsruntime/qv4mm.cpp @@ -378,10 +378,10 @@ void MemoryManager::mark() for (PersistentValuePrivate *weak = m_weakValues; weak; weak = weak->next) { if (!weak->refcount) continue; - QObjectWrapper *qobjectWrapper = weak->value.as<QObjectWrapper>(); + Returned<QObjectWrapper> *qobjectWrapper = weak->value.as<QObjectWrapper>(); if (!qobjectWrapper) continue; - QObject *qobject = qobjectWrapper->object(); + QObject *qobject = qobjectWrapper->getPointer()->object(); if (!qobject) continue; bool keepAlive = QQmlData::keepAliveDuringGarbageCollection(qobject); @@ -396,7 +396,7 @@ void MemoryManager::mark() } if (keepAlive) - qobjectWrapper->mark(); + qobjectWrapper->getPointer()->mark(); } } diff --git a/src/qml/jsruntime/qv4qobjectwrapper.cpp b/src/qml/jsruntime/qv4qobjectwrapper.cpp index 5dd5512c0a..b7a696cc33 100644 --- a/src/qml/jsruntime/qv4qobjectwrapper.cpp +++ b/src/qml/jsruntime/qv4qobjectwrapper.cpp @@ -513,9 +513,9 @@ bool QObjectWrapper::setQmlProperty(ExecutionContext *ctx, QQmlContextData *qmlC } else { QVariant v; if (result->isQList()) - v = ctx->engine->v8Engine->toVariant(*value, qMetaTypeId<QList<QObject *> >()); + v = ctx->engine->v8Engine->toVariant(value, qMetaTypeId<QList<QObject *> >()); else - v = ctx->engine->v8Engine->toVariant(*value, result->propType); + v = ctx->engine->v8Engine->toVariant(value, result->propType); QQmlContextData *callingQmlContext = QV4::QmlContextWrapper::callingContext(ctx->engine); if (!QQmlPropertyPrivate::write(object, *result, v, callingQmlContext)) { @@ -980,7 +980,7 @@ struct CallArgument { inline void *dataPtr(); inline void initAsType(int type); - inline void fromValue(int type, QV8Engine *, const QV4::Value&); + inline void fromValue(int type, QV8Engine *, const ValueRef); inline ReturnedValue toValue(QV8Engine *); private: @@ -1022,21 +1022,8 @@ private: }; } -namespace { -struct CallArgs -{ - CallArgs(int length, const QV4::Value *args) : _length(length), _args(args) {} - int Length() const { return _length; } - QV4::Value operator[](int idx) { return _args[idx]; } - -private: - int _length; - const QV4::Value *_args; -}; -} - static QV4::ReturnedValue CallMethod(QObject *object, int index, int returnType, int argCount, - int *argTypes, QV8Engine *engine, CallArgs &callArgs) + int *argTypes, QV8Engine *engine, QV4::CallData *callArgs) { if (argCount > 0) { @@ -1054,7 +1041,7 @@ static QV4::ReturnedValue CallMethod(QObject *object, int index, int returnType, QVarLengthArray<CallArgument, 9> args(argCount + 1); args[0].initAsType(returnType); for (int ii = 0; ii < argCount; ++ii) - args[ii + 1].fromValue(argTypes[ii], engine, callArgs[ii]); + args[ii + 1].fromValue(argTypes[ii], engine, callArgs->args[ii]); QVarLengthArray<void *, 9> argData(args.count()); for (int ii = 0; ii < args.count(); ++ii) argData[ii] = args[ii].dataPtr(); @@ -1093,9 +1080,9 @@ static QV4::ReturnedValue CallMethod(QObject *object, int index, int returnType, The conversion table is copied out of the \l QScript::callQtMethod() function. */ -static int MatchScore(const QV4::Value &actual, int conversionType) +static int MatchScore(const QV4::ValueRef actual, int conversionType) { - if (actual.isNumber()) { + if (actual->isNumber()) { switch (conversionType) { case QMetaType::Double: return 0; @@ -1122,7 +1109,7 @@ static int MatchScore(const QV4::Value &actual, int conversionType) default: return 10; } - } else if (actual.isString()) { + } else if (actual->isString()) { switch (conversionType) { case QMetaType::QString: return 0; @@ -1131,7 +1118,7 @@ static int MatchScore(const QV4::Value &actual, int conversionType) default: return 10; } - } else if (actual.isBoolean()) { + } else if (actual->isBoolean()) { switch (conversionType) { case QMetaType::Bool: return 0; @@ -1140,7 +1127,7 @@ static int MatchScore(const QV4::Value &actual, int conversionType) default: return 10; } - } else if (actual.asDateObject()) { + } else if (actual->asDateObject()) { switch (conversionType) { case QMetaType::QDateTime: return 0; @@ -1151,14 +1138,14 @@ static int MatchScore(const QV4::Value &actual, int conversionType) default: return 10; } - } else if (actual.as<QV4::RegExpObject>()) { + } else if (actual->as<QV4::RegExpObject>()) { switch (conversionType) { case QMetaType::QRegExp: return 0; default: return 10; } - } else if (actual.asArrayObject()) { + } else if (actual->asArrayObject()) { switch (conversionType) { case QMetaType::QJsonArray: return 3; @@ -1173,7 +1160,7 @@ static int MatchScore(const QV4::Value &actual, int conversionType) default: return 10; } - } else if (actual.isNull()) { + } else if (actual->isNull()) { switch (conversionType) { case QMetaType::VoidStar: case QMetaType::QObjectStar: @@ -1187,7 +1174,7 @@ static int MatchScore(const QV4::Value &actual, int conversionType) return 10; } } - } else if (QV4::Object *obj = actual.asObject()) { + } else if (QV4::Object *obj = actual->asObject()) { QV8Engine *engine = obj->engine()->v8Engine; if (QV4::VariantObject *v = obj->as<QV4::VariantObject>()) { @@ -1279,7 +1266,7 @@ static const QQmlPropertyData * RelatedMethod(QObject *object, } static QV4::ReturnedValue CallPrecise(QObject *object, const QQmlPropertyData &data, - QV8Engine *engine, CallArgs &callArgs) + QV8Engine *engine, QV4::CallData *callArgs) { QByteArray unknownTypeError; @@ -1305,7 +1292,7 @@ static QV4::ReturnedValue CallPrecise(QObject *object, const QQmlPropertyData &d QV8Engine::getV4(engine)->current->throwError(error); } - if (args[0] > callArgs.Length()) { + if (args[0] > callArgs->argc) { QString error = QLatin1String("Insufficient arguments"); QV8Engine::getV4(engine)->current->throwError(error); } @@ -1333,9 +1320,9 @@ Resolve the overloaded method to call. The algorithm works conceptually like th score is constructed by adding the matchScore() result for each of the parameters. */ static QV4::ReturnedValue CallOverloaded(QObject *object, const QQmlPropertyData &data, - QV8Engine *engine, CallArgs &callArgs) + QV8Engine *engine, QV4::CallData *callArgs) { - int argumentCount = callArgs.Length(); + int argumentCount = callArgs->argc; const QQmlPropertyData *best = 0; int bestParameterScore = INT_MAX; @@ -1354,6 +1341,9 @@ static QV4::ReturnedValue CallOverloaded(QObject *object, const QQmlPropertyData QQmlPropertyData dummy; const QQmlPropertyData *attempt = &data; + QV4::Scope scope(QV8Engine::getV4(engine)); + QV4::ScopedValue v(scope); + do { QVarLengthArray<int, 9> dummy; int methodArgumentCount = 0; @@ -1377,7 +1367,7 @@ static QV4::ReturnedValue CallOverloaded(QObject *object, const QQmlPropertyData int methodMatchScore = 0; for (int ii = 0; ii < methodArgumentCount; ++ii) - methodMatchScore += MatchScore(callArgs[ii], methodArgTypes[ii]); + methodMatchScore += MatchScore((v = callArgs->args[ii]), methodArgTypes[ii]); if (bestParameterScore > methodParameterScore || bestMatchScore > methodMatchScore) { best = attempt; @@ -1491,40 +1481,38 @@ void CallArgument::initAsType(int callType) } } -void CallArgument::fromValue(int callType, QV8Engine *engine, const QV4::Value &value) +void CallArgument::fromValue(int callType, QV8Engine *engine, const QV4::ValueRef value) { if (type != 0) { cleanup(); type = 0; } if (callType == qMetaTypeId<QJSValue>()) { QV4::ExecutionEngine *v4 = QV8Engine::getV4(engine); - QV4::Scope scope(v4); - QV4::ScopedValue v(scope, value); - qjsValuePtr = new (&allocData) QJSValue(new QJSValuePrivate(v4, v)); + qjsValuePtr = new (&allocData) QJSValue(new QJSValuePrivate(v4, value)); type = qMetaTypeId<QJSValue>(); } else if (callType == QMetaType::Int) { - intValue = quint32(value.toInt32()); + intValue = quint32(value->toInt32()); type = callType; } else if (callType == QMetaType::UInt) { - intValue = quint32(value.toUInt32()); + intValue = quint32(value->toUInt32()); type = callType; } else if (callType == QMetaType::Bool) { - boolValue = value.toBoolean(); + boolValue = value->toBoolean(); type = callType; } else if (callType == QMetaType::Double) { - doubleValue = double(value.toNumber()); + doubleValue = double(value->toNumber()); type = callType; } else if (callType == QMetaType::Float) { - floatValue = float(value.toNumber()); + floatValue = float(value->toNumber()); type = callType; } else if (callType == QMetaType::QString) { - if (value.isNull() || value.isUndefined()) + if (value->isNull() || value->isUndefined()) qstringPtr = new (&allocData) QString(); else - qstringPtr = new (&allocData) QString(value.toQStringNoThrow()); + qstringPtr = new (&allocData) QString(value->toQStringNoThrow()); type = callType; } else if (callType == QMetaType::QObjectStar) { qobjectPtr = 0; - if (QV4::QObjectWrapper *qobjectWrapper = value.as<QV4::QObjectWrapper>()) + if (QV4::QObjectWrapper *qobjectWrapper = value->as<QV4::QObjectWrapper>()) qobjectPtr = qobjectWrapper->object(); type = callType; } else if (callType == qMetaTypeId<QVariant>()) { @@ -1532,7 +1520,7 @@ void CallArgument::fromValue(int callType, QV8Engine *engine, const QV4::Value & type = callType; } else if (callType == qMetaTypeId<QList<QObject*> >()) { qlistPtr = new (&allocData) QList<QObject *>(); - if (QV4::ArrayObject *array = value.asArrayObject()) { + if (QV4::ArrayObject *array = value->asArrayObject()) { QV4::Scope scope(array->engine()); Scoped<QV4::QObjectWrapper> qobjectWrapper(scope); @@ -1546,19 +1534,19 @@ void CallArgument::fromValue(int callType, QV8Engine *engine, const QV4::Value & } } else { QObject *o = 0; - if (QV4::QObjectWrapper *qobjectWrapper = value.as<QV4::QObjectWrapper>()) + if (QV4::QObjectWrapper *qobjectWrapper = value->as<QV4::QObjectWrapper>()) o = qobjectWrapper->object(); qlistPtr->append(o); } type = callType; } else if (callType == qMetaTypeId<QQmlV4Handle>()) { - handlePtr = new (&allocData) QQmlV4Handle(value.asReturnedValue()); + handlePtr = new (&allocData) QQmlV4Handle(value->asReturnedValue()); type = callType; } else if (callType == QMetaType::QJsonArray) { - jsonArrayPtr = new (&allocData) QJsonArray(QV4::JsonObject::toJsonArray(value.asArrayObject())); + jsonArrayPtr = new (&allocData) QJsonArray(QV4::JsonObject::toJsonArray(value->asArrayObject())); type = callType; } else if (callType == QMetaType::QJsonObject) { - jsonObjectPtr = new (&allocData) QJsonObject(QV4::JsonObject::toJsonObject(value.asObject())); + jsonObjectPtr = new (&allocData) QJsonObject(QV4::JsonObject::toJsonObject(value->asObject())); type = callType; } else if (callType == QMetaType::QJsonValue) { jsonValuePtr = new (&allocData) QJsonValue(QV4::JsonObject::toJsonValue(value)); @@ -1771,11 +1759,10 @@ ReturnedValue QObjectMethod::callInternal(CallData *callData) return rv.asReturnedValue(); } - CallArgs callArgs(callData->argc, callData->args); if (!method.isOverload()) { - return CallPrecise(object, method, v8Engine, callArgs); + return CallPrecise(object, method, v8Engine, callData); } else { - return CallOverloaded(object, method, v8Engine, callArgs); + return CallOverloaded(object, method, v8Engine, callData); } } diff --git a/src/qml/jsruntime/qv4sequenceobject.cpp b/src/qml/jsruntime/qv4sequenceobject.cpp index f0a71a8318..e8ba80de35 100644 --- a/src/qml/jsruntime/qv4sequenceobject.cpp +++ b/src/qml/jsruntime/qv4sequenceobject.cpp @@ -624,15 +624,18 @@ QVariant SequencePrototype::toVariant(QV4::Object *object) return QQml##ElementTypeName##List::toVariant(a); \ } else -QVariant SequencePrototype::toVariant(const QV4::Value &array, int typeHint, bool *succeeded) +QVariant SequencePrototype::toVariant(const QV4::ValueRef array, int typeHint, bool *succeeded) { *succeeded = true; - QV4::ArrayObject *a = array.asArrayObject(); - if (!a) { + if (!array->asArrayObject()) { *succeeded = false; return QVariant(); } + QV4::Scope scope(array->engine()); + // ### GC + QV4::ArrayObject *a = array->asArrayObject(); + FOREACH_QML_SEQUENCE_TYPE(SEQUENCE_TO_VARIANT) { /* else */ *succeeded = false; return QVariant(); } } diff --git a/src/qml/jsruntime/qv4sequenceobject_p.h b/src/qml/jsruntime/qv4sequenceobject_p.h index 260fea9897..ca58b11090 100644 --- a/src/qml/jsruntime/qv4sequenceobject_p.h +++ b/src/qml/jsruntime/qv4sequenceobject_p.h @@ -81,7 +81,7 @@ struct SequencePrototype : public QV4::Object static ReturnedValue fromVariant(QV4::ExecutionEngine *engine, const QVariant& v, bool *succeeded); static int metaTypeForSequence(QV4::Object *object); static QVariant toVariant(QV4::Object *object); - static QVariant toVariant(const QV4::Value &array, int typeHint, bool *succeeded); + static QVariant toVariant(const ValueRef array, int typeHint, bool *succeeded); }; } diff --git a/src/qml/jsruntime/qv4serialize.cpp b/src/qml/jsruntime/qv4serialize.cpp index e62027ab9e..ef2ca8bfc8 100644 --- a/src/qml/jsruntime/qv4serialize.cpp +++ b/src/qml/jsruntime/qv4serialize.cpp @@ -391,7 +391,7 @@ ReturnedValue Serialize::deserialize(const char *&data, QV8Engine *engine) array->arrayDataLen = ii + 1; } array->setArrayLengthUnchecked(seqLength); - QVariant seqVariant = QV4::SequencePrototype::toVariant(array.asValue(), sequenceType, &succeeded); + QVariant seqVariant = QV4::SequencePrototype::toVariant(array, sequenceType, &succeeded); return QV4::SequencePrototype::fromVariant(v4, seqVariant, &succeeded); } } diff --git a/src/qml/jsruntime/qv4value_p.h b/src/qml/jsruntime/qv4value_p.h index 598d30f1f0..3134309d72 100644 --- a/src/qml/jsruntime/qv4value_p.h +++ b/src/qml/jsruntime/qv4value_p.h @@ -348,7 +348,7 @@ struct Q_QML_PRIVATE_EXPORT PersistentValuePrivate { PersistentValuePrivate(ReturnedValue v, ExecutionEngine *engine = 0, bool weak = false); virtual ~PersistentValuePrivate(); - Value value; + SafeValue value; uint refcount; bool weak; QV4::ExecutionEngine *engine; diff --git a/src/qml/jsruntime/qv4variantobject.cpp b/src/qml/jsruntime/qv4variantobject.cpp index 97dcee2fde..de72de2f07 100644 --- a/src/qml/jsruntime/qv4variantobject.cpp +++ b/src/qml/jsruntime/qv4variantobject.cpp @@ -69,24 +69,25 @@ VariantObject::VariantObject(ExecutionEngine *engine, const QVariant &value) internalClass->engine->scarceResources.insert(this); } -QVariant VariantObject::toVariant(const QV4::Value &v) +QVariant VariantObject::toVariant(const QV4::ValueRef v) { - if (Object *o = v.asObject()) - return o->engine()->v8Engine->variantFromJS(v); - - if (v.isString()) - return QVariant(v.stringValue()->toQString()); - if (v.isBoolean()) - return QVariant(v.booleanValue()); - if (v.isNumber()) { - QV4::Value val = v; + if (v->asObject()) + return v->engine()->v8Engine->variantFromJS(v); + + if (v->isString()) + return QVariant(v->stringValue()->toQString()); + if (v->isBoolean()) + return QVariant(v->booleanValue()); + if (v->isNumber()) { + QV4::SafeValue val; + val = v; if (val.isInt32()) return QVariant(val.integerValue()); - return QVariant(v.asDouble()); + return QVariant(v->asDouble()); } - if (v.isNull()) + if (v->isNull()) return QVariant(QMetaType::VoidStar, 0); - Q_ASSERT(v.isUndefined()); + Q_ASSERT(v->isUndefined()); return QVariant(); } diff --git a/src/qml/jsruntime/qv4variantobject_p.h b/src/qml/jsruntime/qv4variantobject_p.h index 65c1db0d88..4d852142aa 100644 --- a/src/qml/jsruntime/qv4variantobject_p.h +++ b/src/qml/jsruntime/qv4variantobject_p.h @@ -71,7 +71,7 @@ public: VariantObject(InternalClass *ic); VariantObject(ExecutionEngine *engine, const QVariant &value); - static QVariant toVariant(const QV4::Value &v); + static QVariant toVariant(const ValueRef v); void addVmePropertyReference(); void removeVmePropertyReference(); diff --git a/src/qml/qml/qqmlproperty.cpp b/src/qml/qml/qqmlproperty.cpp index bcecda9c57..a0fd98483b 100644 --- a/src/qml/qml/qqmlproperty.cpp +++ b/src/qml/qml/qqmlproperty.cpp @@ -1514,13 +1514,13 @@ bool QQmlPropertyPrivate::writeBinding(QObject *object, if (isUndefined) { } else if (core.isQList()) { - value = v8engine->toVariant(*result, qMetaTypeId<QList<QObject *> >()); + value = v8engine->toVariant(result, qMetaTypeId<QList<QObject *> >()); } else if (result->isNull() && core.isQObject()) { value = QVariant::fromValue((QObject *)0); } else if (core.propType == qMetaTypeId<QList<QUrl> >()) { - value = resolvedUrlSequence(v8engine->toVariant(*result, qMetaTypeId<QList<QUrl> >()), context); + value = resolvedUrlSequence(v8engine->toVariant(result, qMetaTypeId<QList<QUrl> >()), context); } else if (!isVarProperty && type != qMetaTypeId<QJSValue>()) { - value = v8engine->toVariant(*result, type); + value = v8engine->toVariant(result, type); } if (expression->hasError()) { diff --git a/src/qml/qml/qqmlvaluetypewrapper.cpp b/src/qml/qml/qqmlvaluetypewrapper.cpp index ba3cfc0801..2740d9b269 100644 --- a/src/qml/qml/qqmlvaluetypewrapper.cpp +++ b/src/qml/qml/qqmlvaluetypewrapper.cpp @@ -385,7 +385,7 @@ void QmlValueTypeWrapper::put(Managed *m, const StringRef name, const ValueRef v oldBinding->destroy(); if (!f) { - QVariant v = r->v8->toVariant(*value, -1); + QVariant v = r->v8->toVariant(value, -1); if (p.isEnumType() && (QMetaType::Type)v.type() == QMetaType::Double) v = v.toInt(); @@ -409,7 +409,7 @@ void QmlValueTypeWrapper::put(Managed *m, const StringRef name, const ValueRef v if (index == -1) return; - QVariant v = r->v8->toVariant(*value, -1); + QVariant v = r->v8->toVariant(value, -1); r->type->setValue(copy->value); QMetaProperty p = r->type->metaObject()->property(index); diff --git a/src/qml/qml/qqmlvmemetaobject.cpp b/src/qml/qml/qqmlvmemetaobject.cpp index 18f3dff39d..9b557f882b 100644 --- a/src/qml/qml/qqmlvmemetaobject.cpp +++ b/src/qml/qml/qqmlvmemetaobject.cpp @@ -1010,8 +1010,8 @@ QVariant QQmlVMEMetaObject::readPropertyAsVariant(int id) if (ensureVarPropertiesAllocated()) { QV4::Scope scope(QQmlEnginePrivate::get(ctxt->engine)->v4engine()); QV4::ScopedObject o(scope, varProperties.value()); - return QQmlEnginePrivate::get(ctxt->engine)->v8engine()->toVariant( - QV4::Value::fromReturnedValue(o->getIndexed(id - firstVarPropertyIndex)), -1); + QV4::ScopedValue val(scope, o->getIndexed(id - firstVarPropertyIndex)); + return QQmlEnginePrivate::get(ctxt->engine)->v8engine()->toVariant(val, -1); } return QVariant(); } else { diff --git a/src/qml/qml/v8/qv8engine.cpp b/src/qml/qml/v8/qv8engine.cpp index 40b512bdc7..a7eb23387f 100644 --- a/src/qml/qml/v8/qv8engine.cpp +++ b/src/qml/qml/v8/qv8engine.cpp @@ -117,27 +117,27 @@ QV8Engine::~QV8Engine() delete m_v4Engine; } -QVariant QV8Engine::toVariant(const QV4::Value &value, int typeHint) +QVariant QV8Engine::toVariant(const QV4::ValueRef value, int typeHint) { - Q_ASSERT (!value.isEmpty()); + Q_ASSERT (!value->isEmpty()); QV4::Scope scope(m_v4Engine); - QV4::ScopedValue v(scope, value); +// QV4::ScopedValue v(scope, value); - if (QV4::VariantObject *v = value.as<QV4::VariantObject>()) + if (QV4::VariantObject *v = value->as<QV4::VariantObject>()) return v->data; if (typeHint == QVariant::Bool) - return QVariant(value.toBoolean()); + return QVariant(value->toBoolean()); if (typeHint == QMetaType::QJsonValue) return QVariant::fromValue(QV4::JsonObject::toJsonValue(value)); if (typeHint == qMetaTypeId<QJSValue>()) - return QVariant::fromValue(QJSValue(new QJSValuePrivate(m_v4Engine, v))); + return QVariant::fromValue(QJSValue(new QJSValuePrivate(m_v4Engine, value))); - if (QV4::Object *object = value.asObject()) { + if (QV4::Object *object = value->asObject()) { if (typeHint == QMetaType::QJsonObject - && !value.asArrayObject() && !value.asFunctionObject()) { + && !value->asArrayObject() && !value->asFunctionObject()) { return QVariant::fromValue(QV4::JsonObject::toJsonObject(object)); } else if (QV4::QObjectWrapper *wrapper = object->as<QV4::QObjectWrapper>()) { return qVariantFromValue<QObject *>(wrapper->object()); @@ -153,7 +153,7 @@ QVariant QV8Engine::toVariant(const QV4::Value &value, int typeHint) return QV4::SequencePrototype::toVariant(object); } - if (QV4::ArrayObject *a = value.asArrayObject()) { + if (QV4::ArrayObject *a = value->asArrayObject()) { QV4::Scope scope(a->engine()); if (typeHint == qMetaTypeId<QList<QObject *> >()) { QList<QObject *> list; @@ -373,27 +373,27 @@ QQmlContextData *QV8Engine::callingContext() // Date -> QVariant(QDateTime) // RegExp -> QVariant(QRegExp) // [Any other object] -> QVariantMap(...) -QVariant QV8Engine::toBasicVariant(const QV4::Value &value) +QVariant QV8Engine::toBasicVariant(const QV4::ValueRef value) { - if (value.isNull() || value.isUndefined()) + if (value->isNullOrUndefined()) return QVariant(); - if (value.isBoolean()) - return value.booleanValue(); - if (value.isInteger()) - return value.integerValue(); - if (value.isNumber()) - return value.asDouble(); - if (value.isString()) - return value.stringValue()->toQString(); - if (QV4::DateObject *d = value.asDateObject()) + if (value->isBoolean()) + return value->booleanValue(); + if (value->isInteger()) + return value->integerValue(); + if (value->isNumber()) + return value->asDouble(); + if (value->isString()) + return value->stringValue()->toQString(); + if (QV4::DateObject *d = value->asDateObject()) return d->toQDateTime(); // NOTE: since we convert QTime to JS Date, round trip will change the variant type (to QDateTime)! - Q_ASSERT(value.isObject()); + Q_ASSERT(value->isObject()); - if (QV4::RegExpObject *re = value.as<QV4::RegExpObject>()) + if (QV4::RegExpObject *re = value->as<QV4::RegExpObject>()) return re->toQRegExp(); - if (QV4::ArrayObject *a = value.asArrayObject()) { + if (QV4::ArrayObject *a = value->asArrayObject()) { QV4::Scope scope(a->engine()); QV4::ScopedValue v(scope); QVariantList rv; @@ -405,8 +405,8 @@ QVariant QV8Engine::toBasicVariant(const QV4::Value &value) } return rv; } - if (!value.asFunctionObject()) - return variantMapFromJS(value.asObject()); + if (!value->asFunctionObject()) + return variantMapFromJS(value->asObject()); return QVariant(); } @@ -620,7 +620,8 @@ QVariantMap QV8Engine::variantMapFromJS(QV4::Object *o, break; QString key = name->toQStringNoThrow(); - result.insert(key, variantFromJS(v, visitedObjects)); + QV4::ScopedValue val(scope, v); + result.insert(key, variantFromJS(val, visitedObjects)); } visitedObjects.remove(o); @@ -713,92 +714,93 @@ QV4::ReturnedValue QV8Engine::metaTypeToJS(int type, const void *data) // Converts a JS value to a meta-type. // data must point to a place that can store a value of the given type. // Returns true if conversion succeeded, false otherwise. -bool QV8Engine::metaTypeFromJS(const QV4::Value &value, int type, void *data) { +bool QV8Engine::metaTypeFromJS(const QV4::ValueRef value, int type, void *data) +{ QV4::Scope scope(QV8Engine::getV4(this)); // check if it's one of the types we know switch (QMetaType::Type(type)) { case QMetaType::Bool: - *reinterpret_cast<bool*>(data) = value.toBoolean(); + *reinterpret_cast<bool*>(data) = value->toBoolean(); return true; case QMetaType::Int: - *reinterpret_cast<int*>(data) = value.toInt32(); + *reinterpret_cast<int*>(data) = value->toInt32(); return true; case QMetaType::UInt: - *reinterpret_cast<uint*>(data) = value.toUInt32(); + *reinterpret_cast<uint*>(data) = value->toUInt32(); return true; case QMetaType::LongLong: - *reinterpret_cast<qlonglong*>(data) = qlonglong(value.toInteger()); + *reinterpret_cast<qlonglong*>(data) = qlonglong(value->toInteger()); return true; case QMetaType::ULongLong: - *reinterpret_cast<qulonglong*>(data) = qulonglong(value.toInteger()); + *reinterpret_cast<qulonglong*>(data) = qulonglong(value->toInteger()); return true; case QMetaType::Double: - *reinterpret_cast<double*>(data) = value.toNumber(); + *reinterpret_cast<double*>(data) = value->toNumber(); return true; case QMetaType::QString: - if (value.isUndefined() || value.isNull()) + if (value->isUndefined() || value->isNull()) *reinterpret_cast<QString*>(data) = QString(); else - *reinterpret_cast<QString*>(data) = value.toString(m_v4Engine->current)->toQString(); + *reinterpret_cast<QString*>(data) = value->toString(m_v4Engine->current)->toQString(); return true; case QMetaType::Float: - *reinterpret_cast<float*>(data) = value.toNumber(); + *reinterpret_cast<float*>(data) = value->toNumber(); return true; case QMetaType::Short: - *reinterpret_cast<short*>(data) = short(value.toInt32()); + *reinterpret_cast<short*>(data) = short(value->toInt32()); return true; case QMetaType::UShort: - *reinterpret_cast<unsigned short*>(data) = value.toUInt16(); + *reinterpret_cast<unsigned short*>(data) = value->toUInt16(); return true; case QMetaType::Char: - *reinterpret_cast<char*>(data) = char(value.toInt32()); + *reinterpret_cast<char*>(data) = char(value->toInt32()); return true; case QMetaType::UChar: - *reinterpret_cast<unsigned char*>(data) = (unsigned char)(value.toInt32()); + *reinterpret_cast<unsigned char*>(data) = (unsigned char)(value->toInt32()); return true; case QMetaType::QChar: - if (value.isString()) { - QString str = value.stringValue()->toQString(); + if (value->isString()) { + QString str = value->stringValue()->toQString(); *reinterpret_cast<QChar*>(data) = str.isEmpty() ? QChar() : str.at(0); } else { - *reinterpret_cast<QChar*>(data) = QChar(ushort(value.toUInt16())); + *reinterpret_cast<QChar*>(data) = QChar(ushort(value->toUInt16())); } return true; case QMetaType::QDateTime: - if (QV4::DateObject *d = value.asDateObject()) { + if (QV4::DateObject *d = value->asDateObject()) { *reinterpret_cast<QDateTime *>(data) = d->toQDateTime(); return true; } break; case QMetaType::QDate: - if (QV4::DateObject *d = value.asDateObject()) { + if (QV4::DateObject *d = value->asDateObject()) { *reinterpret_cast<QDate *>(data) = d->toQDateTime().date(); return true; } break; case QMetaType::QRegExp: - if (QV4::RegExpObject *r = value.as<QV4::RegExpObject>()) { + if (QV4::RegExpObject *r = value->as<QV4::RegExpObject>()) { *reinterpret_cast<QRegExp *>(data) = r->toQRegExp(); return true; } break; case QMetaType::QObjectStar: { - QV4::QObjectWrapper *qobjectWrapper = value.as<QV4::QObjectWrapper>(); - if (qobjectWrapper || value.isNull()) { + QV4::QObjectWrapper *qobjectWrapper = value->as<QV4::QObjectWrapper>(); + if (qobjectWrapper || value->isNull()) { *reinterpret_cast<QObject* *>(data) = qtObjectFromJS(value); return true; } break; } case QMetaType::QStringList: - if (QV4::ArrayObject *a = value.asArrayObject()) { + if (QV4::ArrayObject *a = value->asArrayObject()) { *reinterpret_cast<QStringList *>(data) = a->toQStringList(); return true; } break; case QMetaType::QVariantList: - if (QV4::ArrayObject *a = value.asArrayObject()) { + if (QV4::ArrayObject *a = value->asArrayObject()) { *reinterpret_cast<QVariantList *>(data) = variantListFromJS(a); return true; } break; case QMetaType::QVariantMap: - if (QV4::Object *o = value.asObject()) { + if (QV4::Object *o = value->asObject()) { *reinterpret_cast<QVariantMap *>(data) = variantMapFromJS(o); return true; } break; @@ -809,10 +811,10 @@ bool QV8Engine::metaTypeFromJS(const QV4::Value &value, int type, void *data) { *reinterpret_cast<QJsonValue *>(data) = QV4::JsonObject::toJsonValue(value); return true; case QMetaType::QJsonObject: - *reinterpret_cast<QJsonObject *>(data) = QV4::JsonObject::toJsonObject(value.asObject()); + *reinterpret_cast<QJsonObject *>(data) = QV4::JsonObject::toJsonObject(value->asObject()); return true; case QMetaType::QJsonArray: - *reinterpret_cast<QJsonArray *>(data) = QV4::JsonObject::toJsonArray(value.asArrayObject()); + *reinterpret_cast<QJsonArray *>(data) = QV4::JsonObject::toJsonArray(value->asArrayObject()); return true; default: ; @@ -842,14 +844,14 @@ bool QV8Engine::metaTypeFromJS(const QV4::Value &value, int type, void *data) { QByteArray name = QMetaType::typeName(type); if (convertToNativeQObject(value, name, reinterpret_cast<void* *>(data))) return true; - if (value.as<QV4::VariantObject>() && name.endsWith('*')) { + if (value->as<QV4::VariantObject>() && name.endsWith('*')) { int valueType = QMetaType::type(name.left(name.size()-1)); - QVariant &var = value.as<QV4::VariantObject>()->data; + QVariant &var = value->as<QV4::VariantObject>()->data; if (valueType == var.userType()) { // We have T t, T* is requested, so return &t. *reinterpret_cast<void* *>(data) = var.data(); return true; - } else if (QV4::Object *o = value.asObject()) { + } else if (QV4::Object *o = value->asObject()) { // Look in the prototype chain. QV4::Object *proto = o->prototype(); while (proto) { @@ -860,7 +862,8 @@ bool QV8Engine::metaTypeFromJS(const QV4::Value &value, int type, void *data) { } else if (proto->as<QV4::QObjectWrapper>()) { QByteArray className = name.left(name.size()-1); - if (QObject *qobject = qtObjectFromJS(QV4::Value::fromObject(proto))) + QV4::ScopedObject p(scope, proto); + if (QObject *qobject = qtObjectFromJS(p)) canCast = qobject->qt_metacast(className) != 0; } if (canCast) { @@ -874,11 +877,11 @@ bool QV8Engine::metaTypeFromJS(const QV4::Value &value, int type, void *data) { proto = proto->prototype(); } } - } else if (value.isNull() && name.endsWith('*')) { + } else if (value->isNull() && name.endsWith('*')) { *reinterpret_cast<void* *>(data) = 0; return true; } else if (type == qMetaTypeId<QJSValue>()) { - *reinterpret_cast<QJSValue*>(data) = QJSValuePrivate::get(new QJSValuePrivate(m_v4Engine, QV4::ScopedValue(scope, value))); + *reinterpret_cast<QJSValue*>(data) = QJSValuePrivate::get(new QJSValuePrivate(m_v4Engine, value)); return true; } @@ -901,40 +904,40 @@ QV4::ReturnedValue QV8Engine::variantToJS(const QVariant &value) // Date -> QVariant(QDateTime) // RegExp -> QVariant(QRegExp) // [Any other object] -> QVariantMap(...) -QVariant QV8Engine::variantFromJS(const QV4::Value &value, +QVariant QV8Engine::variantFromJS(const QV4::ValueRef value, V8ObjectSet &visitedObjects) { - Q_ASSERT(!value.isEmpty()); - if (value.isUndefined()) + Q_ASSERT(!value->isEmpty()); + if (value->isUndefined()) return QVariant(); - if (value.isNull()) + if (value->isNull()) return QVariant(QMetaType::VoidStar, 0); - if (value.isBoolean()) - return value.booleanValue(); - if (value.isInteger()) - return value.integerValue(); - if (value.isNumber()) - return value.asDouble(); - if (value.isString()) - return value.stringValue()->toQString(); - Q_ASSERT(value.isObject()); - if (QV4::ArrayObject *a = value.asArrayObject()) + if (value->isBoolean()) + return value->booleanValue(); + if (value->isInteger()) + return value->integerValue(); + if (value->isNumber()) + return value->asDouble(); + if (value->isString()) + return value->stringValue()->toQString(); + Q_ASSERT(value->isObject()); + if (QV4::ArrayObject *a = value->asArrayObject()) return variantListFromJS(a, visitedObjects); - if (QV4::DateObject *d = value.asDateObject()) + if (QV4::DateObject *d = value->asDateObject()) return d->toQDateTime(); - if (QV4::RegExpObject *re = value.as<QV4::RegExpObject>()) + if (QV4::RegExpObject *re = value->as<QV4::RegExpObject>()) return re->toQRegExp(); - if (QV4::VariantObject *v = value.as<QV4::VariantObject>()) + if (QV4::VariantObject *v = value->as<QV4::VariantObject>()) return v->data; - if (value.as<QV4::QObjectWrapper>()) + if (value->as<QV4::QObjectWrapper>()) return qVariantFromValue(qtObjectFromJS(value)); - if (QV4::QmlValueTypeWrapper *v = value.as<QV4::QmlValueTypeWrapper>()) + if (QV4::QmlValueTypeWrapper *v = value->as<QV4::QmlValueTypeWrapper>()) return v->toVariant(); - return variantMapFromJS(value.asObject(), visitedObjects); + return variantMapFromJS(value->asObject(), visitedObjects); } -bool QV8Engine::convertToNativeQObject(const QV4::Value &value, const QByteArray &targetType, void **result) +bool QV8Engine::convertToNativeQObject(const QV4::ValueRef value, const QByteArray &targetType, void **result) { if (!targetType.endsWith('*')) return false; @@ -949,19 +952,21 @@ bool QV8Engine::convertToNativeQObject(const QV4::Value &value, const QByteArray return false; } -QObject *QV8Engine::qtObjectFromJS(const QV4::Value &value) +QObject *QV8Engine::qtObjectFromJS(const QV4::ValueRef value) { - if (!value.isObject()) + if (!value->isObject()) return 0; + QV4::Scope scope(m_v4Engine); + QV4::Scoped<QV4::VariantObject> v(scope, value); - if (QV4::VariantObject *v = value.as<QV4::VariantObject>()) { + if (v) { QVariant variant = v->data; int type = variant.userType(); if (type == QMetaType::QObjectStar) return *reinterpret_cast<QObject* const *>(variant.constData()); } - QV4::QObjectWrapper *wrapper = value.as<QV4::QObjectWrapper>(); + QV4::Scoped<QV4::QObjectWrapper> wrapper(scope, value); if (!wrapper) return 0; return wrapper->object(); diff --git a/src/qml/qml/v8/qv8engine_p.h b/src/qml/qml/v8/qv8engine_p.h index e27be50f29..04f4d5e6be 100644 --- a/src/qml/qml/v8/qv8engine_p.h +++ b/src/qml/qml/v8/qv8engine_p.h @@ -205,7 +205,7 @@ public: void freezeObject(const QV4::ValueRef value); - QVariant toVariant(const QV4::Value &value, int typeHint); + QVariant toVariant(const QV4::ValueRef value, int typeHint); QV4::ReturnedValue fromVariant(const QVariant &); // Return a JS string for the given QString \a string @@ -236,13 +236,13 @@ public: { V8ObjectSet visitedObjects; return variantMapFromJS(object, visitedObjects); } QV4::ReturnedValue variantToJS(const QVariant &value); - inline QVariant variantFromJS(const QV4::Value &value) + inline QVariant variantFromJS(const QV4::ValueRef value) { V8ObjectSet visitedObjects; return variantFromJS(value, visitedObjects); } QV4::ReturnedValue metaTypeToJS(int type, const void *data); - bool metaTypeFromJS(const QV4::Value &value, int type, void *data); + bool metaTypeFromJS(const QV4::ValueRef value, int type, void *data); - bool convertToNativeQObject(const QV4::Value &value, + bool convertToNativeQObject(const QV4::ValueRef value, const QByteArray &targetType, void **result); @@ -253,7 +253,7 @@ public: // used for console.count() int consoleCountHelper(const QString &file, quint16 line, quint16 column); - QObject *qtObjectFromJS(const QV4::Value &value); + QObject *qtObjectFromJS(const QV4::ValueRef value); protected: QJSEngine* q; @@ -275,14 +275,14 @@ protected: QHash<QString, quint32> m_consoleCount; - QVariant toBasicVariant(const QV4::Value &); + QVariant toBasicVariant(const QV4::ValueRef); void initializeGlobal(); private: QVariantList variantListFromJS(QV4::ArrayObject *array, V8ObjectSet &visitedObjects); QVariantMap variantMapFromJS(QV4::Object *object, V8ObjectSet &visitedObjects); - QVariant variantFromJS(const QV4::Value &value, V8ObjectSet &visitedObjects); + QVariant variantFromJS(const QV4::ValueRef value, V8ObjectSet &visitedObjects); Q_DISABLE_COPY(QV8Engine) }; diff --git a/src/qml/types/qqmldelegatemodel.cpp b/src/qml/types/qqmldelegatemodel.cpp index 8c434ccfdc..148332c4bd 100644 --- a/src/qml/types/qqmldelegatemodel.cpp +++ b/src/qml/types/qqmldelegatemodel.cpp @@ -1561,7 +1561,8 @@ bool QQmlDelegateModelPrivate::insert(Compositor::insert_iterator &before, const propertyName = it.nextPropertyNameAsString(&value); if (propertyName->isNull()) break; - cacheItem->setValue(propertyName->toQStringNoThrow(), m_cacheMetaType->v8Engine->toVariant(value, QVariant::Invalid)); + QV4::ScopedValue v(scope, value); + cacheItem->setValue(propertyName->toQStringNoThrow(), m_cacheMetaType->v8Engine->toVariant(v, QVariant::Invalid)); } cacheItem->groups = groups | Compositor::UnresolvedFlag | Compositor::CacheFlag; diff --git a/tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp b/tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp index a5f30a01c2..625971fc05 100644 --- a/tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp +++ b/tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp @@ -2287,7 +2287,7 @@ static inline bool evaluate_error(QV8Engine *engine, const QV4::Value &o, const return false; } -static inline bool evaluate_value(QV8Engine *engine, const QV4::Value &o, +static inline bool evaluate_value(QV8Engine *engine, const QV4::ValueRef o, const char *source, const QV4::Value &result) { QString functionSource = QLatin1String("(function(object) { return ") + @@ -2424,8 +2424,8 @@ void tst_qqmlecmascript::callQtInvokables() o->reset(); { - QV4::Value ret = EVALUATE("object.method_NoArgs_QPointF()"); - QVERIFY(!ret.isUndefined()); + QV4::ScopedValue ret(scope, EVALUATE("object.method_NoArgs_QPointF()")); + QVERIFY(!ret->isUndefined()); QCOMPARE(engine->toVariant(ret, -1), QVariant(QPointF(123, 4.5))); QCOMPARE(o->error(), false); QCOMPARE(o->invoked(), 3); @@ -2434,8 +2434,8 @@ void tst_qqmlecmascript::callQtInvokables() o->reset(); { - QV4::Value ret = EVALUATE("object.method_NoArgs_QObject()"); - QV4::QObjectWrapper *qobjectWrapper = ret.as<QV4::QObjectWrapper>(); + QV4::ScopedValue ret(scope, EVALUATE("object.method_NoArgs_QObject()")); + QV4::QObjectWrapper *qobjectWrapper = ret->as<QV4::QObjectWrapper>(); QVERIFY(qobjectWrapper); QCOMPARE(qobjectWrapper->object(), (QObject *)o); QCOMPARE(o->error(), false); @@ -2460,7 +2460,7 @@ void tst_qqmlecmascript::callQtInvokables() } o->reset(); - QVERIFY(EVALUATE_VALUE("object.method_NoArgs_QVariant()", engine->toString("QML rocks"))); + QVERIFY(EVALUATE_VALUE("object.method_NoArgs_QVariant()", QV4::Value::fromReturnedValue(engine->toString("QML rocks")))); QCOMPARE(o->error(), false); QCOMPARE(o->invoked(), 7); QCOMPARE(o->actuals().count(), 0); |