1 /*
2 * This file is part of the openHiTLS project.
3 *
4 * openHiTLS is licensed under the Mulan PSL v2.
5 * You can use this software according to the terms and conditions of the Mulan PSL v2.
6 * You may obtain a copy of Mulan PSL v2 at:
7 *
8 * http://license.coscl.org.cn/MulanPSL2
9 *
10 * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
11 * EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
12 * MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
13 * See the Mulan PSL v2 for more details.
14 */
15
16 #include "hitls_build.h"
17 #if defined(HITLS_CRYPTO_RSA_BLINDING) || defined(HITLS_CRYPTO_RSA_BSSA)
18
19 #include "crypt_utils.h"
20 #include "crypt_rsa.h"
21 #include "rsa_local.h"
22 #include "crypt_errno.h"
23 #include "bsl_sal.h"
24 #include "securec.h"
25 #include "bsl_err_internal.h"
26
RSA_BlindNewCtx(void)27 RSA_Blind *RSA_BlindNewCtx(void)
28 {
29 RSA_Blind *ret = BSL_SAL_Malloc(sizeof(RSA_Blind));
30 if (ret == NULL) {
31 BSL_ERR_PUSH_ERROR(CRYPT_MEM_ALLOC_FAIL);
32 return NULL;
33 }
34 (void)memset_s(ret, sizeof(RSA_Blind), 0, sizeof(RSA_Blind));
35 return ret;
36 }
37
RSA_BlindFreeCtx(RSA_Blind * b)38 void RSA_BlindFreeCtx(RSA_Blind *b)
39 {
40 if (b == NULL) {
41 return;
42 }
43 BN_Destroy(b->r);
44 BN_Destroy(b->rInv);
45 BSL_SAL_FREE(b);
46 }
47
BlindUpdate(RSA_Blind * b,BN_BigNum * n,BN_Optimizer * opt)48 static int32_t BlindUpdate(RSA_Blind *b, BN_BigNum *n, BN_Optimizer *opt)
49 {
50 int32_t ret = BN_ModMul(b->r, b->r, b->r, n, opt);
51 if (ret != CRYPT_SUCCESS) {
52 BSL_ERR_PUSH_ERROR(ret);
53 return ret;
54 }
55 ret = BN_ModMul(b->rInv, b->rInv, b->rInv, n, opt);
56 if (ret != CRYPT_SUCCESS) {
57 BSL_ERR_PUSH_ERROR(ret);
58 }
59 return ret;
60 }
61
RSA_BlindCovert(RSA_Blind * b,BN_BigNum * data,BN_BigNum * n,BN_Optimizer * opt)62 int32_t RSA_BlindCovert(RSA_Blind *b, BN_BigNum *data, BN_BigNum *n, BN_Optimizer *opt)
63 {
64 int32_t ret;
65
66 ret = BlindUpdate(b, n, opt);
67 if (ret != CRYPT_SUCCESS) {
68 return ret;
69 }
70 // 8. z = m * x mod n
71 ret = BN_ModMul(data, data, b->r, n, opt);
72 if (ret != CRYPT_SUCCESS) {
73 BSL_ERR_PUSH_ERROR(ret);
74 }
75
76 return ret;
77 }
78
RSA_BlindInvert(RSA_Blind * b,BN_BigNum * data,BN_BigNum * n,BN_Optimizer * opt)79 int32_t RSA_BlindInvert(RSA_Blind *b, BN_BigNum *data, BN_BigNum *n, BN_Optimizer *opt)
80 {
81 int32_t ret;
82 ret = BN_ModMul(data, data, b->rInv, n, opt);
83 if (ret != CRYPT_SUCCESS) {
84 BSL_ERR_PUSH_ERROR(ret);
85 }
86 return ret;
87 }
88
RSA_CreateBlind(RSA_Blind * b,uint32_t bits)89 int32_t RSA_CreateBlind(RSA_Blind *b, uint32_t bits)
90 {
91 // create a BigNum
92 b->r = BN_Create(bits);
93 if (b->r == NULL) {
94 BSL_ERR_PUSH_ERROR(CRYPT_MEM_ALLOC_FAIL);
95 return CRYPT_MEM_ALLOC_FAIL;
96 }
97
98 b->rInv = BN_Create(bits);
99 if (b->rInv == NULL) {
100 BSL_ERR_PUSH_ERROR(CRYPT_MEM_ALLOC_FAIL);
101 return CRYPT_MEM_ALLOC_FAIL;
102 }
103 return CRYPT_SUCCESS;
104 }
105
106 /*
107 * Initializes blind signature parameters for an RSA key.
108 * Ref. https://www.rfc-editor.org/rfc/rfc9474.html#name-blind
109 *
110 * As RFC-9474 Section 2.1, we need to do this.
111 * 1. Generates a random blinding factor r
112 * 2. Computes r^(-1) mod n (modular inverse)
113 * 3. Computes r^e mod n (where e is the public exponent)
114 */
RSA_BlindCreateParam(void * libCtx,RSA_Blind * b,BN_BigNum * e,BN_BigNum * n,uint32_t bits,BN_Optimizer * opt)115 int32_t RSA_BlindCreateParam(void *libCtx, RSA_Blind *b, BN_BigNum *e, BN_BigNum *n, uint32_t bits, BN_Optimizer *opt)
116 {
117 int32_t ret;
118 if (b == NULL || e == NULL || n == NULL) {
119 BSL_ERR_PUSH_ERROR(CRYPT_NULL_INPUT);
120 return CRYPT_NULL_INPUT;
121 }
122
123 BN_Destroy(b->r);
124 BN_Destroy(b->rInv);
125 b->r = NULL;
126 b->rInv = NULL;
127
128 ret = RSA_CreateBlind(b, bits);
129 if (ret != CRYPT_SUCCESS) {
130 BSL_ERR_PUSH_ERROR(ret);
131 goto END;
132 }
133
134 // b->r = random_integer_uniform(1, n)
135 ret = BN_RandRangeEx(libCtx, b->r, n);
136 if (ret != CRYPT_SUCCESS) {
137 BSL_ERR_PUSH_ERROR(ret);
138 goto END;
139 }
140
141 // b->rInv = inverse_mod(r, n)
142 ret = BN_ModInv(b->rInv, b->r, n, opt);
143 if (ret != CRYPT_SUCCESS) {
144 BSL_ERR_PUSH_ERROR(ret);
145 goto END;
146 }
147
148 // b->r = RSAVP1(pk, r)
149 ret = BN_ModExp(b->r, b->r, e, n, opt);
150 if (ret != CRYPT_SUCCESS) {
151 BSL_ERR_PUSH_ERROR(ret);
152 goto END;
153 }
154 return ret;
155 END:
156 BN_Destroy(b->r);
157 BN_Destroy(b->rInv);
158 b->r = NULL;
159 b->rInv = NULL;
160 return ret;
161 }
162 #endif /* HITLS_CRYPTO_RSA_BLINDING || HITLS_CRYPTO_RSA_BSSA */