我正在与Bouncy Castle Library合作,并且找不到签署原始邮件的方法,而无需首先对其进行散列/填充。我不确定要传递的参数为alg
。
使用PKCS v1.5填充签署摘要时,我使用的是:" SHA1WithRSA" ," SHA256WithRSA"等(根据摘要类型)。
signature = Signature.getInstance(alg, JCEProvider.CRYPTO_PROVIDER_NAME);
答案 0 :(得分:0)
原始签名只不过是模幂运算。现在似乎有两种选择,但基本上只剩下一种。我将在下面解释。
首先,您认为使用带Signature
的{{1}}应该有效。算法确实存在,但遗憾的是它仍然存在;它只是去除ASN.1结构,指示哈希函数和值。所以没有一个。
虽然signing is not the same as encryption,但最终两个操作都依赖于模幂运算。因此,幸运的是可以使用"NoneWithRSA"
实例来创建所需的功能:
Cipher
现在要注意的一点是,Bouncy Castle的操作与Oracle的SunJCE提供商的操作有所不同。它不仅仅是删除填充,而且忘记将密文放入I2OSP算法(参见PKCS#1标准),该算法正确编码为模数的输出大小。因此,对于特定的键/明文组合,您可以使用小于128字节的密文。通过加密值0很容易看到,其中输出将是零字节。
最后请注意,指定Security.addProvider(new BouncyCastleProvider());
Cipher rsa = Cipher.getInstance("RSA/ECB/NoPadding", BouncyCastleProvider.PROVIDER_NAME);
rsa.init(Cipher.DECRYPT_MODE, kp.getPrivate());
byte[] signatureUsingCipher = rsa.doFinal("owlstead"
.getBytes(StandardCharsets.UTF_8));
System.out.println(Hex.toHexString(signatureUsingCipher));
模式或Cipher.ENCRYPT
模式并不会产生影响;两者都简单地执行模幂运算。但是,Cipher.DECRYPT更可能期望私钥,这就是我在上面的代码中使用它的原因。
您可以生成一个密钥对来测试上面的代码,如下所示:
Cipher.DECRYPT
警告:没有安全填充的签名生成是不安全的; it may result in existential forgery attacks。您只能将其用作构建块以创建安全方案。
答案 1 :(得分:0)