diff options
Diffstat (limited to 'ojluni/src/main/java/sun/security/jca/Providers.java')
-rw-r--r-- | ojluni/src/main/java/sun/security/jca/Providers.java | 291 |
1 files changed, 291 insertions, 0 deletions
diff --git a/ojluni/src/main/java/sun/security/jca/Providers.java b/ojluni/src/main/java/sun/security/jca/Providers.java index e39543af23c..e50ce231255 100644 --- a/ojluni/src/main/java/sun/security/jca/Providers.java +++ b/ojluni/src/main/java/sun/security/jca/Providers.java @@ -26,7 +26,13 @@ package sun.security.jca; +import dalvik.system.VMRuntime; +import java.security.NoSuchAlgorithmException; import java.security.Provider; +import java.util.Arrays; +import java.util.HashSet; +import java.util.Locale; +import java.util.Set; /** * Collection of methods to get and set provider list. Also includes @@ -48,6 +54,10 @@ public class Providers { // Note volatile immutable object, so no synchronization needed. private static volatile ProviderList providerList; + // Android-added: Keep reference to system-created Bouncy Castle provider + // See comments near deprecation methods at the bottom of this file. + private static volatile Provider SYSTEM_BOUNCY_CASTLE_PROVIDER; + static { // set providerList to empty list first in case initialization somehow // triggers a getInstance() call (although that should not happen) @@ -64,6 +74,8 @@ public class Providers { throw new AssertionError("Unable to configure default providers"); } // END Android-added: Initialize all providers and assert that this succeeds. + // Android-added: Set BC provider instance + SYSTEM_BOUNCY_CASTLE_PROVIDER = providerList.getProvider("BC"); } private Providers() { @@ -263,4 +275,283 @@ public class Providers { threadListsUsed--; } + // BEGIN Android-added: Check for requests of deprecated Bouncy Castle algorithms. + // Beginning in Android P, Bouncy Castle versions of algorithms available through + // Conscrypt are deprecated. We will no longer supply them to applications + // with a target API level of P or later, and will print a warning for applications + // with a target API level before P. + // + // We only care about the system-provided Bouncy Castle provider; applications are allowed to + // install their own copy of Bouncy Castle if they want to continue using those implementations. + + /** + * Maximum target API level for which we will provide the deprecated Bouncy Castle algorithms. + * + * Only exists for testing and shouldn't be changed. + * + * @hide + */ + public static final int DEFAULT_MAXIMUM_ALLOWABLE_TARGET_API_LEVEL_FOR_BC_DEPRECATION = 26; + + private static int maximumAllowableApiLevelForBcDeprecation = + DEFAULT_MAXIMUM_ALLOWABLE_TARGET_API_LEVEL_FOR_BC_DEPRECATION; + + /** + * Sets the target API level for BC deprecation, only for use in tests. + * + * @hide + */ + public static void setMaximumAllowableApiLevelForBcDeprecation(int targetApiLevel) { + maximumAllowableApiLevelForBcDeprecation = targetApiLevel; + } + + /** + * Returns the target API level for BC deprecation, only for use in tests. + * + * @hide + */ + public static int getMaximumAllowableApiLevelForBcDeprecation() { + return maximumAllowableApiLevelForBcDeprecation; + } + + /** + * Checks if the installed provider with the given name is the system-installed Bouncy + * Castle provider. If so, throws {@code NoSuchAlgorithmException} if the algorithm + * being requested is deprecated and the application targets a late-enough API level. + * + * @hide + */ + public static synchronized void checkBouncyCastleDeprecation(String provider, + String service, String algorithm) throws NoSuchAlgorithmException { + // Applications may install their own BC provider, only the algorithms from the system + // provider are deprecated. + if ("BC".equals(provider) + && providerList.getProvider(provider) == SYSTEM_BOUNCY_CASTLE_PROVIDER) { + checkBouncyCastleDeprecation(service, algorithm); + } + } + + /** + * Checks if the given provider is the system-installed Bouncy Castle provider. If so, + * throws {@code NoSuchAlgorithmException} if the algorithm being requested is deprecated + * and the application targets a late-enough API level. + * + * @hide + */ + public static synchronized void checkBouncyCastleDeprecation(Provider provider, + String service, String algorithm) throws NoSuchAlgorithmException { + // Applications may install their own BC provider, only the algorithms from the system + // provider are deprecated. + if (provider == SYSTEM_BOUNCY_CASTLE_PROVIDER) { + checkBouncyCastleDeprecation(service, algorithm); + } + } + + // The set of algorithms that are deprecated. This list is created using + // libcore/tools/crypto/src/java/libcore/java/security/ProviderOverlap.java + private static final Set<String> DEPRECATED_ALGORITHMS = new HashSet<String>(); + static { + DEPRECATED_ALGORITHMS.addAll(Arrays.asList( + "ALGORITHMPARAMETERS.1.2.840.113549.3.7", + "ALGORITHMPARAMETERS.2.16.840.1.101.3.4.1.2", + "ALGORITHMPARAMETERS.2.16.840.1.101.3.4.1.22", + "ALGORITHMPARAMETERS.2.16.840.1.101.3.4.1.26", + "ALGORITHMPARAMETERS.2.16.840.1.101.3.4.1.42", + "ALGORITHMPARAMETERS.2.16.840.1.101.3.4.1.46", + "ALGORITHMPARAMETERS.2.16.840.1.101.3.4.1.6", + "ALGORITHMPARAMETERS.AES", + "ALGORITHMPARAMETERS.DESEDE", + "ALGORITHMPARAMETERS.EC", + "ALGORITHMPARAMETERS.GCM", + "ALGORITHMPARAMETERS.OAEP", + "ALGORITHMPARAMETERS.TDEA", + "CERTIFICATEFACTORY.X.509", + "CERTIFICATEFACTORY.X509", + // TODO(flooey, b/67626877): Implement Cipher support + // "CIPHER.1.2.840.113549.3.4", + // "CIPHER.2.16.840.1.101.3.4.1.26", + // "CIPHER.2.16.840.1.101.3.4.1.46", + // "CIPHER.2.16.840.1.101.3.4.1.6", + // "CIPHER.AES/GCM/NOPADDING", + // "CIPHER.ARC4", + // "CIPHER.ARCFOUR", + // "CIPHER.OID.1.2.840.113549.3.4", + // "CIPHER.RC4", + "KEYAGREEMENT.ECDH", + "KEYFACTORY.1.2.840.10045.2.1", + "KEYFACTORY.1.2.840.113549.1.1.1", + "KEYFACTORY.1.2.840.113549.1.1.7", + "KEYFACTORY.1.3.133.16.840.63.0.2", + "KEYFACTORY.2.5.8.1.1", + "KEYFACTORY.EC", + "KEYFACTORY.RSA", + "KEYGENERATOR.1.2.840.113549.2.10", + "KEYGENERATOR.1.2.840.113549.2.11", + "KEYGENERATOR.1.2.840.113549.2.7", + "KEYGENERATOR.1.2.840.113549.2.8", + "KEYGENERATOR.1.2.840.113549.2.9", + "KEYGENERATOR.1.3.6.1.5.5.8.1.1", + "KEYGENERATOR.1.3.6.1.5.5.8.1.2", + "KEYGENERATOR.2.16.840.1.101.3.4.2.1", + "KEYGENERATOR.AES", + "KEYGENERATOR.DESEDE", + "KEYGENERATOR.HMAC-MD5", + "KEYGENERATOR.HMAC-SHA1", + "KEYGENERATOR.HMAC-SHA224", + "KEYGENERATOR.HMAC-SHA256", + "KEYGENERATOR.HMAC-SHA384", + "KEYGENERATOR.HMAC-SHA512", + "KEYGENERATOR.HMAC/MD5", + "KEYGENERATOR.HMAC/SHA1", + "KEYGENERATOR.HMAC/SHA224", + "KEYGENERATOR.HMAC/SHA256", + "KEYGENERATOR.HMAC/SHA384", + "KEYGENERATOR.HMAC/SHA512", + "KEYGENERATOR.HMACMD5", + "KEYGENERATOR.HMACSHA1", + "KEYGENERATOR.HMACSHA224", + "KEYGENERATOR.HMACSHA256", + "KEYGENERATOR.HMACSHA384", + "KEYGENERATOR.HMACSHA512", + "KEYGENERATOR.TDEA", + "KEYPAIRGENERATOR.1.2.840.10045.2.1", + "KEYPAIRGENERATOR.1.2.840.113549.1.1.1", + "KEYPAIRGENERATOR.1.2.840.113549.1.1.7", + "KEYPAIRGENERATOR.1.3.133.16.840.63.0.2", + "KEYPAIRGENERATOR.2.5.8.1.1", + "KEYPAIRGENERATOR.EC", + "KEYPAIRGENERATOR.RSA", + "MAC.1.2.840.113549.2.10", + "MAC.1.2.840.113549.2.11", + "MAC.1.2.840.113549.2.7", + "MAC.1.2.840.113549.2.8", + "MAC.1.2.840.113549.2.9", + "MAC.1.3.6.1.5.5.8.1.1", + "MAC.1.3.6.1.5.5.8.1.2", + "MAC.2.16.840.1.101.3.4.2.1", + "MAC.HMAC-MD5", + "MAC.HMAC-SHA1", + "MAC.HMAC-SHA224", + "MAC.HMAC-SHA256", + "MAC.HMAC-SHA384", + "MAC.HMAC-SHA512", + "MAC.HMAC/MD5", + "MAC.HMAC/SHA1", + "MAC.HMAC/SHA224", + "MAC.HMAC/SHA256", + "MAC.HMAC/SHA384", + "MAC.HMAC/SHA512", + "MAC.HMACMD5", + "MAC.HMACSHA1", + "MAC.HMACSHA224", + "MAC.HMACSHA256", + "MAC.HMACSHA384", + "MAC.HMACSHA512", + "MAC.PBEWITHHMACSHA224", + "MAC.PBEWITHHMACSHA256", + "MAC.PBEWITHHMACSHA384", + "MAC.PBEWITHHMACSHA512", + "MESSAGEDIGEST.1.2.840.113549.2.5", + "MESSAGEDIGEST.1.3.14.3.2.26", + "MESSAGEDIGEST.2.16.840.1.101.3.4.2.1", + "MESSAGEDIGEST.2.16.840.1.101.3.4.2.2", + "MESSAGEDIGEST.2.16.840.1.101.3.4.2.3", + "MESSAGEDIGEST.2.16.840.1.101.3.4.2.4", + "MESSAGEDIGEST.MD5", + "MESSAGEDIGEST.SHA", + "MESSAGEDIGEST.SHA-1", + "MESSAGEDIGEST.SHA-224", + "MESSAGEDIGEST.SHA-256", + "MESSAGEDIGEST.SHA-384", + "MESSAGEDIGEST.SHA-512", + "MESSAGEDIGEST.SHA1", + "MESSAGEDIGEST.SHA224", + "MESSAGEDIGEST.SHA256", + "MESSAGEDIGEST.SHA384", + "MESSAGEDIGEST.SHA512", + "SECRETKEYFACTORY.DESEDE", + "SECRETKEYFACTORY.TDEA", + "SIGNATURE.1.2.840.10045.4.1", + "SIGNATURE.1.2.840.10045.4.3.1", + "SIGNATURE.1.2.840.10045.4.3.2", + "SIGNATURE.1.2.840.10045.4.3.3", + "SIGNATURE.1.2.840.10045.4.3.4", + "SIGNATURE.1.2.840.113549.1.1.11", + "SIGNATURE.1.2.840.113549.1.1.12", + "SIGNATURE.1.2.840.113549.1.1.13", + "SIGNATURE.1.2.840.113549.1.1.14", + "SIGNATURE.1.2.840.113549.1.1.4", + "SIGNATURE.1.2.840.113549.1.1.5", + "SIGNATURE.1.3.14.3.2.29", + "SIGNATURE.ECDSA", + "SIGNATURE.ECDSAWITHSHA1", + "SIGNATURE.MD5/RSA", + "SIGNATURE.MD5WITHRSA", + "SIGNATURE.MD5WITHRSAENCRYPTION", + "SIGNATURE.NONEWITHECDSA", + "SIGNATURE.OID.1.2.840.10045.4.3.1", + "SIGNATURE.OID.1.2.840.10045.4.3.2", + "SIGNATURE.OID.1.2.840.10045.4.3.3", + "SIGNATURE.OID.1.2.840.10045.4.3.4", + "SIGNATURE.OID.1.2.840.113549.1.1.11", + "SIGNATURE.OID.1.2.840.113549.1.1.12", + "SIGNATURE.OID.1.2.840.113549.1.1.13", + "SIGNATURE.OID.1.2.840.113549.1.1.14", + "SIGNATURE.OID.1.2.840.113549.1.1.4", + "SIGNATURE.OID.1.2.840.113549.1.1.5", + "SIGNATURE.OID.1.3.14.3.2.29", + "SIGNATURE.SHA1/RSA", + "SIGNATURE.SHA1WITHECDSA", + "SIGNATURE.SHA1WITHRSA", + "SIGNATURE.SHA1WITHRSAENCRYPTION", + "SIGNATURE.SHA224/ECDSA", + "SIGNATURE.SHA224/RSA", + "SIGNATURE.SHA224WITHECDSA", + "SIGNATURE.SHA224WITHRSA", + "SIGNATURE.SHA224WITHRSAENCRYPTION", + "SIGNATURE.SHA256/ECDSA", + "SIGNATURE.SHA256/RSA", + "SIGNATURE.SHA256WITHECDSA", + "SIGNATURE.SHA256WITHRSA", + "SIGNATURE.SHA256WITHRSAENCRYPTION", + "SIGNATURE.SHA384/ECDSA", + "SIGNATURE.SHA384/RSA", + "SIGNATURE.SHA384WITHECDSA", + "SIGNATURE.SHA384WITHRSA", + "SIGNATURE.SHA384WITHRSAENCRYPTION", + "SIGNATURE.SHA512/ECDSA", + "SIGNATURE.SHA512/RSA", + "SIGNATURE.SHA512WITHECDSA", + "SIGNATURE.SHA512WITHRSA", + "SIGNATURE.SHA512WITHRSAENCRYPTION" + )); + } + + /** + * Throws an exception or logs a warning if the supplied service and algorithm identify + * a deprecated algorithm from Bouncy Castle, depending on the application's target API level. + * Only called if we have already determined that the request is for the system Bouncy Castle + * provider. + */ + private static void checkBouncyCastleDeprecation(String service, String algorithm) + throws NoSuchAlgorithmException { + String key = service + "." + algorithm; + if (DEPRECATED_ALGORITHMS.contains(key.toUpperCase(Locale.US))) { + if (VMRuntime.getRuntime().getTargetSdkVersion() + <= maximumAllowableApiLevelForBcDeprecation) { + // This application is allowed to access these functions, only print a warning + System.logE(" ******** DEPRECATED FUNCTIONALITY ********"); + System.logE(" * The implementation of the " + key + " algorithm from"); + System.logE(" * the BC provider is deprecated in this version of Android."); + System.logE(" * It will be removed in a future version of Android and your"); + System.logE(" * application will no longer be able to request it. Please see"); + System.logE(" * ((TODO(flooey, b/67626877): Blog Post Link)) for more details."); + } else { + throw new NoSuchAlgorithmException("The BC provider no longer provides an" + + " implementation for " + key + ". Please see" + + " ((TODO(flooey, b/67626877): Blog Post Link)) for more details."); + } + } + } + } |