source: asp3_tinet_ecnl_rx/trunk/wolfssl-3.12.2/wolfcrypt/src/rsa.c@ 337

Last change on this file since 337 was 337, checked in by coas-nagasima, 6 years ago

ASP3版ECNLを追加

  • Property svn:eol-style set to native
  • Property svn:mime-type set to text/x-csrc;charset=UTF-8
File size: 58.6 KB
Line 
1/* rsa.c
2 *
3 * Copyright (C) 2006-2017 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 2 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#ifdef HAVE_CONFIG_H
24 #include <config.h>
25#endif
26
27#include <wolfssl/wolfcrypt/settings.h>
28#include <wolfssl/wolfcrypt/error-crypt.h>
29
30#ifndef NO_RSA
31
32#include <wolfssl/wolfcrypt/rsa.h>
33
34#ifdef WOLFSSL_HAVE_SP_RSA
35#include <wolfssl/wolfcrypt/sp.h>
36#endif
37
38/*
39Possible RSA enable options:
40 * NO_RSA: Overall control of RSA default: on (not defined)
41 * WC_RSA_BLINDING: Uses Blinding w/ Private Ops default: off
42 Note: slower by ~20%
43 * WOLFSSL_KEY_GEN: Allows Private Key Generation default: off
44 * RSA_LOW_MEM: NON CRT Private Operations, less memory default: off
45 * WC_NO_RSA_OAEP: Disables RSA OAEP padding default: on (not defined)
46
47*/
48
49/*
50RSA Key Size Configuration:
51 * FP_MAX_BITS: With USE_FAST_MATH only default: 4096
52 If USE_FAST_MATH then use this to override default.
53 Value is key size * 2. Example: RSA 3072 = 6144
54*/
55
56
57#ifdef HAVE_FIPS
58int wc_InitRsaKey(RsaKey* key, void* ptr)
59{
60 if (key == NULL) {
61 return BAD_FUNC_ARG;
62 }
63
64 return InitRsaKey_fips(key, ptr);
65}
66
67int wc_InitRsaKey_ex(RsaKey* key, void* ptr, int devId)
68{
69 (void)devId;
70 if (key == NULL) {
71 return BAD_FUNC_ARG;
72 }
73 return InitRsaKey_fips(key, ptr);
74}
75
76int wc_FreeRsaKey(RsaKey* key)
77{
78 return FreeRsaKey_fips(key);
79}
80
81
82int wc_RsaPublicEncrypt(const byte* in, word32 inLen, byte* out,
83 word32 outLen, RsaKey* key, WC_RNG* rng)
84{
85 if (in == NULL || out == NULL || key == NULL || rng == NULL) {
86 return BAD_FUNC_ARG;
87 }
88 return RsaPublicEncrypt_fips(in, inLen, out, outLen, key, rng);
89}
90
91
92int wc_RsaPrivateDecryptInline(byte* in, word32 inLen, byte** out,
93 RsaKey* key)
94{
95 if (in == NULL || out == NULL || key == NULL) {
96 return BAD_FUNC_ARG;
97 }
98 return RsaPrivateDecryptInline_fips(in, inLen, out, key);
99}
100
101
102int wc_RsaPrivateDecrypt(const byte* in, word32 inLen, byte* out,
103 word32 outLen, RsaKey* key)
104{
105 if (in == NULL || out == NULL || key == NULL) {
106 return BAD_FUNC_ARG;
107 }
108 return RsaPrivateDecrypt_fips(in, inLen, out, outLen, key);
109}
110
111
112int wc_RsaSSL_Sign(const byte* in, word32 inLen, byte* out,
113 word32 outLen, RsaKey* key, WC_RNG* rng)
114{
115 if (in == NULL || out == NULL || key == NULL || inLen == 0) {
116 return BAD_FUNC_ARG;
117 }
118 return RsaSSL_Sign_fips(in, inLen, out, outLen, key, rng);
119}
120
121
122int wc_RsaSSL_VerifyInline(byte* in, word32 inLen, byte** out, RsaKey* key)
123{
124 if (in == NULL || out == NULL || key == NULL) {
125 return BAD_FUNC_ARG;
126 }
127 return RsaSSL_VerifyInline_fips(in, inLen, out, key);
128}
129
130
131int wc_RsaSSL_Verify(const byte* in, word32 inLen, byte* out,
132 word32 outLen, RsaKey* key)
133{
134 if (in == NULL || out == NULL || key == NULL || inLen == 0) {
135 return BAD_FUNC_ARG;
136 }
137 return RsaSSL_Verify_fips(in, inLen, out, outLen, key);
138}
139
140
141int wc_RsaEncryptSize(RsaKey* key)
142{
143 if (key == NULL) {
144 return BAD_FUNC_ARG;
145 }
146 return RsaEncryptSize_fips(key);
147}
148
149
150int wc_RsaFlattenPublicKey(RsaKey* key, byte* a, word32* aSz, byte* b,
151 word32* bSz)
152{
153
154 /* not specified as fips so not needing _fips */
155 return RsaFlattenPublicKey(key, a, aSz, b, bSz);
156}
157#ifdef WOLFSSL_KEY_GEN
158 int wc_MakeRsaKey(RsaKey* key, int size, long e, WC_RNG* rng)
159 {
160 return MakeRsaKey(key, size, e, rng);
161 }
162#endif
163
164
165/* these are functions in asn and are routed to wolfssl/wolfcrypt/asn.c
166* wc_RsaPrivateKeyDecode
167* wc_RsaPublicKeyDecode
168*/
169
170#else /* else build without fips */
171
172#include <wolfssl/wolfcrypt/random.h>
173#include <wolfssl/wolfcrypt/logging.h>
174#ifdef NO_INLINE
175 #include <wolfssl/wolfcrypt/misc.h>
176#else
177 #define WOLFSSL_MISC_INCLUDED
178 #include <wolfcrypt/src/misc.c>
179#endif
180
181#define ERROR_OUT(x) { ret = (x); goto done;}
182
183
184enum {
185 RSA_STATE_NONE = 0,
186
187 RSA_STATE_ENCRYPT_PAD,
188 RSA_STATE_ENCRYPT_EXPTMOD,
189 RSA_STATE_ENCRYPT_RES,
190
191 RSA_STATE_DECRYPT_EXPTMOD,
192 RSA_STATE_DECRYPT_UNPAD,
193 RSA_STATE_DECRYPT_RES,
194};
195
196static void wc_RsaCleanup(RsaKey* key)
197{
198 if (key && key->data) {
199 /* make sure any allocated memory is free'd */
200 if (key->dataIsAlloc) {
201 if (key->type == RSA_PRIVATE_DECRYPT ||
202 key->type == RSA_PRIVATE_ENCRYPT) {
203 ForceZero(key->data, key->dataLen);
204 }
205 XFREE(key->data, key->heap, DYNAMIC_TYPE_WOLF_BIGINT);
206 key->dataIsAlloc = 0;
207 }
208 key->data = NULL;
209 key->dataLen = 0;
210 }
211}
212
213int wc_InitRsaKey_ex(RsaKey* key, void* heap, int devId)
214{
215 int ret = 0;
216
217 if (key == NULL) {
218 return BAD_FUNC_ARG;
219 }
220
221 key->type = RSA_TYPE_UNKNOWN;
222 key->state = RSA_STATE_NONE;
223 key->heap = heap;
224 key->data = NULL;
225 key->dataLen = 0;
226 key->dataIsAlloc = 0;
227#ifdef WC_RSA_BLINDING
228 key->rng = NULL;
229#endif
230
231#ifdef WOLFSSL_ASYNC_CRYPT
232 #ifdef WOLFSSL_CERT_GEN
233 XMEMSET(&key->certSignCtx, 0, sizeof(CertSignCtx));
234 #endif
235
236 #ifdef WC_ASYNC_ENABLE_RSA
237 /* handle as async */
238 ret = wolfAsync_DevCtxInit(&key->asyncDev, WOLFSSL_ASYNC_MARKER_RSA,
239 key->heap, devId);
240 if (ret != 0)
241 return ret;
242 #endif /* WC_ASYNC_ENABLE_RSA */
243#else
244 (void)devId;
245#endif /* WOLFSSL_ASYNC_CRYPT */
246
247 ret = mp_init_multi(&key->n, &key->e, NULL, NULL, NULL, NULL);
248 if (ret != MP_OKAY)
249 return ret;
250
251 ret = mp_init_multi(&key->d, &key->p, &key->q, &key->dP, &key->dQ, &key->u);
252 if (ret != MP_OKAY) {
253 mp_clear(&key->n);
254 mp_clear(&key->e);
255 return ret;
256 }
257
258#ifdef WOLFSSL_XILINX_CRYPT
259 key->pubExp = 0;
260 key->mod = NULL;
261#endif
262
263 return ret;
264}
265
266int wc_InitRsaKey(RsaKey* key, void* heap)
267{
268 return wc_InitRsaKey_ex(key, heap, INVALID_DEVID);
269}
270
271
272#ifdef WOLFSSL_XILINX_CRYPT
273#define MAX_E_SIZE 4
274/* Used to setup hardware state
275 *
276 * key the RSA key to setup
277 *
278 * returns 0 on success
279 */
280int wc_InitRsaHw(RsaKey* key)
281{
282 unsigned char* m; /* RSA modulous */
283 word32 e = 0; /* RSA public exponent */
284 int mSz;
285 int eSz;
286
287 if (key == NULL) {
288 return BAD_FUNC_ARG;
289 }
290
291 mSz = mp_unsigned_bin_size(&(key->n));
292 m = (unsigned char*)XMALLOC(mSz, key->heap, DYNAMIC_TYPE_KEY);
293 if (m == 0) {
294 return MEMORY_E;
295 }
296
297 if (mp_to_unsigned_bin(&(key->n), m) != MP_OKAY) {
298 WOLFSSL_MSG("Unable to get RSA key modulus");
299 XFREE(m, key->heap, DYNAMIC_TYPE_KEY);
300 return MP_READ_E;
301 }
302
303 eSz = mp_unsigned_bin_size(&(key->e));
304 if (eSz > MAX_E_SIZE) {
305 WOLFSSL_MSG("Exponent of size 4 bytes expected");
306 XFREE(m, key->heap, DYNAMIC_TYPE_KEY);
307 return BAD_FUNC_ARG;
308 }
309
310 if (mp_to_unsigned_bin(&(key->e), (byte*)&e + (MAX_E_SIZE - eSz))
311 != MP_OKAY) {
312 XFREE(m, key->heap, DYNAMIC_TYPE_KEY);
313 WOLFSSL_MSG("Unable to get RSA key exponent");
314 return MP_READ_E;
315 }
316
317 /* check for existing mod buffer to avoid memory leak */
318 if (key->mod != NULL) {
319 XFREE(key->mod, key->heap, DYNAMIC_TYPE_KEY);
320 }
321
322 key->pubExp = e;
323 key->mod = m;
324
325 if (XSecure_RsaInitialize(&(key->xRsa), key->mod, NULL,
326 (byte*)&(key->pubExp)) != XST_SUCCESS) {
327 WOLFSSL_MSG("Unable to initialize RSA on hardware");
328 XFREE(m, key->heap, DYNAMIC_TYPE_KEY);
329 return BAD_STATE_E;
330 }
331
332#ifdef WOLFSSL_XILINX_PATCH
333 /* currently a patch of xsecure_rsa.c for 2048 bit keys */
334 if (wc_RsaEncryptSize(key) == 256) {
335 if (XSecure_RsaSetSize(&(key->xRsa), 2048) != XST_SUCCESS) {
336 WOLFSSL_MSG("Unable to set RSA key size on hardware");
337 XFREE(m, key->heap, DYNAMIC_TYPE_KEY);
338 return BAD_STATE_E;
339 }
340 }
341#endif
342
343 return 0;
344}
345#endif /* WOLFSSL_XILINX_CRYPT */
346
347int wc_FreeRsaKey(RsaKey* key)
348{
349 int ret = 0;
350
351 if (key == NULL) {
352 return BAD_FUNC_ARG;
353 }
354
355 wc_RsaCleanup(key);
356
357#if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_RSA)
358 wolfAsync_DevCtxFree(&key->asyncDev, WOLFSSL_ASYNC_MARKER_RSA);
359#endif
360
361 if (key->type == RSA_PRIVATE) {
362 mp_forcezero(&key->u);
363 mp_forcezero(&key->dQ);
364 mp_forcezero(&key->dP);
365 mp_forcezero(&key->q);
366 mp_forcezero(&key->p);
367 mp_forcezero(&key->d);
368 }
369 /* private part */
370 mp_clear(&key->u);
371 mp_clear(&key->dQ);
372 mp_clear(&key->dP);
373 mp_clear(&key->q);
374 mp_clear(&key->p);
375 mp_clear(&key->d);
376
377 /* public part */
378 mp_clear(&key->e);
379 mp_clear(&key->n);
380
381#ifdef WOLFSSL_XILINX_CRYPT
382 XFREE(key->mod, key->heap, DYNAMIC_TYPE_KEY);
383 key->mod = NULL;
384#endif
385
386 return ret;
387}
388
389
390#if !defined(WC_NO_RSA_OAEP) || defined(WC_RSA_PSS)
391/* Uses MGF1 standard as a mask generation function
392 hType: hash type used
393 seed: seed to use for generating mask
394 seedSz: size of seed buffer
395 out: mask output after generation
396 outSz: size of output buffer
397 */
398static int RsaMGF1(enum wc_HashType hType, byte* seed, word32 seedSz,
399 byte* out, word32 outSz, void* heap)
400{
401 byte* tmp;
402 /* needs to be large enough for seed size plus counter(4) */
403 byte tmpA[WC_MAX_DIGEST_SIZE + 4];
404 byte tmpF; /* 1 if dynamic memory needs freed */
405 word32 tmpSz;
406 int hLen;
407 int ret;
408 word32 counter;
409 word32 idx;
410 hLen = wc_HashGetDigestSize(hType);
411 counter = 0;
412 idx = 0;
413
414 (void)heap;
415
416 /* check error return of wc_HashGetDigestSize */
417 if (hLen < 0) {
418 return hLen;
419 }
420
421 /* if tmp is not large enough than use some dynamic memory */
422 if ((seedSz + 4) > sizeof(tmpA) || (word32)hLen > sizeof(tmpA)) {
423 /* find largest amount of memory needed which will be the max of
424 * hLen and (seedSz + 4) since tmp is used to store the hash digest */
425 tmpSz = ((seedSz + 4) > (word32)hLen)? seedSz + 4: (word32)hLen;
426 tmp = (byte*)XMALLOC(tmpSz, heap, DYNAMIC_TYPE_RSA_BUFFER);
427 if (tmp == NULL) {
428 return MEMORY_E;
429 }
430 tmpF = 1; /* make sure to free memory when done */
431 }
432 else {
433 /* use array on the stack */
434 tmpSz = sizeof(tmpA);
435 tmp = tmpA;
436 tmpF = 0; /* no need to free memory at end */
437 }
438
439 do {
440 int i = 0;
441 XMEMCPY(tmp, seed, seedSz);
442
443 /* counter to byte array appended to tmp */
444 tmp[seedSz] = (counter >> 24) & 0xFF;
445 tmp[seedSz + 1] = (counter >> 16) & 0xFF;
446 tmp[seedSz + 2] = (counter >> 8) & 0xFF;
447 tmp[seedSz + 3] = (counter) & 0xFF;
448
449 /* hash and append to existing output */
450 if ((ret = wc_Hash(hType, tmp, (seedSz + 4), tmp, tmpSz)) != 0) {
451 /* check for if dynamic memory was needed, then free */
452 if (tmpF) {
453 XFREE(tmp, heap, DYNAMIC_TYPE_RSA_BUFFER);
454 }
455 return ret;
456 }
457
458 for (i = 0; i < hLen && idx < outSz; i++) {
459 out[idx++] = tmp[i];
460 }
461 counter++;
462 } while (idx < outSz);
463
464 /* check for if dynamic memory was needed, then free */
465 if (tmpF) {
466 XFREE(tmp, heap, DYNAMIC_TYPE_RSA_BUFFER);
467 }
468
469 return 0;
470}
471
472/* helper function to direct which mask generation function is used
473 switeched on type input
474 */
475static int RsaMGF(int type, byte* seed, word32 seedSz, byte* out,
476 word32 outSz, void* heap)
477{
478 int ret;
479
480 switch(type) {
481 #ifndef NO_SHA
482 case WC_MGF1SHA1:
483 ret = RsaMGF1(WC_HASH_TYPE_SHA, seed, seedSz, out, outSz, heap);
484 break;
485 #endif
486 #ifndef NO_SHA256
487 #ifdef WOLFSSL_SHA224
488 case WC_MGF1SHA224:
489 ret = RsaMGF1(WC_HASH_TYPE_SHA224, seed, seedSz, out, outSz, heap);
490 break;
491 #endif
492 case WC_MGF1SHA256:
493 ret = RsaMGF1(WC_HASH_TYPE_SHA256, seed, seedSz, out, outSz, heap);
494 break;
495 #endif
496 #ifdef WOLFSSL_SHA512
497 #ifdef WOLFSSL_SHA384
498 case WC_MGF1SHA384:
499 ret = RsaMGF1(WC_HASH_TYPE_SHA384, seed, seedSz, out, outSz, heap);
500 break;
501 #endif
502 case WC_MGF1SHA512:
503 ret = RsaMGF1(WC_HASH_TYPE_SHA512, seed, seedSz, out, outSz, heap);
504 break;
505 #endif
506 default:
507 WOLFSSL_MSG("Unknown MGF type: check build options");
508 ret = BAD_FUNC_ARG;
509 }
510
511 /* in case of default avoid unused warning */
512 (void)seed;
513 (void)seedSz;
514 (void)out;
515 (void)outSz;
516 (void)heap;
517
518 return ret;
519}
520#endif /* !WC_NO_RSA_OAEP */
521
522
523/* Padding */
524#ifndef WC_NO_RSA_OAEP
525static int RsaPad_OAEP(const byte* input, word32 inputLen, byte* pkcsBlock,
526 word32 pkcsBlockLen, byte padValue, WC_RNG* rng,
527 enum wc_HashType hType, int mgf, byte* optLabel, word32 labelLen,
528 void* heap)
529{
530 int ret;
531 int hLen;
532 int psLen;
533 int i;
534 word32 idx;
535
536 byte* dbMask;
537
538 #ifdef WOLFSSL_SMALL_STACK
539 byte* lHash = NULL;
540 byte* seed = NULL;
541 #else
542 /* must be large enough to contain largest hash */
543 byte lHash[WC_MAX_DIGEST_SIZE];
544 byte seed[ WC_MAX_DIGEST_SIZE];
545 #endif
546
547 /* no label is allowed, but catch if no label provided and length > 0 */
548 if (optLabel == NULL && labelLen > 0) {
549 return BUFFER_E;
550 }
551
552 /* limit of label is the same as limit of hash function which is massive */
553 hLen = wc_HashGetDigestSize(hType);
554 if (hLen < 0) {
555 return hLen;
556 }
557
558 #ifdef WOLFSSL_SMALL_STACK
559 lHash = (byte*)XMALLOC(hLen, heap, DYNAMIC_TYPE_RSA_BUFFER);
560 if (lHash == NULL) {
561 return MEMORY_E;
562 }
563 seed = (byte*)XMALLOC(hLen, heap, DYNAMIC_TYPE_RSA_BUFFER);
564 if (seed == NULL) {
565 XFREE(lHash, heap, DYNAMIC_TYPE_RSA_BUFFER);
566 return MEMORY_E;
567 }
568 #else
569 /* hLen should never be larger than lHash since size is max digest size,
570 but check before blindly calling wc_Hash */
571 if ((word32)hLen > sizeof(lHash)) {
572 WOLFSSL_MSG("OAEP lHash to small for digest!!");
573 return MEMORY_E;
574 }
575 #endif
576
577 if ((ret = wc_Hash(hType, optLabel, labelLen, lHash, hLen)) != 0) {
578 WOLFSSL_MSG("OAEP hash type possibly not supported or lHash to small");
579 #ifdef WOLFSSL_SMALL_STACK
580 XFREE(lHash, heap, DYNAMIC_TYPE_RSA_BUFFER);
581 XFREE(seed, heap, DYNAMIC_TYPE_RSA_BUFFER);
582 #endif
583 return ret;
584 }
585
586 /* handles check of location for idx as well as psLen, cast to int to check
587 for pkcsBlockLen(k) - 2 * hLen - 2 being negative
588 This check is similar to decryption where k > 2 * hLen + 2 as msg
589 size approaches 0. In decryption if k is less than or equal -- then there
590 is no possible room for msg.
591 k = RSA key size
592 hLen = hash digest size -- will always be >= 0 at this point
593 */
594 if ((word32)(2 * hLen + 2) > pkcsBlockLen) {
595 WOLFSSL_MSG("OAEP pad error hash to big for RSA key size");
596 #ifdef WOLFSSL_SMALL_STACK
597 XFREE(lHash, heap, DYNAMIC_TYPE_RSA_BUFFER);
598 XFREE(seed, heap, DYNAMIC_TYPE_RSA_BUFFER);
599 #endif
600 return BAD_FUNC_ARG;
601 }
602
603 if (inputLen > (pkcsBlockLen - 2 * hLen - 2)) {
604 WOLFSSL_MSG("OAEP pad error message too long");
605 #ifdef WOLFSSL_SMALL_STACK
606 XFREE(lHash, heap, DYNAMIC_TYPE_RSA_BUFFER);
607 XFREE(seed, heap, DYNAMIC_TYPE_RSA_BUFFER);
608 #endif
609 return BAD_FUNC_ARG;
610 }
611
612 /* concatenate lHash || PS || 0x01 || msg */
613 idx = pkcsBlockLen - 1 - inputLen;
614 psLen = pkcsBlockLen - inputLen - 2 * hLen - 2;
615 if (pkcsBlockLen < inputLen) { /*make sure not writing over end of buffer */
616 #ifdef WOLFSSL_SMALL_STACK
617 XFREE(lHash, heap, DYNAMIC_TYPE_RSA_BUFFER);
618 XFREE(seed, heap, DYNAMIC_TYPE_RSA_BUFFER);
619 #endif
620 return BUFFER_E;
621 }
622 XMEMCPY(pkcsBlock + (pkcsBlockLen - inputLen), input, inputLen);
623 pkcsBlock[idx--] = 0x01; /* PS and M separator */
624 while (psLen > 0 && idx > 0) {
625 pkcsBlock[idx--] = 0x00;
626 psLen--;
627 }
628
629 idx = idx - hLen + 1;
630 XMEMCPY(pkcsBlock + idx, lHash, hLen);
631
632 /* generate random seed */
633 if ((ret = wc_RNG_GenerateBlock(rng, seed, hLen)) != 0) {
634 #ifdef WOLFSSL_SMALL_STACK
635 XFREE(lHash, heap, DYNAMIC_TYPE_RSA_BUFFER);
636 XFREE(seed, heap, DYNAMIC_TYPE_RSA_BUFFER);
637 #endif
638 return ret;
639 }
640
641 /* create maskedDB from dbMask */
642 dbMask = (byte*)XMALLOC(pkcsBlockLen - hLen - 1, heap, DYNAMIC_TYPE_RSA);
643 if (dbMask == NULL) {
644 #ifdef WOLFSSL_SMALL_STACK
645 XFREE(lHash, heap, DYNAMIC_TYPE_RSA_BUFFER);
646 XFREE(seed, heap, DYNAMIC_TYPE_RSA_BUFFER);
647 #endif
648 return MEMORY_E;
649 }
650 XMEMSET(dbMask, 0, pkcsBlockLen - hLen - 1); /* help static analyzer */
651
652 ret = RsaMGF(mgf, seed, hLen, dbMask, pkcsBlockLen - hLen - 1, heap);
653 if (ret != 0) {
654 XFREE(dbMask, heap, DYNAMIC_TYPE_RSA);
655 #ifdef WOLFSSL_SMALL_STACK
656 XFREE(lHash, heap, DYNAMIC_TYPE_RSA_BUFFER);
657 XFREE(seed, heap, DYNAMIC_TYPE_RSA_BUFFER);
658 #endif
659 return ret;
660 }
661
662 i = 0;
663 idx = hLen + 1;
664 while (idx < pkcsBlockLen && (word32)i < (pkcsBlockLen - hLen -1)) {
665 pkcsBlock[idx] = dbMask[i++] ^ pkcsBlock[idx];
666 idx++;
667 }
668 XFREE(dbMask, heap, DYNAMIC_TYPE_RSA);
669
670
671 /* create maskedSeed from seedMask */
672 idx = 0;
673 pkcsBlock[idx++] = 0x00;
674 /* create seedMask inline */
675 if ((ret = RsaMGF(mgf, pkcsBlock + hLen + 1, pkcsBlockLen - hLen - 1,
676 pkcsBlock + 1, hLen, heap)) != 0) {
677 #ifdef WOLFSSL_SMALL_STACK
678 XFREE(lHash, heap, DYNAMIC_TYPE_RSA_BUFFER);
679 XFREE(seed, heap, DYNAMIC_TYPE_RSA_BUFFER);
680 #endif
681 return ret;
682 }
683
684 /* xor created seedMask with seed to make maskedSeed */
685 i = 0;
686 while (idx < (word32)(hLen + 1) && i < hLen) {
687 pkcsBlock[idx] = pkcsBlock[idx] ^ seed[i++];
688 idx++;
689 }
690
691 #ifdef WOLFSSL_SMALL_STACK
692 XFREE(lHash, heap, DYNAMIC_TYPE_RSA_BUFFER);
693 XFREE(seed, heap, DYNAMIC_TYPE_RSA_BUFFER);
694 #endif
695 (void)padValue;
696
697 return 0;
698}
699#endif /* !WC_NO_RSA_OAEP */
700
701#ifdef WC_RSA_PSS
702/* 0x00 .. 0x00 0x01 | Salt | Gen Hash | 0xbc
703 * XOR MGF over all bytes down to end of Salt
704 * Gen Hash = HASH(8 * 0x00 | Message Hash | Salt)
705 */
706static int RsaPad_PSS(const byte* input, word32 inputLen, byte* pkcsBlock,
707 word32 pkcsBlockLen, WC_RNG* rng, enum wc_HashType hType, int mgf,
708 int bits, void* heap)
709{
710 int ret;
711 int hLen, i;
712 byte* s;
713 byte* m;
714 byte* h;
715 byte salt[WC_MAX_DIGEST_SIZE];
716
717 hLen = wc_HashGetDigestSize(hType);
718 if (hLen < 0)
719 return hLen;
720
721 s = m = pkcsBlock;
722 XMEMSET(m, 0, 8);
723 m += 8;
724 XMEMCPY(m, input, inputLen);
725 m += inputLen;
726 if ((ret = wc_RNG_GenerateBlock(rng, salt, hLen)) != 0)
727 return ret;
728 XMEMCPY(m, salt, hLen);
729 m += hLen;
730
731 h = pkcsBlock + pkcsBlockLen - 1 - hLen;
732 if ((ret = wc_Hash(hType, s, (word32)(m - s), h, hLen)) != 0)
733 return ret;
734 pkcsBlock[pkcsBlockLen - 1] = 0xbc;
735
736 ret = RsaMGF(mgf, h, hLen, pkcsBlock, pkcsBlockLen - hLen - 1, heap);
737 if (ret != 0)
738 return ret;
739 pkcsBlock[0] &= (1 << ((bits - 1) & 0x7)) - 1;
740
741 m = pkcsBlock + pkcsBlockLen - 1 - hLen - hLen - 1;
742 *(m++) ^= 0x01;
743 for (i = 0; i < hLen; i++)
744 m[i] ^= salt[i];
745
746 return 0;
747}
748#endif
749
750static int RsaPad(const byte* input, word32 inputLen, byte* pkcsBlock,
751 word32 pkcsBlockLen, byte padValue, WC_RNG* rng)
752{
753 if (input == NULL || inputLen == 0 || pkcsBlock == NULL ||
754 pkcsBlockLen == 0) {
755 return BAD_FUNC_ARG;
756 }
757
758 pkcsBlock[0] = 0x0; /* set first byte to zero and advance */
759 pkcsBlock++; pkcsBlockLen--;
760 pkcsBlock[0] = padValue; /* insert padValue */
761
762 if (padValue == RSA_BLOCK_TYPE_1) {
763 if (pkcsBlockLen < inputLen + 2) {
764 WOLFSSL_MSG("RsaPad error, invalid length");
765 return RSA_PAD_E;
766 }
767
768 /* pad with 0xff bytes */
769 XMEMSET(&pkcsBlock[1], 0xFF, pkcsBlockLen - inputLen - 2);
770 }
771 else {
772 /* pad with non-zero random bytes */
773 word32 padLen, i;
774 int ret;
775
776 if (pkcsBlockLen < inputLen + 1) {
777 WOLFSSL_MSG("RsaPad error, invalid length");
778 return RSA_PAD_E;
779 }
780
781 padLen = pkcsBlockLen - inputLen - 1;
782 ret = wc_RNG_GenerateBlock(rng, &pkcsBlock[1], padLen);
783 if (ret != 0) {
784 return ret;
785 }
786
787 /* remove zeros */
788 for (i = 1; i < padLen; i++) {
789 if (pkcsBlock[i] == 0) pkcsBlock[i] = 0x01;
790 }
791 }
792
793 pkcsBlock[pkcsBlockLen-inputLen-1] = 0; /* separator */
794 XMEMCPY(pkcsBlock+pkcsBlockLen-inputLen, input, inputLen);
795
796 return 0;
797}
798
799/* helper function to direct which padding is used */
800static int wc_RsaPad_ex(const byte* input, word32 inputLen, byte* pkcsBlock,
801 word32 pkcsBlockLen, byte padValue, WC_RNG* rng, int padType,
802 enum wc_HashType hType, int mgf, byte* optLabel, word32 labelLen, int bits,
803 void* heap)
804{
805 int ret;
806
807 switch (padType)
808 {
809 case WC_RSA_PKCSV15_PAD:
810 /*WOLFSSL_MSG("wolfSSL Using RSA PKCSV15 padding");*/
811 ret = RsaPad(input, inputLen, pkcsBlock, pkcsBlockLen,
812 padValue, rng);
813 break;
814
815 #ifndef WC_NO_RSA_OAEP
816 case WC_RSA_OAEP_PAD:
817 WOLFSSL_MSG("wolfSSL Using RSA OAEP padding");
818 ret = RsaPad_OAEP(input, inputLen, pkcsBlock, pkcsBlockLen,
819 padValue, rng, hType, mgf, optLabel, labelLen, heap);
820 break;
821 #endif
822
823 #ifdef WC_RSA_PSS
824 case WC_RSA_PSS_PAD:
825 WOLFSSL_MSG("wolfSSL Using RSA PSS padding");
826 ret = RsaPad_PSS(input, inputLen, pkcsBlock, pkcsBlockLen, rng,
827 hType, mgf, bits, heap);
828 break;
829 #endif
830
831 default:
832 WOLFSSL_MSG("Unknown RSA Pad Type");
833 ret = RSA_PAD_E;
834 }
835
836 /* silence warning if not used with padding scheme */
837 (void)hType;
838 (void)mgf;
839 (void)optLabel;
840 (void)labelLen;
841 (void)bits;
842 (void)heap;
843
844 return ret;
845}
846
847
848/* UnPadding */
849#ifndef WC_NO_RSA_OAEP
850/* UnPad plaintext, set start to *output, return length of plaintext,
851 * < 0 on error */
852static int RsaUnPad_OAEP(byte *pkcsBlock, unsigned int pkcsBlockLen,
853 byte **output, enum wc_HashType hType, int mgf,
854 byte* optLabel, word32 labelLen, void* heap)
855{
856 int hLen;
857 int ret;
858 byte h[WC_MAX_DIGEST_SIZE]; /* max digest size */
859 byte* tmp;
860 word32 idx;
861
862 /* no label is allowed, but catch if no label provided and length > 0 */
863 if (optLabel == NULL && labelLen > 0) {
864 return BUFFER_E;
865 }
866
867 hLen = wc_HashGetDigestSize(hType);
868 if ((hLen < 0) || (pkcsBlockLen < (2 * (word32)hLen + 2))) {
869 return BAD_FUNC_ARG;
870 }
871
872 tmp = (byte*)XMALLOC(pkcsBlockLen, heap, DYNAMIC_TYPE_RSA_BUFFER);
873 if (tmp == NULL) {
874 return MEMORY_E;
875 }
876 XMEMSET(tmp, 0, pkcsBlockLen);
877
878 /* find seedMask value */
879 if ((ret = RsaMGF(mgf, (byte*)(pkcsBlock + (hLen + 1)),
880 pkcsBlockLen - hLen - 1, tmp, hLen, heap)) != 0) {
881 XFREE(tmp, heap, DYNAMIC_TYPE_RSA_BUFFER);
882 return ret;
883 }
884
885 /* xor seedMask value with maskedSeed to get seed value */
886 for (idx = 0; idx < (word32)hLen; idx++) {
887 tmp[idx] = tmp[idx] ^ pkcsBlock[1 + idx];
888 }
889
890 /* get dbMask value */
891 if ((ret = RsaMGF(mgf, tmp, hLen, tmp + hLen,
892 pkcsBlockLen - hLen - 1, heap)) != 0) {
893 XFREE(tmp, NULL, DYNAMIC_TYPE_RSA_BUFFER);
894 return ret;
895 }
896
897 /* get DB value by doing maskedDB xor dbMask */
898 for (idx = 0; idx < (pkcsBlockLen - hLen - 1); idx++) {
899 pkcsBlock[hLen + 1 + idx] = pkcsBlock[hLen + 1 + idx] ^ tmp[idx + hLen];
900 }
901
902 /* done with use of tmp buffer */
903 XFREE(tmp, heap, DYNAMIC_TYPE_RSA_BUFFER);
904
905 /* advance idx to index of PS and msg separator, account for PS size of 0*/
906 idx = hLen + 1 + hLen;
907 while (idx < pkcsBlockLen && pkcsBlock[idx] == 0) {idx++;}
908
909 /* create hash of label for comparison with hash sent */
910 if ((ret = wc_Hash(hType, optLabel, labelLen, h, hLen)) != 0) {
911 return ret;
912 }
913
914 /* say no to chosen ciphertext attack.
915 Comparison of lHash, Y, and separator value needs to all happen in
916 constant time.
917 Attackers should not be able to get error condition from the timing of
918 these checks.
919 */
920 ret = 0;
921 ret |= ConstantCompare(pkcsBlock + hLen + 1, h, hLen);
922 ret += pkcsBlock[idx++] ^ 0x01; /* separator value is 0x01 */
923 ret += pkcsBlock[0] ^ 0x00; /* Y, the first value, should be 0 */
924
925 if (ret != 0) {
926 WOLFSSL_MSG("RsaUnPad_OAEP: Padding Error");
927 return BAD_PADDING_E;
928 }
929
930 /* adjust pointer to correct location in array and return size of M */
931 *output = (byte*)(pkcsBlock + idx);
932 return pkcsBlockLen - idx;
933}
934#endif /* WC_NO_RSA_OAEP */
935
936#ifdef WC_RSA_PSS
937static int RsaUnPad_PSS(byte *pkcsBlock, unsigned int pkcsBlockLen,
938 byte **output, enum wc_HashType hType, int mgf,
939 int bits, void* heap)
940{
941 int ret;
942 byte* tmp;
943 int hLen, i;
944
945 hLen = wc_HashGetDigestSize(hType);
946 if (hLen < 0)
947 return hLen;
948
949 if (pkcsBlock[pkcsBlockLen - 1] != 0xbc) {
950 WOLFSSL_MSG("RsaUnPad_PSS: Padding Error 0xBC");
951 return BAD_PADDING_E;
952 }
953
954 tmp = (byte*)XMALLOC(pkcsBlockLen, heap, DYNAMIC_TYPE_RSA_BUFFER);
955 if (tmp == NULL) {
956 return MEMORY_E;
957 }
958
959 if ((ret = RsaMGF(mgf, pkcsBlock + pkcsBlockLen - 1 - hLen, hLen,
960 tmp, pkcsBlockLen - 1 - hLen, heap)) != 0) {
961 XFREE(tmp, heap, DYNAMIC_TYPE_RSA_BUFFER);
962 return ret;
963 }
964
965 tmp[0] &= (1 << ((bits - 1) & 0x7)) - 1;
966 for (i = 0; i < (int)(pkcsBlockLen - 1 - hLen - hLen - 1); i++) {
967 if (tmp[i] != pkcsBlock[i]) {
968 XFREE(tmp, heap, DYNAMIC_TYPE_RSA_BUFFER);
969 WOLFSSL_MSG("RsaUnPad_PSS: Padding Error Match");
970 return BAD_PADDING_E;
971 }
972 }
973 if (tmp[i] != (pkcsBlock[i] ^ 0x01)) {
974 XFREE(tmp, heap, DYNAMIC_TYPE_RSA_BUFFER);
975 WOLFSSL_MSG("RsaUnPad_PSS: Padding Error End");
976 return BAD_PADDING_E;
977 }
978 for (i++; i < (int)(pkcsBlockLen - 1 - hLen); i++)
979 pkcsBlock[i] ^= tmp[i];
980
981 XFREE(tmp, heap, DYNAMIC_TYPE_RSA_BUFFER);
982
983 i = pkcsBlockLen - (RSA_PSS_PAD_SZ + 3 * hLen + 1);
984 XMEMSET(pkcsBlock + i, 0, RSA_PSS_PAD_SZ);
985
986 *output = pkcsBlock + i;
987 return RSA_PSS_PAD_SZ + 3 * hLen;
988}
989#endif
990
991/* UnPad plaintext, set start to *output, return length of plaintext,
992 * < 0 on error */
993static int RsaUnPad(const byte *pkcsBlock, unsigned int pkcsBlockLen,
994 byte **output, byte padValue)
995{
996 word32 maxOutputLen = (pkcsBlockLen > 10) ? (pkcsBlockLen - 10) : 0;
997 word32 invalid = 0;
998 word32 i = 1;
999 word32 outputLen;
1000
1001 if (output == NULL || pkcsBlockLen == 0) {
1002 return BAD_FUNC_ARG;
1003 }
1004
1005 if (pkcsBlock[0] != 0x0) { /* skip past zero */
1006 invalid = 1;
1007 }
1008 pkcsBlock++; pkcsBlockLen--;
1009
1010 /* Require block type padValue */
1011 invalid = (pkcsBlock[0] != padValue) || invalid;
1012
1013 /* verify the padding until we find the separator */
1014 if (padValue == RSA_BLOCK_TYPE_1) {
1015 while (i<pkcsBlockLen && pkcsBlock[i++] == 0xFF) {/* Null body */}
1016 }
1017 else {
1018 while (i<pkcsBlockLen && pkcsBlock[i++]) {/* Null body */}
1019 }
1020
1021 if (!(i==pkcsBlockLen || pkcsBlock[i-1]==0)) {
1022 WOLFSSL_MSG("RsaUnPad error, bad formatting");
1023 return RSA_PAD_E;
1024 }
1025
1026 outputLen = pkcsBlockLen - i;
1027 invalid = (outputLen > maxOutputLen) || invalid;
1028
1029 if (invalid) {
1030 WOLFSSL_MSG("RsaUnPad error, invalid formatting");
1031 return RSA_PAD_E;
1032 }
1033
1034 *output = (byte *)(pkcsBlock + i);
1035 return outputLen;
1036}
1037
1038/* helper function to direct unpadding */
1039static int wc_RsaUnPad_ex(byte* pkcsBlock, word32 pkcsBlockLen, byte** out,
1040 byte padValue, int padType, enum wc_HashType hType,
1041 int mgf, byte* optLabel, word32 labelLen, int bits,
1042 void* heap)
1043{
1044 int ret;
1045
1046 switch (padType) {
1047 case WC_RSA_PKCSV15_PAD:
1048 /*WOLFSSL_MSG("wolfSSL Using RSA PKCSV15 un-padding");*/
1049 ret = RsaUnPad(pkcsBlock, pkcsBlockLen, out, padValue);
1050 break;
1051
1052 #ifndef WC_NO_RSA_OAEP
1053 case WC_RSA_OAEP_PAD:
1054 WOLFSSL_MSG("wolfSSL Using RSA OAEP un-padding");
1055 ret = RsaUnPad_OAEP((byte*)pkcsBlock, pkcsBlockLen, out,
1056 hType, mgf, optLabel, labelLen, heap);
1057 break;
1058 #endif
1059
1060 #ifdef WC_RSA_PSS
1061 case WC_RSA_PSS_PAD:
1062 WOLFSSL_MSG("wolfSSL Using RSA PSS un-padding");
1063 ret = RsaUnPad_PSS((byte*)pkcsBlock, pkcsBlockLen, out, hType, mgf,
1064 bits, heap);
1065 break;
1066 #endif
1067
1068 default:
1069 WOLFSSL_MSG("Unknown RSA UnPad Type");
1070 ret = RSA_PAD_E;
1071 }
1072
1073 /* silence warning if not used with padding scheme */
1074 (void)hType;
1075 (void)mgf;
1076 (void)optLabel;
1077 (void)labelLen;
1078 (void)bits;
1079 (void)heap;
1080
1081 return ret;
1082}
1083
1084#if defined(WOLFSSL_XILINX_CRYPT)
1085/*
1086 * Xilinx hardened crypto acceleration.
1087 *
1088 * Returns 0 on success and negative values on error.
1089 */
1090static int wc_RsaFunctionXil(const byte* in, word32 inLen, byte* out,
1091 word32* outLen, int type, RsaKey* key, WC_RNG* rng)
1092{
1093 int ret = 0;
1094 word32 keyLen, len;
1095 (void)rng;
1096
1097 keyLen = wc_RsaEncryptSize(key);
1098 if (keyLen > *outLen) {
1099 WOLFSSL_MSG("Output buffer is not big enough");
1100 return BAD_FUNC_ARG;
1101 }
1102
1103 if (inLen != keyLen) {
1104 WOLFSSL_MSG("Expected that inLen equals RSA key length");
1105 return BAD_FUNC_ARG;
1106 }
1107
1108 switch(type) {
1109 case RSA_PRIVATE_DECRYPT:
1110 case RSA_PRIVATE_ENCRYPT:
1111 /* Currently public exponent is loaded by default.
1112 * In SDK 2017.1 RSA exponent values are expected to be of 4 bytes
1113 * leading to private key operations with Xsecure_RsaDecrypt not being
1114 * supported */
1115 ret = RSA_WRONG_TYPE_E;
1116 break;
1117 case RSA_PUBLIC_ENCRYPT:
1118 case RSA_PUBLIC_DECRYPT:
1119 if (XSecure_RsaDecrypt(&(key->xRsa), in, out) != XST_SUCCESS) {
1120 ret = BAD_STATE_E;
1121 }
1122 break;
1123 default:
1124 ret = RSA_WRONG_TYPE_E;
1125 }
1126
1127 *outLen = keyLen;
1128
1129 return ret;
1130}
1131#endif /* WOLFSSL_XILINX_CRYPT */
1132
1133static int wc_RsaFunctionSync(const byte* in, word32 inLen, byte* out,
1134 word32* outLen, int type, RsaKey* key, WC_RNG* rng)
1135{
1136 mp_int tmp;
1137#ifdef WC_RSA_BLINDING
1138 mp_int rnd, rndi;
1139#endif
1140 int ret = 0;
1141 word32 keyLen, len;
1142
1143#ifdef WOLFSSL_HAVE_SP_RSA
1144#ifndef WOLFSSL_SP_NO_2048
1145 if (mp_count_bits(&key->n) == 2048) {
1146 switch(type) {
1147 case RSA_PRIVATE_DECRYPT:
1148 case RSA_PRIVATE_ENCRYPT:
1149 #ifdef WC_RSA_BLINDING
1150 if (rng == NULL)
1151 return MISSING_RNG_E;
1152 #endif
1153 return sp_RsaPrivate_2048(in, inLen, &key->d, &key->p, &key->q,
1154 &key->dP, &key->dQ, &key->u, &key->n,
1155 out, outLen);
1156 case RSA_PUBLIC_ENCRYPT:
1157 case RSA_PUBLIC_DECRYPT:
1158 return sp_RsaPublic_2048(in, inLen, &key->e, &key->n, out, outLen);
1159 }
1160 }
1161#endif
1162#ifndef WOLFSSL_SP_NO_3072
1163 if (mp_count_bits(&key->n) == 3072) {
1164 switch(type) {
1165 case RSA_PRIVATE_DECRYPT:
1166 case RSA_PRIVATE_ENCRYPT:
1167 #ifdef WC_RSA_BLINDING
1168 if (rng == NULL)
1169 return MISSING_RNG_E;
1170 #endif
1171 return sp_RsaPrivate_3072(in, inLen, &key->d, &key->p, &key->q,
1172 &key->dP, &key->dQ, &key->u, &key->n,
1173 out, outLen);
1174 case RSA_PUBLIC_ENCRYPT:
1175 case RSA_PUBLIC_DECRYPT:
1176 return sp_RsaPublic_3072(in, inLen, &key->e, &key->n, out, outLen);
1177 }
1178 }
1179#endif
1180#endif /* WOLFSSL_HAVE_SP_RSA */
1181
1182 (void)rng;
1183
1184 if (mp_init(&tmp) != MP_OKAY)
1185 return MP_INIT_E;
1186
1187#ifdef WC_RSA_BLINDING
1188 if (type == RSA_PRIVATE_DECRYPT || type == RSA_PRIVATE_ENCRYPT) {
1189 if (mp_init_multi(&rnd, &rndi, NULL, NULL, NULL, NULL) != MP_OKAY) {
1190 mp_clear(&tmp);
1191 return MP_INIT_E;
1192 }
1193 }
1194#endif
1195
1196 if (mp_read_unsigned_bin(&tmp, (byte*)in, inLen) != MP_OKAY)
1197 ERROR_OUT(MP_READ_E);
1198
1199 switch(type) {
1200 case RSA_PRIVATE_DECRYPT:
1201 case RSA_PRIVATE_ENCRYPT:
1202 {
1203 #ifdef WC_RSA_BLINDING
1204 /* blind */
1205 ret = mp_rand(&rnd, get_digit_count(&key->n), rng);
1206 if (ret != MP_OKAY)
1207 goto done;
1208
1209 /* rndi = 1/rnd mod n */
1210 if (mp_invmod(&rnd, &key->n, &rndi) != MP_OKAY)
1211 ERROR_OUT(MP_INVMOD_E);
1212
1213 /* rnd = rnd^e */
1214 if (mp_exptmod(&rnd, &key->e, &key->n, &rnd) != MP_OKAY)
1215 ERROR_OUT(MP_EXPTMOD_E);
1216
1217 /* tmp = tmp*rnd mod n */
1218 if (mp_mulmod(&tmp, &rnd, &key->n, &tmp) != MP_OKAY)
1219 ERROR_OUT(MP_MULMOD_E);
1220 #endif /* WC_RSA_BLINGING */
1221
1222 #ifdef RSA_LOW_MEM /* half as much memory but twice as slow */
1223 if (mp_exptmod(&tmp, &key->d, &key->n, &tmp) != MP_OKAY)
1224 ERROR_OUT(MP_EXPTMOD_E);
1225 #else
1226 /* Return 0 when cond is false and n when cond is true. */
1227 #define COND_N(cond, n) ((0 - (cond)) & (n))
1228 /* If ret has an error value return it otherwise if r is OK then return
1229 * 0 otherwise return e.
1230 */
1231 #define RET_ERR(ret, r, e) \
1232 ((ret) | (COND_N((ret) == 0, COND_N((r) != MP_OKAY, (e)))))
1233
1234 { /* tmpa/b scope */
1235 mp_int tmpa, tmpb;
1236 int r;
1237
1238 if (mp_init(&tmpa) != MP_OKAY)
1239 ERROR_OUT(MP_INIT_E);
1240
1241 if (mp_init(&tmpb) != MP_OKAY) {
1242 mp_clear(&tmpa);
1243 ERROR_OUT(MP_INIT_E);
1244 }
1245
1246 /* tmpa = tmp^dP mod p */
1247 r = mp_exptmod(&tmp, &key->dP, &key->p, &tmpa);
1248 ret = RET_ERR(ret, r, MP_EXPTMOD_E);
1249
1250 /* tmpb = tmp^dQ mod q */
1251 r = mp_exptmod(&tmp, &key->dQ, &key->q, &tmpb);
1252 ret = RET_ERR(ret, r, MP_EXPTMOD_E);
1253
1254 /* tmp = (tmpa - tmpb) * qInv (mod p) */
1255 r = mp_sub(&tmpa, &tmpb, &tmp);
1256 ret = RET_ERR(ret, r, MP_SUB_E);
1257
1258 r = mp_mulmod(&tmp, &key->u, &key->p, &tmp);
1259 ret = RET_ERR(ret, r, MP_MULMOD_E);
1260
1261 /* tmp = tmpb + q * tmp */
1262 r = mp_mul(&tmp, &key->q, &tmp);
1263 ret = RET_ERR(ret, r, MP_MUL_E);
1264
1265 r = mp_add(&tmp, &tmpb, &tmp);
1266 ret = RET_ERR(ret, r, MP_ADD_E);
1267
1268 mp_clear(&tmpa);
1269 mp_clear(&tmpb);
1270
1271 if (ret != 0) {
1272 goto done;
1273 }
1274 #undef RET_ERR
1275 #undef COND_N
1276 } /* tmpa/b scope */
1277 #endif /* RSA_LOW_MEM */
1278
1279 #ifdef WC_RSA_BLINDING
1280 /* unblind */
1281 if (mp_mulmod(&tmp, &rndi, &key->n, &tmp) != MP_OKAY)
1282 ERROR_OUT(MP_MULMOD_E);
1283 #endif /* WC_RSA_BLINDING */
1284
1285 break;
1286 }
1287 case RSA_PUBLIC_ENCRYPT:
1288 case RSA_PUBLIC_DECRYPT:
1289 #ifdef WOLFSSL_XILINX_CRYPT
1290 ret = wc_RsaFunctionXil(in, inLen, out, outLen, type, key, rng);
1291 goto done;
1292 #else
1293 if (mp_exptmod(&tmp, &key->e, &key->n, &tmp) != MP_OKAY)
1294 ERROR_OUT(MP_EXPTMOD_E);
1295 break;
1296 #endif
1297 default:
1298 ERROR_OUT(RSA_WRONG_TYPE_E);
1299 }
1300
1301 keyLen = wc_RsaEncryptSize(key);
1302 if (keyLen > *outLen) {
1303 ERROR_OUT(RSA_BUFFER_E);
1304 }
1305
1306 len = mp_unsigned_bin_size(&tmp);
1307
1308 /* pad front w/ zeros to match key length */
1309 while (len < keyLen) {
1310 *out++ = 0x00;
1311 len++;
1312 }
1313
1314 *outLen = keyLen;
1315
1316 /* convert */
1317 if (mp_to_unsigned_bin(&tmp, out) != MP_OKAY)
1318 ERROR_OUT(MP_TO_E);
1319
1320done:
1321 mp_clear(&tmp);
1322#ifdef WC_RSA_BLINDING
1323 if (type == RSA_PRIVATE_DECRYPT || type == RSA_PRIVATE_ENCRYPT) {
1324 mp_clear(&rndi);
1325 mp_clear(&rnd);
1326 }
1327#endif
1328 return ret;
1329}
1330
1331#if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_RSA)
1332static int wc_RsaFunctionAsync(const byte* in, word32 inLen, byte* out,
1333 word32* outLen, int type, RsaKey* key, WC_RNG* rng)
1334{
1335 int ret = 0;
1336
1337 (void)rng;
1338
1339#ifdef WOLFSSL_ASYNC_CRYPT_TEST
1340 if (wc_AsyncTestInit(&key->asyncDev, ASYNC_TEST_RSA_FUNC)) {
1341 WC_ASYNC_TEST* testDev = &key->asyncDev.test;
1342 testDev->rsaFunc.in = in;
1343 testDev->rsaFunc.inSz = inLen;
1344 testDev->rsaFunc.out = out;
1345 testDev->rsaFunc.outSz = outLen;
1346 testDev->rsaFunc.type = type;
1347 testDev->rsaFunc.key = key;
1348 testDev->rsaFunc.rng = rng;
1349 return WC_PENDING_E;
1350 }
1351#endif /* WOLFSSL_ASYNC_CRYPT_TEST */
1352
1353 switch(type) {
1354 case RSA_PRIVATE_DECRYPT:
1355 case RSA_PRIVATE_ENCRYPT:
1356 #ifdef HAVE_CAVIUM
1357 ret = NitroxRsaExptMod(in, inLen,
1358 key->d.raw.buf, key->d.raw.len,
1359 key->n.raw.buf, key->n.raw.len,
1360 out, outLen, key);
1361 #elif defined(HAVE_INTEL_QA)
1362 #ifdef RSA_LOW_MEM
1363 ret = IntelQaRsaPrivate(&key->asyncDev, in, inLen,
1364 &key->d.raw, &key->n.raw,
1365 out, outLen);
1366 #else
1367 ret = IntelQaRsaCrtPrivate(&key->asyncDev, in, inLen,
1368 &key->p.raw, &key->q.raw,
1369 &key->dP.raw, &key->dQ.raw,
1370 &key->u.raw,
1371 out, outLen);
1372 #endif
1373 #else /* WOLFSSL_ASYNC_CRYPT_TEST */
1374 ret = wc_RsaFunctionSync(in, inLen, out, outLen, type, key, rng);
1375 #endif
1376 break;
1377
1378 case RSA_PUBLIC_ENCRYPT:
1379 case RSA_PUBLIC_DECRYPT:
1380 #ifdef HAVE_CAVIUM
1381 ret = NitroxRsaExptMod(in, inLen,
1382 key->e.raw.buf, key->e.raw.len,
1383 key->n.raw.buf, key->n.raw.len,
1384 out, outLen, key);
1385 #elif defined(HAVE_INTEL_QA)
1386 ret = IntelQaRsaPublic(&key->asyncDev, in, inLen,
1387 &key->e.raw, &key->n.raw,
1388 out, outLen);
1389 #else /* WOLFSSL_ASYNC_CRYPT_TEST */
1390 ret = wc_RsaFunctionSync(in, inLen, out, outLen, type, key, rng);
1391 #endif
1392 break;
1393
1394 default:
1395 ret = RSA_WRONG_TYPE_E;
1396 }
1397
1398 return ret;
1399}
1400#endif /* WOLFSSL_ASYNC_CRYPT && WC_ASYNC_ENABLE_RSA */
1401
1402int wc_RsaFunction(const byte* in, word32 inLen, byte* out,
1403 word32* outLen, int type, RsaKey* key, WC_RNG* rng)
1404{
1405 int ret;
1406
1407 if (key == NULL || in == NULL || inLen == 0 || out == NULL ||
1408 outLen == NULL || *outLen == 0 || type == RSA_TYPE_UNKNOWN) {
1409 return BAD_FUNC_ARG;
1410 }
1411
1412#if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_RSA)
1413 if (key->asyncDev.marker == WOLFSSL_ASYNC_MARKER_RSA &&
1414 key->n.raw.len > 0) {
1415 ret = wc_RsaFunctionAsync(in, inLen, out, outLen, type, key, rng);
1416 }
1417 else
1418#endif
1419 {
1420 ret = wc_RsaFunctionSync(in, inLen, out, outLen, type, key, rng);
1421 }
1422
1423 /* handle error */
1424 if (ret < 0 && ret != WC_PENDING_E) {
1425 if (ret == MP_EXPTMOD_E) {
1426 /* This can happen due to incorrectly set FP_MAX_BITS or missing XREALLOC */
1427 WOLFSSL_MSG("RSA_FUNCTION MP_EXPTMOD_E: memory/config problem");
1428 }
1429
1430 key->state = RSA_STATE_NONE;
1431 wc_RsaCleanup(key);
1432 }
1433
1434 return ret;
1435}
1436
1437
1438/* Internal Wrappers */
1439/* Gives the option of choosing padding type
1440 in : input to be encrypted
1441 inLen: length of input buffer
1442 out: encrypted output
1443 outLen: length of encrypted output buffer
1444 key : wolfSSL initialized RSA key struct
1445 rng : wolfSSL initialized random number struct
1446 rsa_type : type of RSA: RSA_PUBLIC_ENCRYPT, RSA_PUBLIC_DECRYPT,
1447 RSA_PRIVATE_ENCRYPT or RSA_PRIVATE_DECRYPT
1448 pad_value: RSA_BLOCK_TYPE_1 or RSA_BLOCK_TYPE_2
1449 pad_type : type of padding: WC_RSA_PKCSV15_PAD, WC_RSA_OAEP_PAD or
1450 WC_RSA_PSS_PAD
1451 hash : type of hash algorithm to use found in wolfssl/wolfcrypt/hash.h
1452 mgf : type of mask generation function to use
1453 label : optional label
1454 labelSz : size of optional label buffer */
1455static int RsaPublicEncryptEx(const byte* in, word32 inLen, byte* out,
1456 word32 outLen, RsaKey* key, int rsa_type,
1457 byte pad_value, int pad_type,
1458 enum wc_HashType hash, int mgf,
1459 byte* label, word32 labelSz, WC_RNG* rng)
1460{
1461 int ret, sz;
1462
1463 if (in == NULL || inLen == 0 || out == NULL || key == NULL) {
1464 return BAD_FUNC_ARG;
1465 }
1466
1467 sz = wc_RsaEncryptSize(key);
1468 if (sz > (int)outLen) {
1469 return RSA_BUFFER_E;
1470 }
1471
1472 if (sz < RSA_MIN_PAD_SZ) {
1473 return WC_KEY_SIZE_E;
1474 }
1475
1476 if (inLen > (word32)(sz - RSA_MIN_PAD_SZ)) {
1477 return RSA_BUFFER_E;
1478 }
1479
1480 switch (key->state) {
1481 case RSA_STATE_NONE:
1482 case RSA_STATE_ENCRYPT_PAD:
1483 key->state = RSA_STATE_ENCRYPT_PAD;
1484
1485 #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_RSA) && \
1486 defined(HAVE_CAVIUM)
1487 if (key->asyncDev.marker == WOLFSSL_ASYNC_MARKER_RSA && key->n.raw.buf) {
1488 /* Async operations that include padding */
1489 if (rsa_type == RSA_PUBLIC_ENCRYPT &&
1490 pad_value == RSA_BLOCK_TYPE_2) {
1491 key->state = RSA_STATE_ENCRYPT_RES;
1492 key->dataLen = key->n.raw.len;
1493 return NitroxRsaPublicEncrypt(in, inLen, out, outLen, key);
1494 }
1495 else if (rsa_type == RSA_PRIVATE_ENCRYPT &&
1496 pad_value == RSA_BLOCK_TYPE_1) {
1497 key->state = RSA_STATE_ENCRYPT_RES;
1498 key->dataLen = key->n.raw.len;
1499 return NitroxRsaSSL_Sign(in, inLen, out, outLen, key);
1500 }
1501 }
1502 #endif
1503
1504 ret = wc_RsaPad_ex(in, inLen, out, sz, pad_value, rng, pad_type, hash,
1505 mgf, label, labelSz, mp_count_bits(&key->n),
1506 key->heap);
1507 if (ret < 0) {
1508 break;
1509 }
1510
1511 key->state = RSA_STATE_ENCRYPT_EXPTMOD;
1512
1513 FALL_THROUGH;
1514
1515 case RSA_STATE_ENCRYPT_EXPTMOD:
1516
1517 key->dataLen = outLen;
1518 ret = wc_RsaFunction(out, sz, out, &key->dataLen, rsa_type, key, rng);
1519
1520 if (ret >= 0 || ret == WC_PENDING_E) {
1521 key->state = RSA_STATE_ENCRYPT_RES;
1522 }
1523 if (ret < 0) {
1524 break;
1525 }
1526
1527 FALL_THROUGH;
1528
1529 case RSA_STATE_ENCRYPT_RES:
1530 ret = key->dataLen;
1531 break;
1532
1533 default:
1534 ret = BAD_STATE_E;
1535 break;
1536 }
1537
1538 /* if async pending then return and skip done cleanup below */
1539 if (ret == WC_PENDING_E) {
1540 return ret;
1541 }
1542
1543 key->state = RSA_STATE_NONE;
1544 wc_RsaCleanup(key);
1545
1546 return ret;
1547}
1548
1549/* Gives the option of choosing padding type
1550 in : input to be decrypted
1551 inLen: length of input buffer
1552 out: decrypted message
1553 outLen: length of decrypted message in bytes
1554 outPtr: optional inline output pointer (if provided doing inline)
1555 key : wolfSSL initialized RSA key struct
1556 rsa_type : type of RSA: RSA_PUBLIC_ENCRYPT, RSA_PUBLIC_DECRYPT,
1557 RSA_PRIVATE_ENCRYPT or RSA_PRIVATE_DECRYPT
1558 pad_value: RSA_BLOCK_TYPE_1 or RSA_BLOCK_TYPE_2
1559 pad_type : type of padding: WC_RSA_PKCSV15_PAD, WC_RSA_OAEP_PAD
1560 WC_RSA_PSS_PAD
1561 hash : type of hash algorithm to use found in wolfssl/wolfcrypt/hash.h
1562 mgf : type of mask generation function to use
1563 label : optional label
1564 labelSz : size of optional label buffer */
1565static int RsaPrivateDecryptEx(byte* in, word32 inLen, byte* out,
1566 word32 outLen, byte** outPtr, RsaKey* key,
1567 int rsa_type, byte pad_value, int pad_type,
1568 enum wc_HashType hash, int mgf,
1569 byte* label, word32 labelSz, WC_RNG* rng)
1570{
1571 int ret = RSA_WRONG_TYPE_E;
1572
1573 if (in == NULL || inLen == 0 || out == NULL || key == NULL) {
1574 return BAD_FUNC_ARG;
1575 }
1576
1577 switch (key->state) {
1578 case RSA_STATE_NONE:
1579 case RSA_STATE_DECRYPT_EXPTMOD:
1580 key->state = RSA_STATE_DECRYPT_EXPTMOD;
1581 key->dataLen = inLen;
1582
1583 #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_RSA) && \
1584 defined(HAVE_CAVIUM)
1585 /* Async operations that include padding */
1586 if (key->asyncDev.marker == WOLFSSL_ASYNC_MARKER_RSA) {
1587 if (rsa_type == RSA_PRIVATE_DECRYPT &&
1588 pad_value == RSA_BLOCK_TYPE_2) {
1589 key->state = RSA_STATE_DECRYPT_RES;
1590 key->data = NULL;
1591 if (outPtr)
1592 *outPtr = in;
1593 return NitroxRsaPrivateDecrypt(in, inLen, out, &key->dataLen, key);
1594 }
1595 else if (rsa_type == RSA_PUBLIC_DECRYPT &&
1596 pad_value == RSA_BLOCK_TYPE_1) {
1597 key->state = RSA_STATE_DECRYPT_RES;
1598 key->data = NULL;
1599 return NitroxRsaSSL_Verify(in, inLen, out, &key->dataLen, key);
1600 }
1601 }
1602 #endif
1603
1604 /* verify the tmp ptr is NULL, otherwise indicates bad state */
1605 if (key->data != NULL) {
1606 ret = BAD_STATE_E;
1607 break;
1608 }
1609
1610 /* if not doing this inline then allocate a buffer for it */
1611 if (outPtr == NULL) {
1612 key->data = (byte*)XMALLOC(inLen, key->heap, DYNAMIC_TYPE_WOLF_BIGINT);
1613 key->dataIsAlloc = 1;
1614 if (key->data == NULL) {
1615 ret = MEMORY_E;
1616 break;
1617 }
1618 XMEMCPY(key->data, in, inLen);
1619 }
1620 else {
1621 key->data = out;
1622 }
1623 ret = wc_RsaFunction(key->data, inLen, key->data, &key->dataLen, rsa_type,
1624 key, rng);
1625
1626 if (ret >= 0 || ret == WC_PENDING_E) {
1627 key->state = RSA_STATE_DECRYPT_UNPAD;
1628 }
1629 if (ret < 0) {
1630 break;
1631 }
1632
1633 FALL_THROUGH;
1634
1635 case RSA_STATE_DECRYPT_UNPAD:
1636 {
1637 byte* pad = NULL;
1638 ret = wc_RsaUnPad_ex(key->data, key->dataLen, &pad, pad_value, pad_type,
1639 hash, mgf, label, labelSz, mp_count_bits(&key->n),
1640 key->heap);
1641 if (ret > 0 && ret <= (int)outLen && pad != NULL) {
1642 /* only copy output if not inline */
1643 if (outPtr == NULL) {
1644 XMEMCPY(out, pad, ret);
1645 }
1646 else {
1647 *outPtr = pad;
1648 }
1649 }
1650 else if (ret >= 0) {
1651 ret = RSA_BUFFER_E;
1652 }
1653 if (ret < 0) {
1654 break;
1655 }
1656
1657 key->state = RSA_STATE_DECRYPT_RES;
1658
1659 FALL_THROUGH;
1660 }
1661 case RSA_STATE_DECRYPT_RES:
1662 #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_RSA) && \
1663 defined(HAVE_CAVIUM)
1664 if (key->asyncDev.marker == WOLFSSL_ASYNC_MARKER_RSA) {
1665 /* return event ret */
1666 ret = key->asyncDev.event.ret;
1667 if (ret == 0) {
1668 /* convert result */
1669 byte* dataLen = (byte*)&key->dataLen;
1670 ret = (dataLen[0] << 8) | (dataLen[1]);
1671 }
1672 }
1673 #endif
1674 break;
1675
1676 default:
1677 ret = BAD_STATE_E;
1678 break;
1679 }
1680
1681 /* if async pending then return and skip done cleanup below */
1682 if (ret == WC_PENDING_E) {
1683 return ret;
1684 }
1685
1686 key->state = RSA_STATE_NONE;
1687 wc_RsaCleanup(key);
1688
1689 return ret;
1690}
1691
1692
1693/* Public RSA Functions */
1694int wc_RsaPublicEncrypt(const byte* in, word32 inLen, byte* out, word32 outLen,
1695 RsaKey* key, WC_RNG* rng)
1696{
1697 return RsaPublicEncryptEx(in, inLen, out, outLen, key,
1698 RSA_PUBLIC_ENCRYPT, RSA_BLOCK_TYPE_2, WC_RSA_PKCSV15_PAD,
1699 WC_HASH_TYPE_NONE, WC_MGF1NONE, NULL, 0, rng);
1700}
1701
1702
1703#ifndef WC_NO_RSA_OAEP
1704int wc_RsaPublicEncrypt_ex(const byte* in, word32 inLen, byte* out,
1705 word32 outLen, RsaKey* key, WC_RNG* rng, int type,
1706 enum wc_HashType hash, int mgf, byte* label,
1707 word32 labelSz)
1708{
1709 return RsaPublicEncryptEx(in, inLen, out, outLen, key, RSA_PUBLIC_ENCRYPT,
1710 RSA_BLOCK_TYPE_2, type, hash, mgf, label, labelSz, rng);
1711}
1712#endif /* WC_NO_RSA_OAEP */
1713
1714
1715int wc_RsaPrivateDecryptInline(byte* in, word32 inLen, byte** out, RsaKey* key)
1716{
1717 WC_RNG* rng = NULL;
1718#ifdef WC_RSA_BLINDING
1719 rng = key->rng;
1720#endif
1721 return RsaPrivateDecryptEx(in, inLen, in, inLen, out, key,
1722 RSA_PRIVATE_DECRYPT, RSA_BLOCK_TYPE_2, WC_RSA_PKCSV15_PAD,
1723 WC_HASH_TYPE_NONE, WC_MGF1NONE, NULL, 0, rng);
1724}
1725
1726
1727#ifndef WC_NO_RSA_OAEP
1728int wc_RsaPrivateDecryptInline_ex(byte* in, word32 inLen, byte** out,
1729 RsaKey* key, int type, enum wc_HashType hash,
1730 int mgf, byte* label, word32 labelSz)
1731{
1732 WC_RNG* rng = NULL;
1733#ifdef WC_RSA_BLINDING
1734 rng = key->rng;
1735#endif
1736 return RsaPrivateDecryptEx(in, inLen, in, inLen, out, key,
1737 RSA_PRIVATE_DECRYPT, RSA_BLOCK_TYPE_2, type, hash,
1738 mgf, label, labelSz, rng);
1739}
1740#endif /* WC_NO_RSA_OAEP */
1741
1742
1743int wc_RsaPrivateDecrypt(const byte* in, word32 inLen, byte* out,
1744 word32 outLen, RsaKey* key)
1745{
1746 WC_RNG* rng = NULL;
1747#ifdef WC_RSA_BLINDING
1748 rng = key->rng;
1749#endif
1750 return RsaPrivateDecryptEx((byte*)in, inLen, out, outLen, NULL, key,
1751 RSA_PRIVATE_DECRYPT, RSA_BLOCK_TYPE_2, WC_RSA_PKCSV15_PAD,
1752 WC_HASH_TYPE_NONE, WC_MGF1NONE, NULL, 0, rng);
1753}
1754
1755#ifndef WC_NO_RSA_OAEP
1756int wc_RsaPrivateDecrypt_ex(const byte* in, word32 inLen, byte* out,
1757 word32 outLen, RsaKey* key, int type,
1758 enum wc_HashType hash, int mgf, byte* label,
1759 word32 labelSz)
1760{
1761 WC_RNG* rng = NULL;
1762#ifdef WC_RSA_BLINDING
1763 rng = key->rng;
1764#endif
1765 return RsaPrivateDecryptEx((byte*)in, inLen, out, outLen, NULL, key,
1766 RSA_PRIVATE_DECRYPT, RSA_BLOCK_TYPE_2, type, hash, mgf, label,
1767 labelSz, rng);
1768}
1769#endif /* WC_NO_RSA_OAEP */
1770
1771
1772int wc_RsaSSL_VerifyInline(byte* in, word32 inLen, byte** out, RsaKey* key)
1773{
1774 WC_RNG* rng = NULL;
1775#ifdef WC_RSA_BLINDING
1776 rng = key->rng;
1777#endif
1778 return RsaPrivateDecryptEx(in, inLen, in, inLen, out, key,
1779 RSA_PUBLIC_DECRYPT, RSA_BLOCK_TYPE_1, WC_RSA_PKCSV15_PAD,
1780 WC_HASH_TYPE_NONE, WC_MGF1NONE, NULL, 0, rng);
1781}
1782
1783int wc_RsaSSL_Verify(const byte* in, word32 inLen, byte* out, word32 outLen,
1784 RsaKey* key)
1785{
1786 WC_RNG* rng;
1787
1788 if (key == NULL) {
1789 return BAD_FUNC_ARG;
1790 }
1791
1792 rng = NULL;
1793#ifdef WC_RSA_BLINDING
1794 rng = key->rng;
1795#endif
1796 return RsaPrivateDecryptEx((byte*)in, inLen, out, outLen, NULL, key,
1797 RSA_PUBLIC_DECRYPT, RSA_BLOCK_TYPE_1, WC_RSA_PKCSV15_PAD,
1798 WC_HASH_TYPE_NONE, WC_MGF1NONE, NULL, 0, rng);
1799}
1800
1801#ifdef WC_RSA_PSS
1802int wc_RsaPSS_VerifyInline(byte* in, word32 inLen, byte** out,
1803 enum wc_HashType hash, int mgf, RsaKey* key)
1804{
1805 WC_RNG* rng = NULL;
1806#ifdef WC_RSA_BLINDING
1807 rng = key->rng;
1808#endif
1809 return RsaPrivateDecryptEx(in, inLen, in, inLen, out, key,
1810 RSA_PUBLIC_DECRYPT, RSA_BLOCK_TYPE_1, WC_RSA_PSS_PAD,
1811 hash, mgf, NULL, 0, rng);
1812}
1813
1814/* Sig = 8 * 0x00 | Space for Message Hash | Salt | Exp Hash
1815 * Exp Hash = HASH(8 * 0x00 | Message Hash | Salt)
1816 */
1817int wc_RsaPSS_CheckPadding(const byte* in, word32 inSz, byte* sig,
1818 word32 sigSz, enum wc_HashType hashType)
1819{
1820 int ret;
1821
1822 if (in == NULL || sig == NULL ||
1823 inSz != (word32)wc_HashGetDigestSize(hashType) ||
1824 sigSz != RSA_PSS_PAD_SZ + inSz * 3)
1825 ret = BAD_FUNC_ARG;
1826 else {
1827 XMEMCPY(sig + RSA_PSS_PAD_SZ, in, inSz);
1828 ret = wc_Hash(hashType, sig, RSA_PSS_PAD_SZ + inSz * 2, sig, inSz);
1829 if (ret != 0)
1830 return ret;
1831 if (XMEMCMP(sig, sig + RSA_PSS_PAD_SZ + inSz * 2, inSz) != 0) {
1832 WOLFSSL_MSG("RsaPSS_CheckPadding: Padding Error");
1833 ret = BAD_PADDING_E;
1834 }
1835 else
1836 ret = 0;
1837 }
1838
1839 return ret;
1840}
1841#endif
1842
1843int wc_RsaSSL_Sign(const byte* in, word32 inLen, byte* out, word32 outLen,
1844 RsaKey* key, WC_RNG* rng)
1845{
1846 return RsaPublicEncryptEx(in, inLen, out, outLen, key,
1847 RSA_PRIVATE_ENCRYPT, RSA_BLOCK_TYPE_1, WC_RSA_PKCSV15_PAD,
1848 WC_HASH_TYPE_NONE, WC_MGF1NONE, NULL, 0, rng);
1849}
1850
1851#ifdef WC_RSA_PSS
1852int wc_RsaPSS_Sign(const byte* in, word32 inLen, byte* out, word32 outLen,
1853 enum wc_HashType hash, int mgf, RsaKey* key, WC_RNG* rng)
1854{
1855 return RsaPublicEncryptEx(in, inLen, out, outLen, key,
1856 RSA_PRIVATE_ENCRYPT, RSA_BLOCK_TYPE_1, WC_RSA_PSS_PAD,
1857 hash, mgf, NULL, 0, rng);
1858}
1859#endif
1860
1861int wc_RsaEncryptSize(RsaKey* key)
1862{
1863 if (key == NULL) {
1864 return BAD_FUNC_ARG;
1865 }
1866 return mp_unsigned_bin_size(&key->n);
1867}
1868
1869
1870/* flatten RsaKey structure into individual elements (e, n) */
1871int wc_RsaFlattenPublicKey(RsaKey* key, byte* e, word32* eSz, byte* n,
1872 word32* nSz)
1873{
1874 int sz, ret;
1875
1876 if (key == NULL || e == NULL || eSz == NULL || n == NULL || nSz == NULL) {
1877 return BAD_FUNC_ARG;
1878 }
1879
1880 sz = mp_unsigned_bin_size(&key->e);
1881 if ((word32)sz > *eSz)
1882 return RSA_BUFFER_E;
1883 ret = mp_to_unsigned_bin(&key->e, e);
1884 if (ret != MP_OKAY)
1885 return ret;
1886 *eSz = (word32)sz;
1887
1888 sz = wc_RsaEncryptSize(key);
1889 if ((word32)sz > *nSz)
1890 return RSA_BUFFER_E;
1891 ret = mp_to_unsigned_bin(&key->n, n);
1892 if (ret != MP_OKAY)
1893 return ret;
1894 *nSz = (word32)sz;
1895
1896 return 0;
1897}
1898
1899#ifdef WOLFSSL_KEY_GEN
1900/* Make an RSA key for size bits, with e specified, 65537 is a good e */
1901int wc_MakeRsaKey(RsaKey* key, int size, long e, WC_RNG* rng)
1902{
1903 mp_int p, q, tmp1, tmp2, tmp3;
1904 int err;
1905
1906 if (key == NULL || rng == NULL)
1907 return BAD_FUNC_ARG;
1908
1909 if (size < RSA_MIN_SIZE || size > RSA_MAX_SIZE)
1910 return BAD_FUNC_ARG;
1911
1912 if (e < 3 || (e & 1) == 0)
1913 return BAD_FUNC_ARG;
1914
1915#if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_RSA)
1916 if (key->asyncDev.marker == WOLFSSL_ASYNC_MARKER_RSA) {
1917 #ifdef HAVE_CAVIUM
1918 /* TODO: Not implemented */
1919 #elif defined(HAVE_INTEL_QA)
1920 /* TODO: Not implemented */
1921 #else
1922 if (wc_AsyncTestInit(&key->asyncDev, ASYNC_TEST_RSA_MAKE)) {
1923 WC_ASYNC_TEST* testDev = &key->asyncDev.test;
1924 testDev->rsaMake.rng = rng;
1925 testDev->rsaMake.key = key;
1926 testDev->rsaMake.size = size;
1927 testDev->rsaMake.e = e;
1928 return WC_PENDING_E;
1929 }
1930 #endif
1931 }
1932#endif
1933
1934 if ((err = mp_init_multi(&p, &q, &tmp1, &tmp2, &tmp3, NULL)) != MP_OKAY)
1935 return err;
1936
1937 err = mp_set_int(&tmp3, e);
1938
1939 /* make p */
1940 if (err == MP_OKAY) {
1941 do {
1942 err = mp_rand_prime(&p, size/16, rng, key->heap); /* size in bytes/2 */
1943
1944 if (err == MP_OKAY)
1945 err = mp_sub_d(&p, 1, &tmp1); /* tmp1 = p-1 */
1946
1947 if (err == MP_OKAY)
1948 err = mp_gcd(&tmp1, &tmp3, &tmp2); /* tmp2 = gcd(p-1, e) */
1949 } while (err == MP_OKAY && mp_cmp_d(&tmp2, 1) != 0); /* e divides p-1 */
1950 }
1951
1952 /* make q */
1953 if (err == MP_OKAY) {
1954 do {
1955 err = mp_rand_prime(&q, size/16, rng, key->heap); /* size in bytes/2 */
1956
1957 if (err == MP_OKAY)
1958 err = mp_sub_d(&q, 1, &tmp1); /* tmp1 = q-1 */
1959
1960 if (err == MP_OKAY)
1961 err = mp_gcd(&tmp1, &tmp3, &tmp2); /* tmp2 = gcd(q-1, e) */
1962 } while (err == MP_OKAY && mp_cmp_d(&tmp2, 1) != 0); /* e divides q-1 */
1963 }
1964
1965 if (err == MP_OKAY)
1966 err = mp_init_multi(&key->n, &key->e, &key->d, &key->p, &key->q, NULL);
1967
1968 if (err == MP_OKAY)
1969 err = mp_init_multi(&key->dP, &key->dQ, &key->u, NULL, NULL, NULL);
1970
1971 if (err == MP_OKAY)
1972 err = mp_sub_d(&p, 1, &tmp2); /* tmp2 = p-1 */
1973
1974 if (err == MP_OKAY)
1975 err = mp_lcm(&tmp1, &tmp2, &tmp1); /* tmp1 = lcm(p-1, q-1),last loop */
1976
1977 /* make key */
1978 if (err == MP_OKAY)
1979 err = mp_set_int(&key->e, (mp_digit)e); /* key->e = e */
1980
1981 if (err == MP_OKAY) /* key->d = 1/e mod lcm(p-1, q-1) */
1982 err = mp_invmod(&key->e, &tmp1, &key->d);
1983
1984 if (err == MP_OKAY)
1985 err = mp_mul(&p, &q, &key->n); /* key->n = pq */
1986
1987 if (err == MP_OKAY)
1988 err = mp_sub_d(&p, 1, &tmp1);
1989
1990 if (err == MP_OKAY)
1991 err = mp_sub_d(&q, 1, &tmp2);
1992
1993 if (err == MP_OKAY)
1994 err = mp_mod(&key->d, &tmp1, &key->dP);
1995
1996 if (err == MP_OKAY)
1997 err = mp_mod(&key->d, &tmp2, &key->dQ);
1998
1999 if (err == MP_OKAY)
2000 err = mp_invmod(&q, &p, &key->u);
2001
2002 if (err == MP_OKAY)
2003 err = mp_copy(&p, &key->p);
2004
2005 if (err == MP_OKAY)
2006 err = mp_copy(&q, &key->q);
2007
2008 if (err == MP_OKAY)
2009 key->type = RSA_PRIVATE;
2010
2011 mp_clear(&tmp3);
2012 mp_clear(&tmp2);
2013 mp_clear(&tmp1);
2014 mp_clear(&q);
2015 mp_clear(&p);
2016
2017 if (err != MP_OKAY) {
2018 wc_FreeRsaKey(key);
2019 return err;
2020 }
2021
2022#ifdef WOLFSSL_XILINX_CRYPT
2023 if (wc_InitRsaHw(key) != 0) {
2024 return BAD_STATE_E;
2025 }
2026#endif
2027
2028 return 0;
2029}
2030#endif /* WOLFSSL_KEY_GEN */
2031
2032
2033#ifdef WC_RSA_BLINDING
2034
2035int wc_RsaSetRNG(RsaKey* key, WC_RNG* rng)
2036{
2037 if (key == NULL)
2038 return BAD_FUNC_ARG;
2039
2040 key->rng = rng;
2041
2042 return 0;
2043}
2044
2045#endif /* WC_RSA_BLINDING */
2046
2047
2048#undef ERROR_OUT
2049
2050#endif /* HAVE_FIPS */
2051#endif /* NO_RSA */
Note: See TracBrowser for help on using the repository browser.