As you say yourself, you are off the limits of the C++ standard here. Practically, there are compilers that assume that shutdown_in_progress
does not change, if they can prove nothing inside the while
loop is able to change it.
In your case, shutdown_in_progress
is a reference to a boolean variable. So the compiler does in general not know whether that variable is accessed using another name somewhere else. For example it might refer to a global variable that might be changed by do_slow_stuff_with
. If the source code for that function is in the same file, and there are no assignments to any boolean variables in that function, alias analysis might kick in and tell the compiler there are no write accesses to any boolean variables, so definitely nothing aliases shutdown_in_progress
. But as soon as you call some function outside the current translation unit, older versions of gcc can not optimize the access away.
There might be a second way for gcc to prove there is no access to the boolean variable refered to by shutdown in_progress
which is by tracing whether there are any other references to the real target created. For example if the target of the reference is a local variable of the caller, and the caller never passed the address of that variable to any other function, gcc can be sure there are no aliases, so that there is no way for that variable to change. In your case, I am quite sure this kind of optimization (if done at all) does not apply, as you surely have passed the address of shutdown_in_progress
to another function that could initiate shutdown, or it is a global variable.
Finally, gcc makes sure not to optimize any accesses to variables declared as volatile
. While the C++ standard does not guarantee anything about volatile variables in connection with threads, and even in practice you might get very unexpected results if you try to synchronize through volatile variables without using pthread primitives, in this case, using a volatile variable seems to be safe. The problem with volatiles is, that they make sure the write instructions when assigning to multiple of them are ordered correctly, but there is no guarantee readers observe the effects of the writes in that order.
And as a last point, if you don't add pthread function calls and have an evil processor architecture, one processor core executing the function you wrote might work with a stale cached copy of the referenced boolean variable for an indefinite amount of time.