aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMark Wielaard <mark@klomp.org>2005-02-12 13:51:11 +0000
committerMark Wielaard <mark@klomp.org>2005-02-12 13:51:11 +0000
commit0e5088c496ba30087115e4111cd541e155e00caf (patch)
treed1a4c371ccfdcb609926e0a4c67a184227910bb5
parent3644ff70cb67e78fae102a40bed912a8a8862926 (diff)
Fixes bug libgcj/8170
* java/lang/ClassLoader.java (loadClass): Don't rewrap ClassNotFoundException. * gnu/java/lang/MainThread.java (run): Chain NoClassDefFoundError. * gnu/gcj/runtime/NameFinder.java (remove_interpreter): Removed. (remove_internal): New field superceding remove_interpreter. (sanitizeStack): Remove all no-package classes starting with "_Jv_". Remove no-class methods starting with "_Jv_". And Replace null class or method names with the empty string. Stop at either the MainThread or a real Thread run() method. (newElement): Made static. * java/net/URLClassLoader.java (findClass): Throw ClassNotFoundExceptions including urls, plus parent using toString(). (thisString): New field. (toString): New method. git-svn-id: https://gcc.gnu.org/svn/gcc/trunk@94935 138bc75d-0d04-0410-961f-82ee72b054a4
-rw-r--r--libjava/ChangeLog18
-rw-r--r--libjava/gnu/gcj/runtime/NameFinder.java75
-rw-r--r--libjava/gnu/java/lang/MainThread.java4
-rw-r--r--libjava/java/lang/ClassLoader.java15
-rw-r--r--libjava/java/net/URLClassLoader.java41
5 files changed, 110 insertions, 43 deletions
diff --git a/libjava/ChangeLog b/libjava/ChangeLog
index c17af7b7a8c..579ee763451 100644
--- a/libjava/ChangeLog
+++ b/libjava/ChangeLog
@@ -1,3 +1,21 @@
+2005-02-12 Mark Wielaard <mark@klomp.org>
+
+ Fixes bug libgcj/8170
+ * java/lang/ClassLoader.java (loadClass): Don't rewrap
+ ClassNotFoundException.
+ * gnu/java/lang/MainThread.java (run): Chain NoClassDefFoundError.
+ * gnu/gcj/runtime/NameFinder.java (remove_interpreter): Removed.
+ (remove_internal): New field superceding remove_interpreter.
+ (sanitizeStack): Remove all no-package classes starting with "_Jv_".
+ Remove no-class methods starting with "_Jv_". And Replace null
+ class or method names with the empty string. Stop at either the
+ MainThread or a real Thread run() method.
+ (newElement): Made static.
+ * java/net/URLClassLoader.java (findClass): Throw
+ ClassNotFoundExceptions including urls, plus parent using toString().
+ (thisString): New field.
+ (toString): New method.
+
2005-02-10 Tom Tromey <tromey@redhat.com>
* external/sax/Makefile.in: Rebuilt.
diff --git a/libjava/gnu/gcj/runtime/NameFinder.java b/libjava/gnu/gcj/runtime/NameFinder.java
index 024a6eeb232..b14bbf93327 100644
--- a/libjava/gnu/gcj/runtime/NameFinder.java
+++ b/libjava/gnu/gcj/runtime/NameFinder.java
@@ -37,8 +37,8 @@ import java.io.File;
* Whether calls to unknown functions (class and method names are unknown)
* should be removed from the stack trace. Only done when the stack is
* sanitized.</ul>
- * <ul><code>gnu.gcj.runtime.NameFinder.remove_interpreter</code>
- * Whether runtime interpreter calls (methods in the _Jv_InterpMethod class
+ * <ul><code>gnu.gcj.runtime.NameFinder.remove_internal</code>
+ * Whether runtime internal calls (methods in the internal _Jv_* classes
* and functions starting with 'ffi_') should be removed from the stack
* trace. Only done when the stack is sanitized.</ul>
* <ul><code>gnu.gcj.runtime.NameFinder.use_addr2line</code>
@@ -72,10 +72,18 @@ public class NameFinder
= Boolean.valueOf(System.getProperty
("gnu.gcj.runtime.NameFinder.remove_unknown", "true")
).booleanValue();
- private static final boolean remove_interpreter
- = Boolean.valueOf(System.getProperty
+
+ // The remove_interpreter name is an old 3.3/3.4 (deprecated) synonym.
+ private static final boolean remove_internal
+ = (Boolean.valueOf(System.getProperty
+ ("gnu.gcj.runtime.NameFinder.remove_internal", "true")
+ ).booleanValue()
+ ||
+ Boolean.valueOf(System.getProperty
("gnu.gcj.runtime.NameFinder.remove_interpreter", "true")
- ).booleanValue();
+ ).booleanValue()
+ );
+
private static final boolean use_addr2line
= Boolean.valueOf(System.getProperty
("gnu.gcj.runtime.NameFinder.use_addr2line", "true")
@@ -280,7 +288,7 @@ public class NameFinder
consName = className.substring(lastDot + 1) + '(';
int unknown = 0;
- int interpreter = 0;
+ int internal = 0;
int last_throw = -1;
int length = elements.length;
int end = length-1;
@@ -300,19 +308,23 @@ public class NameFinder
|| MName.startsWith("fillInStackTrace("))))
{
last_throw = i;
- // Reset counting of unknown and interpreter frames.
+ // Reset counting of unknown and internal frames.
unknown = 0;
- interpreter = 0;
+ internal = 0;
}
else if (remove_unknown && CName == null
&& (MName == null || MName.startsWith("0x")))
unknown++;
- else if (remove_interpreter
+ else if (remove_internal
&& ((CName == null
&& MName != null && MName.startsWith("ffi_"))
- || (CName != null && CName.equals("_Jv_InterpMethod"))))
- interpreter++;
- else if ("main(java.lang.String[])".equals(MName))
+ || (CName != null && CName.startsWith("_Jv_"))
+ || (CName == null && MName != null
+ && MName.startsWith("_Jv_"))))
+ internal++;
+ else if (("java.lang.Thread".equals(CName)
+ || "gnu.java.lang.MainThread".equals(CName))
+ && "run()".equals(MName))
{
end = i;
break;
@@ -321,11 +333,11 @@ public class NameFinder
int begin = last_throw+1;
// Now filter out everything at the start and the end that is not part
- // of the "normal" user program including any elements that are interpreter
+ // of the "normal" user program including any elements that are internal
// calls or have no usefull information whatsoever.
// Unless that means we filter out all info.
- int nr_elements = end-begin-unknown-interpreter+1;
- if ((begin > 0 || end < length-1 || unknown > 0 || interpreter > 0)
+ int nr_elements = end - begin - unknown - internal + 1;
+ if ((begin > 0 || end < length-1 || unknown > 0 || internal > 0)
&& nr_elements > 0)
{
stack = new StackTraceElement[nr_elements];
@@ -337,14 +349,27 @@ public class NameFinder
if (remove_unknown && CName == null
&& (MName == null || MName.startsWith("0x")))
; // Skip unknown frame
- else if (remove_interpreter
+ else if (remove_internal
&& ((CName == null
- && MName != null && MName.startsWith("ffi_"))
- || (CName != null && CName.equals("_Jv_InterpMethod"))))
- ; // Skip interpreter runtime frame
+ && MName != null && MName.startsWith("ffi_"))
+ || (CName != null && CName.startsWith("_Jv_"))
+ || (CName == null && MName != null
+ && MName.startsWith("_Jv_"))))
+ ; // Skip internal runtime frame
else
{
- stack[pos] = elements[i];
+ // Null Class or Method name in elements are not allowed.
+ if (MName == null || CName == null)
+ {
+ MName = MName == null ? "" : MName;
+ CName = CName == null ? "" : CName;
+ stack[pos] = newElement(elements[i].getFileName(),
+ elements[i].getLineNumber(),
+ CName, MName,
+ elements[i].isNativeMethod());
+ }
+ else
+ stack[pos] = elements[i];
pos++;
}
}
@@ -359,11 +384,11 @@ public class NameFinder
* Native helper method to create a StackTraceElement. Needed to work
* around normal Java access restrictions.
*/
- native private StackTraceElement newElement(String fileName,
- int lineNumber,
- String className,
- String methName,
- boolean isNative);
+ native static private StackTraceElement newElement(String fileName,
+ int lineNumber,
+ String className,
+ String methName,
+ boolean isNative);
/**
* Creates a StackTraceElement given a string and a filename.
diff --git a/libjava/gnu/java/lang/MainThread.java b/libjava/gnu/java/lang/MainThread.java
index 5937b870d3e..14a00ca8d9b 100644
--- a/libjava/gnu/java/lang/MainThread.java
+++ b/libjava/gnu/java/lang/MainThread.java
@@ -95,7 +95,9 @@ final class MainThread extends Thread
}
catch (ClassNotFoundException x)
{
- throw new NoClassDefFoundError(klass_name);
+ NoClassDefFoundError ncdfe = new NoClassDefFoundError(klass_name);
+ ncdfe.initCause(x);
+ throw ncdfe;
}
}
diff --git a/libjava/java/lang/ClassLoader.java b/libjava/java/lang/ClassLoader.java
index 71f41c1cf1b..46e523c6834 100644
--- a/libjava/java/lang/ClassLoader.java
+++ b/libjava/java/lang/ClassLoader.java
@@ -288,8 +288,6 @@ public abstract class ClassLoader
if (c != null)
return c;
- ClassNotFoundException ex = null;
-
// Can the class be loaded by a parent?
try
{
@@ -306,20 +304,9 @@ public abstract class ClassLoader
}
catch (ClassNotFoundException e)
{
- ex = e;
}
// Still not found, we have to do it ourself.
- try
- {
- c = findClass(name);
- }
- catch (ClassNotFoundException cause)
- {
- if (ex != null)
- throw new ClassNotFoundException(ex.toString(), cause);
- else
- throw cause;
- }
+ c = findClass(name);
if (resolve)
resolveClass(c);
return c;
diff --git a/libjava/java/net/URLClassLoader.java b/libjava/java/net/URLClassLoader.java
index 3efc5dca76f..0da6a0356b2 100644
--- a/libjava/java/net/URLClassLoader.java
+++ b/libjava/java/net/URLClassLoader.java
@@ -1,5 +1,6 @@
/* URLClassLoader.java -- ClassLoader that loads classes from one or more URLs
- Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005
+ Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -958,7 +959,7 @@ public class URLClassLoader extends SecureClassLoader
resource = loader.getResource(resourceName);
}
if (resource == null)
- throw new ClassNotFoundException(className + " not found in " + urls);
+ throw new ClassNotFoundException(className + " not found in " + this);
// Try to read the class data, create the CodeSource, Package and
// construct the class (and watch out for those nasty IOExceptions)
@@ -1039,9 +1040,43 @@ public class URLClassLoader extends SecureClassLoader
}
catch (IOException ioe)
{
- throw new ClassNotFoundException(className, ioe);
+ ClassNotFoundException cnfe;
+ cnfe = new ClassNotFoundException(className + " not found in " + this);
+ cnfe.initCause(ioe);
+ throw cnfe;
}
}
+
+ // Cached String representation of this URLClassLoader
+ private String thisString;
+
+ /**
+ * Returns a String representation of this URLClassLoader giving the
+ * actual Class name, the URLs that are searched and the parent
+ * ClassLoader.
+ */
+ public String toString()
+ {
+ if (thisString == null)
+ {
+ StringBuffer sb = new StringBuffer();
+ sb.append(this.getClass().getName());
+ sb.append("{urls=[" );
+ URL[] thisURLs = getURLs();
+ for (int i = 0; i < thisURLs.length; i++)
+ {
+ sb.append(thisURLs[i]);
+ if (i < thisURLs.length - 1)
+ sb.append(',');
+ }
+ sb.append(']');
+ sb.append(", parent=");
+ sb.append(getParent());
+ sb.append('}');
+ thisString = sb.toString();
+ }
+ return thisString;
+ }
/**
* Finds the first occurrence of a resource that can be found. The locations