From 7216a936bc5f806953bb5fa59a460935b952fb33 Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Thu, 19 Jan 2023 18:26:17 +0100 Subject: QVarLengthArray: fix off-by-size() bug in growBy() The growBy() function takes the _increment_ of the size(), so needs to add size() to increment for the call to realloc(). Add a test which hangs (vanilla build) or explodes (valgrind build) without the fix. Amends 26b227e128475da3f88a6b34921a08994bf71cf4. Done-with: Eirik Aavitsland Fixes: QTBUG-110412 Change-Id: I7ea91342fdcb779825c88013a3f86ba6d90ef530 Reviewed-by: Qt CI Bot Reviewed-by: Fabian Kosmale (cherry picked from commit 51e5a2376a8a2956665ff4c3a0e86c8cd9d0847d) Reviewed-by: Qt Cherry-pick Bot --- src/corelib/tools/qvarlengtharray.h | 2 +- .../corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp | 13 +++++++++++++ 2 files changed, 14 insertions(+), 1 deletion(-) diff --git a/src/corelib/tools/qvarlengtharray.h b/src/corelib/tools/qvarlengtharray.h index 9377cc50b4..bd38e2dcc1 100644 --- a/src/corelib/tools/qvarlengtharray.h +++ b/src/corelib/tools/qvarlengtharray.h @@ -181,7 +181,7 @@ public: } protected: void growBy(qsizetype prealloc, void *array, qsizetype increment) - { reallocate_impl(prealloc, array, size(), (std::max)(size() * 2, increment)); } + { reallocate_impl(prealloc, array, size(), (std::max)(size() * 2, size() + increment)); } template reference emplace_back_impl(qsizetype prealloc, void *array, Args&&...args) { diff --git a/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp b/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp index 105a3b27bf..b790cf80fd 100644 --- a/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp +++ b/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp @@ -7,6 +7,8 @@ #include #include +#include +#include #include struct Tracker @@ -386,6 +388,17 @@ void tst_QVarLengthArray::appendCausingRealloc() QVarLengthArray d(1); for (int i=0; i<30; i++) d.append(i); + + // Regression test for QTBUG-110412: + constexpr qsizetype InitialCapacity = 10; + QVarLengthArray d2(InitialCapacity); + std::iota(d2.begin(), d2.end(), 0.0f); + QCOMPARE_EQ(d2.size(), d2.capacity()); // by construction + float floats[1000]; + std::iota(std::begin(floats), std::end(floats), InitialCapacity + 0.0f); + d2.append(floats, q20::ssize(floats)); + QCOMPARE_EQ(d2.size(), q20::ssize(floats) + InitialCapacity); + QCOMPARE_GE(d2.capacity(), d2.size()); } void tst_QVarLengthArray::appendIsStronglyExceptionSafe() -- cgit v1.2.3