3

我想用我的 RSA 私钥加密一些数据,然后用公钥在客户端机器上解密。据我所知,这是使用 RSA 的一种正常方式。但是,据我所知,RSACryptoServiceProvider.NET Framework 中存在此问题。虽然当您向 提供公钥和私钥时解密工作正常,RSACryptoServiceProvider但当您只提供公钥时它就不行了。在这种情况下,我得到一个填充错误:

Error occurred while decoding OAEP padding.

at System.Security.Cryptography.RSACryptoServiceProvider.DecryptKey(SafeKeyHandle pKeyContext, Byte[] pbEncryptedKey, Int32 cbEncryptedKey, Boolean fOAEP, ObjectHandleOnStack ohRetDecryptedKey)
at System.Security.Cryptography.RSACryptoServiceProvider.Decrypt(Byte[] rgb, Boolean fOAEP)

备注:

  • 我加密/解密fOAEP设置为true.
  • 我使用 1024 密钥大小,并且我要加密的数据不超过 65 个字节。
  • 我从 XML 加载我的密钥。

我错过了什么吗?我没有看到任何可以更改的填充设置。

当然,我不能将我的私钥发送到客户端机器......

我应该尝试另一个像 Bouncy Castle 这样的图书馆吗?

我也发现了这个问题,但是没有明确的解决方案,根据作者的说法,他的最终解决方案是使用本文中的代码。但是,如果可能,我更愿意使用 .NET Framework 的代码,但我不明白为什么我的解密失败。

另外,我认为我的数据不会太长,以至于这个答案没有任何意义。

也许我可以使用 SignHash()/VerifyHash() 但我认为那些在加密之前从数据中计算哈希值,而我已经计算了哈希值,我只需要对其进行加密。使用 SignHash() 将限制我可以使用的散列算法的种类,因此最好避免使用它。

4

1 回答 1

1

签名生成包含 3 个不同的部分。首先计算哈希,然后添加填充,最后 RSA 执行模幂运算(可能通过使用中国剩余定理来加快速度)。

签名生成的所有这三个部分都是签名算法的一部分。将签名生成视为三个不同的部分是错误的。将 RSA 签名生成视为使用 RSA 加密是特别错误的。RSA 加密使用它自己的填充机制,与用于签名的填充机制不兼容

这在 PKCS#1 v2.2 标准中得到了很好的解释。

每个原语的主要数学运算是取幂,如第 5.1 节的加密和解密原语。RSASP1 和 RSAVP1 与 RSADP 和 RSAEP 相同,只是它们的输入和输出参数的名称不同;它们是有区别的,因为它们用于不同的目的。

因此,即使标准非常明确地使用不同的函数,即使它们执行基本相同的数学运算。

最终结果很简单:您必须使用RSACryptoServiceProviderPKCS#1 v1.5 兼容签名的类,或者使用 Bouncy Castle C# 库来使用更新的 RSA PSS 签名方案。如果您想为预先计算的哈希创建签名,请使用SignHash,尽管 - 正如您所提到的 - 此功能目前仅限于 SHA-1 或 MD5。

于 2013-08-06T00:47:59.540 回答