我正在尝试使用此代码进行加密和解密,但在.FlushFinalBlock()
期间进行解密时,我的数据长度会持续太长。
我不确定我在这里做错了什么,因为我不在这个问题上。
谁能告诉我这里我做错了什么?加密没问题,但无法解密加密。
static byte[] u8_Salt = new byte[] { 0x26, 0x19, 0x81, 0x4E, 0xA0, 0x6D, 0x95, 0x34, 0x26, 0x75, 0x64, 0x05, 0xF6 };
public static string Encrypt(string data, string password)
{
//
Rfc2898DeriveBytes pdb = new Rfc2898DeriveBytes(password, u8_Salt);
//
Rijndael i_Alg = Rijndael.Create();
i_Alg.Padding = PaddingMode.None;
i_Alg.Key = pdb.GetBytes(32);
i_Alg.IV = pdb.GetBytes(16);
//
using (var cryptoProvider = new DESCryptoServiceProvider())
using (var memoryStream = new MemoryStream())
using (var cryptoStream = new CryptoStream(memoryStream, cryptoProvider.CreateEncryptor(), CryptoStreamMode.Write))
using (var writer = new StreamWriter(cryptoStream))
{
writer.Write(data);
writer.Flush();
cryptoStream.FlushFinalBlock();
writer.Flush();
return Convert.ToBase64String(memoryStream.GetBuffer(), 0, (int)memoryStream.Length);
}
}
public static string Decrypt(string data, string password)
{
Rfc2898DeriveBytes pdb = new Rfc2898DeriveBytes(password, u8_Salt);
//
Rijndael i_Alg = Rijndael.Create();
i_Alg.Padding = PaddingMode.None;
i_Alg.Key = pdb.GetBytes(32);
i_Alg.IV = pdb.GetBytes(16);
//
using (var cryptoProvider = new DESCryptoServiceProvider())
using (var memoryStream = new MemoryStream())
using (var cryptoStream = new CryptoStream(memoryStream, cryptoProvider.CreateDecryptor(), CryptoStreamMode.Write))
using (var writer = new StreamWriter(cryptoStream))
{
writer.Write(data);
writer.Flush();
cryptoStream.FlushFinalBlock();
writer.Flush();
return Convert.ToBase64String(memoryStream.GetBuffer(), 0, (int)memoryStream.Length);
}
}
答案 0 :(得分:3)
您的代码存在一些问题。首先,您要创建 Rijndael(AES)对象。但是,您正在使用DESCryptoServiceProvider
,这意味着您实际上使用的是DES,而不是Rijndael。因此,您还有一个问题,即您没有为算法设置密钥。下面是使用RijndaelManaged
算法重写的两个函数,该算法是.NET上AES
算法的托管实现。我已经测试过,您可以毫无问题地进行加密和解密。另外:不要使用那个盐值,它都在互联网上。
static byte[] u8_Salt = new byte[] { 0x26, 0x19, 0x81, 0x4E, 0xA0, 0x6D, 0x95, 0x34, 0x26, 0x75, 0x64, 0x05, 0xF6 };
public static string EncryptString(string plainText, string password)
{
Rfc2898DeriveBytes pdb = new Rfc2898DeriveBytes(password, u8_Salt);
using (RijndaelManaged i_Alg = new RijndaelManaged { Key = pdb.GetBytes(32), IV = pdb.GetBytes(16) })
{
using (var memoryStream = new MemoryStream())
using (var cryptoStream = new CryptoStream(memoryStream, i_Alg.CreateEncryptor(), CryptoStreamMode.Write))
{
byte[] data = Encoding.UTF8.GetBytes(plainText);
cryptoStream.Write(data, 0, data.Length);
cryptoStream.FlushFinalBlock();
return Convert.ToBase64String(memoryStream.GetBuffer(), 0, (int)memoryStream.Length);
}
}
}
public static string Decrypt(string cipherText, string password)
{
Rfc2898DeriveBytes pdb = new Rfc2898DeriveBytes(password, u8_Salt);
using (RijndaelManaged i_Alg = new RijndaelManaged { Padding = PaddingMode.Zeros, Key = pdb.GetBytes(32), IV = pdb.GetBytes(16) })
{
using (var memoryStream = new MemoryStream())
{
using (var cryptoStream = new CryptoStream(memoryStream, i_Alg.CreateDecryptor(), CryptoStreamMode.Write))
{
byte[] data = Convert.FromBase64String(cipherText);
cryptoStream.Write(data, 0, data.Length);
cryptoStream.Flush();
return Encoding.UTF8.GetString(memoryStream.ToArray());
}
}
}
}
要生成随机盐,我会使用RNGCryptoServiceProvider这将生成一个可以使用的加密安全随机字节数组。您需要在单独的过程中生成它并将其用作盐。