ClassLoader.getParent to throw exception for module classloader

David Holmes david.holmes at oracle.com
Thu Jun 21 17:00:11 PDT 2012


On 22/06/2012 2:03 AM, Paul Sandoz wrote:
> Hi,
>
> http://cr.openjdk.java.net/~psandoz/jigsaw/classloader-getparent/webrev/
>
> In a off-list discussion there was a side comment about making ClassLoader.getParent throwing an exception for a module class loader. This type of thing is easy to loose so marking this down in email.

So that would seem to have far-reaching consequences on various bits of 
code that check the classloader hierarchy to determine when they need to 
do security manager checks.

This leaves me wondering how custom classloaders fit into this world - 
do they have a parent that is a module loader?

David
-----

> This patch results in the failure of:
>
>    jdk/test/org/openjdk/jigsaw/optional-jaxp.sh
>
> See below for the exception in Xerces. The code below is  incorrect for module mode because it assumes a hierarchical delegation model. In com.sun.org.apache.xerces.internal.utils.ObjectFactory.findClassLoader:
>
>          ClassLoader context = SecuritySupport.getContextClassLoader();
>          ClassLoader system = SecuritySupport.getSystemClassLoader();
>
>          ClassLoader chain = system;
>          while (true) {
>              if (context == chain) {
>                  // Assert: we are on JDK 1.1 or we have no Context ClassLoader
>                  // or any Context ClassLoader in chain of system classloader
>                  // (including extension ClassLoader) so extend to widest
>                  // ClassLoader (always look in system ClassLoader if Xerces
>                  // is in boot/extension/system classpath and in current
>                  // ClassLoader otherwise); normal classloaders delegate
>                  // back to system ClassLoader first so this widening doesn't
>                  // change the fact that context ClassLoader will be consulted
>                  ClassLoader current = ObjectFactory.class.getClassLoader();
>
>                  chain = system;
>                  while (true) {
>                      if (current == chain) {
>                          // Assert: Current ClassLoader in chain of
>                          // boot/extension/system ClassLoaders
>                          return system;
>                      }
>                      if (chain == null) {
>                          break;
>                      }
>                      chain = SecuritySupport.getParentClassLoader(chain);
>                  }
>
>                  // Assert: Current ClassLoader not in chain of
>                  // boot/extension/system ClassLoaders
>                  return current;
>              }
>
> When ClassLoader.getParent() returns null in module mode it luckily works for the case of loading a class from within the JAXP module itself.
>
> This area of Xerces may need to be cleaned up to use ServiceLoader.
>
> In this respect the exception actually signaled the potential location of the issue that would of otherwise been hidden and trickier to find. However, the approach of throwing an exception does seem brutal. If an XML parser library is barfing, what else will?
>
> Paul.
>
> Exception in thread "main" java.lang.IllegalStateException: A module class loader does not support the hierarchical delegation mode and has no parent.
> 	at java.lang.ClassLoader.getParent(ClassLoader.java:1429)
> 	at com.sun.org.apache.xerces.internal.utils.SecuritySupport$3.run(SecuritySupport.java:82)
> 	at java.security.AccessController.doPrivileged(Native Method)
> 	at com.sun.org.apache.xerces.internal.utils.SecuritySupport.getParentClassLoader(SecuritySupport.java:78)
> 	at com.sun.org.apache.xerces.internal.utils.ObjectFactory.findClassLoader(ObjectFactory.java:221)
> 	at com.sun.org.apache.xerces.internal.utils.ObjectFactory.newInstance(ObjectFactory.java:255)
> 	at com.sun.org.apache.xerces.internal.impl.dv.DTDDVFactory.getInstance(DTDDVFactory.java:64)
> 	at com.sun.org.apache.xerces.internal.impl.dv.DTDDVFactory.getInstance(DTDDVFactory.java:49)
> 	at com.sun.org.apache.xerces.internal.parsers.XML11Configuration.<init>(XML11Configuration.java:565)
> 	at com.sun.org.apache.xerces.internal.parsers.XIncludeAwareParserConfiguration.<init>(XIncludeAwareParserConfiguration.java:130)
> 	at com.sun.org.apache.xerces.internal.parsers.XIncludeAwareParserConfiguration.<init>(XIncludeAwareParserConfiguration.java:91)
> 	at com.sun.org.apache.xerces.internal.parsers.DOMParser.<init>(DOMParser.java:138)
> 	at com.sun.org.apache.xerces.internal.parsers.DOMParser.<init>(DOMParser.java:122)
> 	at com.sun.org.apache.xerces.internal.jaxp.DocumentBuilderImpl.<init>(DocumentBuilderImpl.java:120)
> 	at com.sun.org.apache.xerces.internal.jaxp.DocumentBuilderFactoryImpl.newDocumentBuilder(DocumentBuilderFactoryImpl.java:76)
> 	at sun.util.xml.XMLUtils.getLoadingDoc(XMLUtils.java:99)
> 	at sun.util.xml.XMLUtils.load(XMLUtils.java:75)
> 	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
> 	at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
> 	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
> 	at java.lang.reflect.Method.invoke(Method.java:474)
> 	at java.util.Properties$XMLUtils.invoke(Properties.java:1157)
> 	at java.util.Properties$XMLUtils.load(Properties.java:1178)
> 	at java.util.Properties.loadFromXML(Properties.java:875)
> 	at org.astro.World.name(World.java:11)
> 	at com.greetings.Hello.main(Hello.java:5)
>



More information about the jigsaw-dev mailing list