"System.Security.Cryptography.CryptographicException:Bad Key." 对于RSACryptoServiceProvider.Decrypt()

Ari*_*iel 9 .net cryptography

我正在玩RSA加密/解密和证书.具体来说,我尝试使用证书的公钥进行加密,然后,当尝试使用与该证书对应的私钥进行解密时,会收到错误:

System.Security.Cryptography.CryptographicException: Bad Key.

   at System.Security.Cryptography.CryptographicException.ThrowCryptographicException(Int32 hr)
   at System.Security.Cryptography.RSACryptoServiceProvider.DecryptKey(SafeKeyHandle pKeyContext, Byte[] pbEncryptedKey, Int3
2 cbEncryptedKey, Boolean fOAEP, ObjectHandleOnStack ohRetDecryptedKey)
   at System.Security.Cryptography.RSACryptoServiceProvider.Decrypt(Byte[] rgb, Boolean fOAEP)
Run Code Online (Sandbox Code Playgroud)

代码是:

private void TestCertificates2()
{
    //////////////////////////////////////////////////////
    // SENDER CODE
    //////////////////////////////////////////////////////

    // get certificate
    var certSender = new X509Certificate2(@"C:\Test.cer");

    // encrypt with public key
    var providerSender = (RSACryptoServiceProvider)certSender.PublicKey.Key;
    var plainSender = Encoding.Default.GetBytes("this is plain text");
    var cipher = providerSender.Encrypt(plainSender, false);

    //////////////////////////////////////////////////////
    // RECEIVER CODE
    //////////////////////////////////////////////////////

    // get certificate
    var store = new X509Store("MY", StoreLocation.LocalMachine);
    store.Open(OpenFlags.ReadOnly | OpenFlags.OpenExistingOnly);
    var certReceiver = store.Certificates.Find(X509FindType.FindBySubjectName, "Test Subject", false)[0];

    // decrypt with private key
    var providerReceiver = (RSACryptoServiceProvider)certReceiver.PrivateKey;
    var plainReceiver = providerReceiver.Decrypt(cipher, false);

    // check they are same
    if (plainSender.Equals(plainReceiver))
    {
        Console.WriteLine("Same!");
    }
}
Run Code Online (Sandbox Code Playgroud)

作为参考,证书是通过创建和安装的

makecert.exe Test.cer -n "CN=Test Subject" -sr LocalMachine -ss My
Run Code Online (Sandbox Code Playgroud)

有人能发现我做错了吗?提前致谢!

Ari*_*iel 7

好的,发现问题是什么:需要告诉makecert 1)证书的主题密钥类型是"Exchange"2)将私钥标记为可导出

所以makecert看起来像

makecert.exe Test.cer -r -n "CN=Test Subject" -sr LocalMachine -ss My -sky Exchange -pe
Run Code Online (Sandbox Code Playgroud)