summaryrefslogtreecommitdiffstats
path: root/tests
diff options
context:
space:
mode:
Diffstat (limited to 'tests')
-rw-r--r--tests/auto/cmake/mockplugins/.cmake.conf2
-rw-r--r--tests/auto/cmake/test_generating_cpp_exports/.cmake.conf2
-rw-r--r--tests/auto/cmake/test_static_resources/.cmake.conf2
-rw-r--r--tests/auto/corelib/thread/qreadwritelock/tst_qreadwritelock.cpp106
-rw-r--r--tests/auto/network/access/qhttp2connection/tst_qhttp2connection.cpp55
-rw-r--r--tests/auto/tools/rcc/data/legal/rcc_legal.cpp2
6 files changed, 165 insertions, 4 deletions
diff --git a/tests/auto/cmake/mockplugins/.cmake.conf b/tests/auto/cmake/mockplugins/.cmake.conf
index be788d10f8e..846c4f3b923 100644
--- a/tests/auto/cmake/mockplugins/.cmake.conf
+++ b/tests/auto/cmake/mockplugins/.cmake.conf
@@ -1 +1 @@
-set(QT_REPO_MODULE_VERSION "6.11.0")
+set(QT_REPO_MODULE_VERSION "6.12.0")
diff --git a/tests/auto/cmake/test_generating_cpp_exports/.cmake.conf b/tests/auto/cmake/test_generating_cpp_exports/.cmake.conf
index be788d10f8e..846c4f3b923 100644
--- a/tests/auto/cmake/test_generating_cpp_exports/.cmake.conf
+++ b/tests/auto/cmake/test_generating_cpp_exports/.cmake.conf
@@ -1 +1 @@
-set(QT_REPO_MODULE_VERSION "6.11.0")
+set(QT_REPO_MODULE_VERSION "6.12.0")
diff --git a/tests/auto/cmake/test_static_resources/.cmake.conf b/tests/auto/cmake/test_static_resources/.cmake.conf
index be788d10f8e..846c4f3b923 100644
--- a/tests/auto/cmake/test_static_resources/.cmake.conf
+++ b/tests/auto/cmake/test_static_resources/.cmake.conf
@@ -1 +1 @@
-set(QT_REPO_MODULE_VERSION "6.11.0")
+set(QT_REPO_MODULE_VERSION "6.12.0")
diff --git a/tests/auto/corelib/thread/qreadwritelock/tst_qreadwritelock.cpp b/tests/auto/corelib/thread/qreadwritelock/tst_qreadwritelock.cpp
index 86dfa5faffc..4c089091f8d 100644
--- a/tests/auto/corelib/thread/qreadwritelock/tst_qreadwritelock.cpp
+++ b/tests/auto/corelib/thread/qreadwritelock/tst_qreadwritelock.cpp
@@ -57,6 +57,7 @@ private slots:
void multipleReadersLoop();
void multipleWritersLoop();
void multipleReadersWritersLoop();
+ void heavyLoadLocks();
void countingTest();
void limitedReaders();
void deleteOnUnlock();
@@ -603,6 +604,111 @@ public:
}
};
+class HeavyLoadLockThread : public QThread
+{
+public:
+ QReadWriteLock &testRwlock;
+ const qsizetype iterations;
+ const int numThreads;
+ inline HeavyLoadLockThread(QReadWriteLock &l, qsizetype iters, int numThreads, QVector<QAtomicInt *> &counters):
+ testRwlock(l),
+ iterations(iters),
+ numThreads(numThreads),
+ counters(counters)
+ { }
+
+private:
+ QVector<QAtomicInt *> &counters;
+ QAtomicInt *getCounter(qsizetype index)
+ {
+ QReadLocker locker(&testRwlock);
+ /*
+ The index is increased monotonically, so the index
+ being requested should be always within or at the end of the
+ counters vector.
+ */
+ Q_ASSERT(index <= counters.size());
+ if (counters.size() <= index || counters[index] == nullptr) {
+ locker.unlock();
+ QWriteLocker wlocker(&testRwlock);
+ if (counters.size() <= index)
+ counters.resize(index + 1, nullptr);
+ if (counters[index] == nullptr)
+ counters[index] = new QAtomicInt(0);
+ return counters[index];
+ }
+ return counters[index];
+ }
+ void releaseCounter(qsizetype index)
+ {
+ QWriteLocker locker(&testRwlock);
+ delete counters[index];
+ counters[index] = nullptr;
+ }
+
+public:
+ void run() override
+ {
+ for (qsizetype i = 0; i < iterations; ++i) {
+ QAtomicInt *counter = getCounter(i);
+ /*
+ Here each counter is accessed by each thread
+ and increaed only once. As a result, when the
+ counter reaches numThreads, i.e. the fetched
+ value before the increment is numThreads-1,
+ we know all threads have accessed this counter
+ and we can delete it safely.
+ */
+ int prev = counter->fetchAndAddRelaxed(1);
+ if (prev == numThreads - 1) {
+#ifdef QT_BUILDING_UNDER_TSAN
+ /*
+ Under TSAN, deleting and freeing an object
+ will trigger a write operation on the memory
+ of the object. Since we used fetchAndAddRelaxed
+ to update the counter, TSAN will report a data
+ race when deleting the counter here. To avoid
+ the false positive, we simply reset the counter
+ to 0 here, with ordered semantics to establish
+ the sequence to ensure the the free-ing option
+ happens after all fetchAndAddRelaxed operations
+ in other threads.
+
+ When not building under TSAN, deleting the counter
+ will not result in any data read or written to the
+ memory region of the counter, so no data race will
+ happen.
+ */
+ counter->fetchAndStoreOrdered(0);
+#endif
+ releaseCounter(i);
+ }
+ }
+ }
+};
+
+/*
+ Multiple threads racing acquiring and releasing
+ locks on the same indices.
+*/
+
+void tst_QReadWriteLock::heavyLoadLocks()
+{
+ constexpr qsizetype iterations = 65536 * 4;
+ constexpr int numThreads = 8;
+ QVector<QAtomicInt *> counters;
+ QReadWriteLock testLock;
+ std::array<std::unique_ptr<HeavyLoadLockThread>, numThreads> threads;
+ for (auto &thread : threads)
+ thread = std::make_unique<HeavyLoadLockThread>(testLock, iterations, numThreads, counters);
+ for (auto &thread : threads)
+ thread->start();
+ for (auto &thread : threads)
+ thread->wait();
+ QVERIFY(counters.size() == iterations);
+ for (qsizetype i = 0; i < iterations; ++i)
+ QVERIFY(counters[i] == nullptr);
+}
/*
A writer acquires a read-lock, a reader locks
diff --git a/tests/auto/network/access/qhttp2connection/tst_qhttp2connection.cpp b/tests/auto/network/access/qhttp2connection/tst_qhttp2connection.cpp
index 417655c31d9..22aa9d44262 100644
--- a/tests/auto/network/access/qhttp2connection/tst_qhttp2connection.cpp
+++ b/tests/auto/network/access/qhttp2connection/tst_qhttp2connection.cpp
@@ -21,6 +21,8 @@ class tst_QHttp2Connection : public QObject
private slots:
void construct();
void constructStream();
+ void streamConfiguration_data();
+ void streamConfiguration();
void testSETTINGSFrame();
void maxHeaderTableSize();
void testPING();
@@ -204,6 +206,59 @@ void tst_QHttp2Connection::constructStream()
QCOMPARE(stream->isUploadingDATA(), false);
}
+void tst_QHttp2Connection::streamConfiguration_data()
+{
+ QTest::addColumn<bool>("useDownloadBuffer");
+
+ QTest::addRow("useDownloadBuffer=true") << true;
+ QTest::addRow("useDownloadBuffer=false") << false;
+}
+
+void tst_QHttp2Connection::streamConfiguration()
+{
+ QFETCH(const bool, useDownloadBuffer);
+
+ auto [client, server] = makeFakeConnectedSockets();
+ auto *clientConnection = makeHttp2Connection(client.get(), {}, Client);
+ auto *serverConnection = makeHttp2Connection(server.get(), {}, Server);
+
+ QHttp2Stream::Configuration config;
+ config.useDownloadBuffer = useDownloadBuffer;
+
+ QHttp2Stream *clientStream = clientConnection->createStream(config).unwrap();
+ QVERIFY(clientStream);
+ QCOMPARE(clientStream->configuration().useDownloadBuffer, useDownloadBuffer);
+ QVERIFY(waitForSettingsExchange(clientConnection, serverConnection));
+
+ QSignalSpy newIncomingStreamSpy{ serverConnection, &QHttp2Connection::newIncomingStream };
+ QSignalSpy clientDataReceivedSpy{ clientStream, &QHttp2Stream::dataReceived };
+
+ HPack::HttpHeader headers = getRequiredHeaders();
+ clientStream->sendHEADERS(headers, false);
+
+ QVERIFY(newIncomingStreamSpy.wait());
+ auto *serverStream = newIncomingStreamSpy.front().front().value<QHttp2Stream *>();
+ QVERIFY(serverStream);
+
+ const HPack::HttpHeader responseHeaders{ { ":status", "200" } };
+ serverStream->sendHEADERS(responseHeaders, false);
+
+ const QByteArray testData = "Hello World"_ba.repeated(100);
+ serverStream->sendDATA(testData, true);
+
+ QVERIFY(clientDataReceivedSpy.wait());
+ QCOMPARE(clientDataReceivedSpy.count(), 1);
+
+ const QByteArray receivedData = clientDataReceivedSpy.front().front().value<QByteArray>();
+ QCOMPARE(receivedData, testData);
+
+ if (useDownloadBuffer) {
+ QCOMPARE(clientStream->downloadBuffer().byteAmount(), testData.size());
+ } else {
+ QVERIFY(clientStream->downloadBuffer().isEmpty());
+ }
+}
+
void tst_QHttp2Connection::testSETTINGSFrame()
{
constexpr qint32 PrefaceLength = 24;
diff --git a/tests/auto/tools/rcc/data/legal/rcc_legal.cpp b/tests/auto/tools/rcc/data/legal/rcc_legal.cpp
index 248ab2e3b48..96f87d192e7 100644
--- a/tests/auto/tools/rcc/data/legal/rcc_legal.cpp
+++ b/tests/auto/tools/rcc/data/legal/rcc_legal.cpp
@@ -3,7 +3,7 @@
** Copyright (C) 2024 Intel Corporation.
** SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only
**
-** Created by: The Resource Compiler for Qt version 6.11.0
+** Created by: The Resource Compiler for Qt version 6.12.0
**
** WARNING! All changes made in this file will be lost!
*****************************************************************************/