Re: JavaMemoryModel: No "Spooky errors at a distance"

From: Bill Pugh (pugh@cs.umd.edu)
Date: Fri Mar 08 2002 - 11:58:06 EST


OK, here is a case that shows potential compiler optimizations could
violate feature 2:

class Foo {
   final int x;
   static Foo p,q;
   Foo(int i) {
         x = i;
        Foo.p = this;
        }
   }

Thread 1:
synchronized (Foo.class) {
   Foo.q = new Foo(42);
   }

Thread 2:

Foo a = Foo.p;
if (a != null && a.x == 0)
   synchronized (Foo.class) {
     Foo b = Foo.q;
     if (a == b) {
       int i = a.x;
       int j = b.x;
       // is it possible for j to be zero?
       System.out.println(i+j);
       }
     }

Now, the semantics of final fields allow a compiler to move the load
of a final field a.x to immediately after the load of a (even through
synchronization barriers). So it is possible for i to be zero.

However, the load of b.x cannot be moved to before the lock is
acquired, so j cannot be zero.

However, a compiler writer might be tempted to decide:
        * since a and b are equal
        * I can reuse the value of a.x as the value of b.x
        * getting the value 0 for j

This is a slight variation on an example I posted 2/1/02. Note that
for this example, except for the special semantics of final fields,
it wouldn't be possible for i to be zero anyway (the synchronization
would force a.x to be reloaded).

        Bill
-------------------------------
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