我用C#编写了两个程序。一个进行加密,另一个进行解密。解密程序抛出异常"输入数据不是一个完整的块"来自加密程序的数据。但是,使用PKCS5_PBKDF2_HMAC_SHA1(),解密程序可以正常使用来自Unix加密程序的加密数据。
加密数据基于64位编码,并保存在文本文件中。前8个字节是salt,接下来的16个字节是IV,其余的是应用程序文本。
如果有人能提供帮助,我将非常感激。
public static string DecryptText(string cipherData)
{
if (string.IsNullOrEmpty(_passwd))
return null;
var decodedBytes = Convert.FromBase64String(cipherData);
// First 8 bytes contain the salt used for key derivation. Use the password from the passwd.dat
// file and the salt to derive the key used to encode the credential.
//
var salt = new byte[8];
Buffer.BlockCopy(decodedBytes, 0, salt, 0, 8);
var derivedBytes = new Rfc2898DeriveBytes(_passwd, salt, 1000);
var key = derivedBytes.GetBytes(32);
// Next 16 bytes contain the initialization vector used to encrypt
//
var ivBytes = new byte[16];
Buffer.BlockCopy(decodedBytes, 8, ivBytes, 0, ivBytes.Length);
// Remaining bytes contain the credential cipher text
//
var cipherBytes = new byte[decodedBytes.Length - 8 - 16];
Buffer.BlockCopy(decodedBytes, 8 + 16, cipherBytes, 0, cipherBytes.Length);
string decryptedData = null;
try
{
using (var aes = new AesCryptoServiceProvider())
{
aes.Key = key;
aes.IV = ivBytes;
using (var ms = new MemoryStream())
{
using (var cs = new CryptoStream(ms, aes.CreateDecryptor(), CryptoStreamMode.Write))
{
cs.Write(cipherBytes, 0, cipherBytes.Length);
cs.Close();
}
decryptedData = Encoding.UTF8.GetString(ms.ToArray());
}
}
}
catch (Exception ex)
{
Console.Write("Caught exception while decryption: {0}: ", ex.Message);
}
return decryptedData;
}
public static string EncryptText(string plainData)
{
if (string.IsNullOrEmpty(_passwd))
return null;
var rfc2898db = new Rfc2898DeriveBytes(_passwd, 8, 1000);
byte[] salt = new byte[8];
Buffer.BlockCopy(rfc2898db.Salt, 0, salt, 0, 8);
byte[] key = new byte[32];
Buffer.BlockCopy(rfc2898db.GetBytes(32), 0, key, 0, 32);
string cipherData;
try
{
var aes = new AesCryptoServiceProvider
{
Key = key,
KeySize = 256,
BlockSize = 128,
Mode = CipherMode.CBC,
Padding = PaddingMode.PKCS7
};
aes.GenerateIV();
byte[] encrypted;
using (var ms = new MemoryStream())
{
using (var cs = new CryptoStream(ms, aes.CreateEncryptor(), CryptoStreamMode.Write))
{
ms.Write(aes.IV, 0, aes.IV.Length);
ms.Write(salt, 0, 8);
cs.Write(Encoding.UTF8.GetBytes(plainData), 0, plainData.Length);
cs.Close();
}
encrypted = ms.ToArray();
}
byte[] encryptedBytes = new byte[SaltLength + IvLength + encrypted.Length];
Buffer.BlockCopy(salt, 0, encryptedBytes, 0, SaltLength);
Buffer.BlockCopy(aes.IV, 0, encryptedBytes, SaltLength, IvLength);
Buffer.BlockCopy(encrypted, 0, encryptedBytes, SaltLength + IvLength, encrypted.Length);
cipherData = Convert.ToBase64String(encryptedBytes);
}
catch (Exception ex)
{
Console.Write("Caught exception while encryption: {0}", ex.Message);
return null;
}
return cipherData;
}