使用 BouncyCastle 创建 CMS 消息时出现 FipsUnapprovedOperationError
FipsUnapprovedOperationError while creating CMS message with BouncyCastle
我正在尝试使用 BouncyCastle FIPS 1.0.0 为 Java 创建 CMS Enveloped 加密消息。我收到以下错误,表明它正在尝试使用 AES 生成随机数(这不是 FIPS 模式的认可算法)。
Exception in thread "main" org.bouncycastle.crypto.fips.FipsUnapprovedOperationError: Attempt to create key with unapproved RNG: AES
at org.bouncycastle.crypto.fips.Utils.validateRandom(Unknown Source)
at org.bouncycastle.crypto.fips.Utils.validateKeyGenRandom(Unknown Source)
at org.bouncycastle.crypto.fips.FipsAES$KeyGenerator.<init>(Unknown Source)
at org.bouncycastle.crypto.fips.FipsAES$KeyGenerator.<init>(Unknown Source)
at org.bouncycastle.jcajce.provider.ProvAES.createInstance(Unknown Source)
at org.bouncycastle.jcajce.provider.BaseKeyGenerator.engineInit(Unknown Source)
at javax.crypto.KeyGenerator.init(KeyGenerator.java:510)
at org.bouncycastle.cms.jcajce.JceCMSContentEncryptorBuilder$CMSOutputEncryptor.<init>(Unknown Source)
at org.bouncycastle.cms.jcajce.JceCMSContentEncryptorBuilder.build(Unknown Source)
首先,我确保将 BouncyCastle 加载为 JCE 提供程序,然后我确保它 运行 在仅 FIPS 批准模式下运行。
if(!CryptoServicesRegistrar.isInApprovedOnlyMode()) {
CryptoServicesRegistrar.setApprovedOnlyMode(true);
}
在那之后,我基本上只是使用 BC FIPS in 100 mini-book 中的示例代码。到目前为止我的代码如下:
private static final String FIPS_PROVIDER = "BCFIPS";
public byte[] encrypt(X509Certificate cert, byte[] dataToEncrypt) throws CertificateEncodingException, CMSException, IOException, InvalidAlgorithmParameterException {
CMSEnvelopedDataGenerator envelopedGen = new CMSEnvelopedDataGenerator();
JcaAlgorithmParametersConverter paramsConverter = new JcaAlgorithmParametersConverter();
AlgorithmIdentifier algId = paramsConverter.getAlgorithmIdentifier(PKCSObjectIdentifiers.id_RSAES_OAEP, OAEPParameterSpec.DEFAULT);
JceKeyTransRecipientInfoGenerator recipientInfo = new JceKeyTransRecipientInfoGenerator(cert, algId);
recipientInfo.setProvider(FIPS_PROVIDER);
envelopedGen.addRecipientInfoGenerator(recipientInfo);
CMSProcessableByteArray processableArray = new CMSProcessableByteArray(dataToEncrypt);
JceCMSContentEncryptorBuilder encryptorBuilder = new JceCMSContentEncryptorBuilder(CMSAlgorithm.AES256_CBC);
encryptorBuilder.setProvider(FIPS_PROVIDER);
OutputEncryptor outputEncryptor = encryptorBuilder.build();
return envelopedGen.generate(processableArray, outputEncryptor).getEncoded();
}
如果我不将 BouncyCastle 置于 FIPS 仅批准模式,则此代码可以正常工作,但我需要能够 运行 在此模式下。有什么方法可以告诉 CMSOutputEncryptor 使用不同的 RNG 算法吗?
您是否尝试过设置 FIPS 认可的 SecureRandom?
CryptoServicesRegistrar.setSecureRandom(
new FipsDRBG.Builder(
new BasicEntropySourceProvider(new SecureRandom(), true))
.build(FipsDRBG.SHA512_HMAC, null, false)
);
然后在您的构建器上(以及您可能需要的任何其他地方):
encryptorBuilder.setSecureRandom(CryptoServicesRegistrar.getSecureRandom());
我正在尝试使用 BouncyCastle FIPS 1.0.0 为 Java 创建 CMS Enveloped 加密消息。我收到以下错误,表明它正在尝试使用 AES 生成随机数(这不是 FIPS 模式的认可算法)。
Exception in thread "main" org.bouncycastle.crypto.fips.FipsUnapprovedOperationError: Attempt to create key with unapproved RNG: AES
at org.bouncycastle.crypto.fips.Utils.validateRandom(Unknown Source)
at org.bouncycastle.crypto.fips.Utils.validateKeyGenRandom(Unknown Source)
at org.bouncycastle.crypto.fips.FipsAES$KeyGenerator.<init>(Unknown Source)
at org.bouncycastle.crypto.fips.FipsAES$KeyGenerator.<init>(Unknown Source)
at org.bouncycastle.jcajce.provider.ProvAES.createInstance(Unknown Source)
at org.bouncycastle.jcajce.provider.BaseKeyGenerator.engineInit(Unknown Source)
at javax.crypto.KeyGenerator.init(KeyGenerator.java:510)
at org.bouncycastle.cms.jcajce.JceCMSContentEncryptorBuilder$CMSOutputEncryptor.<init>(Unknown Source)
at org.bouncycastle.cms.jcajce.JceCMSContentEncryptorBuilder.build(Unknown Source)
首先,我确保将 BouncyCastle 加载为 JCE 提供程序,然后我确保它 运行 在仅 FIPS 批准模式下运行。
if(!CryptoServicesRegistrar.isInApprovedOnlyMode()) {
CryptoServicesRegistrar.setApprovedOnlyMode(true);
}
在那之后,我基本上只是使用 BC FIPS in 100 mini-book 中的示例代码。到目前为止我的代码如下:
private static final String FIPS_PROVIDER = "BCFIPS";
public byte[] encrypt(X509Certificate cert, byte[] dataToEncrypt) throws CertificateEncodingException, CMSException, IOException, InvalidAlgorithmParameterException {
CMSEnvelopedDataGenerator envelopedGen = new CMSEnvelopedDataGenerator();
JcaAlgorithmParametersConverter paramsConverter = new JcaAlgorithmParametersConverter();
AlgorithmIdentifier algId = paramsConverter.getAlgorithmIdentifier(PKCSObjectIdentifiers.id_RSAES_OAEP, OAEPParameterSpec.DEFAULT);
JceKeyTransRecipientInfoGenerator recipientInfo = new JceKeyTransRecipientInfoGenerator(cert, algId);
recipientInfo.setProvider(FIPS_PROVIDER);
envelopedGen.addRecipientInfoGenerator(recipientInfo);
CMSProcessableByteArray processableArray = new CMSProcessableByteArray(dataToEncrypt);
JceCMSContentEncryptorBuilder encryptorBuilder = new JceCMSContentEncryptorBuilder(CMSAlgorithm.AES256_CBC);
encryptorBuilder.setProvider(FIPS_PROVIDER);
OutputEncryptor outputEncryptor = encryptorBuilder.build();
return envelopedGen.generate(processableArray, outputEncryptor).getEncoded();
}
如果我不将 BouncyCastle 置于 FIPS 仅批准模式,则此代码可以正常工作,但我需要能够 运行 在此模式下。有什么方法可以告诉 CMSOutputEncryptor 使用不同的 RNG 算法吗?
您是否尝试过设置 FIPS 认可的 SecureRandom?
CryptoServicesRegistrar.setSecureRandom(
new FipsDRBG.Builder(
new BasicEntropySourceProvider(new SecureRandom(), true))
.build(FipsDRBG.SHA512_HMAC, null, false)
);
然后在您的构建器上(以及您可能需要的任何其他地方):
encryptorBuilder.setSecureRandom(CryptoServicesRegistrar.getSecureRandom());