【发布时间】:2015-06-09 21:34:53
【问题描述】:
我有一个只有 RSA 密钥的公共部分的 EVP_PKEY。我从 DER 编码中的 SubjectPublicKeyInfo 结构中提取了公共部分。这就是我现在拥有的:
unsigned char publicKey[] = {0x30, 0x5a, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, ...}
size_t publicKeyLength = 92;
unsigned char* publicKeyCopy = new unsigned char[publicKeyLength];
memcpy(publicKeyCopy, publicKey, publicKeyLength);
RSA *rsa;
rsa = d2i_RSA_PUBKEY(NULL, (unsigned char const **) &pubKey, pubKeyLen);
EVP_PKEY *pkey = EVP_PKEY_new();
EVP_PKEY_assign_RSA(pkey, rsa);
我知道您可以使用 RSA_check_key to verify a RSA private key,但文档说“它不适用于仅填充了模数和公共指数元素的 RSA 公钥”。
那么,是否可以在没有私有部分的情况下验证密钥?因为如您所见,我只有 EVP_PKEY 的公共部分。我想知道,这甚至可能吗?你会在 EVP_PKEY 的公共部分验证什么?
你可以看到这个问题的答案Programmatically verify a X509 certificate and private key match,但是完整的密钥已经过验证(私有和公共部分)。
小心
本题贴出的原代码有BUG。这是因为内部d2i_RSA_PUBKEY 使用d2i_PUBKEY 而d2i_PUBKEY 使用d2i_X509_PUBKEY(在x_pubkey.c 中)。如果您阅读documentation for d2i_X509,您将看到下一个“警告:必须使用临时变量。一个常见的错误是尝试直接使用缓冲区...”。
因此,更正后的代码必须使用publicKeyCopy 的临时副本,使用后您可以安全地删除publicKeyCopy:
【问题讨论】:
-
您发布的内容看起来像(开始)一个 512 位 RSA 公钥。当您说“验证”时,您的意思仅仅是它格式正确吗?还是您的意思是将其建立为特定公共/私人对的“公共”密钥。后者涉及私钥加密的已知值(通常是签名)。澄清您正在验证的具体内容是什么? “公钥”不是答案。 “关于……的公钥”会很有帮助。
-
感谢您的回复。我想知道公钥是否格式正确,将使用此密钥的客户端只知道这是一个公钥,他将使用它来加密一些数据。这是 DER 格式的密钥lapo.it/asn1js/…。