On Wed, 6 Jan 1999, Chris Abbey wrote:

> John (& all),
>       Sorry I didn't jump into this thread earlier, but the s:n on this list
> has pushed it down my reading priority list ... way down.

Thanks Chris: I'm glad you stepped in. I've changed mine to match yours
(but am now calling it G).

I have two systems here, results differ:
[summer@emu data]$ java_g G | less
[summer@emu data]$ jikes -d ~/Classes/ G.java && jre G
[summer@emu data]$ jre G
[summer@emu data]$ java G

finalize
[summer@emu data]$ java -fullversion
java full version "stevemw:08/29/98-05:16"

[summer@possum data]$ java G
[summer@possum data]$ jre G
[summer@possum data]$ java G
[summer@possum data]$ jre G
[summer@possum data]$ java -fullversion
java full version "Linux_JDK_1.1.7_v1a_green_threads"
[summer@possum data]$ 

In eyeballing the trace, I changed line 9 to this:
System.out.print("\nfinalize\n");
as I got some output (on emu) and  "finalize" was separated from its
followong newline.

Since it works on emu running with java_g, I'm not posting its trace.


>       John's understanding of finalizer and runFinalizersOnExit as I've
> understood him to state it in this thread matches my own interpretation of the
> Java Language spec and JVM spec in this regard. If runFinalizersOnExit is set
> then the finalizer must be called; come hell or high water, that code should
> be given the opportunity to run at some point. It could be when the GC needs to
> purge memory inorder to allocate a request or by explicit call to the API
> java/lang/Runtime.gc()V, or when the runtime is exiting. Note that if the gc
> doesn't have to purge memory to satisfy a request I don't believe it will
> finalize an object, put it on the queue maybe, but not actually do it.
>       I don't have my hands on a functional Linux box for a few days, so I
> tested this on Sun's 1.1.6N reference implementation on WinNT. Can someone
> else (John?) run these tests on the blackdown port? Inorder to really test
> this we need to trace the method dispatching. To do this we need to run with
> the debugable build of the java runtime, java_g (jre_g does not allow method
> tracing????) and we need to flip the switch to turn on the method tracing with
> -tm on command line, or the java/lang/Runtime.traceMethodCalls(Z)V API. The
> command line switch is tedious in that you have to wade through all the
> runtime initialization calls, which aren't very interesting to us so I'll go
> with the API.
>       I've modified John's posted testcase code as follows:
> --begin F.java--
> 00:public class F
> 01:{
> 02:  static //make this code part of "F.<clinit>()V"
> 03:    {
> 04:      Runtime.getRuntime().traceMethodCalls(true); //activate method dispatch 
>trace
> 05:    }
> 06:  protected void finalize() throws Throwable
> 07:    {
> 08://    System.out.println("finalize"); //took too much time, no longer needed
> 09:      super.finalize();
> 10:    }
> 11:  public static void main(String[] args) throws Throwable
> 12:    {
> 13:      F f = new F();
> 14://  System.runFinalizersOnExit(true); //redundant
> 15:      Runtime.getRuntime().runFinalizersOnExit(true);
> 16:      f = null;
> 17://  System.gc(); //not needed
> 18:    }
> 19:}
> --end F.java--
> 
> Then ran it: (all lines begining with '#' are the output, those with '>'
> are my comments to explain what's happening for those unfamiliar with this
> level of the JVM.)
> 
> E:\TEMP\New Folder>javac F.java
> 
> E:\TEMP\New Folder>java_g F
> # main [ 1] | < java/lang/Runtime.traceMethodCalls(Z)V returning
> # main [ 0] < F.<clinit>()V returning
> >class init & therefore load has just finished, so now start the actual pgm
> # main [ 0] > F.main([Ljava/lang/String;)V (1) entered
> >gotta construct an instance first
> # main [ 1] | > F.<init>()V (1) entered
> >superclass ctor
> # main [ 2] | | > java/lang/Object.<init>()V (1) entered
> # main [ 2] | | < java/lang/Object.<init>()V returning
> # main [ 1] | < F.<init>()V returning
> >line 15
> # main [ 1] | > java/lang/Runtime.getRuntime()Ljava/lang/Runtime; (0) entered
> # main [ 1] | < java/lang/Runtime.getRuntime()Ljava/lang/Runtime; returning
> >still line 15
> # main [ 1] | > java/lang/Runtime.runFinalizersOnExit(Z)V (1) entered
> >within the code for runFinalizersOnExit
> >  first check to see if the SecurityManager will let you toggle this
> # main [ 2] | | > java/lang/System.getSecurityManager()Ljava/lang/SecurityManager; 
>(0) entered
> # main [ 2] | | < java/lang/System.getSecurityManager()Ljava/lang/SecurityManager; 
>returning
> >apparently it will... so call the native code that actually toggles it
> # main [ 2] | | > java/lang/Runtime.runFinalizersOnExit0(Z)V (1) entered
> # main [ 2] | | < java/lang/Runtime.runFinalizersOnExit0(Z)V returning
> # main [ 1] | < java/lang/Runtime.runFinalizersOnExit(Z)V returning
> # main [ 0] < F.main([Ljava/lang/String;)V returning
> >that's the end of main, so begin the runtime exit processes
> >  finalize all objects still live 
> # main [ 0] > F.finalize()V (1) entered
> >super.finalize() call on line 9
> # main [ 1] | > java/lang/Object.finalize()V (1) entered
> # main [ 1] | < java/lang/Object.finalize()V returning
> # main [ 0] < F.finalize()V returning
> >now finalize System objects, start with System.in
> # main [ 0] > java/io/FileInputStream.finalize()V (1) entered
> # main [ 0] < java/io/FileInputStream.finalize()V returning
> >then System.out
> # main [ 0] > java/io/FileOutputStream.finalize()V (1) entered
> # main [ 1] | > java/io/OutputStream.flush()V (1) entered
> # main [ 1] | < java/io/OutputStream.flush()V returning
> # main [ 0] < java/io/FileOutputStream.finalize()V returning
> >and System.err
> # main [ 0] > java/io/FileOutputStream.finalize()V (1) entered
> # main [ 1] | > java/io/OutputStream.flush()V (1) entered
> # main [ 1] | < java/io/OutputStream.flush()V returning
> # main [ 0] < java/io/FileOutputStream.finalize()V returning
> >that's all
> E:\TEMP\New Folder>
Here's mine:
[summer@possum data]$ java_g G       
# main [ 1] | < java/lang/Runtime.traceMethodCalls(Z)V returning
# main [ 0] < G.<clinit>()V returning
# main [ 0] > G.main([Ljava/lang/String;)V (1) entered
# main [ 1] | > G.<init>()V (1) entered
# main [ 2] | | > java/lang/Object.<init>()V (1) entered
# main [ 2] | | < java/lang/Object.<init>()V returning
# main [ 1] | < G.<init>()V returning
# main [ 1] | > java/lang/Runtime.getRuntime()Ljava/lang/Runtime; (0) entered
# main [ 1] | < java/lang/Runtime.getRuntime()Ljava/lang/Runtime; returning
# main [ 1] | > java/lang/Runtime.runFinalizersOnExit(Z)V (1) entered
# main [ 2] | | > java/lang/System.getSecurityManager()Ljava/lang/SecurityManager; (0) 
entered
# main [ 2] | | < java/lang/System.getSecurityManager()Ljava/lang/SecurityManager; 
returning
# main [ 2] | | > java/lang/Runtime.runFinalizersOnExit0(Z)V (1) entered
# main [ 2] | | < java/lang/Runtime.runFinalizersOnExit0(Z)V returning
# main [ 1] | < java/lang/Runtime.runFinalizersOnExit(Z)V returning
# main [ 0] < G.main([Ljava/lang/String;)V returning
[summer@possum data]$ 


I've not looked closely at what happens on emu, but it's voluminous and
shows my finalizer being called.

Just for the hell of it, I compiled with javac on both machines (I normally
run jikes): results are the same (finalizer called/notcalled, didn't look
at the trace).

-- 
Cheers
John Summerfield
http://os2.ami.com.au/os2/ for OS/2 support.
Configuration, networking, combined IBM ftpsites index.

Reply via email to