为啥 .NET 中的 AEC 加密产生与 JavaScript 不同的结果?

Posted

技术标签:

【中文标题】为啥 .NET 中的 AEC 加密产生与 JavaScript 不同的结果?【英文标题】:Why AEC encryption in .NET yields different result than JavaScript?为什么 .NET 中的 AEC 加密产生与 JavaScript 不同的结果? 【发布时间】:2021-12-30 13:06:26 【问题描述】:

我要为这个发疯了。花了一整天,仍然无法理解发生了什么。我在 .Net 和 javascript 中都使用 AES256CBC 加密。出于某种原因,我得到了不同的结果,尽管我使用的是相同的密钥。我的代码是:

JavaScript:

function convertStringToArrayBuffer(str) 
        var length = str.length;
        var bytes = new Uint8Array(length);
        for(var i = 0; i < length; i++) 
            bytes[i] = str.charCodeAt(i);
        
        return bytes;
    

    var keyB64 ="sy/d1Ddy/9K3p8x6pWMq2P8Qw2ftUjkkrAA7xFC7aK8=";
    var viB64 = "t8eI2F+QmlUBWZJVIlTX6Q==";

    var dataToEnc = "Test123!"
    let dataInBytes = convertStringToArrayBuffer(dataToEnc);

    let key = window.atob(keyB64);
    let iv = window.atob(viB64);

    console.log(key);
    console.log(iv);
    window.crypto.subtle.importKey("raw", convertStringToArrayBuffer(key).buffer, name: "AES-CBC", length: 256, false, ["encrypt"]).then(function(key)
        console.log(key);
        window.crypto.subtle.encrypt(name: "AES-CBC", iv: convertStringToArrayBuffer(iv).buffer, key, dataInBytes.buffer).then(function(encrypted)
            console.log(encrypted);
        );
    );

这个产生

.net:

public static void Test()
        
            var dataToEnc = "Test123!";
            var keyB64 = "sy/d1Ddy/9K3p8x6pWMq2P8Qw2ftUjkkrAA7xFC7aK8=";
            var viB64 = "t8eI2F+QmlUBWZJVIlTX6Q==";
            var key = Convert.FromBase64String(keyB64);
            var iv = Convert.FromBase64String(viB64);
            var data = Encoding.UTF8.GetBytes(dataToEnc);

            byte[] encrypted = null;
            using (Aes aesAlg = Aes.Create())
            
                aesAlg.Key = key;
                aesAlg.IV = iv;

                ICryptoTransform encryptor = aesAlg.CreateEncryptor(aesAlg.Key, aesAlg.IV);
                using (MemoryStream msEncrypt = new MemoryStream())
                
                    using (CryptoStream csEncrypt = new CryptoStream(msEncrypt, encryptor, CryptoStreamMode.Write))
                    
                        using (StreamWriter swEncrypt = new StreamWriter(csEncrypt))
                        
                            swEncrypt.Write(data);
                        
                        encrypted = msEncrypt.ToArray();
                    
                

            

        

这个产生

我相信它是微不足道的,但我找不到这个。我很感激这里的任何提示。

【问题讨论】:

我建议在过程的每个步骤中进行一些繁琐的调试。首先,将明文字符串编码为字节数组后的字节是否相同? 错误在 C# 代码中。您必须使用swEncrypt.Write(dataToEnc) 而不是swEncrypt.Write(data)。您当前使用的重载会隐式执行data.ToString()。另见TextWriter.Write(object? value)SteamWriter.Write(string? value) 【参考方案1】:

如果其他人遇到此问题,@Topaco 的评论是正确的方法,我将其粘贴在下方

错误在 C# 代码中。您必须使用 swEncrypt.Write(dataToEnc) 而不是 swEncrypt.Write(data)。您当前使用的重载会隐式执行 data.ToString()

【讨论】:

以上是关于为啥 .NET 中的 AEC 加密产生与 JavaScript 不同的结果?的主要内容,如果未能解决你的问题,请参考以下文章

JAVA和.NET使用DES对称加密的区别

Android AEC 不会产生有用的声音

java aes加密与网上在线加密不同。谁能告诉我为啥?求个正确的例子,谢谢了!

为啥我的 .NET 应用程序会产生如此多的页面错误?

Java - 使用 XOR 解密的字符串不产生原始/加密字符串

.net(md5)加密汉字的结果与java(md5)加密汉字的结果不一样。。。