The specific instructions used to increment the variable depends on the instruction set, but unless using some kind of atomic increment, it will break down into load/add/store operations as you are describing. On x86 that might be done with a single inc
instruction, but without locking it will still break down to internal load/add/store operations.
You will want to look at the possible interleaving of those sequences. The interleaving is caused by interruption of the non-atomic sequences. Here is one possible such possible interleaving:
thread 1 thread 2
load
load
add
store
add
store
That sequence will leave the variable incremented only once, by thread 1, because thread 2's increment operation is effectively ignored — thread 1 stores last so "wins". (Thread 2 started with the wrong value in some sense anyway, so thread 2's store has the same value (+1) as thread 1's store.)
So, on one extreme the answer would be that the variable will be incremented only by one. On the other extreme, if each thread successfully increments without interruption of that sequence, then the variable would be incremented 7 times. All intermediate values (incremented by 2-6) are also possible.
Since there is no synchronization at all, we also have to consider the possibility that we observe the original 0 after the joins, though I think this is unlikely due to the natural synchronization of system calls involved in creating threads and joining them.