【问题标题】:How can I import an RSA private key into an RSACryptoServiceProvider?如何将 RSA 私钥导入 RSACryptoServiceProvider?
【发布时间】:2011-05-11 14:54:32
【问题描述】:

我正在尝试将使用 Win32 Crypto API 生成的 RSA 公钥/私钥对导入 .NET 应用程序。创建和导出密钥对的代码如下所示:

// Abbreviated for clarity.
CryptAcquireContext(..., MS_ENHANCED_PROV, ...);

// Generate public/private key pair

CryptCreateHash(..., CALG_SHA1, ...);
CryptHashData(hash, password, ...);
CryptDeriveKey(..., CALG_3DES, hash, CRYPT_EXPORTABLE, ...);
CyrptExportKey(..., derivedKey, PRIVATEKEYBLOB, ...);

基本上,此代码将公钥/私钥对导出为加密 blob。它使用 3DES 算法使用从 SHA-1 哈希派生的密钥进行加密。

现在,当我尝试将此密钥导入 .NET 时,我遇到了问题。我试图接近:

(1) 我创建了一个 RSACyrptoServiceProvider 对象并调用 ImportCspBlob()。这会引发异常,并显示“错误数据”消息。这并不奇怪,因为提供者对象无法知道 blob 是如何加密的。据我所知,根本无法告诉它使用什么算法和密钥。

(2) 我自己手动解密 blob,使用 PasswordDeriveBytes 类,然后将解密后的 blob 传递给 ImportCsbBlob()。再一次,我得到了一个例外。这次消息是“提供程序的错误版本”。我尝试在创建提供程序对象时手动提供提供程序名称(“Microsoft Enhanced Cryptographic Provider v1.0”),但没有任何区别。

让这项工作发挥作用至关重要。有什么想法吗?

解决方案

在 C++ 和 .NET 中生成未加密的公钥/私钥对后,我发现 Microsoft 增强加密提供程序实际上并未加密密钥对的前 8 个字节。 (这一定是引发 .NET 包装器循环的版本控制信息。)修改我的 .NET 解密代码以单独保留前 8 个字节后,一切正常。

此解决方案不是很好,因为它取决于加密提供程序的内部实现细节。不幸的是,我认为没有其他方法,因为 Microsoft 忽略了提供 ImportCspBlob 版本,让您可以指定用于解密的算法和密钥。

【问题讨论】:

    标签: .net interop cryptography


    【解决方案1】:

    在方法 2) 中,验证解密后的密钥是否与加密前相同。

    我认为“从 SHA-1 哈希派生的密钥”不会匹配来自 PasswordDeriveBytes 的密钥

    【讨论】:

    • 我确定密钥派生工作正常,但我会看看是否可以比较两个明文。
    猜你喜欢
    • 1970-01-01
    • 2013-07-31
    • 2019-10-02
    • 1970-01-01
    • 1970-01-01
    • 2014-07-07
    • 2013-07-17
    • 2012-12-22
    相关资源
    最近更新 更多