amplifier
amplifier

Reputation: 1833

Setting exeption for promise causes abort call

I have a throwing function:

void calculateValuesThrowing(std::promise<int>&& pr, int a, int b)
{
    try
    {
        auto timeout = std::chrono::seconds(5);
        logInfo("Calculating value...");
        std::this_thread::sleep_for(timeout);
        if (a == b)
        {
            throw std::runtime_error("a cannot equal b");
        }
        pr.set_value(a + b);
    }
    catch(std::exception& exc)
    {
        pr.set_exception(std::current_exception()); // ok, jump here right after the "throw" above
    }
}

and I call it like that:

somewhere in main() function:

try
{
    std::promise<int> promise;
    auto future = promise.get_future();
    std::thread th(calculateValuesThrowing, std::move(promise), 10, 10);
    auto result = future.get();
    th.join();
}
catch(std::exception& exc)
{
    std::cout << "Error:" << exc.what(); // never get there
}

I expect an exception of calculateValuesThrowing will be "rethrown" so that I could process it in main's catch(), but right after calculateValuesThrowing finishes working I get abort().

What am I doing wrong?

Upvotes: 2

Views: 40

Answers (1)

Asteroids With Wings
Asteroids With Wings

Reputation: 17454

When future.get() throws, th.join() is never invoked so th goes out of scope while the thread is still active. This terminates the program.

Try [sic] something like this instead:

std::promise<int> promise;
auto future = promise.get_future();

std::thread th(calculateValuesThrowing, std::move(promise), 10, 10);
try
{
    auto result = future.get();
}
catch(std::exception& exc)
{
    std::cout << "Error:" << exc.what(); // never get there
}

th.join();

Of course, now you can't use result outside of the try, but that was the case anyway. I don't have enough information about how you use it to suggest a concrete fix for that.

Upvotes: 4

Related Questions