public ICipherBuilder <AlgorithmIdentifier> Build(char[] password) { if (algorithm.Equals(PkcsObjectIdentifiers.IdPbeS2)) { IPasswordBasedDeriverBuilder <FipsPbkd.Parameters> pbeDeriverBuilder = CryptoServicesRegistrar.CreateService(FipsPbkd.PbkdF2).From(converter, password); IPasswordBasedDeriver <FipsPbkd.Parameters> pbeDeriver = pbeDeriverBuilder .WithPrf(digestAlgorithm) .WithSalt(salt) .WithIterationCount(iterationCount) .Build(); byte[] keyEnc = pbeDeriver.DeriveKey(TargetKeyType.CIPHER, (int)Utils.keySizesInBytes[keyEncAlgorithm]); EncryptionScheme encScheme = Utils.GetEncryptionSchemeIdentifier(keyEncAlgorithm, random); PbeS2Parameters algParams = new PbeS2Parameters( new KeyDerivationFunc(PkcsObjectIdentifiers.IdPbkdf2, new Pbkdf2Params(salt, iterationCount, new AlgorithmIdentifier((DerObjectIdentifier)Utils.digestTable[digestAlgorithm], DerNull.Instance))), encScheme); IParameters <Algorithm> cipherParams = Utils.GetCipherParameters(encScheme); if (Utils.IsBlockMode(cipherParams.Algorithm)) { return(new PbeBlockCipherBuilder(new AlgorithmIdentifier(PkcsObjectIdentifiers.IdPbeS2, algParams), Utils.CreateBlockEncryptorBuilder(keyEncAlgorithm, keyEnc, cipherParams))); } else if (Utils.IsAeadMode(cipherParams.Algorithm)) { return(new PkixAeadCipherBuilder(new AlgorithmIdentifier(PkcsObjectIdentifiers.IdPbeS2, algParams), Utils.CreateAeadEncryptorBuilder(keyEncAlgorithm, keyEnc, cipherParams))); } else { return(new PkixCipherBuilder(new AlgorithmIdentifier(PkcsObjectIdentifiers.IdPbeS2, algParams), Utils.CreateEncryptorBuilder(keyEncAlgorithm, keyEnc, cipherParams))); } } else if (algorithm.Equals(PkcsObjectIdentifiers.PbeWithShaAnd2KeyTripleDesCbc) || algorithm.Equals(PkcsObjectIdentifiers.PbeWithShaAnd3KeyTripleDesCbc)) { int keySize = algorithm.Equals(PkcsObjectIdentifiers.PbeWithShaAnd2KeyTripleDesCbc) ? 16 : 24; Pkcs12PbeParams pbeParams = new Pkcs12PbeParams(salt, iterationCount); // we ignore converter as it's specified by the algorithm IPasswordBasedDeriverBuilder <Pbkd.PbkdParameters> pbeDeriverBuilder = CryptoServicesRegistrar.CreateService(Pbkd.Pkcs12).From(PasswordConverter.PKCS12, password); IPasswordBasedDeriver <Pbkd.PbkdParameters> pbeDeriver = pbeDeriverBuilder .WithPrf(FipsShs.Sha1) .WithSalt(pbeParams.GetIV()) .WithIterationCount(pbeParams.Iterations.IntValue) .Build(); byte[][] keyIV = pbeDeriver.DeriveKeyAndIV(TargetKeyType.CIPHER, keySize, 8); AlgorithmIdentifier algDetails = new AlgorithmIdentifier(algorithm, pbeParams); return(new PbeBlockCipherBuilder(algDetails, Utils.CreateBlockEncryptorBuilder(algDetails, keyIV[0], keyIV[1]))); } throw new InvalidOperationException("cannot match algorithm: " + algorithm); }
public ICipherBuilder <AlgorithmIdentifier> CreateDecryptorBuilder(AlgorithmIdentifier algorithmDetails) { if (algorithmDetails.Algorithm.Equals(PkcsObjectIdentifiers.IdPbeS2)) { IPasswordBasedDeriverBuilder <FipsPbkd.Parameters> pbeDeriverBuilder = CryptoServicesRegistrar.CreateService(FipsPbkd.PbkdF2).From(converter.Convert(password)); PbeS2Parameters pbeParams = PbeS2Parameters.GetInstance(algorithmDetails.Parameters); Pbkdf2Params pbkdfParams = Pbkdf2Params.GetInstance(pbeParams.KeyDerivationFunc.Parameters); AlgorithmIdentifier encScheme = pbeParams.EncryptionScheme; IPasswordBasedDeriver <FipsPbkd.Parameters> pbeDeriver = pbeDeriverBuilder .WithPrf((DigestAlgorithm)Utils.digestTable[pbkdfParams.Prf.Algorithm]) .WithSalt(pbkdfParams.GetSalt()) .WithIterationCount(pbkdfParams.IterationCount.IntValue) .Build(); byte[] keyEnc = pbeDeriver.DeriveKey(TargetKeyType.CIPHER, (pbkdfParams.KeyLength != null ? pbkdfParams.KeyLength.IntValue : (int)Utils.keySizesInBytes[encScheme.Algorithm])); IParameters <Algorithm> cipherParams = Utils.GetCipherParameters(encScheme); if (Utils.IsBlockMode(cipherParams.Algorithm)) { return(new PbeBlockCipherBuilder(algorithmDetails, Utils.CreateBlockDecryptorBuilder(encScheme, keyEnc, cipherParams))); } else if (Utils.IsAeadMode(cipherParams.Algorithm)) { return(new PkixAeadCipherBuilder(algorithmDetails, Utils.CreateAeadDecryptorBuilder(encScheme, keyEnc, cipherParams))); } else { return(new PkixCipherBuilder(algorithmDetails, Utils.CreateDecryptorBuilder(encScheme, keyEnc, cipherParams))); } } else if (algorithmDetails.Algorithm.Equals(PkcsObjectIdentifiers.PbeWithShaAnd2KeyTripleDesCbc) || algorithmDetails.Algorithm.Equals(PkcsObjectIdentifiers.PbeWithShaAnd3KeyTripleDesCbc)) { int keySize = algorithmDetails.Algorithm.Equals(PkcsObjectIdentifiers.PbeWithShaAnd2KeyTripleDesCbc) ? 16 : 24; Pkcs12PbeParams pbeParams = Pkcs12PbeParams.GetInstance(algorithmDetails.Parameters); // we ignore converter as it's specified by the algorithm IPasswordBasedDeriverBuilder <Pbkd.PbkdParameters> pbeDeriverBuilder = CryptoServicesRegistrar.CreateService(Pbkd.Pkcs12).From(PasswordConverter.PKCS12, password); IPasswordBasedDeriver <Pbkd.PbkdParameters> pbeDeriver = pbeDeriverBuilder .WithPrf(FipsShs.Sha1) .WithSalt(pbeParams.GetIV()) .WithIterationCount(pbeParams.Iterations.IntValue) .Build(); byte[][] keyIV = pbeDeriver.DeriveKeyAndIV(TargetKeyType.CIPHER, keySize, 8); return(new PbeBlockCipherBuilder(algorithmDetails, Utils.CreateDecryptorBuilder(algorithmDetails, keyIV[0], keyIV[1]))); } throw new InvalidOperationException("cannot match algorithm: " + algorithmDetails.Algorithm); }