Basically, volatile
announces that a value might change behind your program’s back. That prevents compilers from caching the value (in a CPU register) and from optimizing away accesses to that value when they seem unnecessary from the POV of your program.
What should trigger usage of volatile
is when a value changes despite the fact that your program hasn’t written to it, and when no other memory barriers (like mutexes as used for multi-threaded programs) are present.