首页 > 解决方案 > 将 Rijndael 解密逻辑从 C# 更改为 Python

问题描述

我有一些已经加密的数据需要使用 python 解密。C# 中的解密逻辑如下所示。

using System.Security.Cryptography;
private const string Url_ENCRYPTION_KEY = "abcd123456";
private readonly static byte[] URL_SALT = Encoding.ASCII.GetBytes(Url_ENCRYPTION_KEY.Length.ToString());
public static string Decrypt(string inputText) {
    
    try {
        if (!string.IsNullOrEmpty(inputText)) {
            RijndaelManaged rijndaelCipher = new RijndaelManaged();
            byte[] encryptedData = Convert.FromBase64String(inputText.Replace(" ", "+"));
            PasswordDeriveBytes secretKey = new PasswordDeriveBytes(Url_ENCRYPTION_KEY, URL_SALT);

            using (ICryptoTransform decryptor =
                rijndaelCipher.CreateDecryptor(secretKey.GetBytes(32), secretKey.GetBytes(16))) {
                using (MemoryStream memoryStream = new MemoryStream(encryptedData)) {
                    using (CryptoStream cryptoStream =
                        new CryptoStream(memoryStream, decryptor, CryptoStreamMode.Read)) {
                        byte[] plainText = new byte[encryptedData.Length];
                        int decryptedCount = cryptoStream.Read(plainText, 0, plainText.Length);
                        return Encoding.Unicode.GetString(plainText, 0, decryptedCount);
                    }
                }
            }
        }
    }
    catch(Exception ex) {
        //clsErrorHandler.LogError(ex);
    }
    return inputText;
}

我已经尝试过像 pprp 和 python 的密码学这样的库,但是那里的解决方案使用 PBKDF2,而这里的 C# 代码提供密钥和盐的解密器字节作为密钥和 IV 值。从我看来,PasswordDeriveBytes 函数基本上可以作为一个稍微修改的 PBKDF1 工作,但是我尝试的所有解决方案都失败了,因为某种深奥的这种大小与那个大小错误不匹配。这是我发现的 PasswordDeriveBytes 的一种实现,但我不知道如何做类似的事情secretKey.GetBytes(32)并创建解密器

import hashlib
from base64 import b64decode

def MS_PasswordDeriveBytes(pstring, salt, hashfunc, iterations, keylen):
    if iterations > 0:
        lasthash = hashlib.sha1(pstring+salt).digest()
        iterations -= 1
    else:
        print("Iterations must be > 0")
    #If iterations is 1 then basically the same thing happens as 2 based on my testing
    #if iterations == 0 and keylen > len(lasthash):
        #print("Dunno what happens here")
        #return -1
    for i in range(iterations-1):
        lasthash = hashlib.sha1(lasthash)
    bytes = hashlib.sha1(lasthash).digest()
    ctrl = 1
    while len(bytes) < keylen:
        bytes += hashlib.sha1(str(ctrl)+lasthash).digest()
        ctrl += 1
    return(bytes[:keylen])


stpass = 'amp4Z0wpKzJ5Cg0GDT5sJD0sMw0IDAsaGQ1Afik6NwXr6rrSEQE='
slt = 'aGQ1Afik6NampDT5sJEQE4Z0wpsMw0IDAD06rrSswXrKzJ5Cg0G='
initv = '@1B2c3D4e5F6g7H8'
enc_str = b64decode('B5YDTLEDBjd+8zy5lzEfjw==')
derbytes = MS_PasswordDeriveBytes(stpass, slt, hashlib.sha1, iterations=2, keylen=32)

标签: pythonc#rijndaelrijndaelmanaged

解决方案


推荐阅读