I am currently studying concurrent systems, and I've become a little confused with the concept of cache coherency when working with multiple threads and multiple cores at the same time.
Some assumptions as I understand:
- Cores have caches
- Cores may have multiple threads at one time (if hyperthreaded)
- A thread is a single line of commands that are getting processed
- Thus, threads are not physical hardware and threads don't have caches and use the core's cache
Suppose a core has we have two threads and x is a shared variable with value five. Both want to execute:
my_y = x;
Where my_y is a private variable defined by both threads. Now suppose thread 0 executes:
x++;
Finally, suppose that thread 1 now executes:
my_z = x;
Where my_z is another private variable.
My book says the following:
What's the value in
my_z? Is it five? Or is it six? The problem is that there are (at least) three copies ofx: the one in main memory, the one in thread 0's cache, and the one in thread 1's cache.
How does this work? How are there at least three copies of x and why does the book specify that each thread has its own cache? To me, it would make sense that the core which is running the two threads has the value of x in its cache and thus both threads have the value in "their" (shared) cache.
In other words, when x++ is updated, the value in the core's cache would be updated. Then, thread 1 would execute my_z = x; which is still in the core's cache and it is up to date. Thus, there would be no coherency issue because the two threads basically share the cache.
It could be that the book assumes that each core has only one thread, but the book did previously mention something about "if there are more threads than cores". Does "if there are more threads than cores" imply that a core has more than one thread (hyperthreading) or is there some sort of thread scheduling happening so that each core only has one thread at a time?
Even if this is the case (the scheduling of cores and that a core can only have one thread at a time), if a core owns thread 0, executes x++ and then obtains thread 1 who is trying to execute my_z = x; the value of x would still exist in that core's cache, if I'm not mistaken.
Bonus question: how are the private variables of threads stored in memory? Are they stored in the same way as any variable where they get copied in a core's cache when used? If this is the case, will it be a problem to have a private variable in the core's cache if multiple threads are using the cache - whether simultaneously or scheduled?
As per @biziclop 's request, the book states the following assumptions:
- We use MIMD systems, that is, the nodes have the same architecture. (The book doesn't specifically state which architecture this is, though)
- Our programs are SPMD. Thus, we'll write a single program that can use branching to have multiple behaviours.
- We assume cores are identical but operate asynchronously.
- We program in the C language and in this section we focused on Pthreads.
Any help would be appreciated!