diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/corelib/text/qbytearray.cpp | 21 | ||||
| -rw-r--r-- | src/corelib/text/qbytearray.h | 18 | ||||
| -rw-r--r-- | src/corelib/text/qstring.cpp | 18 | ||||
| -rw-r--r-- | src/corelib/text/qstring.h | 18 | ||||
| -rw-r--r-- | src/corelib/tools/qarraydata.cpp | 5 | ||||
| -rw-r--r-- | src/corelib/tools/qarraydata.h | 29 | ||||
| -rw-r--r-- | src/corelib/tools/qarraydataops.h | 27 | ||||
| -rw-r--r-- | src/corelib/tools/qarraydatapointer.h | 53 | ||||
| -rw-r--r-- | src/corelib/tools/qlist.h | 36 |
9 files changed, 77 insertions, 148 deletions
diff --git a/src/corelib/text/qbytearray.cpp b/src/corelib/text/qbytearray.cpp index 1a1b2d86b0e..1b5fa8e5eb5 100644 --- a/src/corelib/text/qbytearray.cpp +++ b/src/corelib/text/qbytearray.cpp @@ -1175,7 +1175,8 @@ QByteArray &QByteArray::operator=(const char *str) const auto capacityAtEnd = d->allocatedCapacity() - d.freeSpaceAtBegin(); if (d->needsDetach() || len > capacityAtEnd || (len < size() && len < (capacityAtEnd >> 1))) - reallocData(len, d->detachFlags()); + // ### inefficient! reallocData() does copy the old data and we then overwrite it in the next line + reallocData(len, QArrayData::KeepSize); memcpy(d.data(), str, len + 1); // include null terminator d.size = len; } @@ -1676,7 +1677,7 @@ void QByteArray::resize(qsizetype size) const auto capacityAtEnd = capacity() - d.freeSpaceAtBegin(); if (d->needsDetach() || size > capacityAtEnd) - reallocData(size, d->detachFlags() | Data::GrowsForward); + reallocData(size, QArrayData::Grow); d.size = size; if (d->allocatedCapacity()) d.data()[size] = 0; @@ -1700,7 +1701,7 @@ QByteArray &QByteArray::fill(char ch, qsizetype size) return *this; } -void QByteArray::reallocData(qsizetype alloc, Data::ArrayOptions options) +void QByteArray::reallocData(qsizetype alloc, QArrayData::AllocationOption option) { if (!alloc) { d = DataPointer::fromRawData(&_empty, 0); @@ -1713,13 +1714,13 @@ void QByteArray::reallocData(qsizetype alloc, Data::ArrayOptions options) const bool slowReallocatePath = d.freeSpaceAtBegin() > 0; if (d->needsDetach() || slowReallocatePath) { - DataPointer dd(Data::allocate(alloc, options), qMin(alloc, d.size)); + DataPointer dd(Data::allocate(alloc, option), qMin(alloc, d.size)); if (dd.size > 0) ::memcpy(dd.data(), d.data(), dd.size); dd.data()[dd.size] = 0; d = dd; } else { - d->reallocate(alloc, options & (QArrayData::GrowsBackwards|QArrayData::GrowsForward) ? QArrayData::Grow : QArrayData::KeepSize); + d->reallocate(alloc, option); } } @@ -1729,7 +1730,7 @@ void QByteArray::reallocGrowData(qsizetype n) n = 1; if (d->needsDetach()) { - DataPointer dd(DataPointer::allocateGrow(d, n, DataPointer::AllocateAtEnd)); + DataPointer dd(DataPointer::allocateGrow(d, n, QArrayData::AllocateAtEnd)); dd->copyAppend(d.data(), d.data() + d.size); dd.data()[dd.size] = 0; d = dd; @@ -1936,9 +1937,9 @@ QByteArray &QByteArray::insert(qsizetype i, QByteArrayView data) sizeToGrow += i - oldSize; if (d->needsDetach() || (sizeToGrow > d.freeSpaceAtBegin() && sizeToGrow > d.freeSpaceAtEnd())) { - DataPointer::AllocationPosition pos = DataPointer::AllocateAtEnd; + QArrayData::AllocationPosition pos = QArrayData::AllocateAtEnd; if (oldSize != 0 && i <= (oldSize >> 1)) - pos = DataPointer::AllocateAtBeginning; + pos = QArrayData::AllocateAtBeginning; DataPointer detached(DataPointer::allocateGrow(d, sizeToGrow, pos)); auto where = d.constBegin() + qMin(i, d->size); @@ -2000,9 +2001,9 @@ QByteArray &QByteArray::insert(qsizetype i, qsizetype count, char ch) sizeToGrow += i - oldSize; if (d->needsDetach() || (sizeToGrow > d.freeSpaceAtBegin() && sizeToGrow > d.freeSpaceAtEnd())) { - DataPointer::AllocationPosition pos = DataPointer::AllocateAtEnd; + QArrayData::AllocationPosition pos = QArrayData::AllocateAtEnd; if (oldSize != 0 && i <= (oldSize >> 1)) - pos = DataPointer::AllocateAtBeginning; + pos = QArrayData::AllocateAtBeginning; DataPointer detached(DataPointer::allocateGrow(d, sizeToGrow, pos)); auto where = d.constBegin() + qMin(i, d->size); diff --git a/src/corelib/text/qbytearray.h b/src/corelib/text/qbytearray.h index c70a7a82d9b..95b607e9dc3 100644 --- a/src/corelib/text/qbytearray.h +++ b/src/corelib/text/qbytearray.h @@ -509,7 +509,7 @@ public: } private: - void reallocData(qsizetype alloc, Data::ArrayOptions options); + void reallocData(qsizetype alloc, QArrayData::AllocationOption option); void reallocGrowData(qsizetype n); void expand(qsizetype i); QByteArray nulTerminated() const; @@ -562,7 +562,7 @@ inline const char *QByteArray::data() const inline const char *QByteArray::constData() const { return data(); } inline void QByteArray::detach() -{ if (d->needsDetach()) reallocData(size(), d->detachFlags()); } +{ if (d->needsDetach()) reallocData(size(), QArrayData::KeepSize); } inline bool QByteArray::isDetached() const { return !d->isShared(); } inline QByteArray::QByteArray(const QByteArray &a) noexcept : d(a.d) @@ -572,22 +572,20 @@ inline qsizetype QByteArray::capacity() const { return qsizetype(d->constAllocat inline void QByteArray::reserve(qsizetype asize) { - if (d->needsDetach() || asize > capacity() - d->freeSpaceAtBegin()) { - reallocData(qMax(size(), asize), d->detachFlags() | Data::CapacityReserved); - } else { + if (d->needsDetach() || asize > capacity() - d->freeSpaceAtBegin()) + reallocData(qMax(size(), asize), QArrayData::KeepSize); + if (d->constAllocatedCapacity()) d->setFlag(Data::CapacityReserved); - } } inline void QByteArray::squeeze() { if (!d.isMutable()) return; - if (d->needsDetach() || size() < capacity()) { - reallocData(size(), d->detachFlags() & ~Data::CapacityReserved); - } else { + if (d->needsDetach() || size() < capacity()) + reallocData(size(), QArrayData::KeepSize); + if (d->constAllocatedCapacity()) d->clearFlag(Data::CapacityReserved); - } } inline char &QByteArray::operator[](qsizetype i) diff --git a/src/corelib/text/qstring.cpp b/src/corelib/text/qstring.cpp index ebdb5710414..40d69c9d9c6 100644 --- a/src/corelib/text/qstring.cpp +++ b/src/corelib/text/qstring.cpp @@ -2415,7 +2415,7 @@ void QString::resize(qsizetype size) const auto capacityAtEnd = capacity() - d.freeSpaceAtBegin(); if (d->needsDetach() || size > capacityAtEnd) - reallocData(size, d->detachFlags() | Data::GrowsForward); + reallocData(size, QArrayData::Grow); d.size = size; if (d->allocatedCapacity()) d.data()[size] = 0; @@ -2497,7 +2497,7 @@ void QString::resize(qsizetype size, QChar fillChar) \sa reserve(), capacity() */ -void QString::reallocData(qsizetype alloc, Data::ArrayOptions allocOptions) +void QString::reallocData(qsizetype alloc, QArrayData::AllocationOption option) { if (!alloc) { d = DataPointer::fromRawData(&_empty, 0); @@ -2510,13 +2510,13 @@ void QString::reallocData(qsizetype alloc, Data::ArrayOptions allocOptions) const bool slowReallocatePath = d.freeSpaceAtBegin() > 0; if (d->needsDetach() || slowReallocatePath) { - DataPointer dd(Data::allocate(alloc, allocOptions), qMin(alloc, d.size)); + DataPointer dd(Data::allocate(alloc, option), qMin(alloc, d.size)); if (dd.size > 0) ::memcpy(dd.data(), d.data(), dd.size * sizeof(QChar)); dd.data()[dd.size] = 0; d = dd; } else { - d->reallocate(alloc, allocOptions & (QArrayData::GrowsBackwards|QArrayData::GrowsForward) ? QArrayData::Grow : QArrayData::KeepSize); + d->reallocate(alloc, option); } } @@ -2526,7 +2526,7 @@ void QString::reallocGrowData(qsizetype n) n = 1; if (d->needsDetach()) { - DataPointer dd(DataPointer::allocateGrow(d, n, DataPointer::AllocateAtEnd)); + DataPointer dd(DataPointer::allocateGrow(d, n, QArrayData::AllocateAtEnd)); dd->copyAppend(d.data(), d.data() + d.size); dd.data()[dd.size] = 0; d = dd; @@ -2737,9 +2737,9 @@ QString& QString::insert(qsizetype i, const QChar *unicode, qsizetype size) sizeToGrow += i - oldSize; if (d->needsDetach() || (sizeToGrow > d.freeSpaceAtBegin() && sizeToGrow > d.freeSpaceAtEnd())) { - DataPointer::AllocationPosition pos = DataPointer::AllocateAtEnd; + QArrayData::AllocationPosition pos = QArrayData::AllocateAtEnd; if (oldSize != 0 && i <= (oldSize >> 1)) - pos = DataPointer::AllocateAtBeginning; + pos = QArrayData::AllocateAtBeginning; DataPointer detached(DataPointer::allocateGrow(d, sizeToGrow, pos)); auto where = d.constBegin() + qMin(i, d->size); @@ -4054,7 +4054,7 @@ QString &QString::replace(const QRegularExpression &re, const QString &after) if (!iterator.hasNext()) // no matches at all return *this; - reallocData(d.size, d->detachFlags()); + reallocData(d.size, QArrayData::KeepSize); qsizetype numCaptures = re.captureCount(); @@ -6157,7 +6157,7 @@ const ushort *QString::utf16() const { if (!d->isMutable()) { // ensure '\0'-termination for ::fromRawData strings - const_cast<QString*>(this)->reallocData(d.size, d->detachFlags()); + const_cast<QString*>(this)->reallocData(d.size, QArrayData::KeepSize); } return reinterpret_cast<const ushort *>(d.data()); } diff --git a/src/corelib/text/qstring.h b/src/corelib/text/qstring.h index 66a99d4e43a..013b367b5ce 100644 --- a/src/corelib/text/qstring.h +++ b/src/corelib/text/qstring.h @@ -1058,7 +1058,7 @@ private: DataPointer d; static const char16_t _empty; - void reallocData(qsizetype alloc, Data::ArrayOptions options); + void reallocData(qsizetype alloc, QArrayData::AllocationOption option); void reallocGrowData(qsizetype n); static int compare_helper(const QChar *data1, qsizetype length1, const QChar *data2, qsizetype length2, @@ -1195,7 +1195,7 @@ inline QChar *QString::data() inline const QChar *QString::constData() const { return data(); } inline void QString::detach() -{ if (d->needsDetach()) reallocData(d.size, d->detachFlags()); } +{ if (d->needsDetach()) reallocData(d.size, QArrayData::KeepSize); } inline bool QString::isDetached() const { return !d->isShared(); } inline void QString::clear() @@ -1267,22 +1267,20 @@ inline QString::~QString() {} inline void QString::reserve(qsizetype asize) { - if (d->needsDetach() || asize >= capacity() - d.freeSpaceAtBegin()) { - reallocData(qMax(asize, size()), d->detachFlags() | Data::CapacityReserved); - } else { + if (d->needsDetach() || asize >= capacity() - d.freeSpaceAtBegin()) + reallocData(qMax(asize, size()), QArrayData::KeepSize); + if (d->constAllocatedCapacity()) d->setFlag(Data::CapacityReserved); - } } inline void QString::squeeze() { if (!d.isMutable()) return; - if (d->needsDetach() || size() < capacity()) { - reallocData(d.size, d->detachFlags() & ~Data::CapacityReserved); - } else { + if (d->needsDetach() || size() < capacity()) + reallocData(d.size, QArrayData::KeepSize); + if (d->constAllocatedCapacity()) d->clearFlag(Data::CapacityReserved); - } } inline QString &QString::setUtf16(const ushort *autf16, qsizetype asize) diff --git a/src/corelib/tools/qarraydata.cpp b/src/corelib/tools/qarraydata.cpp index 4feb52a7103..3217e87cc8e 100644 --- a/src/corelib/tools/qarraydata.cpp +++ b/src/corelib/tools/qarraydata.cpp @@ -185,7 +185,7 @@ static QArrayData *allocateData(qsizetype allocSize) } void *QArrayData::allocate(QArrayData **dptr, qsizetype objectSize, qsizetype alignment, - qsizetype capacity, ArrayOptions options) noexcept + qsizetype capacity, QArrayData::AllocationOption option) noexcept { Q_ASSERT(dptr); // Alignment is a power of two @@ -208,7 +208,7 @@ void *QArrayData::allocate(QArrayData **dptr, qsizetype objectSize, qsizetype al } Q_ASSERT(headerSize > 0); - qsizetype allocSize = calculateBlockSize(capacity, objectSize, headerSize, (options & (GrowsForward|GrowsBackwards)) ? QArrayData::Grow : QArrayData::KeepSize); + qsizetype allocSize = calculateBlockSize(capacity, objectSize, headerSize, option); allocSize = reserveExtraBytes(allocSize); if (Q_UNLIKELY(allocSize < 0)) { // handle overflow. cannot allocate reliably *dptr = nullptr; @@ -220,7 +220,6 @@ void *QArrayData::allocate(QArrayData **dptr, qsizetype objectSize, qsizetype al if (header) { // find where offset should point to so that data() is aligned to alignment bytes data = QTypedArrayData<void>::dataStart(header, alignment); - header->flags = options & CapacityReserved; header->alloc = qsizetype(capacity); } diff --git a/src/corelib/tools/qarraydata.h b/src/corelib/tools/qarraydata.h index 76f2c330430..9ada91d04bf 100644 --- a/src/corelib/tools/qarraydata.h +++ b/src/corelib/tools/qarraydata.h @@ -56,12 +56,14 @@ struct Q_CORE_EXPORT QArrayData KeepSize }; - enum ArrayOption { - /// this option is used by the allocate() function - DefaultAllocationFlags = 0, - CapacityReserved = 0x1, //!< the capacity was reserved by the user, try to keep it - GrowsForward = 0x2, //!< allocate with eyes towards growing through append() - GrowsBackwards = 0x4 //!< allocate with eyes towards growing through prepend() + enum AllocationPosition { + AllocateAtEnd, + AllocateAtBeginning + }; + + enum ArrayOption { + ArrayOptionDefault = 0, + CapacityReserved = 0x1 //!< the capacity was reserved by the user, try to keep it }; Q_DECLARE_FLAGS(ArrayOptions, ArrayOption) @@ -112,20 +114,12 @@ struct Q_CORE_EXPORT QArrayData return newSize; } - ArrayOptions detachFlags() const noexcept - { - ArrayOptions result = DefaultAllocationFlags; - if (flags & CapacityReserved) - result |= CapacityReserved; - return result; - } - [[nodiscard]] #if defined(Q_CC_GNU) __attribute__((__malloc__)) #endif static void *allocate(QArrayData **pdata, qsizetype objectSize, qsizetype alignment, - qsizetype capacity, ArrayOptions options = DefaultAllocationFlags) noexcept; + qsizetype capacity, AllocationOption option = QArrayData::KeepSize) noexcept; [[nodiscard]] static QPair<QArrayData *, void *> reallocateUnaligned(QArrayData *data, void *dataPointer, qsizetype objectSize, qsizetype newCapacity, AllocationOption option) noexcept; static void deallocate(QArrayData *data, qsizetype objectSize, @@ -213,12 +207,11 @@ struct QTypedArrayData struct AlignmentDummy { QArrayData header; T data; }; - [[nodiscard]] static QPair<QTypedArrayData *, T *> allocate(qsizetype capacity, - ArrayOptions options = DefaultAllocationFlags) + [[nodiscard]] static QPair<QTypedArrayData *, T *> allocate(qsizetype capacity, AllocationOption option = QArrayData::KeepSize) { static_assert(sizeof(QTypedArrayData) == sizeof(QArrayData)); QArrayData *d; - void *result = QArrayData::allocate(&d, sizeof(T), alignof(AlignmentDummy), capacity, options); + void *result = QArrayData::allocate(&d, sizeof(T), alignof(AlignmentDummy), capacity, option); #if (defined(Q_CC_GNU) && Q_CC_GNU >= 407) || QT_HAS_BUILTIN(__builtin_assume_aligned) result = __builtin_assume_aligned(result, Q_ALIGNOF(AlignmentDummy)); #endif diff --git a/src/corelib/tools/qarraydataops.h b/src/corelib/tools/qarraydataops.h index a904341effe..7121da66602 100644 --- a/src/corelib/tools/qarraydataops.h +++ b/src/corelib/tools/qarraydataops.h @@ -1094,33 +1094,6 @@ public: } } - // Returns whether reallocation is desirable before adding more elements - // into the container. This is a helper function that one can use to - // theoretically improve average operations performance. Ignoring this - // function does not affect the correctness of the array operations. - bool shouldGrowBeforeInsert(const_iterator where, qsizetype n) const noexcept - { - if (this->d == nullptr) - return true; - if (this->d->flags & QArrayData::CapacityReserved) - return false; - if (!(this->d->flags & (QArrayData::GrowsForward | QArrayData::GrowsBackwards))) - return false; - Q_ASSERT(where >= this->begin() && where <= this->end()); // in range - - const qsizetype freeAtBegin = this->freeSpaceAtBegin(); - const qsizetype freeAtEnd = this->freeSpaceAtEnd(); - - // Idea: always reallocate when not enough space at the corresponding end - if (where == this->end()) { // append or size == 0 - return freeAtEnd < n; - } else if (where == this->begin()) { // prepend - return freeAtBegin < n; - } else { // general insert - return (freeAtBegin < n && freeAtEnd < n); - } - } - // using Base::truncate; // using Base::destroyAll; // using Base::assign; diff --git a/src/corelib/tools/qarraydatapointer.h b/src/corelib/tools/qarraydatapointer.h index 398dc1a607c..d483a5a5e5b 100644 --- a/src/corelib/tools/qarraydatapointer.h +++ b/src/corelib/tools/qarraydatapointer.h @@ -165,7 +165,7 @@ public: bool detach() { if (needsDetach()) { - QPair<Data *, T *> copy = clone(detachFlags()); + QPair<Data *, T *> copy = clone(); QArrayDataPointer old(d, ptr, size); d = copy.first; ptr = copy.second; @@ -185,10 +185,9 @@ public: bool isSharedWith(const QArrayDataPointer &other) const noexcept { return d && d == other.d; } bool needsDetach() const noexcept { return !d || d->needsDetach(); } qsizetype detachCapacity(qsizetype newSize) const noexcept { return d ? d->detachCapacity(newSize) : newSize; } - const typename Data::ArrayOptions flags() const noexcept { return d ? typename Data::ArrayOption(d->flags) : Data::DefaultAllocationFlags; } + const typename Data::ArrayOptions flags() const noexcept { return d ? typename Data::ArrayOption(d->flags) : Data::ArrayOptionDefault; } void setFlag(typename Data::ArrayOptions f) noexcept { Q_ASSERT(d); d->flags |= f; } void clearFlag(typename Data::ArrayOptions f) noexcept { Q_ASSERT(d); d->flags &= ~f; } - typename Data::ArrayOptions detachFlags() const noexcept { return d ? d->detachFlags() : Data::DefaultAllocationFlags; } Data *d_ptr() noexcept { return d; } void setBegin(T *begin) noexcept { ptr = begin; } @@ -207,40 +206,8 @@ public: return d->constAllocatedCapacity() - freeSpaceAtBegin() - this->size; } - static QArrayDataPointer allocateGrow(const QArrayDataPointer &from, - qsizetype newSize, QArrayData::ArrayOptions options) - { - return allocateGrow(from, from.detachCapacity(newSize), newSize, options); - } - - static QArrayDataPointer allocateGrow(const QArrayDataPointer &from, qsizetype capacity, - qsizetype newSize, QArrayData::ArrayOptions options) - { - auto [header, dataPtr] = Data::allocate(capacity, options); - const bool valid = header != nullptr && dataPtr != nullptr; - const bool grows = (options & (Data::GrowsForward | Data::GrowsBackwards)); - if (!valid || !grows) - return QArrayDataPointer(header, dataPtr); - - // must always hold true, as valid is the first condition we check and - // if-statement short-circuits - Q_ASSERT(valid); - - // Idea: * when growing backwards, adjust pointer to prepare free space at the beginning - // * when growing forward, adjust by the previous data pointer offset - - // TODO: what's with CapacityReserved? - dataPtr += (options & Data::GrowsBackwards) ? (header->alloc - newSize) / 2 - : from.freeSpaceAtBegin(); - return QArrayDataPointer(header, dataPtr); - } - - enum AllocationPosition { - AllocateAtEnd, - AllocateAtBeginning - }; // allocate and grow. Ensure that at the minimum requiredSpace is available at the requested end - static QArrayDataPointer allocateGrow(const QArrayDataPointer &from, qsizetype n, AllocationPosition position) + static QArrayDataPointer allocateGrow(const QArrayDataPointer &from, qsizetype n, QArrayData::AllocationPosition position) { // calculate new capacity. We keep the free capacity at the side that does not have to grow // to avoid quadratic behavior with mixed append/prepend cases @@ -249,10 +216,10 @@ public: qsizetype minimalCapacity = qMax(from.size, from.constAllocatedCapacity()) + n; // subtract the free space at the side we want to allocate. This ensures that the total size requested is // the existing allocation at the other side + size + n. - minimalCapacity -= (position == AllocateAtEnd) ? from.freeSpaceAtEnd() : from.freeSpaceAtBegin(); + minimalCapacity -= (position == QArrayData::AllocateAtEnd) ? from.freeSpaceAtEnd() : from.freeSpaceAtBegin(); qsizetype capacity = from.detachCapacity(minimalCapacity); const bool grows = capacity > from.constAllocatedCapacity(); - auto [header, dataPtr] = Data::allocate(capacity, grows ? QArrayData::GrowsBackwards : QArrayData::DefaultAllocationFlags); + auto [header, dataPtr] = Data::allocate(capacity, grows ? QArrayData::Grow : QArrayData::KeepSize); const bool valid = header != nullptr && dataPtr != nullptr; if (!valid) return QArrayDataPointer(header, dataPtr); @@ -261,8 +228,9 @@ public: // * when growing forward, adjust by the previous data pointer offset // TODO: what's with CapacityReserved? - dataPtr += (position == AllocateAtBeginning) ? qMax(0, (header->alloc - from.size - n) / 2) + dataPtr += (position == QArrayData::AllocateAtBeginning) ? qMax(0, (header->alloc - from.size - n) / 2) : from.freeSpaceAtBegin(); + header->flags = from.flags(); return QArrayDataPointer(header, dataPtr); } @@ -277,14 +245,15 @@ public: } private: - [[nodiscard]] QPair<Data *, T *> clone(QArrayData::ArrayOptions options) const + [[nodiscard]] QPair<Data *, T *> clone() const { - QPair<Data *, T *> pair = Data::allocate(detachCapacity(size), options); + QPair<Data *, T *> pair = Data::allocate(detachCapacity(size), QArrayData::KeepSize); QArrayDataPointer copy(pair.first, pair.second, 0); if (size) copy->copyAppend(begin(), end()); - pair.first = copy.d; + if (pair.first) + pair.first->flags = flags(); copy.d = nullptr; copy.ptr = nullptr; return pair; diff --git a/src/corelib/tools/qlist.h b/src/corelib/tools/qlist.h index e278b70b2d7..960bf18cacc 100644 --- a/src/corelib/tools/qlist.h +++ b/src/corelib/tools/qlist.h @@ -291,7 +291,7 @@ public: return; if (d->needsDetach()) { // must allocate memory - DataPointer detached(Data::allocate(d.allocatedCapacity(), d->detachFlags())); + DataPointer detached(Data::allocate(d.allocatedCapacity())); d.swap(detached); } else { d->truncate(0); @@ -582,8 +582,7 @@ inline void QList<T>::resize_internal(qsizetype newSize) if (d->needsDetach() || newSize > capacity() - d.freeSpaceAtBegin()) { // must allocate memory - DataPointer detached(Data::allocate(d->detachCapacity(newSize), - d->detachFlags())); + DataPointer detached(Data::allocate(d->detachCapacity(newSize))); if (size() && newSize) { detached->copyAppend(constBegin(), constBegin() + qMin(newSize, size())); } @@ -608,9 +607,10 @@ void QList<T>::reserve(qsizetype asize) } } - DataPointer detached(Data::allocate(qMax(asize, size()), - d->detachFlags() | Data::CapacityReserved)); + DataPointer detached(Data::allocate(qMax(asize, size()))); detached->copyAppend(constBegin(), constEnd()); + if (detached.d_ptr()) + detached->setFlag(Data::CapacityReserved); d.swap(detached); } @@ -621,15 +621,14 @@ inline void QList<T>::squeeze() return; if (d->needsDetach() || size() < capacity()) { // must allocate memory - DataPointer detached(Data::allocate(size(), d->detachFlags() & ~Data::CapacityReserved)); + DataPointer detached(Data::allocate(size())); if (size()) { detached->copyAppend(constBegin(), constEnd()); } d.swap(detached); - } else { - // We're detached so this is fine - d->clearFlag(Data::CapacityReserved); } + // We're detached so this is fine + d->clearFlag(Data::CapacityReserved); } template <typename T> @@ -646,7 +645,7 @@ inline void QList<T>::remove(qsizetype i, qsizetype n) ((d->flags() & Data::CapacityReserved) == 0 && newSize < d->allocatedCapacity()/2)) { // allocate memory - DataPointer detached(Data::allocate(d->detachCapacity(newSize), d->detachFlags())); + DataPointer detached(Data::allocate(d->detachCapacity(newSize))); const_iterator where = constBegin() + i; if (newSize) { detached->copyAppend(constBegin(), where); @@ -672,7 +671,7 @@ inline void QList<T>::append(const_iterator i1, const_iterator i2) return; const auto distance = std::distance(i1, i2); if (d->needsDetach() || distance > d.freeSpaceAtEnd()) { - DataPointer detached(DataPointer::allocateGrow(d, distance, DataPointer::AllocateAtEnd)); + DataPointer detached(DataPointer::allocateGrow(d, distance, QArrayData::AllocateAtEnd)); detached->copyAppend(constBegin(), constEnd()); detached->copyAppend(i1, i2); d.swap(detached); @@ -691,7 +690,7 @@ inline void QList<T>::append(QList<T> &&other) return append(other); if (d->needsDetach() || other.size() > d.freeSpaceAtEnd()) { - DataPointer detached(DataPointer::allocateGrow(d, other.size(), DataPointer::AllocateAtEnd)); + DataPointer detached(DataPointer::allocateGrow(d, other.size(), QArrayData::AllocateAtEnd)); if (!d->needsDetach()) detached->moveAppend(begin(), end()); @@ -711,7 +710,7 @@ template<typename... Args> inline typename QList<T>::reference QList<T>::emplaceFront(Args &&... args) { if (d->needsDetach() || !d.freeSpaceAtBegin()) { - DataPointer detached(DataPointer::allocateGrow(d, 1, DataPointer::AllocateAtBeginning)); + DataPointer detached(DataPointer::allocateGrow(d, 1, QArrayData::AllocateAtBeginning)); detached->emplace(detached.begin(), std::forward<Args>(args)...); if (!d.needsDetach()) @@ -737,9 +736,9 @@ QList<T>::insert(qsizetype i, qsizetype n, parameter_type t) // it's not worth wasting CPU cycles for that if (d->needsDetach() || (n > d.freeSpaceAtBegin() && n > d.freeSpaceAtEnd())) { - typename DataPointer::AllocationPosition pos = DataPointer::AllocateAtEnd; + typename QArrayData::AllocationPosition pos = QArrayData::AllocateAtEnd; if (d.size != 0 && i <= (d.size >> 1)) - pos = DataPointer::AllocateAtBeginning; + pos = QArrayData::AllocateAtBeginning; DataPointer detached(DataPointer::allocateGrow(d, n, pos)); const_iterator where = constBegin() + i; @@ -767,9 +766,9 @@ QList<T>::emplace(qsizetype i, Args&&... args) Q_ASSERT_X(i >= 0 && i <= d->size, "QList<T>::insert", "index out of range"); if (d->needsDetach() || (d.size == d.constAllocatedCapacity())) { - typename DataPointer::AllocationPosition pos = DataPointer::AllocateAtEnd; + typename QArrayData::AllocationPosition pos = QArrayData::AllocateAtEnd; if (d.size != 0 && i <= (d.size >> 1)) - pos = DataPointer::AllocateAtBeginning; + pos = QArrayData::AllocateAtBeginning; DataPointer detached(DataPointer::allocateGrow(d, 1, pos)); const_iterator where = constBegin() + i; @@ -810,8 +809,7 @@ inline QList<T> &QList<T>::fill(parameter_type t, qsizetype newSize) newSize = size(); if (d->needsDetach() || newSize > capacity()) { // must allocate memory - DataPointer detached(Data::allocate(d->detachCapacity(newSize), - d->detachFlags())); + DataPointer detached(Data::allocate(d->detachCapacity(newSize))); detached->copyAppend(newSize, t); d.swap(detached); } else { |
