openssl3.2 - exp - generate ecc priv key
概述
前面实验已经将ECC加解密的流程用openssl命令模拟出来了.
现在开始将ECC加解密流程中的知识点从openssl.exe源码中迁移到自己工程.
先迁移了一个命令如下
openssl ecparam -name sect571r1 -genkey -noout -out priv_key_s.pem
封装了一个函数, 产生ecc密钥到buffer, 好使.
笔记
/*!
* \file exp020_ecc_gen_priv_key.cpp
* \note openssl3.2 - exp - generate ecc priv key
产生ECC私钥
单步调试, 移植openssl命令行的实现
openssl ecparam -name sect571r1 -genkey -noout -out priv_key_s.pem
*/
#include "my_openSSL_lib.h"
#include <openssl/crypto.h>
#include <openssl/bio.h>
#include <openssl/params.h>
#include <openssl/core_names.h>
#include <openssl/evp.h>
#include <openssl/encoder.h>
#include <stdlib.h>
#include <stdio.h>
#include <assert.h>
#include "CMemHookRec.h"
void my_openssl_app();
bool my_ecc_gen_priv_key(const char* keytype, const char* curve_name, const char* out_format, unsigned char*& pdata, size_t& data_len);
int main(int argc, char** argv)
{
setvbuf(stdout, NULL, _IONBF, 0); // 清掉stdout缓存, 防止调用printf时阻塞
mem_hook();
my_openssl_app();
mem_unhook();
/*! run result
ec priv key:
0000 - 2d 2d 2d 2d 2d 42 45 47-49 4e 20 45 43 20 50 52 -----BEGIN EC PR
0010 - 49 56 41 54 45 20 4b 45-59 2d 2d 2d 2d 2d 0a 4d IVATE KEY-----.M
0020 - 49 48 75 41 67 45 42 42-45 67 43 53 4d 2f 56 6a IHuAgEBBEgCSM/Vj
// ...
0160 - 2b 31 64 0a 58 41 3d 3d-0a 2d 2d 2d 2d 2d 45 4e +1d.XA==.-----EN
0170 - 44 20 45 43 20 50 52 49-56 41 54 45 20 4b 45 59 D EC PRIVATE KEY
0180 - 2d 2d 2d 2d 2d 0a -----.
free map, g_mem_hook_map.size() = 0
*/
return 0;
}
void my_openssl_app()
{
bool b_rc = false;
unsigned char* pdata = NULL;
size_t data_len = 0;
b_rc = my_ecc_gen_priv_key("ec", "sect571r1", "PEM", pdata, data_len);
assert(b_rc);
printf("ec priv key:\n");
BIO_dump_fp(stdout, pdata, data_len);
if (NULL != pdata)
{
OPENSSL_free(pdata);
pdata = NULL;
}
}
bool my_ecc_gen_priv_key(const char* keytype, const char* curve_name, const char* out_format, unsigned char*& pdata, size_t& data_len)
{
// openssl ecparam -name sect571r1 -genkey -noout -out priv_key_s.pem
bool b_rc = false;
OSSL_PARAM _ossl_param_ary[2];
EVP_PKEY_CTX* _evp_pkey_ctx_key_type = NULL;
EVP_PKEY* _evp_pkey_key_type = NULL;
EVP_PKEY_CTX* _evp_pkey_ctx_key = NULL;
OSSL_ENCODER_CTX* _ossl_encoder_ctx = NULL;
OSSL_LIB_CTX* _ossl_lib_ctx = NULL;
EVP_PKEY* _evp_pkey = NULL;
do {
_ossl_lib_ctx = OSSL_LIB_CTX_new();
if (NULL == _ossl_lib_ctx)
{
break;
}
_evp_pkey_ctx_key_type = EVP_PKEY_CTX_new_from_name(_ossl_lib_ctx, keytype, NULL);
if (NULL == _evp_pkey_ctx_key_type)
{
break;
}
if (EVP_PKEY_keygen_init(_evp_pkey_ctx_key_type) <= 0)
{
break;
}
_ossl_param_ary[0] = OSSL_PARAM_construct_utf8_string(OSSL_PKEY_PARAM_GROUP_NAME, (char*)curve_name, 0);
_ossl_param_ary[1] = OSSL_PARAM_construct_end();
if (EVP_PKEY_CTX_set_params(_evp_pkey_ctx_key_type, _ossl_param_ary) <= 0)
{
break;
}
if (EVP_PKEY_keygen(_evp_pkey_ctx_key_type, &_evp_pkey_key_type) <= 0)
{
break;
}
_evp_pkey_ctx_key = EVP_PKEY_CTX_new_from_pkey(_ossl_lib_ctx, _evp_pkey_key_type, NULL);
if (NULL == _evp_pkey_ctx_key)
{
break;
}
if (EVP_PKEY_keygen_init(_evp_pkey_ctx_key) <= 0)
{
break;
}
if (EVP_PKEY_keygen(_evp_pkey_ctx_key, &_evp_pkey) <= 0)
{
break;
}
_ossl_encoder_ctx = OSSL_ENCODER_CTX_new_for_pkey(_evp_pkey, OSSL_KEYMGMT_SELECT_ALL, out_format, NULL, NULL);
if (NULL == _ossl_encoder_ctx)
{
break;
}
/*
int OSSL_ENCODER_to_data(OSSL_ENCODER_CTX *ctx, unsigned char **pdata, size_t *pdata_len);
, unsigned char*& pdata, size_t& data_len*/
if (1 != OSSL_ENCODER_to_data(_ossl_encoder_ctx, &pdata, &data_len))
{
break;
}
b_rc = true;
} while (false);
if (NULL != _ossl_encoder_ctx)
{
OSSL_ENCODER_CTX_free(_ossl_encoder_ctx);
_ossl_encoder_ctx = NULL;
}
if (NULL != _evp_pkey)
{
EVP_PKEY_free(_evp_pkey);
_evp_pkey = NULL;
}
if (NULL != _evp_pkey_key_type)
{
EVP_PKEY_free(_evp_pkey_key_type);
}
if (NULL != _evp_pkey_ctx_key_type)
{
EVP_PKEY_CTX_free(_evp_pkey_ctx_key_type);
_evp_pkey_ctx_key_type = NULL;
}
if (NULL != _evp_pkey_ctx_key)
{
EVP_PKEY_CTX_free(_evp_pkey_ctx_key);
_evp_pkey_ctx_key = NULL;
}
if (NULL != _ossl_lib_ctx)
{
OSSL_LIB_CTX_free(_ossl_lib_ctx);
_ossl_lib_ctx = NULL;
}
return b_rc;
}
备注
在网上查的资料, 大概只能参考一下思路. 想找和自己想的一模一样的东西基本不可能.
还是有了思路, 自己从官方实现(权威, 质量有保证)中移植(扒代码)爽.