diff options
author | Simon Hausmann <simon.hausmann@theqtcompany.com> | 2014-11-20 09:07:52 +0100 |
---|---|---|
committer | Simon Hausmann <simon.hausmann@digia.com> | 2014-12-29 14:39:22 +0100 |
commit | efc3cc717ac1a62965465e909cc99acef627cdb1 (patch) | |
tree | 9d181ca8e9e299fa99b9b7598bfb83bc53056dde /src/qml/qml | |
parent | 65953304a2775e69c7edd46b780aa39f769d32ac (diff) |
Make QQmlPropertyCache available in QJSEngine
The QQmlEngine has two containers for property caches, one for QML types and
one for all-purpose meta-objects. The latter is rather useful and now being
moved to QJSEngine to be available there.
Change-Id: Ieab65c400b8a2e410e5f9eee6d603162dbb864d9
Reviewed-by: Lars Knoll <lars.knoll@digia.com>
Diffstat (limited to 'src/qml/qml')
-rw-r--r-- | src/qml/qml/qqmlboundsignal.cpp | 2 | ||||
-rw-r--r-- | src/qml/qml/qqmlengine.cpp | 20 | ||||
-rw-r--r-- | src/qml/qml/qqmlengine_p.h | 108 | ||||
-rw-r--r-- | src/qml/qml/qqmlopenmetaobject.cpp | 1 | ||||
-rw-r--r-- | src/qml/qml/qqmlpropertycache.cpp | 13 | ||||
-rw-r--r-- | src/qml/qml/qqmlpropertycache_p.h | 10 |
6 files changed, 15 insertions, 139 deletions
diff --git a/src/qml/qml/qqmlboundsignal.cpp b/src/qml/qml/qqmlboundsignal.cpp index f8718ad0ee..8baeefe62b 100644 --- a/src/qml/qml/qqmlboundsignal.cpp +++ b/src/qml/qml/qqmlboundsignal.cpp @@ -217,7 +217,7 @@ void QQmlBoundSignalExpression::evaluate(void **a) //TODO: look at using the property cache here (as in the compiler) // for further optimization QMetaMethod signal = QMetaObjectPrivate::signal(m_target->metaObject(), m_index); - expression += QQmlPropertyCache::signalParameterStringForJS(engine(), signal.parameterNames(), &error); + expression += QQmlPropertyCache::signalParameterStringForJS(scope.engine, signal.parameterNames(), &error); if (!error.isEmpty()) { qmlInfo(scopeObject()) << error; diff --git a/src/qml/qml/qqmlengine.cpp b/src/qml/qml/qqmlengine.cpp index f9de7adc93..8f2c554a7e 100644 --- a/src/qml/qml/qqmlengine.cpp +++ b/src/qml/qml/qqmlengine.cpp @@ -559,7 +559,7 @@ QQmlEnginePrivate::QQmlEnginePrivate(QQmlEngine *e) activeObjectCreator(0), networkAccessManager(0), networkAccessManagerFactory(0), urlInterceptor(0), scarceResourcesRefCount(0), typeLoader(e), importDatabase(e), uniqueId(1), - incubatorCount(0), incubationController(0), mutex(QMutex::Recursive) + incubatorCount(0), incubationController(0) { } @@ -582,8 +582,6 @@ QQmlEnginePrivate::~QQmlEnginePrivate() if (incubationController) incubationController->d = 0; incubationController = 0; - for(QHash<const QMetaObject *, QQmlPropertyCache *>::Iterator iter = propertyCache.begin(); iter != propertyCache.end(); ++iter) - (*iter)->release(); for(QHash<QPair<QQmlType *, int>, QQmlPropertyCache *>::Iterator iter = typePropertyCache.begin(); iter != typePropertyCache.end(); ++iter) (*iter)->release(); for (QHash<int, QQmlCompiledData *>::Iterator iter = m_compositeTypes.begin(); iter != m_compositeTypes.end(); ++iter) @@ -2043,22 +2041,6 @@ QString QQmlEngine::offlineStoragePath() const return d->offlineStoragePath; } -QQmlPropertyCache *QQmlEnginePrivate::createCache(const QMetaObject *mo) -{ - Q_Q(QQmlEngine); - - if (!mo->superClass()) { - QQmlPropertyCache *rv = new QQmlPropertyCache(q, mo); - propertyCache.insert(mo, rv); - return rv; - } else { - QQmlPropertyCache *super = cache(mo->superClass()); - QQmlPropertyCache *rv = super->copyAndAppend(mo); - propertyCache.insert(mo, rv); - return rv; - } -} - QQmlPropertyCache *QQmlEnginePrivate::createCache(QQmlType *type, int minorVersion, QQmlError &error) { diff --git a/src/qml/qml/qqmlengine_p.h b/src/qml/qml/qqmlengine_p.h index a1935b854b..de2a2d3e1d 100644 --- a/src/qml/qml/qqmlengine_p.h +++ b/src/qml/qml/qqmlengine_p.h @@ -208,9 +208,8 @@ public: inline static void deleteInEngineThread(QQmlEngine *, T *); // These methods may be called from the loader thread - inline QQmlPropertyCache *cache(QObject *obj); - inline QQmlPropertyCache *cache(const QMetaObject *); inline QQmlPropertyCache *cache(QQmlType *, int, QQmlError &error); + using QJSEnginePrivate::cache; // These methods may be called from the loader thread bool isQObject(int); @@ -260,40 +259,13 @@ public: static bool qml_debugging_enabled; mutable QMutex networkAccessManagerMutex; - mutable QMutex mutex; private: - // Locker locks the QQmlEnginePrivate data structures for read and write, if necessary. - // Currently, locking is only necessary if the threaded loader is running concurrently. If it is - // either idle, or is running with the main thread blocked, no locking is necessary. This way - // we only pay for locking when we have to. - // Consequently, this class should only be used to protect simple accesses or modifications of the - // QQmlEnginePrivate structures or operations that can be guaranteed not to start activity - // on the loader thread. - // The Locker API is identical to QMutexLocker. Locker reuses the QQmlEnginePrivate::mutex - // QMutex instance and multiple Lockers are recursive in the same thread. - class Locker - { - public: - inline Locker(const QQmlEngine *); - inline Locker(const QQmlEnginePrivate *); - inline ~Locker(); - - inline void unlock(); - inline void relock(); - - private: - const QQmlEnginePrivate *m_ep; - quint32 m_locked:1; - }; - // Must be called locked - QQmlPropertyCache *createCache(const QMetaObject *); QQmlPropertyCache *createCache(QQmlType *, int, QQmlError &error); // These members must be protected by a QQmlEnginePrivate::Locker as they are required by // the threaded loader. Only access them through their respective accessor methods. - QHash<const QMetaObject *, QQmlPropertyCache *> propertyCache; QHash<QPair<QQmlType *, int>, QQmlPropertyCache *> typePropertyCache; QHash<int, int> m_qmlLists; QHash<int, QQmlCompiledData *> m_compositeTypes; @@ -306,38 +278,6 @@ private: void doDeleteInEngineThread(); }; -QQmlEnginePrivate::Locker::Locker(const QQmlEngine *e) -: m_ep(QQmlEnginePrivate::get(e)) -{ - relock(); -} - -QQmlEnginePrivate::Locker::Locker(const QQmlEnginePrivate *e) -: m_ep(e), m_locked(false) -{ - relock(); -} - -QQmlEnginePrivate::Locker::~Locker() -{ - unlock(); -} - -void QQmlEnginePrivate::Locker::unlock() -{ - if (m_locked) { - m_ep->mutex.unlock(); - m_locked = false; - } -} - -void QQmlEnginePrivate::Locker::relock() -{ - Q_ASSERT(!m_locked); - m_ep->mutex.lock(); - m_locked = true; -} - /*! Returns true if the calling thread is the QQmlEngine thread. */ @@ -402,52 +342,6 @@ void QQmlEnginePrivate::deleteInEngineThread(QQmlEngine *engine, T *value) } /*! -Returns a QQmlPropertyCache for \a obj if one is available. - -If \a obj is null, being deleted or contains a dynamic meta object 0 -is returned. - -The returned cache is not referenced, so if it is to be stored, call addref(). - -XXX thread There is a potential future race condition in this and all the cache() -functions. As the QQmlPropertyCache is returned unreferenced, when called -from the loader thread, it is possible that the cache will have been dereferenced -and deleted before the loader thread has a chance to use or reference it. This -can't currently happen as the cache holds a reference to the -QQmlPropertyCache until the QQmlEngine is destroyed. -*/ -QQmlPropertyCache *QQmlEnginePrivate::cache(QObject *obj) -{ - if (!obj || QObjectPrivate::get(obj)->metaObject || QObjectPrivate::get(obj)->wasDeleted) - return 0; - - Locker locker(this); - const QMetaObject *mo = obj->metaObject(); - QQmlPropertyCache *rv = propertyCache.value(mo); - if (!rv) rv = createCache(mo); - return rv; -} - -/*! -Returns a QQmlPropertyCache for \a metaObject. - -As the cache is persisted for the life of the engine, \a metaObject must be -a static "compile time" meta-object, or a meta-object that is otherwise known to -exist for the lifetime of the QQmlEngine. - -The returned cache is not referenced, so if it is to be stored, call addref(). -*/ -QQmlPropertyCache *QQmlEnginePrivate::cache(const QMetaObject *metaObject) -{ - Q_ASSERT(metaObject); - - Locker locker(this); - QQmlPropertyCache *rv = propertyCache.value(metaObject); - if (!rv) rv = createCache(metaObject); - return rv; -} - -/*! Returns a QQmlPropertyCache for \a type with \a minorVersion. The returned cache is not referenced, so if it is to be stored, call addref(). diff --git a/src/qml/qml/qqmlopenmetaobject.cpp b/src/qml/qml/qqmlopenmetaobject.cpp index 9715fdc85d..e234a0bfbe 100644 --- a/src/qml/qml/qqmlopenmetaobject.cpp +++ b/src/qml/qml/qqmlopenmetaobject.cpp @@ -35,6 +35,7 @@ #include <private/qqmlpropertycache_p.h> #include <private/qqmldata_p.h> #include <private/qmetaobjectbuilder_p.h> +#include <qqmlengine.h> #include <qdebug.h> QT_BEGIN_NAMESPACE diff --git a/src/qml/qml/qqmlpropertycache.cpp b/src/qml/qml/qqmlpropertycache.cpp index 363fce4375..b5bc29aaa6 100644 --- a/src/qml/qml/qqmlpropertycache.cpp +++ b/src/qml/qml/qqmlpropertycache.cpp @@ -231,7 +231,7 @@ void QQmlPropertyData::lazyLoad(const QMetaMethod &m) /*! Creates a new empty QQmlPropertyCache. */ -QQmlPropertyCache::QQmlPropertyCache(QQmlEngine *e) +QQmlPropertyCache::QQmlPropertyCache(QJSEngine *e) : engine(e), _parent(0), propertyIndexCacheStart(0), methodIndexCacheStart(0), signalHandlerIndexCacheStart(0), _hasPropertyOverrides(false), _ownMetaObject(false), _metaObject(0), argumentsCache(0) @@ -242,7 +242,7 @@ QQmlPropertyCache::QQmlPropertyCache(QQmlEngine *e) /*! Creates a new QQmlPropertyCache of \a metaObject. */ -QQmlPropertyCache::QQmlPropertyCache(QQmlEngine *e, const QMetaObject *metaObject) +QQmlPropertyCache::QQmlPropertyCache(QJSEngine *e, const QMetaObject *metaObject) : engine(e), _parent(0), propertyIndexCacheStart(0), methodIndexCacheStart(0), signalHandlerIndexCacheStart(0), _hasPropertyOverrides(false), _ownMetaObject(false), _metaObject(0), argumentsCache(0) @@ -818,7 +818,7 @@ void QQmlPropertyCache::resolve(QQmlPropertyData *data) const data->propType = registerResult == -1 ? QMetaType::UnknownType : registerResult; } } - data->flags |= flagsForPropertyType(data->propType, engine); + data->flags |= flagsForPropertyType(data->propType, qobject_cast<QQmlEngine*>(engine)); } data->flags &= ~QQmlPropertyData::NotFullyResolved; @@ -1135,7 +1135,7 @@ QString QQmlPropertyCache::signalParameterStringForJS(int index, QString *errorS } QString error; - QString parameters = signalParameterStringForJS(engine, parameterNameList, &error); + QString parameters = signalParameterStringForJS(QV8Engine::getV4(engine), parameterNameList, &error); A *arguments = static_cast<A *>(signalData->arguments); arguments->signalParameterStringForJS = new QString(!error.isEmpty() ? error : parameters); @@ -1148,11 +1148,10 @@ QString QQmlPropertyCache::signalParameterStringForJS(int index, QString *errorS return *arguments->signalParameterStringForJS; } -QString QQmlPropertyCache::signalParameterStringForJS(QQmlEngine *engine, const QList<QByteArray> ¶meterNameList, QString *errorString) +QString QQmlPropertyCache::signalParameterStringForJS(QV4::ExecutionEngine *engine, const QList<QByteArray> ¶meterNameList, QString *errorString) { - QQmlEnginePrivate *ep = QQmlEnginePrivate::get(engine); bool unnamedParameter = false; - const QSet<QString> &illegalNames = ep->v8engine()->illegalNames(); + const QSet<QString> &illegalNames = engine->v8Engine->illegalNames(); QString error; QString parameters; diff --git a/src/qml/qml/qqmlpropertycache_p.h b/src/qml/qml/qqmlpropertycache_p.h index d3ea336885..224de948eb 100644 --- a/src/qml/qml/qqmlpropertycache_p.h +++ b/src/qml/qml/qqmlpropertycache_p.h @@ -61,6 +61,7 @@ QT_BEGIN_NAMESPACE class QV8Engine; class QMetaProperty; class QQmlEngine; +class QJSEngine; class QQmlPropertyData; class QQmlAccessors; class QMetaObjectBuilder; @@ -242,8 +243,8 @@ class QQmlPropertyCacheMethodArguments; class Q_QML_PRIVATE_EXPORT QQmlPropertyCache : public QQmlRefCount, public QQmlCleanup { public: - QQmlPropertyCache(QQmlEngine *); - QQmlPropertyCache(QQmlEngine *, const QMetaObject *); + QQmlPropertyCache(QJSEngine *); + QQmlPropertyCache(QJSEngine *, const QMetaObject *); virtual ~QQmlPropertyCache(); void update(const QMetaObject *); @@ -311,7 +312,7 @@ public: QList<QByteArray> signalParameterNames(int index) const; QString signalParameterStringForJS(int index, QString *errorString = 0); - static QString signalParameterStringForJS(QQmlEngine *engine, const QList<QByteArray> ¶meterNameList, QString *errorString = 0); + static QString signalParameterStringForJS(QV4::ExecutionEngine *engine, const QList<QByteArray> ¶meterNameList, QString *errorString = 0); const char *className() const; @@ -374,8 +375,7 @@ private: _hasPropertyOverrides |= isOverride; } - // Optional! Only used for calling flagsForPropertyType, in which it is also optional. - QQmlEngine *engine; + QJSEngine *engine; QQmlPropertyCache *_parent; int propertyIndexCacheStart; |