8#ifndef QSHAREDPOINTER_H
9#error Do not include qsharedpointer_impl.h directly
13#pragma qt_sync_skip_header_check
14#pragma qt_sync_stop_processing
24#pragma qt_sync_stop_processing
28#include <QtCore/qatomic.h>
29#include <QtCore/qhashfunctions.h>
30#include <QtCore/qmetatype.h>
31#include <QtCore/qxptype_traits.h>
50template <
class X,
class T>
52template <
class X,
class T>
54template <
class X,
class T>
56template <
class X,
class T>
58template <
class X,
class T>
60template <
class X,
class T>
64template <
class X,
class T>
66template <
class X,
class T>
84 template <
class T,
typename Klass,
typename RetVal>
86 {
if (t) (t->*memberDeleter)(); }
87 template <
class T,
typename Deleter>
118 strongref.storeRelaxed(1);
119 weakref.storeRelaxed(1);
129 Q_CORE_EXPORT
void setQObjectShared(
const QObject *,
bool enable);
141 inline void *
operator new(
std::size_t,
void *ptr)
noexcept {
return ptr; }
142 inline void operator delete(
void *ptr) { ::operator
delete(ptr); }
147 template <
class T,
typename Deleter>
178 template <
class T,
typename Deleter>
187 Self *realself =
static_cast<
Self *>(self);
201 Self *d =
static_cast<
Self *>(::operator
new(
sizeof(
Self)));
211 ExternalRefCountWithCustomDeleter() =
delete;
212 ~ExternalRefCountWithCustomDeleter() =
delete;
256 ExternalRefCountWithContiguousData() =
delete;
257 ~ExternalRefCountWithContiguousData() =
delete;
270 template <
typename X>
271 using IfCompatible =
typename std::enable_if<
std::is_convertible<X*, T*>::value,
bool>::type;
283 T *
data()
const noexcept {
return value.get(); }
284 T *
get()
const noexcept {
return value.get(); }
434 template <
typename... Args>
438# ifdef QT_SHAREDPOINTER_TRACK_POINTERS
439 typename Private::DestroyerFn destroy = &Private::safetyCheckDeleter;
441 typename Private::DestroyerFn destroy = &Private::deleter;
443 typename Private::DestroyerFn noDestroy = &Private::noDeleter;
445 typename std::remove_cv<T>::type *ptr;
446 result.d = Private::create(&ptr, noDestroy);
449 new (ptr) T(
std::forward<Args>(arguments)...);
450 result.value.reset(ptr);
451 result.d->destroyer = destroy;
452 result.d->setQObjectShared(result.value.get(),
true);
453# ifdef QT_SHAREDPOINTER_TRACK_POINTERS
454 internalSafetyCheckAdd(result.d, result.value.get());
456 result.enableSharedFromThis(result.data());
460 template <
typename X>
462 {
return std::less<>()(d, other.d); }
463 template <
typename X>
465 {
return std::less<>()(d, other.d); }
467 template <
typename X>
469 {
return d == other.d; }
470 template <
typename X>
472 {
return d == other.d; }
475 {
return std::hash<Data *>()(d); }
478 template <
typename X>
480 {
return lhs
.data() == rhs.data(); }
481 template <
typename X>
485 return Qt::compareThreeWay(lhs.value, rhs.data());
487 QT_DECLARE_ORDERING_OPERATORS_HELPER(STRONG,
QSharedPointer<T>, QSharedPointer<X>,
489 template <
typename X>)
491 template <
typename X>
494 template <
typename X>
500 {
return lhs.
data() ==
nullptr; }
509 void deref()
noexcept
529 template <
typename X,
typename Deleter>
533# ifdef QT_SHAREDPOINTER_TRACK_POINTERS
540#ifdef QT_SHAREDPOINTER_TRACK_POINTERS
556 void ref()
const noexcept { d->weakref.ref(); d->strongref.ref(); }
558 inline void internalSet(Data *o, T *actual)
563 int tmp = o->strongref.loadRelaxed();
566 if (o->strongref.testAndSetRelaxed(tmp, tmp + 1))
568 tmp = o->strongref.loadRelaxed();
578 this->value.reset(actual);
579 if (!d || d->strongref.loadRelaxed() == 0)
580 this->value =
nullptr;
586 Qt::totally_ordered_wrapper<Type *> value;
594 template <
typename X>
600 template <
typename X>
603 template <
typename X>
615 bool isNull()
const noexcept {
return d ==
nullptr || d->strongref.loadRelaxed() == 0 || value ==
nullptr; }
720 {
return !(*
this ==
o); }
728 {
return !(*
this ==
o); }
730 template <
typename X>
733 template <
typename X>
746 template <
typename X>
749 template <
typename X>
753 template <
typename X>
756 template <
typename X>
785 inline void internalSet(Data *o, T *actual)
790 if (d && !d->weakref.deref())
798 inline T *internalData()
const noexcept
800 return d ==
nullptr || d->strongref.loadRelaxed() == 0 ?
nullptr : value;
809 template <
typename T>
833 inline void initializeFromSharedPointer(
const QSharedPointer<X> &ptr)
const
844template <
class T,
class X>
847 return ptr1.data() - ptr2.data();
849template <
class T,
class X>
852 return ptr1.data() - ptr2;
854template <
class T,
class X>
857 return ptr1 - ptr2.data();
864Q_INLINE_TEMPLATE size_t qHash(
const QSharedPointer<T> &ptr, size_t seed = 0)
866 return qHash(ptr.data(), seed);
871Q_INLINE_TEMPLATE QWeakPointer<T> QSharedPointer<T>::toWeakRef()
const
873 return QWeakPointer<T>(*
this);
886 template <
class X,
class T>
894 template <
class X,
class T>
906template <
class X,
class T>
907Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerCast(
const QSharedPointer<T> &src)
909 X *ptr =
static_cast<X *>(src.data());
910 return QtSharedPointer::copyAndSetPointer(ptr, src);
912template <
class X,
class T>
913Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerCast(QSharedPointer<T> &&src)
915 X *ptr =
static_cast<X *>(src.data());
916 return QtSharedPointer::movePointer(ptr, std::move(src));
918template <
class X,
class T>
919Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerCast(
const QWeakPointer<T> &src)
921 return qSharedPointerCast<X>(src.toStrongRef());
924template <
class X,
class T>
925Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerDynamicCast(
const QSharedPointer<T> &src)
927 X *ptr =
dynamic_cast<X *>(src.data());
929 return QSharedPointer<X>();
930 return QtSharedPointer::copyAndSetPointer(ptr, src);
932template <
class X,
class T>
933Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerDynamicCast(QSharedPointer<T> &&src)
935 X *ptr =
dynamic_cast<X *>(src.data());
937 return QSharedPointer<X>();
938 return QtSharedPointer::movePointer(ptr, std::move(src));
940template <
class X,
class T>
941Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerDynamicCast(
const QWeakPointer<T> &src)
943 return qSharedPointerDynamicCast<X>(src.toStrongRef());
946template <
class X,
class T>
947Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerConstCast(
const QSharedPointer<T> &src)
949 X *ptr =
const_cast<X *>(src.data());
950 return QtSharedPointer::copyAndSetPointer(ptr, src);
952template <
class X,
class T>
953Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerConstCast(QSharedPointer<T> &&src)
955 X *ptr =
const_cast<X *>(src.data());
956 return QtSharedPointer::movePointer(ptr, std::move(src));
958template <
class X,
class T>
959Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerConstCast(
const QWeakPointer<T> &src)
961 return qSharedPointerConstCast<X>(src.toStrongRef());
964template <
class X,
class T>
966QWeakPointer<X> qWeakPointerCast(
const QSharedPointer<T> &src)
968 return qSharedPointerCast<X>(src).toWeakRef();
972template <
class X,
class T>
973Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerObjectCast(
const QSharedPointer<T> &src)
975 X *ptr = qobject_cast<X *>(src.data());
977 return QSharedPointer<X>();
978 return QtSharedPointer::copyAndSetPointer(ptr, src);
980template <
class X,
class T>
981Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerObjectCast(QSharedPointer<T> &&src)
983 X *ptr = qobject_cast<X *>(src.data());
985 return QSharedPointer<X>();
986 return QtSharedPointer::movePointer(ptr, std::move(src));
988template <
class X,
class T>
989Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerObjectCast(
const QWeakPointer<T> &src)
991 return qSharedPointerObjectCast<X>(src.toStrongRef());
994template <
class X,
class T>
1000template <
class X,
class T>
1006template <
class X,
class T>
1016QWeakPointer<
typename std::enable_if<QtPrivate::IsPointerToTypeDerivedFromQObject<T*>::Value, T>::type>
1017qWeakPointerFromVariant(
const QVariant &variant)
1019 return QWeakPointer<T>(qobject_cast<T*>(QtPrivate::EnableInternalData::internalData(QtSharedPointer::weakPointerFromVariant_internal(variant))));
1022QSharedPointer<
typename std::enable_if<QtPrivate::IsPointerToTypeDerivedFromQObject<T*>::Value, T>::type>
1023qSharedPointerFromVariant(
const QVariant &variant)
1025 return qSharedPointerObjectCast<T>(QtSharedPointer::sharedPointerFromVariant_internal(variant));
1030template <
typename X,
class T>
1033 using element_type =
typename std::shared_ptr<X>::element_type;
1034 if (
auto ptr = qobject_cast<element_type *>(src.get()))
1035 return std::shared_ptr<X>(src, ptr);
1036 return std::shared_ptr<X>();
1039template <
typename X,
class T>
1042 using element_type =
typename std::shared_ptr<X>::element_type;
1043 auto castResult = qobject_cast<element_type *>(src.get());
1049 return std::shared_ptr<X>(std::exchange(src,
nullptr), castResult);
1051 return std::shared_ptr<X>();
1054template <
typename X,
class T>
1057 return qobject_pointer_cast<X>(src);
1060template <
typename X,
class T>
1063 return qobject_pointer_cast<X>(
std::move(src));
QSharedPointer< T > sharedFromThis()
QEnableSharedFromThis(const QEnableSharedFromThis &)
QEnableSharedFromThis & operator=(const QEnableSharedFromThis &)
QEnableSharedFromThis()=default
QSharedPointer< const T > sharedFromThis() const
This is an overloaded member function, provided for convenience. It differs from the above function o...
friend bool comparesEqual(const QSharedPointer &lhs, const QSharedPointer< X > &rhs) noexcept
T * operator->() const noexcept
Provides access to the shared pointer's members.
T & operator*() const
Provides access to the shared pointer's members.
T * data() const noexcept
Returns the value of the pointer referenced by this object.
~QSharedPointer()
Destroys this QSharedPointer object.
bool owner_equal(const QSharedPointer< X > &other) const noexcept
operator bool() const noexcept
Returns true if the contained pointer is not \nullptr.
const value_type & const_reference
bool owner_before(const QSharedPointer< X > &other) const noexcept
friend QSharedPointer< X > QtSharedPointer::movePointer(X *ptr, QSharedPointer< Y > &&src)
friend Qt::strong_ordering compareThreeWay(const QSharedPointer &lhs, const QSharedPointer< X > &rhs) noexcept
const value_type * const_pointer
bool isNull() const noexcept
Returns true if this object refers to \nullptr.
bool operator!() const noexcept
Returns true if this object refers to \nullptr.
QSharedPointer & operator=(const QSharedPointer &other) noexcept
Makes this object share other's pointer.
bool owner_equal(const QWeakPointer< X > &other) const noexcept
static QSharedPointer create(Args &&...arguments)
This is an overloaded member function, provided for convenience. It differs from the above function o...
bool owner_before(const QWeakPointer< X > &other) const noexcept
size_t owner_hash() const noexcept
friend QSharedPointer< X > QtSharedPointer::copyAndSetPointer(X *ptr, const QSharedPointer< Y > &src)
const value_type & const_reference
operator bool() const noexcept
Returns true if the contained pointer is not \nullptr.
~QWeakPointer()
Destroys this QWeakPointer object.
bool operator!() const noexcept
Returns true if this object refers to \nullptr.
const value_type * const_pointer
bool isNull() const noexcept
Returns true if this object refers to \nullptr.
QSharedPointer< X > copyAndSetPointer(X *ptr, const QSharedPointer< Y > &src)
void executeDeleter(T *t, Deleter d)
Q_CORE_EXPORT void internalSafetyCheckRemove(const void *)
void executeDeleter(T *t, RetVal(Klass::*memberDeleter)())
Q_CORE_EXPORT void internalSafetyCheckAdd(const void *, const volatile void *)
QSharedPointer< X > movePointer(X *ptr, QSharedPointer< Y > &&src)
T qobject_cast(const QObject *object)
QSharedPointer< X > qSharedPointerConstCast(const QSharedPointer< T > &ptr)
Q_INLINE_TEMPLATE QSharedPointer< T >::difference_type operator-(const QSharedPointer< T > &ptr1, const QSharedPointer< X > &ptr2)
QSharedPointer< X > qSharedPointerObjectCast(QSharedPointer< T > &&ptr)
QSharedPointer< X > qSharedPointerCast(const QSharedPointer< T > &ptr)
QSharedPointer< typename QtSharedPointer::RemovePointer< X >::Type > qobject_cast(const QWeakPointer< T > &src)
QSharedPointer< X > qSharedPointerDynamicCast(const QSharedPointer< T > &ptr)
Q_DECLARE_TYPEINFO_BODY(QSharedPointer< T >, Q_RELOCATABLE_TYPE)
Q_INLINE_TEMPLATE QSharedPointer< T >::difference_type operator-(const QSharedPointer< T > &ptr1, X *ptr2)
QSharedPointer< typename QtSharedPointer::RemovePointer< X >::Type > qobject_cast(const QSharedPointer< T > &src)
QSharedPointer< typename QtSharedPointer::RemovePointer< X >::Type > qobject_cast(QSharedPointer< T > &&src)
Q_INLINE_TEMPLATE QSharedPointer< X >::difference_type operator-(T *ptr1, const QSharedPointer< X > &ptr2)
std::shared_ptr< X > qSharedPointerObjectCast(const std::shared_ptr< T > &src)
std::shared_ptr< X > qobject_pointer_cast(std::shared_ptr< T > &&src)
std::shared_ptr< X > qSharedPointerObjectCast(std::shared_ptr< T > &&src)
std::shared_ptr< X > qobject_pointer_cast(const std::shared_ptr< T > &src)
Q_DECLARE_TYPEINFO_BODY(QWeakPointer< T >, Q_RELOCATABLE_TYPE)
void swap(QWeakPointer< T > &p1, QWeakPointer< T > &p2) noexcept
QSharedPointer< X > qSharedPointerConstCast(QSharedPointer< T > &&ptr)
QSharedPointer< X > qSharedPointerDynamicCast(QSharedPointer< T > &&ptr)
QSharedPointer< X > qSharedPointerCast(QSharedPointer< T > &&ptr)
void swap(QSharedPointer< T > &p1, QSharedPointer< T > &p2) noexcept
QSharedPointer< X > qSharedPointerObjectCast(const QSharedPointer< T > &ptr)
static T * internalData(const QWeakPointer< T > &p) noexcept
CustomDeleter(T *p, NormalDeleter)
CustomDeleter(T *p, Deleter d)
QBasicAtomicInt strongref
void(* DestroyerFn)(ExternalRefCountData *)
void * operator new(std::size_t, void *ptr) noexcept
ExternalRefCountData(Qt::Initialization)
ExternalRefCountData(DestroyerFn d)
QT6_ONLY(Q_CORE_EXPORT void setQObjectShared(const QObject *, bool enable);) inline void checkQObjectShared(...)
void operator delete(void *, void *)
void operator delete(void *ptr)
static void deleter(ExternalRefCountData *self)
static void noDeleter(ExternalRefCountData *)
ExternalRefCountData Parent
std::remove_cv< T >::type NoCVType
static ExternalRefCountData * create(NoCVType **ptr, DestroyerFn destroy)
static void safetyCheckDeleter(ExternalRefCountData *self)
static Self * create(T *ptr, Deleter userDeleter, DestroyerFn actualDeleter)
ExternalRefCountData BaseClass
CustomDeleter< T, Deleter > extra
static void safetyCheckDeleter(ExternalRefCountData *self)
static void deleter(ExternalRefCountData *self)
ExternalRefCountWithCustomDeleter Self