Created
July 7, 2014 18:12
-
-
Save gissuebot/4cba742aba820605f237 to your computer and use it in GitHub Desktop.
Migrated attachment for Guice issue 343, comment 3
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Index: src/com/google/inject/internal/BytecodeGen.java | |
=================================================================== | |
--- src/com/google/inject/internal/BytecodeGen.java (revision 903) | |
+++ src/com/google/inject/internal/BytecodeGen.java (working copy) | |
@@ -59,8 +59,10 @@ | |
private static final Logger logger = Logger.getLogger(BytecodeGen.class.getName()); | |
- static final ClassLoader GUICE_CLASS_LOADER = BytecodeGen.class.getClassLoader(); | |
+ static final ClassLoader GUICE_CLASS_LOADER = canonicalize(BytecodeGen.class.getClassLoader()); | |
+ static final Object NULL_CLASS_LOADER_KEY = new Object(); | |
+ | |
/** ie. "com.google.inject.internal" */ | |
private static final String GUICE_INTERNAL_PACKAGE | |
= BytecodeGen.class.getName().replaceFirst("\\.internal\\..*$", ".internal"); | |
@@ -82,17 +84,17 @@ | |
end[NO_AOP]*/ | |
/** Use "-Dguice.custom.loader=false" to disable custom classloading. */ | |
- static final boolean HOOK_ENABLED | |
- = "true".equals(System.getProperty("guice.custom.loader", "true")); | |
+ static final String CUSTOM_LOADER_SETTING = System.getProperty("guice.custom.loader", "true"); | |
/** | |
* Weak cache of bridge class loaders that make the Guice implementation | |
* classes visible to various code-generated proxies of client classes. | |
*/ | |
- private static final Map<ClassLoader, ClassLoader> CLASS_LOADER_CACHE | |
+ private static final Map<Object, ClassLoader> CLASS_LOADER_CACHE | |
= new MapMaker().weakKeys().weakValues().makeComputingMap( | |
- new Function<ClassLoader, ClassLoader>() { | |
- public ClassLoader apply(final @Nullable ClassLoader typeClassLoader) { | |
+ new Function<Object, ClassLoader>() { | |
+ public ClassLoader apply(@Nullable Object classLoaderKey) { | |
+ final ClassLoader typeClassLoader = getClassLoaderFromKey(classLoaderKey); | |
logger.fine("Creating a bridge ClassLoader for " + typeClassLoader); | |
return AccessController.doPrivileged(new PrivilegedAction<ClassLoader>() { | |
public ClassLoader run() { | |
@@ -104,28 +106,35 @@ | |
/** | |
* For class loaders, {@code null}, is always an alias to the | |
- * {@link ClassLoader#getSystemClassLoader() system class loader}. This method | |
- * will not return null. | |
+ * {@link ClassLoader#getSystemClassLoader() system class loader}. | |
*/ | |
private static ClassLoader canonicalize(ClassLoader classLoader) { | |
- return classLoader != null | |
- ? classLoader | |
- : checkNotNull(getSystemClassLoaderOrNull(), "Couldn't get a ClassLoader"); | |
- } | |
+ if (classLoader != null) { | |
+ return classLoader; | |
+ } | |
- /** | |
- * Returns the system classloader, or {@code null} if we don't have | |
- * permission. | |
- */ | |
- private static ClassLoader getSystemClassLoaderOrNull() { | |
try { | |
return ClassLoader.getSystemClassLoader(); | |
} catch (SecurityException e) { | |
- return null; | |
+ return null; // unable to canonicalize | |
} | |
} | |
/** | |
+ * Returns a non-null key for the given class loader. | |
+ */ | |
+ private static Object getKeyFromClassLoader(ClassLoader classLoader) { | |
+ return classLoader != null ? classLoader : NULL_CLASS_LOADER_KEY; | |
+ } | |
+ | |
+ /** | |
+ * Returns the class loader related to the given key. | |
+ */ | |
+ private static ClassLoader getClassLoaderFromKey(Object key) { | |
+ return key != NULL_CLASS_LOADER_KEY ? (ClassLoader)key : null; | |
+ } | |
+ | |
+ /** | |
* Returns the class loader to host generated classes for {@code type}. | |
*/ | |
public static ClassLoader getClassLoader(Class<?> type) { | |
@@ -133,10 +142,14 @@ | |
} | |
private static ClassLoader getClassLoader(Class<?> type, ClassLoader delegate) { | |
+ if ("FALSE".equalsIgnoreCase(CUSTOM_LOADER_SETTING)) { | |
+ return delegate; | |
+ } | |
+ | |
delegate = canonicalize(delegate); | |
- // if the application is running in the System classloader, assume we can run there too | |
- if (delegate == getSystemClassLoaderOrNull()) { | |
+ // simple case, we're running in the same class-space | |
+ if (GUICE_CLASS_LOADER == delegate && !"EAGER".equalsIgnoreCase(CUSTOM_LOADER_SETTING)) { | |
return delegate; | |
} | |
@@ -145,8 +158,8 @@ | |
return delegate; | |
} | |
- if (HOOK_ENABLED && Visibility.forType(type) == Visibility.PUBLIC) { | |
- return CLASS_LOADER_CACHE.get(delegate); | |
+ if (Visibility.forType(type) == Visibility.PUBLIC) { | |
+ return CLASS_LOADER_CACHE.get(getKeyFromClassLoader(delegate)); | |
} | |
return delegate; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment