8009645: ClassFileTransformer hooks in ClassLoader no longer required
Reviewed-by: mchung, iris
--- a/jdk/src/share/classes/java/lang/ClassLoader.java Fri Mar 08 12:03:26 2013 +0000
+++ b/jdk/src/share/classes/java/lang/ClassLoader.java Fri Mar 08 19:51:09 2013 +0000
@@ -51,7 +51,6 @@
import java.util.Hashtable;
import java.util.WeakHashMap;
import java.util.concurrent.ConcurrentHashMap;
-import sun.misc.ClassFileTransformer;
import sun.misc.CompoundEnumeration;
import sun.misc.Resource;
import sun.misc.URLClassPath;
@@ -669,41 +668,6 @@
return source;
}
- private Class<?> defineTransformedClass(String name, byte[] b, int off, int len,
- ProtectionDomain pd,
- ClassFormatError cfe, String source)
- throws ClassFormatError
- {
- // Class format error - try to transform the bytecode and
- // define the class again
- //
- ClassFileTransformer[] transformers =
- ClassFileTransformer.getTransformers();
- Class<?> c = null;
-
- if (transformers != null) {
- for (ClassFileTransformer transformer : transformers) {
- try {
- // Transform byte code using transformer
- byte[] tb = transformer.transform(b, off, len);
- c = defineClass1(name, tb, 0, tb.length,
- pd, source);
- break;
- } catch (ClassFormatError cfe2) {
- // If ClassFormatError occurs, try next transformer
- }
- }
- }
-
- // Rethrow original ClassFormatError if unable to transform
- // bytecode to well-formed
- //
- if (c == null)
- throw cfe;
-
- return c;
- }
-
private void postDefineClass(Class<?> c, ProtectionDomain pd)
{
if (pd.getCodeSource() != null) {
@@ -783,17 +747,8 @@
throws ClassFormatError
{
protectionDomain = preDefineClass(name, protectionDomain);
-
- Class<?> c = null;
String source = defineClassSourceLocation(protectionDomain);
-
- try {
- c = defineClass1(name, b, off, len, protectionDomain, source);
- } catch (ClassFormatError cfe) {
- c = defineTransformedClass(name, b, off, len, protectionDomain, cfe,
- source);
- }
-
+ Class<?> c = defineClass1(name, b, off, len, protectionDomain, source);
postDefineClass(c, protectionDomain);
return c;
}
@@ -881,20 +836,8 @@
}
protectionDomain = preDefineClass(name, protectionDomain);
-
- Class<?> c = null;
String source = defineClassSourceLocation(protectionDomain);
-
- try {
- c = defineClass2(name, b, b.position(), len, protectionDomain,
- source);
- } catch (ClassFormatError cfe) {
- byte[] tb = new byte[len];
- b.get(tb); // get bytes out of byte buffer.
- c = defineTransformedClass(name, tb, 0, len, protectionDomain, cfe,
- source);
- }
-
+ Class<?> c = defineClass2(name, b, b.position(), len, protectionDomain, source);
postDefineClass(c, protectionDomain);
return c;
}
--- a/jdk/src/share/classes/sun/misc/ClassFileTransformer.java Fri Mar 08 12:03:26 2013 +0000
+++ b/jdk/src/share/classes/sun/misc/ClassFileTransformer.java Fri Mar 08 19:51:09 2013 +0000
@@ -25,43 +25,31 @@
package sun.misc;
import java.util.ArrayList;
+import java.util.List;
/**
- * This is an abstract base class which is called by java.lang.ClassLoader
- * when ClassFormatError is thrown inside defineClass().
- *
- * The purpose of this class is to allow applications (e.g. Java Plug-in)
- * to have a chance to transform the byte code from one form to another
- * if necessary.
- *
- * One application of this class is used by Java Plug-in to transform
- * malformed JDK 1.1 class file into a well-formed Java 2 class file
- * on-the-fly, so JDK 1.1 applets with malformed class file in the
- * Internet may run in Java 2 after transformation.
+ * This is an abstract base class originally intended to be called by
+ * {@code java.lang.ClassLoader} when {@code ClassFormatError} is
+ * thrown inside {@code defineClass()}. It is no longer hooked into
+ * {@code ClassLoader} and will be removed in a future release.
*
* @author Stanley Man-Kit Ho
*/
-public abstract class ClassFileTransformer
-{
- // Singleton of ClassFileTransformer
- //
- private static ArrayList<ClassFileTransformer> transformerList
+@Deprecated
+public abstract class ClassFileTransformer {
+
+ private static final List<ClassFileTransformer> transformers
= new ArrayList<ClassFileTransformer>();
- private static ClassFileTransformer[] transformers
- = new ClassFileTransformer[0];
/**
* Add the class file transformer object.
*
* @param t Class file transformer instance
*/
- public static void add(ClassFileTransformer t)
- {
- synchronized(transformerList)
- {
- transformerList.add(t);
- transformers = transformerList.toArray(new ClassFileTransformer[0]);
+ public static void add(ClassFileTransformer t) {
+ synchronized (transformers) {
+ transformers.add(t);
}
}
@@ -70,13 +58,11 @@
*
* @return ClassFileTransformer object array
*/
- public static ClassFileTransformer[] getTransformers()
- {
- // transformers is not intended to be changed frequently,
- // so it is okay to not put synchronized block here
- // to speed up performance.
- //
- return transformers;
+ public static ClassFileTransformer[] getTransformers() {
+ synchronized (transformers) {
+ ClassFileTransformer[] result = new ClassFileTransformer[transformers.size()];
+ return transformers.toArray(result);
+ }
}
@@ -89,5 +75,5 @@
* @return Transformed byte array
*/
public abstract byte[] transform(byte[] b, int off, int len)
- throws ClassFormatError;
+ throws ClassFormatError;
}