Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-08-04 09:21:18

0001 // Copyright (C) 2022 The Qt Company Ltd.
0002 // Copyright (C) 2019 Intel Corporation.
0003 // SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
0004 // Qt-Security score:significant reason:default
0005 
0006 #ifndef QOBJECTDEFS_H
0007 #define QOBJECTDEFS_H
0008 
0009 #if defined(__OBJC__) && !defined(__cplusplus)
0010 #  warning "File built in Objective-C mode (.m), but using Qt requires Objective-C++ (.mm)"
0011 #endif
0012 
0013 #include <QtCore/qnamespace.h>
0014 #include <QtCore/qobjectdefs_impl.h>
0015 #include <QtCore/qtcoreexports.h>
0016 #include <QtCore/qtmetamacros.h>
0017 
0018 QT_BEGIN_NAMESPACE
0019 
0020 class QByteArray;
0021 struct QArrayData;
0022 
0023 class QString;
0024 
0025 #ifndef QT_NO_META_MACROS
0026 // macro for onaming members
0027 #ifdef METHOD
0028 #undef METHOD
0029 #endif
0030 #ifdef SLOT
0031 #undef SLOT
0032 #endif
0033 #ifdef SIGNAL
0034 #undef SIGNAL
0035 #endif
0036 #endif // QT_NO_META_MACROS
0037 
0038 Q_CORE_EXPORT const char *qFlagLocation(const char *method);
0039 
0040 #ifndef QT_NO_META_MACROS
0041 # define QMETHOD_CODE  0                        // member type codes
0042 # define QSLOT_CODE    1
0043 # define QSIGNAL_CODE  2
0044 # define QT_PREFIX_CODE(code, a) QT_STRINGIFY(code) #a
0045 # define QT_STRINGIFY_METHOD(a) QT_PREFIX_CODE(QMETHOD_CODE, a)
0046 # define QT_STRINGIFY_SLOT(a) QT_PREFIX_CODE(QSLOT_CODE, a)
0047 # define QT_STRINGIFY_SIGNAL(a) QT_PREFIX_CODE(QSIGNAL_CODE, a)
0048 # ifndef QT_NO_DEBUG
0049 #  define QLOCATION "\0" __FILE__ ":" QT_STRINGIFY(__LINE__)
0050 #  ifndef QT_NO_KEYWORDS
0051 #   define METHOD(a)   qFlagLocation(QT_STRINGIFY_METHOD(a) QLOCATION)
0052 #  endif
0053 #  define SLOT(a)     qFlagLocation(QT_STRINGIFY_SLOT(a) QLOCATION)
0054 #  define SIGNAL(a)   qFlagLocation(QT_STRINGIFY_SIGNAL(a) QLOCATION)
0055 # else
0056 #  ifndef QT_NO_KEYWORDS
0057 #   define METHOD(a)  QT_STRINGIFY_METHOD(a)
0058 #  endif
0059 #  define SLOT(a)     QT_STRINGIFY_SLOT(a)
0060 #  define SIGNAL(a)   QT_STRINGIFY_SIGNAL(a)
0061 # endif
0062 #endif // QT_NO_META_MACROS
0063 
0064 #define Q_ARG(Type, data)           QtPrivate::Invoke::argument<Type>(QT_STRINGIFY(Type), data)
0065 #define Q_RETURN_ARG(Type, data)    QtPrivate::Invoke::returnArgument<Type>(QT_STRINGIFY(Type), data)
0066 
0067 class QObject;
0068 class QMetaMethod;
0069 class QMetaEnum;
0070 class QMetaProperty;
0071 class QMetaClassInfo;
0072 
0073 namespace QtPrivate {
0074 class QMetaTypeInterface;
0075 template<typename T> constexpr const QMetaTypeInterface *qMetaTypeInterfaceForType();
0076 }
0077 
0078 struct QMethodRawArguments
0079 {
0080     void **arguments;
0081 };
0082 
0083 #if QT_VERSION < QT_VERSION_CHECK(7, 0, 0)
0084 class Q_CORE_EXPORT QGenericArgument
0085 {
0086 public:
0087     inline QGenericArgument(const char *aName = nullptr, const void *aData = nullptr)
0088         : _data(aData), _name(aName) {}
0089     inline void *data() const { return const_cast<void *>(_data); }
0090     inline const char *name() const { return _name; }
0091 
0092 private:
0093     const void *_data;
0094     const char *_name;
0095 };
0096 
0097 class Q_CORE_EXPORT QGenericReturnArgument: public QGenericArgument
0098 {
0099 public:
0100     inline QGenericReturnArgument(const char *aName = nullptr, void *aData = nullptr)
0101         : QGenericArgument(aName, aData)
0102         {}
0103 };
0104 
0105 template <class T>
0106 class QArgument: public QGenericArgument
0107 {
0108 public:
0109     inline QArgument(const char *aName, const T &aData)
0110         : QGenericArgument(aName, static_cast<const void *>(&aData))
0111         {}
0112 };
0113 template <class T>
0114 class QArgument<T &>: public QGenericArgument
0115 {
0116 public:
0117     inline QArgument(const char *aName, T &aData)
0118         : QGenericArgument(aName, static_cast<const void *>(&aData))
0119         {}
0120 };
0121 
0122 
0123 template <typename T>
0124 class QReturnArgument: public QGenericReturnArgument
0125 {
0126 public:
0127     inline QReturnArgument(const char *aName, T &aData)
0128         : QGenericReturnArgument(aName, static_cast<void *>(&aData))
0129         {}
0130 };
0131 #endif
0132 
0133 struct QMetaMethodArgument
0134 {
0135     const QtPrivate::QMetaTypeInterface *metaType;
0136     const char *name;
0137     const void *data;
0138 };
0139 
0140 struct QMetaMethodReturnArgument
0141 {
0142     const QtPrivate::QMetaTypeInterface *metaType;
0143     const char *name;
0144     void *data;
0145 };
0146 
0147 template <typename T>
0148 struct QTemplatedMetaMethodReturnArgument : QMetaMethodReturnArgument
0149 {
0150     using Type = T;
0151 };
0152 
0153 namespace QtPrivate {
0154 namespace Invoke {
0155 #if QT_VERSION <= QT_VERSION_CHECK(7, 0, 0)
0156 template <typename... Args>
0157 using AreOldStyleArgs = std::disjunction<std::is_base_of<QGenericArgument, Args>...>;
0158 
0159 template <typename T, typename... Args> using IfNotOldStyleArgs =
0160     std::enable_if_t<!AreOldStyleArgs<Args...>::value, T>;
0161 #else
0162 template <typename T, typename... Args> using IfNotOldStyleArgs = T;
0163 #endif
0164 
0165 template <typename T> inline QMetaMethodArgument argument(const char *name, const T &t)
0166 {
0167     if constexpr ((std::is_lvalue_reference_v<T> && std::is_const_v<std::remove_reference_t<T>>) ||
0168             !std::is_reference_v<T>) {
0169         return { qMetaTypeInterfaceForType<T>(), name, std::addressof(t) };
0170     } else {
0171         return { nullptr, name, std::addressof(t) };
0172     }
0173 }
0174 
0175 template <typename T>
0176 inline QTemplatedMetaMethodReturnArgument<T> returnArgument(const char *name, T &t)
0177 {
0178     return { qMetaTypeInterfaceForType<T>(), name, std::addressof(t) };
0179 }
0180 
0181 template <typename T> inline const char *typenameHelper(const T &)
0182 {
0183     return nullptr;
0184 }
0185 template <typename T> inline const void *dataHelper(const T &t)
0186 {
0187     return std::addressof(t);
0188 }
0189 template <typename T> inline const QMetaTypeInterface *metaTypeHelper(const T &)
0190 {
0191     return qMetaTypeInterfaceForType<T>();
0192 }
0193 
0194 inline const char *typenameHelper(QMetaMethodArgument a)
0195 { return a.name; }
0196 inline const void *dataHelper(QMetaMethodArgument a)
0197 { return a.data; }
0198 inline const QMetaTypeInterface *metaTypeHelper(QMetaMethodArgument a)
0199 { return a.metaType; }
0200 
0201 inline const char *typenameHelper(const char *) = delete;
0202 template <typename T> inline const void *dataHelper(const char *) = delete;
0203 inline const QMetaTypeInterface *metaTypeHelper(const char *) = delete;
0204 inline const char *typenameHelper(const char16_t *) = delete;
0205 template <typename T> inline const void *dataHelper(const char16_t *) = delete;
0206 inline const QMetaTypeInterface *metaTypeHelper(const char16_t *) = delete;
0207 
0208 } // namespace QtPrivate::Invoke
0209 
0210 template <typename... Args> inline auto invokeMethodHelper(QMetaMethodReturnArgument r, const Args &... arguments)
0211 {
0212     std::array params = { const_cast<const void *>(r.data), Invoke::dataHelper(arguments)... };
0213     std::array names = { r.name, Invoke::typenameHelper(arguments)... };
0214     std::array types = { r.metaType, Invoke::metaTypeHelper(arguments)... };
0215     static_assert(params.size() == types.size());
0216     static_assert(params.size() == names.size());
0217 
0218     struct R {
0219         decltype(params) parameters;
0220         decltype(names) typeNames;
0221         decltype(types) metaTypes;
0222         constexpr qsizetype parameterCount() const { return qsizetype(parameters.size()); }
0223     };
0224     return R { params, names, types };
0225 }
0226 } // namespace QtPrivate
0227 
0228 template <typename T> void qReturnArg(const T &&) = delete;
0229 template <typename T> inline QTemplatedMetaMethodReturnArgument<T> qReturnArg(T &data)
0230 {
0231     return QtPrivate::Invoke::returnArgument(nullptr, data);
0232 }
0233 
0234 struct Q_CORE_EXPORT QMetaObject
0235 {
0236     class Connection;
0237     const char *className() const;
0238     const QMetaObject *superClass() const;
0239 
0240     bool inherits(const QMetaObject *metaObject) const noexcept;
0241     QObject *cast(QObject *obj) const
0242     { return const_cast<QObject *>(cast(const_cast<const QObject *>(obj))); }
0243     const QObject *cast(const QObject *obj) const;
0244 
0245 #if !defined(QT_NO_TRANSLATION) || defined(Q_QDOC)
0246     QString tr(const char *s, const char *c, int n = -1) const;
0247 #endif // QT_NO_TRANSLATION
0248 
0249     QMetaType metaType() const;
0250 
0251     int methodOffset() const;
0252     int enumeratorOffset() const;
0253     int propertyOffset() const;
0254     int classInfoOffset() const;
0255 
0256     int constructorCount() const;
0257     int methodCount() const;
0258     int enumeratorCount() const;
0259     int propertyCount() const;
0260     int classInfoCount() const;
0261 
0262     int indexOfConstructor(const char *constructor) const;
0263     int indexOfMethod(const char *method) const;
0264     int indexOfSignal(const char *signal) const;
0265     int indexOfSlot(const char *slot) const;
0266     int indexOfEnumerator(const char *name) const;
0267 
0268     int indexOfProperty(const char *name) const;
0269     int indexOfClassInfo(const char *name) const;
0270 
0271     QMetaMethod constructor(int index) const;
0272     QMetaMethod method(int index) const;
0273     QMetaEnum enumerator(int index) const;
0274     QMetaProperty property(int index) const;
0275     QMetaClassInfo classInfo(int index) const;
0276     QMetaProperty userProperty() const;
0277 
0278     static bool checkConnectArgs(const char *signal, const char *method);
0279     static bool checkConnectArgs(const QMetaMethod &signal,
0280                                  const QMetaMethod &method);
0281     static QByteArray normalizedSignature(const char *method);
0282     static QByteArray normalizedType(const char *type);
0283 
0284     // internal index-based connect
0285     static Connection connect(const QObject *sender, int signal_index,
0286                         const QObject *receiver, int method_index,
0287                         int type = 0, int *types = nullptr);
0288     // internal index-based disconnect
0289     static bool disconnect(const QObject *sender, int signal_index,
0290                            const QObject *receiver, int method_index);
0291     static bool disconnectOne(const QObject *sender, int signal_index,
0292                               const QObject *receiver, int method_index);
0293     // internal slot-name based connect
0294     static void connectSlotsByName(QObject *o);
0295 
0296 #ifdef Q_QDOC
0297     template<typename PointerToMemberFunction>
0298     static QMetaObject::Connection connect(const QObject *sender, const QMetaMethod &signal, const QObject *receiver, PointerToMemberFunction method, Qt::ConnectionType type = Qt::AutoConnection);
0299     template<typename Functor>
0300     static QMetaObject::Connection connect(const QObject *sender, const QMetaMethod &signal, const QObject *context, Functor functor, Qt::ConnectionType type = Qt::AutoConnection);
0301 #else
0302     template <typename Func>
0303     static inline Connection
0304         connect(const QObject *sender, const QMetaMethod &signal,
0305                 const typename QtPrivate::ContextTypeForFunctor<Func>::ContextType *context, Func &&slot,
0306                 Qt::ConnectionType type = Qt::AutoConnection);
0307 #endif // Q_QDOC
0308 
0309     // internal index-based signal activation
0310     static void activate(QObject *sender, int signal_index, void **argv);
0311     static void activate(QObject *sender, const QMetaObject *, int local_signal_index, void **argv);
0312     static void activate(QObject *sender, int signal_offset, int local_signal_index, void **argv);
0313     template <typename Ret, typename... Args> static inline void
0314     activate(QObject *sender, const QMetaObject *mo, int local_signal_index, Ret *ret, const Args &... args)
0315     {
0316         void *_a[] = {
0317             const_cast<void *>(reinterpret_cast<const volatile void *>(ret)),
0318             const_cast<void *>(reinterpret_cast<const volatile void *>(std::addressof(args)))...
0319         };
0320         activate(sender, mo, local_signal_index, _a);
0321     }
0322 
0323 #if QT_VERSION <= QT_VERSION_CHECK(7, 0, 0)
0324     static bool invokeMethod(QObject *obj, const char *member,
0325                              Qt::ConnectionType,
0326                              QGenericReturnArgument ret,
0327                              QGenericArgument val0 = QGenericArgument(nullptr),
0328                              QGenericArgument val1 = QGenericArgument(),
0329                              QGenericArgument val2 = QGenericArgument(),
0330                              QGenericArgument val3 = QGenericArgument(),
0331                              QGenericArgument val4 = QGenericArgument(),
0332                              QGenericArgument val5 = QGenericArgument(),
0333                              QGenericArgument val6 = QGenericArgument(),
0334                              QGenericArgument val7 = QGenericArgument(),
0335                              QGenericArgument val8 = QGenericArgument(),
0336                              QGenericArgument val9 = QGenericArgument());
0337 
0338     static inline bool invokeMethod(QObject *obj, const char *member,
0339                              QGenericReturnArgument ret,
0340                              QGenericArgument val0 = QGenericArgument(nullptr),
0341                              QGenericArgument val1 = QGenericArgument(),
0342                              QGenericArgument val2 = QGenericArgument(),
0343                              QGenericArgument val3 = QGenericArgument(),
0344                              QGenericArgument val4 = QGenericArgument(),
0345                              QGenericArgument val5 = QGenericArgument(),
0346                              QGenericArgument val6 = QGenericArgument(),
0347                              QGenericArgument val7 = QGenericArgument(),
0348                              QGenericArgument val8 = QGenericArgument(),
0349                              QGenericArgument val9 = QGenericArgument())
0350     {
0351         return invokeMethod(obj, member, Qt::AutoConnection, ret, val0, val1, val2, val3,
0352                 val4, val5, val6, val7, val8, val9);
0353     }
0354 
0355     static inline bool invokeMethod(QObject *obj, const char *member,
0356                              Qt::ConnectionType type,
0357                              QGenericArgument val0,
0358                              QGenericArgument val1 = QGenericArgument(),
0359                              QGenericArgument val2 = QGenericArgument(),
0360                              QGenericArgument val3 = QGenericArgument(),
0361                              QGenericArgument val4 = QGenericArgument(),
0362                              QGenericArgument val5 = QGenericArgument(),
0363                              QGenericArgument val6 = QGenericArgument(),
0364                              QGenericArgument val7 = QGenericArgument(),
0365                              QGenericArgument val8 = QGenericArgument(),
0366                              QGenericArgument val9 = QGenericArgument())
0367     {
0368         return invokeMethod(obj, member, type, QGenericReturnArgument(), val0, val1, val2,
0369                                  val3, val4, val5, val6, val7, val8, val9);
0370     }
0371 
0372     static inline bool invokeMethod(QObject *obj, const char *member,
0373                              QGenericArgument val0,
0374                              QGenericArgument val1 = QGenericArgument(),
0375                              QGenericArgument val2 = QGenericArgument(),
0376                              QGenericArgument val3 = QGenericArgument(),
0377                              QGenericArgument val4 = QGenericArgument(),
0378                              QGenericArgument val5 = QGenericArgument(),
0379                              QGenericArgument val6 = QGenericArgument(),
0380                              QGenericArgument val7 = QGenericArgument(),
0381                              QGenericArgument val8 = QGenericArgument(),
0382                              QGenericArgument val9 = QGenericArgument())
0383     {
0384         return invokeMethod(obj, member, Qt::AutoConnection, QGenericReturnArgument(), val0,
0385                 val1, val2, val3, val4, val5, val6, val7, val8, val9);
0386     }
0387 #endif // Qt < 7.0
0388 
0389     template <typename ReturnArg, typename... Args> static
0390 #ifdef Q_QDOC
0391     bool
0392 #else
0393     QtPrivate::Invoke::IfNotOldStyleArgs<bool, Args...>
0394 #endif
0395     invokeMethod(QObject *obj, const char *member, Qt::ConnectionType c,
0396                  QTemplatedMetaMethodReturnArgument<ReturnArg> r, Args &&... arguments)
0397     {
0398         auto h = QtPrivate::invokeMethodHelper(r, std::forward<Args>(arguments)...);
0399         return invokeMethodImpl(obj, member, c, h.parameterCount(), h.parameters.data(),
0400                                 h.typeNames.data(), h.metaTypes.data());
0401     }
0402 
0403     template <typename... Args> static
0404 #ifdef Q_QDOC
0405     bool
0406 #else
0407     QtPrivate::Invoke::IfNotOldStyleArgs<bool, Args...>
0408 #endif
0409     invokeMethod(QObject *obj, const char *member, Qt::ConnectionType c, Args &&... arguments)
0410     {
0411         QTemplatedMetaMethodReturnArgument<void> r = {};
0412         return invokeMethod(obj, member, c, r, std::forward<Args>(arguments)...);
0413     }
0414 
0415     template <typename ReturnArg, typename... Args> static
0416 #ifdef Q_QDOC
0417     bool
0418 #else
0419     QtPrivate::Invoke::IfNotOldStyleArgs<bool, Args...>
0420 #endif
0421     invokeMethod(QObject *obj, const char *member, QTemplatedMetaMethodReturnArgument<ReturnArg> r,
0422                  Args &&... arguments)
0423     {
0424         return invokeMethod(obj, member, Qt::AutoConnection, r, std::forward<Args>(arguments)...);
0425     }
0426 
0427     template <typename... Args> static
0428 #ifdef Q_QDOC
0429     bool
0430 #else
0431     QtPrivate::Invoke::IfNotOldStyleArgs<bool, Args...>
0432 #endif
0433     invokeMethod(QObject *obj, const char *member, Args &&... arguments)
0434     {
0435         QTemplatedMetaMethodReturnArgument<void> r = {};
0436         return invokeMethod(obj, member, Qt::AutoConnection, r, std::forward<Args>(arguments)...);
0437     }
0438 
0439 #ifdef Q_QDOC
0440     template<typename Functor, typename FunctorReturnType>
0441     static bool invokeMethod(QObject *context, Functor &&function, Qt::ConnectionType type = Qt::AutoConnection, FunctorReturnType *ret = nullptr);
0442     template<typename Functor, typename FunctorReturnType>
0443     static bool invokeMethod(QObject *context, Functor &&function, FunctorReturnType *ret);
0444 
0445     template<typename Functor, typename FunctorReturnType, typename... Args>
0446     static bool invokeMethod(QObject *context, Functor &&function, Qt::ConnectionType type, QTemplatedMetaMethodReturnArgument<FunctorReturnType> ret, Args &&...arguments);
0447     template<typename Functor, typename FunctorReturnType, typename... Args>
0448     static bool invokeMethod(QObject *context, Functor &&function, QTemplatedMetaMethodReturnArgument<FunctorReturnType> ret, Args &&...arguments);
0449     template<typename Functor, typename... Args>
0450     static bool invokeMethod(QObject *context, Functor &&function, Qt::ConnectionType type, Args &&...arguments);
0451     template<typename Functor, typename... Args>
0452     static bool invokeMethod(QObject *context, Functor &&function, Args &&...arguments);
0453 #else
0454     template <typename Func>
0455     static std::enable_if_t<!std::disjunction_v<std::is_convertible<Func, const char *>,
0456                                                 QtPrivate::Invoke::AreOldStyleArgs<Func>>,
0457                             bool>
0458     invokeMethod(typename QtPrivate::ContextTypeForFunctor<Func>::ContextType *object,
0459                  Func &&function, Qt::ConnectionType type,
0460                  typename QtPrivate::Callable<Func>::ReturnType *ret)
0461     {
0462         using R = typename QtPrivate::Callable<Func>::ReturnType;
0463         const auto getReturnArg = [ret]() -> QTemplatedMetaMethodReturnArgument<R> {
0464             if constexpr (std::is_void_v<R>)
0465                 return {};
0466             else
0467                 return ret ? qReturnArg(*ret) : QTemplatedMetaMethodReturnArgument<R>{};
0468         };
0469         return invokeMethod(object, std::forward<Func>(function), type, getReturnArg());
0470     }
0471     template <typename Func>
0472     static std::enable_if_t<!std::disjunction_v<std::is_convertible<Func, const char *>,
0473                                                 QtPrivate::Invoke::AreOldStyleArgs<Func>>,
0474                             bool>
0475     invokeMethod(typename QtPrivate::ContextTypeForFunctor<Func>::ContextType *object,
0476                  Func &&function, typename QtPrivate::Callable<Func>::ReturnType *ret)
0477     {
0478         return invokeMethod(object, std::forward<Func>(function), Qt::AutoConnection, ret);
0479     }
0480 
0481     template <typename Func, typename... Args>
0482     static std::enable_if_t<!std::disjunction_v<std::is_convertible<Func, const char *>,
0483                                                 QtPrivate::Invoke::AreOldStyleArgs<Args...>>,
0484                             bool>
0485     invokeMethod(typename QtPrivate::ContextTypeForFunctor<Func>::ContextType *object,
0486                  Func &&function, Qt::ConnectionType type,
0487                  QTemplatedMetaMethodReturnArgument<
0488                          typename QtPrivate::Callable<Func, Args...>::ReturnType>
0489                          ret,
0490                  Args &&...args)
0491     {
0492         return invokeMethodCallableHelper(object, std::forward<Func>(function), type, ret,
0493                                           std::forward<Args>(args)...);
0494     }
0495 
0496     template <typename Func, typename... Args>
0497     static std::enable_if_t<!std::disjunction_v<std::is_convertible<Func, const char *>,
0498                                                 QtPrivate::Invoke::AreOldStyleArgs<Args...>>,
0499                             bool>
0500     invokeMethod(typename QtPrivate::ContextTypeForFunctor<Func>::ContextType *object,
0501                  Func &&function, Qt::ConnectionType type, Args &&...args)
0502     {
0503         using R = typename QtPrivate::Callable<Func, Args...>::ReturnType;
0504         QTemplatedMetaMethodReturnArgument<R> r{ QtPrivate::qMetaTypeInterfaceForType<R>(), nullptr,
0505                                                  nullptr };
0506         return invokeMethod(object, std::forward<Func>(function), type, r,
0507                             std::forward<Args>(args)...);
0508     }
0509 
0510     template <typename Func, typename... Args>
0511     static std::enable_if_t<!std::disjunction_v<std::is_convertible<Func, const char *>,
0512                                                 QtPrivate::Invoke::AreOldStyleArgs<Args...>>,
0513                             bool>
0514     invokeMethod(typename QtPrivate::ContextTypeForFunctor<Func>::ContextType *object,
0515                  Func &&function,
0516                  QTemplatedMetaMethodReturnArgument<
0517                          typename QtPrivate::Callable<Func, Args...>::ReturnType>
0518                          ret,
0519                  Args &&...args)
0520     {
0521         return invokeMethod(object, std::forward<Func>(function), Qt::AutoConnection, ret,
0522                             std::forward<Args>(args)...);
0523     }
0524 
0525     template <typename Func, typename... Args>
0526     static std::enable_if_t<!std::disjunction_v<std::is_convertible<Func, const char *>,
0527                                                 QtPrivate::Invoke::AreOldStyleArgs<Args...>>,
0528                             bool>
0529     invokeMethod(typename QtPrivate::ContextTypeForFunctor<Func>::ContextType *object,
0530                  Func &&function, Args &&...args)
0531     {
0532         using R = typename QtPrivate::Callable<Func, Args...>::ReturnType;
0533         QTemplatedMetaMethodReturnArgument<R> r{ QtPrivate::qMetaTypeInterfaceForType<R>(), nullptr,
0534                                                  nullptr };
0535         return invokeMethod(object, std::forward<Func>(function), Qt::AutoConnection, r,
0536                             std::forward<Args>(args)...);
0537     }
0538 
0539 #endif
0540 
0541 #if QT_VERSION < QT_VERSION_CHECK(7, 0, 0)
0542     QObject *newInstance(QGenericArgument val0,
0543                          QGenericArgument val1 = QGenericArgument(),
0544                          QGenericArgument val2 = QGenericArgument(),
0545                          QGenericArgument val3 = QGenericArgument(),
0546                          QGenericArgument val4 = QGenericArgument(),
0547                          QGenericArgument val5 = QGenericArgument(),
0548                          QGenericArgument val6 = QGenericArgument(),
0549                          QGenericArgument val7 = QGenericArgument(),
0550                          QGenericArgument val8 = QGenericArgument(),
0551                          QGenericArgument val9 = QGenericArgument()) const;
0552 #endif
0553 
0554     template <typename... Args>
0555 #ifdef Q_QDOC
0556     QObject *
0557 #else
0558     QtPrivate::Invoke::IfNotOldStyleArgs<QObject *, Args...>
0559 #endif
0560     newInstance(Args &&... arguments) const
0561     {
0562         auto h = QtPrivate::invokeMethodHelper(QMetaMethodReturnArgument{}, std::forward<Args>(arguments)...);
0563         return newInstanceImpl(this, h.parameterCount(), h.parameters.data(),
0564                                h.typeNames.data(), h.metaTypes.data());
0565     }
0566 
0567     enum Call {
0568         InvokeMetaMethod,
0569         ReadProperty,
0570         WriteProperty,
0571         ResetProperty,
0572         CreateInstance,
0573         IndexOfMethod,
0574         RegisterPropertyMetaType,
0575         RegisterMethodArgumentMetaType,
0576         BindableProperty,
0577         CustomCall,
0578         ConstructInPlace,
0579     };
0580 
0581     int static_metacall(Call, int, void **) const;
0582     static int metacall(QObject *, Call, int, void **);
0583 
0584     template <const QMetaObject &MO> static constexpr const QMetaObject *staticMetaObject()
0585     {
0586         return &MO;
0587     }
0588 
0589     struct SuperData {
0590         using Getter = const QMetaObject *(*)();
0591         const QMetaObject *direct;
0592         SuperData() = default;
0593         constexpr SuperData(std::nullptr_t) : direct(nullptr) {}
0594         constexpr SuperData(const QMetaObject *mo) : direct(mo) {}
0595 
0596         constexpr const QMetaObject *operator->() const { return operator const QMetaObject *(); }
0597 
0598 #ifdef QT_NO_DATA_RELOCATION
0599         Getter indirect = nullptr;
0600         constexpr SuperData(Getter g) : direct(nullptr), indirect(g) {}
0601         constexpr operator const QMetaObject *() const
0602         { return indirect ? indirect() : direct; }
0603         template <const QMetaObject &MO> static constexpr SuperData link()
0604         { return SuperData(QMetaObject::staticMetaObject<MO>); }
0605 #else
0606         constexpr SuperData(Getter g) : direct(g()) {}
0607         constexpr operator const QMetaObject *() const
0608         { return direct; }
0609         template <const QMetaObject &MO> static constexpr SuperData link()
0610         { return SuperData(QMetaObject::staticMetaObject<MO>()); }
0611 #endif
0612     };
0613 
0614     struct Data { // private data
0615         SuperData superdata;
0616         const uint *stringdata;
0617         const uint *data;
0618         typedef void (*StaticMetacallFunction)(QObject *, QMetaObject::Call, int, void **);
0619         StaticMetacallFunction static_metacall;
0620         const SuperData *relatedMetaObjects;
0621         const QtPrivate::QMetaTypeInterface *const *metaTypes;
0622         void *extradata; //reserved for future use
0623     } d;
0624 
0625 private:
0626     // Just need to have this here with a separate name so the other inline
0627     // functions can call this without any ambiguity
0628     template <typename Func, typename... Args>
0629     static bool
0630     invokeMethodCallableHelper(typename QtPrivate::ContextTypeForFunctor<Func>::ContextType *object,
0631             Func &&function, Qt::ConnectionType type, const QMetaMethodReturnArgument &ret,
0632             Args &&...args)
0633     {
0634         using Callable = QtPrivate::Callable<Func, Args...>;
0635         using ExpectedArguments = typename Callable::Arguments;
0636         static_assert(sizeof...(Args) <= ExpectedArguments::size, "Too many arguments");
0637         using ActualArguments = QtPrivate::List<Args...>;
0638         static_assert(QtPrivate::CheckCompatibleArguments<ActualArguments,
0639                               ExpectedArguments>::value,
0640                 "Incompatible arguments");
0641 
0642         auto h = QtPrivate::invokeMethodHelper(ret, std::forward<Args>(args)...);
0643 
0644         // NOLINTBEGIN(clang-analyzer-cplusplus.NewDeleteLeaks)
0645         auto callable = new QtPrivate::QCallableObject<std::decay_t<Func>, ActualArguments,
0646                 typename Callable::ReturnType>(std::forward<Func>(function));
0647         return invokeMethodImpl(object, callable, type, h.parameterCount(), h.parameters.data(),
0648                 h.typeNames.data(), h.metaTypes.data());
0649         // NOLINTEND(clang-analyzer-cplusplus.NewDeleteLeaks)
0650     }
0651 
0652     static bool invokeMethodImpl(QObject *object, const char *member, Qt::ConnectionType type,
0653                                  qsizetype parameterCount, const void *const *parameters, const char *const *names,
0654                                  const QtPrivate::QMetaTypeInterface * const *metaTypes);
0655     static bool invokeMethodImpl(QObject *object, QtPrivate::QSlotObjectBase *slotObj,
0656                                  Qt::ConnectionType type, qsizetype parameterCount,
0657                                  const void *const *params, const char *const *names,
0658                                  const QtPrivate::QMetaTypeInterface *const *metaTypes);
0659 #if QT_CORE_REMOVED_SINCE(6, 7)
0660     static bool invokeMethodImpl(QObject *object, QtPrivate::QSlotObjectBase *slot, Qt::ConnectionType type, void *ret);
0661 #endif
0662     static QObject *newInstanceImpl(const QMetaObject *mobj, qsizetype parameterCount,
0663                                     const void **parameters, const char **typeNames,
0664                                     const QtPrivate::QMetaTypeInterface **metaTypes);
0665 
0666     static QMetaObject::Connection connectImpl(const QObject *sender, const QMetaMethod& signal,
0667                                             const QObject *receiver, void **slotPtr,
0668                                             QtPrivate::QSlotObjectBase *slot, Qt::ConnectionType type);
0669 
0670     friend class QTimer;
0671     friend class QChronoTimer;
0672 };
0673 
0674 class Q_CORE_EXPORT QMetaObject::Connection {
0675     mutable // QTBUG-144929
0676     void *d_ptr; //QObjectPrivate::Connection*
0677     explicit Connection(void *data) : d_ptr(data) {  }
0678     friend class QObject;
0679     friend class QObjectPrivate;
0680     friend struct QMetaObject;
0681     bool isConnected_helper() const;
0682 public:
0683     ~Connection();
0684     Connection();
0685     Connection(const Connection &other);
0686     Connection &operator=(const Connection &other);
0687 #ifdef Q_QDOC
0688     operator bool() const;
0689 #else
0690     // still using the restricted bool trick here, in order to support
0691     // code using copy-init (e.g. `bool ok = connect(...)`)
0692     typedef void *Connection::*RestrictedBool;
0693     operator RestrictedBool() const { return d_ptr && isConnected_helper() ? &Connection::d_ptr : nullptr; }
0694 #endif
0695 
0696     Connection(Connection &&other) noexcept : d_ptr(std::exchange(other.d_ptr, nullptr)) {}
0697     QT_MOVE_ASSIGNMENT_OPERATOR_IMPL_VIA_PURE_SWAP(Connection)
0698     void swap(Connection &other) noexcept { qt_ptr_swap(d_ptr, other.d_ptr); }
0699 };
0700 
0701 template <typename Func>
0702 QMetaObject::Connection
0703     QMetaObject::connect(const QObject *sender, const QMetaMethod &signal,
0704                          const typename QtPrivate::ContextTypeForFunctor<Func>::ContextType *context, Func &&slot,
0705                          Qt::ConnectionType type)
0706 {
0707     using Slot = std::decay_t<Func>;
0708     using FunctionSlotType = QtPrivate::FunctionPointer<Slot>;
0709     void **pSlot = nullptr;
0710     QtPrivate::QSlotObjectBase *slotObject;
0711     if constexpr (FunctionSlotType::ArgumentCount != -1) {
0712         slotObject = new QtPrivate::QCallableObject<Slot, typename FunctionSlotType::Arguments, typename FunctionSlotType::ReturnType>(std::forward<Func>(slot));
0713         if constexpr (FunctionSlotType::IsPointerToMemberFunction) {
0714             pSlot = const_cast<void **>(reinterpret_cast<void *const *>(&slot));
0715         } else {
0716             Q_ASSERT_X((type & Qt::UniqueConnection) == 0, "",
0717                 "QObject::connect: Unique connection requires the slot to be a pointer to "
0718                 "a member function of a QObject subclass.");
0719         }
0720     } else {
0721         using FunctorSlotType = QtPrivate::FunctionPointer<decltype(&Slot::operator())>;
0722         slotObject = new QtPrivate::QCallableObject<Slot, typename FunctorSlotType::Arguments, typename FunctorSlotType::ReturnType>(std::forward<Func>(slot));
0723     }
0724     return QMetaObject::connectImpl(sender, signal, context, pSlot, slotObject, type);
0725 }
0726 
0727 inline void swap(QMetaObject::Connection &lhs, QMetaObject::Connection &rhs) noexcept
0728 {
0729     lhs.swap(rhs);
0730 }
0731 
0732 inline const QMetaObject *QMetaObject::superClass() const
0733 { return d.superdata; }
0734 
0735 namespace QtPrivate {
0736     // Trait that tells if a QObject has a Q_OBJECT macro
0737     template <typename Object> struct HasQ_OBJECT_Macro {
0738         template <typename T>
0739         static char test(int (T::*)(QMetaObject::Call, int, void **));
0740         static int test(int (Object::*)(QMetaObject::Call, int, void **));
0741         enum { Value =  sizeof(test(&Object::qt_metacall)) == sizeof(int) };
0742     };
0743 
0744     template <class TgtType, class SrcType>
0745     inline TgtType qobject_cast_helper(SrcType *object)
0746     {
0747         using ObjType = std::remove_cv_t<std::remove_pointer_t<TgtType>> ;
0748         static_assert(std::is_pointer_v<TgtType>,
0749                 "qobject_cast requires to cast towards a pointer type");
0750         static_assert(HasQ_OBJECT_Macro<ObjType>::Value,
0751                 "qobject_cast requires the type to have a Q_OBJECT macro");
0752 
0753         if constexpr (std::is_final_v<ObjType>) {
0754             if (object && object->metaObject() == &ObjType::staticMetaObject)
0755                 return static_cast<TgtType>(object);
0756             return nullptr;
0757         } else {
0758             return static_cast<TgtType>(ObjType::staticMetaObject.cast(object));
0759         }
0760     }
0761 }
0762 
0763 QT_END_NAMESPACE
0764 
0765 #endif // QOBJECTDEFS_H