aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAndrei Golubev <andrei.golubev@qt.io>2022-06-10 15:06:35 +0200
committerAndrei Golubev <andrei.golubev@qt.io>2022-06-15 09:43:01 +0200
commit48ae7468afc06d52844badb3f5f41114f67a360f (patch)
treecc02e5a4df41edd6d49dc068f88a4f643a1e1aab
parentb68aa525883ca9ca8e007de3c5b5177fc49af5f4 (diff)
Fix QQmlTypePrivate memory leak in qmltc-generated types with extensions
Apparently registering the QQmlTypePrivate for a meta-object is not good enough. Somehow clang's ASan failed to discover a memory leak but gcc's ASan did not. After carefully exercising the code and a bit of debugging, turns out we indeed not release manually created QQmlTypePrivate objects. Do release the QQmlTypePrivate correctly now In the process of doing so, remove now-redundant QMetaObject function parameter Amends 26179e693717535eeff2e7b2a6ee99dc02dcd8f9 Pick-to: 6.4 Change-Id: Ia0c808cd8a09cf996672bca9953108facfdf5d4e Reviewed-by: Ulf Hermann <ulf.hermann@qt.io>
-rw-r--r--src/qml/qmltc/qqmltcobjectcreationhelper.cpp11
-rw-r--r--src/qml/qmltc/qqmltcobjectcreationhelper_p.h4
-rw-r--r--tools/qmltc/qmltccompilerpieces.h5
3 files changed, 8 insertions, 12 deletions
diff --git a/src/qml/qmltc/qqmltcobjectcreationhelper.cpp b/src/qml/qmltc/qqmltcobjectcreationhelper.cpp
index 4be6ae0c9f..db8517ca70 100644
--- a/src/qml/qmltc/qqmltcobjectcreationhelper.cpp
+++ b/src/qml/qmltc/qqmltcobjectcreationhelper.cpp
@@ -10,8 +10,7 @@
QT_BEGIN_NAMESPACE
-void qmltcCreateDynamicMetaObject(QObject *object, const QMetaObject *staticMetaObject,
- const QmltcTypeData &data)
+void qmltcCreateDynamicMetaObject(QObject *object, const QmltcTypeData &data)
{
// TODO: when/if qmltc-compiled types would be registered via
// qmltyperegistrar, instead of creating a dummy QQmlTypePrivate, fetch the
@@ -19,9 +18,11 @@ void qmltcCreateDynamicMetaObject(QObject *object, const QMetaObject *staticMeta
// along with the meta object, module name and revision. all that should be
// available ahead-of-time to qmltc.
auto qmlTypePrivate = new QQmlTypePrivate(data.regType);
- // place the newly created QQmlTypePrivate into the qml meta data storage so
- // that it is properly deleted
- QQmlMetaType::registerMetaObjectForType(staticMetaObject, qmlTypePrivate);
+
+ // tie qmlTypePrivate destruction to objects's destruction. the type's
+ // content is not needed once the associated object is deleted
+ QObject::connect(object, &QObject::destroyed,
+ [qmlTypePrivate](QObject *) { qmlTypePrivate->release(); });
// initialize QQmlType::QQmlCppTypeData
Q_ASSERT(data.regType == QQmlType::CppType);
diff --git a/src/qml/qmltc/qqmltcobjectcreationhelper_p.h b/src/qml/qmltc/qqmltcobjectcreationhelper_p.h
index 6f81d5265d..ae4633ac43 100644
--- a/src/qml/qmltc/qqmltcobjectcreationhelper_p.h
+++ b/src/qml/qmltc/qqmltcobjectcreationhelper_p.h
@@ -118,9 +118,7 @@ struct QmltcTypeData
}
};
-Q_QML_PRIVATE_EXPORT void qmltcCreateDynamicMetaObject(QObject *object,
- const QMetaObject *staticMetaObject,
- const QmltcTypeData &data);
+Q_QML_PRIVATE_EXPORT void qmltcCreateDynamicMetaObject(QObject *object, const QmltcTypeData &data);
QT_END_NAMESPACE
diff --git a/tools/qmltc/qmltccompilerpieces.h b/tools/qmltc/qmltccompilerpieces.h
index bc423807fb..9afc001b55 100644
--- a/tools/qmltc/qmltccompilerpieces.h
+++ b/tools/qmltc/qmltccompilerpieces.h
@@ -236,10 +236,7 @@ inline decltype(auto) QmltcCodeGenerator::generate_initCode(QmltcType &current,
if (hasExtension) {
current.init.body << u"{"_s;
current.init.body << u"auto cppData = QmltcTypeData(this);"_s;
- current.init.body
- << QStringLiteral(
- "qmltcCreateDynamicMetaObject(this, &%1::staticMetaObject, cppData);")
- .arg(type->internalName());
+ current.init.body << u"qmltcCreateDynamicMetaObject(this, cppData);"_s;
current.init.body << u"}"_s;
}