openssl 实现ECDH-X25519密钥交换流程

X25519 不能使用EC_KEY接口

X25519和其他的ECC不同,在openssl,没有实现EC_KEY 相关接口,所以
EC_KEY_set_private_key
EC_KEY_new_by_curve_name
EC_KEY_get0_group
这些接口对 X25519是不通的。
openssl 中,X25519被实现为一个独立的算法,并且不是建立在EC库之上,即在EVP_PKEY中的某个地方没有包含X25519的EC_KEY。同样,您将永远无法从X25519 nid创建EC_KEY,因为这毫无意义:EC库不知道如何处理曲线25519,因此无法为其创建EC_KEY。

X25519 Openssl接口实现源码

#include <openssl/evp.h>
#include <openssl/ec.h>
#include <openssl/ossl_typ.h>
#include <openssl/bn.h>
#include <openssl/err.h>
#include <openssl/crypto.h>
#include <openssl/obj_mac.h>
#include <openssl/asn1.h>
#include <openssl/asn1t.h>

#include <stdio.h>

unsigned char pub_data [1000] ={
    0x6b,0xfa,0x30,0x2f,0x99,0x73,0xd1,0xe6,0xec,0xa2,0x42,0xdd,0x65,0xe4,0x57,0x38,0xf8,0x53,0x9e,0xfe,0x75,0xeb,0x42,0x4e,0x91,0xa8,0x48,0x27,0x59,0xdc,0xf7,0x32
};
unsigned char priv_data [1000] ={
0x67, 0xc6, 0x69, 0x73, 0x51, 0xff, 0x4a, 0xec, 0x29, 0xcd, 0xba, 0xab, 0xf2, 0xfb, 0xe3, 0x46, 0x7c, 0xc2, 0x54, 0xf8, 0x1b, 0xe8, 0xe7, 0x8d, 0x76, 0x5a, 0x2e, 0x63, 0x33, 0x9f, 0xc9, 0x9a

};

void dump_hex(const char *str, unsigned char *hex_data, int len) {
    int i = 0;
    printf("hex len %d\n",len);
    printf("%s", str);
    for (i = 0; i < len; i++) {
        if (i % 16 == 0) printf("\n");
        printf("0x%02x, ", hex_data[i]);
    }
    printf("\n");
}

int main(int argc, const char *argv[])
{   
    unsigned char out[100] = {0};
    EVP_PKEY_CTX *ctx;
    EVP_PKEY_CTX *dctx;
    EVP_PKEY *pkey= NULL;
    EVP_PKEY *pub= NULL;
    pub = EVP_PKEY_new();

    ctx = EVP_PKEY_CTX_new_id(NID_X25519, NULL);
    EVP_PKEY_keygen_init(ctx);
    EVP_PKEY_keygen(ctx, &pkey);


    dctx = EVP_PKEY_CTX_new(pkey,0);
    
    //初始化密钥交换
    int er=EVP_PKEY_derive_init(dctx);
    if (er != 1)
    {
        EVP_PKEY_CTX_free(dctx);
        ERR_print_errors_fp(stderr);
        return 0;
    }

    EVP_PKEY_copy_parameters(pub, pkey);
    EVP_PKEY_set1_tls_encodedpoint(pub, pub_data, 32);

#if 1
    unsigned char tmp[1000] = {0};
    size_t tmp_len = 1000;
//    EVP_PKEY_get_raw_private_key(pkey, tmp, &tmp_len);
 //   dump_hex("pri",tmp, tmp_len);
    tmp_len = 1000;
    EVP_PKEY_get_raw_public_key(pkey, tmp ,&tmp_len);
    dump_hex("pub",tmp, tmp_len);
    tmp_len = 1000;
    EVP_PKEY_get_raw_public_key(pub, tmp ,&tmp_len);
    dump_hex("cli pub",tmp, tmp_len);
#endif

    //设定对方公钥                bG  和私钥a
    int re=EVP_PKEY_derive_set_peer(dctx, pub);
    if (re != 1)
    {
        EVP_PKEY_CTX_free(dctx);
        ERR_print_errors_fp(stderr);
        return 0;
    }
    //开始计算
    size_t outsize = 1024;
    re=EVP_PKEY_derive(dctx, out, &outsize);
    if (re != 1)
    {
        EVP_PKEY_CTX_free(dctx);
        ERR_print_errors_fp(stderr);
        return 0;
    }
    dump_hex("share key:",out,outsize);
    
    EVP_PKEY_CTX_free(dctx);
    EVP_PKEY_CTX_free(ctx);
    
    return 0;
}
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

viqjeee

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值