This is the mail archive of the java-patches@gcc.gnu.org mailing list for the Java project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [BC ABI] For entertainment purposes only: gcj-JIT


Andrew> OK, as long as it's still convenient.  You want to be able to set this
Andrew> up in some sensible global way and then forget about ti.

Yeah, that's no problem.  Properties are even nicer since you also
have the option of setting them at link time.  I've got a patch here
to do this and some other minor cleanups I wanted; I'm waiting for
some comments on the VMCompiler thing first (on classpath-patches),
but meanwhile here it is.

One of my big goals here was to ensure ClassLoader remained identical
to Classpath.  There's no need for it to diverge.  (There is still a
divergence after this patch, but that change will either be removed or
put into Classpath -- it is generic.)

I also removed the "verbose" class loading stuff, as that is already
done differently on the trunk.

Tom

Index: gcc/java/ChangeLog
from  Tom Tromey  <tromey@redhat.com>

	* gcj.texi (libgcj Runtime Properties): Document new properties.

Index: gcc/java/gcj.texi
===================================================================
RCS file: /cvs/gcc/gcc/gcc/java/gcj.texi,v
retrieving revision 1.61
diff -u -r1.61 gcj.texi
--- gcc/java/gcj.texi 23 Mar 2004 17:49:22 -0000 1.61
+++ gcc/java/gcj.texi 11 Aug 2004 23:28:23 -0000
@@ -2310,6 +2310,24 @@
 and not tried again.  If this property is set to @samp{never}, then
 lookups are never done.  For more information, @xref{Extensions}.
 
+@item gnu.gcj.jit.compiler
+@c FIXME we should probably have a whole node on this...
+This is the full path to @command{gcj} executable which should be
+used to compile classes just-in-time when
+@code{ClassLoader.defineClass} is called.  If not set, @command{gcj}
+will not be invoked by the runtime; this can also be controlled via
+@code{Compiler.disable}.
+
+@item gnu.gcj.jit.options
+This is a space-separated string of options which should be passed to
+@command{gcj} when in JIT mode.  If not set, a sensible default is
+chosen.
+
+@item gnu.gcj.jit.cachedir
+This is the directory where cached shared library files are
+stored.  If not set, JIT compilation is disabled.  This should never
+be set to a directory that is writable by any other user.
+
 @end table
 
 
Index: libjava/ChangeLog
from  Tom Tromey  <tromey@redhat.com>

	* gcj/javaprims.h: Regenerated.
	* java/lang/natClassLoader.cc (getClassLoader0): Removed.
	(_registerClass): Likewise.
	* Makefile.in: Rebuilt.
	* Makefile.am (core_java_source_files): Added VMCompiler.
	* java/lang/Compiler.java: Rewrote in terms of VMCompiler.
	* java/lang/VMCompiler.java: New file.
	* gnu/gcj/runtime/SharedLibHelper.java (findClass): Removed
	`verbose' code.
	(copyFile): Don't use fully-qualified name.
	(h): Removed.
	* java/lang/natVMClassLoader.cc: Include VMCompiler.h.
	(defineClass): Use VMCompiler.
	* java/lang/ClassLoader.java (defineClass): Removed jit
	compilation code and `verbose' code.
	(getClassLoader0): Removed.
	(_registerClass): Likewise.
	(SharedLibHelpers): Removed.

Index: libjava/Makefile.am
===================================================================
RCS file: /cvs/gcc/gcc/libjava/Makefile.am,v
retrieving revision 1.368.2.3
diff -u -r1.368.2.3 Makefile.am
--- libjava/Makefile.am 10 Aug 2004 18:00:17 -0000 1.368.2.3
+++ libjava/Makefile.am 11 Aug 2004 23:28:26 -0000
@@ -2043,6 +2043,7 @@
 java/lang/VerifyError.java \
 java/lang/VirtualMachineError.java \
 java/lang/VMClassLoader.java \
+java/lang/VMCompiler.java \
 java/lang/VMSecurityManager.java \
 java/lang/VMThrowable.java \
 java/lang/Void.java \
Index: libjava/gcj/javaprims.h
===================================================================
RCS file: /cvs/gcc/gcc/libjava/gcj/javaprims.h,v
retrieving revision 1.48.12.1
diff -u -r1.48.12.1 javaprims.h
--- libjava/gcj/javaprims.h 20 Apr 2004 21:59:38 -0000 1.48.12.1
+++ libjava/gcj/javaprims.h 11 Aug 2004 23:28:28 -0000
@@ -1,6 +1,6 @@
 // javaprims.h - Main external header file for libgcj.  -*- c++ -*-
 
-/* Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003  Free Software Foundation
+/* Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004  Free Software Foundation
 
    This file is part of libgcj.
 
@@ -83,6 +83,7 @@
       class LineNumberInputStream;
       class LineNumberReader;
       class MemberComparator;
+      class MyIOException;
       class NotActiveException;
       class NotSerializableException;
       class ObjectInput;
@@ -211,6 +212,7 @@
       class UnsupportedClassVersionError;
       class UnsupportedOperationException;
       class VMClassLoader;
+      class VMCompiler;
       class VMSecurityManager;
       class VMThrowable;
       class VerifyError;
Index: libjava/gnu/gcj/runtime/SharedLibHelper.java
===================================================================
RCS file: /cvs/gcc/gcc/libjava/gnu/gcj/runtime/SharedLibHelper.java,v
retrieving revision 1.1.32.3
diff -u -r1.1.32.3 SharedLibHelper.java
--- libjava/gnu/gcj/runtime/SharedLibHelper.java 5 Aug 2004 17:39:07 -0000 1.1.32.3
+++ libjava/gnu/gcj/runtime/SharedLibHelper.java 11 Aug 2004 23:28:28 -0000
@@ -1,4 +1,4 @@
-/* Copyright (C) 2001, 2003  Free Software Foundation
+/* Copyright (C) 2001, 2003, 2004  Free Software Foundation
 
    This file is part of libgcj.
 
@@ -16,14 +16,12 @@
 import java.util.Set;
 import java.util.Iterator;
 import java.util.HashSet;
+import java.util.HashMap;
 import java.nio.channels.FileChannel;
 import java.io.*;
 
 public class SharedLibHelper
 {
-   private final java.util.HashMap h = 
-     new java.util.HashMap();
-
   /** Load a shared library, and associate a ClassLoader with it.
    * @param libname named of shared library (passed to dlopen)
    * @param parent the parent ClassLoader
@@ -57,7 +55,7 @@
       }
   }
 
-  static void copyFile (File in, File out) throws java.io.IOException 
+  static void copyFile (File in, File out) throws IOException 
   {
     FileChannel source = new FileInputStream(in).getChannel();
     FileChannel destination = new FileOutputStream(out).getChannel();
@@ -129,19 +127,7 @@
   public Class findClass(String name)
   {
     ensureInit();
-    Class c = (Class)classMap.get(name);
-    if (c != null)
-      {
-	String s = System.getProperty("gnu.classpath.verbose");
-	if (s != null && s.equals("class"))
-	  if (h.get(name) == null)
-	    {
-	      System.err.println("[Loading class " + name 
-				 + " from " + this + "]");
-	      h.put(name,name);
-	    }		
-      }
-    return c;
+    return (Class) classMap.get(name);
   }
 
   public URL findResource (String name)
Index: libjava/java/lang/ClassLoader.java
===================================================================
RCS file: /cvs/gcc/gcc/libjava/java/lang/ClassLoader.java,v
retrieving revision 1.31.18.3
diff -u -r1.31.18.3 ClassLoader.java
--- libjava/java/lang/ClassLoader.java 5 Aug 2004 17:39:06 -0000 1.31.18.3
+++ libjava/java/lang/ClassLoader.java 11 Aug 2004 23:28:29 -0000
@@ -1,5 +1,5 @@
 /* ClassLoader.java -- responsible for loading classes into the VM
-   Copyright (C) 1998, 1999, 2001, 2002, 2003 Free Software Foundation, Inc.
+   Copyright (C) 1998, 1999, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
 
 This file is part of GNU Classpath.
 
@@ -40,9 +40,7 @@
 
 import gnu.java.util.DoubleEnumeration;
 import gnu.java.util.EmptyEnumeration;
-import gnu.gcj.runtime.SharedLibHelper;
 
-import java.io.File;
 import java.io.IOException;
 import java.io.InputStream;
 import java.net.URL;
@@ -52,10 +50,8 @@
 import java.security.ProtectionDomain;
 import java.util.Enumeration;
 import java.util.HashMap;
-import java.util.IdentityHashMap;
 import java.util.Map;
 
-
 /**
  * The ClassLoader is a way of customizing the way Java gets its classes
  * and loads them into memory.  The verifier and other standard Java things
@@ -213,9 +209,6 @@
   // Package visible for use by Class.
   Map classAssertionStatus;
 
-  // All our SharedLibHelpers: when we get gc'd, so do they.
-  Map SharedLibHelpers = new IdentityHashMap();
-
   /**
    * Create a new ClassLoader with as parent the system classloader. There
    * may be a security check for <code>checkCreateClassLoader</code>.
@@ -456,116 +449,8 @@
     if (! initialized)
       throw new SecurityException("attempt to define class from uninitialized class loader");
     
-    Class retval = null;
-
-    String gcjJitCompiler = System.getenv0 ("GCJ_JIT_COMPILER");
-    if (gcjJitCompiler != null)
-      {
-      compile:
-	try
-	  {
-	    // FIXME: Make sure that the class represented by the
-	    // bytes in DATA really is the class named in NAME.  Make
-	    // sure it's not "java.*".
-	    java.security.MessageDigest md = java.security.MessageDigest.getInstance("MD5");
-	    byte digest[] = md.digest(data);
-	    String tmpdir = System.getenv0("GCJ_JIT_TMPDIR");
-	    if (tmpdir == null)
-	      tmpdir = "/tmp";
-	    StringBuffer hexBytes = new StringBuffer(tmpdir);
-	    hexBytes.append("/");
-	    int digestLength = digest.length;
-	    for (int i=0; i<digestLength; i++)
-	      hexBytes.append(Integer.toHexString(digest[i]&0xff));
-	    StringBuffer fileName = new StringBuffer(hexBytes.toString());
-	    fileName.append(".so");
-	    File soFile = new File (fileName.toString());
-	    if (soFile.isFile())
-	      {
-		Class c = null;
-		SharedLibHelper helper 
-		  = SharedLibHelper.findHelper (this, fileName.toString(),
-						domain.getCodeSource());
-		c = helper.findClass (name);
-		if (c != null)
-		  {
-		    SharedLibHelpers.put(helper,c);
-		    retval = c;
-		    _registerClass(retval);
-		    break compile;
-		  }
-	      }
-	    File classFile = new File(hexBytes+".class");
-	    classFile.delete();
-	    if (classFile.createNewFile() != true)	  
-	      throw new IOException ();
-	    java.io.FileOutputStream f = new java.io.FileOutputStream (classFile);
-	    byte[] b = new byte[len];
-	    System.arraycopy(data,offset,b,0,len);
-	    f.write(b);
-	
-	    StringBuffer command = new StringBuffer(gcjJitCompiler);
-	    command.append(" ");
-	    command.append(classFile);
-	    command.append(" ");
-	    String opts = System.getenv0("GCJ_JIT_OPTIONS");
-	    if (opts != null)
-	      command.append(opts);
-	    command.append(" -g -findirect-dispatch -shared -fPIC -o ");
-	    command.append(fileName);
-	    Process p = Runtime.getRuntime().exec(command.toString());
-	    StringBuffer err = new StringBuffer();
-	    {
-	      InputStream stderr = p.getErrorStream();
-	      int ch;
-	      // FIXME: We need a much better way to handle error output
-	      // from the compiler.
-	      while ((ch = stderr.read()) != -1)
-		err.append((char)ch);
-	    }
-	    if (p.waitFor() != 0)
-	      {
-		System.err.println(err.toString());
-		throw new IOException ();
-	      }
-	    {
-	      Class c = null;
-	      SharedLibHelper helper 
-		= SharedLibHelper.findHelper (this, fileName.toString(), 
-					      domain.getCodeSource());
-	      c = helper.findClass (name);
-	      if (c != null)
-		{
-		  SharedLibHelpers.put(helper,c);
-		  retval = c;
-		  _registerClass(retval);
-		}	
-	    }
-	  }
-	catch (Exception _)
-	  {
-	  }
-      }
-    
-    if (retval == null)
-      retval = VMClassLoader.defineClass(this, name, data,
-					 offset, len, domain);
-
-    {	    
-      String s = System.getProperty("gnu.classpath.verbose");
-      if (s != null && s.equals("class"))
-	{
-	  java.security.CodeSource source = domain.getCodeSource();
-	  java.net.URL url = source != null ? source.getLocation() : null;
-	  String URLname = url != null ? url.toString() : null;
-	  if (URLname == null)
-	    URLname = "unknown location";
-	  System.err.println("[Loading class " + retval.getName()
-			     + " from  " + URLname + "]");
-	}
-		
-    }
-
+    Class retval = VMClassLoader.defineClass(this, name, data,
+					     offset, len, domain);
     loadedClasses.put(retval.getName(), retval);
     return retval;
   }
@@ -858,7 +743,7 @@
     if (sm != null)
       {
 	Class c = VMSecurityManager.getClassContext()[1];
-	ClassLoader cl = getClassLoader0(c);
+	ClassLoader cl = c.getClassLoader();
 	if (cl != null && cl != systemClassLoader)
 	  sm.checkPermission(new RuntimePermission("getClassLoader"));
       }
@@ -1079,8 +964,4 @@
       }
     return false;
   }
-
-    static private final native ClassLoader getClassLoader0(Class c);
-
-    private final native void _registerClass(Class c);
 }
Index: libjava/java/lang/Compiler.java
===================================================================
RCS file: /cvs/gcc/gcc/libjava/java/lang/Compiler.java,v
retrieving revision 1.6.66.1
diff -u -r1.6.66.1 Compiler.java
--- libjava/java/lang/Compiler.java 20 May 2004 23:34:03 -0000 1.6.66.1
+++ libjava/java/lang/Compiler.java 11 Aug 2004 23:28:29 -0000
@@ -1,5 +1,5 @@
 /* Compiler.java -- placeholder for Java-to-native runtime compilers
-   Copyright (C) 1998, 1999, 2001, 2002 Free Software Foundation, Inc.
+   Copyright (C) 1998, 1999, 2001, 2002, 2004 Free Software Foundation, Inc.
 
 This file is part of GNU Classpath.
 
@@ -76,8 +76,7 @@
    */
   public static boolean compileClass(Class oneClass)
   {
-    // Never succeed.
-    return false;
+    return VMCompiler.compileClass(oneClass);
   }
 
   /**
@@ -90,8 +89,7 @@
    */
   public static boolean compileClasses(String classNames)
   {
-    // Note the incredibly lame interface.  Always fail.
-    return false;
+    return VMCompiler.compileClasses(classNames);
   }
 
   /**
@@ -105,8 +103,7 @@
    */
   public static Object command(Object arg)
   {
-    // Our implementation defines this to a no-op.
-    return null;
+    return VMCompiler.command(arg);
   }
 
   /**
@@ -116,6 +113,7 @@
    */
   public static void enable()
   {
+    VMCompiler.enable();
   }
 
   /**
@@ -124,5 +122,6 @@
    */
   public static void disable()
   {
+    VMCompiler.disable();
   }
 }
Index: libjava/java/lang/VMCompiler.java
===================================================================
RCS file: libjava/java/lang/VMCompiler.java
diff -N libjava/java/lang/VMCompiler.java
--- /dev/null	1 Jan 1970 00:00:00 -0000
+++ libjava/java/lang/VMCompiler.java 11 Aug 2004 23:28:29 -0000
@@ -0,0 +1,257 @@
+/* VMClassLoader.java -- Reference implementation of compiler interface
+   Copyright (C) 2004 Free Software Foundation
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING.  If not, write to the
+Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+02111-1307 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library.  Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module.  An independent module is a module which is not derived from
+or based on this library.  If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so.  If you do not wish to do so, delete this
+exception statement from your version. */
+
+package java.lang;
+
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.InputStreamReader;
+import java.security.MessageDigest;
+import java.security.ProtectionDomain;
+import java.util.WeakHashMap;
+import java.util.HashSet;
+import gnu.gcj.runtime.SharedLibHelper;
+
+/**
+ * This class is just a per-VM reflection of java.lang.Compiler.
+ * All methods are defined identically.
+ */
+final class VMCompiler
+{
+  // True if we want to use gcj-jit.
+  public static boolean useCompiler = true;
+
+  // True if we're able to use gcj-jit.
+  public static final boolean canUseCompiler;
+
+  // Compiler to use.
+  public static String gcjJitCompiler;
+
+  // Compiler options.
+  public static String gcjJitCompilerOptions;
+
+  // Temporary directory to use.
+  public static String gcjJitTmpdir;
+
+  // This maps a ClassLoader to a set of SharedLibHelper objects that
+  // it has used.  We do things this way to ensure that a
+  // SharedLibHelper is collected if and only if the ClassLoader is.
+  private static WeakHashMap sharedHelperMap = new WeakHashMap();
+
+  static
+  {
+    gcjJitCompiler = System.getProperty("gnu.gcj.jit.compiler");
+    if (gcjJitCompiler == null)
+      canUseCompiler = false;
+    else
+      {
+	gcjJitCompilerOptions = System.getProperty("gnu.gcj.jit.options",
+						   "-g");
+	gcjJitTmpdir = System.getProperty("gnu.gcj.jit.cachedir");
+	// Note that we *don't* choose java.io.tmpdir as a default --
+	// that would allow easy attacks against the VM.
+	if (gcjJitTmpdir == null)
+	  canUseCompiler = false;
+	else
+	  canUseCompiler = true;
+      }
+  }
+
+  /**
+   * Don't allow new `Compiler's to be made.
+   */
+  private VMCompiler()
+  {
+  }
+
+  private static Class loadSharedLibrary(ClassLoader loader,
+					 String fileName,
+					 ProtectionDomain domain)
+  {
+    Class c = null;
+    SharedLibHelper helper 
+      = SharedLibHelper.findHelper (loader, fileName, domain.getCodeSource());
+    c = helper.findClass (fileName);
+    if (c != null)
+      {
+	HashSet hs = (HashSet) sharedHelperMap.get(loader);
+	if (hs == null)
+	  {
+	    hs = new HashSet();
+	    sharedHelperMap.put(loader, hs);
+	  }
+	hs.add(helper);
+      }
+    return c;
+  }
+
+  /**
+   * Compile a class given the bytes for it.  Returns the Class, or
+   * null if compilation failed or otherwise could not be done.
+   */
+  public static Class compileClass(ClassLoader loader,
+				   String name, byte[] data,
+				   int offset, int len,
+				   ProtectionDomain domain)
+  {
+    if (! useCompiler || ! canUseCompiler)
+      return null;
+
+    try
+      {
+	// FIXME: Make sure that the class represented by the
+	// bytes in DATA really is the class named in NAME.  Make
+	// sure it's not "java.*".
+	MessageDigest md = MessageDigest.getInstance("MD5");
+	byte digest[] = md.digest(data);
+	StringBuffer hexBytes = new StringBuffer(gcjJitTmpdir);
+	hexBytes.append(File.separatorChar);
+	int digestLength = digest.length;
+	for (int i = 0; i < digestLength; ++i)
+	  hexBytes.append(Integer.toHexString(digest[i] & 0xff));
+
+	// FIXME: use System.mapLibraryName?
+	// I'm thinking we should use that, plus a class specified
+	// via a property that determines lookup policy.
+	File soFile = new File(hexBytes + ".so");
+	if (soFile.isFile())
+	  return loadSharedLibrary (loader, soFile.toString(), domain);
+
+	File classFile = new File(hexBytes + ".class");
+	classFile.delete();
+	if (classFile.createNewFile() != true)	  
+	  return null;
+
+	FileOutputStream f = new FileOutputStream (classFile);
+	// FIXME: race condition if bytes change... ?
+	f.write(data, offset, len);
+
+	// Invoke the compiler.
+	StringBuffer command = new StringBuffer(gcjJitCompiler);
+	command.append(" ");
+	command.append(classFile);
+	command.append(" ");
+	command.append(gcjJitCompilerOptions);
+	// These options are required.
+	command.append(" -findirect-dispatch -fjni -shared -fPIC -o ");
+	command.append(soFile);
+	Process p = Runtime.getRuntime().exec(command.toString());
+
+	// Read the process' stderr into a string.
+	StringBuffer err = new StringBuffer();
+	InputStreamReader stderr = new InputStreamReader (p.getErrorStream());
+	char[] inBuf = new char[500];
+	int bytesRead;
+	while ((bytesRead = stderr.read (inBuf)) != -1)
+	  err.append(inBuf, 0, bytesRead);
+
+	if (p.waitFor() != 0)
+	  {
+	    // FIXME: we could log err.toString() somewhere...
+	    return null;
+	  }
+
+	return loadSharedLibrary(loader, soFile.toString(), domain);
+      }
+    catch (Exception _)
+      {
+	return null;
+      }
+  }
+
+  /**
+   * Compile the class named by <code>oneClass</code>.
+   *
+   * @param oneClass the class to compile
+   * @return <code>false</code> if no compiler is available or
+   *         compilation failed, <code>true</code> if compilation succeeded
+   * @throws NullPointerException if oneClass is null
+   */
+  public static boolean compileClass(Class oneClass)
+  {
+    // Never succeed.
+    return false;
+  }
+
+  /**
+   * Compile the classes whose name matches <code>classNames</code>.
+   *
+   * @param classNames the name of classes to compile
+   * @return <code>false</code> if no compiler is available or
+   *         compilation failed, <code>true</code> if compilation succeeded
+   * @throws NullPointerException if classNames is null
+   */
+  public static boolean compileClasses(String classNames)
+  {
+    // Note the incredibly lame interface.  Always fail.
+    return false;
+  }
+
+  /**
+   * This method examines the argument and performs an operation
+   * according to the compilers documentation.  No specific operation
+   * is required.
+   *
+   * @param arg a compiler-specific argument
+   * @return a compiler-specific value, including null
+   * @throws NullPointerException if the compiler doesn't like a null arg
+   */
+  public static Object command(Object arg)
+  {
+    // Our implementation defines this to a no-op.
+    return null;
+  }
+
+  /**
+   * Calling <code>Compiler.enable()</code> will cause the compiler
+   * to resume operation if it was previously disabled; provided that a
+   * compiler even exists.
+   */
+  public static void enable()
+  {
+    useCompiler = true;
+  }
+
+  /**
+   * Calling <code>Compiler.disable()</code> will cause the compiler
+   * to be suspended; provided that a compiler even exists.
+   */
+  public static void disable()
+  {
+    useCompiler = false;
+  }
+}
Index: libjava/java/lang/natClassLoader.cc
===================================================================
RCS file: /cvs/gcc/gcc/libjava/java/lang/natClassLoader.cc,v
retrieving revision 1.64.8.3
diff -u -r1.64.8.3 natClassLoader.cc
--- libjava/java/lang/natClassLoader.cc 5 Aug 2004 17:42:58 -0000 1.64.8.3
+++ libjava/java/lang/natClassLoader.cc 11 Aug 2004 23:28:29 -0000
@@ -582,19 +582,6 @@
   element->arrayclass = array_class;
 }
 
-// Return the true ClassLoader for a class, without doing security checks
-::java::lang::ClassLoader *
-::java::lang::ClassLoader::getClassLoader0 (::java::lang::Class *c)
-{
-  return c->loader;
-}
-
-void
-::java::lang::ClassLoader::_registerClass (::java::lang::Class *c)
-{
-  _Jv_RegisterClass (c);
-}
-
 static jclass stack_head;
 
 // These two functions form a stack of classes.   When a class is loaded
Index: libjava/java/lang/natVMClassLoader.cc
===================================================================
RCS file: /cvs/gcc/gcc/libjava/java/lang/natVMClassLoader.cc,v
retrieving revision 1.1.18.1
diff -u -r1.1.18.1 natVMClassLoader.cc
--- libjava/java/lang/natVMClassLoader.cc 20 Apr 2004 21:59:40 -0000 1.1.18.1
+++ libjava/java/lang/natVMClassLoader.cc 11 Aug 2004 23:28:29 -0000
@@ -22,6 +22,7 @@
 #include <java-interp.h>
 
 #include <java/lang/VMClassLoader.h>
+#include <java/lang/VMCompiler.h>
 #include <gnu/gcj/runtime/VMClassLoader.h>
 #include <java/lang/ClassLoader.h>
 #include <java/lang/Class.h>
@@ -37,58 +38,64 @@
 					jint length,
 					java::security::ProtectionDomain *pd)
 {
-#ifdef INTERPRETER
-  jclass klass;
-  klass = new java::lang::Class ();
-  klass->aux_info = (void *) _Jv_AllocBytes (sizeof (_Jv_InterpClass));
-
-  // Synchronize on the class, so that it is not attempted initialized
-  // until we're done loading.
-  JvSynchronize sync (klass);
-
-  // Record the defining loader.  For the system class loader, we
-  // record NULL.
-  if (loader != java::lang::ClassLoader::getSystemClassLoader())
-    klass->loader = loader;
-
-  if (name != 0)
-    {
-      _Jv_Utf8Const *name2 = _Jv_makeUtf8Const (name);
-
-      if (! _Jv_VerifyClassName (name2))
-	throw new java::lang::ClassFormatError
-	  (JvNewStringLatin1 ("erroneous class name"));
-
-      klass->name = name2;
-    }
+  jclass klass = VMCompiler::compileClass(loader, name, data,
+					  offset, length, pd);
 
-  try
+  if (klass != NULL)
     {
-      _Jv_DefineClass (klass, data, offset, length);
+      JvSynchronize sync (&java::lang::Class::class$);
+      _Jv_RegisterClass (klass);
     }
-  catch (java::lang::Throwable *ex)
+#ifdef INTERPRETER
+  else
     {
-      klass->state = JV_STATE_ERROR;
-      klass->notifyAll ();
+      klass = new java::lang::Class ();
+      klass->aux_info = (void *) _Jv_AllocBytes (sizeof (_Jv_InterpClass));
 
-      _Jv_UnregisterClass (klass);
+      // Synchronize on the class, so that it is not attempted initialized
+      // until we're done loading.
+      JvSynchronize sync (klass);
+
+      // Record the defining loader.  For the system class loader, we
+      // record NULL.
+      if (loader != java::lang::ClassLoader::getSystemClassLoader())
+	klass->loader = loader;
+
+      if (name != 0)
+	{
+	  _Jv_Utf8Const *name2 = _Jv_makeUtf8Const (name);
+
+	  if (! _Jv_VerifyClassName (name2))
+	    throw new java::lang::ClassFormatError
+	      (JvNewStringLatin1 ("erroneous class name"));
+
+	  klass->name = name2;
+	}
+
+      try
+	{
+	  _Jv_DefineClass (klass, data, offset, length);
+	}
+      catch (java::lang::Throwable *ex)
+	{
+	  klass->state = JV_STATE_ERROR;
+	  klass->notifyAll ();
+
+	  _Jv_UnregisterClass (klass);
+
+	  // If EX is not a ClassNotFoundException, that's ok, because we
+	  // account for the possibility in defineClass().
+	  throw ex;
+	}
 
-      // If EX is not a ClassNotFoundException, that's ok, because we
-      // account for the possibility in defineClass().
-      throw ex;
-    }
-    
-  klass->protectionDomain = pd;
+      klass->protectionDomain = pd;
 
-  // if everything proceeded sucessfully, we're loaded.
-  JvAssert (klass->state == JV_STATE_LOADED);
+      // if everything proceeded sucessfully, we're loaded.
+      JvAssert (klass->state == JV_STATE_LOADED);
+    }
+#endif // INTERPRETER
 
   return klass;
-
-#else // INTERPRETER
-
-  return 0;
-#endif
 }
 
 // Finish linking a class.  Only called from ClassLoader::resolveClass.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]