diff --git a/src/corelib/thread/qfuture.qdoc b/src/corelib/thread/qfuture.qdoc index b20875c423d..8235fbf1907 100644 --- a/src/corelib/thread/qfuture.qdoc +++ b/src/corelib/thread/qfuture.qdoc @@ -404,7 +404,7 @@ /*! \fn template void QFuture::waitForFinished() Waits for the asynchronous computation to finish (including cancel()ed - computations). + computations), i.e. until isFinished() returns \c true. */ /*! \fn template T QFuture::result() const diff --git a/src/corelib/thread/qfutureinterface.cpp b/src/corelib/thread/qfutureinterface.cpp index a625e05aac3..600dd9bd3f1 100644 --- a/src/corelib/thread/qfutureinterface.cpp +++ b/src/corelib/thread/qfutureinterface.cpp @@ -422,7 +422,7 @@ void QFutureInterfaceBase::waitForResult(int resultIndex) void QFutureInterfaceBase::waitForFinished() { QMutexLocker lock(&d->m_mutex); - const bool alreadyFinished = !isRunningOrPending(); + const bool alreadyFinished = isFinished(); lock.unlock(); if (!alreadyFinished) { @@ -430,7 +430,7 @@ void QFutureInterfaceBase::waitForFinished() lock.relock(); - while (isRunningOrPending()) + while (!isFinished()) d->waitCondition.wait(&d->m_mutex); } diff --git a/src/corelib/thread/qfuturewatcher.cpp b/src/corelib/thread/qfuturewatcher.cpp index 75f5e297e2f..d59b6755a4b 100644 --- a/src/corelib/thread/qfuturewatcher.cpp +++ b/src/corelib/thread/qfuturewatcher.cpp @@ -417,7 +417,7 @@ bool QFutureWatcherBase::isSuspended() const /*! \fn template void QFutureWatcher::waitForFinished() Waits for the asynchronous computation to finish (including cancel()ed - computations). + computations), i.e. until isFinished() returns \c true. */ void QFutureWatcherBase::waitForFinished() { diff --git a/tests/auto/corelib/thread/qfuture/tst_qfuture.cpp b/tests/auto/corelib/thread/qfuture/tst_qfuture.cpp index c1b562e7f49..e6f6827f3f7 100644 --- a/tests/auto/corelib/thread/qfuture/tst_qfuture.cpp +++ b/tests/auto/corelib/thread/qfuture/tst_qfuture.cpp @@ -144,6 +144,7 @@ private slots: void takeResultWorksForTypesWithoutDefaultCtor(); void canceledFutureIsNotValid(); void signalConnect(); + void waitForFinished(); private: using size_type = std::vector::size_type; @@ -3076,5 +3077,29 @@ void tst_QFuture::signalConnect() } } +void tst_QFuture::waitForFinished() +{ + QFutureInterface fi; + auto future = fi.future(); + + QScopedPointer waitingThread (QThread::create([&] { + future.waitForFinished(); + })); + + waitingThread->start(); + + QVERIFY(!waitingThread->wait(200)); + QVERIFY(!waitingThread->isFinished()); + + fi.reportStarted(); + QVERIFY(!waitingThread->wait(200)); + QVERIFY(!waitingThread->isFinished()); + + fi.reportFinished(); + + QVERIFY(waitingThread->wait()); + QVERIFY(waitingThread->isFinished()); +} + QTEST_MAIN(tst_QFuture) #include "tst_qfuture.moc" diff --git a/tests/auto/corelib/thread/qpromise/snippet_qpromise.cpp b/tests/auto/corelib/thread/qpromise/snippet_qpromise.cpp index 2975afca0f9..7180baccca2 100644 --- a/tests/auto/corelib/thread/qpromise/snippet_qpromise.cpp +++ b/tests/auto/corelib/thread/qpromise/snippet_qpromise.cpp @@ -75,11 +75,8 @@ void snippet_QPromise::basicExample() QPromise promise; QFuture future = promise.future(); - // Note: calling reportStarted() prior to thread creation to enforce order - // of calls: first promise.reportStarted() then future.waitForFinished() - promise.reportStarted(); // notifies QFuture that the computation is started - QScopedPointer thread(QThread::create([] (QPromise promise) { + promise.reportStarted(); // notifies QFuture that the computation is started promise.addResult(42); promise.reportFinished(); // notifies QFuture that the computation is finished }, std::move(promise)));