diff options
author | Volker Hilsheimer <volker.hilsheimer@qt.io> | 2023-03-06 18:32:40 +0100 |
---|---|---|
committer | Volker Hilsheimer <volker.hilsheimer@qt.io> | 2023-03-10 15:39:37 +0100 |
commit | 4f02973e2f447dfc92234ec247d7157ea0e1e807 (patch) | |
tree | 93511e0c3111a27f191038c6452d3061cc56e4cb /src/corelib/global/qtclasshelpermacros.h | |
parent | 454dafb0e1a36ef6bbe9eafc240c22f6cd14e312 (diff) |
Make it possible to use QObjectPrivate::connect in private code
In most QObjectPrivate-subclasses, the Q_DECLARE_PUBLIC macro is used in
the private segment of the class declaration. In that case, the q_ptr
becomes a private member of the private class, and then the
QObjectPrivate::connect function can no longer be used, as it needs to
access the d_ptr.
Fix this by declaring QObjectPrivate, and the static-assert-helper, as
friends of the class using the Q_DECLARE_PUBLIC macro.
Adapt the QObject test by moving the Q_DECLARE_PUBLIC macro into
the private section of the test-private, and add a compile test.
Pick-to: 6.5 6.5.0
Change-Id: Ifc04be3b305221e138b1e08bb3a3838d871f4fcb
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Axel Spoerl <axel.spoerl@qt.io>
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Diffstat (limited to 'src/corelib/global/qtclasshelpermacros.h')
-rw-r--r-- | src/corelib/global/qtclasshelpermacros.h | 11 |
1 files changed, 10 insertions, 1 deletions
diff --git a/src/corelib/global/qtclasshelpermacros.h b/src/corelib/global/qtclasshelpermacros.h index e6b66ed5f2..8839e80fb9 100644 --- a/src/corelib/global/qtclasshelpermacros.h +++ b/src/corelib/global/qtclasshelpermacros.h @@ -78,6 +78,13 @@ template <typename T> inline T *qGetPtrHelper(T *ptr) noexcept { return ptr; } template <typename Ptr> inline auto qGetPtrHelper(Ptr &ptr) noexcept -> decltype(ptr.get()) { static_assert(noexcept(ptr.get()), "Smart d pointers for Q_DECLARE_PRIVATE must have noexcept get()"); return ptr.get(); } +class QObject; +class QObjectPrivate; +namespace QtPrivate { + template <typename ObjPrivate> void assertObjectType(QObjectPrivate *d); + inline const QObject *getQObject(const QObjectPrivate *d); +} + #define Q_DECLARE_PRIVATE(Class) \ inline Class##Private* d_func() noexcept \ { Q_CAST_IGNORE_ALIGN(return reinterpret_cast<Class##Private *>(qGetPtrHelper(d_ptr));) } \ @@ -95,7 +102,9 @@ template <typename Ptr> inline auto qGetPtrHelper(Ptr &ptr) noexcept -> decltype #define Q_DECLARE_PUBLIC(Class) \ inline Class* q_func() noexcept { return static_cast<Class *>(q_ptr); } \ inline const Class* q_func() const noexcept { return static_cast<const Class *>(q_ptr); } \ - friend class Class; + friend class Class; \ + friend const QObject *QtPrivate::getQObject(const QObjectPrivate *d); \ + template <typename ObjPrivate> friend void QtPrivate::assertObjectType(QObjectPrivate *d); #define Q_D(Class) Class##Private * const d = d_func() #define Q_Q(Class) Class * const q = q_func() |