Consider the following problem. Given a number,
x, which has been initialized with the value
0, create a program that increments
x one-hundred times so that when the program is finished executing,
We could implement this program without concurrency, using a single thread which increments
x once, then again, and again until it has done so one-hundred times.
Alternatively, we could write a program that spawns one-hundred threads which will individually increment
x once, but collectively increment
x one hundred times.
Such a program might look something like the image to the right.
Does this work? The answer is almost certainly not. That might seem strange now, but to understand why let us discuss what actually happens when our processor executes the
x = x + 1 operation.
From the processor’s perspective this seemingly simple task actually takes three operations to complete:
- Move the value of
xinto a register
1to that value
- Set the value of
xto be the value in that register
Consider what can happen when two threads attempt to increment
x at the same time. If Thread 1 and Thread 2 both move the value of
x into a register before the other has completed its work, our processor could potentially execute these six operations in the following order:
|1||Thread 1 moves
|2||Thread 2 moves
|3||Thread 1 adds
|4||Thread 2 adds
|5||Thread 1 sets
|6||Thread 2 sets
So now two threads have both completed their task of incrementing
x, and yet
x = 1. Note that a perfect interleaving of operations is unnecessary to get this result. All that is necessary is for the first operation of each thread (loading the value of
x into a register) to take place before the final operation of the other is finished.
x has not been incremented properly is the result of this race condition. To fix this, we must make sure that only one thread can modify
x at a given time. In the next exercise, we discuss one way to do this.
Click Next when you’re ready to move on to the next exercise.