Busy waiting for a variable to change without proper synchronization can cause serious problems in concurrent Go programs.
When a goroutine uses a simple loop like for !done {} to wait for another goroutine to change a variable, there are no guarantees
about memory visibility. The Go Memory Model specifies that without synchronization events, there’s no "happens-before" relationship between
goroutines.
This means:
- The waiting goroutine may never observe the write to the variable, causing an infinite loop
- Even if the variable change is observed, other related variable changes may not be visible
- The program behavior becomes unpredictable and may vary between different runs or compiler optimizations
The root cause is the absence of synchronization primitives. Simple variable reads and writes are not atomic operations that establish memory
ordering between goroutines. Without explicit synchronization, the CPU and compiler are free to reorder operations in ways that break the intended
logic.
What is the potential impact?
The program may hang indefinitely due to infinite loops, or exhibit unpredictable behavior due to data races. In production environments, this can
lead to application freezes, resource exhaustion, and unreliable system behavior.