我不是一个加密Maven,但我正在尝试创建一个 CMSEnvelopedDataGenerator
使用bouncycastle 1.67,其中会话密钥使用rsaes oaep加密(1.2.840.113549.1.1.7)
目前,我的代码如下所示:
CMSEnvelopedDataGenerator envelopedGenerator = new CMSEnvelopedDataGenerator();
JcaAlgorithmParametersConverter paramsConverter = new JcaAlgorithmParametersConverter();
OAEPParameterSpec oaepSpec = new OAEPParameterSpec("SHA-256", "MGF1", MGF1ParameterSpec.SHA256, PSource.PSpecified.DEFAULT);
AlgorithmIdentifier algorithmIdentifier;
algorithmIdentifier = paramsConverter.getAlgorithmIdentifier(PKCSObjectIdentifiers.id_RSAES_OAEP, oaepSpec);
JceKeyTransRecipientInfoGenerator recipent = new JceKeyTransRecipientInfoGenerator(receiverCert, algorithmIdentifier).setProvider("BC");
# encrypt
CMSEnvelopedData envelopedData;
envelopedData = envelopedGenerator.generate(
new CMSProcessableByteArray(encodedSignedData),
new JceCMSContentEncryptorBuilder(CMSAlgorithm.AES256_CBC).setProvider("BC").build()
)
但当我通过 openssl asn1parse
,我明白了
115:d=6 hl=2 l= 9 prim: OBJECT :rsaesOaep
126:d=6 hl=2 l= 47 cons: SEQUENCE
128:d=7 hl=2 l= 15 cons: cont [ 0 ]
130:d=8 hl=2 l= 13 cons: SEQUENCE
132:d=9 hl=2 l= 9 prim: OBJECT :sha256
143:d=9 hl=2 l= 0 prim: NULL
145:d=7 hl=2 l= 28 cons: cont [ 1 ]
147:d=8 hl=2 l= 26 cons: SEQUENCE
149:d=9 hl=2 l= 9 prim: OBJECT :mgf1
160:d=9 hl=2 l= 13 cons: SEQUENCE
162:d=10 hl=2 l= 9 prim: OBJECT :sha256
然后是十六进制转储。在我的参考文件中是这样的:
115:d=6 hl=2 l= 9 prim: OBJECT :rsaesOaep
126:d=6 hl=2 l= 43 cons: SEQUENCE
128:d=7 hl=2 l= 13 cons: cont [ 0 ]
130:d=8 hl=2 l= 11 cons: SEQUENCE
132:d=9 hl=2 l= 9 prim: OBJECT :sha256
143:d=7 hl=2 l= 26 cons: cont [ 1 ]
145:d=8 hl=2 l= 24 cons: SEQUENCE
147:d=9 hl=2 l= 9 prim: OBJECT :mgf1
158:d=9 hl=2 l= 11 cons: SEQUENCE
160:d=10 hl=2 l= 9 prim: OBJECT :sha256
在我档案的第143行
143:d=9 hl=2 l= 0 prim: NULL
我不知道那是从哪里来的。
当我使用对引用文件有效的解密代码时,会出现以下异常
exception unwrapping key: bad padding: unable to decrypt block
Caused by: org.bouncycastle.cms.CMSException: exception unwrapping key: bad padding: unable to decrypt block
at org.bouncycastle.cms.jcajce.JceKeyTransRecipient.extractSecretKey(Unknown Source)
at org.bouncycastle.cms.jcajce.JceKeyTransEnvelopedRecipient.getRecipientOperator(Unknown Source)
at org.bouncycastle.cms.KeyTransRecipientInformation.getRecipientOperator(Unknown Source)
at org.bouncycastle.cms.RecipientInformation.getContentStream(Unknown Source)
Caused by: org.bouncycastle.operator.OperatorException: bad padding: unable to decrypt block
at org.bouncycastle.operator.jcajce.JceAsymmetricKeyUnwrapper.generateUnwrappedKey(Unknown Source)
Caused by: org.bouncycastle.jcajce.provider.util.BadBlockException: unable to decrypt block
at org.bouncycastle.jcajce.provider.asymmetric.rsa.CipherSpi.getOutput(Unknown Source)
at org.bouncycastle.jcajce.provider.asymmetric.rsa.CipherSpi.engineDoFinal(Unknown Source)
at javax.crypto.Cipher.doFinal(Cipher.java:2168)
Caused by: org.bouncycastle.crypto.InvalidCipherTextException: data wrong
at org.bouncycastle.crypto.encodings.OAEPEncoding.decodeBlock(Unknown Source)
at org.bouncycastle.crypto.encodings.OAEPEncoding.processBlock(Unknown Source)
我希望它不多,那是失踪。
编辑:
我的错误生成的文件 recipient.getKeyEncryptionAlgorithm().getParameters()
结果
[[0][2.16.840.1.101.3.4.2.1, NULL], [1][1.2.840.113549.1.1.8, [2.16.840.1.101.3.4.2.1, NULL]]]
中的正确文件
[[0][2.16.840.1.101.3.4.2.1], [1][1.2.840.113549.1.1.8, [2.16.840.1.101.3.4.2.1]]]
这些错在哪里 NULL
对于即将到来的sha-256值。
1条答案
按热度按时间ccrfmcuu1#
在bc创建的消息中,您只提到了一个'extra'null,但实际上有两个,第二个在您发布的数据中排除的第一行。文章中的(不同)长度字段,以及
getParameters()
,清楚地表明这一点。那些空值没有错。
这些空值是oaep参数结构中散列算法的参数,是标准所要求的。rfc 3447=pkcs1v2.1是第一个在a.2.1中包含sha-2的版本(2003年,紧随2002年fips 186-2之后):
请注意,这两个哈希规范(标签的外部哈希和mgf1参数中的内部哈希)都是由infoset定义的
HashAlgorithm
并且该集合中所有定义的值(包括sha-256)的参数都显式为null,而不是在通用x.509asn.1允许的情况下忽略(比较rfc5280 4.1.1.2,它使用旧的pre-infoset表示法)。注:a.2.3中的pss也是如此,a.2.4中的rsassa-pkcs1-v15中的digestinfo有一组稍大的哈希算法。这和v2.0中的同等规定(不包括2.0中没有的pss,并且符号略有不同)可能是对pkcs1v1.5在10.1.2中仅使signature digestinfo参数成为“应该”的React(即使在2119之后也是小写,可能是因为这是rsalabs文本而不是ietf),这导致了实现上的变化,导致了有时实际上是正确的签名无法验证,这被认为是一件需要修复的坏事。
因此,您的“参考”文件在技术上违反了标准。然而,由于这些散列算法实际上不使用参数——这就是为什么它们用null编码的原因——bouncycastle可以很容易地容忍并接受省略的大小写。我用一个其他有效的结构进行了测试,它确实是双向的(如果它能处理一些不合适的值(比如插入的八位字节字符串),我也不会感到惊讶,但我没有测试它。)
即使参数编码错误,也不会导致出现异常——它可能是一个显式解码/解析错误(如“缺少必需字段”),或者是一个示例化错误(如“算法x的参数无效”)。在没有bug的情况下,“错误填充”是由损坏、篡改或其他错误的数据(在cms环境中这是非常不可能的)或不匹配的密钥引起的。
检查是否使用匹配的密钥。