2 * Public Key abstraction layer
\r
4 * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved
\r
5 * SPDX-License-Identifier: Apache-2.0
\r
7 * Licensed under the Apache License, Version 2.0 (the "License"); you may
\r
8 * not use this file except in compliance with the License.
\r
9 * You may obtain a copy of the License at
\r
11 * http://www.apache.org/licenses/LICENSE-2.0
\r
13 * Unless required by applicable law or agreed to in writing, software
\r
14 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
\r
15 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
\r
16 * See the License for the specific language governing permissions and
\r
17 * limitations under the License.
\r
19 * This file is part of mbed TLS (https://tls.mbed.org)
\r
22 #if !defined(MBEDTLS_CONFIG_FILE)
\r
23 #include "mbedtls/config.h"
\r
25 #include MBEDTLS_CONFIG_FILE
\r
28 #if defined(MBEDTLS_PK_C)
\r
29 #include "mbedtls/pk.h"
\r
30 #include "mbedtls/pk_internal.h"
\r
32 #include "mbedtls/platform_util.h"
\r
34 #if defined(MBEDTLS_RSA_C)
\r
35 #include "mbedtls/rsa.h"
\r
37 #if defined(MBEDTLS_ECP_C)
\r
38 #include "mbedtls/ecp.h"
\r
40 #if defined(MBEDTLS_ECDSA_C)
\r
41 #include "mbedtls/ecdsa.h"
\r
44 #if defined(MBEDTLS_USE_PSA_CRYPTO)
\r
45 #include "mbedtls/psa_util.h"
\r
51 /* Parameter validation macros based on platform_util.h */
\r
52 #define PK_VALIDATE_RET( cond ) \
\r
53 MBEDTLS_INTERNAL_VALIDATE_RET( cond, MBEDTLS_ERR_PK_BAD_INPUT_DATA )
\r
54 #define PK_VALIDATE( cond ) \
\r
55 MBEDTLS_INTERNAL_VALIDATE( cond )
\r
58 * Initialise a mbedtls_pk_context
\r
60 void mbedtls_pk_init( mbedtls_pk_context *ctx )
\r
62 PK_VALIDATE( ctx != NULL );
\r
64 ctx->pk_info = NULL;
\r
69 * Free (the components of) a mbedtls_pk_context
\r
71 void mbedtls_pk_free( mbedtls_pk_context *ctx )
\r
76 if ( ctx->pk_info != NULL )
\r
77 ctx->pk_info->ctx_free_func( ctx->pk_ctx );
\r
79 mbedtls_platform_zeroize( ctx, sizeof( mbedtls_pk_context ) );
\r
82 #if defined(MBEDTLS_ECDSA_C) && defined(MBEDTLS_ECP_RESTARTABLE)
\r
84 * Initialize a restart context
\r
86 void mbedtls_pk_restart_init( mbedtls_pk_restart_ctx *ctx )
\r
88 PK_VALIDATE( ctx != NULL );
\r
89 ctx->pk_info = NULL;
\r
94 * Free the components of a restart context
\r
96 void mbedtls_pk_restart_free( mbedtls_pk_restart_ctx *ctx )
\r
98 if( ctx == NULL || ctx->pk_info == NULL ||
\r
99 ctx->pk_info->rs_free_func == NULL )
\r
104 ctx->pk_info->rs_free_func( ctx->rs_ctx );
\r
106 ctx->pk_info = NULL;
\r
107 ctx->rs_ctx = NULL;
\r
109 #endif /* MBEDTLS_ECDSA_C && MBEDTLS_ECP_RESTARTABLE */
\r
112 * Get pk_info structure from type
\r
114 const mbedtls_pk_info_t * mbedtls_pk_info_from_type( mbedtls_pk_type_t pk_type )
\r
116 switch( pk_type ) {
\r
117 #if defined(MBEDTLS_RSA_C)
\r
118 case MBEDTLS_PK_RSA:
\r
119 return( &mbedtls_rsa_info );
\r
121 #if defined(MBEDTLS_ECP_C)
\r
122 case MBEDTLS_PK_ECKEY:
\r
123 return( &mbedtls_eckey_info );
\r
124 case MBEDTLS_PK_ECKEY_DH:
\r
125 return( &mbedtls_eckeydh_info );
\r
127 #if defined(MBEDTLS_ECDSA_C)
\r
128 case MBEDTLS_PK_ECDSA:
\r
129 return( &mbedtls_ecdsa_info );
\r
131 /* MBEDTLS_PK_RSA_ALT omitted on purpose */
\r
138 * Initialise context
\r
140 int mbedtls_pk_setup( mbedtls_pk_context *ctx, const mbedtls_pk_info_t *info )
\r
142 PK_VALIDATE_RET( ctx != NULL );
\r
143 if( info == NULL || ctx->pk_info != NULL )
\r
144 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
146 if( ( ctx->pk_ctx = info->ctx_alloc_func() ) == NULL )
\r
147 return( MBEDTLS_ERR_PK_ALLOC_FAILED );
\r
149 ctx->pk_info = info;
\r
154 #if defined(MBEDTLS_USE_PSA_CRYPTO)
\r
156 * Initialise a PSA-wrapping context
\r
158 int mbedtls_pk_setup_opaque( mbedtls_pk_context *ctx, const psa_key_handle_t key )
\r
160 const mbedtls_pk_info_t * const info = &mbedtls_pk_opaque_info;
\r
161 psa_key_handle_t *pk_ctx;
\r
162 psa_key_type_t type;
\r
164 if( ctx == NULL || ctx->pk_info != NULL )
\r
165 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
167 if( PSA_SUCCESS != psa_get_key_information( key, &type, NULL ) )
\r
168 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
170 /* Current implementation of can_do() relies on this. */
\r
171 if( ! PSA_KEY_TYPE_IS_ECC_KEYPAIR( type ) )
\r
172 return( MBEDTLS_ERR_PK_FEATURE_UNAVAILABLE) ;
\r
174 if( ( ctx->pk_ctx = info->ctx_alloc_func() ) == NULL )
\r
175 return( MBEDTLS_ERR_PK_ALLOC_FAILED );
\r
177 ctx->pk_info = info;
\r
179 pk_ctx = (psa_key_handle_t *) ctx->pk_ctx;
\r
184 #endif /* MBEDTLS_USE_PSA_CRYPTO */
\r
186 #if defined(MBEDTLS_PK_RSA_ALT_SUPPORT)
\r
188 * Initialize an RSA-alt context
\r
190 int mbedtls_pk_setup_rsa_alt( mbedtls_pk_context *ctx, void * key,
\r
191 mbedtls_pk_rsa_alt_decrypt_func decrypt_func,
\r
192 mbedtls_pk_rsa_alt_sign_func sign_func,
\r
193 mbedtls_pk_rsa_alt_key_len_func key_len_func )
\r
195 mbedtls_rsa_alt_context *rsa_alt;
\r
196 const mbedtls_pk_info_t *info = &mbedtls_rsa_alt_info;
\r
198 PK_VALIDATE_RET( ctx != NULL );
\r
199 if( ctx->pk_info != NULL )
\r
200 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
202 if( ( ctx->pk_ctx = info->ctx_alloc_func() ) == NULL )
\r
203 return( MBEDTLS_ERR_PK_ALLOC_FAILED );
\r
205 ctx->pk_info = info;
\r
207 rsa_alt = (mbedtls_rsa_alt_context *) ctx->pk_ctx;
\r
209 rsa_alt->key = key;
\r
210 rsa_alt->decrypt_func = decrypt_func;
\r
211 rsa_alt->sign_func = sign_func;
\r
212 rsa_alt->key_len_func = key_len_func;
\r
216 #endif /* MBEDTLS_PK_RSA_ALT_SUPPORT */
\r
219 * Tell if a PK can do the operations of the given type
\r
221 int mbedtls_pk_can_do( const mbedtls_pk_context *ctx, mbedtls_pk_type_t type )
\r
223 /* A context with null pk_info is not set up yet and can't do anything.
\r
224 * For backward compatibility, also accept NULL instead of a context
\r
226 if( ctx == NULL || ctx->pk_info == NULL )
\r
229 return( ctx->pk_info->can_do( type ) );
\r
233 * Helper for mbedtls_pk_sign and mbedtls_pk_verify
\r
235 static inline int pk_hashlen_helper( mbedtls_md_type_t md_alg, size_t *hash_len )
\r
237 const mbedtls_md_info_t *md_info;
\r
239 if( *hash_len != 0 )
\r
242 if( ( md_info = mbedtls_md_info_from_type( md_alg ) ) == NULL )
\r
245 *hash_len = mbedtls_md_get_size( md_info );
\r
249 #if defined(MBEDTLS_ECDSA_C) && defined(MBEDTLS_ECP_RESTARTABLE)
\r
251 * Helper to set up a restart context if needed
\r
253 static int pk_restart_setup( mbedtls_pk_restart_ctx *ctx,
\r
254 const mbedtls_pk_info_t *info )
\r
256 /* Don't do anything if already set up or invalid */
\r
257 if( ctx == NULL || ctx->pk_info != NULL )
\r
260 /* Should never happen when we're called */
\r
261 if( info->rs_alloc_func == NULL || info->rs_free_func == NULL )
\r
262 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
264 if( ( ctx->rs_ctx = info->rs_alloc_func() ) == NULL )
\r
265 return( MBEDTLS_ERR_PK_ALLOC_FAILED );
\r
267 ctx->pk_info = info;
\r
271 #endif /* MBEDTLS_ECDSA_C && MBEDTLS_ECP_RESTARTABLE */
\r
274 * Verify a signature (restartable)
\r
276 int mbedtls_pk_verify_restartable( mbedtls_pk_context *ctx,
\r
277 mbedtls_md_type_t md_alg,
\r
278 const unsigned char *hash, size_t hash_len,
\r
279 const unsigned char *sig, size_t sig_len,
\r
280 mbedtls_pk_restart_ctx *rs_ctx )
\r
282 PK_VALIDATE_RET( ctx != NULL );
\r
283 PK_VALIDATE_RET( ( md_alg == MBEDTLS_MD_NONE && hash_len == 0 ) ||
\r
285 PK_VALIDATE_RET( sig != NULL );
\r
287 if( ctx->pk_info == NULL ||
\r
288 pk_hashlen_helper( md_alg, &hash_len ) != 0 )
\r
289 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
291 #if defined(MBEDTLS_ECDSA_C) && defined(MBEDTLS_ECP_RESTARTABLE)
\r
292 /* optimization: use non-restartable version if restart disabled */
\r
293 if( rs_ctx != NULL &&
\r
294 mbedtls_ecp_restart_is_enabled() &&
\r
295 ctx->pk_info->verify_rs_func != NULL )
\r
299 if( ( ret = pk_restart_setup( rs_ctx, ctx->pk_info ) ) != 0 )
\r
302 ret = ctx->pk_info->verify_rs_func( ctx->pk_ctx,
\r
303 md_alg, hash, hash_len, sig, sig_len, rs_ctx->rs_ctx );
\r
305 if( ret != MBEDTLS_ERR_ECP_IN_PROGRESS )
\r
306 mbedtls_pk_restart_free( rs_ctx );
\r
310 #else /* MBEDTLS_ECDSA_C && MBEDTLS_ECP_RESTARTABLE */
\r
312 #endif /* MBEDTLS_ECDSA_C && MBEDTLS_ECP_RESTARTABLE */
\r
314 if( ctx->pk_info->verify_func == NULL )
\r
315 return( MBEDTLS_ERR_PK_TYPE_MISMATCH );
\r
317 return( ctx->pk_info->verify_func( ctx->pk_ctx, md_alg, hash, hash_len,
\r
322 * Verify a signature
\r
324 int mbedtls_pk_verify( mbedtls_pk_context *ctx, mbedtls_md_type_t md_alg,
\r
325 const unsigned char *hash, size_t hash_len,
\r
326 const unsigned char *sig, size_t sig_len )
\r
328 return( mbedtls_pk_verify_restartable( ctx, md_alg, hash, hash_len,
\r
329 sig, sig_len, NULL ) );
\r
333 * Verify a signature with options
\r
335 int mbedtls_pk_verify_ext( mbedtls_pk_type_t type, const void *options,
\r
336 mbedtls_pk_context *ctx, mbedtls_md_type_t md_alg,
\r
337 const unsigned char *hash, size_t hash_len,
\r
338 const unsigned char *sig, size_t sig_len )
\r
340 PK_VALIDATE_RET( ctx != NULL );
\r
341 PK_VALIDATE_RET( ( md_alg == MBEDTLS_MD_NONE && hash_len == 0 ) ||
\r
343 PK_VALIDATE_RET( sig != NULL );
\r
345 if( ctx->pk_info == NULL )
\r
346 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
348 if( ! mbedtls_pk_can_do( ctx, type ) )
\r
349 return( MBEDTLS_ERR_PK_TYPE_MISMATCH );
\r
351 if( type == MBEDTLS_PK_RSASSA_PSS )
\r
353 #if defined(MBEDTLS_RSA_C) && defined(MBEDTLS_PKCS1_V21)
\r
355 const mbedtls_pk_rsassa_pss_options *pss_opts;
\r
357 #if SIZE_MAX > UINT_MAX
\r
358 if( md_alg == MBEDTLS_MD_NONE && UINT_MAX < hash_len )
\r
359 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
360 #endif /* SIZE_MAX > UINT_MAX */
\r
362 if( options == NULL )
\r
363 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
365 pss_opts = (const mbedtls_pk_rsassa_pss_options *) options;
\r
367 if( sig_len < mbedtls_pk_get_len( ctx ) )
\r
368 return( MBEDTLS_ERR_RSA_VERIFY_FAILED );
\r
370 ret = mbedtls_rsa_rsassa_pss_verify_ext( mbedtls_pk_rsa( *ctx ),
\r
371 NULL, NULL, MBEDTLS_RSA_PUBLIC,
\r
372 md_alg, (unsigned int) hash_len, hash,
\r
373 pss_opts->mgf1_hash_id,
\r
374 pss_opts->expected_salt_len,
\r
379 if( sig_len > mbedtls_pk_get_len( ctx ) )
\r
380 return( MBEDTLS_ERR_PK_SIG_LEN_MISMATCH );
\r
384 return( MBEDTLS_ERR_PK_FEATURE_UNAVAILABLE );
\r
385 #endif /* MBEDTLS_RSA_C && MBEDTLS_PKCS1_V21 */
\r
388 /* General case: no options */
\r
389 if( options != NULL )
\r
390 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
392 return( mbedtls_pk_verify( ctx, md_alg, hash, hash_len, sig, sig_len ) );
\r
396 * Make a signature (restartable)
\r
398 int mbedtls_pk_sign_restartable( mbedtls_pk_context *ctx,
\r
399 mbedtls_md_type_t md_alg,
\r
400 const unsigned char *hash, size_t hash_len,
\r
401 unsigned char *sig, size_t *sig_len,
\r
402 int (*f_rng)(void *, unsigned char *, size_t), void *p_rng,
\r
403 mbedtls_pk_restart_ctx *rs_ctx )
\r
405 PK_VALIDATE_RET( ctx != NULL );
\r
406 PK_VALIDATE_RET( ( md_alg == MBEDTLS_MD_NONE && hash_len == 0 ) ||
\r
408 PK_VALIDATE_RET( sig != NULL );
\r
410 if( ctx->pk_info == NULL ||
\r
411 pk_hashlen_helper( md_alg, &hash_len ) != 0 )
\r
412 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
414 #if defined(MBEDTLS_ECDSA_C) && defined(MBEDTLS_ECP_RESTARTABLE)
\r
415 /* optimization: use non-restartable version if restart disabled */
\r
416 if( rs_ctx != NULL &&
\r
417 mbedtls_ecp_restart_is_enabled() &&
\r
418 ctx->pk_info->sign_rs_func != NULL )
\r
422 if( ( ret = pk_restart_setup( rs_ctx, ctx->pk_info ) ) != 0 )
\r
425 ret = ctx->pk_info->sign_rs_func( ctx->pk_ctx, md_alg,
\r
426 hash, hash_len, sig, sig_len, f_rng, p_rng, rs_ctx->rs_ctx );
\r
428 if( ret != MBEDTLS_ERR_ECP_IN_PROGRESS )
\r
429 mbedtls_pk_restart_free( rs_ctx );
\r
433 #else /* MBEDTLS_ECDSA_C && MBEDTLS_ECP_RESTARTABLE */
\r
435 #endif /* MBEDTLS_ECDSA_C && MBEDTLS_ECP_RESTARTABLE */
\r
437 if( ctx->pk_info->sign_func == NULL )
\r
438 return( MBEDTLS_ERR_PK_TYPE_MISMATCH );
\r
440 return( ctx->pk_info->sign_func( ctx->pk_ctx, md_alg, hash, hash_len,
\r
441 sig, sig_len, f_rng, p_rng ) );
\r
447 int mbedtls_pk_sign( mbedtls_pk_context *ctx, mbedtls_md_type_t md_alg,
\r
448 const unsigned char *hash, size_t hash_len,
\r
449 unsigned char *sig, size_t *sig_len,
\r
450 int (*f_rng)(void *, unsigned char *, size_t), void *p_rng )
\r
452 return( mbedtls_pk_sign_restartable( ctx, md_alg, hash, hash_len,
\r
453 sig, sig_len, f_rng, p_rng, NULL ) );
\r
459 int mbedtls_pk_decrypt( mbedtls_pk_context *ctx,
\r
460 const unsigned char *input, size_t ilen,
\r
461 unsigned char *output, size_t *olen, size_t osize,
\r
462 int (*f_rng)(void *, unsigned char *, size_t), void *p_rng )
\r
464 PK_VALIDATE_RET( ctx != NULL );
\r
465 PK_VALIDATE_RET( input != NULL || ilen == 0 );
\r
466 PK_VALIDATE_RET( output != NULL || osize == 0 );
\r
467 PK_VALIDATE_RET( olen != NULL );
\r
469 if( ctx->pk_info == NULL )
\r
470 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
472 if( ctx->pk_info->decrypt_func == NULL )
\r
473 return( MBEDTLS_ERR_PK_TYPE_MISMATCH );
\r
475 return( ctx->pk_info->decrypt_func( ctx->pk_ctx, input, ilen,
\r
476 output, olen, osize, f_rng, p_rng ) );
\r
482 int mbedtls_pk_encrypt( mbedtls_pk_context *ctx,
\r
483 const unsigned char *input, size_t ilen,
\r
484 unsigned char *output, size_t *olen, size_t osize,
\r
485 int (*f_rng)(void *, unsigned char *, size_t), void *p_rng )
\r
487 PK_VALIDATE_RET( ctx != NULL );
\r
488 PK_VALIDATE_RET( input != NULL || ilen == 0 );
\r
489 PK_VALIDATE_RET( output != NULL || osize == 0 );
\r
490 PK_VALIDATE_RET( olen != NULL );
\r
492 if( ctx->pk_info == NULL )
\r
493 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
495 if( ctx->pk_info->encrypt_func == NULL )
\r
496 return( MBEDTLS_ERR_PK_TYPE_MISMATCH );
\r
498 return( ctx->pk_info->encrypt_func( ctx->pk_ctx, input, ilen,
\r
499 output, olen, osize, f_rng, p_rng ) );
\r
503 * Check public-private key pair
\r
505 int mbedtls_pk_check_pair( const mbedtls_pk_context *pub, const mbedtls_pk_context *prv )
\r
507 PK_VALIDATE_RET( pub != NULL );
\r
508 PK_VALIDATE_RET( prv != NULL );
\r
510 if( pub->pk_info == NULL ||
\r
511 prv->pk_info == NULL )
\r
513 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
516 if( prv->pk_info->check_pair_func == NULL )
\r
517 return( MBEDTLS_ERR_PK_FEATURE_UNAVAILABLE );
\r
519 if( prv->pk_info->type == MBEDTLS_PK_RSA_ALT )
\r
521 if( pub->pk_info->type != MBEDTLS_PK_RSA )
\r
522 return( MBEDTLS_ERR_PK_TYPE_MISMATCH );
\r
526 if( pub->pk_info != prv->pk_info )
\r
527 return( MBEDTLS_ERR_PK_TYPE_MISMATCH );
\r
530 return( prv->pk_info->check_pair_func( pub->pk_ctx, prv->pk_ctx ) );
\r
534 * Get key size in bits
\r
536 size_t mbedtls_pk_get_bitlen( const mbedtls_pk_context *ctx )
\r
538 /* For backward compatibility, accept NULL or a context that
\r
539 * isn't set up yet, and return a fake value that should be safe. */
\r
540 if( ctx == NULL || ctx->pk_info == NULL )
\r
543 return( ctx->pk_info->get_bitlen( ctx->pk_ctx ) );
\r
547 * Export debug information
\r
549 int mbedtls_pk_debug( const mbedtls_pk_context *ctx, mbedtls_pk_debug_item *items )
\r
551 PK_VALIDATE_RET( ctx != NULL );
\r
552 if( ctx->pk_info == NULL )
\r
553 return( MBEDTLS_ERR_PK_BAD_INPUT_DATA );
\r
555 if( ctx->pk_info->debug_func == NULL )
\r
556 return( MBEDTLS_ERR_PK_TYPE_MISMATCH );
\r
558 ctx->pk_info->debug_func( ctx->pk_ctx, items );
\r
563 * Access the PK type name
\r
565 const char *mbedtls_pk_get_name( const mbedtls_pk_context *ctx )
\r
567 if( ctx == NULL || ctx->pk_info == NULL )
\r
568 return( "invalid PK" );
\r
570 return( ctx->pk_info->name );
\r
574 * Access the PK type
\r
576 mbedtls_pk_type_t mbedtls_pk_get_type( const mbedtls_pk_context *ctx )
\r
578 if( ctx == NULL || ctx->pk_info == NULL )
\r
579 return( MBEDTLS_PK_NONE );
\r
581 return( ctx->pk_info->type );
\r
584 #if defined(MBEDTLS_USE_PSA_CRYPTO)
\r
586 * Load the key to a PSA key slot,
\r
587 * then turn the PK context into a wrapper for that key slot.
\r
589 * Currently only works for EC private keys.
\r
591 int mbedtls_pk_wrap_as_opaque( mbedtls_pk_context *pk,
\r
592 psa_key_handle_t *slot,
\r
593 psa_algorithm_t hash_alg )
\r
595 #if !defined(MBEDTLS_ECP_C)
\r
596 return( MBEDTLS_ERR_PK_TYPE_MISMATCH );
\r
598 psa_key_handle_t key;
\r
599 const mbedtls_ecp_keypair *ec;
\r
600 unsigned char d[MBEDTLS_ECP_MAX_BYTES];
\r
602 psa_ecc_curve_t curve_id;
\r
603 psa_key_type_t key_type;
\r
604 psa_key_policy_t policy;
\r
607 /* export the private key material in the format PSA wants */
\r
608 if( mbedtls_pk_get_type( pk ) != MBEDTLS_PK_ECKEY )
\r
609 return( MBEDTLS_ERR_PK_TYPE_MISMATCH );
\r
611 ec = mbedtls_pk_ec( *pk );
\r
612 d_len = ( ec->grp.nbits + 7 ) / 8;
\r
613 if( ( ret = mbedtls_mpi_write_binary( &ec->d, d, d_len ) ) != 0 )
\r
616 curve_id = mbedtls_ecp_curve_info_from_grp_id( ec->grp.id )->tls_id;
\r
617 key_type = PSA_KEY_TYPE_ECC_KEYPAIR(
\r
618 mbedtls_psa_parse_tls_ecc_group ( curve_id ) );
\r
620 /* allocate a key slot */
\r
621 if( PSA_SUCCESS != psa_allocate_key( &key ) )
\r
622 return( MBEDTLS_ERR_PK_HW_ACCEL_FAILED );
\r
625 policy = psa_key_policy_init();
\r
626 psa_key_policy_set_usage( &policy, PSA_KEY_USAGE_SIGN,
\r
627 PSA_ALG_ECDSA(hash_alg) );
\r
628 if( PSA_SUCCESS != psa_set_key_policy( key, &policy ) )
\r
629 return( MBEDTLS_ERR_PK_HW_ACCEL_FAILED );
\r
631 /* import private key in slot */
\r
632 if( PSA_SUCCESS != psa_import_key( key, key_type, d, d_len ) )
\r
633 return( MBEDTLS_ERR_PK_HW_ACCEL_FAILED );
\r
635 /* remember slot number to be destroyed later by caller */
\r
638 /* make PK context wrap the key slot */
\r
639 mbedtls_pk_free( pk );
\r
640 mbedtls_pk_init( pk );
\r
642 return( mbedtls_pk_setup_opaque( pk, key ) );
\r
643 #endif /* MBEDTLS_ECP_C */
\r
645 #endif /* MBEDTLS_USE_PSA_CRYPTO */
\r
646 #endif /* MBEDTLS_PK_C */
\r