diff options
Diffstat (limited to 'crypto/src/cms/KeyAgreeRecipientInfoGenerator.cs')
-rw-r--r-- | crypto/src/cms/KeyAgreeRecipientInfoGenerator.cs | 85 |
1 files changed, 42 insertions, 43 deletions
diff --git a/crypto/src/cms/KeyAgreeRecipientInfoGenerator.cs b/crypto/src/cms/KeyAgreeRecipientInfoGenerator.cs index f74365571..8feb25b43 100644 --- a/crypto/src/cms/KeyAgreeRecipientInfoGenerator.cs +++ b/crypto/src/cms/KeyAgreeRecipientInfoGenerator.cs @@ -1,4 +1,3 @@ -using System; using System.Collections.Generic; using System.IO; @@ -15,46 +14,54 @@ using Org.BouncyCastle.X509; namespace Org.BouncyCastle.Cms { - internal class KeyAgreeRecipientInfoGenerator : RecipientInfoGenerator + internal class KeyAgreeRecipientInfoGenerator + : RecipientInfoGenerator { private static readonly CmsEnvelopedHelper Helper = CmsEnvelopedHelper.Instance; - private DerObjectIdentifier keyAgreementOID; - private DerObjectIdentifier keyEncryptionOID; - private IList<X509Certificate> recipientCerts; - private AsymmetricCipherKeyPair senderKeyPair; + private readonly List<KeyAgreeRecipientIdentifier> m_recipientIDs = new List<KeyAgreeRecipientIdentifier>(); + private readonly List<AsymmetricKeyParameter> m_recipientKeys = new List<AsymmetricKeyParameter>(); - internal KeyAgreeRecipientInfoGenerator() - { - } + private DerObjectIdentifier m_keyAgreementOid; + private DerObjectIdentifier m_keyEncryptionOid; + private AsymmetricCipherKeyPair m_senderKeyPair; - internal DerObjectIdentifier KeyAgreementOID + internal KeyAgreeRecipientInfoGenerator(IEnumerable<X509Certificate> recipientCerts) { - set { this.keyAgreementOID = value; } - } - - internal DerObjectIdentifier KeyEncryptionOID + foreach (var recipientCert in recipientCerts) + { + m_recipientIDs.Add(new KeyAgreeRecipientIdentifier(CmsUtilities.GetIssuerAndSerialNumber(recipientCert))); + m_recipientKeys.Add(recipientCert.GetPublicKey()); + } + } + + internal KeyAgreeRecipientInfoGenerator(byte[] subjectKeyID, AsymmetricKeyParameter publicKey) + { + m_recipientIDs.Add(new KeyAgreeRecipientIdentifier(new RecipientKeyIdentifier(subjectKeyID))); + m_recipientKeys.Add(publicKey); + } + + internal DerObjectIdentifier KeyAgreementOid { - set { this.keyEncryptionOID = value; } + set { m_keyAgreementOid = value; } } - internal IEnumerable<X509Certificate> RecipientCerts + internal DerObjectIdentifier KeyEncryptionOid { - set { this.recipientCerts = new List<X509Certificate>(value); } + set { m_keyEncryptionOid = value; } } internal AsymmetricCipherKeyPair SenderKeyPair { - set { this.senderKeyPair = value; } + set { m_senderKeyPair = value; } } public RecipientInfo Generate(KeyParameter contentEncryptionKey, SecureRandom random) { byte[] keyBytes = contentEncryptionKey.GetKey(); - AsymmetricKeyParameter senderPublicKey = senderKeyPair.Public; - ICipherParameters senderPrivateParams = senderKeyPair.Private; - + AsymmetricKeyParameter senderPublicKey = m_senderKeyPair.Public; + ICipherParameters senderPrivateParams = m_senderKeyPair.Private; OriginatorIdentifierOrKey originator; try @@ -67,14 +74,13 @@ namespace Org.BouncyCastle.Cms throw new InvalidKeyException("cannot extract originator public key: " + e); } - Asn1OctetString ukm = null; - if (keyAgreementOID.Id.Equals(CmsEnvelopedGenerator.ECMqvSha1Kdf)) + if (m_keyAgreementOid.Id.Equals(CmsEnvelopedGenerator.ECMqvSha1Kdf)) { try { IAsymmetricCipherKeyPairGenerator ephemKPG = - GeneratorUtilities.GetKeyPairGenerator(keyAgreementOID); + GeneratorUtilities.GetKeyPairGenerator(m_keyAgreementOid); ephemKPG.Init( ((ECPublicKeyParameters)senderPublicKey).CreateKeyGenerationParameters(random)); @@ -99,22 +105,16 @@ namespace Org.BouncyCastle.Cms } } - - DerSequence paramSeq = new DerSequence( - keyEncryptionOID, - DerNull.Instance); - AlgorithmIdentifier keyEncAlg = new AlgorithmIdentifier(keyAgreementOID, paramSeq); - + DerSequence paramSeq = new DerSequence(m_keyEncryptionOid, DerNull.Instance); + AlgorithmIdentifier keyEncAlg = new AlgorithmIdentifier(m_keyAgreementOid, paramSeq); Asn1EncodableVector recipientEncryptedKeys = new Asn1EncodableVector(); - foreach (X509Certificate recipientCert in recipientCerts) + for (int i = 0; i < m_recipientIDs.Count; ++i) { - // TODO Should there be a SubjectKeyIdentifier-based alternative? - KeyAgreeRecipientIdentifier karid = new KeyAgreeRecipientIdentifier( - CmsUtilities.GetIssuerAndSerialNumber(recipientCert)); + var recipientID = m_recipientIDs[i]; + ICipherParameters recipientPublicParams = m_recipientKeys[i]; - ICipherParameters recipientPublicParams = recipientCert.GetPublicKey(); - if (keyAgreementOID.Id.Equals(CmsEnvelopedGenerator.ECMqvSha1Kdf)) + if (m_keyAgreementOid.Id.Equals(CmsEnvelopedGenerator.ECMqvSha1Kdf)) { recipientPublicParams = new MqvPublicParameters( (ECPublicKeyParameters)recipientPublicParams, @@ -123,31 +123,30 @@ namespace Org.BouncyCastle.Cms // Use key agreement to choose a wrap key for this recipient IBasicAgreement keyAgreement = AgreementUtilities.GetBasicAgreementWithKdf( - keyAgreementOID, keyEncryptionOID.Id); + m_keyAgreementOid, m_keyEncryptionOid.Id); keyAgreement.Init(new ParametersWithRandom(senderPrivateParams, random)); BigInteger agreedValue = keyAgreement.CalculateAgreement(recipientPublicParams); - int keyEncryptionKeySize = GeneratorUtilities.GetDefaultKeySize(keyEncryptionOID) / 8; + int keyEncryptionKeySize = GeneratorUtilities.GetDefaultKeySize(m_keyEncryptionOid) / 8; byte[] keyEncryptionKeyBytes = X9IntegerConverter.IntegerToBytes(agreedValue, keyEncryptionKeySize); KeyParameter keyEncryptionKey = ParameterUtilities.CreateKeyParameter( - keyEncryptionOID, keyEncryptionKeyBytes); + m_keyEncryptionOid, keyEncryptionKeyBytes); // Wrap the content encryption key with the agreement key - IWrapper keyWrapper = WrapperUtilities.GetWrapper(keyEncryptionOID.Id); + IWrapper keyWrapper = WrapperUtilities.GetWrapper(m_keyEncryptionOid.Id); keyWrapper.Init(true, new ParametersWithRandom(keyEncryptionKey, random)); byte[] encryptedKeyBytes = keyWrapper.Wrap(keyBytes, 0, keyBytes.Length); Asn1OctetString encryptedKey = new DerOctetString(encryptedKeyBytes); - recipientEncryptedKeys.Add(new RecipientEncryptedKey(karid, encryptedKey)); + recipientEncryptedKeys.Add(new RecipientEncryptedKey(recipientID, encryptedKey)); } return new RecipientInfo(new KeyAgreeRecipientInfo(originator, ukm, keyEncAlg, new DerSequence(recipientEncryptedKeys))); } - private static OriginatorPublicKey CreateOriginatorPublicKey( - AsymmetricKeyParameter publicKey) + private static OriginatorPublicKey CreateOriginatorPublicKey(AsymmetricKeyParameter publicKey) { SubjectPublicKeyInfo spki = SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(publicKey); return new OriginatorPublicKey( |