6948803: CertPath validation regression caused by SHA1 replacement root and MD2 disable feature
authorweijun
Mon, 24 May 2010 09:28:06 +0800
changeset 5613 1146efa21514
parent 5612 c0d1673e1ca6
child 5614 9b34aca7cd0c
6948803: CertPath validation regression caused by SHA1 replacement root and MD2 disable feature Reviewed-by: xuelei, mullan
jdk/src/share/classes/sun/security/validator/PKIXValidator.java
jdk/test/sun/security/validator/CertReplace.java
jdk/test/sun/security/validator/certreplace.sh
--- a/jdk/src/share/classes/sun/security/validator/PKIXValidator.java	Fri May 21 07:29:48 2010 +0100
+++ b/jdk/src/share/classes/sun/security/validator/PKIXValidator.java	Mon May 24 09:28:06 2010 +0800
@@ -1,5 +1,5 @@
 /*
- * Copyright 2002-2009 Sun Microsystems, Inc.  All Rights Reserved.
+ * Copyright 2002-2010 Sun Microsystems, Inc.  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
@@ -155,12 +155,15 @@
             X500Principal prevIssuer = null;
             for (int i = 0; i < chain.length; i++) {
                 X509Certificate cert = chain[i];
+                X500Principal dn = cert.getSubjectX500Principal();
                 if (i != 0 &&
-                    !cert.getSubjectX500Principal().equals(prevIssuer)) {
+                    !dn.equals(prevIssuer)) {
                     // chain is not ordered correctly, call builder instead
                     return doBuild(chain, otherCerts);
                 }
-                if (trustedCerts.contains(cert)) {
+                if (trustedSubjects.containsKey(dn)
+                        && trustedSubjects.get(dn).getPublicKey()
+                            .equals(cert.getPublicKey())) {
                     if (i == 0) {
                         return new X509Certificate[] {chain[0]};
                     }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/sun/security/validator/CertReplace.java	Mon May 24 09:28:06 2010 +0800
@@ -0,0 +1,63 @@
+/*
+ * Copyright 2010 Sun Microsystems, Inc.  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.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
+ * CA 95054 USA or visit www.sun.com if you need additional information or
+ * have any questions.
+ */
+
+/*
+ * This test is called by certreplace.sh
+ */
+
+import java.io.FileInputStream;
+import java.security.KeyStore;
+import java.security.cert.Certificate;
+import java.security.cert.CertificateFactory;
+import java.security.cert.X509Certificate;
+import java.util.Arrays;
+import java.util.ArrayList;
+import java.util.List;
+import sun.security.validator.Validator;
+
+public class CertReplace {
+
+    private final static String cacerts = "certreplace.jks";
+    private final static String certs = "certreplace.certs";
+
+    public static void main(String[] args) throws Exception {
+
+        KeyStore ks = KeyStore.getInstance("JKS");
+        ks.load(new FileInputStream(cacerts), "changeit".toCharArray());
+        Validator v = Validator.getInstance
+            (Validator.TYPE_PKIX, Validator.VAR_GENERIC, ks);
+        X509Certificate[] chain = createPath();
+        System.out.println(Arrays.toString(v.validate(chain)));
+
+    }
+
+    public static X509Certificate[] createPath() throws Exception {
+        CertificateFactory cf = CertificateFactory.getInstance("X.509");
+        List list = new ArrayList();
+        for (Certificate c: cf.generateCertificates(
+                new FileInputStream(certs))) {
+            list.add((X509Certificate)c);
+        }
+        return (X509Certificate[]) list.toArray(new X509Certificate[0]);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/sun/security/validator/certreplace.sh	Mon May 24 09:28:06 2010 +0800
@@ -0,0 +1,85 @@
+#
+# Copyright 2010 Sun Microsystems, Inc.  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.
+#
+# This code is distributed in the hope that it will be useful, but WITHOUT
+# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+# FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+# version 2 for more details (a copy is included in the LICENSE file that
+# accompanied this code).
+#
+# You should have received a copy of the GNU General Public License version
+# 2 along with this work; if not, write to the Free Software Foundation,
+# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+#
+# Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
+# CA 95054 USA or visit www.sun.com if you need additional information or
+# have any questions.
+#
+
+# @test
+# @bug 6948803
+# @summary CertPath validation regression caused by SHA1 replacement root
+#  and MD2 disable feature
+#
+
+if [ "${TESTSRC}" = "" ] ; then
+  TESTSRC="."
+fi
+if [ "${TESTJAVA}" = "" ] ; then
+  JAVAC_CMD=`which javac`
+  TESTJAVA=`dirname $JAVAC_CMD`/..
+fi
+
+# set platform-dependent variables
+OS=`uname -s`
+case "$OS" in
+  Windows_* )
+    FS="\\"
+    ;;
+  * )
+    FS="/"
+    ;;
+esac
+
+KT="$TESTJAVA${FS}bin${FS}keytool -storepass changeit \
+    -keypass changeit -keystore certreplace.jks"
+JAVAC=$TESTJAVA${FS}bin${FS}javac
+JAVA=$TESTJAVA${FS}bin${FS}java
+
+rm -rf certreplace.jks 2> /dev/null
+
+# 1. Generate 3 aliases in a keystore: ca, int, user
+
+$KT -genkeypair -alias ca -dname CN=CA -keyalg rsa -sigalg md2withrsa -ext bc
+$KT -genkeypair -alias int -dname CN=Int -keyalg rsa
+$KT -genkeypair -alias user -dname CN=User -keyalg rsa
+
+# 2. Signing: ca -> int -> user
+
+$KT -certreq -alias int | $KT -gencert -rfc -alias ca -ext bc \
+    | $KT -import -alias int
+$KT -certreq -alias user | $KT -gencert -rfc -alias int \
+    | $KT -import -alias user
+
+# 3. Create the certchain file
+
+$KT -export -alias user -rfc > certreplace.certs
+$KT -export -rfc -alias int >> certreplace.certs
+$KT -export -rfc -alias ca >> certreplace.certs
+
+# 4. Upgrade ca from MD2withRSA to SHA256withRSA, remove other aliases and
+# make this keystore the cacerts file
+
+$KT -selfcert -alias ca
+$KT -delete -alias int
+$KT -delete -alias user
+
+# 5. Build and run test
+
+$JAVAC -d . ${TESTSRC}${FS}CertReplace.java
+$JAVA CertReplace