我在文本框中输入存档名称以获取此存档的消息。
我在文本框中写密码
我计算盐。
按钮单击
private void button1_Click_1(object sender, EventArgs e)
{
String message;
String password;
String result;
String resultSalt;
String nameResult;
byte[] salt;
password = textBox2.Text;
nameResult = textBox3.Text;
new RNGCryptoServiceProvider().GetBytes(salt = new byte[16]);
resultSalt = Convert.ToBase64String(salt);
if (radioButton1.Checked == true)
{
message = readArchive();
result = Encrypt(message,password,resultSalt);
try
{
File.WriteAllText(nameResult, result);
MessageBox.Show("Encrypt Ok");
}
catch
{
MessageBox.Show("Error");
}
}
else
{
message = readArchive();
result = Decrypt(message,password,result);
try
{
File.WriteAllText(nameResult, resultSalt);
MessageBox.Show("Decrypt OK");
}
catch
{
MessageBox.Show("Error");
}
}
}
方法加密
public static string Encrypt(string message, string pass, string salt)
{
AesCryptoServiceProvider aes = new AesCryptoServiceProvider();
DeriveBytes rgb = new Rfc2898DeriveBytes(pass, Encoding.Unicode.GetBytes(salt), 9);
byte[] key = rgb.GetBytes(aes.KeySize >> 3);
byte[] iv = rgb.GetBytes(aes.BlockSize >> 3);
aes.Mode = CipherMode.CBC;
aes.Key = key;
aes.IV = iv;
ICryptoTransform encryptor = aes.CreateEncryptor();
byte[] data = Encoding.Unicode.GetBytes(message);
byte[] dataencrypt = encryptor.TransformFinalBlock(data, 0, data.Length);
return Convert.ToBase64String(dataencrypt);
}
方法解密
public static string Decrypt(string message, string pass, string salt)
{
AesCryptoServiceProvider aes = new AesCryptoServiceProvider();
DeriveBytes rgb = new Rfc2898DeriveBytes(pass, Encoding.Unicode.GetBytes(salt), 9);
byte[] key = rgb.GetBytes(aes.KeySize >> 3);
byte[] iv = rgb.GetBytes(aes.BlockSize >> 3);
aes.Mode = CipherMode.CBC;
aes.Key = key;
aes.IV = iv;
ICryptoTransform decryptor = aes.CreateDecryptor();
byte[] data = Convert.FromBase64String(message);
byte[] datadecrypt = decryptor.TransformFinalBlock(data, 0, data.Length);
return Encoding.Unicode.GetString(datadecrypt);
}
方法readArchive
private string readArchive()
{
String nameArchive = textBox1.Text;
String text = "";
try
{
text = File.ReadAllText(@nameArchive);
}
catch
{
MessageBox.Show("Error.");
}
return text;
}
错误行
byte[] datadecrypt = decryptor.TransformFinalBlock(data, 0, data.Length);
类型' System.Security.Cryptography.CryptographicException'未处理的例外情况。在System.Core.dll
中附加信息:字符之间的填充无效,无法删除。
答案 0 :(得分:2)
使用resultSalt = Convert.ToBase64String(salt)
对您的salt进行base64编码,然后再将其传递给Encrypt(..)
,然后使用Encoding.Unicode.GetBytes(salt)
获取base64编码字符串的字节值。这可能不是您想要的,而是将其作为byte []传递,或者在使用之前进行正确的base64解码。
但这不是主要问题..主要问题是您将result
传递给Decrypt(..)
而不是resultSalt
。但是当你这样做时,你需要确保它与Encrypt(..)
上使用的相同。目前你在每次点击时都会产生新的盐。