密钥和 IV 分配给 AES 对象的目的是什么?
What is the purpose of key and IV assignment to AES object?
在 MSDN for AES 中,我可以在示例中看到以下部分。
...
using (Aes aesAlg = Aes.Create())
{
aesAlg.Key = Key;
aesAlg.IV = IV;
ICryptoTransform encryptor = aesAlg.CreateEncryptor(aesAlg.Key, aesAlg.IV);
...
} ...
我试图跳过将密钥和 IV 分配给 AES 对象(尽管在创建加密器时像这样设置它们。
...
using (Aes aesAlg = Aes.Create())
{
//aesAlg.Key = Key;
//aesAlg.IV = IV;
ICryptoTransform encryptor = aesAlg.CreateEncryptor(Key, IV);
...
} ...
结果好像没什么区别。但是,由于它是样本的一部分,我担心会出现重要的情况。可能是我只试了没有显示的例子。
什么时候需要将密钥和 IV 分配给 AES 对象?
在第一个代码片段中,您已将值分配给对称算法对象的 Key
和 IV
属性,因此您无需在创建加密时再次传递它们转变。在这种情况下,使用无参数重载,它使用已分配的 Key
和 IV
创建 encryptor/decryptor.
using (Aes aesAlg = Aes.Create())
{
aesAlg.Key = Key;
aesAlg.IV = IV;
ICryptoTransform encryptor = aesAlg.CreateEncryptor();
// ...
}
第二个代码片段将使用传递的 Key
和 IV
参数创建相同的转换,而不考虑 aesAlg.Key
和 aesAlg.IV
值。考虑以下因素:
using (Aes aesAlg = Aes.Create())
{
aesAlg.Key = Key;
aesAlg.IV = IV;
ICryptoTransform encryptor = aesAlg.CreateEncryptor(someOtherKey, somOtherIV);
// ...
}
此处,someOtherKey
和 someOtherIV
用于创建转换,忽略 aesAlg
属性。另一个要考虑的例子:
using (Aes aesAlg = Aes.Create())
{
ICryptoTransform encryptor = aesAlg.CreateEncryptor();
// ...
}
现在,aesAlg.Key
和 aesAlg.IV
属性都是 null
,.CreateEncryptor()
将使用它们来创建转换。但是,该方法不会抛出任何异常,因为这些属性的 getter - 按照设计 - 不会 return null
而是创建和分配随机值。
您可能想尝试以下方法:
private void SomeCaller()
{
using (var crypto = Aes.Create())
{
// A random Key is generated...
PrintHexValue(crypto.Key);
// And assigned...
PrintHexValue(crypto.Key);
var pass = "Konrad Viltersten";
var bytes = Encoding.UTF8.GetBytes(pass);
var rfc = new Rfc2898DeriveBytes(pass,
new SHA256Managed().ComputeHash(bytes), 1000);
var key = rfc.GetBytes(crypto.LegalKeySizes[0].MaxSize / 8);
var iv = rfc.GetBytes(crypto.LegalBlockSizes[0].MinSize / 8);
// Doesn't change the crypto.Key and crypto.IV properties...
var encr = crypto.CreateEncryptor(key, iv);
// The generated password-based key...
PrintHexValue(key);
// The random key remains...
PrintHexValue(crypto.Key);
crypto.Key = key;
crypto.IV = iv;
// The password-based key is assigned to the crypto.Key...
PrintHexValue(crypto.Key);
}
}
private void PrintHexValue(byte[] bytes) =>
Console.WriteLine(BitConverter.ToString(bytes).Replace("-", string.Empty));
结论
您的第二个代码片段是创建加密转换的快捷方式。您将需要第一个在更广泛的范围内,例如 。
在 MSDN for AES 中,我可以在示例中看到以下部分。
...
using (Aes aesAlg = Aes.Create())
{
aesAlg.Key = Key;
aesAlg.IV = IV;
ICryptoTransform encryptor = aesAlg.CreateEncryptor(aesAlg.Key, aesAlg.IV);
...
} ...
我试图跳过将密钥和 IV 分配给 AES 对象(尽管在创建加密器时像这样设置它们。
...
using (Aes aesAlg = Aes.Create())
{
//aesAlg.Key = Key;
//aesAlg.IV = IV;
ICryptoTransform encryptor = aesAlg.CreateEncryptor(Key, IV);
...
} ...
结果好像没什么区别。但是,由于它是样本的一部分,我担心会出现重要的情况。可能是我只试了没有显示的例子。
什么时候需要将密钥和 IV 分配给 AES 对象?
在第一个代码片段中,您已将值分配给对称算法对象的 Key
和 IV
属性,因此您无需在创建加密时再次传递它们转变。在这种情况下,使用无参数重载,它使用已分配的 Key
和 IV
创建 encryptor/decryptor.
using (Aes aesAlg = Aes.Create())
{
aesAlg.Key = Key;
aesAlg.IV = IV;
ICryptoTransform encryptor = aesAlg.CreateEncryptor();
// ...
}
第二个代码片段将使用传递的 Key
和 IV
参数创建相同的转换,而不考虑 aesAlg.Key
和 aesAlg.IV
值。考虑以下因素:
using (Aes aesAlg = Aes.Create())
{
aesAlg.Key = Key;
aesAlg.IV = IV;
ICryptoTransform encryptor = aesAlg.CreateEncryptor(someOtherKey, somOtherIV);
// ...
}
此处,someOtherKey
和 someOtherIV
用于创建转换,忽略 aesAlg
属性。另一个要考虑的例子:
using (Aes aesAlg = Aes.Create())
{
ICryptoTransform encryptor = aesAlg.CreateEncryptor();
// ...
}
现在,aesAlg.Key
和 aesAlg.IV
属性都是 null
,.CreateEncryptor()
将使用它们来创建转换。但是,该方法不会抛出任何异常,因为这些属性的 getter - 按照设计 - 不会 return null
而是创建和分配随机值。
您可能想尝试以下方法:
private void SomeCaller()
{
using (var crypto = Aes.Create())
{
// A random Key is generated...
PrintHexValue(crypto.Key);
// And assigned...
PrintHexValue(crypto.Key);
var pass = "Konrad Viltersten";
var bytes = Encoding.UTF8.GetBytes(pass);
var rfc = new Rfc2898DeriveBytes(pass,
new SHA256Managed().ComputeHash(bytes), 1000);
var key = rfc.GetBytes(crypto.LegalKeySizes[0].MaxSize / 8);
var iv = rfc.GetBytes(crypto.LegalBlockSizes[0].MinSize / 8);
// Doesn't change the crypto.Key and crypto.IV properties...
var encr = crypto.CreateEncryptor(key, iv);
// The generated password-based key...
PrintHexValue(key);
// The random key remains...
PrintHexValue(crypto.Key);
crypto.Key = key;
crypto.IV = iv;
// The password-based key is assigned to the crypto.Key...
PrintHexValue(crypto.Key);
}
}
private void PrintHexValue(byte[] bytes) =>
Console.WriteLine(BitConverter.ToString(bytes).Replace("-", string.Empty));
结论
您的第二个代码片段是创建加密转换的快捷方式。您将需要第一个在更广泛的范围内,例如