ecc.h (32832B)
1 /* ecc.h 2 * 3 * Copyright (C) 2006-2025 wolfSSL Inc. 4 * 5 * This file is part of wolfSSL. 6 * 7 * wolfSSL 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 3 of the License, or 10 * (at your option) any later version. 11 * 12 * wolfSSL 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 18 * along with this program; if not, write to the Free Software 19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA 20 */ 21 22 /*! 23 \file wolfssl/wolfcrypt/ecc.h 24 */ 25 26 27 #ifndef WOLF_CRYPT_ECC_H 28 #define WOLF_CRYPT_ECC_H 29 30 #include <wolfssl/wolfcrypt/types.h> 31 32 #ifdef HAVE_ECC 33 34 #if FIPS_VERSION3_GE(2,0,0) 35 #include <wolfssl/wolfcrypt/fips.h> 36 #endif /* HAVE_FIPS_VERSION >= 2 */ 37 38 #include <wolfssl/wolfcrypt/wolfmath.h> 39 #include <wolfssl/wolfcrypt/random.h> 40 41 #ifdef HAVE_X963_KDF 42 #include <wolfssl/wolfcrypt/hash.h> 43 #endif 44 45 #ifdef WOLFSSL_ASYNC_CRYPT 46 #include <wolfssl/wolfcrypt/async.h> 47 #ifdef WOLFSSL_CERT_GEN 48 #include <wolfssl/wolfcrypt/asn.h> 49 #endif 50 #endif 51 52 #if defined(WOLFSSL_ATECC508A) || defined(WOLFSSL_ATECC608A) 53 #include <wolfssl/wolfcrypt/port/atmel/atmel.h> 54 #endif /* WOLFSSL_ATECC508A */ 55 56 #if defined(WOLFSSL_CRYPTOCELL) 57 #include <wolfssl/wolfcrypt/port/arm/cryptoCell.h> 58 #endif 59 60 #ifdef WOLFSSL_SILABS_SE_ACCEL 61 #include <wolfssl/wolfcrypt/port/silabs/silabs_ecc.h> 62 #endif 63 64 #if defined(WOLFSSL_KCAPI_ECC) 65 #include <wolfssl/wolfcrypt/port/kcapi/kcapi_ecc.h> 66 #endif 67 68 #ifdef WOLFSSL_SE050 69 #include <wolfssl/wolfcrypt/port/nxp/se050_port.h> 70 #endif 71 72 #if defined(WOLFSSL_XILINX_CRYPT_VERSAL) 73 #include <wolfssl/wolfcrypt/port/xilinx/xil-versal-glue.h> 74 #endif 75 76 #ifdef WOLFSSL_HAVE_SP_ECC 77 #include <wolfssl/wolfcrypt/sp_int.h> 78 #endif 79 80 81 #ifdef __cplusplus 82 extern "C" { 83 #endif 84 85 #if FIPS_VERSION3_GE(6,0,0) 86 extern const unsigned int wolfCrypt_FIPS_ecc_ro_sanity[2]; 87 WOLFSSL_LOCAL int wolfCrypt_FIPS_ECC_sanity(void); 88 #endif 89 90 /* Enable curve B parameter if needed */ 91 #if defined(HAVE_COMP_KEY) || defined(ECC_CACHE_CURVE) 92 #ifndef USE_ECC_B_PARAM /* Allow someone to force enable */ 93 #define USE_ECC_B_PARAM 94 #endif 95 #endif 96 97 98 /* Use this as the key->idx if a custom ecc_set is used for key->dp */ 99 #define ECC_CUSTOM_IDX (-1) 100 101 102 /* Determine max ECC bits based on enabled curves */ 103 #if defined(WOLFCRYPT_HAVE_SAKKE) 104 #define MAX_ECC_BITS_NEEDED 1024 105 #elif defined(HAVE_ECC521) || defined(HAVE_ALL_CURVES) 106 #define MAX_ECC_BITS_NEEDED 521 107 #elif defined(HAVE_ECC512) 108 #define MAX_ECC_BITS_NEEDED 512 109 #elif defined(HAVE_ECC384) 110 #define MAX_ECC_BITS_NEEDED 384 111 #elif defined(HAVE_ECC320) 112 #define MAX_ECC_BITS_NEEDED 320 113 #elif !defined(NO_ECC256) || defined(WOLFSSL_SM2) 114 #define MAX_ECC_BITS_NEEDED 256 115 #elif defined(HAVE_ECC239) 116 #define MAX_ECC_BITS_NEEDED 239 117 #elif defined(HAVE_ECC224) 118 #define MAX_ECC_BITS_NEEDED 224 119 #elif defined(HAVE_ECC192) 120 #define MAX_ECC_BITS_NEEDED 192 121 #elif defined(HAVE_ECC160) 122 #define MAX_ECC_BITS_NEEDED 160 123 #elif defined(HAVE_ECC128) 124 #define MAX_ECC_BITS_NEEDED 128 125 #elif defined(HAVE_ECC112) 126 #define MAX_ECC_BITS_NEEDED 112 127 #endif 128 129 #ifndef MAX_ECC_BITS 130 #define MAX_ECC_BITS MAX_ECC_BITS_NEEDED 131 #else 132 #if MAX_ECC_BITS_NEEDED > MAX_ECC_BITS 133 #error configured MAX_ECC_BITS is less than required by enabled curves. 134 #endif 135 #endif 136 137 #if FIPS_VERSION3_GE(6,0,0) 138 #define WC_ECC_FIPS_SIG_MIN 224 139 #define WC_ECC_FIPS_GEN_MIN (WC_ECC_FIPS_SIG_MIN/8) 140 #endif 141 142 #ifdef WOLFSSL_SM2 143 #define WOLFSSL_SM2_KEY_BITS 256 144 #endif 145 146 /* calculate max ECC bytes */ 147 #if ((MAX_ECC_BITS * 2) % 8) == 0 148 #define MAX_ECC_BYTES (MAX_ECC_BITS / 8) 149 #else 150 /* add byte if not aligned */ 151 #define MAX_ECC_BYTES ((MAX_ECC_BITS / 8) + 1) 152 #endif 153 154 #ifndef ECC_MAX_PAD_SZ 155 /* ECC maximum padding size (when MSB is set extra byte required for R and S) */ 156 #define ECC_MAX_PAD_SZ 2 157 #endif 158 159 enum { 160 ECC_PUBLICKEY = 1, 161 ECC_PRIVATEKEY = 2, 162 ECC_PRIVATEKEY_ONLY = 3, 163 ECC_MAXNAME = 16, /* MAX CURVE NAME LENGTH */ 164 SIG_HEADER_SZ = 7, /* ECC signature header size (30 81 87 02 42 [R] 02 42 [S]) */ 165 ECC_BUFSIZE = 257, /* for exported keys temp buffer */ 166 ECC_MINSIZE = ECC_MIN_KEY_SZ/8, /* MIN Private Key size */ 167 #ifdef WOLFCRYPT_HAVE_SAKKE 168 ECC_MAXSIZE = 128, /* MAX Private Key size */ 169 ECC_MAXSIZE_GEN = 128, /* MAX Buffer size required when generating ECC keys*/ 170 #else 171 ECC_MAXSIZE = 66, /* MAX Private Key size */ 172 ECC_MAXSIZE_GEN = 74, /* MAX Buffer size required when generating ECC keys*/ 173 #endif 174 ECC_MAX_OID_LEN = 16, 175 ECC_MAX_SIG_SIZE= ((MAX_ECC_BYTES * 2) + ECC_MAX_PAD_SZ + SIG_HEADER_SZ), 176 177 /* max crypto hardware size */ 178 #if defined(WOLFSSL_ATECC508A) || defined(WOLFSSL_ATECC608A) 179 ECC_MAX_CRYPTO_HW_SIZE = ATECC_KEY_SIZE, /* from port/atmel/atmel.h */ 180 ECC_MAX_CRYPTO_HW_PUBKEY_SIZE = (ATECC_KEY_SIZE*2), 181 #elif defined(PLUTON_CRYPTO_ECC) 182 ECC_MAX_CRYPTO_HW_SIZE = 32, 183 #elif defined(WOLFSSL_SILABS_SE_ACCEL) 184 ECC_MAX_CRYPTO_HW_SIZE = 32, 185 #elif defined(WOLFSSL_CRYPTOCELL) 186 #ifndef CRYPTOCELL_KEY_SIZE 187 CRYPTOCELL_KEY_SIZE = ECC_MAXSIZE, 188 #endif 189 ECC_MAX_CRYPTO_HW_SIZE = CRYPTOCELL_KEY_SIZE, 190 #elif defined(WOLFSSL_SE050) 191 ECC_MAX_CRYPTO_HW_SIZE = 66, 192 #elif defined(WOLFSSL_XILINX_CRYPT_VERSAL) 193 ECC_MAX_CRYPTO_HW_SIZE = MAX_ECC_BYTES, 194 #endif 195 196 197 /* point compression type */ 198 ECC_POINT_COMP_EVEN = 0x02, 199 ECC_POINT_COMP_ODD = 0x03, 200 ECC_POINT_UNCOMP = 0x04, 201 202 /* Shamir's dual add constants */ 203 SHAMIR_PRECOMP_SZ = 16, 204 205 #ifdef WOLF_PRIVATE_KEY_ID 206 ECC_MAX_ID_LEN = 32, 207 ECC_MAX_LABEL_LEN = 32, 208 #endif 209 210 WOLF_ENUM_DUMMY_LAST_ELEMENT(ECC) 211 }; 212 213 #endif /* HAVE_ECC */ 214 215 #if defined(HAVE_ECC) || defined(HAVE_CURVE25519) || \ 216 defined(HAVE_CURVE448) || defined(WOLFCRYPT_HAVE_SAKKE) 217 /* Curve Types */ 218 enum ecc_curve_ids { 219 ECC_CURVE_INVALID = -1, 220 ECC_CURVE_DEF = 0, /* NIST or SECP */ 221 222 /* NIST Prime Curves */ 223 ECC_SECP192R1, /* 1 */ 224 ECC_PRIME192V2, 225 ECC_PRIME192V3, 226 ECC_PRIME239V1, 227 ECC_PRIME239V2, 228 ECC_PRIME239V3, 229 ECC_SECP256R1, /* 7 */ 230 231 /* SECP Curves */ 232 ECC_SECP112R1, 233 ECC_SECP112R2, 234 ECC_SECP128R1, 235 ECC_SECP128R2, 236 ECC_SECP160R1, 237 ECC_SECP160R2, 238 ECC_SECP224R1, /* 14 */ 239 ECC_SECP384R1, /* 15 */ 240 ECC_SECP521R1, /* 16 */ 241 242 /* Koblitz */ 243 ECC_SECP160K1, 244 ECC_SECP192K1, 245 ECC_SECP224K1, 246 ECC_SECP256K1, 247 248 /* Brainpool Curves */ 249 ECC_BRAINPOOLP160R1, 250 ECC_BRAINPOOLP192R1, 251 ECC_BRAINPOOLP224R1, 252 ECC_BRAINPOOLP256R1, 253 ECC_BRAINPOOLP320R1, 254 ECC_BRAINPOOLP384R1, 255 ECC_BRAINPOOLP512R1, 256 257 /* SM2 */ 258 ECC_SM2P256V1, 259 260 /* Twisted Edwards Curves */ 261 #ifdef HAVE_CURVE25519 262 ECC_X25519, 263 #endif 264 #ifdef HAVE_CURVE448 265 ECC_X448, 266 #endif 267 #ifdef WOLFCRYPT_HAVE_SAKKE 268 ECC_SAKKE_1, 269 #endif 270 271 #ifdef WOLFSSL_CUSTOM_CURVES 272 ECC_CURVE_CUSTOM, 273 #endif 274 ECC_CURVE_MAX 275 }; 276 typedef enum ecc_curve_ids ecc_curve_id; 277 #endif 278 279 #ifdef HAVE_ECC 280 281 #ifdef HAVE_OID_ENCODING 282 typedef word16 ecc_oid_t; 283 #else 284 typedef byte ecc_oid_t; 285 /* OID encoded with ASN scheme: 286 first element = (oid[0] * 40) + oid[1] 287 if any element > 127 then MSB 0x80 indicates additional byte */ 288 #endif 289 290 291 #if !defined(WOLFSSL_ECC_CURVE_STATIC) && defined(USE_WINDOWS_API) && \ 292 !defined(__WATCOMC__) 293 /* MSC does something different with the pointers to the arrays than GCC, 294 * and it causes the FIPS checksum to fail. In the case of windows builds, 295 * store everything as arrays instead of pointers to strings. */ 296 297 #define WOLFSSL_ECC_CURVE_STATIC 298 #endif 299 300 /* ECC set type defined a GF(p) curve */ 301 #ifndef WOLFSSL_ECC_CURVE_STATIC 302 struct ecc_set_type { 303 int size; /* The size of the curve in octets */ 304 int id; /* id of this curve */ 305 const char* name; /* name of this curve */ 306 const char* prime; /* prime that defines the field, curve is in (hex) */ 307 const char* Af; /* fields A param (hex) */ 308 const char* Bf; /* fields B param (hex) */ 309 const char* order; /* order of the curve (hex) */ 310 const char* Gx; /* x coordinate of the base point on curve (hex) */ 311 const char* Gy; /* y coordinate of the base point on curve (hex) */ 312 const ecc_oid_t* oid; 313 word32 oidSz; 314 word32 oidSum; /* sum of encoded OID bytes */ 315 int cofactor; 316 }; 317 #else 318 #define MAX_ECC_NAME 16 319 #define MAX_ECC_STRING ((MAX_ECC_BYTES * 2) + 2) 320 /* The values are stored as text strings. */ 321 322 struct ecc_set_type { 323 int size; /* The size of the curve in octets */ 324 int id; /* id of this curve */ 325 char name[MAX_ECC_NAME]; /* name of this curve */ 326 char prime[MAX_ECC_STRING]; /* prime that defines the field, curve is in (hex) */ 327 char Af[MAX_ECC_STRING]; /* fields A param (hex) */ 328 char Bf[MAX_ECC_STRING]; /* fields B param (hex) */ 329 char order[MAX_ECC_STRING]; /* order of the curve (hex) */ 330 char Gx[MAX_ECC_STRING]; /* x coordinate of the base point on curve (hex) */ 331 char Gy[MAX_ECC_STRING]; /* y coordinate of the base point on curve (hex) */ 332 ecc_oid_t oid[10]; 333 word32 oidSz; 334 word32 oidSum; /* sum of encoded OID bytes */ 335 int cofactor; 336 }; 337 #endif 338 339 340 #ifdef ALT_ECC_SIZE 341 342 /* Note on ALT_ECC_SIZE: 343 * The fast math code uses an array of a fixed size to store the big integers. 344 * By default, the array is big enough for RSA keys. There is a size, 345 * FP_MAX_BITS which can be used to make the array smaller when one wants ECC 346 * but not RSA. Some people want fast math sized for both RSA and ECC, where 347 * ECC won't use as much as RSA. The flag ALT_ECC_SIZE switches in an alternate 348 * ecc_point structure that uses an alternate fp_int that has a shorter array 349 * of fp_digits. 350 * 351 * Now, without ALT_ECC_SIZE, the ecc_point has three single item arrays of 352 * mp_ints for the components of the point. With ALT_ECC_SIZE, the components 353 * of the point are pointers that are set to each of a three item array of 354 * alt_fp_ints. While an mp_int will have 4096 bits of digit inside the 355 * structure, the alt_fp_int will only have 512 bits for ECC 256-bit and 356 * 1056-bits for ECC 521-bit. A size value was added in the ALT case, as well, 357 * and is set by mp_init() and alt_fp_init(). The functions fp_zero() and 358 * fp_copy() use the size parameter. An int needs to be initialized before 359 * using it instead of just fp_zeroing it, the init will call zero. The 360 * FP_MAX_BITS_ECC defaults to calculating based on MAX_ECC_BITS, but 361 * can be set to change the number of bits used in the alternate FP_INT. 362 * 363 * The ALT_ECC_SIZE option only applies to stack based fast math USE_FAST_MATH. 364 */ 365 366 #if defined(USE_INTEGER_HEAP_MATH) 367 #error Cannot use integer math with ALT_ECC_SIZE 368 #endif 369 #ifdef WOLFSSL_NO_MALLOC 370 #error ALT_ECC_SIZE cannot be used with no malloc (WOLFSSL_NO_MALLOC) 371 #endif 372 373 #ifdef USE_FAST_MATH 374 375 /* determine max bits required for ECC math */ 376 #ifndef FP_MAX_BITS_ECC 377 /* max bits rounded up by 8 then doubled */ 378 /* (ROUND8(MAX_ECC_BITS) * 2) */ 379 #define FP_MAX_BITS_ECC (2 * \ 380 ((MAX_ECC_BITS + DIGIT_BIT - 1) / DIGIT_BIT) * DIGIT_BIT) 381 382 /* Note: For ECC verify only FP_MAX_BITS_ECC can be reduced to: 383 ROUND8(MAX_ECC_BITS) + ROUND8(DIGIT_BIT) */ 384 #endif 385 386 /* verify alignment */ 387 #if CHAR_BIT == 0 388 #error CHAR_BIT must be nonzero 389 #endif 390 #if FP_MAX_BITS_ECC % CHAR_BIT 391 #error FP_MAX_BITS_ECC must be a multiple of CHAR_BIT 392 #endif 393 394 /* determine buffer size */ 395 /* Add one to accommodate extra digit used by sp_mul(), sp_mulmod(), sp_sqr(), and sp_sqrmod(). */ 396 #define FP_SIZE_ECC ((FP_MAX_BITS_ECC/DIGIT_BIT) + 1) 397 398 399 /* This needs to match the size of the fp_int struct, except the 400 * fp_digit array will be shorter. */ 401 typedef struct alt_fp_int { 402 int used, sign, size; 403 mp_digit dp[FP_SIZE_ECC]; 404 } alt_fp_int; 405 406 #else 407 408 #ifdef FP_MAX_BITS_ECC 409 #define SP_INT_BITS_ECC (FP_MAX_BITS_ECC / 2) 410 #elif SP_INT_BITS < MAX_ECC_BITS 411 #define SP_INT_BITS_ECC SP_INT_BITS 412 #else 413 #define SP_INT_BITS_ECC MAX_ECC_BITS 414 #endif 415 416 #define SP_INT_DIGITS_ECC \ 417 (((SP_INT_BITS_ECC + SP_WORD_SIZE - 1) / SP_WORD_SIZE) * 2 + 1) 418 419 #define FP_SIZE_ECC SP_INT_DIGITS_ECC 420 421 typedef struct alt_fp_int { 422 /** Number of words that contain data. */ 423 unsigned int used; 424 /** Maximum number of words in data. */ 425 unsigned int size; 426 #ifdef WOLFSSL_SP_INT_NEGATIVE 427 /** Indicates whether number is 0/positive or negative. */ 428 unsigned int sign; 429 #endif 430 #ifdef HAVE_WOLF_BIGINT 431 /** Unsigned binary (big endian) representation of number. */ 432 struct WC_BIGINT raw; 433 #endif 434 /** Data of number. */ 435 sp_int_digit dp[SP_INT_DIGITS_ECC]; 436 } alt_fp_int; 437 438 #endif 439 #endif /* ALT_ECC_SIZE */ 440 441 #ifndef WC_ECCKEY_TYPE_DEFINED 442 typedef struct ecc_key ecc_key; 443 #define WC_ECCKEY_TYPE_DEFINED 444 #endif 445 446 #ifndef WC_ECCPOINT_TYPE_DEFINED 447 typedef struct ecc_point ecc_point; 448 #define WC_ECCPOINT_TYPE_DEFINED 449 #endif 450 451 #ifndef WC_ECCSET_TYPE_DEFINED 452 typedef struct ecc_set_type ecc_set_type; 453 #define WC_ECCSET_TYPE_DEFINED 454 #endif 455 456 /* A point on an ECC curve, stored in Jacobian format such that (x,y,z) => 457 (x/z^2, y/z^3, 1) when interpreted as affine */ 458 struct ecc_point { 459 #ifndef ALT_ECC_SIZE 460 mp_int x[1]; /* The x coordinate */ 461 mp_int y[1]; /* The y coordinate */ 462 mp_int z[1]; /* The z coordinate */ 463 #else 464 mp_int* x; /* The x coordinate */ 465 mp_int* y; /* The y coordinate */ 466 mp_int* z; /* The z coordinate */ 467 alt_fp_int xyz[3]; 468 #endif 469 #if defined(WOLFSSL_SMALL_STACK_CACHE) && !defined(WOLFSSL_ECC_NO_SMALL_STACK) 470 ecc_key* key; 471 #endif 472 WC_BITFIELD isAllocated:1; 473 }; 474 475 /* ECC Flags */ 476 enum { 477 WC_ECC_FLAG_NONE = 0x00, 478 WC_ECC_FLAG_COFACTOR = 0x01, 479 WC_ECC_FLAG_DEC_SIGN = 0x02 480 }; 481 482 /* ECC non-blocking */ 483 #ifdef WC_ECC_NONBLOCK 484 typedef struct ecc_nb_ctx { 485 #if defined(WOLFSSL_HAVE_SP_ECC) && defined(WOLFSSL_SP_NONBLOCK) 486 sp_ecc_ctx_t sp_ctx; 487 #else 488 /* build configuration not supported */ 489 #error ECC non-blocking only supports SP (--enable-sp=nonblock) 490 #endif 491 } ecc_nb_ctx_t; 492 #endif /* WC_ECC_NONBLOCK */ 493 494 495 /* An ECC Key */ 496 struct ecc_key { 497 int type; /* Public or Private */ 498 int idx; /* Index into the ecc_sets[] for the parameters of 499 this curve if -1, this key is using user supplied 500 curve in dp */ 501 int state; 502 word32 flags; 503 const ecc_set_type* dp; /* domain parameters, either points to NIST 504 curves (idx >= 0) or user supplied */ 505 #ifdef WOLFSSL_CUSTOM_CURVES 506 int deallocSet; 507 #endif 508 void* heap; /* heap hint */ 509 ecc_point pubkey; /* public key */ 510 #ifndef ALT_ECC_SIZE 511 mp_int k[1]; /* private key */ 512 #else 513 mp_int* k; 514 alt_fp_int ka[1]; 515 #endif 516 #ifdef WOLFSSL_ECC_BLIND_K 517 #ifndef ALT_ECC_SIZE 518 mp_int kb[1]; 519 mp_int ku[1]; 520 #else 521 mp_int* kb; 522 mp_int* ku; 523 alt_fp_int kba[1]; 524 alt_fp_int kua[1]; 525 #endif 526 #endif 527 528 #ifdef WOLFSSL_CAAM 529 word32 blackKey; /* address of key encrypted and in secure memory */ 530 word32 securePubKey; /* address of public key in secure memory */ 531 int partNum; /* partition number*/ 532 #endif 533 #ifdef WOLFSSL_SE050 534 word32 keyId; 535 byte keyIdSet; 536 #endif 537 #if defined(WOLFSSL_ATECC508A) || defined(WOLFSSL_ATECC608A) 538 int slot; /* Key Slot Number (-1 unknown) */ 539 byte pubkey_raw[ECC_MAX_CRYPTO_HW_PUBKEY_SIZE]; 540 #endif 541 #if defined(PLUTON_CRYPTO_ECC) || defined(WOLF_CRYPTO_CB) 542 void* devCtx; 543 int devId; 544 #endif 545 #ifdef WOLFSSL_SILABS_SE_ACCEL 546 sl_se_command_context_t cmd_ctx; 547 sl_se_key_descriptor_t key; 548 /* Used for SiLabs "plaintext" with public X, public Y, and 549 * private D concatenated. These are respectively at offset `0`, 550 * offset `keysize`, and offset `2 * keysize`. 551 */ 552 byte key_raw[3 * ECC_MAX_CRYPTO_HW_SIZE]; 553 #endif 554 #ifdef WOLFSSL_MAXQ10XX_CRYPTO 555 maxq_ecc_t maxq_ctx; 556 #endif 557 #ifdef WOLFSSL_KCAPI_ECC 558 struct kcapi_handle* handle; 559 byte pubkey_raw[MAX_ECC_BYTES * 2]; 560 #endif 561 #if defined(WOLFSSL_XILINX_CRYPT_VERSAL) 562 wc_Xsecure xSec; 563 byte keyRaw[3 * ECC_MAX_CRYPTO_HW_SIZE] ALIGN32; 564 byte* privKey; 565 #endif 566 #ifdef WOLFSSL_ASYNC_CRYPT 567 mp_int* r; /* sign/verify temps */ 568 mp_int* s; 569 WC_ASYNC_DEV asyncDev; 570 #ifdef HAVE_CAVIUM_V 571 mp_int* e; /* Sign, Verify and Shared Secret */ 572 mp_int* signK; 573 #endif 574 #ifdef WOLFSSL_CERT_GEN 575 CertSignCtx certSignCtx; /* context info for cert sign (MakeSignature) */ 576 #endif 577 #endif /* WOLFSSL_ASYNC_CRYPT */ 578 #ifdef WOLF_PRIVATE_KEY_ID 579 byte id[ECC_MAX_ID_LEN]; 580 int idLen; 581 char label[ECC_MAX_LABEL_LEN]; 582 int labelLen; 583 #endif 584 #if defined(WOLFSSL_CRYPTOCELL) 585 ecc_context_t ctx; 586 #endif 587 588 #if defined(WOLFSSL_ECDSA_SET_K) || defined(WOLFSSL_ECDSA_SET_K_ONE_LOOP) || \ 589 defined(WOLFSSL_ECDSA_DETERMINISTIC_K) || \ 590 defined(WOLFSSL_ECDSA_DETERMINISTIC_K_VARIANT) 591 #ifndef WOLFSSL_NO_MALLOC 592 mp_int* sign_k; 593 #else 594 mp_int sign_k[1]; 595 WC_BITFIELD sign_k_set:1; 596 #endif 597 #endif 598 #if defined(WOLFSSL_ECDSA_DETERMINISTIC_K) || \ 599 defined(WOLFSSL_ECDSA_DETERMINISTIC_K_VARIANT) 600 WC_BITFIELD deterministic:1; 601 enum wc_HashType hashType; 602 #endif 603 604 #if defined(WOLFSSL_SMALL_STACK_CACHE) && !defined(WOLFSSL_ECC_NO_SMALL_STACK) 605 mp_int* t1; 606 mp_int* t2; 607 #ifdef ALT_ECC_SIZE 608 mp_int* x; 609 mp_int* y; 610 mp_int* z; 611 #endif 612 #endif 613 614 #ifdef WOLFSSL_DSP 615 remote_handle64 handle; 616 #endif 617 #ifdef ECC_TIMING_RESISTANT 618 WC_RNG* rng; 619 #endif 620 #ifdef WC_ECC_NONBLOCK 621 ecc_nb_ctx_t* nb_ctx; 622 #endif 623 }; 624 625 #ifndef WOLFSSL_ECC_BLIND_K 626 #define ecc_get_k(key) (key)->k 627 #define ecc_blind_k(key, b) (void)b 628 #define ecc_blind_k_rng(key, rng) 0 629 630 #define wc_ecc_key_get_priv(key) (key)->k 631 #else 632 mp_int* ecc_get_k(ecc_key* key); 633 void ecc_blind_k(ecc_key* key, mp_int* b); 634 int ecc_blind_k_rng(ecc_key* key, WC_RNG* rng); 635 636 WOLFSSL_API mp_int* wc_ecc_key_get_priv(ecc_key* key); 637 #endif 638 639 #define WOLFSSL_HAVE_ECC_KEY_GET_PRIV 640 641 642 WOLFSSL_ABI WOLFSSL_API ecc_key* wc_ecc_key_new(void* heap); 643 WOLFSSL_ABI WOLFSSL_API void wc_ecc_key_free(ecc_key* key); 644 645 646 /* ECC predefined curve sets */ 647 #if defined(HAVE_FIPS) && FIPS_VERSION3_LT(6,0,0) 648 extern const ecc_set_type ecc_sets[]; 649 extern const size_t ecc_sets_count; 650 #else 651 WOLFSSL_API const ecc_set_type *wc_ecc_get_sets(void); 652 WOLFSSL_API size_t wc_ecc_get_sets_count(void); 653 #define ecc_sets wc_ecc_get_sets() 654 #define ecc_sets_count wc_ecc_get_sets_count() 655 #endif 656 657 WOLFSSL_API 658 const char* wc_ecc_get_name(int curve_id); 659 660 #ifdef WOLFSSL_PUBLIC_ECC_ADD_DBL 661 #define ECC_API WOLFSSL_API 662 #else 663 #define ECC_API WOLFSSL_LOCAL 664 #endif 665 666 ECC_API int ecc_mul2add(ecc_point* A, mp_int* kA, 667 ecc_point* B, mp_int* kB, 668 ecc_point* C, mp_int* a, mp_int* modulus, void* heap); 669 670 ECC_API int ecc_map(ecc_point* P, mp_int* modulus, mp_digit mp); 671 ECC_API int ecc_map_ex(ecc_point* P, mp_int* modulus, mp_digit mp, int ct); 672 ECC_API int ecc_projective_add_point(ecc_point* P, ecc_point* Q, ecc_point* R, 673 mp_int* a, mp_int* modulus, mp_digit mp); 674 ECC_API int ecc_projective_dbl_point(ecc_point* P, ecc_point* R, mp_int* a, 675 mp_int* modulus, mp_digit mp); 676 677 ECC_API int ecc_projective_add_point_safe(ecc_point* A, ecc_point* B, 678 ecc_point* R, mp_int* a, mp_int* modulus, mp_digit mp, int* infinity); 679 ECC_API int ecc_projective_dbl_point_safe(ecc_point* P, ecc_point* R, mp_int* a, 680 mp_int* modulus, mp_digit mp); 681 682 WOLFSSL_ABI WOLFSSL_API 683 int wc_ecc_make_key(WC_RNG* rng, int keysize, ecc_key* key); 684 WOLFSSL_ABI WOLFSSL_API 685 int wc_ecc_make_key_ex(WC_RNG* rng, int keysize, ecc_key* key, int curve_id); 686 WOLFSSL_API 687 int wc_ecc_make_key_ex2(WC_RNG* rng, int keysize, ecc_key* key, int curve_id, 688 int flags); 689 WOLFSSL_API 690 int wc_ecc_make_pub(ecc_key* key, ecc_point* pubOut); 691 WOLFSSL_API 692 int wc_ecc_make_pub_ex(ecc_key* key, ecc_point* pubOut, WC_RNG* rng); 693 WOLFSSL_ABI WOLFSSL_API 694 int wc_ecc_check_key(ecc_key* key); 695 WOLFSSL_API 696 int wc_ecc_is_point(ecc_point* ecp, mp_int* a, mp_int* b, mp_int* prime); 697 WOLFSSL_API 698 int wc_ecc_get_generator(ecc_point* ecp, int curve_idx); 699 700 #ifdef HAVE_ECC_DHE 701 WOLFSSL_ABI WOLFSSL_API 702 int wc_ecc_shared_secret(ecc_key* private_key, ecc_key* public_key, byte* out, 703 word32* outlen); 704 705 WOLFSSL_API 706 int wc_ecc_shared_secret_ex(ecc_key* private_key, ecc_point* point, 707 byte* out, word32 *outlen); 708 709 /* Internal API for blocking ECDHE call */ 710 WOLFSSL_LOCAL 711 int wc_ecc_shared_secret_gen_sync(ecc_key* private_key, 712 ecc_point* point, byte* out, word32* outlen); 713 714 #if !defined(WOLFSSL_ATECC508A) && !defined(WOLFSSL_ATECC608A) && \ 715 !defined(PLUTON_CRYPTO_ECC) && !defined(WOLFSSL_CRYPTOCELL) 716 #define wc_ecc_shared_secret_ssh wc_ecc_shared_secret_ex /* For backwards compat */ 717 #endif 718 719 #endif /* HAVE_ECC_DHE */ 720 721 #ifdef HAVE_ECC_SIGN 722 WOLFSSL_ABI WOLFSSL_API 723 int wc_ecc_sign_hash(const byte* in, word32 inlen, byte* out, word32 *outlen, 724 WC_RNG* rng, ecc_key* key); 725 WOLFSSL_API 726 int wc_ecc_sign_hash_ex(const byte* in, word32 inlen, WC_RNG* rng, 727 ecc_key* key, mp_int *r, mp_int *s); 728 #if defined(WOLFSSL_ECDSA_DETERMINISTIC_K) || \ 729 defined(WOLFSSL_ECDSA_DETERMINISTIC_K_VARIANT) 730 WOLFSSL_API 731 int wc_ecc_set_deterministic(ecc_key* key, byte flag); 732 WOLFSSL_API 733 int wc_ecc_set_deterministic_ex(ecc_key* key, byte flag, 734 enum wc_HashType hashType); 735 WOLFSSL_API 736 int wc_ecc_gen_deterministic_k(const byte* hash, word32 hashSz, 737 enum wc_HashType hashType, mp_int* priv, mp_int* k, mp_int* order, 738 void* heap); 739 #endif 740 #if defined(WOLFSSL_ECDSA_SET_K) || defined(WOLFSSL_ECDSA_SET_K_ONE_LOOP) 741 WOLFSSL_API 742 int wc_ecc_sign_set_k(const byte* k, word32 klen, ecc_key* key); 743 #endif 744 #endif /* HAVE_ECC_SIGN */ 745 746 #ifdef HAVE_ECC_VERIFY 747 WOLFSSL_ABI WOLFSSL_API 748 int wc_ecc_verify_hash(const byte* sig, word32 siglen, const byte* hash, 749 word32 hashlen, int* res, ecc_key* key); 750 WOLFSSL_API 751 int wc_ecc_verify_hash_ex(mp_int *r, mp_int *s, const byte* hash, 752 word32 hashlen, int* res, ecc_key* key); 753 #endif /* HAVE_ECC_VERIFY */ 754 755 WOLFSSL_ABI WOLFSSL_API 756 int wc_ecc_init(ecc_key* key); 757 WOLFSSL_ABI WOLFSSL_API 758 int wc_ecc_init_ex(ecc_key* key, void* heap, int devId); 759 #ifdef WOLF_PRIVATE_KEY_ID 760 WOLFSSL_API 761 int wc_ecc_init_id(ecc_key* key, unsigned char* id, int len, void* heap, 762 int devId); 763 WOLFSSL_API 764 int wc_ecc_init_label(ecc_key* key, const char* label, void* heap, int devId); 765 #endif 766 #ifdef WOLFSSL_CUSTOM_CURVES 767 WOLFSSL_LOCAL 768 void wc_ecc_free_curve(const ecc_set_type* curve, void* heap); 769 #endif 770 WOLFSSL_ABI WOLFSSL_API 771 int wc_ecc_free(ecc_key* key); 772 WOLFSSL_API 773 int wc_ecc_set_flags(ecc_key* key, word32 flags); 774 WOLFSSL_ABI WOLFSSL_API 775 void wc_ecc_fp_free(void); 776 WOLFSSL_API 777 void wc_ecc_fp_init(void); 778 WOLFSSL_API 779 int wc_ecc_set_rng(ecc_key* key, WC_RNG* rng); 780 781 WOLFSSL_API 782 int wc_ecc_set_curve(ecc_key* key, int keysize, int curve_id); 783 784 WOLFSSL_API 785 int wc_ecc_is_valid_idx(int n); 786 WOLFSSL_API 787 int wc_ecc_get_curve_idx(int curve_id); 788 WOLFSSL_API 789 int wc_ecc_get_curve_id(int curve_idx); 790 #define wc_ecc_get_curve_name_from_id wc_ecc_get_name 791 WOLFSSL_API 792 int wc_ecc_get_curve_size_from_id(int curve_id); 793 794 WOLFSSL_API 795 int wc_ecc_get_curve_idx_from_name(const char* curveName); 796 WOLFSSL_API 797 int wc_ecc_get_curve_size_from_name(const char* curveName); 798 WOLFSSL_API 799 int wc_ecc_get_curve_id_from_name(const char* curveName); 800 WOLFSSL_API 801 int wc_ecc_get_curve_id_from_params(int fieldSize, 802 const byte* prime, word32 primeSz, const byte* Af, word32 AfSz, 803 const byte* Bf, word32 BfSz, const byte* order, word32 orderSz, 804 const byte* Gx, word32 GxSz, const byte* Gy, word32 GySz, int cofactor); 805 WOLFSSL_API 806 int wc_ecc_get_curve_id_from_dp_params(const ecc_set_type* dp); 807 808 WOLFSSL_API 809 int wc_ecc_get_curve_id_from_oid(const byte* oid, word32 len); 810 811 WOLFSSL_API const ecc_set_type* wc_ecc_get_curve_params(int curve_idx); 812 813 WOLFSSL_API 814 ecc_point* wc_ecc_new_point(void); 815 WOLFSSL_API 816 ecc_point* wc_ecc_new_point_h(void* h); 817 WOLFSSL_API 818 void wc_ecc_del_point(ecc_point* p); 819 WOLFSSL_API 820 void wc_ecc_del_point_h(ecc_point* p, void* h); 821 WOLFSSL_API 822 void wc_ecc_forcezero_point(ecc_point* p); 823 WOLFSSL_API 824 int wc_ecc_copy_point(const ecc_point* p, ecc_point *r); 825 WOLFSSL_API 826 int wc_ecc_cmp_point(ecc_point* a, ecc_point *b); 827 WOLFSSL_API 828 int wc_ecc_point_is_at_infinity(ecc_point *p); 829 WOLFSSL_API 830 int wc_ecc_point_is_on_curve(ecc_point *p, int curve_idx); 831 832 #if !defined(WOLFSSL_ATECC508A) && !defined(WOLFSSL_ATECC608A) 833 WOLFSSL_API 834 int wc_ecc_mulmod(const mp_int* k, ecc_point *G, ecc_point *R, 835 mp_int* a, mp_int* modulus, int map); 836 ECC_API 837 int wc_ecc_mulmod_ex(const mp_int* k, ecc_point *G, ecc_point *R, 838 mp_int* a, mp_int* modulus, int map, void* heap); 839 ECC_API 840 int wc_ecc_mulmod_ex2(const mp_int* k, ecc_point *G, ecc_point *R, mp_int* a, 841 mp_int* modulus, mp_int* order, WC_RNG* rng, int map, 842 void* heap); 843 #endif /* !WOLFSSL_ATECC508A */ 844 845 846 #ifdef HAVE_ECC_KEY_EXPORT 847 /* ASN key helpers */ 848 WOLFSSL_ABI WOLFSSL_API 849 int wc_ecc_export_x963(ecc_key* key, byte* out, word32* outLen); 850 WOLFSSL_ABI WOLFSSL_API 851 int wc_ecc_export_x963_ex(ecc_key* key, byte* out, word32* outLen, 852 int compressed); 853 /* extended functionality with compressed option */ 854 #endif /* HAVE_ECC_KEY_EXPORT */ 855 856 #ifdef HAVE_ECC_KEY_IMPORT 857 WOLFSSL_ABI WOLFSSL_API 858 int wc_ecc_import_x963(const byte* in, word32 inLen, ecc_key* key); 859 WOLFSSL_API 860 int wc_ecc_import_x963_ex(const byte* in, word32 inLen, ecc_key* key, 861 int curve_id); 862 WOLFSSL_ABI WOLFSSL_API 863 int wc_ecc_import_private_key(const byte* priv, word32 privSz, const byte* pub, 864 word32 pubSz, ecc_key* key); 865 WOLFSSL_API 866 int wc_ecc_import_private_key_ex(const byte* priv, word32 privSz, 867 const byte* pub, word32 pubSz, ecc_key* key, int curve_id); 868 WOLFSSL_ABI WOLFSSL_API 869 int wc_ecc_rs_to_sig(const char* r, const char* s, byte* out, word32* outlen); 870 WOLFSSL_API 871 int wc_ecc_rs_raw_to_sig(const byte* r, word32 rSz, const byte* s, word32 sSz, 872 byte* out, word32* outlen); 873 WOLFSSL_API 874 int wc_ecc_sig_to_rs(const byte* sig, word32 sigLen, byte* r, word32* rLen, 875 byte* s, word32* sLen); 876 WOLFSSL_ABI WOLFSSL_API 877 int wc_ecc_import_raw(ecc_key* key, const char* qx, const char* qy, 878 const char* d, const char* curveName); 879 WOLFSSL_API 880 int wc_ecc_import_raw_ex(ecc_key* key, const char* qx, const char* qy, 881 const char* d, int curve_id); 882 WOLFSSL_API 883 int wc_ecc_import_unsigned(ecc_key* key, const byte* qx, const byte* qy, 884 const byte* d, int curve_id); 885 #endif /* HAVE_ECC_KEY_IMPORT */ 886 887 #ifdef HAVE_ECC_KEY_EXPORT 888 WOLFSSL_API 889 int wc_ecc_export_ex(ecc_key* key, byte* qx, word32* qxLen, 890 byte* qy, word32* qyLen, byte* d, word32* dLen, 891 int encType); 892 WOLFSSL_ABI WOLFSSL_API 893 int wc_ecc_export_private_only(ecc_key* key, byte* out, word32* outLen); 894 WOLFSSL_API 895 int wc_ecc_export_public_raw(ecc_key* key, byte* qx, word32* qxLen, 896 byte* qy, word32* qyLen); 897 WOLFSSL_API 898 int wc_ecc_export_private_raw(ecc_key* key, byte* qx, word32* qxLen, 899 byte* qy, word32* qyLen, byte* d, word32* dLen); 900 #endif /* HAVE_ECC_KEY_EXPORT */ 901 902 #ifdef HAVE_ECC_KEY_EXPORT 903 WOLFSSL_API 904 int wc_ecc_export_point_der_ex(const int curve_idx, ecc_point* point, byte* out, 905 word32* outLen, int compressed); 906 WOLFSSL_API 907 int wc_ecc_export_point_der(const int curve_idx, ecc_point* point, 908 byte* out, word32* outLen); 909 WOLFSSL_LOCAL 910 int wc_ecc_export_point_der_compressed(const int curve_idx, ecc_point* point, 911 byte* out, word32* outLen); 912 #endif /* HAVE_ECC_KEY_EXPORT */ 913 914 915 #ifdef HAVE_ECC_KEY_IMPORT 916 WOLFSSL_API 917 int wc_ecc_import_point_der_ex(const byte* in, word32 inLen, 918 const int curve_idx, ecc_point* point, 919 int shortKeySize); 920 WOLFSSL_API 921 int wc_ecc_import_point_der(const byte* in, word32 inLen, const int curve_idx, 922 ecc_point* point); 923 #endif /* HAVE_ECC_KEY_IMPORT */ 924 925 /* size helper */ 926 WOLFSSL_ABI WOLFSSL_API 927 int wc_ecc_size(ecc_key* key); 928 WOLFSSL_ABI WOLFSSL_API 929 int wc_ecc_sig_size_calc(int sz); 930 WOLFSSL_ABI WOLFSSL_API 931 int wc_ecc_sig_size(const ecc_key* key); 932 933 WOLFSSL_API 934 int wc_ecc_get_oid(word32 oidSum, const byte** oid, word32* oidSz); 935 936 #ifdef WOLFSSL_CUSTOM_CURVES 937 WOLFSSL_API 938 int wc_ecc_set_custom_curve(ecc_key* key, const ecc_set_type* dp); 939 #endif 940 941 #ifdef HAVE_ECC_ENCRYPT 942 /* ecc encrypt */ 943 944 enum ecEncAlgo { 945 ecAES_128_CBC = 1, /* default */ 946 ecAES_256_CBC = 2, 947 ecAES_128_CTR = 3, 948 ecAES_256_CTR = 4 949 }; 950 951 enum ecKdfAlgo { 952 ecHKDF_SHA256 = 1, /* default */ 953 ecHKDF_SHA1 = 2, 954 ecKDF_X963_SHA1 = 3, 955 ecKDF_X963_SHA256 = 4, 956 ecKDF_SHA1 = 5, 957 ecKDF_SHA256 = 6 958 }; 959 960 enum ecMacAlgo { 961 ecHMAC_SHA256 = 1, /* default */ 962 ecHMAC_SHA1 = 2 963 }; 964 965 enum { 966 KEY_SIZE_128 = 16, 967 KEY_SIZE_256 = 32, 968 IV_SIZE_64 = 8, 969 IV_SIZE_128 = 16, 970 ECC_MAX_IV_SIZE = 16, 971 EXCHANGE_SALT_SZ = 16, 972 EXCHANGE_INFO_SZ = 23 973 }; 974 975 enum ecFlags { 976 REQ_RESP_CLIENT = 1, 977 REQ_RESP_SERVER = 2 978 }; 979 980 #ifndef WOLFSSL_ECIES_GEN_IV_SIZE 981 #define WOLFSSL_ECIES_GEN_IV_SIZE 12 982 #endif 983 984 985 typedef struct ecEncCtx ecEncCtx; 986 987 WOLFSSL_ABI WOLFSSL_API 988 ecEncCtx* wc_ecc_ctx_new(int flags, WC_RNG* rng); 989 WOLFSSL_API 990 ecEncCtx* wc_ecc_ctx_new_ex(int flags, WC_RNG* rng, void* heap); 991 WOLFSSL_ABI WOLFSSL_API 992 void wc_ecc_ctx_free(ecEncCtx* ctx); 993 WOLFSSL_ABI WOLFSSL_API 994 int wc_ecc_ctx_reset(ecEncCtx* ctx, WC_RNG* rng); /* reset for use again w/o alloc/free */ 995 996 WOLFSSL_API 997 int wc_ecc_ctx_set_algo(ecEncCtx* ctx, byte encAlgo, byte kdfAlgo, 998 byte macAlgo); 999 WOLFSSL_API 1000 const byte* wc_ecc_ctx_get_own_salt(ecEncCtx* ctx); 1001 WOLFSSL_API 1002 int wc_ecc_ctx_set_peer_salt(ecEncCtx* ctx, const byte* salt); 1003 WOLFSSL_API 1004 int wc_ecc_ctx_set_own_salt(ecEncCtx* ctx, const byte* salt, word32 sz); 1005 WOLFSSL_API 1006 int wc_ecc_ctx_set_kdf_salt(ecEncCtx* ctx, const byte* salt, word32 sz); 1007 WOLFSSL_API 1008 int wc_ecc_ctx_set_info(ecEncCtx* ctx, const byte* info, int sz); 1009 1010 WOLFSSL_ABI WOLFSSL_API 1011 int wc_ecc_encrypt(ecc_key* privKey, ecc_key* pubKey, const byte* msg, 1012 word32 msgSz, byte* out, word32* outSz, ecEncCtx* ctx); 1013 WOLFSSL_API 1014 int wc_ecc_encrypt_ex(ecc_key* privKey, ecc_key* pubKey, const byte* msg, 1015 word32 msgSz, byte* out, word32* outSz, ecEncCtx* ctx, int compressed); 1016 WOLFSSL_ABI WOLFSSL_API 1017 int wc_ecc_decrypt(ecc_key* privKey, ecc_key* pubKey, const byte* msg, 1018 word32 msgSz, byte* out, word32* outSz, ecEncCtx* ctx); 1019 1020 #endif /* HAVE_ECC_ENCRYPT */ 1021 1022 #ifdef HAVE_X963_KDF 1023 WOLFSSL_API int wc_X963_KDF(enum wc_HashType type, const byte* secret, 1024 word32 secretSz, const byte* sinfo, word32 sinfoSz, 1025 byte* out, word32 outSz); 1026 #endif 1027 1028 #ifdef ECC_CACHE_CURVE 1029 WOLFSSL_API int wc_ecc_curve_cache_init(void); 1030 WOLFSSL_API void wc_ecc_curve_cache_free(void); 1031 #endif 1032 1033 #ifdef HAVE_OID_ENCODING 1034 WOLFSSL_LOCAL int wc_ecc_oid_cache_init(void); 1035 WOLFSSL_LOCAL void wc_ecc_oid_cache_free(void); 1036 #endif 1037 1038 WOLFSSL_API 1039 int wc_ecc_gen_k(WC_RNG* rng, int size, mp_int* k, mp_int* order); 1040 1041 #ifdef WOLFSSL_DSP 1042 WOLFSSL_API 1043 int wc_ecc_set_handle(ecc_key* key, remote_handle64 handle); 1044 WOLFSSL_LOCAL 1045 int sp_dsp_ecc_verify_256(remote_handle64 handle, const byte* hash, word32 hashLen, mp_int* pX, 1046 mp_int* pY, mp_int* pZ, mp_int* r, mp_int* sm, int* res, void* heap); 1047 #endif 1048 1049 #ifdef WOLFSSL_SE050 1050 WOLFSSL_API 1051 int wc_ecc_use_key_id(ecc_key* key, word32 keyId, word32 flags); 1052 WOLFSSL_API 1053 int wc_ecc_get_key_id(ecc_key* key, word32* keyId); 1054 #endif 1055 1056 #ifdef WC_ECC_NONBLOCK 1057 WOLFSSL_API int wc_ecc_set_nonblock(ecc_key *key, ecc_nb_ctx_t* ctx); 1058 #endif 1059 1060 #ifdef __cplusplus 1061 } /* extern "C" */ 1062 #endif 1063 1064 #endif /* HAVE_ECC */ 1065 #endif /* WOLF_CRYPT_ECC_H */