Comparison

util-src/crypto.c @ 13537:fb970df95374

util.crypto: Add more ECC methods pkey_meth_derive: to derive a shared symmetric key from two ECC keys pkey_meth_public_raw: to get the raw form of the public key import_public_ec_raw: to import the raw form of the public key generate_p256_keypair: key generation for the P-256 curve
author Stephen Paul Weber <singpolyma@singpolyma.net>
date Tue, 29 Oct 2024 09:15:50 -0500
parent 12976:a187600ec7d6
comparison
equal deleted inserted replaced
13536:272ea65c3087 13537:fb970df95374
25 #include <openssl/crypto.h> 25 #include <openssl/crypto.h>
26 #include <openssl/ecdsa.h> 26 #include <openssl/ecdsa.h>
27 #include <openssl/err.h> 27 #include <openssl/err.h>
28 #include <openssl/evp.h> 28 #include <openssl/evp.h>
29 #include <openssl/obj_mac.h> 29 #include <openssl/obj_mac.h>
30 #include <openssl/param_build.h>
30 #include <openssl/pem.h> 31 #include <openssl/pem.h>
31 32
32 #if (LUA_VERSION_NUM == 501) 33 #if (LUA_VERSION_NUM == 501)
33 #define luaL_setfuncs(L, R, N) luaL_register(L, NULL, R) 34 #define luaL_setfuncs(L, R, N) luaL_register(L, NULL, R)
34 #endif 35 #endif
90 int key_type = EVP_PKEY_id(pkey); 91 int key_type = EVP_PKEY_id(pkey);
91 lua_pushstring(L, OBJ_nid2sn(key_type)); 92 lua_pushstring(L, OBJ_nid2sn(key_type));
92 return 1; 93 return 1;
93 } 94 }
94 95
96 static int Lpkey_meth_derive(lua_State *L) {
97 size_t outlen;
98 EVP_PKEY *key = pkey_from_arg(L, 1, 0, 0);
99 EVP_PKEY *peer = pkey_from_arg(L, 2, 0, 0);
100 EVP_PKEY_CTX *ctx;
101 BUF_MEM *buf;
102 BIO *bio = new_managed_BIO_s_mem(L);
103 BIO_get_mem_ptr(bio, &buf);
104 if (!(ctx = EVP_PKEY_CTX_new(key, NULL)))
105 goto sslerr;
106 if (EVP_PKEY_derive_init(ctx) <= 0)
107 goto sslerr;
108 if (EVP_PKEY_derive_set_peer(ctx, peer) <= 0)
109 goto sslerr;
110 if (EVP_PKEY_derive(ctx, NULL, &outlen) <= 0)
111 goto sslerr;
112 if (!BUF_MEM_grow_clean(buf, outlen))
113 goto sslerr;
114 if (EVP_PKEY_derive(ctx, (unsigned char*)buf->data, &outlen) <= 0)
115 goto sslerr;
116 EVP_PKEY_CTX_free(ctx);
117 ctx = NULL;
118 lua_pushlstring(L, buf->data, outlen);
119 BIO_reset(bio);
120 return 1;
121 sslerr:
122 if (ctx) {
123 EVP_PKEY_CTX_free(ctx);
124 ctx = NULL;
125 }
126 BIO_reset(bio);
127 return luaL_error(L, "pkey:derive failed");
128 }
129
95 static int base_evp_sign(lua_State *L, const int key_type, const EVP_MD *digest_type) { 130 static int base_evp_sign(lua_State *L, const int key_type, const EVP_MD *digest_type) {
96 EVP_PKEY *pkey = pkey_from_arg(L, 1, (key_type!=NID_rsassaPss)?key_type:NID_rsaEncryption, 1); 131 EVP_PKEY *pkey = pkey_from_arg(L, 1, (key_type!=NID_rsassaPss)?key_type:NID_rsaEncryption, 1);
97 luaL_Buffer sigbuf; 132 luaL_Buffer sigbuf;
98 133
99 size_t msg_len; 134 size_t msg_len;
158 else { 193 else {
159 lua_pushboolean(L, 1); 194 lua_pushboolean(L, 1);
160 } 195 }
161 cleanup: 196 cleanup:
162 EVP_MD_CTX_free(md_ctx); 197 EVP_MD_CTX_free(md_ctx);
198 return 1;
199 }
200
201 static int Lpkey_meth_public_raw(lua_State *L) {
202 OSSL_PARAM *params;
203 EVP_PKEY *pkey = pkey_from_arg(L, 1, 0, 0);
204
205 if (EVP_PKEY_todata(pkey, EVP_PKEY_PUBLIC_KEY, &params)) {
206 OSSL_PARAM *item = params;
207 while (item->key) {
208 if (!strcmp("pub", item->key)) {
209 lua_pushlstring(L, item->data, item->data_size);
210 break;
211 }
212 item++;
213 }
214 if (!item->key) lua_pushnil(L);
215 OSSL_PARAM_free(params);
216 } else {
217 lua_pushnil(L);
218 }
219
163 return 1; 220 return 1;
164 } 221 }
165 222
166 static int Lpkey_meth_public_pem(lua_State *L) { 223 static int Lpkey_meth_public_pem(lua_State *L) {
167 char *data; 224 char *data;
235 292
236 push_pkey(L, pkey, NID_ED25519, 1); 293 push_pkey(L, pkey, NID_ED25519, 1);
237 return 1; 294 return 1;
238 } 295 }
239 296
297 static int Lgenerate_p256_keypair(lua_State *L) {
298 EVP_PKEY *pkey = NULL;
299 EVP_PKEY_CTX *pctx = EVP_PKEY_CTX_new_id(EVP_PKEY_EC, NULL);
300
301 /* Generate key */
302 if (EVP_PKEY_keygen_init(pctx) <= 0) goto err;
303 if (EVP_PKEY_CTX_set_ec_paramgen_curve_nid(pctx, NID_X9_62_prime256v1) <= 0) goto err;
304 if (EVP_PKEY_keygen(pctx, &pkey) <= 0) goto err;
305 EVP_PKEY_CTX_free(pctx);
306
307 push_pkey(L, pkey, NID_X9_62_prime256v1, 1);
308 return 1;
309
310 err:
311 if (pctx) EVP_PKEY_CTX_free(pctx);
312 lua_pushnil(L);
313 return 1;
314 }
315
240 static int Limport_private_pem(lua_State *L) { 316 static int Limport_private_pem(lua_State *L) {
241 EVP_PKEY *pkey = NULL; 317 EVP_PKEY *pkey = NULL;
242 318
243 size_t privkey_bytes; 319 size_t privkey_bytes;
244 const char* privkey_data; 320 const char* privkey_data;
252 } 328 }
253 else { 329 else {
254 lua_pushnil(L); 330 lua_pushnil(L);
255 } 331 }
256 332
333 return 1;
334 }
335
336 static int Limport_public_ec_raw(lua_State *L) {
337 OSSL_PARAM_BLD *param_bld = NULL;
338 OSSL_PARAM *params = NULL;
339 EVP_PKEY_CTX *ctx = NULL;
340 EVP_PKEY *pkey = NULL;
341
342 size_t pubkey_bytes;
343 const char* pubkey_data = luaL_checklstring(L, 1, &pubkey_bytes);
344 const char* curve = luaL_checkstring(L, 2);
345
346 param_bld = OSSL_PARAM_BLD_new();
347 if (!param_bld) goto err;
348 if (!OSSL_PARAM_BLD_push_utf8_string(param_bld, "group", curve, 0)) goto err;
349 if (!OSSL_PARAM_BLD_push_octet_string(param_bld, "pub", pubkey_data, pubkey_bytes)) goto err;
350 params = OSSL_PARAM_BLD_to_param(param_bld);
351 if (!params) goto err;
352 ctx = EVP_PKEY_CTX_new_from_name(NULL, "EC", NULL);
353 if (!ctx) goto err;
354 if (!EVP_PKEY_fromdata_init(ctx)) goto err;
355 if (EVP_PKEY_fromdata(ctx, &pkey, EVP_PKEY_PUBLIC_KEY, params) <= 0) goto err;
356
357 push_pkey(L, pkey, EVP_PKEY_id(pkey), 0);
358
359 EVP_PKEY_CTX_free(ctx);
360 OSSL_PARAM_free(params);
361 OSSL_PARAM_BLD_free(param_bld);
362
363 return 1;
364 err:
365 if (ctx) EVP_PKEY_CTX_free(ctx);
366 if (params) OSSL_PARAM_free(params);
367 if (param_bld) OSSL_PARAM_BLD_free(param_bld);
368 lua_pushnil(L);
257 return 1; 369 return 1;
258 } 370 }
259 371
260 static int Limport_public_pem(lua_State *L) { 372 static int Limport_public_pem(lua_State *L) {
261 EVP_PKEY *pkey = NULL; 373 EVP_PKEY *pkey = NULL;
569 681
570 { "aes_256_ctr_encrypt", Laes_256_ctr_encrypt }, 682 { "aes_256_ctr_encrypt", Laes_256_ctr_encrypt },
571 { "aes_256_ctr_decrypt", Laes_256_ctr_decrypt }, 683 { "aes_256_ctr_decrypt", Laes_256_ctr_decrypt },
572 684
573 { "generate_ed25519_keypair", Lgenerate_ed25519_keypair }, 685 { "generate_ed25519_keypair", Lgenerate_ed25519_keypair },
686 { "generate_p256_keypair", Lgenerate_p256_keypair },
574 687
575 { "import_private_pem", Limport_private_pem }, 688 { "import_private_pem", Limport_private_pem },
576 { "import_public_pem", Limport_public_pem }, 689 { "import_public_pem", Limport_public_pem },
690 { "import_public_ec_raw", Limport_public_ec_raw },
577 691
578 { "parse_ecdsa_signature", Lparse_ecdsa_signature }, 692 { "parse_ecdsa_signature", Lparse_ecdsa_signature },
579 { "build_ecdsa_signature", Lbuild_ecdsa_signature }, 693 { "build_ecdsa_signature", Lbuild_ecdsa_signature },
580 { NULL, NULL } 694 { NULL, NULL }
581 }; 695 };
582 696
583 static const luaL_Reg KeyMethods[] = { 697 static const luaL_Reg KeyMethods[] = {
584 { "private_pem", Lpkey_meth_private_pem }, 698 { "private_pem", Lpkey_meth_private_pem },
585 { "public_pem", Lpkey_meth_public_pem }, 699 { "public_pem", Lpkey_meth_public_pem },
700 { "public_raw", Lpkey_meth_public_raw },
586 { "get_type", Lpkey_meth_get_type }, 701 { "get_type", Lpkey_meth_get_type },
702 { "derive", Lpkey_meth_derive },
587 { NULL, NULL } 703 { NULL, NULL }
588 }; 704 };
589 705
590 static const luaL_Reg KeyMetatable[] = { 706 static const luaL_Reg KeyMetatable[] = {
591 { "__gc", Lpkey_finalizer }, 707 { "__gc", Lpkey_finalizer },