diff options
author | Marc Mutz <marc.mutz@qt.io> | 2023-01-09 10:14:31 +0100 |
---|---|---|
committer | Marc Mutz <marc.mutz@qt.io> | 2023-01-16 22:44:13 +0100 |
commit | 800ebd84f57092ccba24984f3888f97bb5433d8e (patch) | |
tree | 0b5ae93dfcf7535938e89d6a5bbf14ecd0d5ff36 /tests | |
parent | 03ed57afa0c5af5076583dd4e415e54983e7e0a8 (diff) |
QVarLengthArray: cope with vector<unique_ptr>'s copyability
Despite being move-only, std::vector<unique_ptr> advertizes
is_copyable:
https://quuxplusone.github.io/blog/2020/02/05/vector-is-copyable-except-when-its-not/
Our combined reallocation and resizing function, reallocate_impl(),
runs afoul of this when it uses std::is_copyable in a constexpr-if to
implement resize(n, v) without running into problems with move-only
types: the trait is true, but actual instantation runs into a
static_assert in the STL implementation.
To fix, move the problematic resize functionality out of
reallocate_impl() and into the resp. resize_impl overloads. The shrink
functionality remains in reallocate_impl(), because there are many
more users, and it only requires destructible<T>, which isn't
constraining at all.
Amends a00a1d8806cfbf17e04b88d1b4ff4a9cf5b6294a.
Fixes: QTBUG-109745
Pick-to: 6.5 6.4
Change-Id: Ibc5b9cf5375108eb3d8f6c8a16d4fd02dadd73b1
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: MÃ¥rten Nordheim <marten.nordheim@qt.io>
Diffstat (limited to 'tests')
-rw-r--r-- | tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp | 23 |
1 files changed, 23 insertions, 0 deletions
diff --git a/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp b/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp index 81edb36916..105a3b27bf 100644 --- a/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp +++ b/tests/auto/corelib/tools/qvarlengtharray/tst_qvarlengtharray.cpp @@ -92,6 +92,8 @@ private slots: void remove(); void erase(); + // special cases: + void copesWithCopyabilityOfMoveOnlyVector(); // QTBUG-109745 private: template <typename T> void defaultConstructor(); @@ -1640,5 +1642,26 @@ void tst_QVarLengthArray::erase() QCOMPARE(arr, QVarLengthArray<QString>({ "val0" })); } +void tst_QVarLengthArray::copesWithCopyabilityOfMoveOnlyVector() +{ + // std::vector<move-only-type> is_copyable + // (https://quuxplusone.github.io/blog/2020/02/05/vector-is-copyable-except-when-its-not/) + + QVarLengthArray<std::vector<std::unique_ptr<int>>, 2> vla; + vla.emplace_back(42); + vla.emplace_back(43); + vla.emplace_back(44); // goes to the heap + QCOMPARE_EQ(vla.size(), 3); + QCOMPARE_EQ(vla.front().size(), 42U); + QCOMPARE_EQ(vla.front().front(), nullptr); + QCOMPARE_EQ(vla.back().size(), 44U); + + auto moved = std::move(vla); + QCOMPARE_EQ(moved.size(), 3); + QCOMPARE_EQ(moved.front().size(), 42U); + QCOMPARE_EQ(moved.front().front(), nullptr); + QCOMPARE_EQ(moved.back().size(), 44U); +} + QTEST_APPLESS_MAIN(tst_QVarLengthArray) #include "tst_qvarlengtharray.moc" |