Create another class loader for Java5 which overrides getResources() and
use the correct class loader depending on our platform. (FELIX-2569)


git-svn-id: https://svn.apache.org/repos/asf/felix/trunk@999642 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/framework/src/main/java/org/apache/felix/framework/ModuleImpl.java b/framework/src/main/java/org/apache/felix/framework/ModuleImpl.java
index 8d5a173..18ecd24 100644
--- a/framework/src/main/java/org/apache/felix/framework/ModuleImpl.java
+++ b/framework/src/main/java/org/apache/felix/framework/ModuleImpl.java
@@ -155,6 +155,9 @@
     // Thread local to keep track of deferred activation.
     private static final ThreadLocal m_deferredActivation = new ThreadLocal();
 
+    // Flag indicating whether we are on an old JVM or not.
+    private volatile static boolean m_isPreJava5 = false;
+
     /**
      * This constructor is used by the extension manager, since it needs
      * a constructor that does not throw an exception.
@@ -1282,26 +1285,43 @@
     {
         if (m_classLoader == null)
         {
-            if (System.getSecurityManager() != null)
+            // Determine which class loader to use based on which
+            // Java platform we are running on.
+            Class clazz;
+            if (m_isPreJava5)
             {
-                try
-                {
-                    Constructor ctor = (Constructor) m_secureAction.getConstructor(
-                        ModuleClassLoader.class,
-                        new Class[] { ModuleImpl.class, ClassLoader.class });
-                    m_classLoader = (ModuleClassLoader)
-                        m_secureAction.invoke(ctor,
-                        new Object[] { this, determineParentClassLoader() });
-                }
-                catch (Exception ex)
-                {
-                    throw new RuntimeException("Unable to create module class loader: "
-                        + ex.getMessage() + " [" + ex.getClass().getName() + "]");
-                }
+                clazz = ModuleClassLoader.class;
             }
             else
             {
-                m_classLoader = new ModuleClassLoader(determineParentClassLoader());
+                try
+                {
+                    clazz = ModuleClassLoaderJava5.class;
+                }
+                catch (Throwable th)
+                {
+                    // If we are on pre-Java5 then we will get a verify error
+                    // here since we try to override a getResources() which is
+                    // a final method in pre-Java5.
+                    m_isPreJava5 = true;
+                    clazz = ModuleClassLoader.class;
+                }
+            }
+
+            // Use SecureAction to create the class loader if security is
+            // enabled; otherwise, create it directly.
+            try
+            {
+                Constructor ctor = (Constructor) m_secureAction.getConstructor(
+                    clazz, new Class[] { ModuleImpl.class, ClassLoader.class });
+                m_classLoader = (ModuleClassLoader)
+                    m_secureAction.invoke(ctor,
+                    new Object[] { this, determineParentClassLoader() });
+            }
+            catch (Exception ex)
+            {
+                throw new RuntimeException("Unable to create module class loader: "
+                    + ex.getMessage() + " [" + ex.getClass().getName() + "]");
             }
         }
         return m_classLoader;
@@ -1654,6 +1674,24 @@
         m_dexFileClassLoadClass = dexFileClassLoadClass;
     }
 
+    public class ModuleClassLoaderJava5 extends ModuleClassLoader
+    {
+        public ModuleClassLoaderJava5(ClassLoader parent)
+        {
+            super(parent);
+        }
+
+        public Enumeration getResources(String name)
+        {
+            return ModuleImpl.this.getResourcesByDelegation(name);
+        }
+
+        protected Enumeration findResources(String name)
+        {
+            return getResourcesLocal(name);
+        }
+    }
+
     public class ModuleClassLoader extends SecureClassLoader implements BundleReference
     {
         private final Map m_jarContentToDexFile;
diff --git a/framework/src/main/java/org/apache/felix/framework/URLHandlers.java b/framework/src/main/java/org/apache/felix/framework/URLHandlers.java
index d4419c8..e3aa475 100644
--- a/framework/src/main/java/org/apache/felix/framework/URLHandlers.java
+++ b/framework/src/main/java/org/apache/felix/framework/URLHandlers.java
@@ -605,8 +605,8 @@
             if (stack[i].getClassLoader() != null) 
             {
                 String name = stack[i].getClassLoader().getClass().getName();
-                if ("org.apache.felix.framework.ModuleImpl$ModuleClassLoader".equals(name) 
-                    || "org.apache.felix.framework.searchpolicy.ContentClassLoader".equals(name))
+                if (name.startsWith("org.apache.felix.framework.ModuleImpl$ModuleClassLoader")
+                    || name.equals("org.apache.felix.framework.searchpolicy.ContentClassLoader"))
                 {
                     targetClass = stack[i];
                     break;