summaryrefslogtreecommitdiffstats
path: root/tests/auto/corelib/text/qbytearraymatcher/tst_qbytearraymatcher.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'tests/auto/corelib/text/qbytearraymatcher/tst_qbytearraymatcher.cpp')
-rw-r--r--tests/auto/corelib/text/qbytearraymatcher/tst_qbytearraymatcher.cpp134
1 files changed, 104 insertions, 30 deletions
diff --git a/tests/auto/corelib/text/qbytearraymatcher/tst_qbytearraymatcher.cpp b/tests/auto/corelib/text/qbytearraymatcher/tst_qbytearraymatcher.cpp
index 42b978acc8..cb2ede7db6 100644
--- a/tests/auto/corelib/text/qbytearraymatcher/tst_qbytearraymatcher.cpp
+++ b/tests/auto/corelib/text/qbytearraymatcher/tst_qbytearraymatcher.cpp
@@ -1,36 +1,16 @@
-/****************************************************************************
-**
-** Copyright (C) 2016 The Qt Company Ltd.
-** Contact: https://www.qt.io/licensing/
-**
-** This file is part of the test suite of the Qt Toolkit.
-**
-** $QT_BEGIN_LICENSE:GPL-EXCEPT$
-** Commercial License Usage
-** Licensees holding valid commercial Qt licenses may use this file in
-** accordance with the commercial license agreement provided with the
-** Software or, alternatively, in accordance with the terms contained in
-** a written agreement between you and The Qt Company. For licensing terms
-** and conditions see https://www.qt.io/terms-conditions. For further
-** information use the contact form at https://www.qt.io/contact-us.
-**
-** GNU General Public License Usage
-** Alternatively, this file may be used under the terms of the GNU
-** General Public License version 3 as published by the Free Software
-** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
-** included in the packaging of this file. Please review the following
-** information to ensure the GNU General Public License requirements will
-** be met: https://www.gnu.org/licenses/gpl-3.0.html.
-**
-** $QT_END_LICENSE$
-**
-****************************************************************************/
+// Copyright (C) 2016 The Qt Company Ltd.
+// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only
#include <QTest>
#include <qbytearraymatcher.h>
+#include <numeric>
+#include <string>
+
+#include <thread>
+
// COM interface
#if defined(Q_OS_WIN) && defined(interface)
# undef interface
@@ -41,11 +21,46 @@ class tst_QByteArrayMatcher : public QObject
Q_OBJECT
private slots:
+ void overloads();
void interface();
void indexIn();
void staticByteArrayMatcher();
+ void haystacksWithMoreThan4GiBWork();
};
+void tst_QByteArrayMatcher::overloads()
+{
+ QByteArray hello = QByteArrayLiteral("hello");
+ QByteArray hello2 = hello.repeated(2);
+ {
+ QByteArrayMatcher m("hello");
+ QCOMPARE(m.pattern(), "hello");
+ QCOMPARE(m.indexIn("hello"), 0);
+ }
+ {
+ QByteArrayMatcher m("hello", qsizetype(3));
+ QCOMPARE(m.pattern(), "hel");
+ QCOMPARE(m.indexIn("hellohello", qsizetype(2)), -1); // haystack is "he", not: from is 2
+ QCOMPARE(m.indexIn("hellohello", qsizetype(3)), 0); // haystack is "hel", not: from is 3
+ }
+ {
+ QByteArrayMatcher m(hello);
+ QCOMPARE(m.pattern(), "hello");
+ QCOMPARE(m.indexIn(hello), 0);
+ QCOMPARE(m.indexIn(hello2, qsizetype(1)), hello.size());
+ }
+ {
+ QStaticByteArrayMatcher m("hel");
+ QCOMPARE(m.pattern(), "hel");
+ QCOMPARE(m.indexIn("hello"), qsizetype(0));
+ QCOMPARE(m.indexIn("hellohello", qsizetype(2)), -1); // haystack is "he", not: from is 2
+ QCOMPARE(m.indexIn("hellohello", qsizetype(3)), 0); // haystack is "hel", not: from is 3
+ QCOMPARE(m.indexIn(hello), 0);
+ QCOMPARE(m.indexIn(hello2, qsizetype(2)), hello.size()); // from is 2
+ QCOMPARE(m.indexIn(hello2, qsizetype(3)), hello.size()); // from is 3
+ }
+}
+
void tst_QByteArrayMatcher::interface()
{
const char needle[] = "abc123";
@@ -74,12 +89,12 @@ void tst_QByteArrayMatcher::interface()
QCOMPARE(matcher5.indexIn(haystack), 42);
QCOMPARE(matcher6.indexIn(haystack), 42);
- QCOMPARE(matcher1.indexIn(haystack.constData(), haystack.length()), 42);
+ QCOMPARE(matcher1.indexIn(haystack.constData(), haystack.size()), 42);
QCOMPARE(matcher1.indexIn(haystack, 43), 84);
- QCOMPARE(matcher1.indexIn(haystack.constData(), haystack.length(), 43), 84);
+ QCOMPARE(matcher1.indexIn(haystack.constData(), haystack.size(), 43), 84);
QCOMPARE(matcher1.indexIn(haystack, 85), -1);
- QCOMPARE(matcher1.indexIn(haystack.constData(), haystack.length(), 85), -1);
+ QCOMPARE(matcher1.indexIn(haystack.constData(), haystack.size(), 85), -1);
QByteArrayMatcher matcher7(QByteArray("123"));
QCOMPARE(matcher7.indexIn(haystack), 6);
@@ -208,6 +223,65 @@ void tst_QByteArrayMatcher::staticByteArrayMatcher()
}
+void tst_QByteArrayMatcher::haystacksWithMoreThan4GiBWork()
+{
+#if QT_POINTER_SIZE > 4
+ // use a large needle to trigger long skips in the Boyer-Moore algorithm
+ // (to speed up the test)
+ constexpr std::string_view needle = LONG_STRING_256;
+
+ //
+ // GIVEN: a haystack with more than 4 GiB of data
+ //
+
+ // don't use QByteArray because freeSpaceAtEnd() may break reserve()
+ // semantics and a realloc is the last thing we need here
+ std::string large;
+ QElapsedTimer timer;
+ timer.start();
+ constexpr size_t GiB = 1024 * 1024 * 1024;
+ constexpr size_t BaseSize = 4 * GiB + 1;
+ try {
+ large.reserve(BaseSize + needle.size());
+ large.resize(BaseSize, '\0');
+ large.append(needle);
+ } catch (const std::bad_alloc &) {
+ QSKIP("Could not allocate 4GiB plus a couple hundred bytes of RAM.");
+ }
+ QCOMPARE(large.size(), BaseSize + needle.size());
+ qDebug("created dataset in %lld ms", timer.elapsed());
+
+ using MaybeThread = std::thread;
+
+ //
+ // WHEN: trying to match an occurrence past the 4GiB mark
+ //
+
+ qsizetype dynamicResult, staticResult;
+
+ auto t = MaybeThread{[&]{
+ QByteArrayMatcher m(needle);
+ dynamicResult = m.indexIn(large);
+ }};
+ {
+ static_assert(needle == LONG_STRING_256); // need a string literal in the following line:
+ QStaticByteArrayMatcher m(LONG_STRING_256);
+ staticResult = m.indexIn(large.data(), large.size());
+ }
+ t.join();
+
+ //
+ // THEN: the result index is not trucated
+ //
+
+ QCOMPARE(staticResult, qsizetype(BaseSize));
+ QCOMPARE(dynamicResult, qsizetype(BaseSize));
+#else
+ QSKIP("This test is 64-bit only.");
+#endif
+
+}
+
#undef LONG_STRING_256
#undef LONG_STRING_128
#undef LONG_STRING__64