gpt4 book ai didi

c# - 与 RijndaelManaged 加密的行为不一致

转载 作者:行者123 更新时间:2023-11-30 18:39:45 25 4
gpt4 key购买 nike

我在使用 RijndaelManaged 时遇到了一个奇怪的问题。基本上我有一个新实例,我在其中设置了 CipherMode、Padding、IV 和 Key。然后,我创建了另一个实例并将以下属性的相同值从原始实例分配给第二个实例:Mode、Padding、KeySize、FeedbackSize、BlockSize、IV 和 Key。

那么,将所有属性值从实例 1 复制到实例 2 后,我应该会得到相同的结果,对吗?错误的!两个实例的 GetHashCode() 有所不同,但如果我转储它们的属性(上面命名的),那么它们都是相同的。

如果我加密长度等于 block 大小(16 字节,128 位)的文本字符串,那么两者都会产生相同的结果,如果输入小于 BlockSize,则加密结果不一样。

我用它来创建初始 Rijndael 实例。

    public static RijndaelManaged CreateSymmetricKey(string passphrase)
{
RijndaelManaged symCrypto = new RijndaelManaged();
symCrypto.Mode = CipherMode.CBC;
symCrypto.Padding = PaddingMode.PKCS7;
byte[] salt = Encoding.UTF8.GetBytes("dummy dummy dummy dummy test");
Rfc2898DeriveBytes key = new Rfc2898DeriveBytes(passphrase, salt);
symCrypto.Key = key.GetBytes(symCrypto.KeySize / 8);
symCrypto.IV = key.GetBytes(symCrypto.BlockSize / 8);

return symCrypto;
}

为示例加密字符串:

private string Encrypt(RijndaelManaged rm, string text)
{
byte[] encrypted;
// Create a decrytor to perform the stream transform.
ICryptoTransform encryptor = rm.CreateEncryptor(rm.Key, rm.IV);
using (MemoryStream msEncrypt = new MemoryStream())
{
using (CryptoStream csEncrypt = new CryptoStream(msEncrypt, encryptor, CryptoStreamMode.Write))
{
using (StreamWriter swEncrypt = new StreamWriter(csEncrypt))
{
//Write all data to the stream.
swEncrypt.Write(text);
}
encrypted = msEncrypt.ToArray();
}
}
return BitConverter.ToString(encrypted);
}

那就这样吧

RijndaelManaged rm1 = CreateSymmetricKey("there is something weird happening");
RijndaelManaged rm2 = new RijndaelManaged();
// copy ALL public properties to the new instance so that it has the same parameters
rm2.BlockSize = rm1.BlockSize; // 128
rm2.FeedbackSize = rm1.FeedbackSize; // 128
rm2.KeySize = rm1.KeySize; // 256
rm2.Mode = rm1.Mode; // CBC
rm2.Padding = rm1.Padding; // PKCS7
rm2.IV = rm1.IV;
rm2.Key = rm1.Key;
// Encryption
string cypher1 = Encrypt(rm1, "this is a test 6"); // length equal to BlockSize
string cypher2 = Encrypt(rm2, "this is a test 6"); // length equal to BlockSize
string cypher11 = Encrypt(rm1, "this is a test"); // length less than BlockSize
string cypher21 = Encrypt(rm2, "this is a test"); // length less than BlockSize

我得到 cyper1 == cypher2 和 cypher11 != cypher21 也 rm1.GetHashCode() != rm2.GetHashCode() 但所有公共(public)参数都相同!

我还转储了两个实例的所有公共(public)属性,看看我是否遗漏了什么但没有,所有值都是相同的。

最佳答案

您不应该以这种方式使用 GetHashCode()。对于没有覆盖基础 object.GetHashCode() 实现的类,它将返回此特定实例的整数处理程序。
由于两个不同实例的句柄总是不同的,因此永远不会匹配。

此外,GetHashCode() 实际上从未保证唯一性,它只是用作轻量级预检查,在实际相等性被测试之前。
这在任何类型的哈希数据结构中大量使用,如字典等。

有关此主题的更多信息:
http://msdn.microsoft.com/en-us/library/system.object.gethashcode.aspx

我也执行了您的代码,对我来说情况如下:

cyper1 == cypher2 and cypher11 == cypher21

我很确定问题出在 GetHashCode() 的比较上。

关于c# - 与 RijndaelManaged 加密的行为不一致,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9219192/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com