aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorUlf Hermann <ulf.hermann@qt.io>2021-04-08 13:50:46 +0200
committerUlf Hermann <ulf.hermann@qt.io>2021-04-09 12:14:25 +0200
commit4a5b989755cc7e92a3d9045c37d272ee114c702a (patch)
treeaa78ac8e19b56b96619c30e9213877d7ef4096f5
parent028a80801d52edb5dd8f47387ae675b925883f9c (diff)
Do not auto-clean components with live inline components
The inline components do not hold a strong reference to their outer type because that would be a reference cycle. Fixes: QTBUG-92236 Change-Id: I6d76a114352653210f0ece6c198cf761d3b4eda1 Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io> (cherry picked from commit d0d4cc528ba9e3c39c15a2292066dac1d457abd5)
-rw-r--r--src/qml/qml/qqmlmetatype.cpp12
-rw-r--r--tests/auto/qml/qqmllanguage/data/Tab1.qml9
-rw-r--r--tests/auto/qml/qqmllanguage/data/bareInline.qml9
-rw-r--r--tests/auto/qml/qqmllanguage/tst_qqmllanguage.cpp28
4 files changed, 57 insertions, 1 deletions
diff --git a/src/qml/qml/qqmlmetatype.cpp b/src/qml/qml/qqmlmetatype.cpp
index 8a1bbd9459..e4699d0b55 100644
--- a/src/qml/qml/qqmlmetatype.cpp
+++ b/src/qml/qml/qqmlmetatype.cpp
@@ -1260,6 +1260,16 @@ void QQmlMetaType::unregisterType(int typeIndex)
}
}
+static bool hasActiveInlineComponents(const QQmlTypePrivate *d)
+{
+ for (const QQmlType &ic : qAsConst(d->objectIdToICType)) {
+ const QQmlTypePrivate *icPriv = ic.priv();
+ if (icPriv && icPriv->count() > 1)
+ return true;
+ }
+ return false;
+}
+
void QQmlMetaType::freeUnusedTypesAndCaches()
{
QQmlMetaTypeDataPtr data;
@@ -1274,7 +1284,7 @@ void QQmlMetaType::freeUnusedTypesAndCaches()
QList<QQmlType>::Iterator it = data->types.begin();
while (it != data->types.end()) {
const QQmlTypePrivate *d = (*it).priv();
- if (d && d->count() == 1) {
+ if (d && d->count() == 1 && !hasActiveInlineComponents(d)) {
deletedAtLeastOneType = true;
removeQQmlTypePrivate(data->idToType, d);
diff --git a/tests/auto/qml/qqmllanguage/data/Tab1.qml b/tests/auto/qml/qqmllanguage/data/Tab1.qml
new file mode 100644
index 0000000000..e1cd6d8c34
--- /dev/null
+++ b/tests/auto/qml/qqmllanguage/data/Tab1.qml
@@ -0,0 +1,9 @@
+import QtQuick 2.15
+
+Item {
+ component LeftTab: Item {
+ }
+
+ component RightTab: Item {
+ }
+}
diff --git a/tests/auto/qml/qqmllanguage/data/bareInline.qml b/tests/auto/qml/qqmllanguage/data/bareInline.qml
new file mode 100644
index 0000000000..cb79021250
--- /dev/null
+++ b/tests/auto/qml/qqmllanguage/data/bareInline.qml
@@ -0,0 +1,9 @@
+import QtQuick 2.9
+
+Item {
+ width: 800
+ height: 600
+ visible: true
+
+ Tab1.RightTab {}
+}
diff --git a/tests/auto/qml/qqmllanguage/tst_qqmllanguage.cpp b/tests/auto/qml/qqmllanguage/tst_qqmllanguage.cpp
index e247a139ec..de8b2ef7eb 100644
--- a/tests/auto/qml/qqmllanguage/tst_qqmllanguage.cpp
+++ b/tests/auto/qml/qqmllanguage/tst_qqmllanguage.cpp
@@ -48,6 +48,7 @@
#include <private/qqmlscriptstring_p.h>
#include <private/qqmlvmemetaobject_p.h>
#include <private/qqmlcomponent_p.h>
+#include <private/qqmltype_p_p.h>
#include "testtypes.h"
#include "testhttpserver.h"
@@ -331,6 +332,7 @@ private slots:
void arrayToContainer();
void qualifiedScopeInCustomParser();
void accessNullPointerPropertyCache();
+ void bareInlineComponent();
private:
QQmlEngine engine;
@@ -5813,6 +5815,32 @@ void tst_qqmllanguage::accessNullPointerPropertyCache()
QVERIFY(!obj.isNull());
}
+void tst_qqmllanguage::bareInlineComponent()
+{
+ QQmlEngine engine;
+
+ QQmlComponent c(&engine, testFileUrl("bareInline.qml"));
+ QVERIFY2(c.isReady(), qPrintable(c.errorString()));
+ QScopedPointer<QObject> o(c.create());
+ QVERIFY(!o.isNull());
+
+ QQmlMetaType::freeUnusedTypesAndCaches();
+
+ bool tab1Found = false;
+ const auto types = QQmlMetaType::qmlTypes();
+ for (const QQmlType &type : types) {
+ if (type.elementName() == QStringLiteral("Tab1")) {
+ QVERIFY(type.module().isEmpty());
+ tab1Found = true;
+ const auto ics = type.priv()->objectIdToICType;
+ QVERIFY(ics.size() > 0);
+ for (const QQmlType &ic : ics)
+ QVERIFY(ic.containingType() == type);
+ }
+ }
+ QVERIFY(tab1Found);
+}
+
QTEST_MAIN(tst_qqmllanguage)
#include "tst_qqmllanguage.moc"