.net - 如何使用密码生成 Rijndael KEY 和 IV?

标签 .net cryptography rijndael

如何使用密码生成 Rijndael KEY 和 IV? key 长度必须为 256 位。

最佳答案

我认为您正在寻找基于密码的 key 推导。有实现它的 Rfc2898DeriveBytes 类。

Rfc2898DeriveBytes 获取密码、salt 和迭代计数,然后通过调用 GetBytes 方法生成 key 。

RFC 2898 包括从密码和盐创建 key 和初始化向量 (IV) 的方法。您可以使用 PBKDF2,一种基于密码的 key 派生函数,使用允许生成几乎无限长度的 key 的伪随机函数来派生 key 。 Rfc2898DeriveBytes 类可用于从基本 key 和其他参数生成派生 key 。在基于密码的 key 派生函数中,基本 key 是密码,其他参数是盐值和迭代次数。

有关 PBKDF2 的更多信息,请参阅 RFC 2898,“PKCS #5:基于密码的密码术规范版本 2.0”。

例子:

public static byte[] CreateKey(string password)
{
    var salt = new byte[] { 1, 2, 23, 234, 37, 48, 134, 63, 248, 4 };

    const int Iterations = 9872;
    using (var rfc2898DeriveBytes = new Rfc2898DeriveBytes(password, salt, Iterations))
        return rfc2898DeriveBytes.GetBytes(32);
}

您可以在任何对称算法中使用DeriveBytes,而不仅仅是Rijndael
示例:

public static SymmetricAlgorithm InitSymmetric(SymmetricAlgorithm algorithm, string password, int keyBitLength)
{
    var salt = new byte[] { 1, 2, 23, 234, 37, 48, 134, 63, 248, 4 };

    const int Iterations = 234;
    using (var rfc2898DeriveBytes = new Rfc2898DeriveBytes(password, salt, Iterations))
    {
        if (!algorithm.ValidKeySize(keyBitLength))
            throw new InvalidOperationException("Invalid size key");

        algorithm.Key = rfc2898DeriveBytes.GetBytes(keyBitLength / 8);
        algorithm.IV = rfc2898DeriveBytes.GetBytes(algorithm.BlockSize / 8);
        return algorithm;
    }
}

private static byte[] Transform(byte[] bytes, Func<ICryptoTransform> selectCryptoTransform)
{
    using (var memoryStream = new MemoryStream())
    {
        using (var cryptoStream = new CryptoStream(memoryStream, selectCryptoTransform(), CryptoStreamMode.Write))
            cryptoStream.Write(bytes, 0, bytes.Length);
        return memoryStream.ToArray();
    }
}

用法:

public static void Main()
{
    using (var rijndael = InitSymmetric(Rijndael.Create(), "TestPassword", 256))
    {
        var text = "Some text to encrypt";
        var bytes = Encoding.UTF8.GetBytes(text);

        var encryptedBytes = Transform(bytes, rijndael.CreateEncryptor);
        var decryptedBytes = Transform(encryptedBytes, rijndael.CreateDecryptor);

        var decryptedText = Encoding.UTF8.GetString(decryptedBytes);
        Debug.Assert(text == decryptedText);
    }
}

确保更改 saltiterations 参数。

关于.net - 如何使用密码生成 Rijndael KEY 和 IV?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6482883/

相关文章:

javascript - 使用 WebCrypto API 生成 RSA key 对并使用密码保护它

iOS——OpenSSL 和加速加密?

encryption - 我应该从哈希值生成 key 以进行加密吗?

c# - 解密异常 - 要解密的数据长度无效

java - Java 中的 Rijndael 支持

c# - 用于 C# 的 C++ COM DLL

c# - 为什么 "DateTime.Now.ToString("hh tt", new CultureInfo ("de"))"在不同版本的 .Net 中返回不同的结果?

java - 如何检查字符串的前 n 个字节是否为零?

c# - 获取 GPU 显存总量?

c# - 没有 DeploymentItemAttribute 的 MSTest 部署