【问题标题】:Length of the data to Encrypt is invalid要加密的数据长度无效
【发布时间】:2013-01-18 01:35:16
【问题描述】:

获取异常“要加密的数据长度无效”。

private static readonly byte[] salt = Encoding.ASCII.GetBytes("S@sh@kt@ VMS");

public static string Encrypt(string textToEncrypt, string encryptionPassword)
{
    byte[] encryptedBytes = null;
    try
    {
        var algorithm = GetAlgorithm(encryptionPassword);
        algorithm.Padding = PaddingMode.None;
        using (ICryptoTransform encryptor = algorithm.CreateEncryptor(algorithm.Key, algorithm.IV))
        {
            byte[] bytesToEncrypt = Encoding.UTF8.GetBytes(textToEncrypt);
            encryptedBytes = InMemoryCrypt(bytesToEncrypt, encryptor);
        }
    }
    catch (Exception ex)
    {
        MessageBox.Show(ex.Message);
    }
    return Convert.ToBase64String(encryptedBytes);
}

 // Performs an in-memory encrypt/decrypt transformation on a byte array.

private static byte[] InMemoryCrypt(byte[] data, ICryptoTransform transform)
{
    MemoryStream memory = new MemoryStream();
    using (Stream stream = new CryptoStream(memory, transform, CryptoStreamMode.Write))
    {
        stream.Flush();
        stream.Write(data, 0, data.Length);
        //stream.FlushFinalBlock();
    }
    return memory.ToArray();
}

private static RijndaelManaged GetAlgorithm(string encryptionPassword)
{
    // Create an encryption key from the encryptionPassword and salt.
    var key = new Rfc2898DeriveBytes(encryptionPassword, salt);
    // Declare that we are going to use the Rijndael algorithm with the key that we've just got.
    var algorithm = new RijndaelManaged();
    int bytesForKey = algorithm.KeySize/8;
    int bytesForIV = algorithm.BlockSize/8;
    algorithm.Key = key.GetBytes(bytesForKey);
    algorithm.IV = key.GetBytes(bytesForIV);
    return algorithm;
}

而解密程序是:

public static string Decrypt(string encryptedText, string encryptionPassword)
{
    var algorithm = GetAlgorithm(encryptionPassword);
    algorithm.Padding = PaddingMode.PKCS7; 
    byte[] descryptedBytes;
    using (ICryptoTransform decryptor = algorithm.CreateDecryptor(algorithm.Key, algorithm.IV))
    {
        byte[] encryptedBytes = Convert.FromBase64String(encryptedText);
        descryptedBytes = InMemoryCrypt(encryptedBytes, decryptor);
    } 
    return Encoding.UTF8.GetString(descryptedBytes); 
} 

【问题讨论】:

  • 在哪一行?堆栈跟踪是什么样的?
  • stream.Write(data, 0, data.Length);
  • PaddingMode.None 要求输入是块大小的倍数
  • 顺便说一句。常数不是好盐。
  • Thnx that Works BUTTTTTT Now Error: it is Padding doesn't work and cannot be removed"

标签: c#


【解决方案1】:

PaddingMode.None 要求输入是块大小的倍数。使用 PaddingMode.PKCS7 instread 之类的想法。


您的代码的其他一些问题:

  1. 常数不能成为好盐
  2. 常量盐以及从密码中确定性推导 IV 意味着您正在重用 (Key, IV) 对,不应该这样做
  3. 您没有添加身份验证/某种 MAC。这通常会导致填充预言或类似的攻击
  4. 您从 PBKDF2 输出中读取了更多本机大小。这将您的密钥派生速度减半,而不会减慢攻击者的速度。

【讨论】:

  • 有错误 --->>> "填充无效,无法删除。"解密时
  • @Aditya 当我用PKCS7 替换None 时,代码会毫无例外地运行加密。由于您没有发布您的解密代码,我无法帮助您。
  • public static string Decrypt(string encryptedText, string encryptionPassword) { var algorithm = GetAlgorithm(encryptionPassword);算法.Padding = PaddingMode.PKCS7; byte[] 解密字节;使用 (ICryptoTransform 解密器 = algorithm.CreateDecryptor(algorithm.Key, algorithm.IV)) { byte[] encryptedBytes = Convert.FromBase64String(encryptedText); descryptedBytes = InMemoryCrypt(encryptedBytes, 解密器); } return Encoding.UTF8.GetString(descryptedBytes); }
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-12-05
  • 2020-12-19
相关资源
最近更新 更多