Gregory,

I also was stumbled by this failure, especially as the VM provides
scanty diagnostics about it's reason:

<console.log>
*** Error: exception occured in main Thread constructor.
JNI.ExceptionDescribe: java/lang/ExceptionInInitializerError:

java/lang/ExceptionInInitializerError : (null)
ERROR: Destructive unwinding: C++ objects detected on stack!
 droping 0x0012F3A4
setting curr 0x0012F51C
</console.log>

But the stack trace you managed to obtain (how did you, BTW?) prompted
me an extra bootstrap dependency in the j.l.ClassLoader which must be
fixed. Namely, there is a field "defaultDomain", which is incorrectly
initialized in static block, rather than be created lazily as API
specification requires (see javadoc for defineClass(String, byte[],
int, int, ProtectionDomain) ).

--
Regards,
Alexey Varlamov

It looks like the most recent changes to classlib in file operations created
an unresolved bootstrap dependency if security/ directory with its rules and
policies is copied from classlib's lib/ to drlvm lib/ directory. In this case
security cannot initialize correctly because the field
FileInputStream.fileSystem is null at the moment when it is needed. Stack
trace looks like this:

****** STACK DUMP: ************
java/io/FileInputStream.<init>(Ljava/io/File;)V (FileInputStream.java:66)
java/security/Security$1.run()Ljava/lang/Object; (Security.java:113)
java/security/AccessController.doPrivilegedImpl(Ljava/security/PrivilegedAction;Ljava/security/AccessControlContext;)Ljava/lang/Object;
(NULL:-1)
java/security/AccessController.doPrivileged(Ljava/security/PrivilegedAction;)Ljava/lang/Object;
(NULL:-1)
java/security/Security.<clinit>()V (Security.java:116)
org/apache/harmony/security/fortress/PolicyUtils$SecurityPropertyAccessor.run()Ljava/lang/String;
(PolicyUtils.java:148)
org/apache/harmony/security/fortress/PolicyUtils$SecurityPropertyAccessor.run()Ljava/lang/Object;
(PolicyUtils.java:127)
java/security/AccessController.doPrivilegedImpl(Ljava/security/PrivilegedAction;Ljava/security/AccessControlContext;)Ljava/lang/Object;
(NULL:-1)
java/security/AccessController.doPrivileged(Ljava/security/PrivilegedAction;)Ljava/lang/Object;
(NULL:-1)
java/security/Policy.getDefaultProvider()Ljava/security/Policy;
(Policy.java:150)
java/security/Policy.getAccessiblePolicy()Ljava/security/Policy;
(Policy.java:195)
java/security/Policy.getPolicy()Ljava/security/Policy; (Policy.java:131)
java/lang/ClassLoader.<clinit>()V (NULL:-1)
java/lang/Class.desiredAssertionStatus()Z (NULL:-1)
java/util/HashMap.<clinit>()V (HashMap.java:27)
org/apache/harmony/luni/platform/AdapterManager.<init>()V
(AdapterManager.java:34)
org/apache/harmony/luni/platform/Platform.<clinit>()V (Platform.java:34)
java/io/FileOutputStream.<init>(Ljava/io/FileDescriptor;)V
(FileOutputStream.java:119)
java/lang/System.createErr()Ljava/io/PrintStream; (NULL:-1)
java/lang/System.<clinit>()V (NULL:-1)
java/lang/Thread.<init>(Ljava/lang/ThreadGroup;Ljava/lang/Runnable;Ljava/lang/String;J)V
(NULL:-1)
java/lang/Thread.<init>()V (NULL:-1)

At first I was curious as to why FileInputStream.<clinit> is not in the stack,
but I did bytecode dump and found that Sun's javac 1.5 optimized <init>
methods to include <clinit> code into them. So it included line

private IFileSystem fileSystem = Platform.getFileSystem();

into constructor's code and so the value of IFileSystem FILE_SYSTEM from
Platform was returned. But since Platform.<clinit> is clearly in the stack,
Platform's <clinit> was not finished yet by that time. Dumping bytecode for
compiled Platform shows that line 34 is really the assignment of constant
NETWORK_SYSTEM which turns out to be null later down the stack.

This is a quite fundamental problem with classlib's bootstrap and we don't
have any defined bootstrap sequence. When something is initialized in
<clinit> there is no way to be 100% sure it is really initialized in many
classes which are commonly used because <clinit> is called only once and
bootstrap recursion may get to call some methods of a class before <clinit>
actually completes. The workaround for this is instead of using

   Whatever WHATEVER1 = Something.something();
or

   Whatever WHATEVER2 = new Whatever();

do the following

   method() {
       if (WHATEVER1 == null)
           WHATEVER1 = Something.something();

       if (WHATEVER2 == null)
           WHATEVER2 = new Whatever();
   }

but this is ugly, inefficient and my in theory turn classlib bootstrap into
infinite recursion.

I don't know a general solution for this. The order of class resolution, java
compiler optimizations and other factors may affect the bootstrap sequence.

--
Gregory Shimansky, Intel Middleware Products Division

---------------------------------------------------------------------
Terms of use : http://incubator.apache.org/harmony/mailing.html
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



---------------------------------------------------------------------
Terms of use : http://incubator.apache.org/harmony/mailing.html
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to