My teacher in an upper level Java class on threading said something that I wasn't sure of.
He stated that the following code would not necessarily update the ready
variable. According to him, the two threads don't necessarily share the static variable, specifically in the case when each thread (main thread versus ReaderThread
) is running on its own processor and therefore doesn't share the same registers/cache/etc and one CPU won't update the other.
Essentially, he said it is possible that ready
is updated in the main thread, but NOT in the ReaderThread
, so that ReaderThread
will loop infinitely.
He also claimed it was possible for the program to print 0
or 42
. I understand how 42
could be printed, but not 0
. He mentioned this would be the case when the number
variable is set to the default value.
I thought perhaps it is not guaranteed that the static variable is updated between the threads, but this strikes me as very odd for Java. Does making ready
volatile correct this problem?
He showed this code:
public class NoVisibility {
private static boolean ready;
private static int number;
private static class ReaderThread extends Thread {
public void run() {
while (!ready) Thread.yield();
System.out.println(number);
}
}
public static void main(String[] args) {
new ReaderThread().start();
number = 42;
ready = true;
}
}
@dontocsata you can go back to your teacher and school him a little :)
few notes from the real world and regardless what you see or be told. Please NOTE, the words below are regarding this particular case in the exact order shown.
The following 2 variable will reside on the same cache line under virtually any know architecture.
Thread.exit
(main thread) is guaranteed to exit andexit
is guaranteed to cause a memory fence, due to the thread group thread removal (and many other issues). (it's a synchronized call, and I see no single way to be implemented w/o the sync part since the ThreadGroup must terminate as well if no daemon threads are left, etc).The started thread
ReaderThread
is going to keep the process alive since it is not a daemon one! Thusready
andnumber
will be flushed together (or the number before if a context switch occurs) and there is no real reason for reordering in this case at least I can't even think of one. You will need something truly weird to see anything but42
. Again I do presume both static variables will be in the same cache line. I just can't imagine a cache line 4 bytes long OR a JVM that will not assign them in a continuous area (cache line).