Details
-
Bug
-
Resolution: Fixed
-
P1: Critical
-
6.5
-
None
-
3
-
04b5d2b94 (dev), 5b55e8d1f (6.9), 2395d5d8d (6.8), b2884611a (tqtc/lts-6.5)
-
Foundation Sprint 125
Description
In my application, I use QFuture along with its then() method to manage asynchronous operations. Over time, the application experiences crashes, seemingly due to a continuation being invoked twice, which is not the expected behaviour.
Code Sample:
#include "test.h" #include <QFuture> #include <QPromise> #include <QtConcurrent> Test::Test(QObject *parent) : QObject{parent} { connect(this, &Test::tryNext, this, &Test::test, Qt::QueuedConnection); } void Test::test() { auto f = QtConcurrent::run([] {}); //fast function that can finish // before .then is called f.then([this] { emit tryNext(); }); }
I assume that the problem arises because of the following:
- Call QtConcurrent::run with a fast function
- Due to the fast function, QFutureInterfaceBase::reportFinished() is triggered.
- At the same time in another thread, the then method is called and since the future is already finished, it also triggers the continuation and saves it for later invocation.
- After the saving of the continuation, QFutureInterfaceBase::runContinuation() is called and, noticing the continuation already stored, invokes the continuation once again.
- The double invocation of the continuation leads to a crash. (call methods of moved promise)
To reproduce the problem, simply run the attached project and after a small amount of time, it will crash. The crash has been confirmed on macOS and Windows platforms.
Attachments
For Gerrit Dashboard: QTBUG-118032 | ||||||
---|---|---|---|---|---|---|
# | Subject | Branch | Project | Status | CR | V |
623165,4 | QFuture: prevent the continuations from being executed twice | dev | qt/qtbase | Status: MERGED | +2 | 0 |
623732,2 | QFuture: prevent the continuations from being executed twice | 6.9 | qt/qtbase | Status: MERGED | +2 | 0 |
623846,2 | QFuture: prevent the continuations from being executed twice | 6.8 | qt/qtbase | Status: MERGED | +2 | 0 |
624088,2 | QFuture: prevent the continuations from being executed twice | tqtc/lts-6.5 | qt/tqtc-qtbase | Status: MERGED | +2 | 0 |