changeset 7333:75ad6f000a10

8035004: Provider provides less service Reviewed-by: mullan, coffeys
author robm
date Fri, 04 Apr 2014 15:24:14 +0100
parents ad775235b3f9
children 4fc37d23611a
files src/share/classes/java/security/Provider.java
diffstat 1 files changed, 24 insertions(+), 12 deletions(-) [+]
line wrap: on
line diff
--- a/src/share/classes/java/security/Provider.java	Wed Mar 05 20:56:53 2014 -0800
+++ b/src/share/classes/java/security/Provider.java	Fri Apr 04 15:24:14 2014 +0100
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 2014, 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
@@ -1017,7 +1017,7 @@
      * <p>This class defines the methods {@link #supportsParameter
      * supportsParameter()} and {@link #newInstance newInstance()}
      * which are used by the Java security framework when it searches for
-     * suitable services and instantes them. The valid arguments to those
+     * suitable services and instantiates them. The valid arguments to those
      * methods depend on the type of service. For the service types defined
      * within Java SE, see the
      * <a href="../../../technotes/guides/security/crypto/CryptoSpec.html">
@@ -1207,7 +1207,7 @@
          *
          * @throws InvalidParameterException if the value of
          * constructorParameter is invalid for this type of service.
-         * @throws NoSuchAlgorithmException if instantation failed for
+         * @throws NoSuchAlgorithmException if instantiation failed for
          * any other reason.
          */
         public Object newInstance(Object constructorParameter)
@@ -1235,7 +1235,9 @@
                             + " engines");
                     }
                     Class clazz = getImplClass();
-                    return clazz.newInstance();
+                    Class<?>[] empty = {};
+                    Constructor<?> con = clazz.getConstructor(empty);
+                    return con.newInstance();
                 } else {
                     Class paramClass = cap.getConstructorParameterClass();
                     if (constructorParameter != null) {
@@ -1278,13 +1280,18 @@
                     } else {
                         clazz = cl.loadClass(className);
                     }
+                    if (!Modifier.isPublic(clazz.getModifiers())) {
+                        throw new NoSuchAlgorithmException
+                            ("class configured for " + type + " (provider: " +
+                            provider.getName() + ") is not public.");
+                    }
                     classRef = new WeakReference<Class>(clazz);
                 }
                 return clazz;
             } catch (ClassNotFoundException e) {
                 throw new NoSuchAlgorithmException
                     ("class configured for " + type + "(provider: " +
-                    provider.getName() + ")" + "cannot be found.", e);
+                    provider.getName() + ") cannot be found.", e);
             }
         }
 
@@ -1297,15 +1304,21 @@
                 throws Exception {
             Class clazz = getImplClass();
             if (constructorParameter == null) {
-                Object o = clazz.newInstance();
-                return o;
+                // create instance with public no-arg constructor if it exists
+                try {
+                    Class<?>[] empty = {};
+                    Constructor<?> con = clazz.getConstructor(empty);
+                    return con.newInstance();
+                } catch (NoSuchMethodException e) {
+                    throw new NoSuchAlgorithmException("No public no-arg "
+                        + "constructor found in class " + className);
+                }
             }
             Class argClass = constructorParameter.getClass();
             Constructor[] cons = clazz.getConstructors();
             // find first public constructor that can take the
             // argument as parameter
-            for (int i = 0; i < cons.length; i++) {
-                Constructor con = cons[i];
+            for (Constructor<?> con : cons) {
                 Class[] paramTypes = con.getParameterTypes();
                 if (paramTypes.length != 1) {
                     continue;
@@ -1313,10 +1326,9 @@
                 if (paramTypes[0].isAssignableFrom(argClass) == false) {
                     continue;
                 }
-                Object o = con.newInstance(new Object[] {constructorParameter});
-                return o;
+                return con.newInstance(constructorParameter);
             }
-            throw new NoSuchAlgorithmException("No constructor matching "
+            throw new NoSuchAlgorithmException("No public constructor matching "
                 + argClass.getName() + " found in class " + className);
         }