summaryrefslogtreecommitdiffstats
path: root/src/corelib/kernel/qobject.cpp
diff options
context:
space:
mode:
authorAndrei Golubev <andrei.golubev@qt.io>2021-01-15 09:42:19 +0100
committerAndrei Golubev <andrei.golubev@qt.io>2021-01-18 15:54:03 +0100
commit6f520abdab7120789800208dde837b3836f762cc (patch)
treec2292ea73e2d234e00ae73b69277407182f6d5c6 /src/corelib/kernel/qobject.cpp
parent5a0e5521e4455e98f963d65319e87eb53a644610 (diff)
Add new special QObjectPrivate::{connect, disconnect} for QML
Original QML-specific connection mechanism ignores the receiver argument and uses sender as receiver. This causes uncontrollable memory growth in certain cases as connections on receiver persist even after receiver is destroyed New connect() with receiver parameter uses underlying API correctly, disconnect is provided for the symmetry (not sure it's really needed) Task-number: QTBUG-86368 Pick-to: 5.15 6.0 Change-Id: I4580d75b617cb2c4dfb971a4dfb8e943e325572b Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io> Reviewed-by: Thiago Macieira <thiago.macieira@intel.com>
Diffstat (limited to 'src/corelib/kernel/qobject.cpp')
-rw-r--r--src/corelib/kernel/qobject.cpp49
1 files changed, 46 insertions, 3 deletions
diff --git a/src/corelib/kernel/qobject.cpp b/src/corelib/kernel/qobject.cpp
index 9bcf29830b..a729962d4f 100644
--- a/src/corelib/kernel/qobject.cpp
+++ b/src/corelib/kernel/qobject.cpp
@@ -5061,12 +5061,33 @@ bool QObject::disconnectImpl(const QObject *sender, void **signal, const QObject
/*!
\internal
- Used by QML to connect a signal by index to a slot implemented in JavaScript (wrapped in a custom QSlotObjectBase subclass).
+ Used by QML to connect a signal by index to a slot implemented in JavaScript
+ (wrapped in a custom QSlotObjectBase subclass).
+
+ This version of connect assumes that sender and receiver are the same object.
The signal_index is an index relative to the number of methods.
*/
QMetaObject::Connection QObjectPrivate::connect(const QObject *sender, int signal_index, QtPrivate::QSlotObjectBase *slotObj, Qt::ConnectionType type)
{
+ return QObjectPrivate::connect(sender, signal_index, sender, slotObj, type);
+}
+
+/*!
+ \internal
+ Used by QML to connect a signal by index to a slot implemented in JavaScript
+ (wrapped in a custom QSlotObjectBase subclass).
+
+ This is an overload that should be used when \a sender and \a receiver are
+ different objects.
+
+ The signal_index is an index relative to the number of methods.
+ */
+QMetaObject::Connection QObjectPrivate::connect(const QObject *sender, int signal_index,
+ const QObject *receiver,
+ QtPrivate::QSlotObjectBase *slotObj,
+ Qt::ConnectionType type)
+{
if (!sender) {
qCWarning(lcConnect, "QObject::connect: invalid nullptr parameter");
if (slotObj)
@@ -5076,7 +5097,8 @@ QMetaObject::Connection QObjectPrivate::connect(const QObject *sender, int signa
const QMetaObject *senderMetaObject = sender->metaObject();
signal_index = methodIndexToSignalIndex(&senderMetaObject, signal_index);
- return QObjectPrivate::connectImpl(sender, signal_index, sender, /*slot*/nullptr, slotObj, type, /*types*/nullptr, senderMetaObject);
+ return QObjectPrivate::connectImpl(sender, signal_index, receiver, /*slot*/ nullptr, slotObj,
+ type, /*types*/ nullptr, senderMetaObject);
}
/*!
@@ -5084,13 +5106,34 @@ QMetaObject::Connection QObjectPrivate::connect(const QObject *sender, int signa
Used by QML to disconnect a signal by index that's connected to a slot implemented in JavaScript (wrapped in a custom QSlotObjectBase subclass)
In the QML case the slot is not a pointer to a pointer to the function to disconnect, but instead it is a pointer to an array of internal values
required for the disconnect.
+
+ This version of disconnect assumes that sender and receiver are the same object.
*/
bool QObjectPrivate::disconnect(const QObject *sender, int signal_index, void **slot)
{
+ return QObjectPrivate::disconnect(sender, signal_index, sender, slot);
+}
+
+/*!
+ \internal
+
+ Used by QML to disconnect a signal by index that's connected to a slot
+ implemented in JavaScript (wrapped in a custom QSlotObjectBase subclass) In the
+ QML case the slot is not a pointer to a pointer to the function to disconnect,
+ but instead it is a pointer to an array of internal values required for the
+ disconnect.
+
+ This is an overload that should be used when \a sender and \a receiver are
+ different objects.
+ */
+bool QObjectPrivate::disconnect(const QObject *sender, int signal_index, const QObject *receiver,
+ void **slot)
+{
const QMetaObject *senderMetaObject = sender->metaObject();
signal_index = methodIndexToSignalIndex(&senderMetaObject, signal_index);
- return QMetaObjectPrivate::disconnect(sender, signal_index, senderMetaObject, sender, -1, slot);
+ return QMetaObjectPrivate::disconnect(sender, signal_index, senderMetaObject, receiver, -1,
+ slot);
}
/*!