796 lines
22 KiB
C#
796 lines
22 KiB
C#
using System;
|
|
using System.Collections;
|
|
using System.IO;
|
|
using Org.BouncyCastle.Asn1;
|
|
using Org.BouncyCastle.Asn1.IsisMtt;
|
|
using Org.BouncyCastle.Asn1.X509;
|
|
using Org.BouncyCastle.Crypto;
|
|
using Org.BouncyCastle.Crypto.Parameters;
|
|
using Org.BouncyCastle.Math;
|
|
using Org.BouncyCastle.Security;
|
|
using Org.BouncyCastle.Utilities;
|
|
using Org.BouncyCastle.Utilities.Collections;
|
|
using Org.BouncyCastle.Utilities.Date;
|
|
using Org.BouncyCastle.X509;
|
|
using Org.BouncyCastle.X509.Extension;
|
|
using Org.BouncyCastle.X509.Store;
|
|
|
|
namespace Org.BouncyCastle.Pkix;
|
|
|
|
public class PkixCertPathValidatorUtilities
|
|
{
|
|
private static readonly PkixCrlUtilities CrlUtilities = new PkixCrlUtilities();
|
|
|
|
internal static readonly string ANY_POLICY = "2.5.29.32.0";
|
|
|
|
internal static readonly string CRL_NUMBER = X509Extensions.CrlNumber.Id;
|
|
|
|
internal static readonly int KEY_CERT_SIGN = 5;
|
|
|
|
internal static readonly int CRL_SIGN = 6;
|
|
|
|
internal static readonly string[] crlReasons = new string[11]
|
|
{
|
|
"unspecified", "keyCompromise", "cACompromise", "affiliationChanged", "superseded", "cessationOfOperation", "certificateHold", "unknown", "removeFromCRL", "privilegeWithdrawn",
|
|
"aACompromise"
|
|
};
|
|
|
|
internal static TrustAnchor FindTrustAnchor(X509Certificate cert, ISet trustAnchors)
|
|
{
|
|
IEnumerator enumerator = trustAnchors.GetEnumerator();
|
|
TrustAnchor trustAnchor = null;
|
|
AsymmetricKeyParameter asymmetricKeyParameter = null;
|
|
Exception ex = null;
|
|
X509CertStoreSelector x509CertStoreSelector = new X509CertStoreSelector();
|
|
try
|
|
{
|
|
x509CertStoreSelector.Subject = GetIssuerPrincipal(cert);
|
|
}
|
|
catch (IOException innerException)
|
|
{
|
|
throw new Exception("Cannot set subject search criteria for trust anchor.", innerException);
|
|
}
|
|
while (enumerator.MoveNext() && trustAnchor == null)
|
|
{
|
|
trustAnchor = (TrustAnchor)enumerator.Current;
|
|
if (trustAnchor.TrustedCert != null)
|
|
{
|
|
if (x509CertStoreSelector.Match(trustAnchor.TrustedCert))
|
|
{
|
|
asymmetricKeyParameter = trustAnchor.TrustedCert.GetPublicKey();
|
|
}
|
|
else
|
|
{
|
|
trustAnchor = null;
|
|
}
|
|
}
|
|
else if (trustAnchor.CAName != null && trustAnchor.CAPublicKey != null)
|
|
{
|
|
try
|
|
{
|
|
X509Name issuerPrincipal = GetIssuerPrincipal(cert);
|
|
X509Name other = new X509Name(trustAnchor.CAName);
|
|
if (issuerPrincipal.Equivalent(other, inOrder: true))
|
|
{
|
|
asymmetricKeyParameter = trustAnchor.CAPublicKey;
|
|
}
|
|
else
|
|
{
|
|
trustAnchor = null;
|
|
}
|
|
}
|
|
catch (InvalidParameterException)
|
|
{
|
|
trustAnchor = null;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
trustAnchor = null;
|
|
}
|
|
if (asymmetricKeyParameter != null)
|
|
{
|
|
try
|
|
{
|
|
cert.Verify(asymmetricKeyParameter);
|
|
}
|
|
catch (Exception ex3)
|
|
{
|
|
ex = ex3;
|
|
trustAnchor = null;
|
|
}
|
|
}
|
|
}
|
|
if (trustAnchor == null && ex != null)
|
|
{
|
|
throw new Exception("TrustAnchor found but certificate validation failed.", ex);
|
|
}
|
|
return trustAnchor;
|
|
}
|
|
|
|
internal static bool IsIssuerTrustAnchor(X509Certificate cert, ISet trustAnchors)
|
|
{
|
|
try
|
|
{
|
|
return FindTrustAnchor(cert, trustAnchors) != null;
|
|
}
|
|
catch (Exception)
|
|
{
|
|
return false;
|
|
}
|
|
}
|
|
|
|
internal static void AddAdditionalStoresFromAltNames(X509Certificate cert, PkixParameters pkixParams)
|
|
{
|
|
if (cert.GetIssuerAlternativeNames() == null)
|
|
{
|
|
return;
|
|
}
|
|
IEnumerator enumerator = cert.GetIssuerAlternativeNames().GetEnumerator();
|
|
while (enumerator.MoveNext())
|
|
{
|
|
IList list = (IList)enumerator.Current;
|
|
if (list[0].Equals(6))
|
|
{
|
|
string location = (string)list[1];
|
|
AddAdditionalStoreFromLocation(location, pkixParams);
|
|
}
|
|
}
|
|
}
|
|
|
|
internal static DateTime GetValidDate(PkixParameters paramsPKIX)
|
|
{
|
|
return paramsPKIX.Date?.Value ?? DateTime.UtcNow;
|
|
}
|
|
|
|
internal static X509Name GetIssuerPrincipal(object cert)
|
|
{
|
|
if (cert is X509Certificate)
|
|
{
|
|
return ((X509Certificate)cert).IssuerDN;
|
|
}
|
|
return ((IX509AttributeCertificate)cert).Issuer.GetPrincipals()[0];
|
|
}
|
|
|
|
internal static bool IsSelfIssued(X509Certificate cert)
|
|
{
|
|
return cert.SubjectDN.Equivalent(cert.IssuerDN, inOrder: true);
|
|
}
|
|
|
|
internal static AlgorithmIdentifier GetAlgorithmIdentifier(AsymmetricKeyParameter key)
|
|
{
|
|
try
|
|
{
|
|
SubjectPublicKeyInfo subjectPublicKeyInfo = SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(key);
|
|
return subjectPublicKeyInfo.AlgorithmID;
|
|
}
|
|
catch (Exception cause)
|
|
{
|
|
throw new PkixCertPathValidatorException("Subject public key cannot be decoded.", cause);
|
|
}
|
|
}
|
|
|
|
internal static bool IsAnyPolicy(ISet policySet)
|
|
{
|
|
if (policySet != null && !policySet.Contains(ANY_POLICY))
|
|
{
|
|
return policySet.Count == 0;
|
|
}
|
|
return true;
|
|
}
|
|
|
|
internal static void AddAdditionalStoreFromLocation(string location, PkixParameters pkixParams)
|
|
{
|
|
if (!pkixParams.IsAdditionalLocationsEnabled)
|
|
{
|
|
return;
|
|
}
|
|
try
|
|
{
|
|
if (Platform.StartsWith(location, "ldap://"))
|
|
{
|
|
location = location.Substring(7);
|
|
int num = location.IndexOf('/');
|
|
if (num != -1)
|
|
{
|
|
_ = "ldap://" + location.Substring(0, num);
|
|
}
|
|
else
|
|
{
|
|
_ = "ldap://" + location;
|
|
}
|
|
throw Platform.CreateNotImplementedException("LDAP cert/CRL stores");
|
|
}
|
|
}
|
|
catch (Exception)
|
|
{
|
|
throw new Exception("Exception adding X.509 stores.");
|
|
}
|
|
}
|
|
|
|
private static BigInteger GetSerialNumber(object cert)
|
|
{
|
|
if (cert is X509Certificate)
|
|
{
|
|
return ((X509Certificate)cert).SerialNumber;
|
|
}
|
|
return ((X509V2AttributeCertificate)cert).SerialNumber;
|
|
}
|
|
|
|
internal static ISet GetQualifierSet(Asn1Sequence qualifiers)
|
|
{
|
|
ISet set = new HashSet();
|
|
if (qualifiers == null)
|
|
{
|
|
return set;
|
|
}
|
|
foreach (Asn1Encodable qualifier in qualifiers)
|
|
{
|
|
try
|
|
{
|
|
set.Add(PolicyQualifierInfo.GetInstance(qualifier.ToAsn1Object()));
|
|
}
|
|
catch (IOException cause)
|
|
{
|
|
throw new PkixCertPathValidatorException("Policy qualifier info cannot be decoded.", cause);
|
|
}
|
|
}
|
|
return set;
|
|
}
|
|
|
|
internal static PkixPolicyNode RemovePolicyNode(PkixPolicyNode validPolicyTree, IList[] policyNodes, PkixPolicyNode _node)
|
|
{
|
|
PkixPolicyNode parent = _node.Parent;
|
|
if (validPolicyTree == null)
|
|
{
|
|
return null;
|
|
}
|
|
if (parent == null)
|
|
{
|
|
for (int i = 0; i < policyNodes.Length; i++)
|
|
{
|
|
policyNodes[i] = Platform.CreateArrayList();
|
|
}
|
|
return null;
|
|
}
|
|
parent.RemoveChild(_node);
|
|
RemovePolicyNodeRecurse(policyNodes, _node);
|
|
return validPolicyTree;
|
|
}
|
|
|
|
private static void RemovePolicyNodeRecurse(IList[] policyNodes, PkixPolicyNode _node)
|
|
{
|
|
policyNodes[_node.Depth].Remove(_node);
|
|
if (!_node.HasChildren)
|
|
{
|
|
return;
|
|
}
|
|
foreach (PkixPolicyNode child in _node.Children)
|
|
{
|
|
RemovePolicyNodeRecurse(policyNodes, child);
|
|
}
|
|
}
|
|
|
|
internal static void PrepareNextCertB1(int i, IList[] policyNodes, string id_p, IDictionary m_idp, X509Certificate cert)
|
|
{
|
|
bool flag = false;
|
|
IEnumerator enumerator = policyNodes[i].GetEnumerator();
|
|
while (enumerator.MoveNext())
|
|
{
|
|
PkixPolicyNode pkixPolicyNode = (PkixPolicyNode)enumerator.Current;
|
|
if (pkixPolicyNode.ValidPolicy.Equals(id_p))
|
|
{
|
|
flag = true;
|
|
pkixPolicyNode.ExpectedPolicies = (ISet)m_idp[id_p];
|
|
break;
|
|
}
|
|
}
|
|
if (flag)
|
|
{
|
|
return;
|
|
}
|
|
enumerator = policyNodes[i].GetEnumerator();
|
|
while (enumerator.MoveNext())
|
|
{
|
|
PkixPolicyNode pkixPolicyNode2 = (PkixPolicyNode)enumerator.Current;
|
|
if (!ANY_POLICY.Equals(pkixPolicyNode2.ValidPolicy))
|
|
{
|
|
continue;
|
|
}
|
|
ISet policyQualifiers = null;
|
|
Asn1Sequence asn1Sequence = null;
|
|
try
|
|
{
|
|
asn1Sequence = Asn1Sequence.GetInstance(GetExtensionValue(cert, X509Extensions.CertificatePolicies));
|
|
}
|
|
catch (Exception innerException)
|
|
{
|
|
throw new Exception("Certificate policies cannot be decoded.", innerException);
|
|
}
|
|
IEnumerator enumerator2 = asn1Sequence.GetEnumerator();
|
|
while (enumerator2.MoveNext())
|
|
{
|
|
PolicyInformation policyInformation = null;
|
|
try
|
|
{
|
|
policyInformation = PolicyInformation.GetInstance(enumerator2.Current);
|
|
}
|
|
catch (Exception innerException2)
|
|
{
|
|
throw new Exception("Policy information cannot be decoded.", innerException2);
|
|
}
|
|
if (ANY_POLICY.Equals(policyInformation.PolicyIdentifier.Id))
|
|
{
|
|
try
|
|
{
|
|
policyQualifiers = GetQualifierSet(policyInformation.PolicyQualifiers);
|
|
}
|
|
catch (PkixCertPathValidatorException cause)
|
|
{
|
|
throw new PkixCertPathValidatorException("Policy qualifier info set could not be built.", cause);
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
bool critical = false;
|
|
ISet criticalExtensionOids = cert.GetCriticalExtensionOids();
|
|
if (criticalExtensionOids != null)
|
|
{
|
|
critical = criticalExtensionOids.Contains(X509Extensions.CertificatePolicies.Id);
|
|
}
|
|
PkixPolicyNode parent = pkixPolicyNode2.Parent;
|
|
if (ANY_POLICY.Equals(parent.ValidPolicy))
|
|
{
|
|
PkixPolicyNode pkixPolicyNode3 = new PkixPolicyNode(Platform.CreateArrayList(), i, (ISet)m_idp[id_p], parent, policyQualifiers, id_p, critical);
|
|
parent.AddChild(pkixPolicyNode3);
|
|
policyNodes[i].Add(pkixPolicyNode3);
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
|
|
internal static PkixPolicyNode PrepareNextCertB2(int i, IList[] policyNodes, string id_p, PkixPolicyNode validPolicyTree)
|
|
{
|
|
int num = 0;
|
|
foreach (PkixPolicyNode item in Platform.CreateArrayList(policyNodes[i]))
|
|
{
|
|
if (item.ValidPolicy.Equals(id_p))
|
|
{
|
|
PkixPolicyNode parent = item.Parent;
|
|
parent.RemoveChild(item);
|
|
policyNodes[i].RemoveAt(num);
|
|
for (int num2 = i - 1; num2 >= 0; num2--)
|
|
{
|
|
IList list = policyNodes[num2];
|
|
for (int j = 0; j < list.Count; j++)
|
|
{
|
|
PkixPolicyNode pkixPolicyNode2 = (PkixPolicyNode)list[j];
|
|
if (!pkixPolicyNode2.HasChildren)
|
|
{
|
|
validPolicyTree = RemovePolicyNode(validPolicyTree, policyNodes, pkixPolicyNode2);
|
|
if (validPolicyTree == null)
|
|
{
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
num++;
|
|
}
|
|
}
|
|
return validPolicyTree;
|
|
}
|
|
|
|
internal static void GetCertStatus(DateTime validDate, X509Crl crl, object cert, CertStatus certStatus)
|
|
{
|
|
X509Crl x509Crl = null;
|
|
try
|
|
{
|
|
x509Crl = new X509Crl(CertificateList.GetInstance((Asn1Sequence)Asn1Object.FromByteArray(crl.GetEncoded())));
|
|
}
|
|
catch (Exception innerException)
|
|
{
|
|
throw new Exception("Bouncy Castle X509Crl could not be created.", innerException);
|
|
}
|
|
X509CrlEntry revokedCertificate = x509Crl.GetRevokedCertificate(GetSerialNumber(cert));
|
|
if (revokedCertificate == null)
|
|
{
|
|
return;
|
|
}
|
|
X509Name issuerPrincipal = GetIssuerPrincipal(cert);
|
|
if (!issuerPrincipal.Equivalent(revokedCertificate.GetCertificateIssuer(), inOrder: true) && !issuerPrincipal.Equivalent(crl.IssuerDN, inOrder: true))
|
|
{
|
|
return;
|
|
}
|
|
DerEnumerated derEnumerated = null;
|
|
if (revokedCertificate.HasExtensions)
|
|
{
|
|
try
|
|
{
|
|
derEnumerated = DerEnumerated.GetInstance(GetExtensionValue(revokedCertificate, X509Extensions.ReasonCode));
|
|
}
|
|
catch (Exception innerException2)
|
|
{
|
|
throw new Exception("Reason code CRL entry extension could not be decoded.", innerException2);
|
|
}
|
|
}
|
|
if (validDate.Ticks >= revokedCertificate.RevocationDate.Ticks || derEnumerated == null || derEnumerated.Value.TestBit(0) || derEnumerated.Value.TestBit(1) || derEnumerated.Value.TestBit(2) || derEnumerated.Value.TestBit(8))
|
|
{
|
|
if (derEnumerated != null)
|
|
{
|
|
certStatus.Status = derEnumerated.Value.SignValue;
|
|
}
|
|
else
|
|
{
|
|
certStatus.Status = 0;
|
|
}
|
|
certStatus.RevocationDate = new DateTimeObject(revokedCertificate.RevocationDate);
|
|
}
|
|
}
|
|
|
|
internal static AsymmetricKeyParameter GetNextWorkingKey(IList certs, int index)
|
|
{
|
|
X509Certificate x509Certificate = (X509Certificate)certs[index];
|
|
AsymmetricKeyParameter publicKey = x509Certificate.GetPublicKey();
|
|
if (!(publicKey is DsaPublicKeyParameters))
|
|
{
|
|
return publicKey;
|
|
}
|
|
DsaPublicKeyParameters dsaPublicKeyParameters = (DsaPublicKeyParameters)publicKey;
|
|
if (dsaPublicKeyParameters.Parameters != null)
|
|
{
|
|
return dsaPublicKeyParameters;
|
|
}
|
|
for (int i = index + 1; i < certs.Count; i++)
|
|
{
|
|
X509Certificate x509Certificate2 = (X509Certificate)certs[i];
|
|
publicKey = x509Certificate2.GetPublicKey();
|
|
if (!(publicKey is DsaPublicKeyParameters))
|
|
{
|
|
throw new PkixCertPathValidatorException("DSA parameters cannot be inherited from previous certificate.");
|
|
}
|
|
DsaPublicKeyParameters dsaPublicKeyParameters2 = (DsaPublicKeyParameters)publicKey;
|
|
if (dsaPublicKeyParameters2.Parameters != null)
|
|
{
|
|
DsaParameters parameters = dsaPublicKeyParameters2.Parameters;
|
|
try
|
|
{
|
|
return new DsaPublicKeyParameters(dsaPublicKeyParameters.Y, parameters);
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
throw new Exception(ex.Message);
|
|
}
|
|
}
|
|
}
|
|
throw new PkixCertPathValidatorException("DSA parameters cannot be inherited from previous certificate.");
|
|
}
|
|
|
|
internal static DateTime GetValidCertDateFromValidityModel(PkixParameters paramsPkix, PkixCertPath certPath, int index)
|
|
{
|
|
if (paramsPkix.ValidityModel != 1)
|
|
{
|
|
return GetValidDate(paramsPkix);
|
|
}
|
|
if (index <= 0)
|
|
{
|
|
return GetValidDate(paramsPkix);
|
|
}
|
|
if (index - 1 == 0)
|
|
{
|
|
DerGeneralizedTime derGeneralizedTime = null;
|
|
try
|
|
{
|
|
X509Certificate x509Certificate = (X509Certificate)certPath.Certificates[index - 1];
|
|
Asn1OctetString extensionValue = x509Certificate.GetExtensionValue(IsisMttObjectIdentifiers.IdIsisMttATDateOfCertGen);
|
|
derGeneralizedTime = DerGeneralizedTime.GetInstance(extensionValue);
|
|
}
|
|
catch (ArgumentException)
|
|
{
|
|
throw new Exception("Date of cert gen extension could not be read.");
|
|
}
|
|
if (derGeneralizedTime != null)
|
|
{
|
|
try
|
|
{
|
|
return derGeneralizedTime.ToDateTime();
|
|
}
|
|
catch (ArgumentException innerException)
|
|
{
|
|
throw new Exception("Date from date of cert gen extension could not be parsed.", innerException);
|
|
}
|
|
}
|
|
}
|
|
return ((X509Certificate)certPath.Certificates[index - 1]).NotBefore;
|
|
}
|
|
|
|
internal static ICollection FindCertificates(X509CertStoreSelector certSelect, IList certStores)
|
|
{
|
|
ISet set = new HashSet();
|
|
foreach (IX509Store certStore in certStores)
|
|
{
|
|
try
|
|
{
|
|
foreach (X509Certificate match in certStore.GetMatches(certSelect))
|
|
{
|
|
set.Add(match);
|
|
}
|
|
}
|
|
catch (Exception innerException)
|
|
{
|
|
throw new Exception("Problem while picking certificates from X.509 store.", innerException);
|
|
}
|
|
}
|
|
return set;
|
|
}
|
|
|
|
internal static void GetCrlIssuersFromDistributionPoint(DistributionPoint dp, ICollection issuerPrincipals, X509CrlStoreSelector selector, PkixParameters pkixParams)
|
|
{
|
|
IList list = Platform.CreateArrayList();
|
|
if (dp.CrlIssuer != null)
|
|
{
|
|
GeneralName[] names = dp.CrlIssuer.GetNames();
|
|
for (int i = 0; i < names.Length; i++)
|
|
{
|
|
if (names[i].TagNo == 4)
|
|
{
|
|
try
|
|
{
|
|
list.Add(X509Name.GetInstance(names[i].Name.ToAsn1Object()));
|
|
}
|
|
catch (IOException innerException)
|
|
{
|
|
throw new Exception("CRL issuer information from distribution point cannot be decoded.", innerException);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (dp.DistributionPointName == null)
|
|
{
|
|
throw new Exception("CRL issuer is omitted from distribution point but no distributionPoint field present.");
|
|
}
|
|
IEnumerator enumerator = issuerPrincipals.GetEnumerator();
|
|
while (enumerator.MoveNext())
|
|
{
|
|
list.Add((X509Name)enumerator.Current);
|
|
}
|
|
}
|
|
selector.Issuers = list;
|
|
}
|
|
|
|
internal static ISet GetCompleteCrls(DistributionPoint dp, object cert, DateTime currentDate, PkixParameters paramsPKIX)
|
|
{
|
|
X509CrlStoreSelector x509CrlStoreSelector = new X509CrlStoreSelector();
|
|
try
|
|
{
|
|
ISet set = new HashSet();
|
|
if (cert is X509V2AttributeCertificate)
|
|
{
|
|
set.Add(((X509V2AttributeCertificate)cert).Issuer.GetPrincipals()[0]);
|
|
}
|
|
else
|
|
{
|
|
set.Add(GetIssuerPrincipal(cert));
|
|
}
|
|
GetCrlIssuersFromDistributionPoint(dp, set, x509CrlStoreSelector, paramsPKIX);
|
|
}
|
|
catch (Exception innerException)
|
|
{
|
|
throw new Exception("Could not get issuer information from distribution point.", innerException);
|
|
}
|
|
if (cert is X509Certificate)
|
|
{
|
|
x509CrlStoreSelector.CertificateChecking = (X509Certificate)cert;
|
|
}
|
|
else if (cert is X509V2AttributeCertificate)
|
|
{
|
|
x509CrlStoreSelector.AttrCertChecking = (IX509AttributeCertificate)cert;
|
|
}
|
|
x509CrlStoreSelector.CompleteCrlEnabled = true;
|
|
ISet set2 = CrlUtilities.FindCrls(x509CrlStoreSelector, paramsPKIX, currentDate);
|
|
if (set2.IsEmpty)
|
|
{
|
|
if (cert is IX509AttributeCertificate)
|
|
{
|
|
IX509AttributeCertificate iX509AttributeCertificate = (IX509AttributeCertificate)cert;
|
|
throw new Exception(string.Concat("No CRLs found for issuer \"", iX509AttributeCertificate.Issuer.GetPrincipals()[0], "\""));
|
|
}
|
|
X509Certificate x509Certificate = (X509Certificate)cert;
|
|
throw new Exception(string.Concat("No CRLs found for issuer \"", x509Certificate.IssuerDN, "\""));
|
|
}
|
|
return set2;
|
|
}
|
|
|
|
internal static ISet GetDeltaCrls(DateTime currentDate, PkixParameters paramsPKIX, X509Crl completeCRL)
|
|
{
|
|
X509CrlStoreSelector x509CrlStoreSelector = new X509CrlStoreSelector();
|
|
try
|
|
{
|
|
IList list = Platform.CreateArrayList();
|
|
list.Add(completeCRL.IssuerDN);
|
|
x509CrlStoreSelector.Issuers = list;
|
|
}
|
|
catch (IOException innerException)
|
|
{
|
|
throw new Exception("Cannot extract issuer from CRL.", innerException);
|
|
}
|
|
BigInteger bigInteger = null;
|
|
try
|
|
{
|
|
Asn1Object extensionValue = GetExtensionValue(completeCRL, X509Extensions.CrlNumber);
|
|
if (extensionValue != null)
|
|
{
|
|
bigInteger = DerInteger.GetInstance(extensionValue).PositiveValue;
|
|
}
|
|
}
|
|
catch (Exception innerException2)
|
|
{
|
|
throw new Exception("CRL number extension could not be extracted from CRL.", innerException2);
|
|
}
|
|
byte[] issuingDistributionPoint = null;
|
|
try
|
|
{
|
|
Asn1Object extensionValue2 = GetExtensionValue(completeCRL, X509Extensions.IssuingDistributionPoint);
|
|
if (extensionValue2 != null)
|
|
{
|
|
issuingDistributionPoint = extensionValue2.GetDerEncoded();
|
|
}
|
|
}
|
|
catch (Exception innerException3)
|
|
{
|
|
throw new Exception("Issuing distribution point extension value could not be read.", innerException3);
|
|
}
|
|
x509CrlStoreSelector.MinCrlNumber = bigInteger?.Add(BigInteger.One);
|
|
x509CrlStoreSelector.IssuingDistributionPoint = issuingDistributionPoint;
|
|
x509CrlStoreSelector.IssuingDistributionPointEnabled = true;
|
|
x509CrlStoreSelector.MaxBaseCrlNumber = bigInteger;
|
|
ISet set = CrlUtilities.FindCrls(x509CrlStoreSelector, paramsPKIX, currentDate);
|
|
ISet set2 = new HashSet();
|
|
foreach (X509Crl item in set)
|
|
{
|
|
if (isDeltaCrl(item))
|
|
{
|
|
set2.Add(item);
|
|
}
|
|
}
|
|
return set2;
|
|
}
|
|
|
|
private static bool isDeltaCrl(X509Crl crl)
|
|
{
|
|
ISet criticalExtensionOids = crl.GetCriticalExtensionOids();
|
|
return criticalExtensionOids.Contains(X509Extensions.DeltaCrlIndicator.Id);
|
|
}
|
|
|
|
internal static ICollection FindCertificates(X509AttrCertStoreSelector certSelect, IList certStores)
|
|
{
|
|
ISet set = new HashSet();
|
|
foreach (IX509Store certStore in certStores)
|
|
{
|
|
try
|
|
{
|
|
foreach (X509V2AttributeCertificate match in certStore.GetMatches(certSelect))
|
|
{
|
|
set.Add(match);
|
|
}
|
|
}
|
|
catch (Exception innerException)
|
|
{
|
|
throw new Exception("Problem while picking certificates from X.509 store.", innerException);
|
|
}
|
|
}
|
|
return set;
|
|
}
|
|
|
|
internal static void AddAdditionalStoresFromCrlDistributionPoint(CrlDistPoint crldp, PkixParameters pkixParams)
|
|
{
|
|
if (crldp == null)
|
|
{
|
|
return;
|
|
}
|
|
DistributionPoint[] array = null;
|
|
try
|
|
{
|
|
array = crldp.GetDistributionPoints();
|
|
}
|
|
catch (Exception innerException)
|
|
{
|
|
throw new Exception("Distribution points could not be read.", innerException);
|
|
}
|
|
for (int i = 0; i < array.Length; i++)
|
|
{
|
|
DistributionPointName distributionPointName = array[i].DistributionPointName;
|
|
if (distributionPointName == null || distributionPointName.PointType != 0)
|
|
{
|
|
continue;
|
|
}
|
|
GeneralName[] names = GeneralNames.GetInstance(distributionPointName.Name).GetNames();
|
|
for (int j = 0; j < names.Length; j++)
|
|
{
|
|
if (names[j].TagNo == 6)
|
|
{
|
|
string location = DerIA5String.GetInstance(names[j].Name).GetString();
|
|
AddAdditionalStoreFromLocation(location, pkixParams);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
internal static bool ProcessCertD1i(int index, IList[] policyNodes, DerObjectIdentifier pOid, ISet pq)
|
|
{
|
|
IList list = policyNodes[index - 1];
|
|
for (int i = 0; i < list.Count; i++)
|
|
{
|
|
PkixPolicyNode pkixPolicyNode = (PkixPolicyNode)list[i];
|
|
ISet expectedPolicies = pkixPolicyNode.ExpectedPolicies;
|
|
if (expectedPolicies.Contains(pOid.Id))
|
|
{
|
|
ISet set = new HashSet();
|
|
set.Add(pOid.Id);
|
|
PkixPolicyNode pkixPolicyNode2 = new PkixPolicyNode(Platform.CreateArrayList(), index, set, pkixPolicyNode, pq, pOid.Id, critical: false);
|
|
pkixPolicyNode.AddChild(pkixPolicyNode2);
|
|
policyNodes[index].Add(pkixPolicyNode2);
|
|
return true;
|
|
}
|
|
}
|
|
return false;
|
|
}
|
|
|
|
internal static void ProcessCertD1ii(int index, IList[] policyNodes, DerObjectIdentifier _poid, ISet _pq)
|
|
{
|
|
IList list = policyNodes[index - 1];
|
|
for (int i = 0; i < list.Count; i++)
|
|
{
|
|
PkixPolicyNode pkixPolicyNode = (PkixPolicyNode)list[i];
|
|
if (ANY_POLICY.Equals(pkixPolicyNode.ValidPolicy))
|
|
{
|
|
ISet set = new HashSet();
|
|
set.Add(_poid.Id);
|
|
PkixPolicyNode pkixPolicyNode2 = new PkixPolicyNode(Platform.CreateArrayList(), index, set, pkixPolicyNode, _pq, _poid.Id, critical: false);
|
|
pkixPolicyNode.AddChild(pkixPolicyNode2);
|
|
policyNodes[index].Add(pkixPolicyNode2);
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
internal static ICollection FindIssuerCerts(X509Certificate cert, PkixBuilderParameters pkixParams)
|
|
{
|
|
X509CertStoreSelector x509CertStoreSelector = new X509CertStoreSelector();
|
|
ISet set = new HashSet();
|
|
try
|
|
{
|
|
x509CertStoreSelector.Subject = cert.IssuerDN;
|
|
}
|
|
catch (IOException innerException)
|
|
{
|
|
throw new Exception("Subject criteria for certificate selector to find issuer certificate could not be set.", innerException);
|
|
}
|
|
try
|
|
{
|
|
set.AddAll(FindCertificates(x509CertStoreSelector, pkixParams.GetStores()));
|
|
set.AddAll(FindCertificates(x509CertStoreSelector, pkixParams.GetAdditionalStores()));
|
|
return set;
|
|
}
|
|
catch (Exception innerException2)
|
|
{
|
|
throw new Exception("Issuer certificate cannot be searched.", innerException2);
|
|
}
|
|
}
|
|
|
|
internal static Asn1Object GetExtensionValue(IX509Extension ext, DerObjectIdentifier oid)
|
|
{
|
|
Asn1OctetString extensionValue = ext.GetExtensionValue(oid);
|
|
if (extensionValue == null)
|
|
{
|
|
return null;
|
|
}
|
|
return X509ExtensionUtilities.FromExtensionValue(extensionValue);
|
|
}
|
|
}
|