C++11: What happens if you don’t call join() for std::thread

If you have not detached or joined a thread when the destructor is called it will call std::terminate, we can see this by going to the draft C++11 standard we see that section 30.3.1.3 thread destructor says:

If joinable(), calls std::terminate(). Otherwise, has no effects. [
Note: Either implicitly detaching or joining a joinable() thread in
its destructor could result in difficult to debug correctness (for
detach) or performance (for join) bugs encountered only when an
exception is raised. Thus the programmer must ensure that the
destructor is never executed while the thread is still joinable. —end
note ]

as for a rationale for this behavior we can find a good summary in (Not) using std::thread

Why does the destructor of a joinable thread have to call
std::terminate? After all, the destructor could join with the child
thread, or it could detach from the child thread, or it could cancel
the thread. In short, you cannot join in the destructor as this would
result in unexpected (not indicated explicitly in the code) program
freeze in case f2 throws.

and an example follows and also says:

You cannot detach as it would risk the situation where main thread
leaves the scope which the child thread was launched in, and the child
thread keeps running and keeps references to the scope that is already
gone.

The article references N2802: A plea to reconsider detach-on-destruction for thread objects which is argument against the previous proposal which was detach on destruction if joinable and it notes that one of the two alternatives would be to join which could lead to deadlocks the other alternative is what we have today which is std::terminate on destruction if joinable.

Leave a Comment