c# - 尝试用另一种语言解密时 AES 解密错误

标签 c# c++ encryption aes

当我尝试在 C++ 中加密并在 C# 中解密时,出现错误

The input data is not a complete block

但这对我来说没有任何意义,因为如果我尝试用 C++ 解密消息,与我加密的语言相同,它工作正常。

因此,C++ 部分的一些代码:

int main(int argc, char* argv[]) {
 std::string szEncryptionKey = "Sixteen byte key";
 std::string szEncryptionIV = "Sixteen byte key";
 std::string str = "I do not like green eggs and ham I do not like them Sam-I-Am.";
 std::string str_encrypted = encrypt(str, szEncryptionKey, szEncryptionIV);
 std::string str_decrypted = decrypt(str_encrypted, szEncryptionKey, szEncryptionIV);

 std::cout << "str encrypted: " << str_encrypted << std::endl;
 std::cout << "str decrypted: " << str_decrypted << std::endl;

return 0;
}


std::string encrypt(const std::string& str_in, const std::string& key, const std::string& iv)
{

  std::string str_out;
  CryptoPP::CFB_Mode<CryptoPP::AES>::Encryption encryption((byte*)key.c_str(), key.length(), (byte*)iv.c_str());
  CryptoPP::StringSource encryptor(str_in, true,
    new CryptoPP::StreamTransformationFilter(encryption,
        new CryptoPP::Base64Encoder(
            new CryptoPP::StringSink(str_out),
            BlockPaddingSchemeDef::NO_PADDING
        )
     )
  );
 return str_out;
}

我将加密和 base64 编码的字符串以及 KEY 和 IV 带到 C#:

        static void Main(string[] args)
    {
        byte[] bytes = Encoding.UTF8.GetBytes("Sixteen byte key");


            String msg2 = "cboiiqATFAU9KyK49BJMmkLLwiAyaP6yYjyM0oP09xbITLGaxRuLCsTYYzUKANydhO+JO7N00aVz0tmFTg==";
        byte[] msg = Convert.FromBase64String(msg2);
        DecryptStringFromBytes_Aes(msg, bytes, bytes);

static string DecryptStringFromBytes_Aes(byte[] cipherText, byte[] Key, byte[] IV)
    {
        // Check arguments.
        if (cipherText == null || cipherText.Length <= 0)
            throw new ArgumentNullException("cipherText");
        if (Key == null || Key.Length <= 0)
            throw new ArgumentNullException("Key");
        if (IV == null || IV.Length <= 0)
            throw new ArgumentNullException("IV");

        // Declare the string used to hold
        // the decrypted text.

        using (Aes aesAlg = Aes.Create())
        {
            aesAlg.Mode = CipherMode.CFB;
            aesAlg.Padding = PaddingMode.None;
            aesAlg.Key = Key;
            aesAlg.IV = IV;

            // Check arguments.
            if (cipherText == null || cipherText.Length <= 0)
                throw new ArgumentNullException("plainText");
            if (Key == null || Key.Length <= 0)
                throw new ArgumentNullException("Key");
            if (IV == null || IV.Length <= 0)
                throw new ArgumentNullException("IV");
            byte[] encrypted = null;
            // Create an Aes object
            // with the specified key and IV.
            using (ICryptoTransform decrypt = aesAlg.CreateDecryptor(aesAlg.Key, aesAlg.IV))
            {
                byte[] decryptedText = decrypt.TransformFinalBlock(cipherText, 0, cipherText.Length);

               String s = Encoding.UTF8.GetString(decryptedText);

                Console.Write(s);
                return s;
            }
        }
    }

错误信息出现在这一行:

byte[] decryptedText = decrypt.TransformFinalBlock(cipherText, 0, cipherText.Length);

这一行:

byte[] bytes = Encoding.UTF8.GetBytes("Sixteen byte key");

这只是对 UTF8 的猜测,但我不知道它是否是正确的编码。

谁能帮我解决这个问题?

最佳答案

输入数据不是 block 大小的精确倍数,AES 为 16 字节。 msg2 解码后为 61 字节,这不是有效的 AES 加密长度,因此无效并产生错误消息:“输入数据不是完整的 block ".

AES 是基于 block 的,因此如果要加密的数据不是 block 大小的精确倍数,则必须对其进行填充。与 AES 一起使用的一般填充方法是 PKCS#7,有时也称为 PKCS#5。

CFB 模式需要填充,CFB8 模式不需要。

关于c# - 尝试用另一种语言解密时 AES 解密错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49175069/

相关文章:

C# DLL 的包装器

c# - 使用 Autofixture 控制对象树的生成深度

security - 保护 Kubernetes secret 文件以进行源代码控制?

java - 大于 "s"的字符无法加密?

c# - Entity Framework 在调用 savechanges 时复制

c# - 保留录制视频的最后 X 分钟

c++ - (n&(n-1))==0 和 n&(n-1)==0 在 C++ 中做什么?

c++ - SDL 1.3 : How to render video with out displaying it?

java - 制作2D游戏的最佳编程语言和最佳工具包

检测到 Android root?立即卸载应用程序