diff options
author | Kent Hansen <khansen@trolltech.com> | 2009-08-05 14:10:47 (GMT) |
---|---|---|
committer | Kent Hansen <khansen@trolltech.com> | 2009-08-05 14:10:47 (GMT) |
commit | 1d7d5436eea09a232187836e59d2a937a752dee4 (patch) | |
tree | 6bd9ae61abb1467aceddc5a828fc2e65d93b2534 /src/corelib/tools | |
parent | 791bddfcd5cc7540219835ef5d91486acd833c4b (diff) | |
parent | fb8bb148affec842e8fa1a70616c64c7d3066ee8 (diff) | |
download | Qt-1d7d5436eea09a232187836e59d2a937a752dee4.zip Qt-1d7d5436eea09a232187836e59d2a937a752dee4.tar.gz Qt-1d7d5436eea09a232187836e59d2a937a752dee4.tar.bz2 |
Merge branch 'master' of git@scm.dev.nokia.troll.no:qt/qt into qtscript-jsc-backend
Conflicts:
src/script/qscriptextqobject.cpp
Diffstat (limited to 'src/corelib/tools')
-rw-r--r-- | src/corelib/tools/qbytedata_p.h | 12 | ||||
-rw-r--r-- | src/corelib/tools/qcontiguouscache.h | 7 | ||||
-rw-r--r-- | src/corelib/tools/qshareddata.cpp | 2 | ||||
-rw-r--r-- | src/corelib/tools/qsharedpointer.cpp | 149 | ||||
-rw-r--r-- | src/corelib/tools/qsharedpointer.h | 1 | ||||
-rw-r--r-- | src/corelib/tools/qsharedpointer_impl.h | 192 |
6 files changed, 277 insertions, 86 deletions
diff --git a/src/corelib/tools/qbytedata_p.h b/src/corelib/tools/qbytedata_p.h index cc10ea2..f3724f6 100644 --- a/src/corelib/tools/qbytedata_p.h +++ b/src/corelib/tools/qbytedata_p.h @@ -42,8 +42,18 @@ #ifndef QBYTEDATA_H #define QBYTEDATA_H -#include <qbytearray.h> +// +// W A R N I N G +// ------------- +// +// This file is not part of the Qt API. It exists purely as an +// implementation detail. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. +// +#include <qbytearray.h> QT_BEGIN_NAMESPACE diff --git a/src/corelib/tools/qcontiguouscache.h b/src/corelib/tools/qcontiguouscache.h index 0020d22..7221925 100644 --- a/src/corelib/tools/qcontiguouscache.h +++ b/src/corelib/tools/qcontiguouscache.h @@ -44,6 +44,7 @@ #include <QtCore/qatomic.h> #include <limits.h> +#include <new> QT_BEGIN_HEADER @@ -76,6 +77,12 @@ struct QContiguousCacheTypedData int start; int offset; uint sharable : 1; + // uint unused : 31; + + // total is 24 bytes (HP-UX aCC: 40 bytes) + // the next entry is already aligned to 8 bytes + // there will be an 8 byte gap here if T requires 16-byte alignment + // (such as long double on 64-bit platforms, __int128, __float128) T array[1]; }; diff --git a/src/corelib/tools/qshareddata.cpp b/src/corelib/tools/qshareddata.cpp index 3cd37a7..6cd220c 100644 --- a/src/corelib/tools/qshareddata.cpp +++ b/src/corelib/tools/qshareddata.cpp @@ -51,7 +51,7 @@ QT_BEGIN_NAMESPACE QSharedData is designed to be used with QSharedDataPointer or QExplicitlySharedDataPointer to implement custom \l{implicitly - shared} or \l {explicitly shared} classes. QSharedData provides + shared} or explicitly shared classes. QSharedData provides \l{thread-safe} reference counting. See QSharedDataPointer and QExplicitlySharedDataPointer for details. diff --git a/src/corelib/tools/qsharedpointer.cpp b/src/corelib/tools/qsharedpointer.cpp index 59dfffe..f18dee8 100644 --- a/src/corelib/tools/qsharedpointer.cpp +++ b/src/corelib/tools/qsharedpointer.cpp @@ -128,7 +128,7 @@ To access the pointer that QWeakPointer is tracking, you must first create a QSharedPointer object and verify if the pointer - is null or not. + is null or not. See QWeakPointer::toStrongRef() for more information. \sa QSharedPointer */ @@ -210,6 +210,8 @@ If \tt T is a derived type of the template parameter of this class, QSharedPointer will perform an automatic cast. Otherwise, you will get a compiler error. + + \sa QWeakPointer::toStrongRef() */ /*! @@ -362,6 +364,8 @@ Returns a weak reference object that shares the pointer referenced by this object. + + \sa QWeakPointer::QWeakPointer() */ /*! @@ -478,10 +482,78 @@ */ /*! + \fn T *QWeakPointer::data() const + \since 4.6 + + Returns the value of the pointer being tracked by this QWeakPointer, + \b without ensuring that it cannot get deleted. To have that guarantee, + use toStrongRef(), which returns a QSharedPointer object. If this + function can determine that the pointer has already been deleted, it + returns 0. + + It is ok to obtain the value of the pointer and using that value itself, + like for example in debugging statements: + + \code + qDebug("Tracking %p", weakref.data()); + \endcode + + However, dereferencing the pointer is only allowed if you can guarantee + by external means that the pointer does not get deleted. For example, + if you can be certain that no other thread can delete it, nor the + functions that you may call. + + If that is the case, then the following code is valid: + + \code + // this pointer cannot be used in another thread + // so other threads cannot delete it + QWeakPointer<int> weakref = obtainReference(); + + Object *obj = weakref.data(); + if (obj) { + // if the pointer wasn't deleted yet, we know it can't get + // deleted by our own code here nor the functions we call + otherFunction(obj); + } + \endcode + + Use this function with care. + + \sa isNull(), toStrongRef() +*/ + +/*! \fn QSharedPointer<T> QWeakPointer::toStrongRef() const Promotes this weak reference to a strong one and returns a - QSharedPointer object holding that reference. + QSharedPointer object holding that reference. When promoting to + QSharedPointer, this function verifies if the object has been deleted + already or not. If it hasn't, this function increases the reference + count to the shared object, thus ensuring that it will not get + deleted. + + Since this function can fail to obtain a valid strong reference to the + shared object, you should always verify if the conversion succeeded, + by calling QSharedPointer::isNull() on the returned object. + + For example, the following code promotes a QWeakPointer that was held + to a strong reference and, if it succeeded, it prints the value of the + integer that was held: + + \code + QWeakPointer<int> weakref; + + // ... + + QSharedPointer<int> strong = weakref.toStrongRef(); + if (strong) + qDebug() << "The value is:" << *strong; + else + qDebug() << "The value has already been deleted"; + \endcode + + \sa QSharedPointer::QSharedPointer() */ /*! @@ -792,6 +864,56 @@ #include <qset.h> #include <qmutex.h> +#if !defined(QT_NO_QOBJECT) +#include "../kernel/qobject_p.h" + +/*! + \internal + This function is called for a just-created QObject \a obj, to enable + the use of QSharedPointer and QWeakPointer. + + When QSharedPointer is active in a QObject, the object must not be deleted + directly: the lifetime is managed by the QSharedPointer object. In that case, + the deleteLater() and parent-child relationship in QObject only decrease + the strong reference count, instead of deleting the object. +*/ +void QtSharedPointer::ExternalRefCountData::setQObjectShared(const QObject *obj, bool) +{ + Q_ASSERT(obj); + QObjectPrivate *d = QObjectPrivate::get(const_cast<QObject *>(obj)); + + if (d->sharedRefcount) + qFatal("QSharedPointer: pointer %p already has reference counting", obj); + d->sharedRefcount = this; + + // QObject decreases the refcount too, so increase it up + weakref.ref(); +} + +QtSharedPointer::ExternalRefCountData *QtSharedPointer::ExternalRefCountData::getAndRef(const QObject *obj) +{ + Q_ASSERT(obj); + QObjectPrivate *d = QObjectPrivate::get(const_cast<QObject *>(obj)); + ExternalRefCountData *that = d->sharedRefcount; + if (that) { + that->weakref.ref(); + return that; + } + + // we can create the refcount data because it doesn't exist + ExternalRefCountData *x = new ExternalRefCountData(Qt::Uninitialized); + x->strongref = -1; + x->weakref = 2; // the QWeakPointer that called us plus the QObject itself + if (!d->sharedRefcount.testAndSetRelease(0, x)) { + delete x; + d->sharedRefcount->weakref.ref(); + } + return d->sharedRefcount; +} +#endif + + + #if !defined(QT_NO_MEMBER_TEMPLATES) //# define QT_SHARED_POINTER_BACKTRACE_SUPPORT @@ -897,6 +1019,7 @@ QT_BEGIN_NAMESPACE namespace QtSharedPointer { Q_CORE_EXPORT void internalSafetyCheckAdd(const volatile void *); Q_CORE_EXPORT void internalSafetyCheckRemove(const volatile void *); + Q_AUTOTEST_EXPORT void internalSafetyCheckCleanCheck(); } /*! @@ -961,6 +1084,7 @@ void QtSharedPointer::internalSafetyCheckAdd2(const void *d_ptr, const volatile kp->dPointers.insert(d_ptr, data); kp->dataPointers.insert(ptr, d_ptr); + Q_ASSERT(kp->dPointers.size() == kp->dataPointers.size()); } /*! @@ -985,10 +1109,29 @@ void QtSharedPointer::internalSafetyCheckRemove2(const void *d_ptr) Q_ASSERT(it2 != kp->dataPointers.end()); //qDebug("Removing d=%p value=%p", d_ptr, it->pointer); - + // remove entries kp->dataPointers.erase(it2); kp->dPointers.erase(it); + Q_ASSERT(kp->dPointers.size() == kp->dataPointers.size()); +} + +/*! + \internal + Called by the QSharedPointer autotest +*/ +void QtSharedPointer::internalSafetyCheckCleanCheck() +{ +# ifdef QT_BUILD_INTERNAL + KnownPointers *const kp = knownPointers(); + Q_ASSERT_X(kp, "internalSafetyCheckSelfCheck()", "Called after global statics deletion!"); + + if (kp->dPointers.size() != kp->dataPointers.size()) + qFatal("Internal consistency error: the number of pointers is not equal!"); + + if (!kp->dPointers.isEmpty()) + qFatal("Pointer cleaning failed: %d entries remaining", kp->dPointers.size()); +# endif } QT_END_NAMESPACE diff --git a/src/corelib/tools/qsharedpointer.h b/src/corelib/tools/qsharedpointer.h index abd83ad..2f86ce7 100644 --- a/src/corelib/tools/qsharedpointer.h +++ b/src/corelib/tools/qsharedpointer.h @@ -115,6 +115,7 @@ public: QWeakPointer<T> operator=(const QWeakPointer<T> &other); QWeakPointer<T> operator=(const QSharedPointer<T> &other); + T *data() const; void clear(); QSharedPointer<T> toStrongRef() const; diff --git a/src/corelib/tools/qsharedpointer_impl.h b/src/corelib/tools/qsharedpointer_impl.h index b8f4139..8a34362 100644 --- a/src/corelib/tools/qsharedpointer_impl.h +++ b/src/corelib/tools/qsharedpointer_impl.h @@ -94,26 +94,27 @@ namespace QtSharedPointer { template <class T> class InternalRefCount; template <class T> class ExternalRefCount; - template <class X, class T> QSharedPointer<X> strongRefFromWeakHelper(const QWeakPointer<T> &, X*); template <class X, class Y> QSharedPointer<X> copyAndSetPointer(X * ptr, const QSharedPointer<Y> &src); // used in debug mode to verify the reuse of pointers Q_CORE_EXPORT void internalSafetyCheckAdd2(const void *, const volatile void *); Q_CORE_EXPORT void internalSafetyCheckRemove2(const void *); - + template <class T, typename Klass, typename RetVal> inline void executeDeleter(T *t, RetVal (Klass:: *memberDeleter)()) { (t->*memberDeleter)(); } template <class T, typename Deleter> inline void executeDeleter(T *t, Deleter d) { d(t); } + template <class T> inline void normalDeleter(T *t) { delete t; } + + // this uses partial template specialization + // the only compilers that didn't support this were MSVC 6.0 and 2002 + template <class T> struct RemovePointer; + template <class T> struct RemovePointer<T *> { typedef T Type; }; + template <class T> struct RemovePointer<QSharedPointer<T> > { typedef T Type; }; + template <class T> struct RemovePointer<QWeakPointer<T> > { typedef T Type; }; - // - // Depending on its template parameter, QSharedPointer derives from either - // QtSharedPointer::InternalRefCount or from QtSharedPointer::ExternalRefCount. - // Both of these classes derive from QtSharedPointer::Basic, which provides common - // operations, - // template <class T> class Basic { @@ -129,21 +130,10 @@ namespace QtSharedPointer { inline T *operator->() const { return data(); } protected: - inline Basic() : value(0) { } + inline Basic(T *ptr = 0) : value(ptr) { } + inline Basic(Qt::Initialization) { } // ~Basic(); - inline void verifyReconstruction(const T *ptr) - { - Q_ASSERT_X(!ptr || value != ptr, "QSharedPointer", - "QSharedPointer violation: you cannot create two QSharedPointer objects " - "from the same pointer"); - - // make use of the "ptr" variable in the no-op statement below - // since this function is in a public header, we don't - // want warnings on "unused variables" to show up everywhere - ptr = 0; - } - inline void internalConstruct(T *ptr) { value = ptr; @@ -160,14 +150,26 @@ namespace QtSharedPointer { struct ExternalRefCountData { - QAtomicInt weakref; - QAtomicInt strongref; + QBasicAtomicInt weakref; + QBasicAtomicInt strongref; - inline ExternalRefCountData() : weakref(1), strongref(1) { } - virtual inline ~ExternalRefCountData() { Q_ASSERT(!weakref); Q_ASSERT(!strongref); } + inline ExternalRefCountData() + { + QBasicAtomicInt proto = Q_BASIC_ATOMIC_INITIALIZER(1); + weakref = strongref = proto; + } + inline ExternalRefCountData(Qt::Initialization) { } + virtual inline ~ExternalRefCountData() { Q_ASSERT(!weakref); Q_ASSERT(strongref <= 0); } virtual inline bool destroy() { return false; } + +#ifndef QT_NO_QOBJECT + Q_CORE_EXPORT static ExternalRefCountData *getAndRef(const QObject *); + Q_CORE_EXPORT void setQObjectShared(const QObject *, bool enable); +#endif + inline void setQObjectShared(...) { } }; + // sizeof(ExternalRefCount) = 12 (32-bit) / 16 (64-bit) template <class T, typename Deleter> struct CustomDeleter @@ -177,6 +179,9 @@ namespace QtSharedPointer { inline CustomDeleter(T *p, Deleter d) : deleter(d), ptr(p) {} }; + // sizeof(CustomDeleter) = sizeof(Deleter) + sizeof(void*) + // for Deleter = function pointer: 8 (32-bit) / 16 (64-bit) + // for Deleter = PMF: 12 (32-bit) / 24 (64-bit) (GCC) struct ExternalRefCountWithDestroyFn: public ExternalRefCountData { @@ -190,6 +195,7 @@ namespace QtSharedPointer { inline bool destroy() { destroyer(this); return true; } inline void operator delete(void *ptr) { ::operator delete(ptr); } }; + // sizeof(ExternalRefCountWithDestroyFn) = 16 (32-bit) / 24 (64-bit) template <class T, typename Deleter> struct ExternalRefCountWithCustomDeleter: public ExternalRefCountWithDestroyFn @@ -203,11 +209,23 @@ namespace QtSharedPointer { { Self *realself = static_cast<Self *>(self); executeDeleter(realself->extra.ptr, realself->extra.deleter); + + // delete the deleter too + realself->extra.~Next(); + } + static void safetyCheckDeleter(ExternalRefCountData *self) + { + internalSafetyCheckRemove2(self); + deleter(self); } static inline Self *create(T *ptr, Deleter userDeleter) { +# ifdef QT_SHAREDPOINTER_TRACK_POINTERS + DestroyerFn destroy = &safetyCheckDeleter; +# else DestroyerFn destroy = &deleter; +# endif Self *d = static_cast<Self *>(::operator new(sizeof(Self))); // initialize the two sub-objects @@ -234,10 +252,19 @@ namespace QtSharedPointer { static_cast<ExternalRefCountWithContiguousData *>(self); that->data.~T(); } + static void safetyCheckDeleter(ExternalRefCountData *self) + { + internalSafetyCheckRemove2(self); + deleter(self); + } static inline ExternalRefCountData *create(T **ptr) { +# ifdef QT_SHAREDPOINTER_TRACK_POINTERS + DestroyerFn destroy = &safetyCheckDeleter; +# else DestroyerFn destroy = &deleter; +# endif ExternalRefCountWithContiguousData *d = static_cast<ExternalRefCountWithContiguousData *>(::operator new(sizeof(ExternalRefCountWithContiguousData))); @@ -258,9 +285,9 @@ namespace QtSharedPointer { template <class T> class ExternalRefCount: public Basic<T> { - typedef ExternalRefCountData Data; - typedef void (*DeleterFunction)(T *); protected: + typedef ExternalRefCountData Data; + inline void ref() const { d->weakref.ref(); d->strongref.ref(); } inline bool deref() { @@ -272,42 +299,51 @@ namespace QtSharedPointer { inline void internalConstruct(T *ptr) { - Basic<T>::internalConstruct(ptr); - Q_ASSERT(!d); +#ifdef QT_SHAREDPOINTER_TRACK_POINTERS + internalConstruct<void (*)(T *)>(ptr, normalDeleter); +#else if (ptr) d = new Data; -#ifdef QT_SHAREDPOINTER_TRACK_POINTERS - if (ptr) internalSafetyCheckAdd2(d, ptr); + else + d = 0; + internalFinishConstruction(ptr); #endif } template <typename Deleter> inline void internalConstruct(T *ptr, Deleter deleter) { - Basic<T>::internalConstruct(ptr); - Q_ASSERT(!d); if (ptr) d = ExternalRefCountWithCustomDeleter<T, Deleter>::create(ptr, deleter); -#ifdef QT_SHAREDPOINTER_TRACK_POINTERS - if (ptr) internalSafetyCheckAdd2(d, ptr); -#endif + else + d = 0; + internalFinishConstruction(ptr); } inline void internalCreate() { T *ptr; d = ExternalRefCountWithContiguousData<T>::create(&ptr); + Basic<T>::internalConstruct(ptr); + } + inline void internalFinishConstruction(T *ptr) + { Basic<T>::internalConstruct(ptr); + if (ptr) d->setQObjectShared(ptr, true); #ifdef QT_SHAREDPOINTER_TRACK_POINTERS if (ptr) internalSafetyCheckAdd2(d, ptr); #endif } inline ExternalRefCount() : d(0) { } - inline ~ExternalRefCount() { if (d && !deref()) delete d; } + inline ExternalRefCount(Qt::Initialization i) : Basic<T>(i) { } inline ExternalRefCount(const ExternalRefCount<T> &other) : Basic<T>(other), d(other.d) { if (d) ref(); } + template <class X> + inline ExternalRefCount(const ExternalRefCount<X> &other) : Basic<T>(other.value), d(other.d) + { if (d) ref(); } + inline ~ExternalRefCount() { if (d && !deref()) delete d; } template <class X> inline void internalCopy(const ExternalRefCount<X> &other) @@ -317,32 +353,35 @@ namespace QtSharedPointer { inline void internalDestroy() { -#ifdef QT_SHAREDPOINTER_TRACK_POINTERS - internalSafetyCheckRemove2(d); -#endif if (!d->destroy()) delete this->value; } - private: #if defined(Q_NO_TEMPLATE_FRIENDS) public: #else template <class X> friend class ExternalRefCount; template <class X> friend class QWeakPointer; template <class X, class Y> friend QSharedPointer<X> copyAndSetPointer(X * ptr, const QSharedPointer<Y> &src); - template <class X, class Y> friend QSharedPointer<X> QtSharedPointer::strongRefFromWeakHelper(const QWeakPointer<Y> &src, X *); #endif inline void internalSet(Data *o, T *actual) { - if (d == o) return; - if (o && !o->strongref) - o = 0; if (o) { - verifyReconstruction(actual); - o->weakref.ref(); - o->strongref.ref(); + // increase the strongref, but never up from zero + // or less (-1 is used by QWeakPointer on untracked QObject) + register int tmp = o->strongref; + while (tmp > 0) { + // try to increment from "tmp" to "tmp + 1" + if (o->strongref.testAndSetRelaxed(tmp, tmp + 1)) + break; // succeeded + tmp = o->strongref; // failed, try again + } + + if (tmp > 0) + o->weakref.ref(); + else + o = 0; } if (d && !deref()) delete d; @@ -350,9 +389,6 @@ namespace QtSharedPointer { this->value = d && d->strongref ? actual : 0; } -#if defined(QT_BUILD_INTERNAL) - public: -#endif Data *d; private: @@ -368,7 +404,8 @@ public: inline QSharedPointer() { } // inline ~QSharedPointer() { } - inline explicit QSharedPointer(T *ptr) { internalConstruct(ptr); } + inline explicit QSharedPointer(T *ptr) : BaseClass(Qt::Uninitialized) + { internalConstruct(ptr); } template <typename Deleter> inline QSharedPointer(T *ptr, Deleter d) { internalConstruct(ptr, d); } @@ -380,13 +417,9 @@ public: return *this; } - inline QSharedPointer(const QWeakPointer<T> &other) - { *this = QtSharedPointer::strongRefFromWeakHelper(other, static_cast<T*>(0)); } - inline QSharedPointer<T> &operator=(const QWeakPointer<T> &other) - { *this = QtSharedPointer::strongRefFromWeakHelper(other, static_cast<T*>(0)); return *this; } - template <class X> - inline QSharedPointer(const QSharedPointer<X> &other) { *this = other; } + inline QSharedPointer(const QSharedPointer<X> &other) : BaseClass(other) + { } template <class X> inline QSharedPointer<T> &operator=(const QSharedPointer<X> &other) @@ -397,12 +430,12 @@ public: } template <class X> - inline QSharedPointer(const QWeakPointer<X> &other) - { *this = QtSharedPointer::strongRefFromWeakHelper(other, static_cast<T *>(0)); } + inline QSharedPointer(const QWeakPointer<X> &other) : BaseClass(Qt::Uninitialized) + { this->d = 0; *this = other; } template <class X> inline QSharedPointer<T> &operator=(const QWeakPointer<X> &other) - { *this = strongRefFromWeakHelper(other, static_cast<T *>(0)); return *this; } + { internalSet(other.d, other.value); return *this; } template <class X> QSharedPointer<X> staticCast() const @@ -434,14 +467,18 @@ public: QWeakPointer<T> toWeakRef() const; +protected: + inline QSharedPointer(Qt::Initialization i) : BaseClass(i) {} + public: static inline QSharedPointer<T> create() { - QSharedPointer<T> result; + QSharedPointer<T> result(Qt::Uninitialized); result.internalCreate(); // now initialize the data new (result.data()) T(); + result.internalFinishConstruction(result.data()); return result; } }; @@ -456,9 +493,19 @@ public: inline bool isNull() const { return d == 0 || d->strongref == 0 || value == 0; } inline operator RestrictedBool() const { return isNull() ? 0 : &QWeakPointer::value; } inline bool operator !() const { return isNull(); } + inline T *data() const { return d == 0 || d->strongref == 0 ? 0 : value; } inline QWeakPointer() : d(0), value(0) { } inline ~QWeakPointer() { if (d && !d->weakref.deref()) delete d; } + + // special constructor that is enabled only if X derives from QObject + template <class X> + inline QWeakPointer(X *ptr) : d(ptr ? d->getAndRef(ptr) : 0), value(ptr) + { } + template <class X> + inline QWeakPointer &operator=(X *ptr) + { return *this = QWeakPointer(ptr); } + inline QWeakPointer(const QWeakPointer<T> &o) : d(o.d), value(o.value) { if (d) d->weakref.ref(); } inline QWeakPointer<T> &operator=(const QWeakPointer<T> &o) @@ -510,7 +557,7 @@ public: template <class X> inline bool operator==(const QSharedPointer<X> &o) const - { return d == o.d && value == static_cast<const T *>(o.data()); } + { return d == o.d; } template <class X> inline bool operator!=(const QSharedPointer<X> &o) const @@ -525,7 +572,7 @@ private: #if defined(Q_NO_TEMPLATE_FRIENDS) public: #else - template <class X, class Y> friend QSharedPointer<X> QtSharedPointer::strongRefFromWeakHelper(const QWeakPointer<Y> &src, X *); + template <class X> friend class QSharedPointer; #endif inline void internalSet(Data *o, T *actual) @@ -602,14 +649,6 @@ namespace QtSharedPointer { result.internalSet(src.d, ptr); return result; } - template <class X, class T> - Q_INLINE_TEMPLATE QSharedPointer<X> strongRefFromWeakHelper - (const QT_PREPEND_NAMESPACE(QWeakPointer<T>) &src, X *) - { - QSharedPointer<X> result; - result.internalSet(src.d, src.value); - return result; - } } // cast operators @@ -669,14 +708,6 @@ Q_INLINE_TEMPLATE QSharedPointer<X> qSharedPointerObjectCast(const QWeakPointer< return qSharedPointerObjectCast<X>(src.toStrongRef()); } -# ifndef QT_NO_PARTIAL_TEMPLATE_SPECIALIZATION -namespace QtSharedPointer { - template <class T> struct RemovePointer; - template <class T> struct RemovePointer<T *> { typedef T Type; }; - template <class T> struct RemovePointer<QSharedPointer<T> > { typedef T Type; }; - template <class T> struct RemovePointer<QWeakPointer<T> > { typedef T Type; }; -} - template <class X, class T> inline QSharedPointer<typename QtSharedPointer::RemovePointer<X>::Type> qobject_cast(const QSharedPointer<T> &src) @@ -689,7 +720,6 @@ qobject_cast(const QWeakPointer<T> &src) { return qSharedPointerObjectCast<typename QtSharedPointer::RemovePointer<X>::Type, T>(src); } -# endif #endif |