I want to start by stating something that I believe needs to be
guaranteed by the memory model, and then see where that takes us.
I propose that the memory model not allow "Spooky errors at a
distance". Specifically, say you have two Runnable tasks, r1 and r2.
Consider two ways to execute these tasks:
1) Run each in their own thread
2) Give both to a thread pool or Executor, where they might be executed
sequentially by a single thread.
Now, I will argue feature 1: assuming you aren't playing games with
ThreadLocals or thread identity, using (2) should never be worse than
using (1). If using (2) could be worse, Executors become unattractive
and debugging nearly impossible.
In particular, say that
a) some other thread has published a reference to an object x while
x is being constructed
b) r1 loads a reference to x in a way that doesn't guarantee
the object is initialized before the reference is loaded
c) r2 loads a reference to x, but uses synchronization to
guarantee that the reference is not loaded until x is
Now, I argue that even if r1 and r2 are run in the same thread, r2 should see
the correctly initialized version of x. Otherwise, "spooky action at
a distance" can cause serious errors in your software.
If you agree with feature 1, then I further argue for feature 2: if
task r3 loads two difference references to x, the first incorrectly
synchronized and the second correctly synchronized, then loads
through the second reference should be valid, even if loads through
the first reference are not. The reason for feature 2 is that I think
it would be very difficult to distinguish between feature 1 and
feature 2 in the semantics.
Before I go further in discussing the implications of these features,
I want to see if there is general support that these two features are
a requirement for a memory model that supports reliable software.
JavaMemoryModel mailing list - http://www.cs.umd.edu/~pugh/java/memoryModel
This archive was generated by hypermail 2b29 : Thu Oct 13 2005 - 07:00:38 EDT