>
> Say we have:
>
> class A {
> OutputStream x = new FileOutputStream("log");
> InputStream y;
> static int z;
> protected void finalize() { ... }
> }
> A a = new A();
> a.y = new FileInputStream("test");
> A.z = 69;
> a = null;
>
> As written, when the finalize method is invoked, which writes, if
> any, is the finalizer guaranteed to see?
> x1) The write to the x field (in the constructor)
> x2) The writes that construct the FileOutputStream which is assigned to x
> y1) The write to the y field (after construction)
> y2) The writes that construct the FileIntputStream which is assigned to y
> z) The write to the static field (after the last live reference to a)
>
Bill,
According to the principle of least astonishment, the finalizer would see
everything in your list.
But if you want to depend on 'synchronized' for visibility, I suggest you add
an implicit 'synchronized' to the finalizer invocation and let the chips fall
where they may.
For example, let the finalizing thread synchronize on the last remaining
reference:
synchronized (ref) { ref.finalize(); }
Or, add an implicit synchronization to the finalizer body:
protected void finalize() throws Throwable {
synchronized (this) {
// ... body ...
}
}
Or simply tell everyone to synchronize their finalizers (the education you
spoke of).
In any of the above, the finalizer would only see x1 and x2, written during
construction. (And this depends on how constructors are synchronized - see
below.)
By the way, am I correct that you're suggesting that constructors behave as if
they were implicitly synchronized?
Is there a way to code that explicitly? For example:
public A() {
super();
synchronized (this) {
// ... body ...
}
}
Fyi. In the Java2 v1.2.2 distribution there are about 20 finalizers in the
java.* and javax.* code, combined, and about 60 in the sun.* code.
-- Joe Bowbeer------------------------------- JavaMemoryModel mailing list - http://www.cs.umd.edu/~pugh/java/memoryModel
This archive was generated by hypermail 2b29 : Thu Oct 13 2005 - 07:00:24 EDT