xref: /openssl/crypto/evp/p_lib.c (revision f83707dc)
1 /*
2  * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved.
3  *
4  * Licensed under the Apache License 2.0 (the "License").  You may not use
5  * this file except in compliance with the License.  You can obtain a copy
6  * in the file LICENSE in the source distribution or at
7  * https://www.openssl.org/source/license.html
8  */
9 
10 /*
11  * DSA low level APIs are deprecated for public use, but still ok for
12  * internal use.
13  */
14 #include "internal/deprecated.h"
15 
16 #include <assert.h>
17 #include <stdio.h>
18 #include "internal/cryptlib.h"
19 #include "internal/refcount.h"
20 #include "internal/namemap.h"
21 #include <openssl/bn.h>
22 #include <openssl/err.h>
23 #include <openssl/objects.h>
24 #include <openssl/evp.h>
25 #include <openssl/rsa.h>
26 #include <openssl/dsa.h>
27 #include <openssl/dh.h>
28 #include <openssl/ec.h>
29 #include <openssl/cmac.h>
30 #ifndef FIPS_MODULE
31 # include <openssl/engine.h>
32 #endif
33 #include <openssl/params.h>
34 #include <openssl/param_build.h>
35 #include <openssl/encoder.h>
36 #include <openssl/core_names.h>
37 
38 #include "internal/numbers.h"   /* includes SIZE_MAX */
39 #include "internal/ffc.h"
40 #include "crypto/evp.h"
41 #include "crypto/dh.h"
42 #include "crypto/dsa.h"
43 #include "crypto/ec.h"
44 #include "crypto/ecx.h"
45 #include "crypto/rsa.h"
46 #ifndef FIPS_MODULE
47 # include "crypto/asn1.h"
48 # include "crypto/x509.h"
49 #endif
50 #include "internal/provider.h"
51 #include "evp_local.h"
52 
53 static int pkey_set_type(EVP_PKEY *pkey, ENGINE *e, int type, const char *str,
54                          int len, EVP_KEYMGMT *keymgmt);
55 static void evp_pkey_free_it(EVP_PKEY *key);
56 
57 #ifndef FIPS_MODULE
58 
59 /* The type of parameters selected in key parameter functions */
60 # define SELECT_PARAMETERS OSSL_KEYMGMT_SELECT_DOMAIN_PARAMETERS
61 
EVP_PKEY_get_bits(const EVP_PKEY * pkey)62 int EVP_PKEY_get_bits(const EVP_PKEY *pkey)
63 {
64     int size = 0;
65 
66     if (pkey != NULL) {
67         size = pkey->cache.bits;
68         if (pkey->ameth != NULL && pkey->ameth->pkey_bits != NULL)
69             size = pkey->ameth->pkey_bits(pkey);
70     }
71     if (size <= 0) {
72         ERR_raise(ERR_LIB_EVP, EVP_R_UNKNOWN_BITS);
73         return 0;
74     }
75     return size;
76 }
77 
EVP_PKEY_get_security_bits(const EVP_PKEY * pkey)78 int EVP_PKEY_get_security_bits(const EVP_PKEY *pkey)
79 {
80     int size = 0;
81 
82     if (pkey != NULL) {
83         size = pkey->cache.security_bits;
84         if (pkey->ameth != NULL && pkey->ameth->pkey_security_bits != NULL)
85             size = pkey->ameth->pkey_security_bits(pkey);
86     }
87     if (size <= 0) {
88         ERR_raise(ERR_LIB_EVP, EVP_R_UNKNOWN_SECURITY_BITS);
89         return 0;
90     }
91     return size;
92 }
93 
EVP_PKEY_save_parameters(EVP_PKEY * pkey,int mode)94 int EVP_PKEY_save_parameters(EVP_PKEY *pkey, int mode)
95 {
96 # ifndef OPENSSL_NO_DSA
97     if (pkey->type == EVP_PKEY_DSA) {
98         int ret = pkey->save_parameters;
99 
100         if (mode >= 0)
101             pkey->save_parameters = mode;
102         return ret;
103     }
104 # endif
105 # ifndef OPENSSL_NO_EC
106     if (pkey->type == EVP_PKEY_EC) {
107         int ret = pkey->save_parameters;
108 
109         if (mode >= 0)
110             pkey->save_parameters = mode;
111         return ret;
112     }
113 # endif
114     return 0;
115 }
116 
EVP_PKEY_set_ex_data(EVP_PKEY * key,int idx,void * arg)117 int EVP_PKEY_set_ex_data(EVP_PKEY *key, int idx, void *arg)
118 {
119     return CRYPTO_set_ex_data(&key->ex_data, idx, arg);
120 }
121 
EVP_PKEY_get_ex_data(const EVP_PKEY * key,int idx)122 void *EVP_PKEY_get_ex_data(const EVP_PKEY *key, int idx)
123 {
124     return CRYPTO_get_ex_data(&key->ex_data, idx);
125 }
126 
EVP_PKEY_copy_parameters(EVP_PKEY * to,const EVP_PKEY * from)127 int EVP_PKEY_copy_parameters(EVP_PKEY *to, const EVP_PKEY *from)
128 {
129     /*
130      * Clean up legacy stuff from this function when legacy support is gone.
131      */
132 
133     EVP_PKEY *downgraded_from = NULL;
134     int ok = 0;
135 
136     /*
137      * If |to| is a legacy key and |from| isn't, we must make a downgraded
138      * copy of |from|.  If that fails, this function fails.
139      */
140     if (evp_pkey_is_legacy(to) && evp_pkey_is_provided(from)) {
141         if (!evp_pkey_copy_downgraded(&downgraded_from, from))
142             goto end;
143         from = downgraded_from;
144     }
145 
146     /*
147      * Make sure |to| is typed.  Content is less important at this early
148      * stage.
149      *
150      * 1.  If |to| is untyped, assign |from|'s key type to it.
151      * 2.  If |to| contains a legacy key, compare its |type| to |from|'s.
152      *     (|from| was already downgraded above)
153      *
154      * If |to| is a provided key, there's nothing more to do here, functions
155      * like evp_keymgmt_util_copy() and evp_pkey_export_to_provider() called
156      * further down help us find out if they are the same or not.
157      */
158     if (evp_pkey_is_blank(to)) {
159         if (evp_pkey_is_legacy(from)) {
160             if (EVP_PKEY_set_type(to, from->type) == 0)
161                 goto end;
162         } else {
163             if (EVP_PKEY_set_type_by_keymgmt(to, from->keymgmt) == 0)
164                 goto end;
165         }
166     } else if (evp_pkey_is_legacy(to)) {
167         if (to->type != from->type) {
168             ERR_raise(ERR_LIB_EVP, EVP_R_DIFFERENT_KEY_TYPES);
169             goto end;
170         }
171     }
172 
173     if (EVP_PKEY_missing_parameters(from)) {
174         ERR_raise(ERR_LIB_EVP, EVP_R_MISSING_PARAMETERS);
175         goto end;
176     }
177 
178     if (!EVP_PKEY_missing_parameters(to)) {
179         if (EVP_PKEY_parameters_eq(to, from) == 1)
180             ok = 1;
181         else
182             ERR_raise(ERR_LIB_EVP, EVP_R_DIFFERENT_PARAMETERS);
183         goto end;
184     }
185 
186     /* For purely provided keys, we just call the keymgmt utility */
187     if (to->keymgmt != NULL && from->keymgmt != NULL) {
188         ok = evp_keymgmt_util_copy(to, (EVP_PKEY *)from, SELECT_PARAMETERS);
189         goto end;
190     }
191 
192     /*
193      * If |to| is provided, we know that |from| is legacy at this point.
194      * Try exporting |from| to |to|'s keymgmt, then use evp_keymgmt_dup()
195      * to copy the appropriate data to |to|'s keydata.
196      * We cannot override existing data so do it only if there is no keydata
197      * in |to| yet.
198      */
199     if (to->keymgmt != NULL && to->keydata == NULL) {
200         EVP_KEYMGMT *to_keymgmt = to->keymgmt;
201         void *from_keydata =
202             evp_pkey_export_to_provider((EVP_PKEY *)from, NULL, &to_keymgmt,
203                                         NULL);
204 
205         /*
206          * If we get a NULL, it could be an internal error, or it could be
207          * that there's a key mismatch.  We're pretending the latter...
208          */
209         if (from_keydata == NULL)
210             ERR_raise(ERR_LIB_EVP, EVP_R_DIFFERENT_KEY_TYPES);
211         else
212             ok = (to->keydata = evp_keymgmt_dup(to->keymgmt,
213                                                 from_keydata,
214                                                 SELECT_PARAMETERS)) != NULL;
215         goto end;
216     }
217 
218     /* Both keys are legacy */
219     if (from->ameth != NULL && from->ameth->param_copy != NULL)
220         ok = from->ameth->param_copy(to, from);
221  end:
222     EVP_PKEY_free(downgraded_from);
223     return ok;
224 }
225 
EVP_PKEY_missing_parameters(const EVP_PKEY * pkey)226 int EVP_PKEY_missing_parameters(const EVP_PKEY *pkey)
227 {
228     if (pkey != NULL) {
229         if (pkey->keymgmt != NULL)
230             return !evp_keymgmt_util_has((EVP_PKEY *)pkey, SELECT_PARAMETERS);
231         else if (pkey->ameth != NULL && pkey->ameth->param_missing != NULL)
232             return pkey->ameth->param_missing(pkey);
233     }
234     return 0;
235 }
236 
237 /*
238  * This function is called for any mixture of keys except pure legacy pair.
239  * When legacy keys are gone, we replace a call to this functions with
240  * a call to evp_keymgmt_util_match().
241  */
evp_pkey_cmp_any(const EVP_PKEY * a,const EVP_PKEY * b,int selection)242 static int evp_pkey_cmp_any(const EVP_PKEY *a, const EVP_PKEY *b,
243                             int selection)
244 {
245     EVP_KEYMGMT *keymgmt1 = NULL, *keymgmt2 = NULL;
246     void *keydata1 = NULL, *keydata2 = NULL, *tmp_keydata = NULL;
247 
248     /* If none of them are provided, this function shouldn't have been called */
249     if (!ossl_assert(evp_pkey_is_provided(a) || evp_pkey_is_provided(b)))
250         return -2;
251 
252     /* For purely provided keys, we just call the keymgmt utility */
253     if (evp_pkey_is_provided(a) && evp_pkey_is_provided(b))
254         return evp_keymgmt_util_match((EVP_PKEY *)a, (EVP_PKEY *)b, selection);
255 
256     /*
257      * At this point, one of them is provided, the other not.  This allows
258      * us to compare types using legacy NIDs.
259      */
260     if (evp_pkey_is_legacy(a)
261         && !EVP_KEYMGMT_is_a(b->keymgmt, OBJ_nid2sn(a->type)))
262         return -1;               /* not the same key type */
263     if (evp_pkey_is_legacy(b)
264         && !EVP_KEYMGMT_is_a(a->keymgmt, OBJ_nid2sn(b->type)))
265         return -1;               /* not the same key type */
266 
267     /*
268      * We've determined that they both are the same keytype, so the next
269      * step is to do a bit of cross export to ensure we have keydata for
270      * both keys in the same keymgmt.
271      */
272     keymgmt1 = a->keymgmt;
273     keydata1 = a->keydata;
274     keymgmt2 = b->keymgmt;
275     keydata2 = b->keydata;
276 
277     if (keymgmt2 != NULL && keymgmt2->match != NULL) {
278         tmp_keydata =
279             evp_pkey_export_to_provider((EVP_PKEY *)a, NULL, &keymgmt2, NULL);
280         if (tmp_keydata != NULL) {
281             keymgmt1 = keymgmt2;
282             keydata1 = tmp_keydata;
283         }
284     }
285     if (tmp_keydata == NULL && keymgmt1 != NULL && keymgmt1->match != NULL) {
286         tmp_keydata =
287             evp_pkey_export_to_provider((EVP_PKEY *)b, NULL, &keymgmt1, NULL);
288         if (tmp_keydata != NULL) {
289             keymgmt2 = keymgmt1;
290             keydata2 = tmp_keydata;
291         }
292     }
293 
294     /* If we still don't have matching keymgmt implementations, we give up */
295     if (keymgmt1 != keymgmt2)
296         return -2;
297 
298     /* If the keymgmt implementations are NULL, the export failed */
299     if (keymgmt1 == NULL)
300         return -2;
301 
302     return evp_keymgmt_match(keymgmt1, keydata1, keydata2, selection);
303 }
304 
305 # ifndef OPENSSL_NO_DEPRECATED_3_0
EVP_PKEY_cmp_parameters(const EVP_PKEY * a,const EVP_PKEY * b)306 int EVP_PKEY_cmp_parameters(const EVP_PKEY *a, const EVP_PKEY *b)
307 {
308     return EVP_PKEY_parameters_eq(a, b);
309 }
310 #endif
311 
EVP_PKEY_parameters_eq(const EVP_PKEY * a,const EVP_PKEY * b)312 int EVP_PKEY_parameters_eq(const EVP_PKEY *a, const EVP_PKEY *b)
313 {
314     /*
315      * This will just call evp_keymgmt_util_match when legacy support
316      * is gone.
317      */
318 
319     if (a->keymgmt != NULL || b->keymgmt != NULL)
320         return evp_pkey_cmp_any(a, b, SELECT_PARAMETERS);
321 
322     /* All legacy keys */
323     if (a->type != b->type)
324         return -1;
325     if (a->ameth != NULL && a->ameth->param_cmp != NULL)
326         return a->ameth->param_cmp(a, b);
327     return -2;
328 }
329 
330 # ifndef OPENSSL_NO_DEPRECATED_3_0
EVP_PKEY_cmp(const EVP_PKEY * a,const EVP_PKEY * b)331 int EVP_PKEY_cmp(const EVP_PKEY *a, const EVP_PKEY *b)
332 {
333     return EVP_PKEY_eq(a, b);
334 }
335 #endif
336 
EVP_PKEY_eq(const EVP_PKEY * a,const EVP_PKEY * b)337 int EVP_PKEY_eq(const EVP_PKEY *a, const EVP_PKEY *b)
338 {
339     /*
340      * This will just call evp_keymgmt_util_match when legacy support
341      * is gone.
342      */
343 
344     /* Trivial shortcuts */
345     if (a == b)
346         return 1;
347     if (a == NULL || b == NULL)
348         return 0;
349 
350     if (a->keymgmt != NULL || b->keymgmt != NULL) {
351         int selection = SELECT_PARAMETERS;
352 
353         if (evp_keymgmt_util_has((EVP_PKEY *)a, OSSL_KEYMGMT_SELECT_PUBLIC_KEY)
354             && evp_keymgmt_util_has((EVP_PKEY *)b, OSSL_KEYMGMT_SELECT_PUBLIC_KEY))
355             selection |= OSSL_KEYMGMT_SELECT_PUBLIC_KEY;
356         else
357             selection |= OSSL_KEYMGMT_SELECT_KEYPAIR;
358         return evp_pkey_cmp_any(a, b, selection);
359     }
360 
361     /* All legacy keys */
362     if (a->type != b->type)
363         return -1;
364 
365     if (a->ameth != NULL) {
366         int ret;
367         /* Compare parameters if the algorithm has them */
368         if (a->ameth->param_cmp != NULL) {
369             ret = a->ameth->param_cmp(a, b);
370             if (ret <= 0)
371                 return ret;
372         }
373 
374         if (a->ameth->pub_cmp != NULL)
375             return a->ameth->pub_cmp(a, b);
376     }
377 
378     return -2;
379 }
380 
381 
new_raw_key_int(OSSL_LIB_CTX * libctx,const char * strtype,const char * propq,int nidtype,ENGINE * e,const unsigned char * key,size_t len,int key_is_priv)382 static EVP_PKEY *new_raw_key_int(OSSL_LIB_CTX *libctx,
383                                  const char *strtype,
384                                  const char *propq,
385                                  int nidtype,
386                                  ENGINE *e,
387                                  const unsigned char *key,
388                                  size_t len,
389                                  int key_is_priv)
390 {
391     EVP_PKEY *pkey = NULL;
392     EVP_PKEY_CTX *ctx = NULL;
393     const EVP_PKEY_ASN1_METHOD *ameth = NULL;
394     int result = 0;
395 
396 # ifndef OPENSSL_NO_ENGINE
397     /* Check if there is an Engine for this type */
398     if (e == NULL) {
399         ENGINE *tmpe = NULL;
400 
401         if (strtype != NULL)
402             ameth = EVP_PKEY_asn1_find_str(&tmpe, strtype, -1);
403         else if (nidtype != EVP_PKEY_NONE)
404             ameth = EVP_PKEY_asn1_find(&tmpe, nidtype);
405 
406         /* If tmpe is NULL then no engine is claiming to support this type */
407         if (tmpe == NULL)
408             ameth = NULL;
409 
410         ENGINE_finish(tmpe);
411     }
412 # endif
413 
414     if (e == NULL && ameth == NULL) {
415         /*
416          * No engine is claiming to support this type, so lets see if we have
417          * a provider.
418          */
419         ctx = EVP_PKEY_CTX_new_from_name(libctx,
420                                          strtype != NULL ? strtype
421                                                          : OBJ_nid2sn(nidtype),
422                                          propq);
423         if (ctx == NULL)
424             goto err;
425         /* May fail if no provider available */
426         ERR_set_mark();
427         if (EVP_PKEY_fromdata_init(ctx) == 1) {
428             OSSL_PARAM params[] = { OSSL_PARAM_END, OSSL_PARAM_END };
429 
430             ERR_clear_last_mark();
431             params[0] = OSSL_PARAM_construct_octet_string(
432                             key_is_priv ? OSSL_PKEY_PARAM_PRIV_KEY
433                                         : OSSL_PKEY_PARAM_PUB_KEY,
434                             (void *)key, len);
435 
436             if (EVP_PKEY_fromdata(ctx, &pkey, EVP_PKEY_KEYPAIR, params) != 1) {
437                 ERR_raise(ERR_LIB_EVP, EVP_R_KEY_SETUP_FAILED);
438                 goto err;
439             }
440 
441             EVP_PKEY_CTX_free(ctx);
442 
443             return pkey;
444         }
445         ERR_pop_to_mark();
446         /* else not supported so fallback to legacy */
447     }
448 
449     /* Legacy code path */
450 
451     pkey = EVP_PKEY_new();
452     if (pkey == NULL) {
453         ERR_raise(ERR_LIB_EVP, ERR_R_EVP_LIB);
454         goto err;
455     }
456 
457     if (!pkey_set_type(pkey, e, nidtype, strtype, -1, NULL)) {
458         /* ERR_raise(ERR_LIB_EVP, ...) already called */
459         goto err;
460     }
461 
462     if (!ossl_assert(pkey->ameth != NULL))
463         goto err;
464 
465     if (key_is_priv) {
466         if (pkey->ameth->set_priv_key == NULL) {
467             ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE);
468             goto err;
469         }
470 
471         if (!pkey->ameth->set_priv_key(pkey, key, len)) {
472             ERR_raise(ERR_LIB_EVP, EVP_R_KEY_SETUP_FAILED);
473             goto err;
474         }
475     } else {
476         if (pkey->ameth->set_pub_key == NULL) {
477             ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE);
478             goto err;
479         }
480 
481         if (!pkey->ameth->set_pub_key(pkey, key, len)) {
482             ERR_raise(ERR_LIB_EVP, EVP_R_KEY_SETUP_FAILED);
483             goto err;
484         }
485     }
486 
487     result = 1;
488  err:
489     if (!result) {
490         EVP_PKEY_free(pkey);
491         pkey = NULL;
492     }
493     EVP_PKEY_CTX_free(ctx);
494     return pkey;
495 }
496 
EVP_PKEY_new_raw_private_key_ex(OSSL_LIB_CTX * libctx,const char * keytype,const char * propq,const unsigned char * priv,size_t len)497 EVP_PKEY *EVP_PKEY_new_raw_private_key_ex(OSSL_LIB_CTX *libctx,
498                                           const char *keytype,
499                                           const char *propq,
500                                           const unsigned char *priv, size_t len)
501 {
502     return new_raw_key_int(libctx, keytype, propq, EVP_PKEY_NONE, NULL, priv,
503                            len, 1);
504 }
505 
EVP_PKEY_new_raw_private_key(int type,ENGINE * e,const unsigned char * priv,size_t len)506 EVP_PKEY *EVP_PKEY_new_raw_private_key(int type, ENGINE *e,
507                                        const unsigned char *priv,
508                                        size_t len)
509 {
510     return new_raw_key_int(NULL, NULL, NULL, type, e, priv, len, 1);
511 }
512 
EVP_PKEY_new_raw_public_key_ex(OSSL_LIB_CTX * libctx,const char * keytype,const char * propq,const unsigned char * pub,size_t len)513 EVP_PKEY *EVP_PKEY_new_raw_public_key_ex(OSSL_LIB_CTX *libctx,
514                                          const char *keytype, const char *propq,
515                                          const unsigned char *pub, size_t len)
516 {
517     return new_raw_key_int(libctx, keytype, propq, EVP_PKEY_NONE, NULL, pub,
518                            len, 0);
519 }
520 
EVP_PKEY_new_raw_public_key(int type,ENGINE * e,const unsigned char * pub,size_t len)521 EVP_PKEY *EVP_PKEY_new_raw_public_key(int type, ENGINE *e,
522                                       const unsigned char *pub,
523                                       size_t len)
524 {
525     return new_raw_key_int(NULL, NULL, NULL, type, e, pub, len, 0);
526 }
527 
528 struct raw_key_details_st {
529     unsigned char **key;
530     size_t *len;
531     int selection;
532 };
533 
534 static OSSL_CALLBACK get_raw_key_details;
get_raw_key_details(const OSSL_PARAM params[],void * arg)535 static int get_raw_key_details(const OSSL_PARAM params[], void *arg)
536 {
537     const OSSL_PARAM *p = NULL;
538     struct raw_key_details_st *raw_key = arg;
539 
540     if (raw_key->selection == OSSL_KEYMGMT_SELECT_PRIVATE_KEY) {
541         if ((p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_PRIV_KEY))
542                 != NULL)
543             return OSSL_PARAM_get_octet_string(p, (void **)raw_key->key,
544                                                raw_key->key == NULL ? 0 : *raw_key->len,
545                                                raw_key->len);
546     } else if (raw_key->selection == OSSL_KEYMGMT_SELECT_PUBLIC_KEY) {
547         if ((p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_PUB_KEY))
548                 != NULL)
549             return OSSL_PARAM_get_octet_string(p, (void **)raw_key->key,
550                                                raw_key->key == NULL ? 0 : *raw_key->len,
551                                                raw_key->len);
552     }
553 
554     return 0;
555 }
556 
EVP_PKEY_get_raw_private_key(const EVP_PKEY * pkey,unsigned char * priv,size_t * len)557 int EVP_PKEY_get_raw_private_key(const EVP_PKEY *pkey, unsigned char *priv,
558                                  size_t *len)
559 {
560     if (pkey->keymgmt != NULL) {
561         struct raw_key_details_st raw_key;
562 
563         raw_key.key = priv == NULL ? NULL : &priv;
564         raw_key.len = len;
565         raw_key.selection = OSSL_KEYMGMT_SELECT_PRIVATE_KEY;
566 
567         return evp_keymgmt_util_export(pkey, OSSL_KEYMGMT_SELECT_PRIVATE_KEY,
568                                        get_raw_key_details, &raw_key);
569     }
570 
571     if (pkey->ameth == NULL) {
572         ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE);
573         return 0;
574     }
575 
576     if (pkey->ameth->get_priv_key == NULL) {
577         ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE);
578         return 0;
579     }
580 
581     if (!pkey->ameth->get_priv_key(pkey, priv, len)) {
582         ERR_raise(ERR_LIB_EVP, EVP_R_GET_RAW_KEY_FAILED);
583         return 0;
584     }
585 
586     return 1;
587 }
588 
EVP_PKEY_get_raw_public_key(const EVP_PKEY * pkey,unsigned char * pub,size_t * len)589 int EVP_PKEY_get_raw_public_key(const EVP_PKEY *pkey, unsigned char *pub,
590                                 size_t *len)
591 {
592     if (pkey->keymgmt != NULL) {
593         struct raw_key_details_st raw_key;
594 
595         raw_key.key = pub == NULL ? NULL : &pub;
596         raw_key.len = len;
597         raw_key.selection = OSSL_KEYMGMT_SELECT_PUBLIC_KEY;
598 
599         return evp_keymgmt_util_export(pkey, OSSL_KEYMGMT_SELECT_PUBLIC_KEY,
600                                        get_raw_key_details, &raw_key);
601     }
602 
603     if (pkey->ameth == NULL) {
604         ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE);
605         return 0;
606     }
607 
608      if (pkey->ameth->get_pub_key == NULL) {
609         ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE);
610         return 0;
611     }
612 
613     if (!pkey->ameth->get_pub_key(pkey, pub, len)) {
614         ERR_raise(ERR_LIB_EVP, EVP_R_GET_RAW_KEY_FAILED);
615         return 0;
616     }
617 
618     return 1;
619 }
620 
new_cmac_key_int(const unsigned char * priv,size_t len,const char * cipher_name,const EVP_CIPHER * cipher,OSSL_LIB_CTX * libctx,const char * propq,ENGINE * e)621 static EVP_PKEY *new_cmac_key_int(const unsigned char *priv, size_t len,
622                                   const char *cipher_name,
623                                   const EVP_CIPHER *cipher,
624                                   OSSL_LIB_CTX *libctx,
625                                   const char *propq, ENGINE *e)
626 {
627 # ifndef OPENSSL_NO_CMAC
628 #  ifndef OPENSSL_NO_ENGINE
629     const char *engine_id = e != NULL ? ENGINE_get_id(e) : NULL;
630 #  endif
631     OSSL_PARAM params[5], *p = params;
632     EVP_PKEY *pkey = NULL;
633     EVP_PKEY_CTX *ctx;
634 
635     if (cipher != NULL)
636         cipher_name = EVP_CIPHER_get0_name(cipher);
637 
638     if (cipher_name == NULL) {
639         ERR_raise(ERR_LIB_EVP, EVP_R_KEY_SETUP_FAILED);
640         return NULL;
641     }
642 
643     ctx = EVP_PKEY_CTX_new_from_name(libctx, "CMAC", propq);
644     if (ctx == NULL)
645         goto err;
646 
647     if (EVP_PKEY_fromdata_init(ctx) <= 0) {
648         ERR_raise(ERR_LIB_EVP, EVP_R_KEY_SETUP_FAILED);
649         goto err;
650     }
651 
652     *p++ = OSSL_PARAM_construct_octet_string(OSSL_PKEY_PARAM_PRIV_KEY,
653                                             (void *)priv, len);
654     *p++ = OSSL_PARAM_construct_utf8_string(OSSL_PKEY_PARAM_CIPHER,
655                                             (char *)cipher_name, 0);
656     if (propq != NULL)
657         *p++ = OSSL_PARAM_construct_utf8_string(OSSL_PKEY_PARAM_PROPERTIES,
658                                                 (char *)propq, 0);
659 #  ifndef OPENSSL_NO_ENGINE
660     if (engine_id != NULL)
661         *p++ = OSSL_PARAM_construct_utf8_string(OSSL_PKEY_PARAM_ENGINE,
662                                                 (char *)engine_id, 0);
663 #  endif
664     *p = OSSL_PARAM_construct_end();
665 
666     if (EVP_PKEY_fromdata(ctx, &pkey, EVP_PKEY_KEYPAIR, params) <= 0) {
667         ERR_raise(ERR_LIB_EVP, EVP_R_KEY_SETUP_FAILED);
668         goto err;
669     }
670 
671  err:
672     EVP_PKEY_CTX_free(ctx);
673 
674     return pkey;
675 # else
676     ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE);
677     return NULL;
678 # endif
679 }
680 
EVP_PKEY_new_CMAC_key(ENGINE * e,const unsigned char * priv,size_t len,const EVP_CIPHER * cipher)681 EVP_PKEY *EVP_PKEY_new_CMAC_key(ENGINE *e, const unsigned char *priv,
682                                 size_t len, const EVP_CIPHER *cipher)
683 {
684     return new_cmac_key_int(priv, len, NULL, cipher, NULL, NULL, e);
685 }
686 
EVP_PKEY_set_type(EVP_PKEY * pkey,int type)687 int EVP_PKEY_set_type(EVP_PKEY *pkey, int type)
688 {
689     return pkey_set_type(pkey, NULL, type, NULL, -1, NULL);
690 }
691 
EVP_PKEY_set_type_str(EVP_PKEY * pkey,const char * str,int len)692 int EVP_PKEY_set_type_str(EVP_PKEY *pkey, const char *str, int len)
693 {
694     return pkey_set_type(pkey, NULL, EVP_PKEY_NONE, str, len, NULL);
695 }
696 
697 # ifndef OPENSSL_NO_ENGINE
EVP_PKEY_set1_engine(EVP_PKEY * pkey,ENGINE * e)698 int EVP_PKEY_set1_engine(EVP_PKEY *pkey, ENGINE *e)
699 {
700     if (e != NULL) {
701         if (!ENGINE_init(e)) {
702             ERR_raise(ERR_LIB_EVP, ERR_R_ENGINE_LIB);
703             return 0;
704         }
705         if (ENGINE_get_pkey_meth(e, pkey->type) == NULL) {
706             ENGINE_finish(e);
707             ERR_raise(ERR_LIB_EVP, EVP_R_UNSUPPORTED_ALGORITHM);
708             return 0;
709         }
710     }
711     ENGINE_finish(pkey->pmeth_engine);
712     pkey->pmeth_engine = e;
713     return 1;
714 }
715 
EVP_PKEY_get0_engine(const EVP_PKEY * pkey)716 ENGINE *EVP_PKEY_get0_engine(const EVP_PKEY *pkey)
717 {
718     return pkey->engine;
719 }
720 # endif
721 
722 # ifndef OPENSSL_NO_DEPRECATED_3_0
detect_foreign_key(EVP_PKEY * pkey)723 static void detect_foreign_key(EVP_PKEY *pkey)
724 {
725     switch (pkey->type) {
726     case EVP_PKEY_RSA:
727     case EVP_PKEY_RSA_PSS:
728         pkey->foreign = pkey->pkey.rsa != NULL
729                         && ossl_rsa_is_foreign(pkey->pkey.rsa);
730         break;
731 #  ifndef OPENSSL_NO_EC
732     case EVP_PKEY_SM2:
733         break;
734     case EVP_PKEY_EC:
735         pkey->foreign = pkey->pkey.ec != NULL
736                         && ossl_ec_key_is_foreign(pkey->pkey.ec);
737         break;
738 #  endif
739 #  ifndef OPENSSL_NO_DSA
740     case EVP_PKEY_DSA:
741         pkey->foreign = pkey->pkey.dsa != NULL
742                         && ossl_dsa_is_foreign(pkey->pkey.dsa);
743         break;
744 #endif
745 #  ifndef OPENSSL_NO_DH
746     case EVP_PKEY_DH:
747         pkey->foreign = pkey->pkey.dh != NULL
748                         && ossl_dh_is_foreign(pkey->pkey.dh);
749         break;
750 #endif
751     default:
752         pkey->foreign = 0;
753         break;
754     }
755 }
756 
EVP_PKEY_assign(EVP_PKEY * pkey,int type,void * key)757 int EVP_PKEY_assign(EVP_PKEY *pkey, int type, void *key)
758 {
759 #  ifndef OPENSSL_NO_EC
760     int pktype;
761 
762     pktype = EVP_PKEY_type(type);
763     if ((key != NULL) && (pktype == EVP_PKEY_EC || pktype == EVP_PKEY_SM2)) {
764         const EC_GROUP *group = EC_KEY_get0_group(key);
765 
766         if (group != NULL) {
767             int curve = EC_GROUP_get_curve_name(group);
768 
769             /*
770              * Regardless of what is requested the SM2 curve must be SM2 type,
771              * and non SM2 curves are EC type.
772              */
773             if (curve == NID_sm2 && pktype == EVP_PKEY_EC)
774                 type = EVP_PKEY_SM2;
775             else if(curve != NID_sm2 && pktype == EVP_PKEY_SM2)
776                 type = EVP_PKEY_EC;
777         }
778     }
779 #  endif
780 
781     if (pkey == NULL || !EVP_PKEY_set_type(pkey, type))
782         return 0;
783 
784     pkey->pkey.ptr = key;
785     detect_foreign_key(pkey);
786 
787     return (key != NULL);
788 }
789 # endif
790 
EVP_PKEY_get0(const EVP_PKEY * pkey)791 void *EVP_PKEY_get0(const EVP_PKEY *pkey)
792 {
793     if (pkey == NULL)
794         return NULL;
795 
796     if (!evp_pkey_is_provided(pkey))
797         return pkey->pkey.ptr;
798 
799     return NULL;
800 }
801 
EVP_PKEY_get0_hmac(const EVP_PKEY * pkey,size_t * len)802 const unsigned char *EVP_PKEY_get0_hmac(const EVP_PKEY *pkey, size_t *len)
803 {
804     const ASN1_OCTET_STRING *os = NULL;
805     if (pkey->type != EVP_PKEY_HMAC) {
806         ERR_raise(ERR_LIB_EVP, EVP_R_EXPECTING_AN_HMAC_KEY);
807         return NULL;
808     }
809     os = evp_pkey_get_legacy((EVP_PKEY *)pkey);
810     if (os != NULL) {
811         *len = os->length;
812         return os->data;
813     }
814     return NULL;
815 }
816 
817 # ifndef OPENSSL_NO_POLY1305
EVP_PKEY_get0_poly1305(const EVP_PKEY * pkey,size_t * len)818 const unsigned char *EVP_PKEY_get0_poly1305(const EVP_PKEY *pkey, size_t *len)
819 {
820     const ASN1_OCTET_STRING *os = NULL;
821     if (pkey->type != EVP_PKEY_POLY1305) {
822         ERR_raise(ERR_LIB_EVP, EVP_R_EXPECTING_A_POLY1305_KEY);
823         return NULL;
824     }
825     os = evp_pkey_get_legacy((EVP_PKEY *)pkey);
826     if (os != NULL) {
827         *len = os->length;
828         return os->data;
829     }
830     return NULL;
831 }
832 # endif
833 
834 # ifndef OPENSSL_NO_SIPHASH
EVP_PKEY_get0_siphash(const EVP_PKEY * pkey,size_t * len)835 const unsigned char *EVP_PKEY_get0_siphash(const EVP_PKEY *pkey, size_t *len)
836 {
837     const ASN1_OCTET_STRING *os = NULL;
838 
839     if (pkey->type != EVP_PKEY_SIPHASH) {
840         ERR_raise(ERR_LIB_EVP, EVP_R_EXPECTING_A_SIPHASH_KEY);
841         return NULL;
842     }
843     os = evp_pkey_get_legacy((EVP_PKEY *)pkey);
844     if (os != NULL) {
845         *len = os->length;
846         return os->data;
847     }
848     return NULL;
849 }
850 # endif
851 
852 # ifndef OPENSSL_NO_DSA
evp_pkey_get0_DSA_int(const EVP_PKEY * pkey)853 static DSA *evp_pkey_get0_DSA_int(const EVP_PKEY *pkey)
854 {
855     if (pkey->type != EVP_PKEY_DSA) {
856         ERR_raise(ERR_LIB_EVP, EVP_R_EXPECTING_A_DSA_KEY);
857         return NULL;
858     }
859     return evp_pkey_get_legacy((EVP_PKEY *)pkey);
860 }
861 
EVP_PKEY_get0_DSA(const EVP_PKEY * pkey)862 const DSA *EVP_PKEY_get0_DSA(const EVP_PKEY *pkey)
863 {
864     return evp_pkey_get0_DSA_int(pkey);
865 }
866 
EVP_PKEY_set1_DSA(EVP_PKEY * pkey,DSA * key)867 int EVP_PKEY_set1_DSA(EVP_PKEY *pkey, DSA *key)
868 {
869     int ret = EVP_PKEY_assign_DSA(pkey, key);
870     if (ret)
871         DSA_up_ref(key);
872     return ret;
873 }
EVP_PKEY_get1_DSA(EVP_PKEY * pkey)874 DSA *EVP_PKEY_get1_DSA(EVP_PKEY *pkey)
875 {
876     DSA *ret = evp_pkey_get0_DSA_int(pkey);
877 
878     if (ret != NULL)
879         DSA_up_ref(ret);
880     return ret;
881 }
882 # endif /*  OPENSSL_NO_DSA */
883 
884 # ifndef OPENSSL_NO_ECX
evp_pkey_get0_ECX_KEY(const EVP_PKEY * pkey,int type)885 static const ECX_KEY *evp_pkey_get0_ECX_KEY(const EVP_PKEY *pkey, int type)
886 {
887     if (EVP_PKEY_get_base_id(pkey) != type) {
888         ERR_raise(ERR_LIB_EVP, EVP_R_EXPECTING_A_ECX_KEY);
889         return NULL;
890     }
891     return evp_pkey_get_legacy((EVP_PKEY *)pkey);
892 }
893 
evp_pkey_get1_ECX_KEY(EVP_PKEY * pkey,int type)894 static ECX_KEY *evp_pkey_get1_ECX_KEY(EVP_PKEY *pkey, int type)
895 {
896     ECX_KEY *ret = (ECX_KEY *)evp_pkey_get0_ECX_KEY(pkey, type);
897 
898     if (ret != NULL && !ossl_ecx_key_up_ref(ret))
899         ret = NULL;
900     return ret;
901 }
902 
903 #  define IMPLEMENT_ECX_VARIANT(NAME)                                   \
904     ECX_KEY *ossl_evp_pkey_get1_##NAME(EVP_PKEY *pkey)                  \
905     {                                                                   \
906         return evp_pkey_get1_ECX_KEY(pkey, EVP_PKEY_##NAME);            \
907     }
908 IMPLEMENT_ECX_VARIANT(X25519)
IMPLEMENT_ECX_VARIANT(X448)909 IMPLEMENT_ECX_VARIANT(X448)
910 IMPLEMENT_ECX_VARIANT(ED25519)
911 IMPLEMENT_ECX_VARIANT(ED448)
912 
913 # endif /* OPENSSL_NO_ECX */
914 
915 # if !defined(OPENSSL_NO_DH) && !defined(OPENSSL_NO_DEPRECATED_3_0)
916 
917 int EVP_PKEY_set1_DH(EVP_PKEY *pkey, DH *dhkey)
918 {
919     int ret, type;
920 
921     /*
922      * ossl_dh_is_named_safe_prime_group() returns 1 for named safe prime groups
923      * related to ffdhe and modp (which cache q = (p - 1) / 2),
924      * and returns 0 for all other dh parameter generation types including
925      * RFC5114 named groups.
926      *
927      * The EVP_PKEY_DH type is used for dh parameter generation types:
928      *  - named safe prime groups related to ffdhe and modp
929      *  - safe prime generator
930      *
931      * The type EVP_PKEY_DHX is used for dh parameter generation types
932      *  - fips186-4 and fips186-2
933      *  - rfc5114 named groups.
934      *
935      * The EVP_PKEY_DH type is used to save PKCS#3 data than can be stored
936      * without a q value.
937      * The EVP_PKEY_DHX type is used to save X9.42 data that requires the
938      * q value to be stored.
939      */
940     if (ossl_dh_is_named_safe_prime_group(dhkey))
941         type = EVP_PKEY_DH;
942     else
943         type = DH_get0_q(dhkey) == NULL ? EVP_PKEY_DH : EVP_PKEY_DHX;
944 
945     ret = EVP_PKEY_assign(pkey, type, dhkey);
946 
947     if (ret)
948         DH_up_ref(dhkey);
949     return ret;
950 }
951 
evp_pkey_get0_DH_int(const EVP_PKEY * pkey)952 DH *evp_pkey_get0_DH_int(const EVP_PKEY *pkey)
953 {
954     if (pkey->type != EVP_PKEY_DH && pkey->type != EVP_PKEY_DHX) {
955         ERR_raise(ERR_LIB_EVP, EVP_R_EXPECTING_A_DH_KEY);
956         return NULL;
957     }
958     return evp_pkey_get_legacy((EVP_PKEY *)pkey);
959 }
960 
EVP_PKEY_get0_DH(const EVP_PKEY * pkey)961 const DH *EVP_PKEY_get0_DH(const EVP_PKEY *pkey)
962 {
963     return evp_pkey_get0_DH_int(pkey);
964 }
965 
EVP_PKEY_get1_DH(EVP_PKEY * pkey)966 DH *EVP_PKEY_get1_DH(EVP_PKEY *pkey)
967 {
968     DH *ret = evp_pkey_get0_DH_int(pkey);
969 
970     if (ret != NULL)
971         DH_up_ref(ret);
972     return ret;
973 }
974 # endif
975 
EVP_PKEY_type(int type)976 int EVP_PKEY_type(int type)
977 {
978     int ret;
979     const EVP_PKEY_ASN1_METHOD *ameth;
980     ENGINE *e;
981     ameth = EVP_PKEY_asn1_find(&e, type);
982     if (ameth)
983         ret = ameth->pkey_id;
984     else
985         ret = NID_undef;
986 # ifndef OPENSSL_NO_ENGINE
987     ENGINE_finish(e);
988 # endif
989     return ret;
990 }
991 
EVP_PKEY_get_id(const EVP_PKEY * pkey)992 int EVP_PKEY_get_id(const EVP_PKEY *pkey)
993 {
994     return pkey->type;
995 }
996 
EVP_PKEY_get_base_id(const EVP_PKEY * pkey)997 int EVP_PKEY_get_base_id(const EVP_PKEY *pkey)
998 {
999     return EVP_PKEY_type(pkey->type);
1000 }
1001 
1002 /*
1003  * These hard coded cases are pure hackery to get around the fact
1004  * that names in crypto/objects/objects.txt are a mess.  There is
1005  * no "EC", and "RSA" leads to the NID for 2.5.8.1.1, an OID that's
1006  * fallen out in favor of { pkcs-1 1 }, i.e. 1.2.840.113549.1.1.1,
1007  * the NID of which is used for EVP_PKEY_RSA.  Strangely enough,
1008  * "DSA" is accurate...  but still, better be safe and hard-code
1009  * names that we know.
1010  * On a similar topic, EVP_PKEY_type(EVP_PKEY_SM2) will result in
1011  * EVP_PKEY_EC, because of aliasing.
1012  * This should be cleaned away along with all other #legacy support.
1013  */
1014 static const OSSL_ITEM standard_name2type[] = {
1015     { EVP_PKEY_RSA,     "RSA" },
1016     { EVP_PKEY_RSA_PSS, "RSA-PSS" },
1017     { EVP_PKEY_EC,      "EC" },
1018     { EVP_PKEY_ED25519, "ED25519" },
1019     { EVP_PKEY_ED448,   "ED448" },
1020     { EVP_PKEY_X25519,  "X25519" },
1021     { EVP_PKEY_X448,    "X448" },
1022     { EVP_PKEY_SM2,     "SM2" },
1023     { EVP_PKEY_DH,      "DH" },
1024     { EVP_PKEY_DHX,     "X9.42 DH" },
1025     { EVP_PKEY_DHX,     "DHX" },
1026     { EVP_PKEY_DSA,     "DSA" },
1027 };
1028 
evp_pkey_name2type(const char * name)1029 int evp_pkey_name2type(const char *name)
1030 {
1031     int type;
1032     size_t i;
1033 
1034     for (i = 0; i < OSSL_NELEM(standard_name2type); i++) {
1035         if (OPENSSL_strcasecmp(name, standard_name2type[i].ptr) == 0)
1036             return (int)standard_name2type[i].id;
1037     }
1038 
1039     if ((type = EVP_PKEY_type(OBJ_sn2nid(name))) != NID_undef)
1040         return type;
1041     return EVP_PKEY_type(OBJ_ln2nid(name));
1042 }
1043 
evp_pkey_type2name(int type)1044 const char *evp_pkey_type2name(int type)
1045 {
1046     size_t i;
1047 
1048     for (i = 0; i < OSSL_NELEM(standard_name2type); i++) {
1049         if (type == (int)standard_name2type[i].id)
1050             return standard_name2type[i].ptr;
1051     }
1052 
1053     return OBJ_nid2sn(type);
1054 }
1055 
EVP_PKEY_is_a(const EVP_PKEY * pkey,const char * name)1056 int EVP_PKEY_is_a(const EVP_PKEY *pkey, const char *name)
1057 {
1058     if (pkey == NULL)
1059         return 0;
1060     if (pkey->keymgmt == NULL)
1061         return pkey->type == evp_pkey_name2type(name);
1062     return EVP_KEYMGMT_is_a(pkey->keymgmt, name);
1063 }
1064 
EVP_PKEY_type_names_do_all(const EVP_PKEY * pkey,void (* fn)(const char * name,void * data),void * data)1065 int EVP_PKEY_type_names_do_all(const EVP_PKEY *pkey,
1066                                void (*fn)(const char *name, void *data),
1067                                void *data)
1068 {
1069     if (!evp_pkey_is_typed(pkey))
1070         return 0;
1071 
1072     if (!evp_pkey_is_provided(pkey)) {
1073         const char *name = OBJ_nid2sn(EVP_PKEY_get_id(pkey));
1074 
1075         fn(name, data);
1076         return 1;
1077     }
1078     return EVP_KEYMGMT_names_do_all(pkey->keymgmt, fn, data);
1079 }
1080 
EVP_PKEY_can_sign(const EVP_PKEY * pkey)1081 int EVP_PKEY_can_sign(const EVP_PKEY *pkey)
1082 {
1083     if (pkey->keymgmt == NULL) {
1084         switch (EVP_PKEY_get_base_id(pkey)) {
1085         case EVP_PKEY_RSA:
1086         case EVP_PKEY_RSA_PSS:
1087             return 1;
1088 # ifndef OPENSSL_NO_DSA
1089         case EVP_PKEY_DSA:
1090             return 1;
1091 # endif
1092 # ifndef OPENSSL_NO_EC
1093         case EVP_PKEY_ED25519:
1094         case EVP_PKEY_ED448:
1095             return 1;
1096         case EVP_PKEY_EC:        /* Including SM2 */
1097             return EC_KEY_can_sign(pkey->pkey.ec);
1098 # endif
1099         default:
1100             break;
1101         }
1102     } else {
1103         const OSSL_PROVIDER *prov = EVP_KEYMGMT_get0_provider(pkey->keymgmt);
1104         OSSL_LIB_CTX *libctx = ossl_provider_libctx(prov);
1105         const char *supported_sig =
1106             pkey->keymgmt->query_operation_name != NULL
1107             ? pkey->keymgmt->query_operation_name(OSSL_OP_SIGNATURE)
1108             : EVP_KEYMGMT_get0_name(pkey->keymgmt);
1109         EVP_SIGNATURE *signature = NULL;
1110 
1111         signature = EVP_SIGNATURE_fetch(libctx, supported_sig, NULL);
1112         if (signature != NULL) {
1113             EVP_SIGNATURE_free(signature);
1114             return 1;
1115         }
1116     }
1117     return 0;
1118 }
1119 
print_reset_indent(BIO ** out,int pop_f_prefix,long saved_indent)1120 static int print_reset_indent(BIO **out, int pop_f_prefix, long saved_indent)
1121 {
1122     BIO_set_indent(*out, saved_indent);
1123     if (pop_f_prefix) {
1124         BIO *next = BIO_pop(*out);
1125 
1126         BIO_free(*out);
1127         *out = next;
1128     }
1129     return 1;
1130 }
1131 
print_set_indent(BIO ** out,int * pop_f_prefix,long * saved_indent,long indent)1132 static int print_set_indent(BIO **out, int *pop_f_prefix, long *saved_indent,
1133                             long indent)
1134 {
1135     *pop_f_prefix = 0;
1136     *saved_indent = 0;
1137     if (indent > 0) {
1138         long i = BIO_get_indent(*out);
1139 
1140         *saved_indent =  (i < 0 ? 0 : i);
1141         if (BIO_set_indent(*out, indent) <= 0) {
1142             BIO *prefbio = BIO_new(BIO_f_prefix());
1143 
1144             if (prefbio == NULL)
1145                 return 0;
1146             *out = BIO_push(prefbio, *out);
1147             *pop_f_prefix = 1;
1148         }
1149         if (BIO_set_indent(*out, indent) <= 0) {
1150             print_reset_indent(out, *pop_f_prefix, *saved_indent);
1151             return 0;
1152         }
1153     }
1154     return 1;
1155 }
1156 
unsup_alg(BIO * out,const EVP_PKEY * pkey,int indent,const char * kstr)1157 static int unsup_alg(BIO *out, const EVP_PKEY *pkey, int indent,
1158                      const char *kstr)
1159 {
1160     return BIO_indent(out, indent, 128)
1161         && BIO_printf(out, "%s algorithm \"%s\" unsupported\n",
1162                       kstr, OBJ_nid2ln(pkey->type)) > 0;
1163 }
1164 
print_pkey(const EVP_PKEY * pkey,BIO * out,int indent,int selection,const char * propquery,int (* legacy_print)(BIO * out,const EVP_PKEY * pkey,int indent,ASN1_PCTX * pctx),ASN1_PCTX * legacy_pctx)1165 static int print_pkey(const EVP_PKEY *pkey, BIO *out, int indent,
1166                       int selection /* For provided encoding */,
1167                       const char *propquery /* For provided encoding */,
1168                       int (*legacy_print)(BIO *out, const EVP_PKEY *pkey,
1169                                           int indent, ASN1_PCTX *pctx),
1170                       ASN1_PCTX *legacy_pctx /* For legacy print */)
1171 {
1172     int pop_f_prefix;
1173     long saved_indent;
1174     OSSL_ENCODER_CTX *ctx = NULL;
1175     int ret = -2;                /* default to unsupported */
1176 
1177     if (!print_set_indent(&out, &pop_f_prefix, &saved_indent, indent))
1178         return 0;
1179 
1180     ctx = OSSL_ENCODER_CTX_new_for_pkey(pkey, selection, "TEXT", NULL,
1181                                         propquery);
1182     if (OSSL_ENCODER_CTX_get_num_encoders(ctx) != 0)
1183         ret = OSSL_ENCODER_to_bio(ctx, out);
1184     OSSL_ENCODER_CTX_free(ctx);
1185 
1186     if (ret != -2)
1187         goto end;
1188 
1189     /* legacy fallback */
1190     if (legacy_print != NULL)
1191         ret = legacy_print(out, pkey, 0, legacy_pctx);
1192     else
1193         ret = unsup_alg(out, pkey, 0, "Public Key");
1194 
1195  end:
1196     print_reset_indent(&out, pop_f_prefix, saved_indent);
1197     return ret;
1198 }
1199 
EVP_PKEY_print_public(BIO * out,const EVP_PKEY * pkey,int indent,ASN1_PCTX * pctx)1200 int EVP_PKEY_print_public(BIO *out, const EVP_PKEY *pkey,
1201                           int indent, ASN1_PCTX *pctx)
1202 {
1203     return print_pkey(pkey, out, indent, EVP_PKEY_PUBLIC_KEY, NULL,
1204                       (pkey->ameth != NULL ? pkey->ameth->pub_print : NULL),
1205                       pctx);
1206 }
1207 
EVP_PKEY_print_private(BIO * out,const EVP_PKEY * pkey,int indent,ASN1_PCTX * pctx)1208 int EVP_PKEY_print_private(BIO *out, const EVP_PKEY *pkey,
1209                            int indent, ASN1_PCTX *pctx)
1210 {
1211     return print_pkey(pkey, out, indent, EVP_PKEY_PRIVATE_KEY, NULL,
1212                       (pkey->ameth != NULL ? pkey->ameth->priv_print : NULL),
1213                       pctx);
1214 }
1215 
EVP_PKEY_print_params(BIO * out,const EVP_PKEY * pkey,int indent,ASN1_PCTX * pctx)1216 int EVP_PKEY_print_params(BIO *out, const EVP_PKEY *pkey,
1217                           int indent, ASN1_PCTX *pctx)
1218 {
1219     return print_pkey(pkey, out, indent, EVP_PKEY_KEY_PARAMETERS, NULL,
1220                       (pkey->ameth != NULL ? pkey->ameth->param_print : NULL),
1221                       pctx);
1222 }
1223 
1224 # ifndef OPENSSL_NO_STDIO
EVP_PKEY_print_public_fp(FILE * fp,const EVP_PKEY * pkey,int indent,ASN1_PCTX * pctx)1225 int EVP_PKEY_print_public_fp(FILE *fp, const EVP_PKEY *pkey,
1226                              int indent, ASN1_PCTX *pctx)
1227 {
1228     int ret;
1229     BIO *b = BIO_new_fp(fp, BIO_NOCLOSE);
1230 
1231     if (b == NULL)
1232         return 0;
1233     ret = EVP_PKEY_print_public(b, pkey, indent, pctx);
1234     BIO_free(b);
1235     return ret;
1236 }
1237 
EVP_PKEY_print_private_fp(FILE * fp,const EVP_PKEY * pkey,int indent,ASN1_PCTX * pctx)1238 int EVP_PKEY_print_private_fp(FILE *fp, const EVP_PKEY *pkey,
1239                               int indent, ASN1_PCTX *pctx)
1240 {
1241     int ret;
1242     BIO *b = BIO_new_fp(fp, BIO_NOCLOSE);
1243 
1244     if (b == NULL)
1245         return 0;
1246     ret = EVP_PKEY_print_private(b, pkey, indent, pctx);
1247     BIO_free(b);
1248     return ret;
1249 }
1250 
EVP_PKEY_print_params_fp(FILE * fp,const EVP_PKEY * pkey,int indent,ASN1_PCTX * pctx)1251 int EVP_PKEY_print_params_fp(FILE *fp, const EVP_PKEY *pkey,
1252                              int indent, ASN1_PCTX *pctx)
1253 {
1254     int ret;
1255     BIO *b = BIO_new_fp(fp, BIO_NOCLOSE);
1256 
1257     if (b == NULL)
1258         return 0;
1259     ret = EVP_PKEY_print_params(b, pkey, indent, pctx);
1260     BIO_free(b);
1261     return ret;
1262 }
1263 # endif
1264 
mdname2nid(const char * mdname,void * data)1265 static void mdname2nid(const char *mdname, void *data)
1266 {
1267     int *nid = (int *)data;
1268 
1269     if (*nid != NID_undef)
1270         return;
1271 
1272     *nid = OBJ_sn2nid(mdname);
1273     if (*nid == NID_undef)
1274         *nid = OBJ_ln2nid(mdname);
1275 }
1276 
legacy_asn1_ctrl_to_param(EVP_PKEY * pkey,int op,int arg1,void * arg2)1277 static int legacy_asn1_ctrl_to_param(EVP_PKEY *pkey, int op,
1278                                      int arg1, void *arg2)
1279 {
1280     if (pkey->keymgmt == NULL)
1281         return 0;
1282     switch (op) {
1283     case ASN1_PKEY_CTRL_DEFAULT_MD_NID:
1284         {
1285             char mdname[80] = "";
1286             int rv = EVP_PKEY_get_default_digest_name(pkey, mdname,
1287                                                       sizeof(mdname));
1288 
1289             if (rv > 0) {
1290                 int mdnum;
1291                 OSSL_LIB_CTX *libctx = ossl_provider_libctx(pkey->keymgmt->prov);
1292                 /* Make sure the MD is in the namemap if available */
1293                 EVP_MD *md;
1294                 OSSL_NAMEMAP *namemap;
1295                 int nid = NID_undef;
1296 
1297                 (void)ERR_set_mark();
1298                 md = EVP_MD_fetch(libctx, mdname, NULL);
1299                 (void)ERR_pop_to_mark();
1300                 namemap = ossl_namemap_stored(libctx);
1301 
1302                 /*
1303                  * The only reason to fetch the MD was to make sure it is in the
1304                  * namemap. We can immediately free it.
1305                  */
1306                 EVP_MD_free(md);
1307                 mdnum = ossl_namemap_name2num(namemap, mdname);
1308                 if (mdnum == 0)
1309                     return 0;
1310 
1311                 /*
1312                  * We have the namemap number - now we need to find the
1313                  * associated nid
1314                  */
1315                 if (!ossl_namemap_doall_names(namemap, mdnum, mdname2nid, &nid))
1316                     return 0;
1317                 *(int *)arg2 = nid;
1318             }
1319             return rv;
1320         }
1321     default:
1322         return -2;
1323     }
1324 }
1325 
evp_pkey_asn1_ctrl(EVP_PKEY * pkey,int op,int arg1,void * arg2)1326 static int evp_pkey_asn1_ctrl(EVP_PKEY *pkey, int op, int arg1, void *arg2)
1327 {
1328     if (pkey->ameth == NULL)
1329         return legacy_asn1_ctrl_to_param(pkey, op, arg1, arg2);
1330     if (pkey->ameth->pkey_ctrl == NULL)
1331         return -2;
1332     return pkey->ameth->pkey_ctrl(pkey, op, arg1, arg2);
1333 }
1334 
EVP_PKEY_get_default_digest_nid(EVP_PKEY * pkey,int * pnid)1335 int EVP_PKEY_get_default_digest_nid(EVP_PKEY *pkey, int *pnid)
1336 {
1337     if (pkey == NULL)
1338         return 0;
1339     return evp_pkey_asn1_ctrl(pkey, ASN1_PKEY_CTRL_DEFAULT_MD_NID, 0, pnid);
1340 }
1341 
EVP_PKEY_get_default_digest_name(EVP_PKEY * pkey,char * mdname,size_t mdname_sz)1342 int EVP_PKEY_get_default_digest_name(EVP_PKEY *pkey,
1343                                      char *mdname, size_t mdname_sz)
1344 {
1345     if (pkey->ameth == NULL)
1346         return evp_keymgmt_util_get_deflt_digest_name(pkey->keymgmt,
1347                                                       pkey->keydata,
1348                                                       mdname, mdname_sz);
1349 
1350     {
1351         int nid = NID_undef;
1352         int rv = EVP_PKEY_get_default_digest_nid(pkey, &nid);
1353         const char *name = rv > 0 ? OBJ_nid2sn(nid) : NULL;
1354 
1355         if (rv > 0)
1356             OPENSSL_strlcpy(mdname, name, mdname_sz);
1357         return rv;
1358     }
1359 }
1360 
EVP_PKEY_get_group_name(const EVP_PKEY * pkey,char * gname,size_t gname_sz,size_t * gname_len)1361 int EVP_PKEY_get_group_name(const EVP_PKEY *pkey, char *gname, size_t gname_sz,
1362                             size_t *gname_len)
1363 {
1364     return EVP_PKEY_get_utf8_string_param(pkey, OSSL_PKEY_PARAM_GROUP_NAME,
1365                                           gname, gname_sz, gname_len);
1366 }
1367 
EVP_PKEY_digestsign_supports_digest(EVP_PKEY * pkey,OSSL_LIB_CTX * libctx,const char * name,const char * propq)1368 int EVP_PKEY_digestsign_supports_digest(EVP_PKEY *pkey, OSSL_LIB_CTX *libctx,
1369                                         const char *name, const char *propq)
1370 {
1371     int rv;
1372     EVP_MD_CTX *ctx = NULL;
1373 
1374     if ((ctx = EVP_MD_CTX_new()) == NULL)
1375         return -1;
1376 
1377     ERR_set_mark();
1378     rv = EVP_DigestSignInit_ex(ctx, NULL, name, libctx,
1379                                propq, pkey, NULL);
1380     ERR_pop_to_mark();
1381 
1382     EVP_MD_CTX_free(ctx);
1383     return rv;
1384 }
1385 
EVP_PKEY_set1_encoded_public_key(EVP_PKEY * pkey,const unsigned char * pub,size_t publen)1386 int EVP_PKEY_set1_encoded_public_key(EVP_PKEY *pkey, const unsigned char *pub,
1387                                      size_t publen)
1388 {
1389     if (pkey == NULL)
1390         return 0;
1391     if (evp_pkey_is_provided(pkey))
1392         return
1393             EVP_PKEY_set_octet_string_param(pkey,
1394                                             OSSL_PKEY_PARAM_ENCODED_PUBLIC_KEY,
1395                                             (unsigned char *)pub, publen);
1396 
1397     if (publen > INT_MAX)
1398         return 0;
1399     /* Historically this function was EVP_PKEY_set1_tls_encodedpoint */
1400     if (evp_pkey_asn1_ctrl(pkey, ASN1_PKEY_CTRL_SET1_TLS_ENCPT, publen,
1401                            (void *)pub) <= 0)
1402         return 0;
1403     return 1;
1404 }
1405 
EVP_PKEY_get1_encoded_public_key(EVP_PKEY * pkey,unsigned char ** ppub)1406 size_t EVP_PKEY_get1_encoded_public_key(EVP_PKEY *pkey, unsigned char **ppub)
1407 {
1408     int rv;
1409 
1410     if (pkey == NULL)
1411         return 0;
1412     if (evp_pkey_is_provided(pkey)) {
1413         size_t return_size = OSSL_PARAM_UNMODIFIED;
1414         unsigned char *buf;
1415 
1416         /*
1417          * We know that this is going to fail, but it will give us a size
1418          * to allocate.
1419          */
1420         EVP_PKEY_get_octet_string_param(pkey,
1421                                         OSSL_PKEY_PARAM_ENCODED_PUBLIC_KEY,
1422                                         NULL, 0, &return_size);
1423         if (return_size == OSSL_PARAM_UNMODIFIED)
1424             return 0;
1425 
1426         *ppub = NULL;
1427         buf = OPENSSL_malloc(return_size);
1428         if (buf == NULL)
1429             return 0;
1430 
1431         if (!EVP_PKEY_get_octet_string_param(pkey,
1432                                              OSSL_PKEY_PARAM_ENCODED_PUBLIC_KEY,
1433                                              buf, return_size, NULL)) {
1434             OPENSSL_free(buf);
1435             return 0;
1436         }
1437         *ppub = buf;
1438         return return_size;
1439     }
1440 
1441 
1442     rv = evp_pkey_asn1_ctrl(pkey, ASN1_PKEY_CTRL_GET1_TLS_ENCPT, 0, ppub);
1443     if (rv <= 0)
1444         return 0;
1445     return rv;
1446 }
1447 
1448 #endif /* FIPS_MODULE */
1449 
1450 /*- All methods below can also be used in FIPS_MODULE */
1451 
EVP_PKEY_new(void)1452 EVP_PKEY *EVP_PKEY_new(void)
1453 {
1454     EVP_PKEY *ret = OPENSSL_zalloc(sizeof(*ret));
1455 
1456     if (ret == NULL)
1457         return NULL;
1458 
1459     ret->type = EVP_PKEY_NONE;
1460     ret->save_type = EVP_PKEY_NONE;
1461 
1462     if (!CRYPTO_NEW_REF(&ret->references, 1))
1463         goto err;
1464 
1465     ret->lock = CRYPTO_THREAD_lock_new();
1466     if (ret->lock == NULL) {
1467         ERR_raise(ERR_LIB_EVP, ERR_R_CRYPTO_LIB);
1468         goto err;
1469     }
1470 
1471 #ifndef FIPS_MODULE
1472     ret->save_parameters = 1;
1473     if (!CRYPTO_new_ex_data(CRYPTO_EX_INDEX_EVP_PKEY, ret, &ret->ex_data)) {
1474         ERR_raise(ERR_LIB_EVP, ERR_R_CRYPTO_LIB);
1475         goto err;
1476     }
1477 #endif
1478     return ret;
1479 
1480  err:
1481     CRYPTO_FREE_REF(&ret->references);
1482     CRYPTO_THREAD_lock_free(ret->lock);
1483     OPENSSL_free(ret);
1484     return NULL;
1485 }
1486 
1487 /*
1488  * Setup a public key management method.
1489  *
1490  * For legacy keys, either |type| or |str| is expected to have the type
1491  * information.  In this case, the setup consists of finding an ASN1 method
1492  * and potentially an ENGINE, and setting those fields in |pkey|.
1493  *
1494  * For provider side keys, |keymgmt| is expected to be non-NULL.  In this
1495  * case, the setup consists of setting the |keymgmt| field in |pkey|.
1496  *
1497  * If pkey is NULL just return 1 or 0 if the key management method exists.
1498  */
1499 
pkey_set_type(EVP_PKEY * pkey,ENGINE * e,int type,const char * str,int len,EVP_KEYMGMT * keymgmt)1500 static int pkey_set_type(EVP_PKEY *pkey, ENGINE *e, int type, const char *str,
1501                          int len, EVP_KEYMGMT *keymgmt)
1502 {
1503 #ifndef FIPS_MODULE
1504     const EVP_PKEY_ASN1_METHOD *ameth = NULL;
1505     ENGINE **eptr = (e == NULL) ? &e :  NULL;
1506 #endif
1507 
1508     /*
1509      * The setups can't set both legacy and provider side methods.
1510      * It is forbidden
1511      */
1512     if (!ossl_assert(type == EVP_PKEY_NONE || keymgmt == NULL)
1513         || !ossl_assert(e == NULL || keymgmt == NULL)) {
1514         ERR_raise(ERR_LIB_EVP, ERR_R_INTERNAL_ERROR);
1515         return 0;
1516     }
1517 
1518     if (pkey != NULL) {
1519         int free_it = 0;
1520 
1521 #ifndef FIPS_MODULE
1522         free_it = free_it || pkey->pkey.ptr != NULL;
1523 #endif
1524         free_it = free_it || pkey->keydata != NULL;
1525         if (free_it)
1526             evp_pkey_free_it(pkey);
1527 #ifndef FIPS_MODULE
1528         /*
1529          * If key type matches and a method exists then this lookup has
1530          * succeeded once so just indicate success.
1531          */
1532         if (pkey->type != EVP_PKEY_NONE
1533             && type == pkey->save_type
1534             && pkey->ameth != NULL)
1535             return 1;
1536 # ifndef OPENSSL_NO_ENGINE
1537         /* If we have ENGINEs release them */
1538         ENGINE_finish(pkey->engine);
1539         pkey->engine = NULL;
1540         ENGINE_finish(pkey->pmeth_engine);
1541         pkey->pmeth_engine = NULL;
1542 # endif
1543 #endif
1544     }
1545 #ifndef FIPS_MODULE
1546     if (str != NULL)
1547         ameth = EVP_PKEY_asn1_find_str(eptr, str, len);
1548     else if (type != EVP_PKEY_NONE)
1549         ameth = EVP_PKEY_asn1_find(eptr, type);
1550 # ifndef OPENSSL_NO_ENGINE
1551     if (pkey == NULL && eptr != NULL)
1552         ENGINE_finish(e);
1553 # endif
1554 #endif
1555 
1556 
1557     {
1558         int check = 1;
1559 
1560 #ifndef FIPS_MODULE
1561         check = check && ameth == NULL;
1562 #endif
1563         check = check && keymgmt == NULL;
1564         if (check) {
1565             ERR_raise(ERR_LIB_EVP, EVP_R_UNSUPPORTED_ALGORITHM);
1566             return 0;
1567         }
1568     }
1569     if (pkey != NULL) {
1570         if (keymgmt != NULL && !EVP_KEYMGMT_up_ref(keymgmt)) {
1571             ERR_raise(ERR_LIB_EVP, ERR_R_INTERNAL_ERROR);
1572             return 0;
1573         }
1574 
1575         pkey->keymgmt = keymgmt;
1576 
1577         pkey->save_type = type;
1578         pkey->type = type;
1579 
1580 #ifndef FIPS_MODULE
1581         /*
1582          * If the internal "origin" key is provider side, don't save |ameth|.
1583          * The main reason is that |ameth| is one factor to detect that the
1584          * internal "origin" key is a legacy one.
1585          */
1586         if (keymgmt == NULL)
1587             pkey->ameth = ameth;
1588 
1589         /*
1590          * The EVP_PKEY_ASN1_METHOD |pkey_id| retains its legacy key purpose
1591          * for any key type that has a legacy implementation, regardless of
1592          * if the internal key is a legacy or a provider side one.  When
1593          * there is no legacy implementation for the key, the type becomes
1594          * EVP_PKEY_KEYMGMT, which indicates that one should be cautious
1595          * with functions that expect legacy internal keys.
1596          */
1597         if (ameth != NULL) {
1598             if (type == EVP_PKEY_NONE)
1599                 pkey->type = ameth->pkey_id;
1600         } else {
1601             pkey->type = EVP_PKEY_KEYMGMT;
1602         }
1603 # ifndef OPENSSL_NO_ENGINE
1604         if (eptr == NULL && e != NULL && !ENGINE_init(e)) {
1605             ERR_raise(ERR_LIB_EVP, EVP_R_INITIALIZATION_ERROR);
1606             return 0;
1607         }
1608 # endif
1609         pkey->engine = e;
1610 #endif
1611     }
1612     return 1;
1613 }
1614 
1615 #ifndef FIPS_MODULE
find_ameth(const char * name,void * data)1616 static void find_ameth(const char *name, void *data)
1617 {
1618     const char **str = data;
1619 
1620     /*
1621      * The error messages from pkey_set_type() are uninteresting here,
1622      * and misleading.
1623      */
1624     ERR_set_mark();
1625 
1626     if (pkey_set_type(NULL, NULL, EVP_PKEY_NONE, name, strlen(name),
1627                       NULL)) {
1628         if (str[0] == NULL)
1629             str[0] = name;
1630         else if (str[1] == NULL)
1631             str[1] = name;
1632     }
1633 
1634     ERR_pop_to_mark();
1635 }
1636 #endif
1637 
EVP_PKEY_set_type_by_keymgmt(EVP_PKEY * pkey,EVP_KEYMGMT * keymgmt)1638 int EVP_PKEY_set_type_by_keymgmt(EVP_PKEY *pkey, EVP_KEYMGMT *keymgmt)
1639 {
1640 #ifndef FIPS_MODULE
1641 # define EVP_PKEY_TYPE_STR str[0]
1642 # define EVP_PKEY_TYPE_STRLEN (str[0] == NULL ? -1 : (int)strlen(str[0]))
1643     /*
1644      * Find at most two strings that have an associated EVP_PKEY_ASN1_METHOD
1645      * Ideally, only one should be found.  If two (or more) are found, the
1646      * match is ambiguous.  This should never happen, but...
1647      */
1648     const char *str[2] = { NULL, NULL };
1649 
1650     if (!EVP_KEYMGMT_names_do_all(keymgmt, find_ameth, &str)
1651             || str[1] != NULL) {
1652         ERR_raise(ERR_LIB_EVP, ERR_R_INTERNAL_ERROR);
1653         return 0;
1654     }
1655 #else
1656 # define EVP_PKEY_TYPE_STR NULL
1657 # define EVP_PKEY_TYPE_STRLEN -1
1658 #endif
1659     return pkey_set_type(pkey, NULL, EVP_PKEY_NONE,
1660                          EVP_PKEY_TYPE_STR, EVP_PKEY_TYPE_STRLEN,
1661                          keymgmt);
1662 
1663 #undef EVP_PKEY_TYPE_STR
1664 #undef EVP_PKEY_TYPE_STRLEN
1665 }
1666 
EVP_PKEY_up_ref(EVP_PKEY * pkey)1667 int EVP_PKEY_up_ref(EVP_PKEY *pkey)
1668 {
1669     int i;
1670 
1671     if (CRYPTO_UP_REF(&pkey->references, &i) <= 0)
1672         return 0;
1673 
1674     REF_PRINT_COUNT("EVP_PKEY", pkey);
1675     REF_ASSERT_ISNT(i < 2);
1676     return ((i > 1) ? 1 : 0);
1677 }
1678 
1679 #ifndef FIPS_MODULE
EVP_PKEY_dup(EVP_PKEY * pkey)1680 EVP_PKEY *EVP_PKEY_dup(EVP_PKEY *pkey)
1681 {
1682     EVP_PKEY *dup_pk;
1683 
1684     if (pkey == NULL) {
1685         ERR_raise(ERR_LIB_EVP, ERR_R_PASSED_NULL_PARAMETER);
1686         return NULL;
1687     }
1688 
1689     if ((dup_pk = EVP_PKEY_new()) == NULL)
1690         return NULL;
1691 
1692     if (evp_pkey_is_blank(pkey))
1693         goto done;
1694 
1695     if (evp_pkey_is_provided(pkey)) {
1696         if (!evp_keymgmt_util_copy(dup_pk, pkey,
1697                                    OSSL_KEYMGMT_SELECT_ALL))
1698             goto err;
1699         goto done;
1700     }
1701 
1702     if (evp_pkey_is_legacy(pkey)) {
1703         const EVP_PKEY_ASN1_METHOD *ameth = pkey->ameth;
1704 
1705         if (ameth == NULL || ameth->copy == NULL) {
1706             if (pkey->pkey.ptr == NULL /* empty key, just set type */
1707                 && EVP_PKEY_set_type(dup_pk, pkey->type) != 0)
1708                 goto done;
1709             ERR_raise(ERR_LIB_EVP, EVP_R_UNSUPPORTED_KEY_TYPE);
1710             goto err;
1711         }
1712         if (!ameth->copy(dup_pk, pkey))
1713             goto err;
1714         goto done;
1715     }
1716 
1717     goto err;
1718 done:
1719     /* copy auxiliary data */
1720     if (!CRYPTO_dup_ex_data(CRYPTO_EX_INDEX_EVP_PKEY,
1721                             &dup_pk->ex_data, &pkey->ex_data))
1722         goto err;
1723 
1724     if (pkey->attributes != NULL) {
1725         if ((dup_pk->attributes = ossl_x509at_dup(pkey->attributes)) == NULL)
1726             goto err;
1727     }
1728     return dup_pk;
1729 err:
1730     EVP_PKEY_free(dup_pk);
1731     return NULL;
1732 }
1733 
evp_pkey_free_legacy(EVP_PKEY * x)1734 void evp_pkey_free_legacy(EVP_PKEY *x)
1735 {
1736     const EVP_PKEY_ASN1_METHOD *ameth = x->ameth;
1737     ENGINE *tmpe = NULL;
1738 
1739     if (ameth == NULL && x->legacy_cache_pkey.ptr != NULL)
1740         ameth = EVP_PKEY_asn1_find(&tmpe, x->type);
1741 
1742     if (ameth != NULL) {
1743         if (x->legacy_cache_pkey.ptr != NULL) {
1744             /*
1745              * We should never have both a legacy origin key, and a key in the
1746              * legacy cache.
1747              */
1748             assert(x->pkey.ptr == NULL);
1749             /*
1750              * For the purposes of freeing we make the legacy cache look like
1751              * a legacy origin key.
1752              */
1753             x->pkey = x->legacy_cache_pkey;
1754             x->legacy_cache_pkey.ptr = NULL;
1755         }
1756         if (ameth->pkey_free != NULL)
1757             ameth->pkey_free(x);
1758         x->pkey.ptr = NULL;
1759     }
1760 # ifndef OPENSSL_NO_ENGINE
1761     ENGINE_finish(tmpe);
1762     ENGINE_finish(x->engine);
1763     x->engine = NULL;
1764     ENGINE_finish(x->pmeth_engine);
1765     x->pmeth_engine = NULL;
1766 # endif
1767 }
1768 #endif  /* FIPS_MODULE */
1769 
evp_pkey_free_it(EVP_PKEY * x)1770 static void evp_pkey_free_it(EVP_PKEY *x)
1771 {
1772     /* internal function; x is never NULL */
1773     evp_keymgmt_util_clear_operation_cache(x);
1774 #ifndef FIPS_MODULE
1775     evp_pkey_free_legacy(x);
1776 #endif
1777 
1778     if (x->keymgmt != NULL) {
1779         evp_keymgmt_freedata(x->keymgmt, x->keydata);
1780         EVP_KEYMGMT_free(x->keymgmt);
1781         x->keymgmt = NULL;
1782         x->keydata = NULL;
1783     }
1784     x->type = EVP_PKEY_NONE;
1785 }
1786 
EVP_PKEY_free(EVP_PKEY * x)1787 void EVP_PKEY_free(EVP_PKEY *x)
1788 {
1789     int i;
1790 
1791     if (x == NULL)
1792         return;
1793 
1794     CRYPTO_DOWN_REF(&x->references, &i);
1795     REF_PRINT_COUNT("EVP_PKEY", x);
1796     if (i > 0)
1797         return;
1798     REF_ASSERT_ISNT(i < 0);
1799     evp_pkey_free_it(x);
1800 #ifndef FIPS_MODULE
1801     CRYPTO_free_ex_data(CRYPTO_EX_INDEX_EVP_PKEY, x, &x->ex_data);
1802 #endif
1803     CRYPTO_THREAD_lock_free(x->lock);
1804     CRYPTO_FREE_REF(&x->references);
1805 #ifndef FIPS_MODULE
1806     sk_X509_ATTRIBUTE_pop_free(x->attributes, X509_ATTRIBUTE_free);
1807 #endif
1808     OPENSSL_free(x);
1809 }
1810 
EVP_PKEY_get_size(const EVP_PKEY * pkey)1811 int EVP_PKEY_get_size(const EVP_PKEY *pkey)
1812 {
1813     int size = 0;
1814 
1815     if (pkey != NULL) {
1816         size = pkey->cache.size;
1817 #ifndef FIPS_MODULE
1818         if (pkey->ameth != NULL && pkey->ameth->pkey_size != NULL)
1819             size = pkey->ameth->pkey_size(pkey);
1820 #endif
1821     }
1822     if (size <= 0) {
1823         ERR_raise(ERR_LIB_EVP, EVP_R_UNKNOWN_MAX_SIZE);
1824         return 0;
1825     }
1826     return size;
1827 }
1828 
EVP_PKEY_get0_description(const EVP_PKEY * pkey)1829 const char *EVP_PKEY_get0_description(const EVP_PKEY *pkey)
1830 {
1831     if (!evp_pkey_is_assigned(pkey))
1832         return NULL;
1833 
1834     if (evp_pkey_is_provided(pkey) && pkey->keymgmt->description != NULL)
1835         return pkey->keymgmt->description;
1836 #ifndef FIPS_MODULE
1837     if (pkey->ameth != NULL)
1838         return pkey->ameth->info;
1839 #endif
1840     return NULL;
1841 }
1842 
evp_pkey_export_to_provider(EVP_PKEY * pk,OSSL_LIB_CTX * libctx,EVP_KEYMGMT ** keymgmt,const char * propquery)1843 void *evp_pkey_export_to_provider(EVP_PKEY *pk, OSSL_LIB_CTX *libctx,
1844                                   EVP_KEYMGMT **keymgmt,
1845                                   const char *propquery)
1846 {
1847     EVP_KEYMGMT *allocated_keymgmt = NULL;
1848     EVP_KEYMGMT *tmp_keymgmt = NULL;
1849     int selection = OSSL_KEYMGMT_SELECT_ALL;
1850     void *keydata = NULL;
1851     int check;
1852 
1853     if (pk == NULL)
1854         return NULL;
1855 
1856     /* No key data => nothing to export */
1857     check = 1;
1858 #ifndef FIPS_MODULE
1859     check = check && pk->pkey.ptr == NULL;
1860 #endif
1861     check = check && pk->keydata == NULL;
1862     if (check)
1863         return NULL;
1864 
1865 #ifndef FIPS_MODULE
1866     if (pk->pkey.ptr != NULL) {
1867         /*
1868          * If the legacy key doesn't have an dirty counter or export function,
1869          * give up
1870          */
1871         if (pk->ameth->dirty_cnt == NULL || pk->ameth->export_to == NULL)
1872             return NULL;
1873     }
1874 #endif
1875 
1876     if (keymgmt != NULL) {
1877         tmp_keymgmt = *keymgmt;
1878         *keymgmt = NULL;
1879     }
1880 
1881     /*
1882      * If no keymgmt was given or found, get a default keymgmt.  We do so by
1883      * letting EVP_PKEY_CTX_new_from_pkey() do it for us, then we steal it.
1884      */
1885     if (tmp_keymgmt == NULL) {
1886         EVP_PKEY_CTX *ctx = EVP_PKEY_CTX_new_from_pkey(libctx, pk, propquery);
1887 
1888         if (ctx == NULL)
1889             goto end;
1890         allocated_keymgmt = tmp_keymgmt = ctx->keymgmt;
1891         ctx->keymgmt = NULL;
1892         EVP_PKEY_CTX_free(ctx);
1893     }
1894 
1895     /* If there's still no keymgmt to be had, give up */
1896     if (tmp_keymgmt == NULL)
1897         goto end;
1898 
1899 #ifndef FIPS_MODULE
1900     if (pk->pkey.ptr != NULL) {
1901         OP_CACHE_ELEM *op;
1902 
1903         /*
1904          * If the legacy "origin" hasn't changed since last time, we try
1905          * to find our keymgmt in the operation cache.  If it has changed,
1906          * |i| remains zero, and we will clear the cache further down.
1907          */
1908         if (pk->ameth->dirty_cnt(pk) == pk->dirty_cnt_copy) {
1909             if (!CRYPTO_THREAD_read_lock(pk->lock))
1910                 goto end;
1911             op = evp_keymgmt_util_find_operation_cache(pk, tmp_keymgmt,
1912                                                        selection);
1913 
1914             /*
1915              * If |tmp_keymgmt| is present in the operation cache, it means
1916              * that export doesn't need to be redone.  In that case, we take
1917              * token copies of the cached pointers, to have token success
1918              * values to return. It is possible (e.g. in a no-cached-fetch
1919              * build), for op->keymgmt to be a different pointer to tmp_keymgmt
1920              * even though the name/provider must be the same. In other words
1921              * the keymgmt instance may be different but still equivalent, i.e.
1922              * same algorithm/provider instance - but we make the simplifying
1923              * assumption that the keydata can be used with either keymgmt
1924              * instance. Not doing so introduces significant complexity and
1925              * probably requires refactoring - since we would have to ripple
1926              * the change in keymgmt instance up the call chain.
1927              */
1928             if (op != NULL && op->keymgmt != NULL) {
1929                 keydata = op->keydata;
1930                 CRYPTO_THREAD_unlock(pk->lock);
1931                 goto end;
1932             }
1933             CRYPTO_THREAD_unlock(pk->lock);
1934         }
1935 
1936         /* Make sure that the keymgmt key type matches the legacy NID */
1937         if (!EVP_KEYMGMT_is_a(tmp_keymgmt, OBJ_nid2sn(pk->type)))
1938             goto end;
1939 
1940         if ((keydata = evp_keymgmt_newdata(tmp_keymgmt)) == NULL)
1941             goto end;
1942 
1943         if (!pk->ameth->export_to(pk, keydata, tmp_keymgmt->import,
1944                                   libctx, propquery)) {
1945             evp_keymgmt_freedata(tmp_keymgmt, keydata);
1946             keydata = NULL;
1947             goto end;
1948         }
1949 
1950         /*
1951          * If the dirty counter changed since last time, then clear the
1952          * operation cache.  In that case, we know that |i| is zero.  Just
1953          * in case this is a re-export, we increment then decrement the
1954          * keymgmt reference counter.
1955          */
1956         if (!EVP_KEYMGMT_up_ref(tmp_keymgmt)) { /* refcnt++ */
1957             evp_keymgmt_freedata(tmp_keymgmt, keydata);
1958             keydata = NULL;
1959             goto end;
1960         }
1961 
1962         if (!CRYPTO_THREAD_write_lock(pk->lock))
1963             goto end;
1964         if (pk->ameth->dirty_cnt(pk) != pk->dirty_cnt_copy
1965                 && !evp_keymgmt_util_clear_operation_cache(pk)) {
1966             CRYPTO_THREAD_unlock(pk->lock);
1967             evp_keymgmt_freedata(tmp_keymgmt, keydata);
1968             keydata = NULL;
1969             EVP_KEYMGMT_free(tmp_keymgmt);
1970             goto end;
1971         }
1972         EVP_KEYMGMT_free(tmp_keymgmt); /* refcnt-- */
1973 
1974         /* Check to make sure some other thread didn't get there first */
1975         op = evp_keymgmt_util_find_operation_cache(pk, tmp_keymgmt, selection);
1976         if (op != NULL && op->keymgmt != NULL) {
1977             void *tmp_keydata = op->keydata;
1978 
1979             CRYPTO_THREAD_unlock(pk->lock);
1980             evp_keymgmt_freedata(tmp_keymgmt, keydata);
1981             keydata = tmp_keydata;
1982             goto end;
1983         }
1984 
1985         /* Add the new export to the operation cache */
1986         if (!evp_keymgmt_util_cache_keydata(pk, tmp_keymgmt, keydata,
1987                                             selection)) {
1988             CRYPTO_THREAD_unlock(pk->lock);
1989             evp_keymgmt_freedata(tmp_keymgmt, keydata);
1990             keydata = NULL;
1991             goto end;
1992         }
1993 
1994         /* Synchronize the dirty count */
1995         pk->dirty_cnt_copy = pk->ameth->dirty_cnt(pk);
1996 
1997         CRYPTO_THREAD_unlock(pk->lock);
1998         goto end;
1999     }
2000 #endif  /* FIPS_MODULE */
2001 
2002     keydata = evp_keymgmt_util_export_to_provider(pk, tmp_keymgmt, selection);
2003 
2004  end:
2005     /*
2006      * If nothing was exported, |tmp_keymgmt| might point at a freed
2007      * EVP_KEYMGMT, so we clear it to be safe.  It shouldn't be useful for
2008      * the caller either way in that case.
2009      */
2010     if (keydata == NULL)
2011         tmp_keymgmt = NULL;
2012 
2013     if (keymgmt != NULL && tmp_keymgmt != NULL) {
2014         *keymgmt = tmp_keymgmt;
2015         allocated_keymgmt = NULL;
2016     }
2017 
2018     EVP_KEYMGMT_free(allocated_keymgmt);
2019     return keydata;
2020 }
2021 
2022 #ifndef FIPS_MODULE
evp_pkey_copy_downgraded(EVP_PKEY ** dest,const EVP_PKEY * src)2023 int evp_pkey_copy_downgraded(EVP_PKEY **dest, const EVP_PKEY *src)
2024 {
2025     EVP_PKEY *allocpkey = NULL;
2026 
2027     if (!ossl_assert(dest != NULL))
2028         return 0;
2029 
2030     if (evp_pkey_is_assigned(src) && evp_pkey_is_provided(src)) {
2031         EVP_KEYMGMT *keymgmt = src->keymgmt;
2032         void *keydata = src->keydata;
2033         int type = src->type;
2034         const char *keytype = NULL;
2035 
2036         keytype = EVP_KEYMGMT_get0_name(keymgmt);
2037 
2038         /*
2039          * If the type is EVP_PKEY_NONE, then we have a problem somewhere
2040          * else in our code.  If it's not one of the well known EVP_PKEY_xxx
2041          * values, it should at least be EVP_PKEY_KEYMGMT at this point.
2042          * The check is kept as a safety measure.
2043          */
2044         if (!ossl_assert(type != EVP_PKEY_NONE)) {
2045             ERR_raise_data(ERR_LIB_EVP, ERR_R_INTERNAL_ERROR,
2046                            "keymgmt key type = %s but legacy type = EVP_PKEY_NONE",
2047                            keytype);
2048             return 0;
2049         }
2050 
2051         /* Prefer the legacy key type name for error reporting */
2052         if (type != EVP_PKEY_KEYMGMT)
2053             keytype = OBJ_nid2sn(type);
2054 
2055         /* Make sure we have a clean slate to copy into */
2056         if (*dest == NULL) {
2057             allocpkey = *dest = EVP_PKEY_new();
2058             if (*dest == NULL) {
2059                 ERR_raise(ERR_LIB_EVP, ERR_R_EVP_LIB);
2060                 return 0;
2061             }
2062         } else {
2063             evp_pkey_free_it(*dest);
2064         }
2065 
2066         if (EVP_PKEY_set_type(*dest, type)) {
2067             /* If the key is typed but empty, we're done */
2068             if (keydata == NULL)
2069                 return 1;
2070 
2071             if ((*dest)->ameth->import_from == NULL) {
2072                 ERR_raise_data(ERR_LIB_EVP, EVP_R_NO_IMPORT_FUNCTION,
2073                                "key type = %s", keytype);
2074             } else {
2075                 /*
2076                  * We perform the export in the same libctx as the keymgmt
2077                  * that we are using.
2078                  */
2079                 OSSL_LIB_CTX *libctx =
2080                     ossl_provider_libctx(keymgmt->prov);
2081                 EVP_PKEY_CTX *pctx =
2082                     EVP_PKEY_CTX_new_from_pkey(libctx, *dest, NULL);
2083 
2084                 if (pctx == NULL)
2085                     ERR_raise(ERR_LIB_EVP, ERR_R_EVP_LIB);
2086 
2087                 if (pctx != NULL
2088                     && evp_keymgmt_export(keymgmt, keydata,
2089                                           OSSL_KEYMGMT_SELECT_ALL,
2090                                           (*dest)->ameth->import_from,
2091                                           pctx)) {
2092                     /* Synchronize the dirty count */
2093                     (*dest)->dirty_cnt_copy = (*dest)->ameth->dirty_cnt(*dest);
2094 
2095                     EVP_PKEY_CTX_free(pctx);
2096                     return 1;
2097                 }
2098                 EVP_PKEY_CTX_free(pctx);
2099             }
2100 
2101             ERR_raise_data(ERR_LIB_EVP, EVP_R_KEYMGMT_EXPORT_FAILURE,
2102                            "key type = %s", keytype);
2103         }
2104     }
2105 
2106     if (allocpkey != NULL) {
2107         EVP_PKEY_free(allocpkey);
2108         *dest = NULL;
2109     }
2110     return 0;
2111 }
2112 
evp_pkey_get_legacy(EVP_PKEY * pk)2113 void *evp_pkey_get_legacy(EVP_PKEY *pk)
2114 {
2115     EVP_PKEY *tmp_copy = NULL;
2116     void *ret = NULL;
2117 
2118     if (!ossl_assert(pk != NULL))
2119         return NULL;
2120 
2121     /*
2122      * If this isn't an assigned provider side key, we just use any existing
2123      * origin legacy key.
2124      */
2125     if (!evp_pkey_is_assigned(pk))
2126         return NULL;
2127     if (!evp_pkey_is_provided(pk))
2128         return pk->pkey.ptr;
2129 
2130     if (!CRYPTO_THREAD_read_lock(pk->lock))
2131         return NULL;
2132 
2133     ret = pk->legacy_cache_pkey.ptr;
2134 
2135     if (!CRYPTO_THREAD_unlock(pk->lock))
2136         return NULL;
2137 
2138     if (ret != NULL)
2139         return ret;
2140 
2141     if (!evp_pkey_copy_downgraded(&tmp_copy, pk))
2142         goto err;
2143 
2144     if (!CRYPTO_THREAD_write_lock(pk->lock))
2145         goto err;
2146 
2147     /* Check again in case some other thread has updated it in the meantime */
2148     ret = pk->legacy_cache_pkey.ptr;
2149     if (ret == NULL) {
2150         /* Steal the legacy key reference from the temporary copy */
2151         ret = pk->legacy_cache_pkey.ptr = tmp_copy->pkey.ptr;
2152         tmp_copy->pkey.ptr = NULL;
2153     }
2154 
2155     if (!CRYPTO_THREAD_unlock(pk->lock)) {
2156         ret = NULL;
2157         goto err;
2158     }
2159 
2160  err:
2161     EVP_PKEY_free(tmp_copy);
2162 
2163     return ret;
2164 }
2165 #endif  /* FIPS_MODULE */
2166 
EVP_PKEY_get_bn_param(const EVP_PKEY * pkey,const char * key_name,BIGNUM ** bn)2167 int EVP_PKEY_get_bn_param(const EVP_PKEY *pkey, const char *key_name,
2168                           BIGNUM **bn)
2169 {
2170     int ret = 0;
2171     OSSL_PARAM params[2];
2172     unsigned char buffer[2048];
2173     unsigned char *buf = NULL;
2174     size_t buf_sz = 0;
2175 
2176     if (key_name == NULL
2177         || bn == NULL)
2178         return 0;
2179 
2180     memset(buffer, 0, sizeof(buffer));
2181     params[0] = OSSL_PARAM_construct_BN(key_name, buffer, sizeof(buffer));
2182     params[1] = OSSL_PARAM_construct_end();
2183     if (!EVP_PKEY_get_params(pkey, params)) {
2184         if (!OSSL_PARAM_modified(params) || params[0].return_size == 0)
2185             return 0;
2186         buf_sz = params[0].return_size;
2187         /*
2188          * If it failed because the buffer was too small then allocate the
2189          * required buffer size and retry.
2190          */
2191         buf = OPENSSL_zalloc(buf_sz);
2192         if (buf == NULL)
2193             return 0;
2194         params[0].data = buf;
2195         params[0].data_size = buf_sz;
2196 
2197         if (!EVP_PKEY_get_params(pkey, params))
2198             goto err;
2199     }
2200     /* Fail if the param was not found */
2201     if (!OSSL_PARAM_modified(params))
2202         goto err;
2203     ret = OSSL_PARAM_get_BN(params, bn);
2204 err:
2205     if (buf != NULL) {
2206         if (OSSL_PARAM_modified(params))
2207             OPENSSL_clear_free(buf, buf_sz);
2208         else
2209             OPENSSL_free(buf);
2210     } else if (OSSL_PARAM_modified(params)) {
2211         OPENSSL_cleanse(buffer, params[0].data_size);
2212     }
2213     return ret;
2214 }
2215 
EVP_PKEY_get_octet_string_param(const EVP_PKEY * pkey,const char * key_name,unsigned char * buf,size_t max_buf_sz,size_t * out_len)2216 int EVP_PKEY_get_octet_string_param(const EVP_PKEY *pkey, const char *key_name,
2217                                     unsigned char *buf, size_t max_buf_sz,
2218                                     size_t *out_len)
2219 {
2220     OSSL_PARAM params[2];
2221     int ret1 = 0, ret2 = 0;
2222 
2223     if (key_name == NULL)
2224         return 0;
2225 
2226     params[0] = OSSL_PARAM_construct_octet_string(key_name, buf, max_buf_sz);
2227     params[1] = OSSL_PARAM_construct_end();
2228     if ((ret1 = EVP_PKEY_get_params(pkey, params)))
2229         ret2 = OSSL_PARAM_modified(params);
2230     if (ret2 && out_len != NULL)
2231         *out_len = params[0].return_size;
2232     return ret1 && ret2;
2233 }
2234 
EVP_PKEY_get_utf8_string_param(const EVP_PKEY * pkey,const char * key_name,char * str,size_t max_buf_sz,size_t * out_len)2235 int EVP_PKEY_get_utf8_string_param(const EVP_PKEY *pkey, const char *key_name,
2236                                     char *str, size_t max_buf_sz,
2237                                     size_t *out_len)
2238 {
2239     OSSL_PARAM params[2];
2240     int ret1 = 0, ret2 = 0;
2241 
2242     if (key_name == NULL)
2243         return 0;
2244 
2245     params[0] = OSSL_PARAM_construct_utf8_string(key_name, str, max_buf_sz);
2246     params[1] = OSSL_PARAM_construct_end();
2247     if ((ret1 = EVP_PKEY_get_params(pkey, params)))
2248         ret2 = OSSL_PARAM_modified(params);
2249     if (ret2 && out_len != NULL)
2250         *out_len = params[0].return_size;
2251 
2252     if (ret2 && params[0].return_size == max_buf_sz)
2253         /* There was no space for a NUL byte */
2254         return 0;
2255     /* Add a terminating NUL byte for good measure */
2256     if (ret2 && str != NULL)
2257         str[params[0].return_size] = '\0';
2258 
2259     return ret1 && ret2;
2260 }
2261 
EVP_PKEY_get_int_param(const EVP_PKEY * pkey,const char * key_name,int * out)2262 int EVP_PKEY_get_int_param(const EVP_PKEY *pkey, const char *key_name,
2263                            int *out)
2264 {
2265     OSSL_PARAM params[2];
2266 
2267     if (key_name == NULL)
2268         return 0;
2269 
2270     params[0] = OSSL_PARAM_construct_int(key_name, out);
2271     params[1] = OSSL_PARAM_construct_end();
2272     return EVP_PKEY_get_params(pkey, params)
2273         && OSSL_PARAM_modified(params);
2274 }
2275 
EVP_PKEY_get_size_t_param(const EVP_PKEY * pkey,const char * key_name,size_t * out)2276 int EVP_PKEY_get_size_t_param(const EVP_PKEY *pkey, const char *key_name,
2277                               size_t *out)
2278 {
2279     OSSL_PARAM params[2];
2280 
2281     if (key_name == NULL)
2282         return 0;
2283 
2284     params[0] = OSSL_PARAM_construct_size_t(key_name, out);
2285     params[1] = OSSL_PARAM_construct_end();
2286     return EVP_PKEY_get_params(pkey, params)
2287         && OSSL_PARAM_modified(params);
2288 }
2289 
EVP_PKEY_set_int_param(EVP_PKEY * pkey,const char * key_name,int in)2290 int EVP_PKEY_set_int_param(EVP_PKEY *pkey, const char *key_name, int in)
2291 {
2292     OSSL_PARAM params[2];
2293 
2294     if (key_name == NULL)
2295         return 0;
2296 
2297     params[0] = OSSL_PARAM_construct_int(key_name, &in);
2298     params[1] = OSSL_PARAM_construct_end();
2299     return EVP_PKEY_set_params(pkey, params);
2300 }
2301 
EVP_PKEY_set_size_t_param(EVP_PKEY * pkey,const char * key_name,size_t in)2302 int EVP_PKEY_set_size_t_param(EVP_PKEY *pkey, const char *key_name, size_t in)
2303 {
2304     OSSL_PARAM params[2];
2305 
2306     if (key_name == NULL)
2307         return 0;
2308 
2309     params[0] = OSSL_PARAM_construct_size_t(key_name, &in);
2310     params[1] = OSSL_PARAM_construct_end();
2311     return EVP_PKEY_set_params(pkey, params);
2312 }
2313 
EVP_PKEY_set_bn_param(EVP_PKEY * pkey,const char * key_name,const BIGNUM * bn)2314 int EVP_PKEY_set_bn_param(EVP_PKEY *pkey, const char *key_name,
2315                           const BIGNUM *bn)
2316 {
2317     OSSL_PARAM params[2];
2318     unsigned char buffer[2048];
2319     int bsize = 0;
2320 
2321     if (key_name == NULL
2322         || bn == NULL
2323         || pkey == NULL
2324         || !evp_pkey_is_assigned(pkey))
2325         return 0;
2326 
2327     bsize = BN_num_bytes(bn);
2328     if (!ossl_assert(bsize <= (int)sizeof(buffer)))
2329         return 0;
2330 
2331     if (BN_bn2nativepad(bn, buffer, bsize) < 0)
2332         return 0;
2333     params[0] = OSSL_PARAM_construct_BN(key_name, buffer, bsize);
2334     params[1] = OSSL_PARAM_construct_end();
2335     return EVP_PKEY_set_params(pkey, params);
2336 }
2337 
EVP_PKEY_set_utf8_string_param(EVP_PKEY * pkey,const char * key_name,const char * str)2338 int EVP_PKEY_set_utf8_string_param(EVP_PKEY *pkey, const char *key_name,
2339                                    const char *str)
2340 {
2341     OSSL_PARAM params[2];
2342 
2343     if (key_name == NULL)
2344         return 0;
2345 
2346     params[0] = OSSL_PARAM_construct_utf8_string(key_name, (char *)str, 0);
2347     params[1] = OSSL_PARAM_construct_end();
2348     return EVP_PKEY_set_params(pkey, params);
2349 }
2350 
EVP_PKEY_set_octet_string_param(EVP_PKEY * pkey,const char * key_name,const unsigned char * buf,size_t bsize)2351 int EVP_PKEY_set_octet_string_param(EVP_PKEY *pkey, const char *key_name,
2352                                     const unsigned char *buf, size_t bsize)
2353 {
2354     OSSL_PARAM params[2];
2355 
2356     if (key_name == NULL)
2357         return 0;
2358 
2359     params[0] = OSSL_PARAM_construct_octet_string(key_name,
2360                                                   (unsigned char *)buf, bsize);
2361     params[1] = OSSL_PARAM_construct_end();
2362     return EVP_PKEY_set_params(pkey, params);
2363 }
2364 
EVP_PKEY_settable_params(const EVP_PKEY * pkey)2365 const OSSL_PARAM *EVP_PKEY_settable_params(const EVP_PKEY *pkey)
2366 {
2367     return (pkey != NULL && evp_pkey_is_provided(pkey))
2368         ? EVP_KEYMGMT_settable_params(pkey->keymgmt)
2369         : NULL;
2370 }
2371 
EVP_PKEY_set_params(EVP_PKEY * pkey,OSSL_PARAM params[])2372 int EVP_PKEY_set_params(EVP_PKEY *pkey, OSSL_PARAM params[])
2373 {
2374     if (pkey != NULL) {
2375         if (evp_pkey_is_provided(pkey)) {
2376             pkey->dirty_cnt++;
2377             return evp_keymgmt_set_params(pkey->keymgmt, pkey->keydata, params);
2378         }
2379 #ifndef FIPS_MODULE
2380         /*
2381          * We will hopefully never find the need to set individual data in
2382          * EVP_PKEYs with a legacy internal key, but we can't be entirely
2383          * sure.  This bit of code can be enabled if we find the need.  If
2384          * not, it can safely be removed when #legacy support is removed.
2385          */
2386 # if 0
2387         else if (evp_pkey_is_legacy(pkey)) {
2388             return evp_pkey_set_params_to_ctrl(pkey, params);
2389         }
2390 # endif
2391 #endif
2392     }
2393     ERR_raise(ERR_LIB_EVP, EVP_R_INVALID_KEY);
2394     return 0;
2395 }
2396 
EVP_PKEY_gettable_params(const EVP_PKEY * pkey)2397 const OSSL_PARAM *EVP_PKEY_gettable_params(const EVP_PKEY *pkey)
2398 {
2399     return (pkey != NULL && evp_pkey_is_provided(pkey))
2400         ? EVP_KEYMGMT_gettable_params(pkey->keymgmt)
2401         : NULL;
2402 }
2403 
EVP_PKEY_get_params(const EVP_PKEY * pkey,OSSL_PARAM params[])2404 int EVP_PKEY_get_params(const EVP_PKEY *pkey, OSSL_PARAM params[])
2405 {
2406     if (pkey != NULL) {
2407         if (evp_pkey_is_provided(pkey))
2408             return evp_keymgmt_get_params(pkey->keymgmt, pkey->keydata, params) > 0;
2409 #ifndef FIPS_MODULE
2410         else if (evp_pkey_is_legacy(pkey))
2411             return evp_pkey_get_params_to_ctrl(pkey, params) > 0;
2412 #endif
2413     }
2414     ERR_raise(ERR_LIB_EVP, EVP_R_INVALID_KEY);
2415     return 0;
2416 }
2417 
2418 #ifndef FIPS_MODULE
EVP_PKEY_get_ec_point_conv_form(const EVP_PKEY * pkey)2419 int EVP_PKEY_get_ec_point_conv_form(const EVP_PKEY *pkey)
2420 {
2421     char name[80];
2422     size_t name_len;
2423 
2424     if (pkey == NULL)
2425         return 0;
2426 
2427     if (pkey->keymgmt == NULL
2428             || pkey->keydata == NULL) {
2429 # ifndef OPENSSL_NO_EC
2430         /* Might work through the legacy route */
2431         const EC_KEY *ec = EVP_PKEY_get0_EC_KEY(pkey);
2432 
2433         if (ec == NULL)
2434             return 0;
2435 
2436         return EC_KEY_get_conv_form(ec);
2437 # else
2438         return 0;
2439 # endif
2440     }
2441 
2442     if (!EVP_PKEY_get_utf8_string_param(pkey,
2443                                         OSSL_PKEY_PARAM_EC_POINT_CONVERSION_FORMAT,
2444                                         name, sizeof(name), &name_len))
2445         return 0;
2446 
2447     if (strcmp(name, "uncompressed") == 0)
2448         return POINT_CONVERSION_UNCOMPRESSED;
2449 
2450     if (strcmp(name, "compressed") == 0)
2451         return POINT_CONVERSION_COMPRESSED;
2452 
2453     if (strcmp(name, "hybrid") == 0)
2454         return POINT_CONVERSION_HYBRID;
2455 
2456     return 0;
2457 }
2458 
EVP_PKEY_get_field_type(const EVP_PKEY * pkey)2459 int EVP_PKEY_get_field_type(const EVP_PKEY *pkey)
2460 {
2461     char fstr[80];
2462     size_t fstrlen;
2463 
2464     if (pkey == NULL)
2465         return 0;
2466 
2467     if (pkey->keymgmt == NULL
2468             || pkey->keydata == NULL) {
2469 # ifndef OPENSSL_NO_EC
2470         /* Might work through the legacy route */
2471         const EC_KEY *ec = EVP_PKEY_get0_EC_KEY(pkey);
2472         const EC_GROUP *grp;
2473 
2474         if (ec == NULL)
2475             return 0;
2476         grp = EC_KEY_get0_group(ec);
2477         if (grp == NULL)
2478             return 0;
2479 
2480         return EC_GROUP_get_field_type(grp);
2481 # else
2482         return 0;
2483 # endif
2484     }
2485 
2486     if (!EVP_PKEY_get_utf8_string_param(pkey, OSSL_PKEY_PARAM_EC_FIELD_TYPE,
2487                                         fstr, sizeof(fstr), &fstrlen))
2488         return 0;
2489 
2490     if (strcmp(fstr, SN_X9_62_prime_field) == 0)
2491         return NID_X9_62_prime_field;
2492     else if (strcmp(fstr, SN_X9_62_characteristic_two_field))
2493         return NID_X9_62_characteristic_two_field;
2494 
2495     return 0;
2496 }
2497 #endif
2498