Hi Peter,

Thanks for reporting this.

It would be helpful to know the original intent of the author, but i suspect 
this is a bug (even though null is commonly used to refer to the bootstrap CL).

FWIW i cannot find any explicit cases in the JDK that relies on this behaviour 
to explicitly limit the loading of service provider classes to those in rt.jar, 
which would be kind of a pointless use of SL :-)

I am inclined to think that fixing this is mostly harmless, since passing a 
null CL renders SL useless for anything but service provider classes in rt.jar, 
and there are so very few of those provider classes i.e. this issue is likely 
to have been mostly worked around by explicitly passing in a non-null CL, such 
as ClassLoader.getSystemClassLoader().

However, I say mostly harmless because fixing this will change behaviour to no 
longer produce an error that would otherwise be acted on. This may be the case 
for libraries that use SL and the user passed a CL to the library and the 
library on error uses, for example. the thread context CL. Who knows, CL code 
can be very strange.

Paul.

On Sep 14, 2012, at 10:20 AM, Peter Levart <[email protected]> wrote:

> I reported this as Bug ID: 7198496
> 
> Regards, Peter
> 
> On 09/13/2012 05:13 PM, Peter Levart wrote:
>> Hi,
>> 
>> The javadoc for java.util.ServiceLoader.load(Class service, ClassLoader 
>> loader) method says about it's parameters:
>> 
>>     * @param  service
>>     *         The interface or abstract class representing the service
>>     *
>>     * @param  loader
>>     *         The class loader to be used to load provider-configuration 
>> files
>>     *         and provider classes, or <tt>null</tt> if the system class
>>     *         loader (or, failing that, the bootstrap class loader) is to be
>>     *         used
>> 
>> So one might think that calling:
>> 
>>    ServiceLoader.load(service, null);
>> 
>> is equivalent to:
>> 
>>    ServiceLoader.load(service, ClassLoader.getSystemClassLoader());
>> 
>> 
>> But it is not. Either this is a bug in ServiceLoader or javadoc has to be 
>> changed.
>> 
>> If null is specified as ClassLoader then ServiceLoader locates 
>> META-INF/services/interface.name resources using system ClassLoader (using 
>> ClassLoader.getSystemResources), but loads implementation classes using 
>> bootstrap ClassLoader (using Class.forName(className, true, null)).
>> 
>> If this is not the expected behaviour then the fix is simple (in the private 
>> constructor of ServiceLoader[217]):
>> 
>> -    loader = cl;
>> +   loader = cl == null ? ClassLoader.getSystemClassLoader() : cl;
>> 
>> 
>> 
>> Regards, Peter
>> 
>> 
>> 
>> 
> 

Reply via email to