Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependents: TYBLE16_simple_data_logger TYBLE16_MP3_Air
pkparse.c
00001 /* 00002 * Public Key layer for parsing key files and structures 00003 * 00004 * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved 00005 * SPDX-License-Identifier: Apache-2.0 00006 * 00007 * Licensed under the Apache License, Version 2.0 (the "License"); you may 00008 * not use this file except in compliance with the License. 00009 * You may obtain a copy of the License at 00010 * 00011 * http://www.apache.org/licenses/LICENSE-2.0 00012 * 00013 * Unless required by applicable law or agreed to in writing, software 00014 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT 00015 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00016 * See the License for the specific language governing permissions and 00017 * limitations under the License. 00018 * 00019 * This file is part of mbed TLS (https://tls.mbed.org) 00020 */ 00021 00022 #if !defined(MBEDTLS_CONFIG_FILE) 00023 #include "mbedtls/config.h" 00024 #else 00025 #include MBEDTLS_CONFIG_FILE 00026 #endif 00027 00028 #if defined(MBEDTLS_PK_PARSE_C) 00029 00030 #include "mbedtls/pk.h" 00031 #include "mbedtls/asn1.h" 00032 #include "mbedtls/oid.h" 00033 #include "mbedtls/platform_util.h" 00034 00035 #include <string.h> 00036 00037 #if defined(MBEDTLS_RSA_C) 00038 #include "mbedtls/rsa.h" 00039 #endif 00040 #if defined(MBEDTLS_ECP_C) 00041 #include "mbedtls/ecp.h" 00042 #endif 00043 #if defined(MBEDTLS_ECDSA_C) 00044 #include "mbedtls/ecdsa.h" 00045 #endif 00046 #if defined(MBEDTLS_PEM_PARSE_C) 00047 #include "mbedtls/pem.h" 00048 #endif 00049 #if defined(MBEDTLS_PKCS5_C) 00050 #include "mbedtls/pkcs5.h" 00051 #endif 00052 #if defined(MBEDTLS_PKCS12_C) 00053 #include "mbedtls/pkcs12.h" 00054 #endif 00055 00056 #if defined(MBEDTLS_PLATFORM_C) 00057 #include "mbedtls/platform.h" 00058 #else 00059 #include <stdlib.h> 00060 #define mbedtls_calloc calloc 00061 #define mbedtls_free free 00062 #endif 00063 00064 /* Parameter validation macros based on platform_util.h */ 00065 #define PK_VALIDATE_RET( cond ) \ 00066 MBEDTLS_INTERNAL_VALIDATE_RET( cond, MBEDTLS_ERR_PK_BAD_INPUT_DATA ) 00067 #define PK_VALIDATE( cond ) \ 00068 MBEDTLS_INTERNAL_VALIDATE( cond ) 00069 00070 #if defined(MBEDTLS_FS_IO) 00071 /* 00072 * Load all data from a file into a given buffer. 00073 * 00074 * The file is expected to contain either PEM or DER encoded data. 00075 * A terminating null byte is always appended. It is included in the announced 00076 * length only if the data looks like it is PEM encoded. 00077 */ 00078 int mbedtls_pk_load_file( const char *path, unsigned char **buf, size_t *n ) 00079 { 00080 FILE *f; 00081 long size; 00082 00083 PK_VALIDATE_RET( path != NULL ); 00084 PK_VALIDATE_RET( buf != NULL ); 00085 PK_VALIDATE_RET( n != NULL ); 00086 00087 if( ( f = fopen( path, "rb" ) ) == NULL ) 00088 return( MBEDTLS_ERR_PK_FILE_IO_ERROR ); 00089 00090 fseek( f, 0, SEEK_END ); 00091 if( ( size = ftell( f ) ) == -1 ) 00092 { 00093 fclose( f ); 00094 return( MBEDTLS_ERR_PK_FILE_IO_ERROR ); 00095 } 00096 fseek( f, 0, SEEK_SET ); 00097 00098 *n = (size_t) size; 00099 00100 if( *n + 1 == 0 || 00101 ( *buf = mbedtls_calloc( 1, *n + 1 ) ) == NULL ) 00102 { 00103 fclose( f ); 00104 return( MBEDTLS_ERR_PK_ALLOC_FAILED ); 00105 } 00106 00107 if( fread( *buf, 1, *n, f ) != *n ) 00108 { 00109 fclose( f ); 00110 00111 mbedtls_platform_zeroize( *buf, *n ); 00112 mbedtls_free( *buf ); 00113 00114 return( MBEDTLS_ERR_PK_FILE_IO_ERROR ); 00115 } 00116 00117 fclose( f ); 00118 00119 (*buf)[*n] = '\0'; 00120 00121 if( strstr( (const char *) *buf, "-----BEGIN " ) != NULL ) 00122 ++*n; 00123 00124 return( 0 ); 00125 } 00126 00127 /* 00128 * Load and parse a private key 00129 */ 00130 int mbedtls_pk_parse_keyfile( mbedtls_pk_context *ctx, 00131 const char *path, const char *pwd ) 00132 { 00133 int ret; 00134 size_t n; 00135 unsigned char *buf; 00136 00137 PK_VALIDATE_RET( ctx != NULL ); 00138 PK_VALIDATE_RET( path != NULL ); 00139 00140 if( ( ret = mbedtls_pk_load_file( path, &buf, &n ) ) != 0 ) 00141 return( ret ); 00142 00143 if( pwd == NULL ) 00144 ret = mbedtls_pk_parse_key( ctx, buf, n, NULL, 0 ); 00145 else 00146 ret = mbedtls_pk_parse_key( ctx, buf, n, 00147 (const unsigned char *) pwd, strlen( pwd ) ); 00148 00149 mbedtls_platform_zeroize( buf, n ); 00150 mbedtls_free( buf ); 00151 00152 return( ret ); 00153 } 00154 00155 /* 00156 * Load and parse a public key 00157 */ 00158 int mbedtls_pk_parse_public_keyfile( mbedtls_pk_context *ctx, const char *path ) 00159 { 00160 int ret; 00161 size_t n; 00162 unsigned char *buf; 00163 00164 PK_VALIDATE_RET( ctx != NULL ); 00165 PK_VALIDATE_RET( path != NULL ); 00166 00167 if( ( ret = mbedtls_pk_load_file( path, &buf, &n ) ) != 0 ) 00168 return( ret ); 00169 00170 ret = mbedtls_pk_parse_public_key( ctx, buf, n ); 00171 00172 mbedtls_platform_zeroize( buf, n ); 00173 mbedtls_free( buf ); 00174 00175 return( ret ); 00176 } 00177 #endif /* MBEDTLS_FS_IO */ 00178 00179 #if defined(MBEDTLS_ECP_C) 00180 /* Minimally parse an ECParameters buffer to and mbedtls_asn1_buf 00181 * 00182 * ECParameters ::= CHOICE { 00183 * namedCurve OBJECT IDENTIFIER 00184 * specifiedCurve SpecifiedECDomain -- = SEQUENCE { ... } 00185 * -- implicitCurve NULL 00186 * } 00187 */ 00188 static int pk_get_ecparams( unsigned char **p, const unsigned char *end, 00189 mbedtls_asn1_buf *params ) 00190 { 00191 int ret; 00192 00193 if ( end - *p < 1 ) 00194 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + 00195 MBEDTLS_ERR_ASN1_OUT_OF_DATA ); 00196 00197 /* Tag may be either OID or SEQUENCE */ 00198 params->tag = **p; 00199 if( params->tag != MBEDTLS_ASN1_OID 00200 #if defined(MBEDTLS_PK_PARSE_EC_EXTENDED) 00201 && params->tag != ( MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE ) 00202 #endif 00203 ) 00204 { 00205 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + 00206 MBEDTLS_ERR_ASN1_UNEXPECTED_TAG ); 00207 } 00208 00209 if( ( ret = mbedtls_asn1_get_tag( p, end, ¶ms->len, params->tag ) ) != 0 ) 00210 { 00211 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00212 } 00213 00214 params->p = *p; 00215 *p += params->len; 00216 00217 if( *p != end ) 00218 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + 00219 MBEDTLS_ERR_ASN1_LENGTH_MISMATCH ); 00220 00221 return( 0 ); 00222 } 00223 00224 #if defined(MBEDTLS_PK_PARSE_EC_EXTENDED) 00225 /* 00226 * Parse a SpecifiedECDomain (SEC 1 C.2) and (mostly) fill the group with it. 00227 * WARNING: the resulting group should only be used with 00228 * pk_group_id_from_specified(), since its base point may not be set correctly 00229 * if it was encoded compressed. 00230 * 00231 * SpecifiedECDomain ::= SEQUENCE { 00232 * version SpecifiedECDomainVersion(ecdpVer1 | ecdpVer2 | ecdpVer3, ...), 00233 * fieldID FieldID {{FieldTypes}}, 00234 * curve Curve, 00235 * base ECPoint, 00236 * order INTEGER, 00237 * cofactor INTEGER OPTIONAL, 00238 * hash HashAlgorithm OPTIONAL, 00239 * ... 00240 * } 00241 * 00242 * We only support prime-field as field type, and ignore hash and cofactor. 00243 */ 00244 static int pk_group_from_specified( const mbedtls_asn1_buf *params, mbedtls_ecp_group *grp ) 00245 { 00246 int ret; 00247 unsigned char *p = params->p; 00248 const unsigned char * const end = params->p + params->len; 00249 const unsigned char *end_field, *end_curve; 00250 size_t len; 00251 int ver; 00252 00253 /* SpecifiedECDomainVersion ::= INTEGER { 1, 2, 3 } */ 00254 if( ( ret = mbedtls_asn1_get_int( &p, end, &ver ) ) != 0 ) 00255 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00256 00257 if( ver < 1 || ver > 3 ) 00258 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT ); 00259 00260 /* 00261 * FieldID { FIELD-ID:IOSet } ::= SEQUENCE { -- Finite field 00262 * fieldType FIELD-ID.&id({IOSet}), 00263 * parameters FIELD-ID.&Type({IOSet}{@fieldType}) 00264 * } 00265 */ 00266 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 00267 MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE ) ) != 0 ) 00268 return( ret ); 00269 00270 end_field = p + len; 00271 00272 /* 00273 * FIELD-ID ::= TYPE-IDENTIFIER 00274 * FieldTypes FIELD-ID ::= { 00275 * { Prime-p IDENTIFIED BY prime-field } | 00276 * { Characteristic-two IDENTIFIED BY characteristic-two-field } 00277 * } 00278 * prime-field OBJECT IDENTIFIER ::= { id-fieldType 1 } 00279 */ 00280 if( ( ret = mbedtls_asn1_get_tag( &p, end_field, &len, MBEDTLS_ASN1_OID ) ) != 0 ) 00281 return( ret ); 00282 00283 if( len != MBEDTLS_OID_SIZE( MBEDTLS_OID_ANSI_X9_62_PRIME_FIELD ) || 00284 memcmp( p, MBEDTLS_OID_ANSI_X9_62_PRIME_FIELD, len ) != 0 ) 00285 { 00286 return( MBEDTLS_ERR_PK_FEATURE_UNAVAILABLE ); 00287 } 00288 00289 p += len; 00290 00291 /* Prime-p ::= INTEGER -- Field of size p. */ 00292 if( ( ret = mbedtls_asn1_get_mpi( &p, end_field, &grp->P ) ) != 0 ) 00293 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00294 00295 grp->pbits = mbedtls_mpi_bitlen( &grp->P ); 00296 00297 if( p != end_field ) 00298 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + 00299 MBEDTLS_ERR_ASN1_LENGTH_MISMATCH ); 00300 00301 /* 00302 * Curve ::= SEQUENCE { 00303 * a FieldElement, 00304 * b FieldElement, 00305 * seed BIT STRING OPTIONAL 00306 * -- Shall be present if used in SpecifiedECDomain 00307 * -- with version equal to ecdpVer2 or ecdpVer3 00308 * } 00309 */ 00310 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 00311 MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE ) ) != 0 ) 00312 return( ret ); 00313 00314 end_curve = p + len; 00315 00316 /* 00317 * FieldElement ::= OCTET STRING 00318 * containing an integer in the case of a prime field 00319 */ 00320 if( ( ret = mbedtls_asn1_get_tag( &p, end_curve, &len, MBEDTLS_ASN1_OCTET_STRING ) ) != 0 || 00321 ( ret = mbedtls_mpi_read_binary( &grp->A , p, len ) ) != 0 ) 00322 { 00323 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00324 } 00325 00326 p += len; 00327 00328 if( ( ret = mbedtls_asn1_get_tag( &p, end_curve, &len, MBEDTLS_ASN1_OCTET_STRING ) ) != 0 || 00329 ( ret = mbedtls_mpi_read_binary( &grp->B , p, len ) ) != 0 ) 00330 { 00331 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00332 } 00333 00334 p += len; 00335 00336 /* Ignore seed BIT STRING OPTIONAL */ 00337 if( ( ret = mbedtls_asn1_get_tag( &p, end_curve, &len, MBEDTLS_ASN1_BIT_STRING ) ) == 0 ) 00338 p += len; 00339 00340 if( p != end_curve ) 00341 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + 00342 MBEDTLS_ERR_ASN1_LENGTH_MISMATCH ); 00343 00344 /* 00345 * ECPoint ::= OCTET STRING 00346 */ 00347 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, MBEDTLS_ASN1_OCTET_STRING ) ) != 0 ) 00348 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00349 00350 if( ( ret = mbedtls_ecp_point_read_binary( grp, &grp->G , 00351 ( const unsigned char *) p, len ) ) != 0 ) 00352 { 00353 /* 00354 * If we can't read the point because it's compressed, cheat by 00355 * reading only the X coordinate and the parity bit of Y. 00356 */ 00357 if( ret != MBEDTLS_ERR_ECP_FEATURE_UNAVAILABLE || 00358 ( p[0] != 0x02 && p[0] != 0x03 ) || 00359 len != mbedtls_mpi_size( &grp->P ) + 1 || 00360 mbedtls_mpi_read_binary( &grp->G .X , p + 1, len - 1 ) != 0 || 00361 mbedtls_mpi_lset( &grp->G .Y , p[0] - 2 ) != 0 || 00362 mbedtls_mpi_lset( &grp->G .Z , 1 ) != 0 ) 00363 { 00364 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT ); 00365 } 00366 } 00367 00368 p += len; 00369 00370 /* 00371 * order INTEGER 00372 */ 00373 if( ( ret = mbedtls_asn1_get_mpi( &p, end, &grp->N ) ) != 0 ) 00374 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00375 00376 grp->nbits = mbedtls_mpi_bitlen( &grp->N ); 00377 00378 /* 00379 * Allow optional elements by purposefully not enforcing p == end here. 00380 */ 00381 00382 return( 0 ); 00383 } 00384 00385 /* 00386 * Find the group id associated with an (almost filled) group as generated by 00387 * pk_group_from_specified(), or return an error if unknown. 00388 */ 00389 static int pk_group_id_from_group( const mbedtls_ecp_group *grp, mbedtls_ecp_group_id *grp_id ) 00390 { 00391 int ret = 0; 00392 mbedtls_ecp_group ref; 00393 const mbedtls_ecp_group_id *id; 00394 00395 mbedtls_ecp_group_init( &ref ); 00396 00397 for( id = mbedtls_ecp_grp_id_list(); *id != MBEDTLS_ECP_DP_NONE; id++ ) 00398 { 00399 /* Load the group associated to that id */ 00400 mbedtls_ecp_group_free( &ref ); 00401 MBEDTLS_MPI_CHK( mbedtls_ecp_group_load( &ref, *id ) ); 00402 00403 /* Compare to the group we were given, starting with easy tests */ 00404 if( grp->pbits == ref.pbits && grp->nbits == ref.nbits && 00405 mbedtls_mpi_cmp_mpi( &grp->P , &ref.P ) == 0 && 00406 mbedtls_mpi_cmp_mpi( &grp->A , &ref.A ) == 0 && 00407 mbedtls_mpi_cmp_mpi( &grp->B , &ref.B ) == 0 && 00408 mbedtls_mpi_cmp_mpi( &grp->N , &ref.N ) == 0 && 00409 mbedtls_mpi_cmp_mpi( &grp->G .X , &ref.G .X ) == 0 && 00410 mbedtls_mpi_cmp_mpi( &grp->G .Z , &ref.G .Z ) == 0 && 00411 /* For Y we may only know the parity bit, so compare only that */ 00412 mbedtls_mpi_get_bit( &grp->G .Y , 0 ) == mbedtls_mpi_get_bit( &ref.G .Y , 0 ) ) 00413 { 00414 break; 00415 } 00416 00417 } 00418 00419 cleanup: 00420 mbedtls_ecp_group_free( &ref ); 00421 00422 *grp_id = *id; 00423 00424 if( ret == 0 && *id == MBEDTLS_ECP_DP_NONE ) 00425 ret = MBEDTLS_ERR_ECP_FEATURE_UNAVAILABLE; 00426 00427 return( ret ); 00428 } 00429 00430 /* 00431 * Parse a SpecifiedECDomain (SEC 1 C.2) and find the associated group ID 00432 */ 00433 static int pk_group_id_from_specified( const mbedtls_asn1_buf *params, 00434 mbedtls_ecp_group_id *grp_id ) 00435 { 00436 int ret; 00437 mbedtls_ecp_group grp; 00438 00439 mbedtls_ecp_group_init( &grp ); 00440 00441 if( ( ret = pk_group_from_specified( params, &grp ) ) != 0 ) 00442 goto cleanup; 00443 00444 ret = pk_group_id_from_group( &grp, grp_id ); 00445 00446 cleanup: 00447 mbedtls_ecp_group_free( &grp ); 00448 00449 return( ret ); 00450 } 00451 #endif /* MBEDTLS_PK_PARSE_EC_EXTENDED */ 00452 00453 /* 00454 * Use EC parameters to initialise an EC group 00455 * 00456 * ECParameters ::= CHOICE { 00457 * namedCurve OBJECT IDENTIFIER 00458 * specifiedCurve SpecifiedECDomain -- = SEQUENCE { ... } 00459 * -- implicitCurve NULL 00460 */ 00461 static int pk_use_ecparams( const mbedtls_asn1_buf *params, mbedtls_ecp_group *grp ) 00462 { 00463 int ret; 00464 mbedtls_ecp_group_id grp_id; 00465 00466 if( params->tag == MBEDTLS_ASN1_OID ) 00467 { 00468 if( mbedtls_oid_get_ec_grp( params, &grp_id ) != 0 ) 00469 return( MBEDTLS_ERR_PK_UNKNOWN_NAMED_CURVE ); 00470 } 00471 else 00472 { 00473 #if defined(MBEDTLS_PK_PARSE_EC_EXTENDED) 00474 if( ( ret = pk_group_id_from_specified( params, &grp_id ) ) != 0 ) 00475 return( ret ); 00476 #else 00477 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT ); 00478 #endif 00479 } 00480 00481 /* 00482 * grp may already be initilialized; if so, make sure IDs match 00483 */ 00484 if( grp->id != MBEDTLS_ECP_DP_NONE && grp->id != grp_id ) 00485 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT ); 00486 00487 if( ( ret = mbedtls_ecp_group_load( grp, grp_id ) ) != 0 ) 00488 return( ret ); 00489 00490 return( 0 ); 00491 } 00492 00493 /* 00494 * EC public key is an EC point 00495 * 00496 * The caller is responsible for clearing the structure upon failure if 00497 * desired. Take care to pass along the possible ECP_FEATURE_UNAVAILABLE 00498 * return code of mbedtls_ecp_point_read_binary() and leave p in a usable state. 00499 */ 00500 static int pk_get_ecpubkey( unsigned char **p, const unsigned char *end, 00501 mbedtls_ecp_keypair *key ) 00502 { 00503 int ret; 00504 00505 if( ( ret = mbedtls_ecp_point_read_binary( &key->grp , &key->Q , 00506 (const unsigned char *) *p, end - *p ) ) == 0 ) 00507 { 00508 ret = mbedtls_ecp_check_pubkey( &key->grp , &key->Q ); 00509 } 00510 00511 /* 00512 * We know mbedtls_ecp_point_read_binary consumed all bytes or failed 00513 */ 00514 *p = (unsigned char *) end; 00515 00516 return( ret ); 00517 } 00518 #endif /* MBEDTLS_ECP_C */ 00519 00520 #if defined(MBEDTLS_RSA_C) 00521 /* 00522 * RSAPublicKey ::= SEQUENCE { 00523 * modulus INTEGER, -- n 00524 * publicExponent INTEGER -- e 00525 * } 00526 */ 00527 static int pk_get_rsapubkey( unsigned char **p, 00528 const unsigned char *end, 00529 mbedtls_rsa_context *rsa ) 00530 { 00531 int ret; 00532 size_t len; 00533 00534 if( ( ret = mbedtls_asn1_get_tag( p, end, &len, 00535 MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE ) ) != 0 ) 00536 return( MBEDTLS_ERR_PK_INVALID_PUBKEY + ret ); 00537 00538 if( *p + len != end ) 00539 return( MBEDTLS_ERR_PK_INVALID_PUBKEY + 00540 MBEDTLS_ERR_ASN1_LENGTH_MISMATCH ); 00541 00542 /* Import N */ 00543 if( ( ret = mbedtls_asn1_get_tag( p, end, &len, MBEDTLS_ASN1_INTEGER ) ) != 0 ) 00544 return( MBEDTLS_ERR_PK_INVALID_PUBKEY + ret ); 00545 00546 if( ( ret = mbedtls_rsa_import_raw( rsa, *p, len, NULL, 0, NULL, 0, 00547 NULL, 0, NULL, 0 ) ) != 0 ) 00548 return( MBEDTLS_ERR_PK_INVALID_PUBKEY ); 00549 00550 *p += len; 00551 00552 /* Import E */ 00553 if( ( ret = mbedtls_asn1_get_tag( p, end, &len, MBEDTLS_ASN1_INTEGER ) ) != 0 ) 00554 return( MBEDTLS_ERR_PK_INVALID_PUBKEY + ret ); 00555 00556 if( ( ret = mbedtls_rsa_import_raw( rsa, NULL, 0, NULL, 0, NULL, 0, 00557 NULL, 0, *p, len ) ) != 0 ) 00558 return( MBEDTLS_ERR_PK_INVALID_PUBKEY ); 00559 00560 *p += len; 00561 00562 if( mbedtls_rsa_complete( rsa ) != 0 || 00563 mbedtls_rsa_check_pubkey( rsa ) != 0 ) 00564 { 00565 return( MBEDTLS_ERR_PK_INVALID_PUBKEY ); 00566 } 00567 00568 if( *p != end ) 00569 return( MBEDTLS_ERR_PK_INVALID_PUBKEY + 00570 MBEDTLS_ERR_ASN1_LENGTH_MISMATCH ); 00571 00572 return( 0 ); 00573 } 00574 #endif /* MBEDTLS_RSA_C */ 00575 00576 /* Get a PK algorithm identifier 00577 * 00578 * AlgorithmIdentifier ::= SEQUENCE { 00579 * algorithm OBJECT IDENTIFIER, 00580 * parameters ANY DEFINED BY algorithm OPTIONAL } 00581 */ 00582 static int pk_get_pk_alg( unsigned char **p, 00583 const unsigned char *end, 00584 mbedtls_pk_type_t *pk_alg, mbedtls_asn1_buf *params ) 00585 { 00586 int ret; 00587 mbedtls_asn1_buf alg_oid; 00588 00589 memset( params, 0, sizeof(mbedtls_asn1_buf) ); 00590 00591 if( ( ret = mbedtls_asn1_get_alg( p, end, &alg_oid, params ) ) != 0 ) 00592 return( MBEDTLS_ERR_PK_INVALID_ALG + ret ); 00593 00594 if( mbedtls_oid_get_pk_alg( &alg_oid, pk_alg ) != 0 ) 00595 return( MBEDTLS_ERR_PK_UNKNOWN_PK_ALG ); 00596 00597 /* 00598 * No parameters with RSA (only for EC) 00599 */ 00600 if( *pk_alg == MBEDTLS_PK_RSA && 00601 ( ( params->tag != MBEDTLS_ASN1_NULL && params->tag != 0 ) || 00602 params->len != 0 ) ) 00603 { 00604 return( MBEDTLS_ERR_PK_INVALID_ALG ); 00605 } 00606 00607 return( 0 ); 00608 } 00609 00610 /* 00611 * SubjectPublicKeyInfo ::= SEQUENCE { 00612 * algorithm AlgorithmIdentifier, 00613 * subjectPublicKey BIT STRING } 00614 */ 00615 int mbedtls_pk_parse_subpubkey( unsigned char **p, const unsigned char *end, 00616 mbedtls_pk_context *pk ) 00617 { 00618 int ret; 00619 size_t len; 00620 mbedtls_asn1_buf alg_params; 00621 mbedtls_pk_type_t pk_alg = MBEDTLS_PK_NONE; 00622 const mbedtls_pk_info_t *pk_info; 00623 00624 PK_VALIDATE_RET( p != NULL ); 00625 PK_VALIDATE_RET( *p != NULL ); 00626 PK_VALIDATE_RET( end != NULL ); 00627 PK_VALIDATE_RET( pk != NULL ); 00628 00629 if( ( ret = mbedtls_asn1_get_tag( p, end, &len, 00630 MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE ) ) != 0 ) 00631 { 00632 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00633 } 00634 00635 end = *p + len; 00636 00637 if( ( ret = pk_get_pk_alg( p, end, &pk_alg, &alg_params ) ) != 0 ) 00638 return( ret ); 00639 00640 if( ( ret = mbedtls_asn1_get_bitstring_null( p, end, &len ) ) != 0 ) 00641 return( MBEDTLS_ERR_PK_INVALID_PUBKEY + ret ); 00642 00643 if( *p + len != end ) 00644 return( MBEDTLS_ERR_PK_INVALID_PUBKEY + 00645 MBEDTLS_ERR_ASN1_LENGTH_MISMATCH ); 00646 00647 if( ( pk_info = mbedtls_pk_info_from_type( pk_alg ) ) == NULL ) 00648 return( MBEDTLS_ERR_PK_UNKNOWN_PK_ALG ); 00649 00650 if( ( ret = mbedtls_pk_setup( pk, pk_info ) ) != 0 ) 00651 return( ret ); 00652 00653 #if defined(MBEDTLS_RSA_C) 00654 if( pk_alg == MBEDTLS_PK_RSA ) 00655 { 00656 ret = pk_get_rsapubkey( p, end, mbedtls_pk_rsa( *pk ) ); 00657 } else 00658 #endif /* MBEDTLS_RSA_C */ 00659 #if defined(MBEDTLS_ECP_C) 00660 if( pk_alg == MBEDTLS_PK_ECKEY_DH || pk_alg == MBEDTLS_PK_ECKEY ) 00661 { 00662 ret = pk_use_ecparams( &alg_params, &mbedtls_pk_ec( *pk )->grp ); 00663 if( ret == 0 ) 00664 ret = pk_get_ecpubkey( p, end, mbedtls_pk_ec( *pk ) ); 00665 } else 00666 #endif /* MBEDTLS_ECP_C */ 00667 ret = MBEDTLS_ERR_PK_UNKNOWN_PK_ALG; 00668 00669 if( ret == 0 && *p != end ) 00670 ret = MBEDTLS_ERR_PK_INVALID_PUBKEY 00671 MBEDTLS_ERR_ASN1_LENGTH_MISMATCH; 00672 00673 if( ret != 0 ) 00674 mbedtls_pk_free( pk ); 00675 00676 return( ret ); 00677 } 00678 00679 #if defined(MBEDTLS_RSA_C) 00680 /* 00681 * Parse a PKCS#1 encoded private RSA key 00682 */ 00683 static int pk_parse_key_pkcs1_der( mbedtls_rsa_context *rsa, 00684 const unsigned char *key, 00685 size_t keylen ) 00686 { 00687 int ret, version; 00688 size_t len; 00689 unsigned char *p, *end; 00690 00691 mbedtls_mpi T; 00692 mbedtls_mpi_init( &T ); 00693 00694 p = (unsigned char *) key; 00695 end = p + keylen; 00696 00697 /* 00698 * This function parses the RSAPrivateKey (PKCS#1) 00699 * 00700 * RSAPrivateKey ::= SEQUENCE { 00701 * version Version, 00702 * modulus INTEGER, -- n 00703 * publicExponent INTEGER, -- e 00704 * privateExponent INTEGER, -- d 00705 * prime1 INTEGER, -- p 00706 * prime2 INTEGER, -- q 00707 * exponent1 INTEGER, -- d mod (p-1) 00708 * exponent2 INTEGER, -- d mod (q-1) 00709 * coefficient INTEGER, -- (inverse of q) mod p 00710 * otherPrimeInfos OtherPrimeInfos OPTIONAL 00711 * } 00712 */ 00713 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 00714 MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE ) ) != 0 ) 00715 { 00716 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00717 } 00718 00719 end = p + len; 00720 00721 if( ( ret = mbedtls_asn1_get_int( &p, end, &version ) ) != 0 ) 00722 { 00723 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00724 } 00725 00726 if( version != 0 ) 00727 { 00728 return( MBEDTLS_ERR_PK_KEY_INVALID_VERSION ); 00729 } 00730 00731 /* Import N */ 00732 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 00733 MBEDTLS_ASN1_INTEGER ) ) != 0 || 00734 ( ret = mbedtls_rsa_import_raw( rsa, p, len, NULL, 0, NULL, 0, 00735 NULL, 0, NULL, 0 ) ) != 0 ) 00736 goto cleanup; 00737 p += len; 00738 00739 /* Import E */ 00740 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 00741 MBEDTLS_ASN1_INTEGER ) ) != 0 || 00742 ( ret = mbedtls_rsa_import_raw( rsa, NULL, 0, NULL, 0, NULL, 0, 00743 NULL, 0, p, len ) ) != 0 ) 00744 goto cleanup; 00745 p += len; 00746 00747 /* Import D */ 00748 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 00749 MBEDTLS_ASN1_INTEGER ) ) != 0 || 00750 ( ret = mbedtls_rsa_import_raw( rsa, NULL, 0, NULL, 0, NULL, 0, 00751 p, len, NULL, 0 ) ) != 0 ) 00752 goto cleanup; 00753 p += len; 00754 00755 /* Import P */ 00756 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 00757 MBEDTLS_ASN1_INTEGER ) ) != 0 || 00758 ( ret = mbedtls_rsa_import_raw( rsa, NULL, 0, p, len, NULL, 0, 00759 NULL, 0, NULL, 0 ) ) != 0 ) 00760 goto cleanup; 00761 p += len; 00762 00763 /* Import Q */ 00764 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 00765 MBEDTLS_ASN1_INTEGER ) ) != 0 || 00766 ( ret = mbedtls_rsa_import_raw( rsa, NULL, 0, NULL, 0, p, len, 00767 NULL, 0, NULL, 0 ) ) != 0 ) 00768 goto cleanup; 00769 p += len; 00770 00771 /* Complete the RSA private key */ 00772 if( ( ret = mbedtls_rsa_complete( rsa ) ) != 0 ) 00773 goto cleanup; 00774 00775 /* Check optional parameters */ 00776 if( ( ret = mbedtls_asn1_get_mpi( &p, end, &T ) ) != 0 || 00777 ( ret = mbedtls_asn1_get_mpi( &p, end, &T ) ) != 0 || 00778 ( ret = mbedtls_asn1_get_mpi( &p, end, &T ) ) != 0 ) 00779 goto cleanup; 00780 00781 if( p != end ) 00782 { 00783 ret = MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + 00784 MBEDTLS_ERR_ASN1_LENGTH_MISMATCH ; 00785 } 00786 00787 cleanup: 00788 00789 mbedtls_mpi_free( &T ); 00790 00791 if( ret != 0 ) 00792 { 00793 /* Wrap error code if it's coming from a lower level */ 00794 if( ( ret & 0xff80 ) == 0 ) 00795 ret = MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret; 00796 else 00797 ret = MBEDTLS_ERR_PK_KEY_INVALID_FORMAT; 00798 00799 mbedtls_rsa_free( rsa ); 00800 } 00801 00802 return( ret ); 00803 } 00804 #endif /* MBEDTLS_RSA_C */ 00805 00806 #if defined(MBEDTLS_ECP_C) 00807 /* 00808 * Parse a SEC1 encoded private EC key 00809 */ 00810 static int pk_parse_key_sec1_der( mbedtls_ecp_keypair *eck, 00811 const unsigned char *key, 00812 size_t keylen ) 00813 { 00814 int ret; 00815 int version, pubkey_done; 00816 size_t len; 00817 mbedtls_asn1_buf params; 00818 unsigned char *p = (unsigned char *) key; 00819 unsigned char *end = p + keylen; 00820 unsigned char *end2; 00821 00822 /* 00823 * RFC 5915, or SEC1 Appendix C.4 00824 * 00825 * ECPrivateKey ::= SEQUENCE { 00826 * version INTEGER { ecPrivkeyVer1(1) } (ecPrivkeyVer1), 00827 * privateKey OCTET STRING, 00828 * parameters [0] ECParameters {{ NamedCurve }} OPTIONAL, 00829 * publicKey [1] BIT STRING OPTIONAL 00830 * } 00831 */ 00832 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 00833 MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE ) ) != 0 ) 00834 { 00835 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00836 } 00837 00838 end = p + len; 00839 00840 if( ( ret = mbedtls_asn1_get_int( &p, end, &version ) ) != 0 ) 00841 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00842 00843 if( version != 1 ) 00844 return( MBEDTLS_ERR_PK_KEY_INVALID_VERSION ); 00845 00846 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, MBEDTLS_ASN1_OCTET_STRING ) ) != 0 ) 00847 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00848 00849 if( ( ret = mbedtls_mpi_read_binary( &eck->d , p, len ) ) != 0 ) 00850 { 00851 mbedtls_ecp_keypair_free( eck ); 00852 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00853 } 00854 00855 p += len; 00856 00857 pubkey_done = 0; 00858 if( p != end ) 00859 { 00860 /* 00861 * Is 'parameters' present? 00862 */ 00863 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 00864 MBEDTLS_ASN1_CONTEXT_SPECIFIC | MBEDTLS_ASN1_CONSTRUCTED | 0 ) ) == 0 ) 00865 { 00866 if( ( ret = pk_get_ecparams( &p, p + len, ¶ms) ) != 0 || 00867 ( ret = pk_use_ecparams( ¶ms, &eck->grp ) ) != 0 ) 00868 { 00869 mbedtls_ecp_keypair_free( eck ); 00870 return( ret ); 00871 } 00872 } 00873 else if( ret != MBEDTLS_ERR_ASN1_UNEXPECTED_TAG ) 00874 { 00875 mbedtls_ecp_keypair_free( eck ); 00876 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00877 } 00878 } 00879 00880 if( p != end ) 00881 { 00882 /* 00883 * Is 'publickey' present? If not, or if we can't read it (eg because it 00884 * is compressed), create it from the private key. 00885 */ 00886 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 00887 MBEDTLS_ASN1_CONTEXT_SPECIFIC | MBEDTLS_ASN1_CONSTRUCTED | 1 ) ) == 0 ) 00888 { 00889 end2 = p + len; 00890 00891 if( ( ret = mbedtls_asn1_get_bitstring_null( &p, end2, &len ) ) != 0 ) 00892 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00893 00894 if( p + len != end2 ) 00895 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + 00896 MBEDTLS_ERR_ASN1_LENGTH_MISMATCH ); 00897 00898 if( ( ret = pk_get_ecpubkey( &p, end2, eck ) ) == 0 ) 00899 pubkey_done = 1; 00900 else 00901 { 00902 /* 00903 * The only acceptable failure mode of pk_get_ecpubkey() above 00904 * is if the point format is not recognized. 00905 */ 00906 if( ret != MBEDTLS_ERR_ECP_FEATURE_UNAVAILABLE ) 00907 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT ); 00908 } 00909 } 00910 else if( ret != MBEDTLS_ERR_ASN1_UNEXPECTED_TAG ) 00911 { 00912 mbedtls_ecp_keypair_free( eck ); 00913 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00914 } 00915 } 00916 00917 if( ! pubkey_done && 00918 ( ret = mbedtls_ecp_mul( &eck->grp , &eck->Q , &eck->d , &eck->grp .G , 00919 NULL, NULL ) ) != 0 ) 00920 { 00921 mbedtls_ecp_keypair_free( eck ); 00922 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00923 } 00924 00925 if( ( ret = mbedtls_ecp_check_privkey( &eck->grp , &eck->d ) ) != 0 ) 00926 { 00927 mbedtls_ecp_keypair_free( eck ); 00928 return( ret ); 00929 } 00930 00931 return( 0 ); 00932 } 00933 #endif /* MBEDTLS_ECP_C */ 00934 00935 /* 00936 * Parse an unencrypted PKCS#8 encoded private key 00937 * 00938 * Notes: 00939 * 00940 * - This function does not own the key buffer. It is the 00941 * responsibility of the caller to take care of zeroizing 00942 * and freeing it after use. 00943 * 00944 * - The function is responsible for freeing the provided 00945 * PK context on failure. 00946 * 00947 */ 00948 static int pk_parse_key_pkcs8_unencrypted_der( 00949 mbedtls_pk_context *pk, 00950 const unsigned char* key, 00951 size_t keylen ) 00952 { 00953 int ret, version; 00954 size_t len; 00955 mbedtls_asn1_buf params; 00956 unsigned char *p = (unsigned char *) key; 00957 unsigned char *end = p + keylen; 00958 mbedtls_pk_type_t pk_alg = MBEDTLS_PK_NONE; 00959 const mbedtls_pk_info_t *pk_info; 00960 00961 /* 00962 * This function parses the PrivateKeyInfo object (PKCS#8 v1.2 = RFC 5208) 00963 * 00964 * PrivateKeyInfo ::= SEQUENCE { 00965 * version Version, 00966 * privateKeyAlgorithm PrivateKeyAlgorithmIdentifier, 00967 * privateKey PrivateKey, 00968 * attributes [0] IMPLICIT Attributes OPTIONAL } 00969 * 00970 * Version ::= INTEGER 00971 * PrivateKeyAlgorithmIdentifier ::= AlgorithmIdentifier 00972 * PrivateKey ::= OCTET STRING 00973 * 00974 * The PrivateKey OCTET STRING is a SEC1 ECPrivateKey 00975 */ 00976 00977 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 00978 MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE ) ) != 0 ) 00979 { 00980 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00981 } 00982 00983 end = p + len; 00984 00985 if( ( ret = mbedtls_asn1_get_int( &p, end, &version ) ) != 0 ) 00986 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00987 00988 if( version != 0 ) 00989 return( MBEDTLS_ERR_PK_KEY_INVALID_VERSION + ret ); 00990 00991 if( ( ret = pk_get_pk_alg( &p, end, &pk_alg, ¶ms ) ) != 0 ) 00992 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00993 00994 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, MBEDTLS_ASN1_OCTET_STRING ) ) != 0 ) 00995 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 00996 00997 if( len < 1 ) 00998 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + 00999 MBEDTLS_ERR_ASN1_OUT_OF_DATA ); 01000 01001 if( ( pk_info = mbedtls_pk_info_from_type( pk_alg ) ) == NULL ) 01002 return( MBEDTLS_ERR_PK_UNKNOWN_PK_ALG ); 01003 01004 if( ( ret = mbedtls_pk_setup( pk, pk_info ) ) != 0 ) 01005 return( ret ); 01006 01007 #if defined(MBEDTLS_RSA_C) 01008 if( pk_alg == MBEDTLS_PK_RSA ) 01009 { 01010 if( ( ret = pk_parse_key_pkcs1_der( mbedtls_pk_rsa( *pk ), p, len ) ) != 0 ) 01011 { 01012 mbedtls_pk_free( pk ); 01013 return( ret ); 01014 } 01015 } else 01016 #endif /* MBEDTLS_RSA_C */ 01017 #if defined(MBEDTLS_ECP_C) 01018 if( pk_alg == MBEDTLS_PK_ECKEY || pk_alg == MBEDTLS_PK_ECKEY_DH ) 01019 { 01020 if( ( ret = pk_use_ecparams( ¶ms, &mbedtls_pk_ec( *pk )->grp ) ) != 0 || 01021 ( ret = pk_parse_key_sec1_der( mbedtls_pk_ec( *pk ), p, len ) ) != 0 ) 01022 { 01023 mbedtls_pk_free( pk ); 01024 return( ret ); 01025 } 01026 } else 01027 #endif /* MBEDTLS_ECP_C */ 01028 return( MBEDTLS_ERR_PK_UNKNOWN_PK_ALG ); 01029 01030 return( 0 ); 01031 } 01032 01033 /* 01034 * Parse an encrypted PKCS#8 encoded private key 01035 * 01036 * To save space, the decryption happens in-place on the given key buffer. 01037 * Also, while this function may modify the keybuffer, it doesn't own it, 01038 * and instead it is the responsibility of the caller to zeroize and properly 01039 * free it after use. 01040 * 01041 */ 01042 #if defined(MBEDTLS_PKCS12_C) || defined(MBEDTLS_PKCS5_C) 01043 static int pk_parse_key_pkcs8_encrypted_der( 01044 mbedtls_pk_context *pk, 01045 unsigned char *key, size_t keylen, 01046 const unsigned char *pwd, size_t pwdlen ) 01047 { 01048 int ret, decrypted = 0; 01049 size_t len; 01050 unsigned char *buf; 01051 unsigned char *p, *end; 01052 mbedtls_asn1_buf pbe_alg_oid, pbe_params; 01053 #if defined(MBEDTLS_PKCS12_C) 01054 mbedtls_cipher_type_t cipher_alg; 01055 mbedtls_md_type_t md_alg; 01056 #endif 01057 01058 p = key; 01059 end = p + keylen; 01060 01061 if( pwdlen == 0 ) 01062 return( MBEDTLS_ERR_PK_PASSWORD_REQUIRED ); 01063 01064 /* 01065 * This function parses the EncryptedPrivateKeyInfo object (PKCS#8) 01066 * 01067 * EncryptedPrivateKeyInfo ::= SEQUENCE { 01068 * encryptionAlgorithm EncryptionAlgorithmIdentifier, 01069 * encryptedData EncryptedData 01070 * } 01071 * 01072 * EncryptionAlgorithmIdentifier ::= AlgorithmIdentifier 01073 * 01074 * EncryptedData ::= OCTET STRING 01075 * 01076 * The EncryptedData OCTET STRING is a PKCS#8 PrivateKeyInfo 01077 * 01078 */ 01079 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, 01080 MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE ) ) != 0 ) 01081 { 01082 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 01083 } 01084 01085 end = p + len; 01086 01087 if( ( ret = mbedtls_asn1_get_alg( &p, end, &pbe_alg_oid, &pbe_params ) ) != 0 ) 01088 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 01089 01090 if( ( ret = mbedtls_asn1_get_tag( &p, end, &len, MBEDTLS_ASN1_OCTET_STRING ) ) != 0 ) 01091 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT + ret ); 01092 01093 buf = p; 01094 01095 /* 01096 * Decrypt EncryptedData with appropriate PBE 01097 */ 01098 #if defined(MBEDTLS_PKCS12_C) 01099 if( mbedtls_oid_get_pkcs12_pbe_alg( &pbe_alg_oid, &md_alg, &cipher_alg ) == 0 ) 01100 { 01101 if( ( ret = mbedtls_pkcs12_pbe( &pbe_params, MBEDTLS_PKCS12_PBE_DECRYPT, 01102 cipher_alg, md_alg, 01103 pwd, pwdlen, p, len, buf ) ) != 0 ) 01104 { 01105 if( ret == MBEDTLS_ERR_PKCS12_PASSWORD_MISMATCH ) 01106 return( MBEDTLS_ERR_PK_PASSWORD_MISMATCH ); 01107 01108 return( ret ); 01109 } 01110 01111 decrypted = 1; 01112 } 01113 else if( MBEDTLS_OID_CMP( MBEDTLS_OID_PKCS12_PBE_SHA1_RC4_128, &pbe_alg_oid ) == 0 ) 01114 { 01115 if( ( ret = mbedtls_pkcs12_pbe_sha1_rc4_128( &pbe_params, 01116 MBEDTLS_PKCS12_PBE_DECRYPT, 01117 pwd, pwdlen, 01118 p, len, buf ) ) != 0 ) 01119 { 01120 return( ret ); 01121 } 01122 01123 // Best guess for password mismatch when using RC4. If first tag is 01124 // not MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE 01125 // 01126 if( *buf != ( MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE ) ) 01127 return( MBEDTLS_ERR_PK_PASSWORD_MISMATCH ); 01128 01129 decrypted = 1; 01130 } 01131 else 01132 #endif /* MBEDTLS_PKCS12_C */ 01133 #if defined(MBEDTLS_PKCS5_C) 01134 if( MBEDTLS_OID_CMP( MBEDTLS_OID_PKCS5_PBES2, &pbe_alg_oid ) == 0 ) 01135 { 01136 if( ( ret = mbedtls_pkcs5_pbes2( &pbe_params, MBEDTLS_PKCS5_DECRYPT, pwd, pwdlen, 01137 p, len, buf ) ) != 0 ) 01138 { 01139 if( ret == MBEDTLS_ERR_PKCS5_PASSWORD_MISMATCH ) 01140 return( MBEDTLS_ERR_PK_PASSWORD_MISMATCH ); 01141 01142 return( ret ); 01143 } 01144 01145 decrypted = 1; 01146 } 01147 else 01148 #endif /* MBEDTLS_PKCS5_C */ 01149 { 01150 ((void) pwd); 01151 } 01152 01153 if( decrypted == 0 ) 01154 return( MBEDTLS_ERR_PK_FEATURE_UNAVAILABLE ); 01155 01156 return( pk_parse_key_pkcs8_unencrypted_der( pk, buf, len ) ); 01157 } 01158 #endif /* MBEDTLS_PKCS12_C || MBEDTLS_PKCS5_C */ 01159 01160 /* 01161 * Parse a private key 01162 */ 01163 int mbedtls_pk_parse_key( mbedtls_pk_context *pk, 01164 const unsigned char *key, size_t keylen, 01165 const unsigned char *pwd, size_t pwdlen ) 01166 { 01167 int ret; 01168 const mbedtls_pk_info_t *pk_info; 01169 #if defined(MBEDTLS_PEM_PARSE_C) 01170 size_t len; 01171 mbedtls_pem_context pem; 01172 #endif 01173 01174 PK_VALIDATE_RET( pk != NULL ); 01175 if( keylen == 0 ) 01176 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT ); 01177 PK_VALIDATE_RET( key != NULL ); 01178 01179 #if defined(MBEDTLS_PEM_PARSE_C) 01180 mbedtls_pem_init( &pem ); 01181 01182 #if defined(MBEDTLS_RSA_C) 01183 /* Avoid calling mbedtls_pem_read_buffer() on non-null-terminated string */ 01184 if( key[keylen - 1] != '\0' ) 01185 ret = MBEDTLS_ERR_PEM_NO_HEADER_FOOTER_PRESENT; 01186 else 01187 ret = mbedtls_pem_read_buffer( &pem, 01188 "-----BEGIN RSA PRIVATE KEY-----", 01189 "-----END RSA PRIVATE KEY-----", 01190 key, pwd, pwdlen, &len ); 01191 01192 if( ret == 0 ) 01193 { 01194 pk_info = mbedtls_pk_info_from_type( MBEDTLS_PK_RSA ); 01195 if( ( ret = mbedtls_pk_setup( pk, pk_info ) ) != 0 || 01196 ( ret = pk_parse_key_pkcs1_der( mbedtls_pk_rsa( *pk ), 01197 pem.buf , pem.buflen ) ) != 0 ) 01198 { 01199 mbedtls_pk_free( pk ); 01200 } 01201 01202 mbedtls_pem_free( &pem ); 01203 return( ret ); 01204 } 01205 else if( ret == MBEDTLS_ERR_PEM_PASSWORD_MISMATCH ) 01206 return( MBEDTLS_ERR_PK_PASSWORD_MISMATCH ); 01207 else if( ret == MBEDTLS_ERR_PEM_PASSWORD_REQUIRED ) 01208 return( MBEDTLS_ERR_PK_PASSWORD_REQUIRED ); 01209 else if( ret != MBEDTLS_ERR_PEM_NO_HEADER_FOOTER_PRESENT ) 01210 return( ret ); 01211 #endif /* MBEDTLS_RSA_C */ 01212 01213 #if defined(MBEDTLS_ECP_C) 01214 /* Avoid calling mbedtls_pem_read_buffer() on non-null-terminated string */ 01215 if( key[keylen - 1] != '\0' ) 01216 ret = MBEDTLS_ERR_PEM_NO_HEADER_FOOTER_PRESENT; 01217 else 01218 ret = mbedtls_pem_read_buffer( &pem, 01219 "-----BEGIN EC PRIVATE KEY-----", 01220 "-----END EC PRIVATE KEY-----", 01221 key, pwd, pwdlen, &len ); 01222 if( ret == 0 ) 01223 { 01224 pk_info = mbedtls_pk_info_from_type( MBEDTLS_PK_ECKEY ); 01225 01226 if( ( ret = mbedtls_pk_setup( pk, pk_info ) ) != 0 || 01227 ( ret = pk_parse_key_sec1_der( mbedtls_pk_ec( *pk ), 01228 pem.buf , pem.buflen ) ) != 0 ) 01229 { 01230 mbedtls_pk_free( pk ); 01231 } 01232 01233 mbedtls_pem_free( &pem ); 01234 return( ret ); 01235 } 01236 else if( ret == MBEDTLS_ERR_PEM_PASSWORD_MISMATCH ) 01237 return( MBEDTLS_ERR_PK_PASSWORD_MISMATCH ); 01238 else if( ret == MBEDTLS_ERR_PEM_PASSWORD_REQUIRED ) 01239 return( MBEDTLS_ERR_PK_PASSWORD_REQUIRED ); 01240 else if( ret != MBEDTLS_ERR_PEM_NO_HEADER_FOOTER_PRESENT ) 01241 return( ret ); 01242 #endif /* MBEDTLS_ECP_C */ 01243 01244 /* Avoid calling mbedtls_pem_read_buffer() on non-null-terminated string */ 01245 if( key[keylen - 1] != '\0' ) 01246 ret = MBEDTLS_ERR_PEM_NO_HEADER_FOOTER_PRESENT; 01247 else 01248 ret = mbedtls_pem_read_buffer( &pem, 01249 "-----BEGIN PRIVATE KEY-----", 01250 "-----END PRIVATE KEY-----", 01251 key, NULL, 0, &len ); 01252 if( ret == 0 ) 01253 { 01254 if( ( ret = pk_parse_key_pkcs8_unencrypted_der( pk, 01255 pem.buf , pem.buflen ) ) != 0 ) 01256 { 01257 mbedtls_pk_free( pk ); 01258 } 01259 01260 mbedtls_pem_free( &pem ); 01261 return( ret ); 01262 } 01263 else if( ret != MBEDTLS_ERR_PEM_NO_HEADER_FOOTER_PRESENT ) 01264 return( ret ); 01265 01266 #if defined(MBEDTLS_PKCS12_C) || defined(MBEDTLS_PKCS5_C) 01267 /* Avoid calling mbedtls_pem_read_buffer() on non-null-terminated string */ 01268 if( key[keylen - 1] != '\0' ) 01269 ret = MBEDTLS_ERR_PEM_NO_HEADER_FOOTER_PRESENT; 01270 else 01271 ret = mbedtls_pem_read_buffer( &pem, 01272 "-----BEGIN ENCRYPTED PRIVATE KEY-----", 01273 "-----END ENCRYPTED PRIVATE KEY-----", 01274 key, NULL, 0, &len ); 01275 if( ret == 0 ) 01276 { 01277 if( ( ret = pk_parse_key_pkcs8_encrypted_der( pk, 01278 pem.buf , pem.buflen , 01279 pwd, pwdlen ) ) != 0 ) 01280 { 01281 mbedtls_pk_free( pk ); 01282 } 01283 01284 mbedtls_pem_free( &pem ); 01285 return( ret ); 01286 } 01287 else if( ret != MBEDTLS_ERR_PEM_NO_HEADER_FOOTER_PRESENT ) 01288 return( ret ); 01289 #endif /* MBEDTLS_PKCS12_C || MBEDTLS_PKCS5_C */ 01290 #else 01291 ((void) pwd); 01292 ((void) pwdlen); 01293 #endif /* MBEDTLS_PEM_PARSE_C */ 01294 01295 /* 01296 * At this point we only know it's not a PEM formatted key. Could be any 01297 * of the known DER encoded private key formats 01298 * 01299 * We try the different DER format parsers to see if one passes without 01300 * error 01301 */ 01302 #if defined(MBEDTLS_PKCS12_C) || defined(MBEDTLS_PKCS5_C) 01303 { 01304 unsigned char *key_copy; 01305 01306 if( ( key_copy = mbedtls_calloc( 1, keylen ) ) == NULL ) 01307 return( MBEDTLS_ERR_PK_ALLOC_FAILED ); 01308 01309 memcpy( key_copy, key, keylen ); 01310 01311 ret = pk_parse_key_pkcs8_encrypted_der( pk, key_copy, keylen, 01312 pwd, pwdlen ); 01313 01314 mbedtls_platform_zeroize( key_copy, keylen ); 01315 mbedtls_free( key_copy ); 01316 } 01317 01318 if( ret == 0 ) 01319 return( 0 ); 01320 01321 mbedtls_pk_free( pk ); 01322 mbedtls_pk_init( pk ); 01323 01324 if( ret == MBEDTLS_ERR_PK_PASSWORD_MISMATCH ) 01325 { 01326 return( ret ); 01327 } 01328 #endif /* MBEDTLS_PKCS12_C || MBEDTLS_PKCS5_C */ 01329 01330 if( ( ret = pk_parse_key_pkcs8_unencrypted_der( pk, key, keylen ) ) == 0 ) 01331 return( 0 ); 01332 01333 mbedtls_pk_free( pk ); 01334 mbedtls_pk_init( pk ); 01335 01336 #if defined(MBEDTLS_RSA_C) 01337 01338 pk_info = mbedtls_pk_info_from_type( MBEDTLS_PK_RSA ); 01339 if( mbedtls_pk_setup( pk, pk_info ) == 0 && 01340 pk_parse_key_pkcs1_der( mbedtls_pk_rsa( *pk ), key, keylen ) == 0 ) 01341 { 01342 return( 0 ); 01343 } 01344 01345 mbedtls_pk_free( pk ); 01346 mbedtls_pk_init( pk ); 01347 #endif /* MBEDTLS_RSA_C */ 01348 01349 #if defined(MBEDTLS_ECP_C) 01350 pk_info = mbedtls_pk_info_from_type( MBEDTLS_PK_ECKEY ); 01351 if( mbedtls_pk_setup( pk, pk_info ) == 0 && 01352 pk_parse_key_sec1_der( mbedtls_pk_ec( *pk ), 01353 key, keylen ) == 0 ) 01354 { 01355 return( 0 ); 01356 } 01357 mbedtls_pk_free( pk ); 01358 #endif /* MBEDTLS_ECP_C */ 01359 01360 /* If MBEDTLS_RSA_C is defined but MBEDTLS_ECP_C isn't, 01361 * it is ok to leave the PK context initialized but not 01362 * freed: It is the caller's responsibility to call pk_init() 01363 * before calling this function, and to call pk_free() 01364 * when it fails. If MBEDTLS_ECP_C is defined but MBEDTLS_RSA_C 01365 * isn't, this leads to mbedtls_pk_free() being called 01366 * twice, once here and once by the caller, but this is 01367 * also ok and in line with the mbedtls_pk_free() calls 01368 * on failed PEM parsing attempts. */ 01369 01370 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT ); 01371 } 01372 01373 /* 01374 * Parse a public key 01375 */ 01376 int mbedtls_pk_parse_public_key( mbedtls_pk_context *ctx, 01377 const unsigned char *key, size_t keylen ) 01378 { 01379 int ret; 01380 unsigned char *p; 01381 #if defined(MBEDTLS_RSA_C) 01382 const mbedtls_pk_info_t *pk_info; 01383 #endif 01384 #if defined(MBEDTLS_PEM_PARSE_C) 01385 size_t len; 01386 mbedtls_pem_context pem; 01387 #endif 01388 01389 PK_VALIDATE_RET( ctx != NULL ); 01390 if( keylen == 0 ) 01391 return( MBEDTLS_ERR_PK_KEY_INVALID_FORMAT ); 01392 PK_VALIDATE_RET( key != NULL || keylen == 0 ); 01393 01394 #if defined(MBEDTLS_PEM_PARSE_C) 01395 mbedtls_pem_init( &pem ); 01396 #if defined(MBEDTLS_RSA_C) 01397 /* Avoid calling mbedtls_pem_read_buffer() on non-null-terminated string */ 01398 if( key[keylen - 1] != '\0' ) 01399 ret = MBEDTLS_ERR_PEM_NO_HEADER_FOOTER_PRESENT; 01400 else 01401 ret = mbedtls_pem_read_buffer( &pem, 01402 "-----BEGIN RSA PUBLIC KEY-----", 01403 "-----END RSA PUBLIC KEY-----", 01404 key, NULL, 0, &len ); 01405 01406 if( ret == 0 ) 01407 { 01408 p = pem.buf ; 01409 if( ( pk_info = mbedtls_pk_info_from_type( MBEDTLS_PK_RSA ) ) == NULL ) 01410 return( MBEDTLS_ERR_PK_UNKNOWN_PK_ALG ); 01411 01412 if( ( ret = mbedtls_pk_setup( ctx, pk_info ) ) != 0 ) 01413 return( ret ); 01414 01415 if ( ( ret = pk_get_rsapubkey( &p, p + pem.buflen , mbedtls_pk_rsa( *ctx ) ) ) != 0 ) 01416 mbedtls_pk_free( ctx ); 01417 01418 mbedtls_pem_free( &pem ); 01419 return( ret ); 01420 } 01421 else if( ret != MBEDTLS_ERR_PEM_NO_HEADER_FOOTER_PRESENT ) 01422 { 01423 mbedtls_pem_free( &pem ); 01424 return( ret ); 01425 } 01426 #endif /* MBEDTLS_RSA_C */ 01427 01428 /* Avoid calling mbedtls_pem_read_buffer() on non-null-terminated string */ 01429 if( key[keylen - 1] != '\0' ) 01430 ret = MBEDTLS_ERR_PEM_NO_HEADER_FOOTER_PRESENT; 01431 else 01432 ret = mbedtls_pem_read_buffer( &pem, 01433 "-----BEGIN PUBLIC KEY-----", 01434 "-----END PUBLIC KEY-----", 01435 key, NULL, 0, &len ); 01436 01437 if( ret == 0 ) 01438 { 01439 /* 01440 * Was PEM encoded 01441 */ 01442 p = pem.buf ; 01443 01444 ret = mbedtls_pk_parse_subpubkey( &p, p + pem.buflen , ctx ); 01445 mbedtls_pem_free( &pem ); 01446 return( ret ); 01447 } 01448 else if( ret != MBEDTLS_ERR_PEM_NO_HEADER_FOOTER_PRESENT ) 01449 { 01450 mbedtls_pem_free( &pem ); 01451 return( ret ); 01452 } 01453 mbedtls_pem_free( &pem ); 01454 #endif /* MBEDTLS_PEM_PARSE_C */ 01455 01456 #if defined(MBEDTLS_RSA_C) 01457 if( ( pk_info = mbedtls_pk_info_from_type( MBEDTLS_PK_RSA ) ) == NULL ) 01458 return( MBEDTLS_ERR_PK_UNKNOWN_PK_ALG ); 01459 01460 if( ( ret = mbedtls_pk_setup( ctx, pk_info ) ) != 0 ) 01461 return( ret ); 01462 01463 p = (unsigned char *)key; 01464 ret = pk_get_rsapubkey( &p, p + keylen, mbedtls_pk_rsa( *ctx ) ); 01465 if( ret == 0 ) 01466 { 01467 return( ret ); 01468 } 01469 mbedtls_pk_free( ctx ); 01470 if( ret != ( MBEDTLS_ERR_PK_INVALID_PUBKEY + MBEDTLS_ERR_ASN1_UNEXPECTED_TAG ) ) 01471 { 01472 return( ret ); 01473 } 01474 #endif /* MBEDTLS_RSA_C */ 01475 p = (unsigned char *) key; 01476 01477 ret = mbedtls_pk_parse_subpubkey( &p, p + keylen, ctx ); 01478 01479 return( ret ); 01480 } 01481 01482 #endif /* MBEDTLS_PK_PARSE_C */
Generated on Tue Jul 12 2022 13:54:41 by
