1 /* 2 * Public Key layer for writing key files and structures 3 * 4 * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved 5 * SPDX-License-Identifier: GPL-2.0 6 * 7 * This program is free software; you can redistribute it and/or modify 8 * it under the terms of the GNU General Public License as published by 9 * the Free Software Foundation; either version 2 of the License, or 10 * (at your option) any later version. 11 * 12 * This program is distributed in the hope that it will be useful, 13 * but WITHOUT ANY WARRANTY; without even the implied warranty of 14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 * GNU General Public License for more details. 16 * 17 * You should have received a copy of the GNU General Public License along 18 * with this program; if not, write to the Free Software Foundation, Inc., 19 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * This file is part of mbed TLS (https://tls.mbed.org) 22 */ 23 24 #if !defined(MBEDTLS_CONFIG_FILE) 25 #include "mbedtls/config.h" 26 #else 27 #include MBEDTLS_CONFIG_FILE 28 #endif 29 30 #if defined(MBEDTLS_PK_WRITE_C) 31 32 #include "mbedtls/pk.h" 33 #include "mbedtls/asn1write.h" 34 #include "mbedtls/oid.h" 35 36 #include <string.h> 37 38 #if defined(MBEDTLS_RSA_C) 39 #include "mbedtls/rsa.h" 40 #endif 41 #if defined(MBEDTLS_ECP_C) 42 #include "mbedtls/bignum.h" 43 #include "mbedtls/ecp.h" 44 #endif 45 #if defined(MBEDTLS_ECDSA_C) 46 #include "mbedtls/ecdsa.h" 47 #endif 48 #if defined(MBEDTLS_PEM_WRITE_C) 49 #include "mbedtls/pem.h" 50 #endif 51 52 #if defined(MBEDTLS_PLATFORM_C) 53 #include "mbedtls/platform.h" 54 #else 55 #include <stdlib.h> 56 #define mbedtls_calloc calloc 57 #define mbedtls_free free 58 #endif 59 60 #if defined(MBEDTLS_ECP_C) 61 /* Implementation that should never be optimized out by the compiler */ 62 static void mbedtls_zeroize( void *v, size_t n ) { 63 volatile unsigned char *p = (unsigned char*)v; while( n-- ) *p++ = 0; 64 } 65 #endif /* MBEDTLS_ECP_C */ 66 67 #if defined(MBEDTLS_RSA_C) 68 /* 69 * RSAPublicKey ::= SEQUENCE { 70 * modulus INTEGER, -- n 71 * publicExponent INTEGER -- e 72 * } 73 */ 74 static int pk_write_rsa_pubkey( unsigned char **p, unsigned char *start, 75 mbedtls_rsa_context *rsa ) 76 { 77 int ret; 78 size_t len = 0; 79 mbedtls_mpi T; 80 81 mbedtls_mpi_init( &T ); 82 83 /* Export E */ 84 if ( ( ret = mbedtls_rsa_export( rsa, NULL, NULL, NULL, NULL, &T ) ) != 0 || 85 ( ret = mbedtls_asn1_write_mpi( p, start, &T ) ) < 0 ) 86 goto end_of_export; 87 len += ret; 88 89 /* Export N */ 90 if ( ( ret = mbedtls_rsa_export( rsa, &T, NULL, NULL, NULL, NULL ) ) != 0 || 91 ( ret = mbedtls_asn1_write_mpi( p, start, &T ) ) < 0 ) 92 goto end_of_export; 93 len += ret; 94 95 end_of_export: 96 97 mbedtls_mpi_free( &T ); 98 if( ret < 0 ) 99 return( ret ); 100 101 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_len( p, start, len ) ); 102 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_tag( p, start, MBEDTLS_ASN1_CONSTRUCTED | 103 MBEDTLS_ASN1_SEQUENCE ) ); 104 105 return( (int) len ); 106 } 107 #endif /* MBEDTLS_RSA_C */ 108 109 #if defined(MBEDTLS_ECP_C) 110 /* 111 * EC public key is an EC point 112 */ 113 static int pk_write_ec_pubkey( unsigned char **p, unsigned char *start, 114 mbedtls_ecp_keypair *ec ) 115 { 116 int ret; 117 size_t len = 0; 118 unsigned char buf[MBEDTLS_ECP_MAX_PT_LEN]; 119 120 if( ( ret = mbedtls_ecp_point_write_binary( &ec->grp, &ec->Q, 121 MBEDTLS_ECP_PF_UNCOMPRESSED, 122 &len, buf, sizeof( buf ) ) ) != 0 ) 123 { 124 return( ret ); 125 } 126 127 if( *p < start || (size_t)( *p - start ) < len ) 128 return( MBEDTLS_ERR_ASN1_BUF_TOO_SMALL ); 129 130 *p -= len; 131 memcpy( *p, buf, len ); 132 133 return( (int) len ); 134 } 135 136 /* 137 * ECParameters ::= CHOICE { 138 * namedCurve OBJECT IDENTIFIER 139 * } 140 */ 141 static int pk_write_ec_param( unsigned char **p, unsigned char *start, 142 mbedtls_ecp_keypair *ec ) 143 { 144 int ret; 145 size_t len = 0; 146 const char *oid; 147 size_t oid_len; 148 149 if( ( ret = mbedtls_oid_get_oid_by_ec_grp( ec->grp.id, &oid, &oid_len ) ) != 0 ) 150 return( ret ); 151 152 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_oid( p, start, oid, oid_len ) ); 153 154 return( (int) len ); 155 } 156 157 /* 158 * privateKey OCTET STRING -- always of length ceil(log2(n)/8) 159 */ 160 static int pk_write_ec_private( unsigned char **p, unsigned char *start, 161 mbedtls_ecp_keypair *ec ) 162 { 163 int ret; 164 size_t byte_length = ( ec->grp.pbits + 7 ) / 8; 165 unsigned char tmp[MBEDTLS_ECP_MAX_BYTES]; 166 167 ret = mbedtls_mpi_write_binary( &ec->d, tmp, byte_length ); 168 if( ret != 0 ) 169 goto exit; 170 ret = mbedtls_asn1_write_octet_string( p, start, tmp, byte_length ); 171 172 exit: 173 mbedtls_zeroize( tmp, byte_length ); 174 return( ret ); 175 } 176 #endif /* MBEDTLS_ECP_C */ 177 178 int mbedtls_pk_write_pubkey( unsigned char **p, unsigned char *start, 179 const mbedtls_pk_context *key ) 180 { 181 int ret; 182 size_t len = 0; 183 184 #if defined(MBEDTLS_RSA_C) 185 if( mbedtls_pk_get_type( key ) == MBEDTLS_PK_RSA ) 186 MBEDTLS_ASN1_CHK_ADD( len, pk_write_rsa_pubkey( p, start, mbedtls_pk_rsa( *key ) ) ); 187 else 188 #endif 189 #if defined(MBEDTLS_ECP_C) 190 if( mbedtls_pk_get_type( key ) == MBEDTLS_PK_ECKEY ) 191 MBEDTLS_ASN1_CHK_ADD( len, pk_write_ec_pubkey( p, start, mbedtls_pk_ec( *key ) ) ); 192 else 193 #endif 194 return( MBEDTLS_ERR_PK_FEATURE_UNAVAILABLE ); 195 196 return( (int) len ); 197 } 198 199 int mbedtls_pk_write_pubkey_der( mbedtls_pk_context *key, unsigned char *buf, size_t size ) 200 { 201 int ret; 202 unsigned char *c; 203 size_t len = 0, par_len = 0, oid_len; 204 const char *oid; 205 206 c = buf + size; 207 208 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_pk_write_pubkey( &c, buf, key ) ); 209 210 if( c - buf < 1 ) 211 return( MBEDTLS_ERR_ASN1_BUF_TOO_SMALL ); 212 213 /* 214 * SubjectPublicKeyInfo ::= SEQUENCE { 215 * algorithm AlgorithmIdentifier, 216 * subjectPublicKey BIT STRING } 217 */ 218 *--c = 0; 219 len += 1; 220 221 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_len( &c, buf, len ) ); 222 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_tag( &c, buf, MBEDTLS_ASN1_BIT_STRING ) ); 223 224 if( ( ret = mbedtls_oid_get_oid_by_pk_alg( mbedtls_pk_get_type( key ), 225 &oid, &oid_len ) ) != 0 ) 226 { 227 return( ret ); 228 } 229 230 #if defined(MBEDTLS_ECP_C) 231 if( mbedtls_pk_get_type( key ) == MBEDTLS_PK_ECKEY ) 232 { 233 MBEDTLS_ASN1_CHK_ADD( par_len, pk_write_ec_param( &c, buf, mbedtls_pk_ec( *key ) ) ); 234 } 235 #endif 236 237 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_algorithm_identifier( &c, buf, oid, oid_len, 238 par_len ) ); 239 240 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_len( &c, buf, len ) ); 241 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_tag( &c, buf, MBEDTLS_ASN1_CONSTRUCTED | 242 MBEDTLS_ASN1_SEQUENCE ) ); 243 244 return( (int) len ); 245 } 246 247 int mbedtls_pk_write_key_der( mbedtls_pk_context *key, unsigned char *buf, size_t size ) 248 { 249 int ret; 250 unsigned char *c = buf + size; 251 size_t len = 0; 252 253 #if defined(MBEDTLS_RSA_C) 254 if( mbedtls_pk_get_type( key ) == MBEDTLS_PK_RSA ) 255 { 256 mbedtls_mpi T; /* Temporary holding the exported parameters */ 257 mbedtls_rsa_context *rsa = mbedtls_pk_rsa( *key ); 258 259 /* 260 * Export the parameters one after another to avoid simultaneous copies. 261 */ 262 263 mbedtls_mpi_init( &T ); 264 265 /* Export QP */ 266 if( ( ret = mbedtls_rsa_export_crt( rsa, NULL, NULL, &T ) ) != 0 || 267 ( ret = mbedtls_asn1_write_mpi( &c, buf, &T ) ) < 0 ) 268 goto end_of_export; 269 len += ret; 270 271 /* Export DQ */ 272 if( ( ret = mbedtls_rsa_export_crt( rsa, NULL, &T, NULL ) ) != 0 || 273 ( ret = mbedtls_asn1_write_mpi( &c, buf, &T ) ) < 0 ) 274 goto end_of_export; 275 len += ret; 276 277 /* Export DP */ 278 if( ( ret = mbedtls_rsa_export_crt( rsa, &T, NULL, NULL ) ) != 0 || 279 ( ret = mbedtls_asn1_write_mpi( &c, buf, &T ) ) < 0 ) 280 goto end_of_export; 281 len += ret; 282 283 /* Export Q */ 284 if ( ( ret = mbedtls_rsa_export( rsa, NULL, NULL, 285 &T, NULL, NULL ) ) != 0 || 286 ( ret = mbedtls_asn1_write_mpi( &c, buf, &T ) ) < 0 ) 287 goto end_of_export; 288 len += ret; 289 290 /* Export P */ 291 if ( ( ret = mbedtls_rsa_export( rsa, NULL, &T, 292 NULL, NULL, NULL ) ) != 0 || 293 ( ret = mbedtls_asn1_write_mpi( &c, buf, &T ) ) < 0 ) 294 goto end_of_export; 295 len += ret; 296 297 /* Export D */ 298 if ( ( ret = mbedtls_rsa_export( rsa, NULL, NULL, 299 NULL, &T, NULL ) ) != 0 || 300 ( ret = mbedtls_asn1_write_mpi( &c, buf, &T ) ) < 0 ) 301 goto end_of_export; 302 len += ret; 303 304 /* Export E */ 305 if ( ( ret = mbedtls_rsa_export( rsa, NULL, NULL, 306 NULL, NULL, &T ) ) != 0 || 307 ( ret = mbedtls_asn1_write_mpi( &c, buf, &T ) ) < 0 ) 308 goto end_of_export; 309 len += ret; 310 311 /* Export N */ 312 if ( ( ret = mbedtls_rsa_export( rsa, &T, NULL, 313 NULL, NULL, NULL ) ) != 0 || 314 ( ret = mbedtls_asn1_write_mpi( &c, buf, &T ) ) < 0 ) 315 goto end_of_export; 316 len += ret; 317 318 end_of_export: 319 320 mbedtls_mpi_free( &T ); 321 if( ret < 0 ) 322 return( ret ); 323 324 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_int( &c, buf, 0 ) ); 325 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_len( &c, buf, len ) ); 326 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_tag( &c, 327 buf, MBEDTLS_ASN1_CONSTRUCTED | 328 MBEDTLS_ASN1_SEQUENCE ) ); 329 } 330 else 331 #endif /* MBEDTLS_RSA_C */ 332 #if defined(MBEDTLS_ECP_C) 333 if( mbedtls_pk_get_type( key ) == MBEDTLS_PK_ECKEY ) 334 { 335 mbedtls_ecp_keypair *ec = mbedtls_pk_ec( *key ); 336 size_t pub_len = 0, par_len = 0; 337 338 /* 339 * RFC 5915, or SEC1 Appendix C.4 340 * 341 * ECPrivateKey ::= SEQUENCE { 342 * version INTEGER { ecPrivkeyVer1(1) } (ecPrivkeyVer1), 343 * privateKey OCTET STRING, 344 * parameters [0] ECParameters {{ NamedCurve }} OPTIONAL, 345 * publicKey [1] BIT STRING OPTIONAL 346 * } 347 */ 348 349 /* publicKey */ 350 MBEDTLS_ASN1_CHK_ADD( pub_len, pk_write_ec_pubkey( &c, buf, ec ) ); 351 352 if( c - buf < 1 ) 353 return( MBEDTLS_ERR_ASN1_BUF_TOO_SMALL ); 354 *--c = 0; 355 pub_len += 1; 356 357 MBEDTLS_ASN1_CHK_ADD( pub_len, mbedtls_asn1_write_len( &c, buf, pub_len ) ); 358 MBEDTLS_ASN1_CHK_ADD( pub_len, mbedtls_asn1_write_tag( &c, buf, MBEDTLS_ASN1_BIT_STRING ) ); 359 360 MBEDTLS_ASN1_CHK_ADD( pub_len, mbedtls_asn1_write_len( &c, buf, pub_len ) ); 361 MBEDTLS_ASN1_CHK_ADD( pub_len, mbedtls_asn1_write_tag( &c, buf, 362 MBEDTLS_ASN1_CONTEXT_SPECIFIC | MBEDTLS_ASN1_CONSTRUCTED | 1 ) ); 363 len += pub_len; 364 365 /* parameters */ 366 MBEDTLS_ASN1_CHK_ADD( par_len, pk_write_ec_param( &c, buf, ec ) ); 367 368 MBEDTLS_ASN1_CHK_ADD( par_len, mbedtls_asn1_write_len( &c, buf, par_len ) ); 369 MBEDTLS_ASN1_CHK_ADD( par_len, mbedtls_asn1_write_tag( &c, buf, 370 MBEDTLS_ASN1_CONTEXT_SPECIFIC | MBEDTLS_ASN1_CONSTRUCTED | 0 ) ); 371 len += par_len; 372 373 /* privateKey */ 374 MBEDTLS_ASN1_CHK_ADD( len, pk_write_ec_private( &c, buf, ec ) ); 375 376 /* version */ 377 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_int( &c, buf, 1 ) ); 378 379 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_len( &c, buf, len ) ); 380 MBEDTLS_ASN1_CHK_ADD( len, mbedtls_asn1_write_tag( &c, buf, MBEDTLS_ASN1_CONSTRUCTED | 381 MBEDTLS_ASN1_SEQUENCE ) ); 382 } 383 else 384 #endif /* MBEDTLS_ECP_C */ 385 return( MBEDTLS_ERR_PK_FEATURE_UNAVAILABLE ); 386 387 return( (int) len ); 388 } 389 390 #if defined(MBEDTLS_PEM_WRITE_C) 391 392 #define PEM_BEGIN_PUBLIC_KEY "-----BEGIN PUBLIC KEY-----\n" 393 #define PEM_END_PUBLIC_KEY "-----END PUBLIC KEY-----\n" 394 395 #define PEM_BEGIN_PRIVATE_KEY_RSA "-----BEGIN RSA PRIVATE KEY-----\n" 396 #define PEM_END_PRIVATE_KEY_RSA "-----END RSA PRIVATE KEY-----\n" 397 #define PEM_BEGIN_PRIVATE_KEY_EC "-----BEGIN EC PRIVATE KEY-----\n" 398 #define PEM_END_PRIVATE_KEY_EC "-----END EC PRIVATE KEY-----\n" 399 400 /* 401 * Max sizes of key per types. Shown as tag + len (+ content). 402 */ 403 404 #if defined(MBEDTLS_RSA_C) 405 /* 406 * RSA public keys: 407 * SubjectPublicKeyInfo ::= SEQUENCE { 1 + 3 408 * algorithm AlgorithmIdentifier, 1 + 1 (sequence) 409 * + 1 + 1 + 9 (rsa oid) 410 * + 1 + 1 (params null) 411 * subjectPublicKey BIT STRING } 1 + 3 + (1 + below) 412 * RSAPublicKey ::= SEQUENCE { 1 + 3 413 * modulus INTEGER, -- n 1 + 3 + MPI_MAX + 1 414 * publicExponent INTEGER -- e 1 + 3 + MPI_MAX + 1 415 * } 416 */ 417 #define RSA_PUB_DER_MAX_BYTES 38 + 2 * MBEDTLS_MPI_MAX_SIZE 418 419 /* 420 * RSA private keys: 421 * RSAPrivateKey ::= SEQUENCE { 1 + 3 422 * version Version, 1 + 1 + 1 423 * modulus INTEGER, 1 + 3 + MPI_MAX + 1 424 * publicExponent INTEGER, 1 + 3 + MPI_MAX + 1 425 * privateExponent INTEGER, 1 + 3 + MPI_MAX + 1 426 * prime1 INTEGER, 1 + 3 + MPI_MAX / 2 + 1 427 * prime2 INTEGER, 1 + 3 + MPI_MAX / 2 + 1 428 * exponent1 INTEGER, 1 + 3 + MPI_MAX / 2 + 1 429 * exponent2 INTEGER, 1 + 3 + MPI_MAX / 2 + 1 430 * coefficient INTEGER, 1 + 3 + MPI_MAX / 2 + 1 431 * otherPrimeInfos OtherPrimeInfos OPTIONAL 0 (not supported) 432 * } 433 */ 434 #define MPI_MAX_SIZE_2 MBEDTLS_MPI_MAX_SIZE / 2 + \ 435 MBEDTLS_MPI_MAX_SIZE % 2 436 #define RSA_PRV_DER_MAX_BYTES 47 + 3 * MBEDTLS_MPI_MAX_SIZE \ 437 + 5 * MPI_MAX_SIZE_2 438 439 #else /* MBEDTLS_RSA_C */ 440 441 #define RSA_PUB_DER_MAX_BYTES 0 442 #define RSA_PRV_DER_MAX_BYTES 0 443 444 #endif /* MBEDTLS_RSA_C */ 445 446 #if defined(MBEDTLS_ECP_C) 447 /* 448 * EC public keys: 449 * SubjectPublicKeyInfo ::= SEQUENCE { 1 + 2 450 * algorithm AlgorithmIdentifier, 1 + 1 (sequence) 451 * + 1 + 1 + 7 (ec oid) 452 * + 1 + 1 + 9 (namedCurve oid) 453 * subjectPublicKey BIT STRING 1 + 2 + 1 [1] 454 * + 1 (point format) [1] 455 * + 2 * ECP_MAX (coords) [1] 456 * } 457 */ 458 #define ECP_PUB_DER_MAX_BYTES 30 + 2 * MBEDTLS_ECP_MAX_BYTES 459 460 /* 461 * EC private keys: 462 * ECPrivateKey ::= SEQUENCE { 1 + 2 463 * version INTEGER , 1 + 1 + 1 464 * privateKey OCTET STRING, 1 + 1 + ECP_MAX 465 * parameters [0] ECParameters OPTIONAL, 1 + 1 + (1 + 1 + 9) 466 * publicKey [1] BIT STRING OPTIONAL 1 + 2 + [1] above 467 * } 468 */ 469 #define ECP_PRV_DER_MAX_BYTES 29 + 3 * MBEDTLS_ECP_MAX_BYTES 470 471 #else /* MBEDTLS_ECP_C */ 472 473 #define ECP_PUB_DER_MAX_BYTES 0 474 #define ECP_PRV_DER_MAX_BYTES 0 475 476 #endif /* MBEDTLS_ECP_C */ 477 478 #define PUB_DER_MAX_BYTES RSA_PUB_DER_MAX_BYTES > ECP_PUB_DER_MAX_BYTES ? \ 479 RSA_PUB_DER_MAX_BYTES : ECP_PUB_DER_MAX_BYTES 480 #define PRV_DER_MAX_BYTES RSA_PRV_DER_MAX_BYTES > ECP_PRV_DER_MAX_BYTES ? \ 481 RSA_PRV_DER_MAX_BYTES : ECP_PRV_DER_MAX_BYTES 482 483 int mbedtls_pk_write_pubkey_pem( mbedtls_pk_context *key, unsigned char *buf, size_t size ) 484 { 485 int ret; 486 unsigned char output_buf[PUB_DER_MAX_BYTES]; 487 size_t olen = 0; 488 489 if( ( ret = mbedtls_pk_write_pubkey_der( key, output_buf, 490 sizeof(output_buf) ) ) < 0 ) 491 { 492 return( ret ); 493 } 494 495 if( ( ret = mbedtls_pem_write_buffer( PEM_BEGIN_PUBLIC_KEY, PEM_END_PUBLIC_KEY, 496 output_buf + sizeof(output_buf) - ret, 497 ret, buf, size, &olen ) ) != 0 ) 498 { 499 return( ret ); 500 } 501 502 return( 0 ); 503 } 504 505 int mbedtls_pk_write_key_pem( mbedtls_pk_context *key, unsigned char *buf, size_t size ) 506 { 507 int ret; 508 unsigned char output_buf[PRV_DER_MAX_BYTES]; 509 const char *begin, *end; 510 size_t olen = 0; 511 512 if( ( ret = mbedtls_pk_write_key_der( key, output_buf, sizeof(output_buf) ) ) < 0 ) 513 return( ret ); 514 515 #if defined(MBEDTLS_RSA_C) 516 if( mbedtls_pk_get_type( key ) == MBEDTLS_PK_RSA ) 517 { 518 begin = PEM_BEGIN_PRIVATE_KEY_RSA; 519 end = PEM_END_PRIVATE_KEY_RSA; 520 } 521 else 522 #endif 523 #if defined(MBEDTLS_ECP_C) 524 if( mbedtls_pk_get_type( key ) == MBEDTLS_PK_ECKEY ) 525 { 526 begin = PEM_BEGIN_PRIVATE_KEY_EC; 527 end = PEM_END_PRIVATE_KEY_EC; 528 } 529 else 530 #endif 531 return( MBEDTLS_ERR_PK_FEATURE_UNAVAILABLE ); 532 533 if( ( ret = mbedtls_pem_write_buffer( begin, end, 534 output_buf + sizeof(output_buf) - ret, 535 ret, buf, size, &olen ) ) != 0 ) 536 { 537 return( ret ); 538 } 539 540 return( 0 ); 541 } 542 #endif /* MBEDTLS_PEM_WRITE_C */ 543 544 #endif /* MBEDTLS_PK_WRITE_C */ 545