123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500 |
- #if !BESTHTTP_DISABLE_ALTERNATE_SSL && (!UNITY_WEBGL || UNITY_EDITOR)
- #pragma warning disable
- using System;
- using System.Collections;
- using System.IO;
- using System.Text;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Asn1;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Asn1.Cmp;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Asn1.Cms;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Asn1.Ess;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Asn1.Oiw;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Asn1.Pkcs;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Asn1.Tsp;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Asn1.X509;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Cms;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Crypto;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Crypto.Operators;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Math;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Utilities;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.X509;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.X509.Store;
- namespace BestHTTP.SecureProtocol.Org.BouncyCastle.Tsp
- {
- public enum Resolution
- {
- R_SECONDS, R_TENTHS_OF_SECONDS, R_HUNDREDTHS_OF_SECONDS, R_MILLISECONDS
- }
- public class TimeStampTokenGenerator
- {
- private int accuracySeconds = -1;
- private int accuracyMillis = -1;
- private int accuracyMicros = -1;
- private bool ordering = false;
- private GeneralName tsa = null;
- private DerObjectIdentifier tsaPolicyOID;
-
- private IX509Store x509Certs;
- private IX509Store x509Crls;
- private SignerInfoGenerator signerInfoGenerator;
- IDigestFactory digestCalculator;
- private Resolution resolution = Resolution.R_SECONDS;
-
- public Resolution Resolution
- {
- get { return resolution; }
- set { resolution = value; }
- }
- /**
- * basic creation - only the default attributes will be included here.
- */
- public TimeStampTokenGenerator(
- AsymmetricKeyParameter key,
- X509Certificate cert,
- string digestOID,
- string tsaPolicyOID)
- : this(key, cert, digestOID, tsaPolicyOID, null, null)
- {
- }
- public TimeStampTokenGenerator(
- SignerInfoGenerator signerInfoGen,
- IDigestFactory digestCalculator,
- DerObjectIdentifier tsaPolicy,
- bool isIssuerSerialIncluded)
- {
- this.signerInfoGenerator = signerInfoGen;
- this.digestCalculator = digestCalculator;
- this.tsaPolicyOID = tsaPolicy;
- if (signerInfoGenerator.certificate == null)
- {
- throw new ArgumentException("SignerInfoGenerator must have an associated certificate");
- }
- X509Certificate assocCert = signerInfoGenerator.certificate;
- TspUtil.ValidateCertificate(assocCert);
- try
- {
- IStreamCalculator calculator = digestCalculator.CreateCalculator();
- Stream stream = calculator.Stream;
- byte[] certEnc = assocCert.GetEncoded();
- stream.Write(certEnc, 0, certEnc.Length);
- stream.Flush();
- BestHTTP.SecureProtocol.Org.BouncyCastle.Utilities.Platform.Dispose(stream);
- if (((AlgorithmIdentifier)digestCalculator.AlgorithmDetails).Algorithm.Equals(OiwObjectIdentifiers.IdSha1))
- {
- EssCertID essCertID = new EssCertID(
- ((IBlockResult)calculator.GetResult()).Collect(),
- isIssuerSerialIncluded ?
- new IssuerSerial(
- new GeneralNames(
- new GeneralName(assocCert.IssuerDN)),
- new DerInteger(assocCert.SerialNumber)) : null);
- this.signerInfoGenerator = signerInfoGen.NewBuilder()
- .WithSignedAttributeGenerator(new TableGen(signerInfoGen, essCertID))
- .Build(signerInfoGen.contentSigner, signerInfoGen.certificate);
- }
- else
- {
- AlgorithmIdentifier digestAlgID = new AlgorithmIdentifier(
- ((AlgorithmIdentifier)digestCalculator.AlgorithmDetails).Algorithm);
- EssCertIDv2 essCertID = new EssCertIDv2(
- ((IBlockResult)calculator.GetResult()).Collect(),
- isIssuerSerialIncluded ?
- new IssuerSerial(
- new GeneralNames(
- new GeneralName(assocCert.IssuerDN)),
- new DerInteger(assocCert.SerialNumber)) : null);
- this.signerInfoGenerator = signerInfoGen.NewBuilder()
- .WithSignedAttributeGenerator(new TableGen2(signerInfoGen, essCertID))
- .Build(signerInfoGen.contentSigner, signerInfoGen.certificate);
- }
- }
- catch (Exception ex)
- {
- throw new TspException("Exception processing certificate", ex);
- }
- }
- /**
- * create with a signer with extra signed/unsigned attributes.
- */
- public TimeStampTokenGenerator(
- AsymmetricKeyParameter key,
- X509Certificate cert,
- string digestOID,
- string tsaPolicyOID,
- Asn1.Cms.AttributeTable signedAttr,
- Asn1.Cms.AttributeTable unsignedAttr) : this(
- makeInfoGenerator(key, cert, digestOID, signedAttr, unsignedAttr),
- Asn1DigestFactory.Get(OiwObjectIdentifiers.IdSha1),
- tsaPolicyOID != null ? new DerObjectIdentifier(tsaPolicyOID):null, false)
- {
- }
- internal static SignerInfoGenerator makeInfoGenerator(
- AsymmetricKeyParameter key,
- X509Certificate cert,
- string digestOID,
- Asn1.Cms.AttributeTable signedAttr,
- Asn1.Cms.AttributeTable unsignedAttr)
- {
- TspUtil.ValidateCertificate(cert);
- //
- // Add the ESSCertID attribute
- //
- IDictionary signedAttrs;
- if (signedAttr != null)
- {
- signedAttrs = signedAttr.ToDictionary();
- }
- else
- {
- signedAttrs = BestHTTP.SecureProtocol.Org.BouncyCastle.Utilities.Platform.CreateHashtable();
- }
- //try
- //{
- // byte[] hash = DigestUtilities.CalculateDigest("SHA-1", cert.GetEncoded());
- // EssCertID essCertid = new EssCertID(hash);
- // Asn1.Cms.Attribute attr = new Asn1.Cms.Attribute(
- // PkcsObjectIdentifiers.IdAASigningCertificate,
- // new DerSet(new SigningCertificate(essCertid)));
- // signedAttrs[attr.AttrType] = attr;
- //}
- //catch (CertificateEncodingException e)
- //{
- // throw new TspException("Exception processing certificate.", e);
- //}
- //catch (SecurityUtilityException e)
- //{
- // throw new TspException("Can't find a SHA-1 implementation.", e);
- //}
- string digestName = CmsSignedHelper.Instance.GetDigestAlgName(digestOID);
- string signatureName = digestName + "with" + CmsSignedHelper.Instance.GetEncryptionAlgName(CmsSignedHelper.Instance.GetEncOid(key, digestOID));
- Asn1SignatureFactory sigfact = new Asn1SignatureFactory(signatureName, key);
- return new SignerInfoGeneratorBuilder()
- .WithSignedAttributeGenerator(
- new DefaultSignedAttributeTableGenerator(
- new Asn1.Cms.AttributeTable(signedAttrs)))
- .WithUnsignedAttributeGenerator(
- new SimpleAttributeTableGenerator(unsignedAttr))
- .Build(sigfact, cert);
- }
- public void SetCertificates(
- IX509Store certificates)
- {
- this.x509Certs = certificates;
- }
- public void SetCrls(
- IX509Store crls)
- {
- this.x509Crls = crls;
- }
- public void SetAccuracySeconds(
- int accuracySeconds)
- {
- this.accuracySeconds = accuracySeconds;
- }
- public void SetAccuracyMillis(
- int accuracyMillis)
- {
- this.accuracyMillis = accuracyMillis;
- }
- public void SetAccuracyMicros(
- int accuracyMicros)
- {
- this.accuracyMicros = accuracyMicros;
- }
- public void SetOrdering(
- bool ordering)
- {
- this.ordering = ordering;
- }
- public void SetTsa(
- GeneralName tsa)
- {
- this.tsa = tsa;
- }
- //------------------------------------------------------------------------------
- public TimeStampToken Generate(
- TimeStampRequest request,
- BigInteger serialNumber,
- DateTime genTime)
- {
- return Generate(request, serialNumber, genTime, null);
- }
- public TimeStampToken Generate(
- TimeStampRequest request,
- BigInteger serialNumber,
- DateTime genTime, X509Extensions additionalExtensions)
- {
- DerObjectIdentifier digestAlgOID = new DerObjectIdentifier(request.MessageImprintAlgOid);
- AlgorithmIdentifier algID = new AlgorithmIdentifier(digestAlgOID, DerNull.Instance);
- MessageImprint messageImprint = new MessageImprint(algID, request.GetMessageImprintDigest());
- Accuracy accuracy = null;
- if (accuracySeconds > 0 || accuracyMillis > 0 || accuracyMicros > 0)
- {
- DerInteger seconds = null;
- if (accuracySeconds > 0)
- {
- seconds = new DerInteger(accuracySeconds);
- }
- DerInteger millis = null;
- if (accuracyMillis > 0)
- {
- millis = new DerInteger(accuracyMillis);
- }
- DerInteger micros = null;
- if (accuracyMicros > 0)
- {
- micros = new DerInteger(accuracyMicros);
- }
- accuracy = new Accuracy(seconds, millis, micros);
- }
- DerBoolean derOrdering = null;
- if (ordering)
- {
- derOrdering = DerBoolean.GetInstance(ordering);
- }
- DerInteger nonce = null;
- if (request.Nonce != null)
- {
- nonce = new DerInteger(request.Nonce);
- }
-
- DerObjectIdentifier tsaPolicy = tsaPolicyOID;
- if (request.ReqPolicy != null)
- {
- tsaPolicy = new DerObjectIdentifier(request.ReqPolicy);
- }
- if (tsaPolicy == null)
- {
- throw new TspValidationException("request contains no policy", PkiFailureInfo.UnacceptedPolicy);
- }
- X509Extensions respExtensions = request.Extensions;
- if (additionalExtensions != null)
- {
- X509ExtensionsGenerator extGen = new X509ExtensionsGenerator();
- if (respExtensions != null)
- {
- foreach(object oid in respExtensions.ExtensionOids)
- {
- DerObjectIdentifier id = DerObjectIdentifier.GetInstance(oid);
- extGen.AddExtension(id, respExtensions.GetExtension(DerObjectIdentifier.GetInstance(id)));
- }
- }
- foreach (object oid in additionalExtensions.ExtensionOids)
- {
- DerObjectIdentifier id = DerObjectIdentifier.GetInstance(oid);
- extGen.AddExtension(id, additionalExtensions.GetExtension(DerObjectIdentifier.GetInstance(id)));
- }
-
- respExtensions = extGen.Generate();
- }
- DerGeneralizedTime generalizedTime;
- if (resolution != Resolution.R_SECONDS)
- {
- generalizedTime = new DerGeneralizedTime(createGeneralizedTime(genTime));
- }
- else
- {
- generalizedTime = new DerGeneralizedTime(genTime);
- }
- TstInfo tstInfo = new TstInfo(tsaPolicy, messageImprint,
- new DerInteger(serialNumber), generalizedTime, accuracy,
- derOrdering, nonce, tsa, respExtensions);
- try
- {
- CmsSignedDataGenerator signedDataGenerator = new CmsSignedDataGenerator();
- byte[] derEncodedTstInfo = tstInfo.GetDerEncoded();
- if (request.CertReq)
- {
- signedDataGenerator.AddCertificates(x509Certs);
- }
- signedDataGenerator.AddCrls(x509Crls);
- signedDataGenerator.AddSignerInfoGenerator(signerInfoGenerator);
- CmsSignedData signedData = signedDataGenerator.Generate(
- PkcsObjectIdentifiers.IdCTTstInfo.Id,
- new CmsProcessableByteArray(derEncodedTstInfo),
- true);
- return new TimeStampToken(signedData);
- }
- catch (CmsException cmsEx)
- {
- throw new TspException("Error generating time-stamp token", cmsEx);
- }
- catch (IOException e)
- {
- throw new TspException("Exception encoding info", e);
- }
- catch (X509StoreException e)
- {
- throw new TspException("Exception handling CertStore", e);
- }
- // catch (InvalidAlgorithmParameterException e)
- // {
- // throw new TspException("Exception handling CertStore CRLs", e);
- // }
- }
- private string createGeneralizedTime(DateTime genTime)
- {
- String format = "yyyyMMddHHmmss.fff";
-
- StringBuilder sBuild = new StringBuilder(genTime.ToString(format));
- int dotIndex = sBuild.ToString().IndexOf(".");
- if (dotIndex <0)
- {
- sBuild.Append("Z");
- return sBuild.ToString();
- }
- switch(resolution)
- {
- case Resolution.R_TENTHS_OF_SECONDS:
- if (sBuild.Length > dotIndex + 2)
- {
- sBuild.Remove(dotIndex + 2, sBuild.Length-(dotIndex+2));
- }
- break;
- case Resolution.R_HUNDREDTHS_OF_SECONDS:
- if (sBuild.Length > dotIndex + 3)
- {
- sBuild.Remove(dotIndex + 3, sBuild.Length-(dotIndex+3));
- }
- break;
- case Resolution.R_SECONDS:
- case Resolution.R_MILLISECONDS:
- // do nothing.
- break;
-
- }
-
- while (sBuild[sBuild.Length - 1] == '0')
- {
- sBuild.Remove(sBuild.Length - 1,1);
- }
- if (sBuild.Length - 1 == dotIndex)
- {
- sBuild.Remove(sBuild.Length - 1, 1);
- }
- sBuild.Append("Z");
- return sBuild.ToString();
- }
- private class TableGen : CmsAttributeTableGenerator
- {
- private readonly SignerInfoGenerator infoGen;
- private readonly EssCertID essCertID;
- public TableGen(SignerInfoGenerator infoGen, EssCertID essCertID)
- {
- this.infoGen = infoGen;
- this.essCertID = essCertID;
- }
- public Asn1.Cms.AttributeTable GetAttributes(IDictionary parameters)
- {
- Asn1.Cms.AttributeTable tab = infoGen.signedGen.GetAttributes(parameters);
- if (tab[PkcsObjectIdentifiers.IdAASigningCertificate] == null)
- {
- return tab.Add(PkcsObjectIdentifiers.IdAASigningCertificate, new SigningCertificate(essCertID));
- }
- return tab;
- }
- }
- private class TableGen2 : CmsAttributeTableGenerator
- {
- private readonly SignerInfoGenerator infoGen;
- private readonly EssCertIDv2 essCertID;
- public TableGen2(SignerInfoGenerator infoGen, EssCertIDv2 essCertID)
- {
- this.infoGen = infoGen;
- this.essCertID = essCertID;
- }
- public Asn1.Cms.AttributeTable GetAttributes(IDictionary parameters)
- {
- Asn1.Cms.AttributeTable tab = infoGen.signedGen.GetAttributes(parameters);
- if (tab[PkcsObjectIdentifiers.IdAASigningCertificateV2] == null)
- {
- return tab.Add(PkcsObjectIdentifiers.IdAASigningCertificateV2, new SigningCertificateV2(essCertID));
- }
- return tab;
- }
- }
- }
- }
- #pragma warning restore
- #endif
|