2016-08-15 49 views
1

我正在使用微软的RSACryptoServiceProvider类来加密/解密数据。 但是,解密函数会抛出一个异常“错误的数据”。 每次使用加密/解密时,是否需要创建提供程序类的新实例?c#Rsa解密引发“坏数据”异常

RSA提供者类

static public byte[] RSAEncrypt(byte[] byteEncrypt, RSAParameters RSAInfo, bool isOAEP) 
    { 
     try 
     { 
      using (RSACryptoServiceProvider RSA = new RSACryptoServiceProvider()) 
      { 
       RSA.ImportParameters(RSAInfo); 

       //Encrypt the passed byte array and specify OAEP padding. 
       return RSA.Encrypt(byteEncrypt, isOAEP); 
      } 
     } 
     catch (CryptographicException e) 
     { 
      Console.WriteLine(e.Message); 
      return null; 
     } 
    } 

    static public byte[] RSADecrypt(byte[] byteDecrypt, RSAParameters RSAInfo, bool isOAEP) 
    { 
     try 
     { 
      using (RSACryptoServiceProvider RSA = new RSACryptoServiceProvider(4096)) 
      { 
       //Import the RSA Key information. This needs 
       //to include the private key information. 
       RSA.ImportParameters(RSAInfo); 

       //Decrypt the passed byte array and specify OAEP padding. 
       return RSA.Decrypt(byteDecrypt, isOAEP); 
      } 
     } 
     catch (CryptographicException e) 
     { 
      Console.WriteLine(e.ToString()); 
      return null; 
     } 
    } 
} 

使用

UnicodeEncoding ByteConverter = new UnicodeEncoding(); 
    RSACryptoServiceProvider RSA = new RSACryptoServiceProvider(4096); 
    byte[] plainPassword; 
    byte[] encryptedPassword; 

    plainPassword = ByteConverter.GetBytes(connectionStringPasswordTextBox.Text); 
    encryptedPassword = CryptoHelper.RSAEncrypt(plainPassword, RSA.ExportParameters(false), false); 
    RSACryptoServiceProvider RSA = new RSACryptoServiceProvider(4096); 
    byte[] decryptedPassword = CryptoHelper.RSADecrypt(Convert.FromBase64String(connectionString.password), RSA.ExportParameters(true), false); 

编辑

例外已更改为 “参数不正确” 给多了一些尝试后。我认为这与创建一个rsa类instaead的实例有关,每次创建新实例时都会使用它。

+0

你检查出这个:http://stackoverflow.com/questions/9659898/bad -data-cryptographicexception? –

+1

是的,我甚至不顾一切地查看谷歌的第二页。 – Miral

+0

有趣的是,当创建第二个RSACryptoServiceProvider时,由创建一个新的密钥集导致该问题。然而,MSDN提供了一个“默认键”(https://msdn.microsoft.com/en-us/library/zseyf239(v=vs.110).aspx),但没有关于实际含义的文档。 –

回答

1

RSACryptoServiceProvider(int)构造函数生成一个新密钥(除非CAPI为空名称返回一个键;我不确定这是否可能)。所以这个代码是用一个密钥加密并试图用另一个密钥解密的。由此产生的答案很难理解,抛出异常。

  • 生成您的密钥一次,并从中保存RSAParameters。
  • 为了让您的代码更具可移植性,请避免说“RSACryptoServiceProvider”;只要可能就谈论RSA。
    • 不幸的是,密钥创建是一个不可能的时间,因为当KeySize更改时,RSACryptoServiceProvider不会生成新的密钥。

所以,你应该用更多的东西像这样在.NET 4.6或更高版本:

public static byte[] RSAEncrypt(
    byte[] byteEncrypt, 
    RSAParameters rsaInfo, 
    RSAEncryptionPadding padding) 
{ 
    try 
    { 
     using (RSA rsa = RSA.Create()) 
     { 
      rsa.ImportParameters(rsaInfo); 
      return rsa.Encrypt(byteEncrypt, padding); 
     } 
    } 
    catch (CryptographicException e) 
    { 
     Console.WriteLine(e.Message); 
     return null; 
    } 
} 
+0

它说加密或解密方法的“方法不支持”。 – Miral

+0

您是否正在调用Encrypt(byte [],RSAEncryptionPadding)或EncryptValue(byte [])?后者会抛出NotSupportedException。如果您没有看到需要使用RSAEncryptionPadding的版本,则可能是针对.NET 4.5.2或更低版本(它是4.6中的新版本)。请参阅https://msdn.microsoft.com/en-us/library/system.security.cryptography.rsa.encrypt(v=vs.110).aspx和https://msdn.microsoft.com/en-us/ library/system.security.cryptography.rsa.encryptvalue(v = vs.110).aspx – bartonjs

+0

它不允许我调用Encrypt方法,当我调用EncryptValue方法时,它会抛出NotSupportedException – Miral