diff options
author | Sona Kurazyan <sona.kurazyan@qt.io> | 2020-03-26 13:22:46 +0100 |
---|---|---|
committer | Sona Kurazyan <sona.kurazyan@qt.io> | 2020-04-01 21:51:06 +0200 |
commit | 495f958b9ac5c45196e743fcba300fcfd25b90a3 (patch) | |
tree | eb24af3b1fffb770328b11dfccdfc3c783e7ff76 /tests/auto/corelib | |
parent | 7909de1bebe3bac32286513025fc00220cd29ec1 (diff) |
Store QFuture exceptions as std::exception_ptr
Replaced the internal ExceptionHolder for storing QException* by
std::exception_ptr. This will allow to report and store exceptions
of types that are not derived from QException.
Task-number: QTBUG-81588
Change-Id: I96be919d8289448b3e608310e51a16cebc586301
Reviewed-by: Vitaly Fanaskov <vitaly.fanaskov@qt.io>
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Diffstat (limited to 'tests/auto/corelib')
-rw-r--r-- | tests/auto/corelib/thread/qfuture/tst_qfuture.cpp | 102 |
1 files changed, 86 insertions, 16 deletions
diff --git a/tests/auto/corelib/thread/qfuture/tst_qfuture.cpp b/tests/auto/corelib/thread/qfuture/tst_qfuture.cpp index 7e314d63ba..4e20741055 100644 --- a/tests/auto/corelib/thread/qfuture/tst_qfuture.cpp +++ b/tests/auto/corelib/thread/qfuture/tst_qfuture.cpp @@ -1418,6 +1418,23 @@ QFuture<void> createDerivedExceptionFuture() return f; } +struct TestException +{ +}; + +QFuture<int> createCustomExceptionFuture() +{ + QFutureInterface<int> i; + i.reportStarted(); + QFuture<int> f = i.future(); + int r = 0; + i.reportResult(r); + auto exception = std::make_exception_ptr(TestException()); + i.reportException(exception); + i.reportFinished(); + return f; +} + void tst_QFuture::exceptions() { // test throwing from waitForFinished @@ -1502,6 +1519,18 @@ void tst_QFuture::exceptions() } QVERIFY(caught); } + + // Custom exceptions + { + QFuture<int> f = createCustomExceptionFuture(); + bool caught = false; + try { + f.result(); + } catch (const TestException &) { + caught = true; + } + QVERIFY(caught); + } } class MyClass @@ -2040,46 +2069,87 @@ void tst_QFuture::thenOnExceptionFuture() } } +template<class Exception, bool hasTestMsg = false> +QFuture<void> createExceptionContinuation(QtFuture::Launch policy = QtFuture::Launch::Sync) +{ + QFutureInterface<void> promise; + + auto then = promise.future().then(policy, [] { + if constexpr (hasTestMsg) + throw Exception("TEST"); + else + throw Exception(); + }); + + promise.reportStarted(); + promise.reportFinished(); + + return then; +} + void tst_QFuture::thenThrows() { - // Continuation throws an exception + // Continuation throws a QException { - QFutureInterface<void> promise; + auto future = createExceptionContinuation<QException>(); - QFuture<void> then = promise.future().then([]() { throw QException(); }); + bool caught = false; + try { + future.waitForFinished(); + } catch (const QException &) { + caught = true; + } + QVERIFY(caught); + } - promise.reportStarted(); - promise.reportFinished(); + // Continuation throws an exception derived from QException + { + auto future = createExceptionContinuation<DerivedException>(); bool caught = false; try { - then.waitForFinished(); - } catch (QException &) { + future.waitForFinished(); + } catch (const QException &) { caught = true; + } catch (const std::exception &) { + QFAIL("The exception should be caught by the above catch block."); } + QVERIFY(caught); } - // Same with QtFuture::Launch::Async + // Continuation throws std::exception { - QFutureInterface<void> promise; + auto future = createExceptionContinuation<std::runtime_error, true>(); - QFuture<void> then = - promise.future().then(QtFuture::Launch::Async, []() { throw QException(); }); + bool caught = false; + try { + future.waitForFinished(); + } catch (const QException &) { + QFAIL("The exception should be caught by the below catch block."); + } catch (const std::exception &e) { + QCOMPARE(e.what(), "TEST"); + caught = true; + } - promise.reportStarted(); - promise.reportFinished(); + QVERIFY(caught); + } + + // Same with QtFuture::Launch::Async + { + auto future = createExceptionContinuation<QException>(QtFuture::Launch::Async); bool caught = false; try { - then.waitForFinished(); - } catch (QException &) { + future.waitForFinished(); + } catch (const QException &) { caught = true; } QVERIFY(caught); } } -#endif + +#endif // QT_NO_EXCEPTIONS void tst_QFuture::testSingleResult(const UniquePtr &p) { |