123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301 |
- #if !BESTHTTP_DISABLE_ALTERNATE_SSL && (!UNITY_WEBGL || UNITY_EDITOR)
- #pragma warning disable
- using System;
- using System.IO;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Asn1;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Asn1.Cms;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Asn1.X509;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Crypto;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Crypto.Generators;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Crypto.IO;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Crypto.Parameters;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Security;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Utilities;
- using BestHTTP.SecureProtocol.Org.BouncyCastle.Utilities.IO;
- namespace BestHTTP.SecureProtocol.Org.BouncyCastle.Cms
- {
- /**
- * General class for generating a CMS authenticated-data message stream.
- * <p>
- * A simple example of usage.
- * <pre>
- * CMSAuthenticatedDataStreamGenerator edGen = new CMSAuthenticatedDataStreamGenerator();
- *
- * edGen.addKeyTransRecipient(cert);
- *
- * ByteArrayOutputStream bOut = new ByteArrayOutputStream();
- *
- * OutputStream out = edGen.open(
- * bOut, CMSAuthenticatedDataGenerator.AES128_CBC, "BC");*
- * out.write(data);
- *
- * out.close();
- * </pre>
- * </p>
- */
- public class CmsAuthenticatedDataStreamGenerator
- : CmsAuthenticatedGenerator
- {
- // TODO Add support
- // private object _originatorInfo = null;
- // private object _unprotectedAttributes = null;
- private int _bufferSize;
- private bool _berEncodeRecipientSet;
- /**
- * base constructor
- */
- public CmsAuthenticatedDataStreamGenerator()
- {
- }
- /**
- * constructor allowing specific source of randomness
- * @param rand instance of SecureRandom to use
- */
- public CmsAuthenticatedDataStreamGenerator(
- SecureRandom rand)
- : base(rand)
- {
- }
- /**
- * Set the underlying string size for encapsulated data
- *
- * @param bufferSize length of octet strings to buffer the data.
- */
- public void SetBufferSize(
- int bufferSize)
- {
- _bufferSize = bufferSize;
- }
- /**
- * Use a BER Set to store the recipient information
- */
- public void SetBerEncodeRecipients(
- bool berEncodeRecipientSet)
- {
- _berEncodeRecipientSet = berEncodeRecipientSet;
- }
- /**
- * generate an enveloped object that contains an CMS Enveloped Data
- * object using the given provider and the passed in key generator.
- * @throws java.io.IOException
- */
- private Stream Open(
- Stream outStr,
- string macOid,
- CipherKeyGenerator keyGen)
- {
- // FIXME Will this work for macs?
- byte[] encKeyBytes = keyGen.GenerateKey();
- KeyParameter encKey = ParameterUtilities.CreateKeyParameter(macOid, encKeyBytes);
- Asn1Encodable asn1Params = GenerateAsn1Parameters(macOid, encKeyBytes);
- ICipherParameters cipherParameters;
- AlgorithmIdentifier macAlgId = GetAlgorithmIdentifier(
- macOid, encKey, asn1Params, out cipherParameters);
- Asn1EncodableVector recipientInfos = new Asn1EncodableVector();
- foreach (RecipientInfoGenerator rig in recipientInfoGenerators)
- {
- try
- {
- recipientInfos.Add(rig.Generate(encKey, rand));
- }
- catch (InvalidKeyException e)
- {
- throw new CmsException("key inappropriate for algorithm.", e);
- }
- catch (GeneralSecurityException e)
- {
- throw new CmsException("error making encrypted content.", e);
- }
- }
- // FIXME Only passing key at the moment
- // return Open(outStr, macAlgId, cipherParameters, recipientInfos);
- return Open(outStr, macAlgId, encKey, recipientInfos);
- }
- protected Stream Open(
- Stream outStr,
- AlgorithmIdentifier macAlgId,
- ICipherParameters cipherParameters,
- Asn1EncodableVector recipientInfos)
- {
- try
- {
- //
- // ContentInfo
- //
- BerSequenceGenerator cGen = new BerSequenceGenerator(outStr);
- cGen.AddObject(CmsObjectIdentifiers.AuthenticatedData);
- //
- // Authenticated Data
- //
- BerSequenceGenerator authGen = new BerSequenceGenerator(
- cGen.GetRawOutputStream(), 0, true);
- authGen.AddObject(new DerInteger(AuthenticatedData.CalculateVersion(null)));
- Stream authRaw = authGen.GetRawOutputStream();
- Asn1Generator recipGen = _berEncodeRecipientSet
- ? (Asn1Generator) new BerSetGenerator(authRaw)
- : new DerSetGenerator(authRaw);
- foreach (Asn1Encodable ae in recipientInfos)
- {
- recipGen.AddObject(ae);
- }
- recipGen.Close();
- authGen.AddObject(macAlgId);
- BerSequenceGenerator eiGen = new BerSequenceGenerator(authRaw);
- eiGen.AddObject(CmsObjectIdentifiers.Data);
- Stream octetOutputStream = CmsUtilities.CreateBerOctetOutputStream(
- eiGen.GetRawOutputStream(), 0, true, _bufferSize);
- IMac mac = MacUtilities.GetMac(macAlgId.Algorithm);
- // TODO Confirm no ParametersWithRandom needed
- mac.Init(cipherParameters);
- Stream mOut = new TeeOutputStream(octetOutputStream, new MacSink(mac));
- return new CmsAuthenticatedDataOutputStream(mOut, mac, cGen, authGen, eiGen);
- }
- catch (SecurityUtilityException e)
- {
- throw new CmsException("couldn't create cipher.", e);
- }
- catch (InvalidKeyException e)
- {
- throw new CmsException("key invalid in message.", e);
- }
- catch (IOException e)
- {
- throw new CmsException("exception decoding algorithm parameters.", e);
- }
- }
- /**
- * generate an enveloped object that contains an CMS Enveloped Data object
- */
- public Stream Open(
- Stream outStr,
- string encryptionOid)
- {
- CipherKeyGenerator keyGen = GeneratorUtilities.GetKeyGenerator(encryptionOid);
- keyGen.Init(new KeyGenerationParameters(rand, keyGen.DefaultStrength));
- return Open(outStr, encryptionOid, keyGen);
- }
- /**
- * generate an enveloped object that contains an CMS Enveloped Data object
- */
- public Stream Open(
- Stream outStr,
- string encryptionOid,
- int keySize)
- {
- CipherKeyGenerator keyGen = GeneratorUtilities.GetKeyGenerator(encryptionOid);
- keyGen.Init(new KeyGenerationParameters(rand, keySize));
- return Open(outStr, encryptionOid, keyGen);
- }
- private class CmsAuthenticatedDataOutputStream
- : BaseOutputStream
- {
- private readonly Stream macStream;
- private readonly IMac mac;
- private readonly BerSequenceGenerator cGen;
- private readonly BerSequenceGenerator authGen;
- private readonly BerSequenceGenerator eiGen;
- public CmsAuthenticatedDataOutputStream(
- Stream macStream,
- IMac mac,
- BerSequenceGenerator cGen,
- BerSequenceGenerator authGen,
- BerSequenceGenerator eiGen)
- {
- this.macStream = macStream;
- this.mac = mac;
- this.cGen = cGen;
- this.authGen = authGen;
- this.eiGen = eiGen;
- }
- public override void WriteByte(
- byte b)
- {
- macStream.WriteByte(b);
- }
- public override void Write(
- byte[] bytes,
- int off,
- int len)
- {
- macStream.Write(bytes, off, len);
- }
- #if PORTABLE || NETFX_CORE
- protected override void Dispose(bool disposing)
- {
- if (disposing)
- {
- BestHTTP.SecureProtocol.Org.BouncyCastle.Utilities.Platform.Dispose(macStream);
- // TODO Parent context(s) should really be be closed explicitly
- eiGen.Close();
- // [TODO] auth attributes go here
- byte[] macOctets = MacUtilities.DoFinal(mac);
- authGen.AddObject(new DerOctetString(macOctets));
- // [TODO] unauth attributes go here
- authGen.Close();
- cGen.Close();
- }
- base.Dispose(disposing);
- }
- #else
- public override void Close()
- {
- BestHTTP.SecureProtocol.Org.BouncyCastle.Utilities.Platform.Dispose(macStream);
- // TODO Parent context(s) should really be be closed explicitly
- eiGen.Close();
- // [TODO] auth attributes go here
- byte[] macOctets = MacUtilities.DoFinal(mac);
- authGen.AddObject(new DerOctetString(macOctets));
- // [TODO] unauth attributes go here
- authGen.Close();
- cGen.Close();
- base.Close();
- }
- #endif
- }
- }
- }
- #pragma warning restore
- #endif
|