# HG changeset patch # User xuelei # Date 1429679394 0 # Node ID e4d5230193dac6d78a2902a907a248b69696a96a # Parent cca718f2fcf0a610ab4086b59a4df824606bdb85 8076328: Enforce key exchange constraints Reviewed-by: wetmore, igerasim, ahgross, asmotrak diff -r cca718f2fcf0 -r e4d5230193da jdk/src/java.base/share/classes/sun/security/ssl/ClientHandshaker.java --- a/jdk/src/java.base/share/classes/sun/security/ssl/ClientHandshaker.java Tue Apr 21 20:33:34 2015 +0100 +++ b/jdk/src/java.base/share/classes/sun/security/ssl/ClientHandshaker.java Wed Apr 22 05:09:54 2015 +0000 @@ -723,6 +723,14 @@ // NOTREACHED } ephemeralServerKey = mesg.getPublicKey(); + + // check constraints of RSA PublicKey + if (!algorithmConstraints.permits( + EnumSet.of(CryptoPrimitive.KEY_AGREEMENT), ephemeralServerKey)) { + + throw new SSLHandshakeException("RSA ServerKeyExchange " + + "does not comply to algorithm constraints"); + } } /* @@ -739,6 +747,9 @@ dh = new DHCrypt(mesg.getModulus(), mesg.getBase(), sslContext.getSecureRandom()); serverDH = mesg.getServerPublicKey(); + + // check algorithm constraints + dh.checkConstraints(algorithmConstraints, serverDH); } private void serverKeyExchange(ECDH_ServerKeyExchange mesg) @@ -749,6 +760,14 @@ ECPublicKey key = mesg.getPublicKey(); ecdh = new ECDHCrypt(key.getParams(), sslContext.getSecureRandom()); ephemeralServerKey = key; + + // check constraints of EC PublicKey + if (!algorithmConstraints.permits( + EnumSet.of(CryptoPrimitive.KEY_AGREEMENT), ephemeralServerKey)) { + + throw new SSLHandshakeException("ECDH ServerKeyExchange " + + "does not comply to algorithm constraints"); + } } /* diff -r cca718f2fcf0 -r e4d5230193da jdk/src/java.base/share/classes/sun/security/ssl/DHCrypt.java --- a/jdk/src/java.base/share/classes/sun/security/ssl/DHCrypt.java Tue Apr 21 20:33:34 2015 +0100 +++ b/jdk/src/java.base/share/classes/sun/security/ssl/DHCrypt.java Wed Apr 22 05:09:54 2015 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 2014, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1996, 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 @@ -34,6 +34,7 @@ import javax.crypto.KeyAgreement; import javax.crypto.interfaces.DHPublicKey; import javax.crypto.spec.*; +import java.util.EnumSet; import sun.security.util.KeyUtil; @@ -216,6 +217,28 @@ } } + // Check constraints of the specified DH public key. + void checkConstraints(AlgorithmConstraints constraints, + BigInteger peerPublicValue) throws SSLHandshakeException { + + try { + KeyFactory kf = JsseJce.getKeyFactory("DiffieHellman"); + DHPublicKeySpec spec = + new DHPublicKeySpec(peerPublicValue, modulus, base); + DHPublicKey publicKey = (DHPublicKey)kf.generatePublic(spec); + + // check constraints of DHPublicKey + if (!constraints.permits( + EnumSet.of(CryptoPrimitive.KEY_AGREEMENT), publicKey)) { + throw new SSLHandshakeException( + "DHPublicKey does not comply to algorithm constraints"); + } + } catch (GeneralSecurityException gse) { + throw (SSLHandshakeException) new SSLHandshakeException( + "Could not generate DHPublicKey").initCause(gse); + } + } + // Generate and validate DHPublicKeySpec private DHPublicKeySpec generateDHPublicKeySpec(KeyPairGenerator kpg) throws GeneralSecurityException { diff -r cca718f2fcf0 -r e4d5230193da jdk/src/java.base/share/classes/sun/security/ssl/ECDHCrypt.java --- a/jdk/src/java.base/share/classes/sun/security/ssl/ECDHCrypt.java Tue Apr 21 20:33:34 2015 +0100 +++ b/jdk/src/java.base/share/classes/sun/security/ssl/ECDHCrypt.java Wed Apr 22 05:09:54 2015 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2006, 2014, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2006, 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 @@ -29,6 +29,7 @@ import java.security.interfaces.ECPublicKey; import java.security.spec.*; +import java.util.EnumSet; import javax.crypto.SecretKey; import javax.crypto.KeyAgreement; import javax.net.ssl.SSLHandshakeException; @@ -88,8 +89,11 @@ return publicKey; } - // called by ClientHandshaker with either the server's static or ephemeral public key - SecretKey getAgreedSecret(PublicKey peerPublicKey) throws SSLHandshakeException { + // called by ClientHandshaker with either the server's static or + // ephemeral public key + SecretKey getAgreedSecret( + PublicKey peerPublicKey) throws SSLHandshakeException { + try { KeyAgreement ka = JsseJce.getKeyAgreement("ECDH"); ka.init(privateKey); @@ -102,10 +106,13 @@ } // called by ServerHandshaker - SecretKey getAgreedSecret(byte[] encodedPoint) throws SSLHandshakeException { + SecretKey getAgreedSecret( + byte[] encodedPoint) throws SSLHandshakeException { + try { ECParameterSpec params = publicKey.getParams(); - ECPoint point = JsseJce.decodePoint(encodedPoint, params.getCurve()); + ECPoint point = + JsseJce.decodePoint(encodedPoint, params.getCurve()); KeyFactory kf = JsseJce.getKeyFactory("EC"); ECPublicKeySpec spec = new ECPublicKeySpec(point, params); PublicKey peerPublicKey = kf.generatePublic(spec); @@ -116,4 +123,30 @@ } } + // Check constraints of the specified EC public key. + void checkConstraints(AlgorithmConstraints constraints, + byte[] encodedPoint) throws SSLHandshakeException { + + try { + + ECParameterSpec params = publicKey.getParams(); + ECPoint point = + JsseJce.decodePoint(encodedPoint, params.getCurve()); + ECPublicKeySpec spec = new ECPublicKeySpec(point, params); + + KeyFactory kf = JsseJce.getKeyFactory("EC"); + ECPublicKey publicKey = (ECPublicKey)kf.generatePublic(spec); + + // check constraints of ECPublicKey + if (!constraints.permits( + EnumSet.of(CryptoPrimitive.KEY_AGREEMENT), publicKey)) { + throw new SSLHandshakeException( + "ECPublicKey does not comply to algorithm constraints"); + } + } catch (GeneralSecurityException | java.io.IOException e) { + throw (SSLHandshakeException) new SSLHandshakeException( + "Could not generate ECPublicKey").initCause(e); + } + } + } diff -r cca718f2fcf0 -r e4d5230193da jdk/src/java.base/share/classes/sun/security/ssl/Handshaker.java --- a/jdk/src/java.base/share/classes/sun/security/ssl/Handshaker.java Tue Apr 21 20:33:34 2015 +0100 +++ b/jdk/src/java.base/share/classes/sun/security/ssl/Handshaker.java Wed Apr 22 05:09:54 2015 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 1996, 2014, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1996, 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 @@ -87,7 +87,7 @@ String identificationProtocol; // The cryptographic algorithm constraints - private AlgorithmConstraints algorithmConstraints = null; + AlgorithmConstraints algorithmConstraints = null; // Local supported signature and algorithms Collection localSupportedSignAlgs; diff -r cca718f2fcf0 -r e4d5230193da jdk/src/java.base/share/classes/sun/security/ssl/ServerHandshaker.java --- a/jdk/src/java.base/share/classes/sun/security/ssl/ServerHandshaker.java Tue Apr 21 20:33:34 2015 +0100 +++ b/jdk/src/java.base/share/classes/sun/security/ssl/ServerHandshaker.java Wed Apr 22 05:09:54 2015 +0000 @@ -32,6 +32,7 @@ import java.security.cert.*; import java.security.interfaces.*; import java.security.spec.ECParameterSpec; +import java.math.BigInteger; import javax.crypto.SecretKey; import javax.crypto.spec.SecretKeySpec; @@ -1571,7 +1572,13 @@ if (debug != null && Debug.isOn("handshake")) { mesg.print(System.out); } - return dh.getAgreedSecret(mesg.getClientPublicKey(), false); + + BigInteger publicKeyValue = mesg.getClientPublicKey(); + + // check algorithm constraints + dh.checkConstraints(algorithmConstraints, publicKeyValue); + + return dh.getAgreedSecret(publicKeyValue, false); } private SecretKey clientKeyExchange(ECDHClientKeyExchange mesg) @@ -1580,7 +1587,13 @@ if (debug != null && Debug.isOn("handshake")) { mesg.print(System.out); } - return ecdh.getAgreedSecret(mesg.getEncodedPoint()); + + byte[] publicPoint = mesg.getEncodedPoint(); + + // check algorithm constraints + ecdh.checkConstraints(algorithmConstraints, publicPoint); + + return ecdh.getAgreedSecret(publicPoint); } /* diff -r cca718f2fcf0 -r e4d5230193da jdk/src/java.base/share/conf/security/java.security --- a/jdk/src/java.base/share/conf/security/java.security Tue Apr 21 20:33:34 2015 +0100 +++ b/jdk/src/java.base/share/conf/security/java.security Wed Apr 22 05:09:54 2015 +0000 @@ -541,7 +541,7 @@ # # Example: # jdk.tls.disabledAlgorithms=MD5, SSLv3, DSA, RSA keySize < 2048 -jdk.tls.disabledAlgorithms=SSLv3, RC4 +jdk.tls.disabledAlgorithms=SSLv3, RC4, DH keySize < 768 # Legacy algorithms for Secure Socket Layer/Transport Layer Security (SSL/TLS) # processing in JSSE implementation. @@ -580,7 +580,7 @@ # 1. JSSE cipher suite name, e.g., TLS_RSA_WITH_AES_128_CBC_SHA # 2. JSSE key exchange algorithm name, e.g., RSA # 3. JSSE cipher (encryption) algorithm name, e.g., AES_128_CBC -# 4. JSSE message digest algorithm name, e.g., SHA-1 +# 4. JSSE message digest algorithm name, e.g., SHA # # See SSL/TLS specifications and "Java Cryptography Architecture Standard # Algorithm Name Documentation" for information about the algorithm names. @@ -598,4 +598,4 @@ DHE_DSS_EXPORT, DHE_RSA_EXPORT, DH_anon_EXPORT, DH_DSS_EXPORT, \ DH_RSA_EXPORT, RSA_EXPORT, \ DH_anon, ECDH_anon, \ - RC4_128, RC4_40, DES_CBC, DES40_CBC \ No newline at end of file + RC4_128, RC4_40, DES_CBC, DES40_CBC diff -r cca718f2fcf0 -r e4d5230193da jdk/test/javax/net/ssl/sanity/interop/ClientJSSEServerJSSE.java --- a/jdk/test/javax/net/ssl/sanity/interop/ClientJSSEServerJSSE.java Tue Apr 21 20:33:34 2015 +0100 +++ b/jdk/test/javax/net/ssl/sanity/interop/ClientJSSEServerJSSE.java Wed Apr 22 05:09:54 2015 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2002, 2014, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2002, 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 @@ -33,13 +33,10 @@ public class ClientJSSEServerJSSE { public static void main(String[] args) throws Exception { - // reset the security property to make sure that the algorithms + // reset security properties to make sure that the algorithms // and keys used in this test are not disabled. Security.setProperty("jdk.tls.disabledAlgorithms", ""); - - // MD5 is used in this test case, don't disable MD5 algorithm. - Security.setProperty( - "jdk.certpath.disabledAlgorithms", "MD2, RSA keySize < 1024"); + Security.setProperty("jdk.certpath.disabledAlgorithms", ""); CipherTest.main(new JSSEFactory(), args); } diff -r cca718f2fcf0 -r e4d5230193da jdk/test/sun/security/ec/TestEC.java --- a/jdk/test/sun/security/ec/TestEC.java Tue Apr 21 20:33:34 2015 +0100 +++ b/jdk/test/sun/security/ec/TestEC.java Wed Apr 22 05:09:54 2015 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2009, 2014, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2009, 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 @@ -60,13 +60,10 @@ public class TestEC { public static void main(String[] args) throws Exception { - // reset the security property to make sure that the algorithms + // reset security properties to make sure that the algorithms // and keys used in this test are not disabled. Security.setProperty("jdk.tls.disabledAlgorithms", ""); - - // MD5 is used in this test case, don't disable MD5 algorithm. - Security.setProperty( - "jdk.certpath.disabledAlgorithms", "MD2, RSA keySize < 1024"); + Security.setProperty("jdk.certpath.disabledAlgorithms", ""); ProvidersSnapshot snapshot = ProvidersSnapshot.create(); try { diff -r cca718f2fcf0 -r e4d5230193da jdk/test/sun/security/pkcs11/sslecc/ClientJSSEServerJSSE.java --- a/jdk/test/sun/security/pkcs11/sslecc/ClientJSSEServerJSSE.java Tue Apr 21 20:33:34 2015 +0100 +++ b/jdk/test/sun/security/pkcs11/sslecc/ClientJSSEServerJSSE.java Wed Apr 22 05:09:54 2015 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2002, 2014, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2002, 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 @@ -43,18 +43,15 @@ private static String[] cmdArgs; public static void main(String[] args) throws Exception { - // reset the security property to make sure that the algorithms - // and keys used in this test are not disabled. - Security.setProperty("jdk.tls.disabledAlgorithms", ""); - cmdArgs = args; main(new ClientJSSEServerJSSE()); } public void main(Provider p) throws Exception { - // MD5 is used in this test case, don't disable MD5 algorithm. - Security.setProperty( - "jdk.certpath.disabledAlgorithms", "MD2, RSA keySize < 1024"); + // reset security properties to make sure that the algorithms + // and keys used in this test are not disabled. + Security.setProperty("jdk.tls.disabledAlgorithms", ""); + Security.setProperty("jdk.certpath.disabledAlgorithms", ""); if (p.getService("KeyFactory", "EC") == null) { System.out.println("Provider does not support EC, skipping"); diff -r cca718f2fcf0 -r e4d5230193da jdk/test/sun/security/ssl/DHKeyExchange/DHEKeySizing.java --- a/jdk/test/sun/security/ssl/DHKeyExchange/DHEKeySizing.java Tue Apr 21 20:33:34 2015 +0100 +++ b/jdk/test/sun/security/ssl/DHKeyExchange/DHEKeySizing.java Wed Apr 22 05:09:54 2015 +0000 @@ -377,9 +377,10 @@ } public static void main(String args[]) throws Exception { - // reset the security property to make sure that the algorithms + // reset security properties to make sure that the algorithms // and keys used in this test are not disabled. Security.setProperty("jdk.tls.disabledAlgorithms", ""); + Security.setProperty("jdk.certpath.disabledAlgorithms", ""); if (args.length != 4) { System.out.println( diff -r cca718f2fcf0 -r e4d5230193da jdk/test/sun/security/ssl/ServerHandshaker/AnonCipherWithWantClientAuth.java --- a/jdk/test/sun/security/ssl/ServerHandshaker/AnonCipherWithWantClientAuth.java Tue Apr 21 20:33:34 2015 +0100 +++ b/jdk/test/sun/security/ssl/ServerHandshaker/AnonCipherWithWantClientAuth.java Wed Apr 22 05:09:54 2015 +0000 @@ -1,5 +1,5 @@ /* - * Copyright (c) 2001, 2011, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2001, 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 @@ -21,19 +21,22 @@ * questions. */ +// +// SunJSSE does not support dynamic system properties, no way to re-use +// system properties in samevm/agentvm mode. +// + /* * @test * @bug 4392475 * @summary Calling setWantClientAuth(true) disables anonymous suites * @run main/othervm/timeout=180 AnonCipherWithWantClientAuth - * - * SunJSSE does not support dynamic system properties, no way to re-use - * system properties in samevm/agentvm mode. */ import java.io.*; import java.net.*; import javax.net.ssl.*; +import java.security.Security; public class AnonCipherWithWantClientAuth { @@ -156,6 +159,11 @@ volatile Exception clientException = null; public static void main(String[] args) throws Exception { + // reset security properties to make sure that the algorithms + // and keys used in this test are not disabled. + Security.setProperty("jdk.tls.disabledAlgorithms", ""); + Security.setProperty("jdk.certpath.disabledAlgorithms", ""); + String keyFilename = System.getProperty("test.src", "./") + "/" + pathToStores + "/" + keyStoreFile;