src/java.security.sasl/share/classes/javax/security/sasl/Sasl.java
Print this page
7191662: JCE providers should be located via ServiceLoader
@@ -1,7 +1,7 @@
/*
- * Copyright (c) 1999, 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
@@ -31,11 +31,14 @@
import java.util.Iterator;
import java.util.Map;
import java.util.Set;
import java.util.HashSet;
import java.util.Collections;
+import java.security.InvalidParameterException;
+import java.security.NoSuchAlgorithmException;
import java.security.Provider;
+import java.security.Provider.Service;
import java.security.Security;
/**
* A static class for creating SASL clients and servers.
*<p>
@@ -358,30 +361,31 @@
Map<String,?> props,
CallbackHandler cbh) throws SaslException {
SaslClient mech = null;
SaslClientFactory fac;
- String className;
+ Service service;
String mechName;
for (int i = 0; i < mechanisms.length; i++) {
if ((mechName=mechanisms[i]) == null) {
throw new NullPointerException(
"Mechanism name cannot be null");
} else if (mechName.length() == 0) {
continue;
}
- String mechFilter = "SaslClientFactory." + mechName;
- Provider[] provs = Security.getProviders(mechFilter);
- for (int j = 0; provs != null && j < provs.length; j++) {
- className = provs[j].getProperty(mechFilter);
- if (className == null) {
- // Case is ignored
+ String type = "SaslClientFactory";
+ Provider[] provs = Security.getProviders(type + "." + mechName);
+ if (provs != null) {
+ for (Provider p : provs) {
+ service = p.getService(type, mechName);
+ if (service == null) {
+ // no such service exists
continue;
}
- fac = (SaslClientFactory) loadFactory(provs[j], className);
+ fac = (SaslClientFactory) loadFactory(service);
if (fac != null) {
mech = fac.createSaslClient(
new String[]{mechanisms[i]}, authorizationId,
protocol, serverName, props, cbh);
if (mech != null) {
@@ -388,15 +392,15 @@
return mech;
}
}
}
}
-
+ }
return null;
}
- private static Object loadFactory(Provider p, String className)
+ private static Object loadFactory(Service service)
throws SaslException {
try {
/*
* Load the implementation class with the same class loader
* that was used to load the provider.
@@ -404,22 +408,13 @@
* caller's class loader must be the same as or an ancestor of
* the class loader being returned. Otherwise, the caller must
* have "getClassLoader" permission, or a SecurityException
* will be thrown.
*/
- ClassLoader cl = p.getClass().getClassLoader();
- Class<?> implClass;
- implClass = Class.forName(className, true, cl);
- return implClass.newInstance();
- } catch (ClassNotFoundException e) {
- throw new SaslException("Cannot load class " + className, e);
- } catch (InstantiationException e) {
- throw new SaslException("Cannot instantiate class " + className, e);
- } catch (IllegalAccessException e) {
- throw new SaslException("Cannot access class " + className, e);
- } catch (SecurityException e) {
- throw new SaslException("Cannot access class " + className, e);
+ return service.newInstance(null);
+ } catch (InvalidParameterException | NoSuchAlgorithmException e) {
+ throw new SaslException("Cannot instantiate service " + service, e);
}
}
/**
@@ -501,36 +496,37 @@
javax.security.auth.callback.CallbackHandler cbh)
throws SaslException {
SaslServer mech = null;
SaslServerFactory fac;
- String className;
+ Service service;
if (mechanism == null) {
throw new NullPointerException("Mechanism name cannot be null");
} else if (mechanism.length() == 0) {
return null;
}
- String mechFilter = "SaslServerFactory." + mechanism;
- Provider[] provs = Security.getProviders(mechFilter);
- for (int j = 0; provs != null && j < provs.length; j++) {
- className = provs[j].getProperty(mechFilter);
- if (className == null) {
+ String type = "SaslServerFactory";
+ Provider[] provs = Security.getProviders(type + "." + mechanism);
+ if (provs != null) {
+ for (Provider p : provs) {
+ service = p.getService(type, mechanism);
+ if (service == null) {
throw new SaslException("Provider does not support " +
- mechFilter);
+ mechanism + " " + type);
}
- fac = (SaslServerFactory) loadFactory(provs[j], className);
+ fac = (SaslServerFactory) loadFactory(service);
if (fac != null) {
mech = fac.createSaslServer(
mechanism, protocol, serverName, props, cbh);
if (mech != null) {
return mech;
}
}
}
-
+ }
return null;
}
/**
* Gets an enumeration of known factories for producing {@code SaslClient}.
@@ -580,42 +576,27 @@
if ((serviceName == null) || (serviceName.length() == 0) ||
(serviceName.endsWith("."))) {
return result;
}
-
- Provider[] providers = Security.getProviders();
- HashSet<String> classes = new HashSet<String>();
+ Provider[] provs = Security.getProviders();
Object fac;
- for (int i = 0; i < providers.length; i++) {
- classes.clear();
+ for (Provider p : provs) {
- // Check the keys for each provider.
- for (Enumeration<Object> e = providers[i].keys(); e.hasMoreElements(); ) {
- String currentKey = (String)e.nextElement();
- if (currentKey.startsWith(serviceName)) {
- // We should skip the currentKey if it contains a
- // whitespace. The reason is: such an entry in the
- // provider property contains attributes for the
- // implementation of an algorithm. We are only interested
- // in entries which lead to the implementation
- // classes.
- if (currentKey.indexOf(' ') < 0) {
- String className = providers[i].getProperty(currentKey);
- if (!classes.contains(className)) {
- classes.add(className);
+ Iterator<Service> iter = p.getServices().iterator();
+ while (iter.hasNext()) {
+ Service s = iter.next();
+ if (s.getType().equals(serviceName)) {
try {
- fac = loadFactory(providers[i], className);
+ fac = loadFactory(s);
if (fac != null) {
result.add(fac);
}
- }catch (Exception ignore) {
+ } catch (Exception ignore) {
}
}
- }
- }
}
}
return Collections.unmodifiableSet(result);
}
}