According to the documentation here and here, the join method of a C++11 thread will throw a std::system_error
if joinable() == false
. Thus the natural way to wait for a thread to complete execution is something along the lines of:
if (thread2.joinable()) thread2.join();
However, this has the possibility to throw a std::system_error. Consider thread 1 calls thread2.joinable(), returns true, indicating that the thread2 is still running. Then the scheduler pauses thread1 and switches contexts to thread 2. Thread 2 completes, and then thread 1 resumes. Thread 1 calls thread2.join(), but thread2 has already completed, and as a result, std::system_error is thrown.
A possible solution is to wrap the whole thing in a try block:
try {
thread2.join();
catch (std::system_error &e) {}
But then when a legitimate std::system_error is thrown, possibly to indicate that the thread failed to join, the program continues on, acting as though everything is fine and dandy. Is there a proper way to join a thread besides using a try/catch block like this?
joinable
does not do what you think it does. All it does is return whether the thread object is not associated with a thread. However,thread::join
will fail if the thread object also represents the current thread. So the only reason forthread::join
to fail due to lack ofjoinable
is if you tried to join with yourself.A completed thread (which isn't your own) is still perfectly joinable.