【发布时间】:2014-03-25 18:31:30
【问题描述】:
我有这种使用 AES 加密东西的代码和平,更准确地说是 Rijndael 算法来模仿 (http://dcx.sybase.com/index.html#sa160/en/dbreference/encrypt-function.html) SQL Anywhere 16 的行为,为了简单起见,密钥是假的:
var Key = Encoding.ASCII.GetBytes("1234567812345678");
var IV = Encoding.ASCII.GetBytes("1234567812345678");
var text = "stuff";
string encrypted;
var aes = new RijndaelManaged { Mode = CipherMode.CBC, Padding = PaddingMode.PKCS7, BlockSize = 128, KeySize = 128, Key = Key, IV = IV };
using (var encryptor = aes.CreateEncryptor())
{
var tmp = Encoding.ASCII.GetBytes(text);
encrypted = Convert.ToBase64String(encryptor.TransformFinalBlock(tmp, 0, tmp.Length));
}
Console.WriteLine("Encrypted text: " + encrypted);
我得到的结果是:do3BgGEeCWS5+mruUU1Czg== nXnrIX9m4zCxupbPsw3zsg==
在 SQL Anywhere 16 中对其进行解密:
select cast(decrypt(base64_decode('do3BgGEeCWS5+mruUU1Czg=='), '1234567812345678', 'AES(format=RAW;padding=PKCS5)', '1234567812345678') as varchar)
我得到这个结果:s t u f stuff
所以它几乎工作,在十六进制比较它是 0x73007400750066006600 而不是 0x7374756666。此外,如果我在 C# 中解密相同的文本(解密源可以在下面找到),我也得到相同的空格,我做错了什么?
我也尝试了其他方式,在 SQL Anywhere 中加密:
select base64_encode(encrypt('stuff', '1234567812345678', 'AES(format=RAW;padding=PKCS5)', '1234567812345678'))
得到这条线:nXnrIX9m4zCxupbPsw3zsg==
尝试使用相同的程序在 C# 中解密:
string decrypted;
using (var decryptor = aes.CreateDecryptor())
{
var tmp = System.Convert.FromBase64String(encrypted);
decrypted = Encoding.ASCII.GetString(decryptor.TransformFinalBlock(tmp, 0, tmp.Length));
};
Console.WriteLine("Decrypted text: " + decrypted);
我得到了正确的结果:stuff 里面没有不必要的空格。
所以它有一个镜像缺陷,任何想法是从哪里来的那些额外的空间?
更新:错误出现在 var tmp = Encoding.Unicode.GetBytes(text);行,将 Unicode 更改为 ASCII。
【问题讨论】:
标签: c# sql encryption aes sqlanywhere