c++ - CryptDecrypt winapi 函数出错?

标签 c++ cryptoapi

我写了一个简单的程序来加载由 openssl 生成的公钥来解密由公钥的私钥加密的字符串。但我不知道为什么我失败了

b = CryptDecrypt(hKey,NULL,FALSE,0,pbEncrypt,&cbEncrypt);

我收到错误“8009000D NTE_NO_KEY key 不存在。”。有人可以向我解释一下吗?

void DecodeString() 
{

    CHAR* publicKey = 
        "-----BEGIN PUBLIC KEY-----"
        "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAv+yyzdZaqcE7qOOZ8pyN"
        "o1n3PS2U/ewT2gGSQeixP+VixQGrxnssT3zlbeUND8CVX+tZGwkcIZZD09Rkx9vh"
        "z7vLUFD7dngupo/aL6pfehb95citD31DUswc9BTJjQySpSSG6zWDSBJMELDYaCa4"
        "MIU7odoCg2EbQBwRWX7upWiR+shyxnPYklY8ZUpVCtIdHXmPO5eMaI1elftqNw1N"
        "n/Id4pFFif11Lmny3s3ADfItuyMfTwU6jwgsPaoqrX5FCnurlAVl/mcfpMVpsPju"
        "XWw2IlvZP5SkTW4G6V+Bt+xDI6SW3dvMi6gJngHLUKekbhZxcFWuv3hus8ojpo+I"
        "mwIDAQAB"
        "-----END PUBLIC KEY-----";

    BYTE* derPubKey;
    DWORD derPubKeyLen;
    BOOL b = CryptStringToBinaryA(publicKey, 0, CRYPT_STRING_BASE64HEADER, NULL, &derPubKeyLen, NULL, NULL);
    DWORD error = GetLastError();
    _ASSERT(error == 0);
    _ASSERT(b == TRUE);
    derPubKey = new BYTE[derPubKeyLen];
    b = CryptStringToBinaryA(publicKey, 0, CRYPT_STRING_BASE64HEADER, derPubKey, &derPubKeyLen, NULL, NULL);
    error = GetLastError();
    _ASSERT(error == 0);
    _ASSERT(b == TRUE);
    CERT_PUBLIC_KEY_INFO *publicKeyInfo;
    DWORD publicKeyInfoLen;
    HCRYPTPROV hProv = 0;
    HCRYPTKEY hKey = 0;
    b = CryptDecodeObjectEx(X509_ASN_ENCODING, X509_PUBLIC_KEY_INFO, derPubKey, derPubKeyLen, CRYPT_ENCODE_ALLOC_FLAG, NULL, &publicKeyInfo, &publicKeyInfoLen);
    error = GetLastError();
    _ASSERT(error == 0);
    _ASSERT(b == TRUE);
    b = CryptAcquireContext(&hProv, NULL, NULL, PROV_RSA_FULL, CRYPT_VERIFYCONTEXT);
    error = GetLastError();
    _ASSERT(error == 0);
    _ASSERT(b == TRUE);
    b = CryptImportPublicKeyInfo(hProv, X509_ASN_ENCODING, publicKeyInfo, &hKey);
    error = GetLastError();
    _ASSERT(error == 0);
    _ASSERT(b == TRUE);
    //same test decrypt
    CHAR* sameTest = "nJZ6MN6MIrpbLQiRvfLFIHHzneQBe2rucaKSykXeHgf8Zth5FNPZPdiPhWcHq0/K"
        "KgRHv2ON+gPyFbjsdDl2cixPgNGXs1FfI/RvkH+Icn+6rYq5uPBM5oQVriyiWI9/"
        "QiC56LP0ooouqLg9e2U5zJmC/ftCODkFyL748Fx3godXzDl1mNB7bx/Ua6Z93KeB"
        "OgNvYZH3tcZZYlgoX4GVf4ocO0aZ8pQjEB8p9hMWfIDRCIckDAncy21tHDmWDqZ4"
        "H7CZjbdNyaiWe5Cr6+CYs25+r3AdIlXOKWuphgbckKDHh4r7nMX0AX+iHXGjCgkM"
        "iwi4yz7wF+Ow/CcGHkAMTQ==";

    BYTE* pbEncrypt = 0;
    DWORD cbEncrypt = 0;
    b = CryptStringToBinaryA(sameTest, 0, CRYPT_STRING_BASE64, NULL, &cbEncrypt, NULL, NULL);
    error = GetLastError();
    _ASSERT(error == 0);
    _ASSERT(b == TRUE);
    pbEncrypt = new BYTE[cbEncrypt];
    printf("%s\n",(CHAR*)pbEncrypt);
    b = CryptStringToBinaryA(sameTest, 0, CRYPT_STRING_BASE64, pbEncrypt, &cbEncrypt, NULL, NULL);
    error = GetLastError();
    _ASSERT(error == 0);
    _ASSERT(b == TRUE);
    printf("%s\n",(CHAR*)pbEncrypt);
    b = CryptDecrypt(hKey,NULL,FALSE,0,pbEncrypt,&cbEncrypt);
    error = GetLastError();
    _ASSERT(error == 0);
    _ASSERT(b == TRUE);
    printf("%s\n",(CHAR*)pbEncrypt);
}

最佳答案

您不能使用公钥来解密用私钥加密的内容。公钥只能用于加密,而私钥只能用于解密。

来自 Wikipedia :

[...] The distinguishing technique used in public-key cryptography is the use of asymmetric key algorithms, where the key used to encrypt a message is not the same as the key used to decrypt it. Each user has a pair of cryptographic keys - a public encryption key and a private decryption key. The publicly available encrypting-key is widely distributed, while the private decrypting-key is known only to the recipient. Messages are encrypted with the recipient's public key, and can be decrypted only with the corresponding private key.[...]

关于c++ - CryptDecrypt winapi 函数出错?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8272822/

相关文章:

C++ Eigen 只读稀疏 block 子表达式?怎么写?

c++ - 使用 pthreads 优雅地退出主线程

c++ - 此示例中指定的 128 位 AES key 是什么格式?

c++ - 添加 std::pair 和 + 运算符

C++ 析构函数和所有权

c# - 如何抑制 "An application is requesting access to a protected item"弹出窗口

openssl - CryptoAPI:使用 CryptVerifySignature 使用公钥验证来自 openssl 的签名

c++ - 在 Windows 7 上使用 SHA2-512 (CALG_SHA_512) 返回 "Invalid Algorithm Specified"

c++ - 如何使用 CryptoAPI 和 SignerSign 为带有附加证书的 EXE 签名

C++11 等价于 boost shared_mutex