为什么.NET4/C#中RijndaelManaged抛出填充无效且无法移除异常?
问题根源
你的解密方法中CryptoStream数据流方向配置完全错误,是导致Padding校验失败的直接原因。
错误点拆解
- 当使用
CryptoStreamMode.Read模式时,CryptoStream会从传入的源流读取待处理数据,处理完成后输出解密后的数据 - 你当前的代码错误地将空内存流作为CryptoStream的输入源,又通过
Read方法将加密数据写入目标数组,完全搞反了数据流向,导致解密输入为空/无效,最终PKCS7填充校验失败。
修正后的解密代码
public static byte[] Decrypt(byte[] encryptedData, byte[] key, byte[] iv) { byte[] data; using (var aes = new RijndaelManaged() { Padding = PaddingMode.PKCS7, Mode = CipherMode.CBC, KeySize = KEY_SIZE, BlockSize = BLOCK_SIZE }) { var decryptor = aes.CreateDecryptor(key, iv); // 修正:将加密数据作为输入源流 using (var msEncrypted = new MemoryStream(encryptedData)) { using (var csDecrypt = new CryptoStream(msEncrypted, decryptor, CryptoStreamMode.Read)) { // 修正:从CryptoStream读取解密后的数据写入内存流 using (var msResult = new MemoryStream()) { csDecrypt.CopyTo(msResult); data = msResult.ToArray(); } } } } return data; } public static byte[] Decrypt(byte[] encryptedData, string sKey, byte[] iv) { return Decrypt(encryptedData, Encoding.UTF8.GetBytes(sKey), iv); }
额外校验建议
- 确认
KEY_SIZE常量为合法的AES密钥长度:128/192/256(对应密钥字节长度16/24/32) - 确认
BLOCK_SIZE常量固定为128,AES算法块大小不可修改,避免出现算法行为不匹配 - 字符串密钥转字节时如果使用UTF8编码,要注意密钥长度必须严格匹配
KEY_SIZE对应的字节数,不要用字符串截断逻辑
内容的提问来源于stack exchange,提问作者bananabr
相关产品推荐
相关产品推荐

