summaryrefslogtreecommitdiffstats
path: root/tests/auto/corelib/thread
diff options
context:
space:
mode:
Diffstat (limited to 'tests/auto/corelib/thread')
-rw-r--r--tests/auto/corelib/thread/CMakeLists.txt24
-rw-r--r--tests/auto/corelib/thread/qfuture/CMakeLists.txt1
-rw-r--r--tests/auto/corelib/thread/qfuture/tst_qfuture.cpp28
-rw-r--r--tests/auto/corelib/thread/qresultstore/CMakeLists.txt1
-rw-r--r--tests/auto/corelib/thread/qresultstore/tst_qresultstore.cpp33
-rw-r--r--tests/auto/corelib/thread/qthread/tst_qthread.cpp74
6 files changed, 113 insertions, 48 deletions
diff --git a/tests/auto/corelib/thread/CMakeLists.txt b/tests/auto/corelib/thread/CMakeLists.txt
index 68110b652b..d25d0205f5 100644
--- a/tests/auto/corelib/thread/CMakeLists.txt
+++ b/tests/auto/corelib/thread/CMakeLists.txt
@@ -17,11 +17,20 @@ if(QT_FEATURE_thread)
add_subdirectory(qatomicint)
add_subdirectory(qatomicinteger)
add_subdirectory(qatomicpointer)
- add_subdirectory(qresultstore)
- if(QT_FEATURE_concurrent AND NOT INTEGRITY)
- add_subdirectory(qfuture)
+ if(QT_FEATURE_future)
+ if(QT_FEATURE_concurrent AND NOT INTEGRITY)
+ add_subdirectory(qfuture)
+ endif()
+ add_subdirectory(qresultstore)
+ add_subdirectory(qfuturesynchronizer)
+ if(NOT INTEGRITY)
+ add_subdirectory(qpromise)
+ endif()
+ # QTBUG-87431
+ if(TARGET Qt::Concurrent AND NOT INTEGRITY)
+ add_subdirectory(qfuturewatcher)
+ endif()
endif()
- add_subdirectory(qfuturesynchronizer)
add_subdirectory(qmutex)
add_subdirectory(qmutexlocker)
add_subdirectory(qreadlocker)
@@ -36,12 +45,5 @@ if(QT_FEATURE_thread)
add_subdirectory(qthreadstorage)
add_subdirectory(qwaitcondition)
add_subdirectory(qwritelocker)
- if(NOT INTEGRITY)
- add_subdirectory(qpromise)
- endif()
endif()
-# QTBUG-87431
-if(TARGET Qt::Concurrent AND NOT INTEGRITY)
- add_subdirectory(qfuturewatcher)
-endif()
diff --git a/tests/auto/corelib/thread/qfuture/CMakeLists.txt b/tests/auto/corelib/thread/qfuture/CMakeLists.txt
index aa989f3df1..ba5730d5cf 100644
--- a/tests/auto/corelib/thread/qfuture/CMakeLists.txt
+++ b/tests/auto/corelib/thread/qfuture/CMakeLists.txt
@@ -16,6 +16,7 @@ qt_internal_add_test(tst_qfuture
tst_qfuture.cpp
LIBRARIES
Qt::CorePrivate
+ Qt::TestPrivate
)
qt_internal_extend_target(tst_qfuture CONDITION MSVC
diff --git a/tests/auto/corelib/thread/qfuture/tst_qfuture.cpp b/tests/auto/corelib/thread/qfuture/tst_qfuture.cpp
index 3fc796514d..4cb29c514a 100644
--- a/tests/auto/corelib/thread/qfuture/tst_qfuture.cpp
+++ b/tests/auto/corelib/thread/qfuture/tst_qfuture.cpp
@@ -17,6 +17,7 @@
#include <private/qobject_p.h>
#include <QTest>
+#include <QtTest/private/qcomparisontesthelper_p.h>
#include <qfuture.h>
#include <qfuturewatcher.h>
#include <qresultstore.h>
@@ -161,6 +162,7 @@ class tst_QFuture: public QObject
{
Q_OBJECT
private slots:
+ void compareCompiles();
void resultStore();
void future();
void futureToVoid();
@@ -273,6 +275,12 @@ private:
QtPrivate::ResultStoreBase &store;
};
+void tst_QFuture::compareCompiles()
+{
+ QTestPrivate::testEqualityOperatorsCompile<QFuture<int>::const_iterator>();
+ QTestPrivate::testEqualityOperatorsCompile<QFuture<QString>::const_iterator>();
+}
+
void tst_QFuture::resultStore()
{
int int0 = 0;
@@ -1359,16 +1367,16 @@ void tst_QFuture::iterators()
QFuture<int>::const_iterator i1 = f.begin(), i2 = i1 + 1;
QFuture<int>::const_iterator c1 = i1, c2 = c1 + 1;
- QCOMPARE(i1, i1);
- QCOMPARE(i1, c1);
- QCOMPARE(c1, i1);
- QCOMPARE(c1, c1);
- QCOMPARE(i2, i2);
- QCOMPARE(i2, c2);
- QCOMPARE(c2, i2);
- QCOMPARE(c2, c2);
- QCOMPARE(1 + i1, i1 + 1);
- QCOMPARE(1 + c1, c1 + 1);
+ QT_TEST_EQUALITY_OPS(i1, i1, true);
+ QT_TEST_EQUALITY_OPS(i1, c1, true);
+ QT_TEST_EQUALITY_OPS(c1, i1, true);
+ QT_TEST_EQUALITY_OPS(c1, c1, true);
+ QT_TEST_EQUALITY_OPS(i2, i2, true);
+ QT_TEST_EQUALITY_OPS(i2, c2, true);
+ QT_TEST_EQUALITY_OPS(c2, i2, true);
+ QT_TEST_EQUALITY_OPS(c2, c2, true);
+ QT_TEST_EQUALITY_OPS(1 + i1, i1 + 1, true);
+ QT_TEST_EQUALITY_OPS(1 + c1, c1 + 1, true);
QVERIFY(i1 != i2);
QVERIFY(i1 != c2);
diff --git a/tests/auto/corelib/thread/qresultstore/CMakeLists.txt b/tests/auto/corelib/thread/qresultstore/CMakeLists.txt
index 0f9d8d9e52..5abfc14ac6 100644
--- a/tests/auto/corelib/thread/qresultstore/CMakeLists.txt
+++ b/tests/auto/corelib/thread/qresultstore/CMakeLists.txt
@@ -16,4 +16,5 @@ qt_internal_add_test(tst_qresultstore
tst_qresultstore.cpp
LIBRARIES
Qt::CorePrivate
+ Qt::TestPrivate
)
diff --git a/tests/auto/corelib/thread/qresultstore/tst_qresultstore.cpp b/tests/auto/corelib/thread/qresultstore/tst_qresultstore.cpp
index 265b2cd1f6..722184a72a 100644
--- a/tests/auto/corelib/thread/qresultstore/tst_qresultstore.cpp
+++ b/tests/auto/corelib/thread/qresultstore/tst_qresultstore.cpp
@@ -2,7 +2,7 @@
// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only
#include <QTest>
-
+#include <QtTest/private/qcomparisontesthelper_p.h>
#include <qresultstore.h>
using namespace QtPrivate;
@@ -23,6 +23,7 @@ class tst_QtConcurrentResultStore : public QObject
public slots:
void init();
private slots:
+ void compareCompiles();
void construction();
void iterators();
void addResult();
@@ -52,6 +53,11 @@ void tst_QtConcurrentResultStore::init()
vec1 = QList<int> { 4, 5 };
}
+void tst_QtConcurrentResultStore::compareCompiles()
+{
+ QTestPrivate::testEqualityOperatorsCompile<ResultIteratorBase>();
+}
+
void tst_QtConcurrentResultStore::construction()
{
ResultStoreBase store;
@@ -74,17 +80,20 @@ void tst_QtConcurrentResultStore::iterators()
storebase.addResult(1, &int1); // ResultStoreBase does not take ownership, only ResultStore<> does.
ResultIteratorBase it = storebase.begin();
QCOMPARE(it.resultIndex(), 0);
- QCOMPARE(it, storebase.begin());
+ QT_TEST_EQUALITY_OPS(it, storebase.begin(), true);
QVERIFY(it != storebase.end());
++it;
QCOMPARE(it.resultIndex(), 1);
QVERIFY(it != storebase.begin());
QVERIFY(it != storebase.end());
+ QT_TEST_EQUALITY_OPS(it, storebase.begin(), false);
+ QT_TEST_EQUALITY_OPS(it, storebase.end(), false);
++it;
QVERIFY(it != storebase.begin());
QCOMPARE(it, storebase.end());
+ QT_TEST_EQUALITY_OPS(it, storebase.end(), true);
}
}
@@ -147,8 +156,8 @@ void tst_QtConcurrentResultStore::addResults()
store.addResults(-1, &vec1);
ResultIteratorBase it = store.begin();
QCOMPARE(it.resultIndex(), 0);
- QCOMPARE(it, store.begin());
- QVERIFY(it != store.end());
+ QT_TEST_EQUALITY_OPS(it, store.begin(), true);
+ QT_TEST_EQUALITY_OPS(it, store.end(), false);
++it;
QCOMPARE(it.resultIndex(), 1);
@@ -162,7 +171,7 @@ void tst_QtConcurrentResultStore::addResults()
QCOMPARE(it.resultIndex(), 3);
++it;
- QCOMPARE(it, store.end());
+ QT_TEST_EQUALITY_OPS(it, store.end(), true);
QList<int> empty;
const auto countBefore = store.count();
@@ -184,22 +193,22 @@ void tst_QtConcurrentResultStore::resultIndex()
ResultIteratorBase it = store.begin();
QCOMPARE(it.resultIndex(), 0);
- QVERIFY(it == store.begin());
- QVERIFY(it != store.end());
+ QT_TEST_EQUALITY_OPS(it, store.begin(), true);
+ QT_TEST_EQUALITY_OPS(it, store.end(), false);
++it;
QCOMPARE(it.resultIndex(), 1);
- QVERIFY(it != store.begin());
- QVERIFY(it != store.end());
+ QT_TEST_EQUALITY_OPS(it, store.begin(), false);
+ QT_TEST_EQUALITY_OPS(it, store.end(), false);
++it;
QCOMPARE(it.resultIndex(), 2);
- QVERIFY(it != store.end());
+ QT_TEST_EQUALITY_OPS(it, store.end(), false);
++it;
QCOMPARE(it.resultIndex(), 3);
- QVERIFY(it != store.end());
+ QT_TEST_EQUALITY_OPS(it, store.end(), false);
++it;
- QVERIFY(it == store.end());
+ QT_TEST_EQUALITY_OPS(it, store.end(), true);
QCOMPARE(store.resultAt(0).value<int>(), int0);
QCOMPARE(store.resultAt(1).value<int>(), vec0[0]);
diff --git a/tests/auto/corelib/thread/qthread/tst_qthread.cpp b/tests/auto/corelib/thread/qthread/tst_qthread.cpp
index b163235d81..18c8d5fbd5 100644
--- a/tests/auto/corelib/thread/qthread/tst_qthread.cpp
+++ b/tests/auto/corelib/thread/qthread/tst_qthread.cpp
@@ -1299,8 +1299,16 @@ public:
}
void registerSocketNotifier(QSocketNotifier *) override {}
void unregisterSocketNotifier(QSocketNotifier *) override {}
- void registerTimer(Qt::TimerId, Duration, Qt::TimerType, QObject *) override {}
- bool unregisterTimer(Qt::TimerId) override { return false; }
+ void registerTimer(Qt::TimerId id, Duration, Qt::TimerType, QObject *) override
+ {
+ if (registeredTimerId <= Qt::TimerId::Invalid)
+ registeredTimerId = id;
+ }
+ bool unregisterTimer(Qt::TimerId id) override
+ {
+ Qt::TimerId oldId = std::exchange(registeredTimerId, Qt::TimerId::Invalid);
+ return id == oldId;
+ }
bool unregisterTimers(QObject *) override { return false; }
QList<TimerInfoV2> timersForObject(QObject *) const override { return {}; }
Duration remainingTime(Qt::TimerId) const override { return 0s; }
@@ -1313,25 +1321,47 @@ public:
#endif
QBasicAtomicInt visited; // bool
+ Qt::TimerId registeredTimerId = Qt::TimerId::Invalid;
};
-class ThreadObj : public QObject
+struct ThreadLocalContent
{
- Q_OBJECT
-public slots:
- void visit() {
- emit visited();
+ static inline const QMetaObject *atStart;
+ static inline const QMetaObject *atEnd;
+ QSemaphore *sem;
+ QBasicTimer timer;
+
+ ThreadLocalContent(QObject *obj, QSemaphore *sem)
+ : sem(sem)
+ {
+ ensureEventDispatcher();
+ atStart = QAbstractEventDispatcher::instance()->metaObject();
+ timer.start(10s, obj);
+ }
+ ~ThreadLocalContent()
+ {
+ ensureEventDispatcher();
+ atEnd = QAbstractEventDispatcher::instance()->metaObject();
+ timer.stop();
+ sem->release();
+ }
+
+ void ensureEventDispatcher()
+ {
+ // QEventLoop's constructor has a call to QThreadData::ensureEventDispatcher()
+ QEventLoop dummy;
}
-signals:
- void visited();
};
void tst_QThread::customEventDispatcher()
{
+ ThreadLocalContent::atStart = ThreadLocalContent::atEnd = nullptr;
+
QThread thr;
// there should be no ED yet
QVERIFY(!thr.eventDispatcher());
DummyEventDispatcher *ed = new DummyEventDispatcher;
+ QPointer<DummyEventDispatcher> weak_ed(ed);
thr.setEventDispatcher(ed);
// the new ED should be set
QCOMPARE(thr.eventDispatcher(), ed);
@@ -1340,25 +1370,39 @@ void tst_QThread::customEventDispatcher()
thr.start();
// start() should not overwrite the ED
QCOMPARE(thr.eventDispatcher(), ed);
+ QVERIFY(!weak_ed.isNull());
- ThreadObj obj;
+ QObject obj;
obj.moveToThread(&thr);
// move was successful?
QCOMPARE(obj.thread(), &thr);
- QEventLoop loop;
- connect(&obj, SIGNAL(visited()), &loop, SLOT(quit()), Qt::QueuedConnection);
- QMetaObject::invokeMethod(&obj, "visit", Qt::QueuedConnection);
- loop.exec();
+
+ QSemaphore threadLocalSemaphore;
+ QMetaObject::invokeMethod(&obj, [&]() {
+#ifndef Q_OS_WIN
+ // On Windows, the thread_locals are unsequenced between DLLs, so this
+ // could run after QThreadPrivate::finish()
+ static thread_local
+#endif
+ ThreadLocalContent d(&obj, &threadLocalSemaphore);
+ }, Qt::BlockingQueuedConnection);
+
// test that the ED has really been used
QVERIFY(ed->visited.loadRelaxed());
+ // and it's ours
+ QCOMPARE(ThreadLocalContent::atStart->className(), "DummyEventDispatcher");
- QPointer<DummyEventDispatcher> weak_ed(ed);
QVERIFY(!weak_ed.isNull());
thr.quit();
+
// wait for thread to be stopped
QVERIFY(thr.wait(30000));
+ QVERIFY(threadLocalSemaphore.tryAcquire(1, 30s));
+
// test that ED has been deleted
QVERIFY(weak_ed.isNull());
+ // test that ED was ours
+ QCOMPARE(ThreadLocalContent::atEnd->className(), "DummyEventDispatcher");
}
class Job : public QObject