吾爱破解 - 52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 582|回复: 3
收起左侧

[求助] 怎么使用win CNG API AES算法解密

[复制链接]
pananning 发表于 2024-4-23 04:34
python代码如下
[Asm] 纯文本查看 复制代码
keys = AES.new(dg.digest(), AES.MODE_ECB).decrypt(lsakey[60:])

[Asm] 纯文本查看 复制代码
#include <Windows.h>
#include <bcrypt.h>
#include <stdio.h>

#define NT_SUCCESS(Status) (((NTSTATUS)(Status)) >= 0)

void PrintHex(const BYTE* data, DWORD dataSize);

int main() {
    BCRYPT_ALG_HANDLE hAlgorithm = NULL;
    BCRYPT_KEY_HANDLE hKey = NULL;
    NTSTATUS status;

    BYTE syskey[] = { /* your syskey bytes here */ };
    BYTE lsakey[] = { /* your lsakey bytes here */ };
    BYTE aesKey[32];  // AES-256 密钥大小为 32 字节

    // 打开 AES 加密提供程序
    status = BCryptOpenAlgorithmProvider(&hAlgorithm, BCRYPT_AES_ALGORITHM, NULL, 0);
    if (!NT_SUCCESS(status)) {
        printf("BCryptOpenAlgorithmProvider failed with status: 0x%x\n", status);
        return 1;
    }

    // 设置密钥对象
    status = BCryptGenerateSymmetricKey(hAlgorithm, &hKey, NULL, 0, syskey, sizeof(syskey), 0);
    if (!NT_SUCCESS(status)) {
        printf("BCryptGenerateSymmetricKey failed with status: 0x%x\n", status);
        BCryptCloseAlgorithmProvider(hAlgorithm, 0);
        return 1;
    }

    // 解密 lsakey[60:] 使用 ECB 模式
    BYTE decryptedKey[32];  // 解密后的密钥大小为 32 字节
    status = BCryptDecrypt(hKey, lsakey + 60, 32, NULL, NULL, 0, decryptedKey, sizeof(decryptedKey), NULL, 0);
    if (!NT_SUCCESS(status)) {
        printf("BCryptDecrypt failed with status: 0x%x\n", status);
    } else {
        printf("Decrypted key:\n");
        PrintHex(decryptedKey, sizeof(decryptedKey));
    }

    // 清理资源
    BCryptDestroyKey(hKey);
    BCryptCloseAlgorithmProvider(hAlgorithm, 0);

    return 0;
}

void PrintHex(const BYTE* data, DWORD dataSize) {
    for (DWORD i = 0; i < dataSize; ++i) {
        printf("%02x", data[i]);
    }
    printf("\n");
}

虽然运行没出错,但结果不一样,求大佬把这个python代码改成c++

免费评分

参与人数 1吾爱币 +1 热心值 +1 收起 理由
为之奈何? + 1 + 1 我很赞同!

查看全部评分

发帖前要善用论坛搜索功能,那里可能会有你要找的答案或者已经有人发布过相同内容了,请勿重复发帖。

508 发表于 2024-4-23 06:19
Python代码用于AES解密,使用`Crypto.Cipher.AES`模块。我将提供一个简化的C++实现,这个实现使用Windows的加密API,类似于你提供的C++代码示例。

你的Python代码似乎是从中间开始的,可能缺失了一些关键的初始化部分。但是,我会假设`dg.digest()`返回一个256位(32字节)的AES密钥,并且你已经有了一个名为`lsakey`的数据数组,你想从第60字节开始解密剩余部分。

下面是一个改写的C++版本,它模拟了你描述的Python代码的行为:

```cpp
#include <Windows.h>
#include <bcrypt.h>
#include <stdio.h>

#define NT_SUCCESS(Status) (((NTSTATUS)(Status)) >= 0)

void PrintHex(const BYTE* data, DWORD dataSize);

int main() {
    BCRYPT_ALG_HANDLE hAlgorithm = NULL;
    BCRYPT_KEY_HANDLE hKey = NULL;
    NTSTATUS status;

    // 假设 dg.digest() 的结果存储在 aesKey 中,这应是32字节的密钥
    BYTE aesKey[32] = { /* 从 dg.digest() 得到的 AES-256 密钥数据 */ };
    BYTE lsakey[92] = { /* 包含密文和可能的其他数据,确保总长度至少为 92 字节 */ };

    // 打开 AES 加密提供程序
    status = BCryptOpenAlgorithmProvider(&hAlgorithm, BCRYPT_AES_ALGORITHM, NULL, 0);
    if (!NT_SUCCESS(status)) {
        printf("BCryptOpenAlgorithmProvider failed with status: 0x%x\n", status);
        return 1;
    }

    // 设置密钥对象
    status = BCryptGenerateSymmetricKey(hAlgorithm, &hKey, NULL, 0, aesKey, sizeof(aesKey), 0);
    if (!NT_SUCCESS(status)) {
        printf("BCryptGenerateSymmetricKey failed with status: 0x%x\n", status);
        BCryptCloseAlgorithmProvider(hAlgorithm, 0);
        return 1;
    }

    // 解密 lsakey[60:] 使用 ECB 模式
    BYTE decryptedData[32]; // 根据你的需求调整大小
    DWORD decryptedDataSize = sizeof(decryptedData);
    status = BCryptDecrypt(hKey, lsakey + 60, 32, NULL, NULL, 0, decryptedData, decryptedDataSize, &decryptedDataSize, 0);
    if (!NT_SUCCESS(status)) {
        printf("BCryptDecrypt failed with status: 0x%x\n", status);
    } else {
        printf("Decrypted data:\n");
        PrintHex(decryptedData, decryptedDataSize);
    }

    // 清理资源
    BCryptDestroyKey(hKey);
    BCryptCloseAlgorithmProvider(hAlgorithm, 0);

    return 0;
}

void PrintHex(const BYTE* data, DWORD dataSize) {
    for (DWORD i = 0; i < dataSize; ++i) {
        printf("%02x", data[i]);
    }
    printf("\n");
}
```

请注意,你需要将`aesKey`数组填充为正确的值,即从`dg.digest()`函数得到的值,此函数在你的原始Python代码中被调用。此外,确保`lsakey`数组足够大,可以包含至少92字节的数据(60字节偏移加32字节解密数据)。这个示例假设你解密的数据是32字节长,这通常对应于AES-256加密块的大小。根据你的具体需求调整大小和参数。
tyq2003 发表于 2024-4-23 08:10
cfnm123 发表于 2024-5-14 17:57
[Asm] 纯文本查看 复制代码
#include <Windows.h>
#include <bcrypt.h>
#include <iostream>
#include <vector>

#pragma comment(lib, "bcrypt.lib")

void PrintHex(const BYTE* data, DWORD dataSize);

int main() {
    BCRYPT_ALG_HANDLE hAlgorithm = NULL;
    BCRYPT_KEY_HANDLE hKey = NULL;
    NTSTATUS status;

    std::vector<BYTE> syskey = {/* your syskey bytes here, ensure it's the same length as in Python code */};
    std::vector<BYTE> lsakey = {/* your lsakey bytes here */};
    std::vector<BYTE> decryptedKey(32);  // AES-256, key size is 32 bytes

    // Open the AES algorithm provider
    status = BCryptOpenAlgorithmProvider(&hAlgorithm, BCRYPT_AES_ALGORITHM, NULL, 0);
    if (!NT_SUCCESS(status)) {
        std::cerr << "BCryptOpenAlgorithmProvider failed with status: 0x" << std::hex << status << std::endl;
        return 1;
    }

    // Import the key - assuming syskey is already the correct key derived similarly to dg.digest()
    status = BCryptGenerateSymmetricKey(hAlgorithm, &hKey, NULL, 0, syskey.data(), syskey.size(), 0);
    if (!NT_SUCCESS(status)) {
        std::cerr << "BCryptGenerateSymmetricKey failed with status: 0x" << std::hex << status << std::endl;
        BCryptCloseAlgorithmProvider(hAlgorithm, 0);
        return 1;
    }

    // Decrypt lsakey[60:] using ECB mode
    DWORD decryptedSize = 0;
    status = BCryptDecrypt(hKey, lsakey.data() + 60, 32, NULL, NULL, 0, decryptedKey.data(), decryptedKey.size(), &decryptedSize, BCRYPT_BLOCK_PADDING);
    if (!NT_SUCCESS(status)) {
        std::cerr << "BCryptDecrypt failed with status: 0x" << std::hex << status << std::endl;
    } else {
        std::cout << "Decrypted key:" << std::endl;
        PrintHex(decryptedKey.data(), decryptedSize);
    }

    // Clean up
    BCryptDestroyKey(hKey);
    BCryptCloseAlgorithmProvider(hAlgorithm, 0);

    return 0;
}

void PrintHex(const BYTE* data, DWORD dataSize) {
    for (DWORD i = 0; i < dataSize; ++i) {
        std::cout << std::hex << std::setw(2) << std::setfill('0') << static_cast<int>(data[i]);
    }
    std::cout << std::endl;
}
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则

返回列表

RSS订阅|小黑屋|处罚记录|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2024-11-24 14:28

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表