From e0c9b44db93e7b65ce4ce5e16d7a0b9b89b0c39a Mon Sep 17 00:00:00 2001 From: stevenh Date: Fri, 13 May 2011 01:57:00 +0100 Subject: [PATCH] Fixed java plugin class loader so it works with plugins that contain classes also present in other plugins. This also removes the changes from commit 1c4bde50bc12d130f6c8 which was added in order to fix this issue but wasn't ideal as it required plugins to be updated which isnt required with this fix --- .../bukkit/plugin/java/JavaPluginLoader.java | 3 +- .../bukkit/plugin/java/PluginClassLoader.java | 32 ++++++++++++------- .../plugin/java/annotations/DontExport.java | 16 ---------- 3 files changed, 21 insertions(+), 30 deletions(-) delete mode 100644 src/main/java/org/bukkit/plugin/java/annotations/DontExport.java diff --git a/src/main/java/org/bukkit/plugin/java/JavaPluginLoader.java b/src/main/java/org/bukkit/plugin/java/JavaPluginLoader.java index 93eb0f2c..f38b7d1f 100644 --- a/src/main/java/org/bukkit/plugin/java/JavaPluginLoader.java +++ b/src/main/java/org/bukkit/plugin/java/JavaPluginLoader.java @@ -27,7 +27,6 @@ import org.bukkit.event.vehicle.*; import org.bukkit.event.world.*; import org.bukkit.event.weather.*; import org.bukkit.plugin.*; -import org.bukkit.plugin.java.annotations.DontExport; import org.yaml.snakeyaml.error.YAMLException; /** @@ -218,7 +217,7 @@ public final class JavaPluginLoader implements PluginLoader { } public void setClass(final String name, final Class clazz) { - if ((!classes.containsKey(name)) && (clazz.getAnnotation(DontExport.class) != null)) { + if (!classes.containsKey(name)) { classes.put(name, clazz); } } diff --git a/src/main/java/org/bukkit/plugin/java/PluginClassLoader.java b/src/main/java/org/bukkit/plugin/java/PluginClassLoader.java index f998e309..085b2012 100644 --- a/src/main/java/org/bukkit/plugin/java/PluginClassLoader.java +++ b/src/main/java/org/bukkit/plugin/java/PluginClassLoader.java @@ -25,27 +25,35 @@ public class PluginClassLoader extends URLClassLoader { } protected Class findClass(String name, boolean checkGlobal) throws ClassNotFoundException { + // We use the following load order: + // 1. Local first, this avoids IllegalAccessError exceptions for duplicate classes + // 2. Global cache second which prevents ClassCastException's apparently Class result = classes.get(name); - - if (result == null) { - if (checkGlobal) { - result = loader.getClassByName(name); - } - - if (result == null) { + if ( null == result ) { + try { result = super.findClass(name); - - if (result != null) { - loader.setClass(name, result); + classes.put(name, result); + loader.setClass(name, result); + } catch ( ClassNotFoundException e ) { + if ( checkGlobal ) { + result = loader.getClassByName(name); + if ( null == result ) { + // We really couldnt find it + throw new ClassNotFoundException(name); + } + } else { + throw e; // no more options just rethrow } } - - classes.put(name, result); } + // NOTE: setClass already does a not exists check + loader.setClass(name, result); + return result; } + public Set getClasses() { return classes.keySet(); } diff --git a/src/main/java/org/bukkit/plugin/java/annotations/DontExport.java b/src/main/java/org/bukkit/plugin/java/annotations/DontExport.java deleted file mode 100644 index dd6efb9b..00000000 --- a/src/main/java/org/bukkit/plugin/java/annotations/DontExport.java +++ /dev/null @@ -1,16 +0,0 @@ - -package org.bukkit.plugin.java.annotations; - -import java.lang.annotation.ElementType; -import java.lang.annotation.Retention; -import java.lang.annotation.RetentionPolicy; -import java.lang.annotation.Target; - -/** - * Flags a class as private and not to be exported with other plugins - */ -@Target(ElementType.TYPE) -@Retention(RetentionPolicy.RUNTIME) -public @interface DontExport { - -}