harmony-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From "Jack Cai" <greensi...@gmail.com>
Subject Re: [class loading] what's the expected behavior when a static method is invoked before its class is initialized?
Date Mon, 05 Jan 2009 05:58:58 GMT
I guess we can use lazy load to eliminate the problem. In Chunrong's test
case, the assignation of Child.ROOT field can be held until its value is
used (like in the line "System.err.println(Child.ROOT);"). I'm not sure how
the SPEC says about lazy load, but lazy load just works here.

-Jack

2009/1/5 Nathan Beyer <ndbeyer@apache.org>

> On Sun, Jan 4, 2009 at 10:08 PM, Xiao-Feng Li <xiaofeng.li@gmail.com>
> wrote:
> > On Mon, Jan 5, 2009 at 5:12 AM, Ian Rogers <rogers.email@gmail.com>
> wrote:
> >> 2009/1/4 Nathan Beyer <ndbeyer@apache.org>
> >>
> >>> Could any of the IBM folks on the list get some advice from some class
> >>> loader experts?
> >>>
> >>> -Nathan
> >>>
> >>
> >>  Hi Nathan,
> >>
> >> from reading the description I can describe how Jikes RVM avoids this
> >> problem (I'm not an IBM VME expert and I've not run the test case to
> check
> >> that Jikes RVM passes it). In Jikes RVM we have two variants of all
> calls,
> >> ones to unresolved methods and ones to resolved methods. Unresolved
> calls
> >> are to classes whose initializer hasn't yet been run. If two threads are
> >> calling a static method the first will resolve it and in the process
> acquire
> >> a lock, the second thread must wait for the lock before it can attempt
> to
> >> resolve the method (at which point it will discover the method was
> resolved
> >> by the other thread and leave early). Checking for classes being
> resolved
> >> litters all of the class loader code, and we're slightly proactive in
> >> resolving in the case of reflected methods so that we needn't check for
> >> resolution when performing reflected method invocation (which is now
> pretty
> >> much unnecessary since [1] where we generate bytecodes at runtime to
> perform
> >> reflection). An aside, I wrote a paper where I use the class loader as a
> >> test case for optimizations based on stationary/immutable fields
> specified
> >> via constraints [2], this work specialized the class loader to handle
> the
> >> resolved case as a class is normally accessed when it is resolved
> (figures
> >> in the paper).
> >
> > Thanks for the explanation.
> >
> > Let me try to explain the problem we are meeting:
> >
> > 1. A thread invokes a static method createChild of a class Parent. It
> > causes class Parent be initialized.
> >
> > 2. In Parent's initialization, it creates an array of class Child. It
> > leads to class Child be initialized.
>
> Is this the problem? The initialization bit in the spec only says that
> a non-constant field [1] that references a type T, should cause the
> initialization of type T. This brings up two questions for me. One,
> does that implicitly include arrays of a type T? Two, why is Child
> getting loaded in the example, since it is a constant (static and
> final)?
>
> The second bit seems to be violating the spec. Am I reading it wrong?
>
> [1]
> http://java.sun.com/docs/books/jvms/second_edition/html/Concepts.doc.html#19075
>
> >
> > 3. In Child's initialization, it invokes Parent.createChild() to
> > initialize a static field ROOT. This leads to re-entrance of Parent
> > initialization.
> >
> > 4. The thread finds Parent is under initialization by itself, it quits
> > the initialization process and invokes Parent.createChild().
> >
> > 5. This invocation should not be permitted by the VM spec, and we
> > don't know how to deal with it. It can't wait for the initialization
> > process finished, because it is in the path of the initialization. It
> > has to do something to proceed with the initialization.
>
> Since you put "should not" in this statement, I presume this is just
> an opinion and their isn't any source that supports this, correct?
>
> -Nathan
>
> >
> > Below is the code of the micro test. Chunrong, please correct me if my
> > understanding is inaccurate.
> >
> > So my suggestion is to ignore the static method invocation for the
> > class under initialization...
> >
> >
> > public class Main {
> >    public static void main(String[] args) {
> >        Child c = Parent.createChild();
> >        System.err.println(c);
> >        System.err.println(Child.ROOT);
> >    }
> > }
> >
> > class Parent {
> >    private static final Child[] childCache = new Child[5];
> >
> >    public static Child createChild(){
> >        return childCache[0];
> >    }
> > }
> >
> > class Child {
> >    public static final Child ROOT = Parent.createChild();
> > }
> >
> > Thanks,
> > xiaofeng
> >
> >> Regards,
> >> Ian Rogers
> >>
> >> [1]
> >>
> http://icooolps.loria.fr/icooolps2008/Papers/ICOOOLPS2008_paper08_Rogers_Zhao_Watson_final.pdf
> >> [2] http://portal.acm.org/citation.cfm?id=1411746
> >>
> >
> >
> >
> > --
> > Managed Runtime Technology Center, Intel
> >
>

Mime
  • Unnamed multipart/alternative (inline, None, 0 bytes)
View raw message