From d10ddb040a0be1e179c60d0e364c7ab28b059e15 Mon Sep 17 00:00:00 2001 From: Ulf Hermann Date: Wed, 27 Mar 2019 16:03:57 +0100 Subject: Make sure we can delete value type providers in any order Previously the null provider had to be deleted last as it would leave a dangling pointer in the global static. This meant that we could not delete any other value providers on shutdown as the deletion order between different Q_GLOBAL_STATICs is undefined. Task-number: QTBUG-74348 Change-Id: I12aab6ab9ec4c71b90af69c5f824e0c6686433f5 Reviewed-by: Simon Hausmann --- src/qml/qml/qqmlglobal.cpp | 62 +++++++++++++++++++--------------------------- 1 file changed, 26 insertions(+), 36 deletions(-) (limited to 'src/qml/qml/qqmlglobal.cpp') diff --git a/src/qml/qml/qqmlglobal.cpp b/src/qml/qml/qqmlglobal.cpp index 1d60c518c4..a10ded6487 100644 --- a/src/qml/qml/qqmlglobal.cpp +++ b/src/qml/qml/qqmlglobal.cpp @@ -231,57 +231,47 @@ bool QQmlValueTypeProvider::store(int, const void *, void *, size_t) { return fa bool QQmlValueTypeProvider::read(const QVariant&, void *, int) { return false; } bool QQmlValueTypeProvider::write(int, const void *, QVariant&) { return false; } -Q_GLOBAL_STATIC(QQmlValueTypeProvider, nullValueTypeProvider) -static QQmlValueTypeProvider *valueTypeProvider = nullptr; +struct ValueTypeProviderList { + QQmlValueTypeProvider nullProvider; + QQmlValueTypeProvider *head = &nullProvider; +}; -static QQmlValueTypeProvider **getValueTypeProvider(void) -{ - if (valueTypeProvider == nullptr) { - valueTypeProvider = nullValueTypeProvider; - } - - return &valueTypeProvider; -} +Q_GLOBAL_STATIC(ValueTypeProviderList, valueTypeProviders) Q_QML_PRIVATE_EXPORT void QQml_addValueTypeProvider(QQmlValueTypeProvider *newProvider) { - static QQmlValueTypeProvider **providerPtr = getValueTypeProvider(); - newProvider->next = *providerPtr; - *providerPtr = newProvider; + if (ValueTypeProviderList *providers = valueTypeProviders()) { + newProvider->next = providers->head; + providers->head = newProvider; + } } Q_QML_PRIVATE_EXPORT void QQml_removeValueTypeProvider(QQmlValueTypeProvider *oldProvider) { - if (oldProvider == nullValueTypeProvider) { - // don't remove the null provider - // we get here when the QtQml library is being unloaded - return; - } - - // the only entry with next = 0 is the null provider - Q_ASSERT(oldProvider->next); - - QQmlValueTypeProvider *prev = valueTypeProvider; - if (prev == oldProvider) { - valueTypeProvider = oldProvider->next; - return; - } + if (ValueTypeProviderList *providers = valueTypeProviders()) { + QQmlValueTypeProvider *prev = providers->head; + if (prev == oldProvider) { + providers->head = oldProvider->next; + return; + } - // singly-linked list removal - for ( ; prev; prev = prev->next) { - if (prev->next != oldProvider) - continue; // this is not the provider you're looking for - prev->next = oldProvider->next; - return; + // singly-linked list removal + for (; prev; prev = prev->next) { + if (prev->next != oldProvider) + continue; // this is not the provider you're looking for + prev->next = oldProvider->next; + return; + } } qWarning("QQml_removeValueTypeProvider: was asked to remove provider %p but it was not found", oldProvider); } -Q_AUTOTEST_EXPORT QQmlValueTypeProvider *QQml_valueTypeProvider(void) +Q_AUTOTEST_EXPORT QQmlValueTypeProvider *QQml_valueTypeProvider() { - static QQmlValueTypeProvider **providerPtr = getValueTypeProvider(); - return *providerPtr; + if (ValueTypeProviderList *providers = valueTypeProviders()) + return providers->head; + return nullptr; } QQmlColorProvider::~QQmlColorProvider() {} -- cgit v1.2.3 From 28dfb8207f6a8a38fc587143f7f19325c3395059 Mon Sep 17 00:00:00 2001 From: Nodir Temirkhodjaev Date: Tue, 9 Apr 2019 21:26:53 +0500 Subject: Warn about non-existent providers only with the loaded QtQml library Task-number: QTBUG-74996 Change-Id: Ibc5de6e79889724850c9cdc16c8ba066a76298d1 Reviewed-by: Ulf Hermann --- src/qml/qml/qqmlglobal.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src/qml/qml/qqmlglobal.cpp') diff --git a/src/qml/qml/qqmlglobal.cpp b/src/qml/qml/qqmlglobal.cpp index a10ded6487..04e6b2aa75 100644 --- a/src/qml/qml/qqmlglobal.cpp +++ b/src/qml/qml/qqmlglobal.cpp @@ -262,9 +262,9 @@ Q_QML_PRIVATE_EXPORT void QQml_removeValueTypeProvider(QQmlValueTypeProvider *ol prev->next = oldProvider->next; return; } - } - qWarning("QQml_removeValueTypeProvider: was asked to remove provider %p but it was not found", oldProvider); + qWarning("QQml_removeValueTypeProvider: was asked to remove provider %p but it was not found", oldProvider); + } } Q_AUTOTEST_EXPORT QQmlValueTypeProvider *QQml_valueTypeProvider() -- cgit v1.2.3 From 65299ce292180a845eb2d76756faeeaa1456d8f0 Mon Sep 17 00:00:00 2001 From: Ulf Hermann Date: Thu, 4 Apr 2019 16:00:36 +0200 Subject: Remove QQmlV4Handle This is just an alias for QV4::ReturnedValue. We can as well use the latter. Change-Id: Ibd2c038a3ca726b39a8f0f05e02922adb9fccbdb Reviewed-by: Simon Hausmann --- src/qml/qml/qqmlglobal.cpp | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'src/qml/qml/qqmlglobal.cpp') diff --git a/src/qml/qml/qqmlglobal.cpp b/src/qml/qml/qqmlglobal.cpp index 04e6b2aa75..acebb6bac3 100644 --- a/src/qml/qml/qqmlglobal.cpp +++ b/src/qml/qml/qqmlglobal.cpp @@ -149,7 +149,8 @@ QVariant QQmlValueTypeProvider::createVariantFromString(int type, const QString return QVariant(); } -QVariant QQmlValueTypeProvider::createVariantFromJsObject(int type, QQmlV4Handle obj, QV4::ExecutionEngine *e, bool *ok) +QVariant QQmlValueTypeProvider::createVariantFromJsObject(int type, const QV4::Value &obj, + QV4::ExecutionEngine *e, bool *ok) { QVariant v; @@ -225,7 +226,7 @@ bool QQmlValueTypeProvider::createFromString(int, const QString &, void *, size_ bool QQmlValueTypeProvider::createStringFrom(int, const void *, QString *) { return false; } bool QQmlValueTypeProvider::variantFromString(const QString &, QVariant *) { return false; } bool QQmlValueTypeProvider::variantFromString(int, const QString &, QVariant *) { return false; } -bool QQmlValueTypeProvider::variantFromJsObject(int, QQmlV4Handle, QV4::ExecutionEngine *, QVariant *) { return false; } +bool QQmlValueTypeProvider::variantFromJsObject(int, const QV4::Value &, QV4::ExecutionEngine *, QVariant *) { return false; } bool QQmlValueTypeProvider::equal(int, const void *, const QVariant&) { return false; } bool QQmlValueTypeProvider::store(int, const void *, void *, size_t) { return false; } bool QQmlValueTypeProvider::read(const QVariant&, void *, int) { return false; } -- cgit v1.2.3