8160655: Fix denyAfter and usage types for security properties
Reviewed-by: mullan, xuelei
This commit is contained in:
parent
125d4ea7d0
commit
ff277c8508
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 1996, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 1996, 2017, 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
|
||||
@ -37,6 +37,7 @@ import java.security.PublicKey;
|
||||
import java.security.Signature;
|
||||
import java.security.SignatureException;
|
||||
import java.security.Timestamp;
|
||||
import java.security.cert.CertPathValidatorException;
|
||||
import java.security.cert.CertificateException;
|
||||
import java.security.cert.CertificateFactory;
|
||||
import java.security.cert.CertPath;
|
||||
@ -48,6 +49,7 @@ import java.util.EnumSet;
|
||||
import java.util.Set;
|
||||
|
||||
import sun.security.timestamp.TimestampToken;
|
||||
import sun.security.util.ConstraintsParameters;
|
||||
import sun.security.util.Debug;
|
||||
import sun.security.util.DerEncoder;
|
||||
import sun.security.util.DerInputStream;
|
||||
@ -321,6 +323,8 @@ public class SignerInfo implements DerEncoder {
|
||||
data = content.getContentBytes();
|
||||
}
|
||||
|
||||
ConstraintsParameters cparams =
|
||||
new ConstraintsParameters(timestamp);
|
||||
String digestAlgname = getDigestAlgorithmId().getName();
|
||||
|
||||
byte[] dataSigned;
|
||||
@ -347,11 +351,11 @@ public class SignerInfo implements DerEncoder {
|
||||
if (messageDigest == null) // fail if there is no message digest
|
||||
return null;
|
||||
|
||||
// check that algorithm is not restricted
|
||||
if (!JAR_DISABLED_CHECK.permits(DIGEST_PRIMITIVE_SET,
|
||||
digestAlgname, null)) {
|
||||
throw new SignatureException("Digest check failed. " +
|
||||
"Disabled algorithm used: " + digestAlgname);
|
||||
// check that digest algorithm is not restricted
|
||||
try {
|
||||
JAR_DISABLED_CHECK.permits(digestAlgname, cparams);
|
||||
} catch (CertPathValidatorException e) {
|
||||
throw new SignatureException(e.getMessage(), e);
|
||||
}
|
||||
|
||||
MessageDigest md = MessageDigest.getInstance(digestAlgname);
|
||||
@ -385,17 +389,18 @@ public class SignerInfo implements DerEncoder {
|
||||
String algname = AlgorithmId.makeSigAlg(
|
||||
digestAlgname, encryptionAlgname);
|
||||
|
||||
// check that algorithm is not restricted
|
||||
if (!JAR_DISABLED_CHECK.permits(SIG_PRIMITIVE_SET, algname, null)) {
|
||||
throw new SignatureException("Signature check failed. " +
|
||||
"Disabled algorithm used: " + algname);
|
||||
// check that jar signature algorithm is not restricted
|
||||
try {
|
||||
JAR_DISABLED_CHECK.permits(algname, cparams);
|
||||
} catch (CertPathValidatorException e) {
|
||||
throw new SignatureException(e.getMessage(), e);
|
||||
}
|
||||
|
||||
X509Certificate cert = getCertificate(block);
|
||||
PublicKey key = cert.getPublicKey();
|
||||
if (cert == null) {
|
||||
return null;
|
||||
}
|
||||
PublicKey key = cert.getPublicKey();
|
||||
|
||||
// check if the public key is restricted
|
||||
if (!JAR_DISABLED_CHECK.permits(SIG_PRIMITIVE_SET, key)) {
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2009, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2009, 2017, 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
|
||||
@ -28,6 +28,7 @@ package sun.security.provider.certpath;
|
||||
import java.security.AlgorithmConstraints;
|
||||
import java.security.CryptoPrimitive;
|
||||
import java.security.Timestamp;
|
||||
import java.security.cert.CertPathValidator;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.Date;
|
||||
@ -53,9 +54,10 @@ import java.security.interfaces.DSAPublicKey;
|
||||
import java.security.spec.DSAPublicKeySpec;
|
||||
|
||||
import sun.security.util.AnchorCertificates;
|
||||
import sun.security.util.CertConstraintParameters;
|
||||
import sun.security.util.ConstraintsParameters;
|
||||
import sun.security.util.Debug;
|
||||
import sun.security.util.DisabledAlgorithmConstraints;
|
||||
import sun.security.validator.Validator;
|
||||
import sun.security.x509.X509CertImpl;
|
||||
import sun.security.x509.X509CRLImpl;
|
||||
import sun.security.x509.AlgorithmId;
|
||||
@ -79,6 +81,7 @@ public final class AlgorithmChecker extends PKIXCertPathChecker {
|
||||
private final Date pkixdate;
|
||||
private PublicKey prevPubKey;
|
||||
private final Timestamp jarTimestamp;
|
||||
private final String variant;
|
||||
|
||||
private static final Set<CryptoPrimitive> SIGNATURE_PRIMITIVE_SET =
|
||||
Collections.unmodifiableSet(EnumSet.of(CryptoPrimitive.SIGNATURE));
|
||||
@ -109,64 +112,36 @@ public final class AlgorithmChecker extends PKIXCertPathChecker {
|
||||
*
|
||||
* @param anchor the trust anchor selected to validate the target
|
||||
* certificate
|
||||
* @param variant is the Validator variants of the operation. A null value
|
||||
* passed will set it to Validator.GENERIC.
|
||||
*/
|
||||
public AlgorithmChecker(TrustAnchor anchor) {
|
||||
this(anchor, certPathDefaultConstraints, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new {@code AlgorithmChecker} with the
|
||||
* given {@code TrustAnchor} and {@code AlgorithmConstraints}.
|
||||
*
|
||||
* @param anchor the trust anchor selected to validate the target
|
||||
* certificate
|
||||
* @param constraints the algorithm constraints (or null)
|
||||
*
|
||||
* @throws IllegalArgumentException if the {@code anchor} is null
|
||||
*/
|
||||
public AlgorithmChecker(TrustAnchor anchor,
|
||||
AlgorithmConstraints constraints) {
|
||||
this(anchor, constraints, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new {@code AlgorithmChecker} with the
|
||||
* given {@code AlgorithmConstraints}.
|
||||
* <p>
|
||||
* Note that this constructor will be used to check a certification
|
||||
* path where the trust anchor is unknown, or a certificate list which may
|
||||
* contain the trust anchor. This constructor is used by SunJSSE.
|
||||
*
|
||||
* @param constraints the algorithm constraints (or null)
|
||||
*/
|
||||
public AlgorithmChecker(AlgorithmConstraints constraints) {
|
||||
this.prevPubKey = null;
|
||||
this.trustedPubKey = null;
|
||||
this.constraints = constraints;
|
||||
this.pkixdate = null;
|
||||
this.jarTimestamp = null;
|
||||
public AlgorithmChecker(TrustAnchor anchor, String variant) {
|
||||
this(anchor, certPathDefaultConstraints, null, variant);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new {@code AlgorithmChecker} with the given
|
||||
* {@code Timestamp}.
|
||||
* {@code AlgorithmConstraints}, {@code Timestamp}, and/or {@code Variant}.
|
||||
* <p>
|
||||
* Note that this constructor will be used to check a certification
|
||||
* path for signed JAR files that are timestamped.
|
||||
* Note that this constructor can initialize a variation of situations where
|
||||
* the AlgorithmConstraints, Timestamp, or Variant maybe known.
|
||||
*
|
||||
* @param constraints the algorithm constraints (or null)
|
||||
* @param jarTimestamp Timestamp passed for JAR timestamp constraint
|
||||
* checking. Set to null if not applicable.
|
||||
* @param variant is the Validator variants of the operation. A null value
|
||||
* passed will set it to Validator.GENERIC.
|
||||
*/
|
||||
public AlgorithmChecker(Timestamp jarTimestamp) {
|
||||
public AlgorithmChecker(AlgorithmConstraints constraints,
|
||||
Timestamp jarTimestamp, String variant) {
|
||||
this.prevPubKey = null;
|
||||
this.trustedPubKey = null;
|
||||
this.constraints = certPathDefaultConstraints;
|
||||
if (jarTimestamp == null) {
|
||||
throw new IllegalArgumentException(
|
||||
"Timestamp cannot be null");
|
||||
}
|
||||
this.pkixdate = jarTimestamp.getTimestamp();
|
||||
this.constraints = (constraints == null ? certPathDefaultConstraints :
|
||||
constraints);
|
||||
this.pkixdate = (jarTimestamp != null ? jarTimestamp.getTimestamp() :
|
||||
null);
|
||||
this.jarTimestamp = jarTimestamp;
|
||||
this.variant = (variant == null ? Validator.VAR_GENERIC : variant);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -178,12 +153,13 @@ public final class AlgorithmChecker extends PKIXCertPathChecker {
|
||||
* @param constraints the algorithm constraints (or null)
|
||||
* @param pkixdate Date the constraints are checked against. The value is
|
||||
* either the PKIXParameter date or null for the current date.
|
||||
* @param variant is the Validator variants of the operation. A null value
|
||||
* passed will set it to Validator.GENERIC.
|
||||
*
|
||||
* @throws IllegalArgumentException if the {@code anchor} is null
|
||||
*/
|
||||
public AlgorithmChecker(TrustAnchor anchor,
|
||||
AlgorithmConstraints constraints,
|
||||
Date pkixdate) {
|
||||
AlgorithmConstraints constraints, Date pkixdate, String variant) {
|
||||
|
||||
if (anchor != null) {
|
||||
if (anchor.getTrustedCert() != null) {
|
||||
@ -207,6 +183,7 @@ public final class AlgorithmChecker extends PKIXCertPathChecker {
|
||||
this.constraints = constraints;
|
||||
this.pkixdate = pkixdate;
|
||||
this.jarTimestamp = null;
|
||||
this.variant = (variant == null ? Validator.VAR_GENERIC : variant);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -217,11 +194,13 @@ public final class AlgorithmChecker extends PKIXCertPathChecker {
|
||||
* certificate
|
||||
* @param pkixdate Date the constraints are checked against. The value is
|
||||
* either the PKIXParameter date or null for the current date.
|
||||
* @param variant is the Validator variants of the operation. A null value
|
||||
* passed will set it to Validator.GENERIC.
|
||||
*
|
||||
* @throws IllegalArgumentException if the {@code anchor} is null
|
||||
*/
|
||||
public AlgorithmChecker(TrustAnchor anchor, Date pkixdate) {
|
||||
this(anchor, certPathDefaultConstraints, pkixdate);
|
||||
public AlgorithmChecker(TrustAnchor anchor, Date pkixdate, String variant) {
|
||||
this(anchor, certPathDefaultConstraints, pkixdate, variant);
|
||||
}
|
||||
|
||||
// Check this 'cert' for restrictions in the AnchorCertificates
|
||||
@ -286,6 +265,28 @@ public final class AlgorithmChecker extends PKIXCertPathChecker {
|
||||
null, null, -1, PKIXReason.INVALID_KEY_USAGE);
|
||||
}
|
||||
|
||||
X509CertImpl x509Cert;
|
||||
AlgorithmId algorithmId;
|
||||
try {
|
||||
x509Cert = X509CertImpl.toImpl((X509Certificate)cert);
|
||||
algorithmId = (AlgorithmId)x509Cert.get(X509CertImpl.SIG_ALG);
|
||||
} catch (CertificateException ce) {
|
||||
throw new CertPathValidatorException(ce);
|
||||
}
|
||||
|
||||
AlgorithmParameters currSigAlgParams = algorithmId.getParameters();
|
||||
PublicKey currPubKey = cert.getPublicKey();
|
||||
String currSigAlg = x509Cert.getSigAlgName();
|
||||
|
||||
// Check the signature algorithm and parameters against constraints.
|
||||
if (!constraints.permits(SIGNATURE_PRIMITIVE_SET, currSigAlg,
|
||||
currSigAlgParams)) {
|
||||
throw new CertPathValidatorException(
|
||||
"Algorithm constraints check failed on signature " +
|
||||
"algorithm: " + currSigAlg, null, null, -1,
|
||||
BasicReason.ALGORITHM_CONSTRAINED);
|
||||
}
|
||||
|
||||
// Assume all key usage bits are set if key usage is not present
|
||||
Set<CryptoPrimitive> primitives = KU_PRIMITIVE_SET;
|
||||
|
||||
@ -322,101 +323,74 @@ public final class AlgorithmChecker extends PKIXCertPathChecker {
|
||||
}
|
||||
}
|
||||
|
||||
PublicKey currPubKey = cert.getPublicKey();
|
||||
ConstraintsParameters cp =
|
||||
new ConstraintsParameters((X509Certificate)cert,
|
||||
trustedMatch, pkixdate, jarTimestamp, variant);
|
||||
|
||||
// Check against local constraints if it is DisabledAlgorithmConstraints
|
||||
if (constraints instanceof DisabledAlgorithmConstraints) {
|
||||
// Check against DisabledAlgorithmConstraints certpath constraints.
|
||||
// permits() will throw exception on failure.
|
||||
((DisabledAlgorithmConstraints)constraints).permits(primitives,
|
||||
new CertConstraintParameters((X509Certificate)cert,
|
||||
trustedMatch, pkixdate, jarTimestamp));
|
||||
// If there is no previous key, set one and exit
|
||||
if (prevPubKey == null) {
|
||||
prevPubKey = currPubKey;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
X509CertImpl x509Cert;
|
||||
AlgorithmId algorithmId;
|
||||
try {
|
||||
x509Cert = X509CertImpl.toImpl((X509Certificate)cert);
|
||||
algorithmId = (AlgorithmId)x509Cert.get(X509CertImpl.SIG_ALG);
|
||||
} catch (CertificateException ce) {
|
||||
throw new CertPathValidatorException(ce);
|
||||
}
|
||||
|
||||
AlgorithmParameters currSigAlgParams = algorithmId.getParameters();
|
||||
String currSigAlg = x509Cert.getSigAlgName();
|
||||
|
||||
// If 'constraints' is not of DisabledAlgorithmConstraints, check all
|
||||
// everything individually
|
||||
if (!(constraints instanceof DisabledAlgorithmConstraints)) {
|
||||
// Check the current signature algorithm
|
||||
if (!constraints.permits(
|
||||
SIGNATURE_PRIMITIVE_SET,
|
||||
currSigAlg, currSigAlgParams)) {
|
||||
throw new CertPathValidatorException(
|
||||
"Algorithm constraints check failed on signature " +
|
||||
"algorithm: " + currSigAlg, null, null, -1,
|
||||
BasicReason.ALGORITHM_CONSTRAINED);
|
||||
}
|
||||
((DisabledAlgorithmConstraints)constraints).permits(currSigAlg, cp);
|
||||
// DisabledAlgorithmsConstraints does not check primitives, so key
|
||||
// additional key check.
|
||||
|
||||
} else {
|
||||
// Perform the default constraints checking anyway.
|
||||
certPathDefaultConstraints.permits(currSigAlg, cp);
|
||||
// Call locally set constraints to check key with primitives.
|
||||
if (!constraints.permits(primitives, currPubKey)) {
|
||||
throw new CertPathValidatorException(
|
||||
"Algorithm constraints check failed on keysize: " +
|
||||
sun.security.util.KeyUtil.getKeySize(currPubKey),
|
||||
"Algorithm constraints check failed on key " +
|
||||
currPubKey.getAlgorithm() + " with size of " +
|
||||
sun.security.util.KeyUtil.getKeySize(currPubKey) +
|
||||
"bits",
|
||||
null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
|
||||
}
|
||||
}
|
||||
|
||||
// If there is no previous key, set one and exit
|
||||
if (prevPubKey == null) {
|
||||
prevPubKey = currPubKey;
|
||||
return;
|
||||
}
|
||||
|
||||
// Check with previous cert for signature algorithm and public key
|
||||
if (prevPubKey != null) {
|
||||
if (!constraints.permits(
|
||||
SIGNATURE_PRIMITIVE_SET,
|
||||
currSigAlg, prevPubKey, currSigAlgParams)) {
|
||||
throw new CertPathValidatorException(
|
||||
if (!constraints.permits(
|
||||
SIGNATURE_PRIMITIVE_SET,
|
||||
currSigAlg, prevPubKey, currSigAlgParams)) {
|
||||
throw new CertPathValidatorException(
|
||||
"Algorithm constraints check failed on " +
|
||||
"signature algorithm: " + currSigAlg,
|
||||
null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
|
||||
}
|
||||
|
||||
// Inherit key parameters from previous key
|
||||
if (PKIX.isDSAPublicKeyWithoutParams(currPubKey)) {
|
||||
// Inherit DSA parameters from previous key
|
||||
if (!(prevPubKey instanceof DSAPublicKey)) {
|
||||
throw new CertPathValidatorException("Input key is not " +
|
||||
"of a appropriate type for inheriting parameters");
|
||||
}
|
||||
|
||||
// Inherit key parameters from previous key
|
||||
if (PKIX.isDSAPublicKeyWithoutParams(currPubKey)) {
|
||||
// Inherit DSA parameters from previous key
|
||||
if (!(prevPubKey instanceof DSAPublicKey)) {
|
||||
throw new CertPathValidatorException("Input key is not " +
|
||||
"of a appropriate type for inheriting parameters");
|
||||
}
|
||||
|
||||
DSAParams params = ((DSAPublicKey)prevPubKey).getParams();
|
||||
if (params == null) {
|
||||
throw new CertPathValidatorException(
|
||||
DSAParams params = ((DSAPublicKey)prevPubKey).getParams();
|
||||
if (params == null) {
|
||||
throw new CertPathValidatorException(
|
||||
"Key parameters missing from public key.");
|
||||
}
|
||||
}
|
||||
|
||||
try {
|
||||
BigInteger y = ((DSAPublicKey)currPubKey).getY();
|
||||
KeyFactory kf = KeyFactory.getInstance("DSA");
|
||||
DSAPublicKeySpec ks = new DSAPublicKeySpec(y,
|
||||
params.getP(),
|
||||
params.getQ(),
|
||||
params.getG());
|
||||
currPubKey = kf.generatePublic(ks);
|
||||
} catch (GeneralSecurityException e) {
|
||||
throw new CertPathValidatorException("Unable to generate " +
|
||||
try {
|
||||
BigInteger y = ((DSAPublicKey)currPubKey).getY();
|
||||
KeyFactory kf = KeyFactory.getInstance("DSA");
|
||||
DSAPublicKeySpec ks = new DSAPublicKeySpec(y, params.getP(),
|
||||
params.getQ(), params.getG());
|
||||
currPubKey = kf.generatePublic(ks);
|
||||
} catch (GeneralSecurityException e) {
|
||||
throw new CertPathValidatorException("Unable to generate " +
|
||||
"key with inherited parameters: " + e.getMessage(), e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// reset the previous public key
|
||||
prevPubKey = currPubKey;
|
||||
|
||||
// check the extended key usage, ignore the check now
|
||||
// List<String> extendedKeyUsages = x509Cert.getExtendedKeyUsage();
|
||||
|
||||
// DO NOT remove any unresolved critical extensions
|
||||
}
|
||||
|
||||
/**
|
||||
@ -456,8 +430,10 @@ public final class AlgorithmChecker extends PKIXCertPathChecker {
|
||||
*
|
||||
* @param key the public key to verify the CRL signature
|
||||
* @param crl the target CRL
|
||||
* @param variant is the Validator variants of the operation. A null value
|
||||
* passed will set it to Validator.GENERIC.
|
||||
*/
|
||||
static void check(PublicKey key, X509CRL crl)
|
||||
static void check(PublicKey key, X509CRL crl, String variant)
|
||||
throws CertPathValidatorException {
|
||||
|
||||
X509CRLImpl x509CRLImpl = null;
|
||||
@ -468,7 +444,7 @@ public final class AlgorithmChecker extends PKIXCertPathChecker {
|
||||
}
|
||||
|
||||
AlgorithmId algorithmId = x509CRLImpl.getSigAlgId();
|
||||
check(key, algorithmId);
|
||||
check(key, algorithmId, variant);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -476,20 +452,16 @@ public final class AlgorithmChecker extends PKIXCertPathChecker {
|
||||
*
|
||||
* @param key the public key to verify the CRL signature
|
||||
* @param algorithmId signature algorithm Algorithm ID
|
||||
* @param variant is the Validator variants of the operation. A null value
|
||||
* passed will set it to Validator.GENERIC.
|
||||
*/
|
||||
static void check(PublicKey key, AlgorithmId algorithmId)
|
||||
static void check(PublicKey key, AlgorithmId algorithmId, String variant)
|
||||
throws CertPathValidatorException {
|
||||
String sigAlgName = algorithmId.getName();
|
||||
AlgorithmParameters sigAlgParams = algorithmId.getParameters();
|
||||
|
||||
if (!certPathDefaultConstraints.permits(
|
||||
SIGNATURE_PRIMITIVE_SET, sigAlgName, key, sigAlgParams)) {
|
||||
throw new CertPathValidatorException(
|
||||
"Algorithm constraints check failed on signature algorithm: " +
|
||||
sigAlgName + " is disabled",
|
||||
null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
|
||||
}
|
||||
certPathDefaultConstraints.permits(new ConstraintsParameters(
|
||||
sigAlgName, sigAlgParams, key, variant));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2002, 2015, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2002, 2017, 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,6 +33,7 @@ import javax.security.auth.x500.X500Principal;
|
||||
import java.util.*;
|
||||
|
||||
import sun.security.util.Debug;
|
||||
import sun.security.validator.Validator;
|
||||
import static sun.security.x509.PKIXExtensions.*;
|
||||
import sun.security.x509.*;
|
||||
|
||||
@ -65,6 +66,20 @@ public class DistributionPointFetcher {
|
||||
* Return the X509CRLs matching this selector. The selector must be
|
||||
* an X509CRLSelector with certificateChecking set.
|
||||
*/
|
||||
public static Collection<X509CRL> getCRLs(X509CRLSelector selector,
|
||||
boolean signFlag, PublicKey prevKey, String provider,
|
||||
List<CertStore> certStores, boolean[] reasonsMask,
|
||||
Set<TrustAnchor> trustAnchors, Date validity, String variant)
|
||||
throws CertStoreException
|
||||
{
|
||||
return getCRLs(selector, signFlag, prevKey, null, provider, certStores,
|
||||
reasonsMask, trustAnchors, validity, variant);
|
||||
}
|
||||
/**
|
||||
* Return the X509CRLs matching this selector. The selector must be
|
||||
* an X509CRLSelector with certificateChecking set.
|
||||
*/
|
||||
// Called by com.sun.deploy.security.RevocationChecker
|
||||
public static Collection<X509CRL> getCRLs(X509CRLSelector selector,
|
||||
boolean signFlag,
|
||||
PublicKey prevKey,
|
||||
@ -76,7 +91,7 @@ public class DistributionPointFetcher {
|
||||
throws CertStoreException
|
||||
{
|
||||
return getCRLs(selector, signFlag, prevKey, null, provider, certStores,
|
||||
reasonsMask, trustAnchors, validity);
|
||||
reasonsMask, trustAnchors, validity, Validator.VAR_GENERIC);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -91,7 +106,8 @@ public class DistributionPointFetcher {
|
||||
List<CertStore> certStores,
|
||||
boolean[] reasonsMask,
|
||||
Set<TrustAnchor> trustAnchors,
|
||||
Date validity)
|
||||
Date validity,
|
||||
String variant)
|
||||
throws CertStoreException
|
||||
{
|
||||
X509Certificate cert = selector.getCertificateChecking();
|
||||
@ -120,7 +136,7 @@ public class DistributionPointFetcher {
|
||||
DistributionPoint point = t.next();
|
||||
Collection<X509CRL> crls = getCRLs(selector, certImpl,
|
||||
point, reasonsMask, signFlag, prevKey, prevCert, provider,
|
||||
certStores, trustAnchors, validity);
|
||||
certStores, trustAnchors, validity, variant);
|
||||
results.addAll(crls);
|
||||
}
|
||||
if (debug != null) {
|
||||
@ -145,7 +161,7 @@ public class DistributionPointFetcher {
|
||||
X509CertImpl certImpl, DistributionPoint point, boolean[] reasonsMask,
|
||||
boolean signFlag, PublicKey prevKey, X509Certificate prevCert,
|
||||
String provider, List<CertStore> certStores,
|
||||
Set<TrustAnchor> trustAnchors, Date validity)
|
||||
Set<TrustAnchor> trustAnchors, Date validity, String variant)
|
||||
throws CertStoreException {
|
||||
|
||||
// check for full name
|
||||
@ -208,7 +224,7 @@ public class DistributionPointFetcher {
|
||||
selector.setIssuerNames(null);
|
||||
if (selector.match(crl) && verifyCRL(certImpl, point, crl,
|
||||
reasonsMask, signFlag, prevKey, prevCert, provider,
|
||||
trustAnchors, certStores, validity)) {
|
||||
trustAnchors, certStores, validity, variant)) {
|
||||
crls.add(crl);
|
||||
}
|
||||
} catch (IOException | CRLException e) {
|
||||
@ -316,7 +332,7 @@ public class DistributionPointFetcher {
|
||||
X509CRL crl, boolean[] reasonsMask, boolean signFlag,
|
||||
PublicKey prevKey, X509Certificate prevCert, String provider,
|
||||
Set<TrustAnchor> trustAnchors, List<CertStore> certStores,
|
||||
Date validity) throws CRLException, IOException {
|
||||
Date validity, String variant) throws CRLException, IOException {
|
||||
|
||||
if (debug != null) {
|
||||
debug.println("DistributionPointFetcher.verifyCRL: " +
|
||||
@ -663,7 +679,7 @@ public class DistributionPointFetcher {
|
||||
|
||||
// check the crl signature algorithm
|
||||
try {
|
||||
AlgorithmChecker.check(prevKey, crl);
|
||||
AlgorithmChecker.check(prevKey, crl, variant);
|
||||
} catch (CertPathValidatorException cpve) {
|
||||
if (debug != null) {
|
||||
debug.println("CRL signature algorithm check failed: " + cpve);
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2009, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2009, 2017, 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
|
||||
@ -45,6 +45,7 @@ import java.util.Map;
|
||||
|
||||
import sun.security.action.GetIntegerAction;
|
||||
import sun.security.util.Debug;
|
||||
import sun.security.validator.Validator;
|
||||
import sun.security.x509.AccessDescription;
|
||||
import sun.security.x509.AuthorityInfoAccessExtension;
|
||||
import sun.security.x509.GeneralName;
|
||||
@ -94,42 +95,6 @@ public final class OCSP {
|
||||
|
||||
private OCSP() {}
|
||||
|
||||
/**
|
||||
* Obtains the revocation status of a certificate using OCSP using the most
|
||||
* common defaults. The OCSP responder URI is retrieved from the
|
||||
* certificate's AIA extension. The OCSP responder certificate is assumed
|
||||
* to be the issuer's certificate (or issued by the issuer CA).
|
||||
*
|
||||
* @param cert the certificate to be checked
|
||||
* @param issuerCert the issuer certificate
|
||||
* @return the RevocationStatus
|
||||
* @throws IOException if there is an exception connecting to or
|
||||
* communicating with the OCSP responder
|
||||
* @throws CertPathValidatorException if an exception occurs while
|
||||
* encoding the OCSP Request or validating the OCSP Response
|
||||
*/
|
||||
public static RevocationStatus check(X509Certificate cert,
|
||||
X509Certificate issuerCert)
|
||||
throws IOException, CertPathValidatorException {
|
||||
CertId certId = null;
|
||||
URI responderURI = null;
|
||||
try {
|
||||
X509CertImpl certImpl = X509CertImpl.toImpl(cert);
|
||||
responderURI = getResponderURI(certImpl);
|
||||
if (responderURI == null) {
|
||||
throw new CertPathValidatorException
|
||||
("No OCSP Responder URI in certificate");
|
||||
}
|
||||
certId = new CertId(issuerCert, certImpl.getSerialNumberObject());
|
||||
} catch (CertificateException | IOException e) {
|
||||
throw new CertPathValidatorException
|
||||
("Exception while encoding OCSPRequest", e);
|
||||
}
|
||||
OCSPResponse ocspResponse = check(Collections.singletonList(certId),
|
||||
responderURI, new OCSPResponse.IssuerInfo(issuerCert), null, null,
|
||||
Collections.<Extension>emptyList());
|
||||
return (RevocationStatus)ocspResponse.getSingleResponse(certId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Obtains the revocation status of a certificate using OCSP.
|
||||
@ -146,6 +111,8 @@ public final class OCSP {
|
||||
* @throws CertPathValidatorException if an exception occurs while
|
||||
* encoding the OCSP Request or validating the OCSP Response
|
||||
*/
|
||||
|
||||
// Called by com.sun.deploy.security.TrustDecider
|
||||
public static RevocationStatus check(X509Certificate cert,
|
||||
X509Certificate issuerCert,
|
||||
URI responderURI,
|
||||
@ -154,27 +121,27 @@ public final class OCSP {
|
||||
throws IOException, CertPathValidatorException
|
||||
{
|
||||
return check(cert, issuerCert, responderURI, responderCert, date,
|
||||
Collections.<Extension>emptyList());
|
||||
Collections.<Extension>emptyList(), Validator.VAR_GENERIC);
|
||||
}
|
||||
|
||||
// Called by com.sun.deploy.security.TrustDecider
|
||||
|
||||
public static RevocationStatus check(X509Certificate cert,
|
||||
X509Certificate issuerCert,
|
||||
URI responderURI,
|
||||
X509Certificate responderCert,
|
||||
Date date, List<Extension> extensions)
|
||||
X509Certificate issuerCert, URI responderURI,
|
||||
X509Certificate responderCert, Date date, List<Extension> extensions,
|
||||
String variant)
|
||||
throws IOException, CertPathValidatorException
|
||||
{
|
||||
return check(cert, responderURI, null, issuerCert, responderCert, date, extensions);
|
||||
return check(cert, responderURI, null, issuerCert, responderCert, date,
|
||||
extensions, variant);
|
||||
}
|
||||
|
||||
public static RevocationStatus check(X509Certificate cert,
|
||||
URI responderURI, TrustAnchor anchor, X509Certificate issuerCert,
|
||||
X509Certificate responderCert, Date date,
|
||||
List<Extension> extensions)
|
||||
List<Extension> extensions, String variant)
|
||||
throws IOException, CertPathValidatorException
|
||||
{
|
||||
CertId certId = null;
|
||||
CertId certId;
|
||||
try {
|
||||
X509CertImpl certImpl = X509CertImpl.toImpl(cert);
|
||||
certId = new CertId(issuerCert, certImpl.getSerialNumberObject());
|
||||
@ -184,7 +151,7 @@ public final class OCSP {
|
||||
}
|
||||
OCSPResponse ocspResponse = check(Collections.singletonList(certId),
|
||||
responderURI, new OCSPResponse.IssuerInfo(anchor, issuerCert),
|
||||
responderCert, date, extensions);
|
||||
responderCert, date, extensions, variant);
|
||||
return (RevocationStatus) ocspResponse.getSingleResponse(certId);
|
||||
}
|
||||
|
||||
@ -206,10 +173,10 @@ public final class OCSP {
|
||||
* @throws CertPathValidatorException if an exception occurs while
|
||||
* encoding the OCSP Request or validating the OCSP Response
|
||||
*/
|
||||
static OCSPResponse check(List<CertId> certIds, URI responderURI,
|
||||
static OCSPResponse check(List<CertId> certIds, URI responderURI,
|
||||
OCSPResponse.IssuerInfo issuerInfo,
|
||||
X509Certificate responderCert, Date date,
|
||||
List<Extension> extensions)
|
||||
List<Extension> extensions, String variant)
|
||||
throws IOException, CertPathValidatorException
|
||||
{
|
||||
byte[] nonce = null;
|
||||
@ -226,7 +193,7 @@ public final class OCSP {
|
||||
|
||||
// verify the response
|
||||
ocspResponse.verify(certIds, issuerInfo, responderCert, date,
|
||||
nonce);
|
||||
nonce, variant);
|
||||
} catch (IOException ioe) {
|
||||
throw new CertPathValidatorException(
|
||||
"Unable to determine revocation status due to network error",
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2003, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2003, 2017, 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
|
||||
@ -41,7 +41,6 @@ import java.util.Date;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
import java.util.Set;
|
||||
import javax.security.auth.x500.X500Principal;
|
||||
|
||||
@ -375,7 +374,8 @@ public final class OCSPResponse {
|
||||
}
|
||||
|
||||
void verify(List<CertId> certIds, IssuerInfo issuerInfo,
|
||||
X509Certificate responderCert, Date date, byte[] nonce)
|
||||
X509Certificate responderCert, Date date, byte[] nonce,
|
||||
String variant)
|
||||
throws CertPathValidatorException
|
||||
{
|
||||
switch (responseStatus) {
|
||||
@ -508,7 +508,8 @@ public final class OCSPResponse {
|
||||
// Check algorithm constraints specified in security property
|
||||
// "jdk.certpath.disabledAlgorithms".
|
||||
AlgorithmChecker algChecker =
|
||||
new AlgorithmChecker(issuerInfo.getAnchor(), date);
|
||||
new AlgorithmChecker(issuerInfo.getAnchor(), date,
|
||||
variant);
|
||||
algChecker.init(false);
|
||||
algChecker.check(signerCert, Collections.<String>emptySet());
|
||||
|
||||
@ -568,7 +569,7 @@ public final class OCSPResponse {
|
||||
if (signerCert != null) {
|
||||
// Check algorithm constraints specified in security property
|
||||
// "jdk.certpath.disabledAlgorithms".
|
||||
AlgorithmChecker.check(signerCert.getPublicKey(), sigAlgId);
|
||||
AlgorithmChecker.check(signerCert.getPublicKey(), sigAlgId, variant);
|
||||
|
||||
if (!verifySignature(signerCert)) {
|
||||
throw new CertPathValidatorException(
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2012, 2017, 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,6 +87,7 @@ class PKIX {
|
||||
private Set<TrustAnchor> anchors;
|
||||
private List<X509Certificate> certs;
|
||||
private Timestamp timestamp;
|
||||
private String variant;
|
||||
|
||||
ValidatorParams(CertPath cp, PKIXParameters params)
|
||||
throws InvalidAlgorithmParameterException
|
||||
@ -102,8 +103,9 @@ class PKIX {
|
||||
ValidatorParams(PKIXParameters params)
|
||||
throws InvalidAlgorithmParameterException
|
||||
{
|
||||
if (params instanceof PKIXTimestampParameters) {
|
||||
timestamp = ((PKIXTimestampParameters) params).getTimestamp();
|
||||
if (params instanceof PKIXExtendedParameters) {
|
||||
timestamp = ((PKIXExtendedParameters) params).getTimestamp();
|
||||
variant = ((PKIXExtendedParameters) params).getVariant();
|
||||
}
|
||||
|
||||
this.anchors = params.getTrustAnchors();
|
||||
@ -199,6 +201,10 @@ class PKIX {
|
||||
Timestamp timestamp() {
|
||||
return timestamp;
|
||||
}
|
||||
|
||||
String variant() {
|
||||
return variant;
|
||||
}
|
||||
}
|
||||
|
||||
static class BuilderParams extends ValidatorParams {
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2000, 2017, 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
|
||||
@ -173,9 +173,10 @@ public final class PKIXCertPathValidator extends CertPathValidatorSpi {
|
||||
// add standard checkers that we will be using
|
||||
certPathCheckers.add(untrustedChecker);
|
||||
if (params.timestamp() == null) {
|
||||
certPathCheckers.add(new AlgorithmChecker(anchor, params.date()));
|
||||
certPathCheckers.add(new AlgorithmChecker(anchor, params.date(), null));
|
||||
} else {
|
||||
certPathCheckers.add(new AlgorithmChecker(params.timestamp()));
|
||||
certPathCheckers.add(new AlgorithmChecker(null,
|
||||
params.timestamp(), params.variant()));
|
||||
}
|
||||
certPathCheckers.add(new KeyChecker(certPathLen,
|
||||
params.targetCertConstraints()));
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2016, 2017, 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
|
||||
@ -39,19 +39,23 @@ import java.util.Set;
|
||||
|
||||
/**
|
||||
* This class is a wrapper for PKIXBuilderParameters so that a Timestamp object
|
||||
* can be passed alone when PKIXCertPath is checking signed jar files.
|
||||
* and a string for the variant type, can be passed when doing certpath
|
||||
* checking.
|
||||
*/
|
||||
|
||||
public class PKIXTimestampParameters extends PKIXBuilderParameters {
|
||||
public class PKIXExtendedParameters extends PKIXBuilderParameters {
|
||||
|
||||
private final PKIXBuilderParameters p;
|
||||
private Timestamp jarTimestamp;
|
||||
private final String variant;
|
||||
|
||||
public PKIXTimestampParameters(PKIXBuilderParameters params,
|
||||
Timestamp timestamp) throws InvalidAlgorithmParameterException {
|
||||
public PKIXExtendedParameters(PKIXBuilderParameters params,
|
||||
Timestamp timestamp, String variant)
|
||||
throws InvalidAlgorithmParameterException {
|
||||
super(params.getTrustAnchors(), null);
|
||||
p = params;
|
||||
jarTimestamp = timestamp;
|
||||
this.variant = variant;
|
||||
}
|
||||
|
||||
public Timestamp getTimestamp() {
|
||||
@ -61,6 +65,10 @@ public class PKIXTimestampParameters extends PKIXBuilderParameters {
|
||||
jarTimestamp = t;
|
||||
}
|
||||
|
||||
public String getVariant() {
|
||||
return variant;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setDate(Date d) {
|
||||
p.setDate(d);
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2012, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2012, 2017, 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
|
||||
@ -579,7 +579,7 @@ class RevocationChecker extends PKIXRevocationChecker {
|
||||
approvedCRLs.addAll(DistributionPointFetcher.getCRLs(
|
||||
sel, signFlag, prevKey, prevCert,
|
||||
params.sigProvider(), certStores,
|
||||
reasonsMask, anchors, null));
|
||||
reasonsMask, anchors, null, params.variant()));
|
||||
}
|
||||
} catch (CertStoreException e) {
|
||||
if (e instanceof CertStoreTypeException) {
|
||||
@ -727,7 +727,7 @@ class RevocationChecker extends PKIXRevocationChecker {
|
||||
}
|
||||
}
|
||||
response.verify(Collections.singletonList(certId), issuerInfo,
|
||||
responderCert, params.date(), nonce);
|
||||
responderCert, params.date(), nonce, params.variant());
|
||||
|
||||
} else {
|
||||
URI responderURI = (this.responderURI != null)
|
||||
@ -741,7 +741,7 @@ class RevocationChecker extends PKIXRevocationChecker {
|
||||
|
||||
response = OCSP.check(Collections.singletonList(certId),
|
||||
responderURI, issuerInfo, responderCert, null,
|
||||
ocspExtensions);
|
||||
ocspExtensions, params.variant());
|
||||
}
|
||||
} catch (IOException e) {
|
||||
throw new CertPathValidatorException(
|
||||
@ -853,7 +853,7 @@ class RevocationChecker extends PKIXRevocationChecker {
|
||||
if (DistributionPointFetcher.verifyCRL(
|
||||
certImpl, point, crl, reasonsMask, signFlag,
|
||||
prevKey, null, params.sigProvider(), anchors,
|
||||
certStores, params.date()))
|
||||
certStores, params.date(), params.variant()))
|
||||
{
|
||||
results.add(crl);
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2000, 2015, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2000, 2017, 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
|
||||
@ -344,7 +344,7 @@ public final class SunCertPathBuilder extends CertPathBuilderSpi {
|
||||
|
||||
// add the algorithm checker
|
||||
checkers.add(new AlgorithmChecker(builder.trustAnchor,
|
||||
buildParams.date()));
|
||||
buildParams.date(), null));
|
||||
|
||||
BasicChecker basicChecker = null;
|
||||
if (nextState.keyParamsNeeded()) {
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 1999, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 1999, 2017, 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
|
||||
@ -37,6 +37,7 @@ import javax.net.ssl.*;
|
||||
|
||||
import sun.security.provider.certpath.AlgorithmChecker;
|
||||
import sun.security.action.GetPropertyAction;
|
||||
import sun.security.validator.Validator;
|
||||
|
||||
public abstract class SSLContextImpl extends SSLContextSpi {
|
||||
|
||||
@ -1436,7 +1437,7 @@ final class AbstractTrustManagerWrapper extends X509ExtendedTrustManager
|
||||
constraints = new SSLAlgorithmConstraints(sslSocket, true);
|
||||
}
|
||||
|
||||
checkAlgorithmConstraints(chain, constraints);
|
||||
checkAlgorithmConstraints(chain, constraints, isClient);
|
||||
}
|
||||
}
|
||||
|
||||
@ -1478,12 +1479,12 @@ final class AbstractTrustManagerWrapper extends X509ExtendedTrustManager
|
||||
constraints = new SSLAlgorithmConstraints(engine, true);
|
||||
}
|
||||
|
||||
checkAlgorithmConstraints(chain, constraints);
|
||||
checkAlgorithmConstraints(chain, constraints, isClient);
|
||||
}
|
||||
}
|
||||
|
||||
private void checkAlgorithmConstraints(X509Certificate[] chain,
|
||||
AlgorithmConstraints constraints) throws CertificateException {
|
||||
AlgorithmConstraints constraints, boolean isClient) throws CertificateException {
|
||||
|
||||
try {
|
||||
// Does the certificate chain end with a trusted certificate?
|
||||
@ -1501,7 +1502,9 @@ final class AbstractTrustManagerWrapper extends X509ExtendedTrustManager
|
||||
|
||||
// A forward checker, need to check from trust to target
|
||||
if (checkedLength >= 0) {
|
||||
AlgorithmChecker checker = new AlgorithmChecker(constraints);
|
||||
AlgorithmChecker checker =
|
||||
new AlgorithmChecker(constraints, null,
|
||||
(isClient ? Validator.VAR_TLS_CLIENT : Validator.VAR_TLS_SERVER));
|
||||
checker.init(false);
|
||||
for (int i = checkedLength; i >= 0; i--) {
|
||||
Certificate cert = chain[i];
|
||||
|
@ -39,6 +39,7 @@ import java.security.cert.Certificate;
|
||||
import javax.net.ssl.*;
|
||||
|
||||
import sun.security.provider.certpath.AlgorithmChecker;
|
||||
import sun.security.validator.Validator;
|
||||
|
||||
/**
|
||||
* The new X509 key manager implementation. The main differences to the
|
||||
@ -661,6 +662,15 @@ final class X509KeyManagerImpl extends X509ExtendedKeyManager
|
||||
|
||||
return CheckResult.OK;
|
||||
}
|
||||
|
||||
public String getValidator() {
|
||||
if (this == CLIENT) {
|
||||
return Validator.VAR_TLS_CLIENT;
|
||||
} else if (this == SERVER) {
|
||||
return Validator.VAR_TLS_SERVER;
|
||||
}
|
||||
return Validator.VAR_GENERIC;
|
||||
}
|
||||
}
|
||||
|
||||
// enum for the result of the extension check
|
||||
@ -774,7 +784,8 @@ final class X509KeyManagerImpl extends X509ExtendedKeyManager
|
||||
|
||||
// check the algorithm constraints
|
||||
if (constraints != null &&
|
||||
!conformsToAlgorithmConstraints(constraints, chain)) {
|
||||
!conformsToAlgorithmConstraints(constraints, chain,
|
||||
checkType.getValidator())) {
|
||||
|
||||
if (useDebug) {
|
||||
debug.println("Ignoring alias " + alias +
|
||||
@ -811,9 +822,10 @@ final class X509KeyManagerImpl extends X509ExtendedKeyManager
|
||||
}
|
||||
|
||||
private static boolean conformsToAlgorithmConstraints(
|
||||
AlgorithmConstraints constraints, Certificate[] chain) {
|
||||
AlgorithmConstraints constraints, Certificate[] chain,
|
||||
String variant) {
|
||||
|
||||
AlgorithmChecker checker = new AlgorithmChecker(constraints);
|
||||
AlgorithmChecker checker = new AlgorithmChecker(constraints, null, variant);
|
||||
try {
|
||||
checker.init(false);
|
||||
} catch (CertPathValidatorException cpve) {
|
||||
|
@ -1,76 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 2016, 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
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* 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 Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.security.util;
|
||||
|
||||
import java.security.Timestamp;
|
||||
import java.security.cert.X509Certificate;
|
||||
import java.util.Date;
|
||||
|
||||
/**
|
||||
* This class is a wrapper for keeping state and passing objects between PKIX,
|
||||
* AlgorithmChecker, and DisabledAlgorithmConstraints.
|
||||
*/
|
||||
public class CertConstraintParameters {
|
||||
// A certificate being passed to check against constraints.
|
||||
private final X509Certificate cert;
|
||||
// This is true if the trust anchor in the certificate chain matches a cert
|
||||
// in AnchorCertificates
|
||||
private final boolean trustedMatch;
|
||||
// PKIXParameter date
|
||||
private final Date pkixDate;
|
||||
// Timestamp of the signed JAR file
|
||||
private final Timestamp jarTimestamp;
|
||||
|
||||
public CertConstraintParameters(X509Certificate c, boolean match,
|
||||
Date pkixdate, Timestamp jarTime) {
|
||||
cert = c;
|
||||
trustedMatch = match;
|
||||
pkixDate = pkixdate;
|
||||
jarTimestamp = jarTime;
|
||||
}
|
||||
|
||||
public CertConstraintParameters(X509Certificate c) {
|
||||
this(c, false, null, null);
|
||||
}
|
||||
|
||||
// Returns if the trust anchor has a match if anchor checking is enabled.
|
||||
public boolean isTrustedMatch() {
|
||||
return trustedMatch;
|
||||
}
|
||||
|
||||
public X509Certificate getCertificate() {
|
||||
return cert;
|
||||
}
|
||||
|
||||
public Date getPKIXParamDate() {
|
||||
return pkixDate;
|
||||
}
|
||||
|
||||
public Timestamp getJARTimestamp() {
|
||||
return jarTimestamp;
|
||||
}
|
||||
|
||||
}
|
@ -0,0 +1,135 @@
|
||||
/*
|
||||
* Copyright (c) 2016, 2017 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
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation. Oracle designates this
|
||||
* particular file as subject to the "Classpath" exception as provided
|
||||
* by Oracle in the LICENSE file that accompanied this code.
|
||||
*
|
||||
* 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 Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package sun.security.util;
|
||||
|
||||
import sun.security.validator.Validator;
|
||||
|
||||
import java.security.AlgorithmParameters;
|
||||
import java.security.Key;
|
||||
import java.security.Timestamp;
|
||||
import java.security.cert.X509Certificate;
|
||||
import java.util.Date;
|
||||
|
||||
/**
|
||||
* This class contains parameters for checking against constraints that extend
|
||||
* past the publicly available parameters in java.security.AlgorithmConstraints.
|
||||
|
||||
* This is currently on passed between between PKIX, AlgorithmChecker,
|
||||
* and DisabledAlgorithmConstraints.
|
||||
*/
|
||||
public class ConstraintsParameters {
|
||||
/*
|
||||
* The below 3 values are used the same as the permit() methods
|
||||
* published in java.security.AlgorithmConstraints.
|
||||
*/
|
||||
// Algorithm string to be checked against constraints
|
||||
private final String algorithm;
|
||||
// AlgorithmParameters to the algorithm being checked
|
||||
private final AlgorithmParameters algParams;
|
||||
// Public Key being checked against constraints
|
||||
private final Key publicKey;
|
||||
|
||||
/*
|
||||
* New values that are checked against constraints that the current public
|
||||
* API does not support.
|
||||
*/
|
||||
// A certificate being passed to check against constraints.
|
||||
private final X509Certificate cert;
|
||||
// This is true if the trust anchor in the certificate chain matches a cert
|
||||
// in AnchorCertificates
|
||||
private final boolean trustedMatch;
|
||||
// PKIXParameter date
|
||||
private final Date pkixDate;
|
||||
// Timestamp of the signed JAR file
|
||||
private final Timestamp jarTimestamp;
|
||||
private final String variant;
|
||||
|
||||
public ConstraintsParameters(X509Certificate c, boolean match,
|
||||
Date pkixdate, Timestamp jarTime, String variant) {
|
||||
cert = c;
|
||||
trustedMatch = match;
|
||||
pkixDate = pkixdate;
|
||||
jarTimestamp = jarTime;
|
||||
this.variant = (variant == null ? Validator.VAR_GENERIC : variant);
|
||||
algorithm = null;
|
||||
algParams = null;
|
||||
publicKey = null;
|
||||
}
|
||||
|
||||
public ConstraintsParameters(String algorithm, AlgorithmParameters params,
|
||||
Key key, String variant) {
|
||||
this.algorithm = algorithm;
|
||||
algParams = params;
|
||||
this.publicKey = key;
|
||||
cert = null;
|
||||
trustedMatch = false;
|
||||
pkixDate = null;
|
||||
jarTimestamp = null;
|
||||
this.variant = (variant == null ? Validator.VAR_GENERIC : variant);
|
||||
}
|
||||
|
||||
|
||||
public ConstraintsParameters(X509Certificate c) {
|
||||
this(c, false, null, null,
|
||||
Validator.VAR_GENERIC);
|
||||
}
|
||||
|
||||
public ConstraintsParameters(Timestamp jarTime) {
|
||||
this(null, false, null, jarTime, Validator.VAR_GENERIC);
|
||||
}
|
||||
|
||||
public String getAlgorithm() {
|
||||
return algorithm;
|
||||
}
|
||||
|
||||
public AlgorithmParameters getAlgParams() {
|
||||
return algParams;
|
||||
}
|
||||
|
||||
public Key getPublicKey() {
|
||||
return publicKey;
|
||||
}
|
||||
// Returns if the trust anchor has a match if anchor checking is enabled.
|
||||
public boolean isTrustedMatch() {
|
||||
return trustedMatch;
|
||||
}
|
||||
|
||||
public X509Certificate getCertificate() {
|
||||
return cert;
|
||||
}
|
||||
|
||||
public Date getPKIXParamDate() {
|
||||
return pkixDate;
|
||||
}
|
||||
|
||||
public Timestamp getJARTimestamp() {
|
||||
return jarTimestamp;
|
||||
}
|
||||
|
||||
public String getVariant() {
|
||||
return variant;
|
||||
}
|
||||
}
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2010, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2010, 2017, 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
|
||||
@ -25,6 +25,8 @@
|
||||
|
||||
package sun.security.util;
|
||||
|
||||
import sun.security.validator.Validator;
|
||||
|
||||
import java.security.CryptoPrimitive;
|
||||
import java.security.AlgorithmParameters;
|
||||
import java.security.Key;
|
||||
@ -32,10 +34,12 @@ import java.security.cert.CertPathValidatorException;
|
||||
import java.security.cert.CertPathValidatorException.BasicReason;
|
||||
import java.security.cert.X509Certificate;
|
||||
import java.text.SimpleDateFormat;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Calendar;
|
||||
import java.util.Date;
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
@ -100,12 +104,6 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
@Override
|
||||
public final boolean permits(Set<CryptoPrimitive> primitives,
|
||||
String algorithm, AlgorithmParameters parameters) {
|
||||
|
||||
if (primitives == null || primitives.isEmpty()) {
|
||||
throw new IllegalArgumentException(
|
||||
"No cryptographic primitive specified");
|
||||
}
|
||||
|
||||
return checkAlgorithm(disabledAlgorithms, algorithm, decomposer);
|
||||
}
|
||||
|
||||
@ -133,6 +131,18 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
return checkConstraints(primitives, algorithm, key, parameters);
|
||||
}
|
||||
|
||||
public final void permits(ConstraintsParameters cp)
|
||||
throws CertPathValidatorException {
|
||||
permits(cp.getAlgorithm(), cp);
|
||||
}
|
||||
|
||||
public final void permits(String algorithm, Key key,
|
||||
AlgorithmParameters params, String variant)
|
||||
throws CertPathValidatorException {
|
||||
permits(algorithm, new ConstraintsParameters(algorithm, params, key,
|
||||
(variant == null) ? Validator.VAR_GENERIC : variant));
|
||||
}
|
||||
|
||||
/*
|
||||
* Check if a x509Certificate object is permitted. Check if all
|
||||
* algorithms are allowed, certificate constraints, and the
|
||||
@ -140,18 +150,10 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
*
|
||||
* Uses new style permit() which throws exceptions.
|
||||
*/
|
||||
public final void permits(Set<CryptoPrimitive> primitives,
|
||||
CertConstraintParameters cp) throws CertPathValidatorException {
|
||||
checkConstraints(primitives, cp);
|
||||
}
|
||||
|
||||
/*
|
||||
* Check if Certificate object is within the constraints.
|
||||
* Uses new style permit() which throws exceptions.
|
||||
*/
|
||||
public final void permits(Set<CryptoPrimitive> primitives,
|
||||
X509Certificate cert) throws CertPathValidatorException {
|
||||
checkConstraints(primitives, new CertConstraintParameters(cert));
|
||||
public final void permits(String algorithm, ConstraintsParameters cp)
|
||||
throws CertPathValidatorException {
|
||||
algorithmConstraints.permits(algorithm, cp);
|
||||
}
|
||||
|
||||
// Check if a string is contained inside the property
|
||||
@ -174,7 +176,7 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
throw new IllegalArgumentException("The key cannot be null");
|
||||
}
|
||||
|
||||
// check the signature algorithm
|
||||
// check the signature algorithm with parameters
|
||||
if (algorithm != null && algorithm.length() != 0) {
|
||||
if (!permits(primitives, algorithm, parameters)) {
|
||||
return false;
|
||||
@ -190,36 +192,6 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
return algorithmConstraints.permits(key);
|
||||
}
|
||||
|
||||
/*
|
||||
* Check algorithm constraints with Certificate
|
||||
* Uses new style permit() which throws exceptions.
|
||||
*/
|
||||
private void checkConstraints(Set<CryptoPrimitive> primitives,
|
||||
CertConstraintParameters cp) throws CertPathValidatorException {
|
||||
|
||||
X509Certificate cert = cp.getCertificate();
|
||||
String algorithm = cert.getSigAlgName();
|
||||
|
||||
// Check signature algorithm is not disabled
|
||||
if (!permits(primitives, algorithm, null)) {
|
||||
throw new CertPathValidatorException(
|
||||
"Algorithm constraints check failed on disabled "+
|
||||
"signature algorithm: " + algorithm,
|
||||
null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
|
||||
}
|
||||
|
||||
// Check key algorithm is not disabled
|
||||
if (!permits(primitives, cert.getPublicKey().getAlgorithm(), null)) {
|
||||
throw new CertPathValidatorException(
|
||||
"Algorithm constraints check failed on disabled "+
|
||||
"public key algorithm: " + algorithm,
|
||||
null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
|
||||
}
|
||||
|
||||
// Check the certificate and key constraints
|
||||
algorithmConstraints.permits(cp);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Key and Certificate Constraints
|
||||
@ -234,13 +206,13 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
* 'true' means the operation is allowed.
|
||||
* 'false' means it failed the constraints and is disallowed.
|
||||
*
|
||||
* When passing CertConstraintParameters through permit(), an exception
|
||||
* When passing ConstraintsParameters through permit(), an exception
|
||||
* will be thrown on a failure to better identify why the operation was
|
||||
* disallowed.
|
||||
*/
|
||||
|
||||
private static class Constraints {
|
||||
private Map<String, Set<Constraint>> constraintsMap = new HashMap<>();
|
||||
private Map<String, List<Constraint>> constraintsMap = new HashMap<>();
|
||||
|
||||
private static class Holder {
|
||||
private static final Pattern DENY_AFTER_PATTERN = Pattern.compile(
|
||||
@ -260,23 +232,22 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
|
||||
// Check if constraint is a complete disabling of an
|
||||
// algorithm or has conditions.
|
||||
String algorithm;
|
||||
String policy;
|
||||
int space = constraintEntry.indexOf(' ');
|
||||
if (space > 0) {
|
||||
algorithm = AlgorithmDecomposer.hashName(
|
||||
constraintEntry.substring(0, space).
|
||||
toUpperCase(Locale.ENGLISH));
|
||||
policy = constraintEntry.substring(space + 1);
|
||||
} else {
|
||||
algorithm = constraintEntry.toUpperCase(Locale.ENGLISH);
|
||||
if (!constraintsMap.containsKey(algorithm)) {
|
||||
constraintsMap.putIfAbsent(algorithm,
|
||||
new HashSet<>());
|
||||
}
|
||||
String algorithm = AlgorithmDecomposer.hashName(
|
||||
((space > 0 ? constraintEntry.substring(0, space) :
|
||||
constraintEntry).
|
||||
toUpperCase(Locale.ENGLISH)));
|
||||
List<Constraint> constraintList =
|
||||
constraintsMap.getOrDefault(algorithm,
|
||||
new ArrayList<>(1));
|
||||
constraintsMap.putIfAbsent(algorithm, constraintList);
|
||||
if (space <= 0) {
|
||||
constraintList.add(new DisabledConstraint(algorithm));
|
||||
continue;
|
||||
}
|
||||
|
||||
String policy = constraintEntry.substring(space + 1);
|
||||
|
||||
// Convert constraint conditions into Constraint classes
|
||||
Constraint c, lastConstraint = null;
|
||||
// Allow only one jdkCA entry per constraint entry
|
||||
@ -315,7 +286,7 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
c = new jdkCAConstraint(algorithm);
|
||||
jdkCALimit = true;
|
||||
|
||||
} else if(entry.startsWith("denyAfter") &&
|
||||
} else if (entry.startsWith("denyAfter") &&
|
||||
(matcher = Holder.DENY_AFTER_PATTERN.matcher(entry))
|
||||
.matches()) {
|
||||
if (debug != null) {
|
||||
@ -332,6 +303,12 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
c = new DenyAfterConstraint(algorithm, year, month,
|
||||
day);
|
||||
denyAfterLimit = true;
|
||||
} else if (entry.startsWith("usage")) {
|
||||
String s[] = (entry.substring(5)).trim().split(" ");
|
||||
c = new UsageConstraint(algorithm, s);
|
||||
if (debug != null) {
|
||||
debug.println("Constraints usage length is " + s.length);
|
||||
}
|
||||
} else {
|
||||
throw new IllegalArgumentException("Error in security" +
|
||||
" property. Constraint unknown: " + entry);
|
||||
@ -340,11 +317,7 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
// Link multiple conditions for a single constraint
|
||||
// into a linked list.
|
||||
if (lastConstraint == null) {
|
||||
if (!constraintsMap.containsKey(algorithm)) {
|
||||
constraintsMap.putIfAbsent(algorithm,
|
||||
new HashSet<>());
|
||||
}
|
||||
constraintsMap.get(algorithm).add(c);
|
||||
constraintList.add(c);
|
||||
} else {
|
||||
lastConstraint.nextConstraint = c;
|
||||
}
|
||||
@ -354,17 +327,17 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
}
|
||||
|
||||
// Get applicable constraints based off the signature algorithm
|
||||
private Set<Constraint> getConstraints(String algorithm) {
|
||||
private List<Constraint> getConstraints(String algorithm) {
|
||||
return constraintsMap.get(algorithm);
|
||||
}
|
||||
|
||||
// Check if KeySizeConstraints permit the specified key
|
||||
public boolean permits(Key key) {
|
||||
Set<Constraint> set = getConstraints(key.getAlgorithm());
|
||||
if (set == null) {
|
||||
List<Constraint> list = getConstraints(key.getAlgorithm());
|
||||
if (list == null) {
|
||||
return true;
|
||||
}
|
||||
for (Constraint constraint : set) {
|
||||
for (Constraint constraint : list) {
|
||||
if (!constraint.permits(key)) {
|
||||
if (debug != null) {
|
||||
debug.println("keySizeConstraint: failed key " +
|
||||
@ -377,31 +350,35 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
}
|
||||
|
||||
// Check if constraints permit this cert.
|
||||
public void permits(CertConstraintParameters cp)
|
||||
public void permits(String algorithm, ConstraintsParameters cp)
|
||||
throws CertPathValidatorException {
|
||||
X509Certificate cert = cp.getCertificate();
|
||||
|
||||
if (debug != null) {
|
||||
debug.println("Constraints.permits(): " + cert.getSigAlgName());
|
||||
debug.println("Constraints.permits(): " + algorithm +
|
||||
" Variant: " + cp.getVariant());
|
||||
}
|
||||
|
||||
// Get all signature algorithms to check for constraints
|
||||
Set<String> algorithms =
|
||||
AlgorithmDecomposer.decomposeOneHash(cert.getSigAlgName());
|
||||
if (algorithms == null || algorithms.isEmpty()) {
|
||||
return;
|
||||
Set<String> algorithms = new HashSet<>();
|
||||
if (algorithm != null) {
|
||||
algorithms.addAll(AlgorithmDecomposer.decomposeOneHash(algorithm));
|
||||
}
|
||||
|
||||
// Attempt to add the public key algorithm to the set
|
||||
algorithms.add(cert.getPublicKey().getAlgorithm());
|
||||
|
||||
// Attempt to add the public key algorithm if cert provided
|
||||
if (cert != null) {
|
||||
algorithms.add(cert.getPublicKey().getAlgorithm());
|
||||
}
|
||||
if (cp.getPublicKey() != null) {
|
||||
algorithms.add(cp.getPublicKey().getAlgorithm());
|
||||
}
|
||||
// Check all applicable constraints
|
||||
for (String algorithm : algorithms) {
|
||||
Set<Constraint> set = getConstraints(algorithm);
|
||||
if (set == null) {
|
||||
for (String alg : algorithms) {
|
||||
List<Constraint> list = getConstraints(alg);
|
||||
if (list == null) {
|
||||
continue;
|
||||
}
|
||||
for (Constraint constraint : set) {
|
||||
for (Constraint constraint : list) {
|
||||
constraint.permits(cp);
|
||||
}
|
||||
}
|
||||
@ -467,17 +444,17 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
|
||||
/**
|
||||
* Check if an algorithm constraint is permitted with a given
|
||||
* CertConstraintParameters.
|
||||
* ConstraintsParameters.
|
||||
*
|
||||
* If the check inside of {@code permits()} fails, it must call
|
||||
* {@code next()} with the same {@code CertConstraintParameters}
|
||||
* {@code next()} with the same {@code ConstraintsParameters}
|
||||
* parameter passed if multiple constraints need to be checked.
|
||||
*
|
||||
* @param cp CertConstraintParameter containing certificate info
|
||||
* @throws CertPathValidatorException if constraint disallows.
|
||||
*
|
||||
*/
|
||||
public abstract void permits(CertConstraintParameters cp)
|
||||
public abstract void permits(ConstraintsParameters cp)
|
||||
throws CertPathValidatorException;
|
||||
|
||||
/**
|
||||
@ -491,12 +468,12 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
* were disallowed, the last constraint will throw
|
||||
* {@code CertPathValidatorException}.
|
||||
*
|
||||
* @param cp CertConstraintParameters
|
||||
* @param cp ConstraintsParameters
|
||||
* @return 'true' if constraint allows the operation, 'false' if
|
||||
* we are at the end of the constraint list or,
|
||||
* {@code nextConstraint} is null.
|
||||
*/
|
||||
boolean next(CertConstraintParameters cp)
|
||||
boolean next(ConstraintsParameters cp)
|
||||
throws CertPathValidatorException {
|
||||
if (nextConstraint != null) {
|
||||
nextConstraint.permits(cp);
|
||||
@ -525,6 +502,14 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
String extendedMsg(ConstraintsParameters cp) {
|
||||
return (cp.getCertificate() == null ? "." :
|
||||
" used with certificate: " +
|
||||
cp.getCertificate().getSubjectX500Principal() +
|
||||
(cp.getVariant() != Validator.VAR_GENERIC ?
|
||||
". Usage was " + cp.getVariant() : "."));
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
@ -537,11 +522,11 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
}
|
||||
|
||||
/*
|
||||
* Check if CertConstraintParameters has a trusted match, if it does
|
||||
* Check if ConstraintsParameters has a trusted match, if it does
|
||||
* call next() for any following constraints. If it does not, exit
|
||||
* as this constraint(s) does not restrict the operation.
|
||||
*/
|
||||
public void permits(CertConstraintParameters cp)
|
||||
public void permits(ConstraintsParameters cp)
|
||||
throws CertPathValidatorException {
|
||||
if (debug != null) {
|
||||
debug.println("jdkCAConstraints.permits(): " + algorithm);
|
||||
@ -554,8 +539,7 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
}
|
||||
throw new CertPathValidatorException(
|
||||
"Algorithm constraints check failed on certificate " +
|
||||
"anchor limits. " + algorithm + " used with " +
|
||||
cp.getCertificate().getSubjectX500Principal(),
|
||||
"anchor limits. " + algorithm + extendedMsg(cp),
|
||||
null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
|
||||
}
|
||||
}
|
||||
@ -615,7 +599,7 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
* constraints. Throw an exception if this is the last constraint.
|
||||
*/
|
||||
@Override
|
||||
public void permits(CertConstraintParameters cp)
|
||||
public void permits(ConstraintsParameters cp)
|
||||
throws CertPathValidatorException {
|
||||
Date currentDate;
|
||||
String errmsg;
|
||||
@ -628,7 +612,7 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
errmsg = "PKIXParameter date: ";
|
||||
} else {
|
||||
currentDate = new Date();
|
||||
errmsg = "Certificate date: ";
|
||||
errmsg = "Current date: ";
|
||||
}
|
||||
|
||||
if (!denyAfterDate.after(currentDate)) {
|
||||
@ -637,9 +621,9 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
}
|
||||
throw new CertPathValidatorException(
|
||||
"denyAfter constraint check failed: " + algorithm +
|
||||
" used with Constraint date: " +
|
||||
dateFormat.format(denyAfterDate) + "; "
|
||||
+ errmsg + dateFormat.format(currentDate),
|
||||
" used with Constraint date: " +
|
||||
dateFormat.format(denyAfterDate) + "; " + errmsg +
|
||||
dateFormat.format(currentDate) + extendedMsg(cp),
|
||||
null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
|
||||
}
|
||||
}
|
||||
@ -660,6 +644,48 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* The usage constraint is for the "usage" keyword. It checks against the
|
||||
* variant value in ConstraintsParameters.
|
||||
*/
|
||||
private static class UsageConstraint extends Constraint {
|
||||
String[] usages;
|
||||
|
||||
UsageConstraint(String algorithm, String[] usages) {
|
||||
this.algorithm = algorithm;
|
||||
this.usages = usages;
|
||||
}
|
||||
|
||||
public void permits(ConstraintsParameters cp)
|
||||
throws CertPathValidatorException {
|
||||
for (String usage : usages) {
|
||||
|
||||
String v = null;
|
||||
if (usage.compareToIgnoreCase("TLSServer") == 0) {
|
||||
v = Validator.VAR_TLS_SERVER;
|
||||
} else if (usage.compareToIgnoreCase("TLSClient") == 0) {
|
||||
v = Validator.VAR_TLS_CLIENT;
|
||||
} else if (usage.compareToIgnoreCase("SignedJAR") == 0) {
|
||||
v = Validator.VAR_PLUGIN_CODE_SIGNING;
|
||||
}
|
||||
|
||||
if (debug != null) {
|
||||
debug.println("Checking if usage constraint " + v +
|
||||
" matches " + cp.getVariant());
|
||||
}
|
||||
if (cp.getVariant().compareTo(v) == 0) {
|
||||
if (next(cp)) {
|
||||
return;
|
||||
}
|
||||
throw new CertPathValidatorException("Usage constraint " +
|
||||
usage + " check failed: " + algorithm +
|
||||
extendedMsg(cp),
|
||||
null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* This class contains constraints dealing with the key size
|
||||
* support limits per algorithm. e.g. "keySize <= 1024"
|
||||
@ -713,17 +739,22 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
* constraint Any permitted constraint will exit the linked list
|
||||
* to allow the operation.
|
||||
*/
|
||||
public void permits(CertConstraintParameters cp)
|
||||
public void permits(ConstraintsParameters cp)
|
||||
throws CertPathValidatorException {
|
||||
if (!permitsImpl(cp.getCertificate().getPublicKey())) {
|
||||
Key key = null;
|
||||
if (cp.getPublicKey() != null) {
|
||||
key = cp.getPublicKey();
|
||||
} else if (cp.getCertificate() != null) {
|
||||
key = cp.getCertificate().getPublicKey();
|
||||
}
|
||||
if (key != null && !permitsImpl(key)) {
|
||||
if (nextConstraint != null) {
|
||||
nextConstraint.permits(cp);
|
||||
return;
|
||||
}
|
||||
throw new CertPathValidatorException(
|
||||
"Algorithm constraints check failed on keysize limits. "
|
||||
+ algorithm + " " + size + "bit key used with "
|
||||
+ cp.getCertificate().getSubjectX500Principal(),
|
||||
+ algorithm + " " + size + "bit key" + extendedMsg(cp),
|
||||
null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
|
||||
}
|
||||
}
|
||||
@ -762,5 +793,26 @@ public class DisabledAlgorithmConstraints extends AbstractAlgorithmConstraints {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* This constraint is used for the complete disabling of the algorithm.
|
||||
*/
|
||||
private static class DisabledConstraint extends Constraint {
|
||||
DisabledConstraint(String algo) {
|
||||
algorithm = algo;
|
||||
}
|
||||
|
||||
public void permits(ConstraintsParameters cp)
|
||||
throws CertPathValidatorException {
|
||||
throw new CertPathValidatorException(
|
||||
"Algorithm constraints check failed on disabled " +
|
||||
"algorithm: " + algorithm + extendedMsg(cp),
|
||||
null, null, -1, BasicReason.ALGORITHM_CONSTRAINED);
|
||||
}
|
||||
|
||||
public boolean permits(Key key) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 1997, 2017, 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
|
||||
@ -28,25 +28,23 @@ package sun.security.util;
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.IOException;
|
||||
import java.security.CodeSigner;
|
||||
import java.security.CryptoPrimitive;
|
||||
import java.security.GeneralSecurityException;
|
||||
import java.security.MessageDigest;
|
||||
import java.security.NoSuchAlgorithmException;
|
||||
import java.security.SignatureException;
|
||||
import java.security.Timestamp;
|
||||
import java.security.cert.CertPath;
|
||||
import java.security.cert.X509Certificate;
|
||||
import java.security.cert.CertificateException;
|
||||
import java.security.cert.CertificateFactory;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Base64;
|
||||
import java.util.Collections;
|
||||
import java.util.EnumSet;
|
||||
import java.util.HashMap;
|
||||
import java.util.Hashtable;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.jar.Attributes;
|
||||
import java.util.jar.JarException;
|
||||
import java.util.jar.JarFile;
|
||||
@ -61,9 +59,6 @@ public class SignatureFileVerifier {
|
||||
/* Are we debugging ? */
|
||||
private static final Debug debug = Debug.getInstance("jar");
|
||||
|
||||
private static final Set<CryptoPrimitive> DIGEST_PRIMITIVE_SET =
|
||||
Collections.unmodifiableSet(EnumSet.of(CryptoPrimitive.MESSAGE_DIGEST));
|
||||
|
||||
private static final DisabledAlgorithmConstraints JAR_DISABLED_CHECK =
|
||||
new DisabledAlgorithmConstraints(
|
||||
DisabledAlgorithmConstraints.PROPERTY_JAR_DISABLED_ALGS);
|
||||
@ -97,6 +92,14 @@ public class SignatureFileVerifier {
|
||||
/* for generating certpath objects */
|
||||
private CertificateFactory certificateFactory = null;
|
||||
|
||||
/** Algorithms that have been checked if they are weak. */
|
||||
private Map<String, Boolean> permittedAlgs= new HashMap<>();
|
||||
|
||||
/** TSA timestamp of signed jar. The newest timestamp is used. If there
|
||||
* was no TSA timestamp used when signed, current time is used ("null").
|
||||
*/
|
||||
private Timestamp timestamp = null;
|
||||
|
||||
/**
|
||||
* Create the named SignatureFileVerifier.
|
||||
*
|
||||
@ -222,15 +225,8 @@ public class SignatureFileVerifier {
|
||||
|
||||
/** get digest from cache */
|
||||
|
||||
private MessageDigest getDigest(String algorithm) throws SignatureException {
|
||||
// check that algorithm is not restricted
|
||||
if (!JAR_DISABLED_CHECK.permits(DIGEST_PRIMITIVE_SET, algorithm, null)) {
|
||||
SignatureException e =
|
||||
new SignatureException("SignatureFile check failed. " +
|
||||
"Disabled algorithm used: " + algorithm);
|
||||
throw e;
|
||||
}
|
||||
|
||||
private MessageDigest getDigest(String algorithm)
|
||||
throws SignatureException {
|
||||
if (createdDigests == null)
|
||||
createdDigests = new HashMap<>();
|
||||
|
||||
@ -302,6 +298,27 @@ public class SignatureFileVerifier {
|
||||
if (newSigners == null)
|
||||
return;
|
||||
|
||||
/*
|
||||
* Look for the latest timestamp in the signature block. If an entry
|
||||
* has no timestamp, use current time (aka null).
|
||||
*/
|
||||
for (CodeSigner s: newSigners) {
|
||||
if (debug != null) {
|
||||
debug.println("Gathering timestamp for: " + s.toString());
|
||||
}
|
||||
if (s.getTimestamp() == null) {
|
||||
timestamp = null;
|
||||
break;
|
||||
} else if (timestamp == null) {
|
||||
timestamp = s.getTimestamp();
|
||||
} else {
|
||||
if (timestamp.getTimestamp().before(
|
||||
s.getTimestamp().getTimestamp())) {
|
||||
timestamp = s.getTimestamp();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Iterator<Map.Entry<String,Attributes>> entries =
|
||||
sf.getEntries().entrySet().iterator();
|
||||
|
||||
@ -344,6 +361,68 @@ public class SignatureFileVerifier {
|
||||
updateSigners(newSigners, signers, JarFile.MANIFEST_NAME);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if algorithm is permitted using the permittedAlgs Map.
|
||||
* If the algorithm is not in the map, check against disabled algorithms and
|
||||
* store the result. If the algorithm is in the map use that result.
|
||||
* False is returned for weak algorithm, true for good algorithms.
|
||||
*/
|
||||
boolean permittedCheck(String key, String algorithm) {
|
||||
Boolean permitted = permittedAlgs.get(algorithm);
|
||||
if (permitted == null) {
|
||||
try {
|
||||
JAR_DISABLED_CHECK.permits(algorithm,
|
||||
new ConstraintsParameters(timestamp));
|
||||
} catch(GeneralSecurityException e) {
|
||||
permittedAlgs.put(algorithm, Boolean.FALSE);
|
||||
permittedAlgs.put(key.toUpperCase(), Boolean.FALSE);
|
||||
if (debug != null) {
|
||||
if (e.getMessage() != null) {
|
||||
debug.println(key + ": " + e.getMessage());
|
||||
} else {
|
||||
debug.println(key + ": " + algorithm +
|
||||
" was disabled, no exception msg given.");
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
permittedAlgs.put(algorithm, Boolean.TRUE);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Algorithm has already been checked, return the value from map.
|
||||
return permitted.booleanValue();
|
||||
}
|
||||
|
||||
/**
|
||||
* With a given header (*-DIGEST*), return a string that lists all the
|
||||
* algorithms associated with the header.
|
||||
* If there are none, return "Unknown Algorithm".
|
||||
*/
|
||||
String getWeakAlgorithms(String header) {
|
||||
String w = "";
|
||||
try {
|
||||
for (String key : permittedAlgs.keySet()) {
|
||||
if (key.endsWith(header)) {
|
||||
w += key.substring(0, key.length() - header.length()) + " ";
|
||||
}
|
||||
}
|
||||
} catch (RuntimeException e) {
|
||||
w = "Unknown Algorithm(s). Error processing " + header + ". " +
|
||||
e.getMessage();
|
||||
}
|
||||
|
||||
// This means we have an error in finding weak algorithms, run in
|
||||
// debug mode to see permittedAlgs map's values.
|
||||
if (w.length() == 0) {
|
||||
return "Unknown Algorithm(s)";
|
||||
}
|
||||
|
||||
return w;
|
||||
}
|
||||
|
||||
/**
|
||||
* See if the whole manifest was signed.
|
||||
*/
|
||||
@ -354,6 +433,7 @@ public class SignatureFileVerifier {
|
||||
{
|
||||
Attributes mattr = sf.getMainAttributes();
|
||||
boolean manifestSigned = false;
|
||||
boolean weakAlgs = true;
|
||||
|
||||
// go through all the attributes and process *-Digest-Manifest entries
|
||||
for (Map.Entry<Object,Object> se : mattr.entrySet()) {
|
||||
@ -364,6 +444,15 @@ public class SignatureFileVerifier {
|
||||
// 16 is length of "-Digest-Manifest"
|
||||
String algorithm = key.substring(0, key.length()-16);
|
||||
|
||||
// Check if this algorithm is permitted, skip if false.
|
||||
if (!permittedCheck(key, algorithm)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// A non-weak algorithm was used, any weak algorithms found do
|
||||
// not need to be reported.
|
||||
weakAlgs = false;
|
||||
|
||||
manifestDigests.add(key);
|
||||
manifestDigests.add(se.getValue());
|
||||
MessageDigest digest = getDigest(algorithm);
|
||||
@ -373,15 +462,14 @@ public class SignatureFileVerifier {
|
||||
Base64.getMimeDecoder().decode((String)se.getValue());
|
||||
|
||||
if (debug != null) {
|
||||
debug.println("Signature File: Manifest digest " +
|
||||
digest.getAlgorithm());
|
||||
debug.println( " sigfile " + toHex(expectedHash));
|
||||
debug.println( " computed " + toHex(computedHash));
|
||||
debug.println();
|
||||
debug.println("Signature File: Manifest digest " +
|
||||
algorithm);
|
||||
debug.println( " sigfile " + toHex(expectedHash));
|
||||
debug.println( " computed " + toHex(computedHash));
|
||||
debug.println();
|
||||
}
|
||||
|
||||
if (MessageDigest.isEqual(computedHash,
|
||||
expectedHash)) {
|
||||
if (MessageDigest.isEqual(computedHash, expectedHash)) {
|
||||
manifestSigned = true;
|
||||
} else {
|
||||
//XXX: we will continue and verify each section
|
||||
@ -389,15 +477,31 @@ public class SignatureFileVerifier {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (debug != null) {
|
||||
debug.println("PermittedAlgs mapping: ");
|
||||
for (String key : permittedAlgs.keySet()) {
|
||||
debug.println(key + " : " +
|
||||
permittedAlgs.get(key).toString());
|
||||
}
|
||||
}
|
||||
|
||||
// If there were only weak algorithms used, throw an exception.
|
||||
if (weakAlgs) {
|
||||
String weakAlgorithms = getWeakAlgorithms("-DIGEST-MANIFEST");
|
||||
throw new SignatureException("Manifest hash check failed " +
|
||||
"(DIGEST-MANIFEST). Disabled algorithm(s) used: " +
|
||||
weakAlgorithms);
|
||||
}
|
||||
return manifestSigned;
|
||||
}
|
||||
|
||||
private boolean verifyManifestMainAttrs(Manifest sf,
|
||||
ManifestDigester md)
|
||||
private boolean verifyManifestMainAttrs(Manifest sf, ManifestDigester md)
|
||||
throws IOException, SignatureException
|
||||
{
|
||||
Attributes mattr = sf.getMainAttributes();
|
||||
boolean attrsVerified = true;
|
||||
boolean weakAlgs = true;
|
||||
|
||||
// go through all the attributes and process
|
||||
// digest entries for the manifest main attributes
|
||||
@ -408,6 +512,15 @@ public class SignatureFileVerifier {
|
||||
String algorithm =
|
||||
key.substring(0, key.length() - ATTR_DIGEST.length());
|
||||
|
||||
// Check if this algorithm is permitted, skip if false.
|
||||
if (!permittedCheck(key, algorithm)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// A non-weak algorithm was used, any weak algorithms found do
|
||||
// not need to be reported.
|
||||
weakAlgs = false;
|
||||
|
||||
MessageDigest digest = getDigest(algorithm);
|
||||
if (digest != null) {
|
||||
ManifestDigester.Entry mde =
|
||||
@ -425,8 +538,7 @@ public class SignatureFileVerifier {
|
||||
debug.println();
|
||||
}
|
||||
|
||||
if (MessageDigest.isEqual(computedHash,
|
||||
expectedHash)) {
|
||||
if (MessageDigest.isEqual(computedHash, expectedHash)) {
|
||||
// good
|
||||
} else {
|
||||
// we will *not* continue and verify each section
|
||||
@ -442,6 +554,23 @@ public class SignatureFileVerifier {
|
||||
}
|
||||
}
|
||||
|
||||
if (debug != null) {
|
||||
debug.println("PermittedAlgs mapping: ");
|
||||
for (String key : permittedAlgs.keySet()) {
|
||||
debug.println(key + " : " +
|
||||
permittedAlgs.get(key).toString());
|
||||
}
|
||||
}
|
||||
|
||||
// If there were only weak algorithms used, throw an exception.
|
||||
if (weakAlgs) {
|
||||
String weakAlgorithms = getWeakAlgorithms("-DIGEST-" +
|
||||
ManifestDigester.MF_MAIN_ATTRS);
|
||||
throw new SignatureException("Manifest Main Attribute check " +
|
||||
"failed (DIGEST-" + ManifestDigester.MF_MAIN_ATTRS +
|
||||
"). " + "Disabled algorithm(s) used: " + weakAlgorithms);
|
||||
}
|
||||
|
||||
// this method returns 'true' if either:
|
||||
// . manifest main attributes were not signed, or
|
||||
// . manifest main attributes were signed and verified
|
||||
@ -464,6 +593,7 @@ public class SignatureFileVerifier {
|
||||
{
|
||||
boolean oneDigestVerified = false;
|
||||
ManifestDigester.Entry mde = md.get(name,block.isOldStyle());
|
||||
boolean weakAlgs = true;
|
||||
|
||||
if (mde == null) {
|
||||
throw new SecurityException(
|
||||
@ -471,7 +601,6 @@ public class SignatureFileVerifier {
|
||||
}
|
||||
|
||||
if (sfAttr != null) {
|
||||
|
||||
//sun.security.util.HexDumpEncoder hex = new sun.security.util.HexDumpEncoder();
|
||||
//hex.encodeBuffer(data, System.out);
|
||||
|
||||
@ -483,6 +612,15 @@ public class SignatureFileVerifier {
|
||||
// 7 is length of "-Digest"
|
||||
String algorithm = key.substring(0, key.length()-7);
|
||||
|
||||
// Check if this algorithm is permitted, skip if false.
|
||||
if (!permittedCheck(key, algorithm)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// A non-weak algorithm was used, any weak algorithms found do
|
||||
// not need to be reported.
|
||||
weakAlgs = false;
|
||||
|
||||
MessageDigest digest = getDigest(algorithm);
|
||||
|
||||
if (digest != null) {
|
||||
@ -532,6 +670,23 @@ public class SignatureFileVerifier {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (debug != null) {
|
||||
debug.println("PermittedAlgs mapping: ");
|
||||
for (String key : permittedAlgs.keySet()) {
|
||||
debug.println(key + " : " +
|
||||
permittedAlgs.get(key).toString());
|
||||
}
|
||||
}
|
||||
|
||||
// If there were only weak algorithms used, throw an exception.
|
||||
if (weakAlgs) {
|
||||
String weakAlgorithms = getWeakAlgorithms("DIGEST");
|
||||
throw new SignatureException("Manifest Main Attribute check " +
|
||||
"failed (DIGEST). " + "Disabled algorithm(s) used: " +
|
||||
weakAlgorithms);
|
||||
}
|
||||
|
||||
return oneDigestVerified;
|
||||
}
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2002, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2002, 2017, 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,7 +33,7 @@ import java.security.cert.*;
|
||||
import javax.security.auth.x500.X500Principal;
|
||||
import sun.security.action.GetBooleanAction;
|
||||
import sun.security.provider.certpath.AlgorithmChecker;
|
||||
import sun.security.provider.certpath.PKIXTimestampParameters;
|
||||
import sun.security.provider.certpath.PKIXExtendedParameters;
|
||||
|
||||
/**
|
||||
* Validator implementation built on the PKIX CertPath API. This
|
||||
@ -199,9 +199,9 @@ public final class PKIXValidator extends Validator {
|
||||
PKIXBuilderParameters pkixParameters = null;
|
||||
if (parameter instanceof Timestamp && plugin) {
|
||||
try {
|
||||
pkixParameters = new PKIXTimestampParameters(
|
||||
pkixParameters = new PKIXExtendedParameters(
|
||||
(PKIXBuilderParameters) parameterTemplate.clone(),
|
||||
(Timestamp) parameter);
|
||||
(Timestamp) parameter, variant);
|
||||
} catch (InvalidAlgorithmParameterException e) {
|
||||
// ignore exception
|
||||
}
|
||||
@ -211,7 +211,8 @@ public final class PKIXValidator extends Validator {
|
||||
|
||||
// add new algorithm constraints checker
|
||||
if (constraints != null) {
|
||||
pkixParameters.addCertPathChecker(new AlgorithmChecker(constraints));
|
||||
pkixParameters.addCertPathChecker(
|
||||
new AlgorithmChecker(constraints, null, variant));
|
||||
}
|
||||
|
||||
// attach it to the PKIXBuilderParameters.
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2002, 2016, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2002, 2017, 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
|
||||
@ -155,12 +155,14 @@ public final class SimpleValidator extends Validator {
|
||||
|
||||
// create default algorithm constraints checker
|
||||
TrustAnchor anchor = new TrustAnchor(anchorCert, null);
|
||||
AlgorithmChecker defaultAlgChecker = new AlgorithmChecker(anchor);
|
||||
AlgorithmChecker defaultAlgChecker =
|
||||
new AlgorithmChecker(anchor, variant);
|
||||
|
||||
// create application level algorithm constraints checker
|
||||
AlgorithmChecker appAlgChecker = null;
|
||||
if (constraints != null) {
|
||||
appAlgChecker = new AlgorithmChecker(anchor, constraints);
|
||||
appAlgChecker = new AlgorithmChecker(anchor, constraints, null,
|
||||
variant);
|
||||
}
|
||||
|
||||
// verify top down, starting at the certificate issued by
|
||||
|
@ -494,7 +494,8 @@ krb5.kdc.bad.policy = tryLast
|
||||
# (see below)
|
||||
#
|
||||
# Constraint:
|
||||
# KeySizeConstraint | CAConstraint | DenyAfterConstraint
|
||||
# KeySizeConstraint | CAConstraint | DenyAfterConstraint |
|
||||
# UsageConstraint
|
||||
#
|
||||
# KeySizeConstraint:
|
||||
# keySize Operator KeyLength
|
||||
@ -511,6 +512,9 @@ krb5.kdc.bad.policy = tryLast
|
||||
# DenyAfterConstraint:
|
||||
# denyAfter YYYY-MM-DD
|
||||
#
|
||||
# UsageConstraint:
|
||||
# usage [TLSServer] [TLSClient] [SignedJAR]
|
||||
#
|
||||
# The "AlgorithmName" is the standard algorithm name of the disabled
|
||||
# algorithm. See "Java Cryptography Architecture Standard Algorithm Name
|
||||
# Documentation" for information about Standard Algorithm Names. Matching
|
||||
@ -560,6 +564,19 @@ krb5.kdc.bad.policy = tryLast
|
||||
# Example: To deny usage of RSA 2048 bit certificates after Feb 3 2020,
|
||||
# use the following: "RSA keySize == 2048 & denyAfter 2020-02-03"
|
||||
#
|
||||
# UsageConstraint:
|
||||
# usage [TLSServer] [TLSClient] [SignedJAR]
|
||||
# This constraint prohibits the specified algorithm for
|
||||
# a specified usage. This should be used when disabling an algorithm
|
||||
# for all usages is not practical. 'TLSServer' restricts the algorithm
|
||||
# in TLS server certificate chains when server authentication is
|
||||
# performed. 'TLSClient' restricts the algorithm in TLS client
|
||||
# certificate chains when client authentication is performed.
|
||||
# 'SignedJAR' constrains use of certificates in signed jar files.
|
||||
# The usage type follows the keyword and more than one usage type can
|
||||
# be specified with a whitespace delimiter.
|
||||
# Example: "SHA1 usage TLSServer TLSClient"
|
||||
#
|
||||
# When an algorithm must satisfy more than one constraint, it must be
|
||||
# delimited by an ampersand '&'. For example, to restrict certificates in a
|
||||
# chain that terminate at a distribution provided trust anchor and contain
|
||||
@ -599,17 +616,20 @@ jdk.certpath.disabledAlgorithms=MD2, MD5, SHA1 jdkCA & denyAfter 2017-01-01, \
|
||||
# " DisabledAlgorithm { , DisabledAlgorithm } "
|
||||
#
|
||||
# DisabledAlgorithm:
|
||||
# AlgorithmName [Constraint]
|
||||
# AlgorithmName [Constraint] { '&' Constraint }
|
||||
#
|
||||
# AlgorithmName:
|
||||
# (see below)
|
||||
#
|
||||
# Constraint:
|
||||
# KeySizeConstraint
|
||||
# KeySizeConstraint | DenyAfterConstraint
|
||||
#
|
||||
# KeySizeConstraint:
|
||||
# keySize Operator KeyLength
|
||||
#
|
||||
# DenyAfterConstraint:
|
||||
# denyAfter YYYY-MM-DD
|
||||
#
|
||||
# Operator:
|
||||
# <= | < | == | != | >= | >
|
||||
#
|
||||
@ -620,6 +640,8 @@ jdk.certpath.disabledAlgorithms=MD2, MD5, SHA1 jdkCA & denyAfter 2017-01-01, \
|
||||
# implementation. It is not guaranteed to be examined and used by other
|
||||
# implementations.
|
||||
#
|
||||
# See "jdk.certpath.disabledAlgorithms" for syntax descriptions.
|
||||
#
|
||||
jdk.jar.disabledAlgorithms=MD2, MD5, RSA keySize < 1024, \
|
||||
DSA keySize < 1024
|
||||
|
||||
|
@ -456,7 +456,7 @@ public class TimestampCheck {
|
||||
.shouldMatch("Timestamp signature algorithm: .*key.*weak");
|
||||
verify(file, "-J-Djava.security.debug=jar")
|
||||
.shouldHaveExitValue(0)
|
||||
.shouldMatch("SignatureException:.*Disabled");
|
||||
.shouldMatch("SignatureException:.*disabled");
|
||||
}
|
||||
|
||||
static void checkHalfWeak(String file) throws Throwable {
|
||||
|
Loading…
x
Reference in New Issue
Block a user