summaryrefslogtreecommitdiffstats
path: root/tests
diff options
context:
space:
mode:
authorAndrei Golubev <andrei.golubev@qt.io>2021-03-24 16:47:33 +0100
committerAndrei Golubev <andrei.golubev@qt.io>2021-04-26 17:07:07 +0200
commita0253f5f0249024580050e4ec22d50cb139ef8d9 (patch)
tree43a61a5f66f94ed3af4c8fbd06814c05c71c39ce /tests
parent10b46e7f0faecc42a94cc2e25ad3edd08ae28083 (diff)
Resurrect data moves in QList
Use the data moves to readjust the free space in the QList, which ultimately fixes the out-of-memory issues caused by cases like: forever { list.prepend(list.back()); list.removeLast(); } Task-number: QTBUG-91801 Task-number: QTBUG-91360 Task-number: QTBUG-93019 Pick-to: dev 6.0 6.1 Change-Id: Iacff69cbf36b8b5b176bb2663df635ec972c875c Reviewed-by: Lars Knoll <lars.knoll@qt.io>
Diffstat (limited to 'tests')
-rw-r--r--tests/auto/corelib/tools/qarraydata/simplevector.h17
-rw-r--r--tests/auto/corelib/tools/qlist/tst_qlist.cpp59
2 files changed, 59 insertions, 17 deletions
diff --git a/tests/auto/corelib/tools/qarraydata/simplevector.h b/tests/auto/corelib/tools/qarraydata/simplevector.h
index 747af3d422..1fc5e9b8e1 100644
--- a/tests/auto/corelib/tools/qarraydata/simplevector.h
+++ b/tests/auto/corelib/tools/qarraydata/simplevector.h
@@ -209,22 +209,7 @@ public:
d->insert(0, first, last - first);
}
- void append(const_iterator first, const_iterator last)
- {
- if (first == last)
- return;
-
- auto requiredSize = qsizetype(last - first);
- if (d->needsDetach() || d.freeSpaceAtEnd() < requiredSize) {
- DataPointer oldData;
- d.reallocateAndGrow(QArrayData::GrowsAtEnd, requiredSize, &oldData);
-
- d->copyAppend(first, last);
- return;
- }
-
- d->copyAppend(first, last);
- }
+ void append(const_iterator first, const_iterator last) { d->growAppend(first, last); }
void insert(int position, const_iterator first, const_iterator last)
{
diff --git a/tests/auto/corelib/tools/qlist/tst_qlist.cpp b/tests/auto/corelib/tools/qlist/tst_qlist.cpp
index 80adb0f6a1..14c679562f 100644
--- a/tests/auto/corelib/tools/qlist/tst_qlist.cpp
+++ b/tests/auto/corelib/tools/qlist/tst_qlist.cpp
@@ -348,8 +348,13 @@ private slots:
void emplaceWithElementFromTheSameContainer_data();
void fromReadOnlyData() const;
-
void qtbug_90359() const;
+ void reinsertToBeginInt_qtbug91360() const { reinsertToBegin<int>(); }
+ void reinsertToBeginMovable_qtbug91360() const { reinsertToBegin<Movable>(); }
+ void reinsertToBeginCustom_qtbug91360() const { reinsertToBegin<Custom>(); }
+ void reinsertToEndInt_qtbug91360() const { reinsertToEnd<int>(); }
+ void reinsertToEndMovable_qtbug91360() const { reinsertToEnd<Movable>(); }
+ void reinsertToEndCustom_qtbug91360() const { reinsertToEnd<Custom>(); }
private:
template<typename T> void copyConstructor() const;
@@ -379,6 +384,10 @@ private:
template<typename T> void detachThreadSafety() const;
template<typename T> void emplaceImpl() const;
template<typename T> void emplaceConsistentWithStdVectorImpl() const;
+ template<typename T>
+ void reinsertToBegin() const;
+ template<typename T>
+ void reinsertToEnd() const;
};
@@ -3265,5 +3274,53 @@ void tst_QList::qtbug_90359() const
QCOMPARE(actual, expected);
}
+template<typename T>
+void tst_QList::reinsertToBegin() const
+{
+ QList<T> list(1);
+ const auto reinsert = [](QList<T> &list) {
+ list.prepend(list.back());
+ list.removeLast();
+ };
+
+ // this constant is big enough for the QList to stop reallocating, after
+ // all, size is always less than 3
+ const int maxIters = 128;
+ for (int i = 0; i < maxIters; ++i) {
+ reinsert(list);
+ }
+
+ // if QList continues to grow, it's an error
+ qsizetype capacity = list.capacity();
+ for (int i = 0, enoughIters = int(capacity) * 2; i < enoughIters; ++i) {
+ reinsert(list);
+ QCOMPARE(capacity, list.capacity());
+ }
+}
+
+template<typename T>
+void tst_QList::reinsertToEnd() const
+{
+ QList<T> list(1);
+ const auto reinsert = [](QList<T> &list) {
+ list.append(list.front());
+ list.removeFirst();
+ };
+
+ // this constant is big enough for the QList to stop reallocating, after
+ // all, size is always less than 3
+ const int maxIters = 128;
+ for (int i = 0; i < maxIters; ++i) {
+ reinsert(list);
+ }
+
+ // if QList continues to grow, it's an error
+ qsizetype capacity = list.capacity();
+ for (int i = 0, enoughIters = int(capacity) * 2; i < enoughIters; ++i) {
+ reinsert(list);
+ QCOMPARE(capacity, list.capacity());
+ }
+}
+
QTEST_MAIN(tst_QList)
#include "tst_qlist.moc"