# HG changeset patch # User weijun # Date 1484697773 -28800 # Node ID b50e0f90d2846338b42541746ee43c85560de4f7 # Parent 66e6655abfdee6c64cec72db1ed7826b942acf93 8172529: Use PKIXValidator in jarsigner Reviewed-by: xuelei, mullan, alanb diff -r 66e6655abfde -r b50e0f90d284 jdk/src/java.base/share/classes/module-info.java --- a/jdk/src/java.base/share/classes/module-info.java Tue Jan 17 11:34:47 2017 -0800 +++ b/jdk/src/java.base/share/classes/module-info.java Wed Jan 18 08:02:53 2017 +0800 @@ -290,6 +290,8 @@ jdk.crypto.token, jdk.jartool, jdk.security.auth; + exports sun.security.validator to + jdk.jartool; exports sun.text.resources to jdk.localedata; exports sun.util.cldr to diff -r 66e6655abfde -r b50e0f90d284 jdk/src/jdk.jartool/share/classes/sun/security/tools/jarsigner/Main.java --- a/jdk/src/jdk.jartool/share/classes/sun/security/tools/jarsigner/Main.java Tue Jan 17 11:34:47 2017 -0800 +++ b/jdk/src/jdk.jartool/share/classes/sun/security/tools/jarsigner/Main.java Wed Jan 18 08:02:53 2017 +0800 @@ -26,6 +26,8 @@ package sun.security.tools.jarsigner; import java.io.*; +import java.security.cert.CertPathValidatorException; +import java.security.cert.PKIXBuilderParameters; import java.util.*; import java.util.zip.*; import java.util.jar.*; @@ -40,11 +42,9 @@ import java.net.SocketTimeoutException; import java.net.URL; import java.security.cert.CertPath; -import java.security.cert.CertPathValidator; import java.security.cert.CertificateExpiredException; import java.security.cert.CertificateFactory; import java.security.cert.CertificateNotYetValidException; -import java.security.cert.PKIXParameters; import java.security.cert.TrustAnchor; import java.util.Map.Entry; @@ -54,6 +54,8 @@ import sun.security.pkcs.SignerInfo; import sun.security.timestamp.TimestampToken; import sun.security.tools.KeyStoreUtil; +import sun.security.validator.Validator; +import sun.security.validator.ValidatorException; import sun.security.x509.*; import sun.security.util.*; @@ -177,9 +179,7 @@ private boolean seeWeak = false; - CertificateFactory certificateFactory; - CertPathValidator validator; - PKIXParameters pkixParameters; + PKIXBuilderParameters pkixParameters; public void run(String args[]) { try { @@ -1623,19 +1623,10 @@ try { validateCertChain(certs); } catch (Exception e) { - if (debug) { - e.printStackTrace(); - } - if (e.getCause() != null && - (e.getCause() instanceof CertificateExpiredException || - e.getCause() instanceof CertificateNotYetValidException)) { - // No more warning, we alreay have hasExpiredCert or notYetValidCert - } else { - chainNotValidated = true; - chainNotValidatedReason = e; - sb.append(tab).append(rb.getString(".CertPath.not.validated.")) - .append(e.getLocalizedMessage()).append("]\n"); // TODO - } + chainNotValidated = true; + chainNotValidatedReason = e; + sb.append(tab).append(rb.getString(".CertPath.not.validated.")) + .append(e.getLocalizedMessage()).append("]\n"); // TODO } if (certs.size() == 1 && KeyStoreUtil.isSelfSigned((X509Certificate)certs.get(0))) { @@ -1654,9 +1645,6 @@ } try { - - certificateFactory = CertificateFactory.getInstance("X.509"); - validator = CertPathValidator.getInstance("PKIX"); Set tas = new HashSet<>(); try { KeyStore caks = KeyStoreUtil.getCacertsKeyStore(); @@ -1732,7 +1720,7 @@ } } finally { try { - pkixParameters = new PKIXParameters(tas); + pkixParameters = new PKIXBuilderParameters(tas, null); pkixParameters.setRevocationEnabled(false); } catch (InvalidAlgorithmParameterException ex) { // Only if tas is empty @@ -1899,17 +1887,8 @@ try { validateCertChain(Arrays.asList(certChain)); } catch (Exception e) { - if (debug) { - e.printStackTrace(); - } - if (e.getCause() != null && - (e.getCause() instanceof CertificateExpiredException || - e.getCause() instanceof CertificateNotYetValidException)) { - // No more warning, we already have hasExpiredCert or notYetValidCert - } else { - chainNotValidated = true; - chainNotValidatedReason = e; - } + chainNotValidated = true; + chainNotValidatedReason = e; } if (KeyStoreUtil.isSelfSigned(certChain[0])) { @@ -1966,18 +1945,40 @@ } void validateCertChain(List certs) throws Exception { - int cpLen = 0; - out: for (; cpLen 0) { - CertPath cp = certificateFactory.generateCertPath( - (cpLen == certs.size())? certs: certs.subList(0, cpLen)); - validator.validate(cp, pkixParameters); + throw e; } } diff -r 66e6655abfde -r b50e0f90d284 jdk/test/sun/security/tools/jarsigner/concise_jarsigner.sh --- a/jdk/test/sun/security/tools/jarsigner/concise_jarsigner.sh Tue Jan 17 11:34:47 2017 -0800 +++ b/jdk/test/sun/security/tools/jarsigner/concise_jarsigner.sh Wed Jan 18 08:02:53 2017 +0800 @@ -22,7 +22,7 @@ # # @test -# @bug 6802846 +# @bug 6802846 8172529 # @summary jarsigner needs enhanced cert validation(options) # # @run shell/timeout=240 concise_jarsigner.sh @@ -52,7 +52,7 @@ KS=js.ks KT="$TESTJAVA${FS}bin${FS}keytool ${TESTTOOLVMOPTS} -storepass changeit -keypass changeit -keystore $KS -keyalg rsa -keysize 1024" JAR="$TESTJAVA${FS}bin${FS}jar ${TESTTOOLVMOPTS}" -JARSIGNER="$TESTJAVA${FS}bin${FS}jarsigner ${TESTTOOLVMOPTS}" +JARSIGNER="$TESTJAVA${FS}bin${FS}jarsigner ${TESTTOOLVMOPTS} -debug" JAVAC="$TESTJAVA${FS}bin${FS}javac ${TESTTOOLVMOPTS} ${TESTJAVACOPTS}" rm $KS @@ -138,7 +138,7 @@ [ $LINES = 4 ] || exit $LINENO # ========================================================== -# Second part: exit code 2, 4, 8 +# Second part: exit code 2, 4, 8. # 16 and 32 already covered in the first part # ========================================================== @@ -174,11 +174,14 @@ $JARSIGNER -strict -keystore $KS -storepass changeit a.jar goodeku [ $? = 0 ] || exit $LINENO -# badchain signed by ca, but ca is removed later +# badchain signed by ca1, but ca1 is removed later $KT -genkeypair -alias badchain -dname CN=badchain -validity 365 -$KT -certreq -alias badchain | $KT -gencert -alias ca -validity 365 | \ +$KT -genkeypair -alias ca1 -dname CN=ca1 -ext bc -validity 365 +$KT -certreq -alias badchain | $KT -gencert -alias ca1 -validity 365 | \ $KT -importcert -alias badchain -$KT -delete -alias ca +# save ca1.cert for easy replay +$KT -exportcert -file ca1.cert -alias ca1 +$KT -delete -alias ca1 $JARSIGNER -strict -keystore $KS -storepass changeit a.jar badchain [ $? = 4 ] || exit $LINENO @@ -204,13 +207,41 @@ $JARSIGNER -strict -keystore $KS -storepass changeit -certchain certchain a.jar altchain [ $? = 0 ] || exit $LINENO -# but if ca2 is removed, -certchain does not work +# if ca2 is removed, -certchain still work because altchain is a self-signed entry and +# it is trusted by jarsigner +# save ca2.cert for easy replay +$KT -exportcert -file ca2.cert -alias ca2 $KT -delete -alias ca2 $JARSIGNER -strict -keystore $KS -storepass changeit -certchain certchain a.jar altchain +[ $? = 0 ] || exit $LINENO + +# if cert is imported, -certchain won't work because this certificate entry is not trusted +$KT -importcert -file certchain -alias altchain -noprompt +$JARSIGNER -strict -keystore $KS -storepass changeit -certchain certchain a.jar altchain [ $? = 4 ] || exit $LINENO $JARSIGNER -verify a.jar [ $? = 0 ] || exit $LINENO +# ========================================================== +# 8172529 +# ========================================================== + +$KT -genkeypair -alias ee -dname CN=ee +$KT -genkeypair -alias caone -dname CN=caone +$KT -genkeypair -alias catwo -dname CN=catwo + +$KT -certreq -alias ee | $KT -gencert -alias catwo -rfc > ee.cert +$KT -certreq -alias catwo | $KT -gencert -alias caone -sigalg MD5withRSA -rfc > catwo.cert + +# This certchain contains a cross-signed weak catwo.cert +cat ee.cert catwo.cert | $KT -importcert -alias ee + +$JAR cvf a.jar A1.class +$JARSIGNER -strict -keystore $KS -storepass changeit a.jar ee +[ $? = 0 ] || exit $LINENO +$JARSIGNER -strict -keystore $KS -storepass changeit -verify a.jar +[ $? = 0 ] || exit $LINENO + echo OK exit 0