gpt4 book ai didi

C# 版本的 OpenSSL EVP_BytesToKey 方法?

转载 作者:太空狗 更新时间:2023-10-30 00:12:03 25 4
gpt4 key购买 nike

我正在寻找 OpenSSL 的直接 .NET 实现 EVP_BytesToKey功能。我发现的最接近的是 System.Security.Cryptography.PasswordDeriveBytes类(和 Rfc2898DeriveBytes )但它似乎是 slightly different并且不会生成与 EVP_BytesToKey 相同的keyiv

我也找到了这个implementation这似乎是一个好的开始,但没有考虑迭代次数。

我知道有 OpenSSL.NET,但它只是原生 openssl DLL 的包装器,而不是“真正的”.NET 实现。

最佳答案

我找到了 EVP_BytesToKey 方法的伪代码解释(在 openssl 源的 /doc/ssleay.txt 中):

/* M[] is an array of message digests
* MD() is the message digest function */
M[0]=MD(data . salt);
for (i=1; i<count; i++) M[0]=MD(M[0]);

i=1
while (data still needed for key and iv)
{
M[i]=MD(M[i-1] . data . salt);
for (i=1; i<count; i++) M[i]=MD(M[i]);
i++;
}

If the salt is NULL, it is not used.
The digests are concatenated together.
M = M[0] . M[1] . M[2] .......

因此,基于此,我能够想出这个 C# 方法(这似乎适合我的目的,并假定 32 字节 key 和 16 字节 iv):

private static void DeriveKeyAndIV(byte[] data, byte[] salt, int count, out byte[] key, out byte[] iv)
{
List<byte> hashList = new List<byte>();
byte[] currentHash = new byte[0];

int preHashLength = data.Length + ((salt != null) ? salt.Length : 0);
byte[] preHash = new byte[preHashLength];

System.Buffer.BlockCopy(data, 0, preHash, 0, data.Length);
if (salt != null)
System.Buffer.BlockCopy(salt, 0, preHash, data.Length, salt.Length);

MD5 hash = MD5.Create();
currentHash = hash.ComputeHash(preHash);

for (int i = 1; i < count; i++)
{
currentHash = hash.ComputeHash(currentHash);
}

hashList.AddRange(currentHash);

while (hashList.Count < 48) // for 32-byte key and 16-byte iv
{
preHashLength = currentHash.Length + data.Length + ((salt != null) ? salt.Length : 0);
preHash = new byte[preHashLength];

System.Buffer.BlockCopy(currentHash, 0, preHash, 0, currentHash.Length);
System.Buffer.BlockCopy(data, 0, preHash, currentHash.Length, data.Length);
if (salt != null)
System.Buffer.BlockCopy(salt, 0, preHash, currentHash.Length + data.Length, salt.Length);

currentHash = hash.ComputeHash(preHash);

for (int i = 1; i < count; i++)
{
currentHash = hash.ComputeHash(currentHash);
}

hashList.AddRange(currentHash);
}
hash.Clear();
key = new byte[32];
iv = new byte[16];
hashList.CopyTo(0, key, 0, 32);
hashList.CopyTo(32, iv, 0, 16);
}

更新:这里的实现大致相同,但使用了 .NET DeriveBytes 接口(interface):https://gist.github.com/1339719


OpenSSL 1.1.0c changed the digest algorithm用于一些内部组件。以前使用MD5,1.1.0改用SHA256。请注意,此更改不会影响 EVP_BytesToKeyopenssl enc 等命令。

关于C# 版本的 OpenSSL EVP_BytesToKey 方法?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8008253/

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