I'm trying to join two pplx tasks using the && operator of task, where both sub tasks can throw exceptions.
I understand from the ppl documentation that I can catch an exception in a final, task-based continuation. This works in Casablanca as well. However, I can catch only one exception in my final continuation. If both sub tasks throw, one remains unhandled.
Here's a minimal example illustrating my problem:
#include <pplx/pplxtasks.h>
#include <iostream>
int main(int argc, char *argv[])
{
int a = 0; int b = 0;
auto t1 = pplx::create_task([a] { return a+1; })
.then([](int a) { throw std::runtime_error("a");
return a+1; });
auto t2 = pplx::create_task([b] { return b+1; })
.then([](int b) { throw std::runtime_error("b");
return b+1; });
(t1 && t2)
.then([] (std::vector<int>) { /*...*/ })
.then([] (pplx::task<void> prev) {
try {
prev.get();
} catch (std::runtime_error e) {
std::cout << "caught " << e.what() << std::endl;
}
});
std::cin.get();
}
The try/catch is able to catch whichever of the two exceptions occurs first. How can I catch the other?
You would have to add a final task-based continuation to each sub-task. I would suggest re-throwing any exception you catch, however, that would likely be a bad idea since the continuation task doesn't realize that the 2 exceptions are equivalent see below example for proof.
Output:
caught a
caught final a
caught b
Also, if you remove the sleep, you will receive a "Trace/breakpoint trap" exception.