OpenSSL 3.x.x
将公钥序列化的方法如下:
size_t serializedPublicKeyLen = 0;
if (EVP_PKEY_get_octet_string_param(keyPair, OSSL_PKEY_PARAM_PUB_KEY,
NULL, 0, &serializedPublicKeyLen) != 1) {
return;
}
unsigned char* serializedPublicKey = (unsigned char*)OPENSSL_malloc(serializedPublicKeyLen);
if (serializedPublicKey == NULL) {
return;
}
if (EVP_PKEY_get_octet_string_param(keyPair, OSSL_PKEY_PARAM_PUB_KEY,
serializedPublicKey, serializedPublicKeyLen, &serializedPublicKeyLen) != 1) {
return;
}
OPENSSL_free(serializedPublicKey);
将公钥反序列化:
OSSL_PARAM_BLD* paramBuild = OSSL_PARAM_BLD_new();
if (paramBuild == NULL) {
return;
}
const char curveName[] = "secp384r1";
if (OSSL_PARAM_BLD_push_utf8_string(paramBuild,
OSSL_PKEY_PARAM_GROUP_NAME, curveName, 0) != 1) {
OSSL_PARAM_BLD_free(paramBuild);
return;
}
if (OSSL_PARAM_BLD_push_octet_string(paramBuild, OSSL_PKEY_PARAM_PUB_KEY,
serializedPublicKey, serializedPublicKeyLen) != 1) {
OSSL_PARAM_BLD_free(paramBuild);
return;
}
OSSL_PARAM* params = OSSL_PARAM_BLD_to_param(paramBuild);
if (params == NULL) {
OSSL_PARAM_BLD_free(paramBuild);
return;
}
EVP_PKEY_CTX* publicKeyCtx = EVP_PKEY_CTX_new_from_name(NULL, "EC", NULL);
if (publicKeyCtx == NULL) {
OSSL_PARAM_BLD_free(paramBuild);
OSSL_PARAM_free(params);
return;
}
if (EVP_PKEY_fromdata_init(publicKeyCtx) <= 0) {
OSSL_PARAM_BLD_free(paramBuild);
OSSL_PARAM_free(params);
EVP_PKEY_CTX_free(publicKeyCtx);
return;
}
EVP_PKEY* publicKey = NULL;
if (EVP_PKEY_fromdata(publicKeyCtx, &publicKey,
EVP_PKEY_PUBLIC_KEY, params) <= 0) {
OSSL_PARAM_BLD_free(paramBuild);
OSSL_PARAM_free(params);
EVP_PKEY_CTX_free(publicKeyCtx);
return;
}
OSSL_PARAM_BLD_free(paramBuild);
OSSL_PARAM_free(params);
EVP_PKEY_CTX_free(publicKeyCtx);
一个完整的C++
OpenSSL 3示例:
ec-diffie-hellman-openssl.h,
ec-diffie-hellman-openssl.cpp。
一个完整的C++
LibreSSL 3/OpenSSL 1示例:
ec-diffie-hellman-libressl.h,
ec-diffie-hellman-libressl.cpp。
要序列化私钥,你需要获取BIGNUM:
BIGNUM* privateKey = NULL;
EVP_PKEY_get_bn_param(keyPair, OSSL_PKEY_PARAM_PRIV_KEY, &privateKey);
然后,您可以使用其中一个BIGNUM序列化函数:
https://www.openssl.org/docs/man3.0/man3/BN_bn2bin.html
为了反序列化私钥,您可以使用上面链接中的一个BIGNUM反序列化函数,然后通过OSSL_PARAM_BLD_push_BN将其推送到使用OSSL_PKEY_PARAM_PRIV_KEY参数构建的参数中。