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 #ifdef HITLS_CRYPTO_CODECSKEY
18
19 #include <stdint.h>
20 #include <string.h>
21
22 #ifdef HITLS_BSL_SAL_FILE
23 #include "sal_file.h"
24 #endif
25 #include "bsl_types.h"
26 #include "bsl_asn1.h"
27
28 #ifdef HITLS_BSL_PEM
29 #include "bsl_pem_internal.h"
30 #endif // HITLS_BSL_PEM
31
32 #include "bsl_err_internal.h"
33 #include "crypt_errno.h"
34 #include "crypt_types.h"
35 #include "crypt_eal_pkey.h"
36 #include "crypt_eal_codecs.h"
37 #include "crypt_encode_decode_local.h"
38 #include "crypt_encode_decode_key.h"
39
CRYPT_EAL_GetEncodeFormat(const char * format)40 int32_t CRYPT_EAL_GetEncodeFormat(const char *format)
41 {
42 if (format == NULL) {
43 return BSL_FORMAT_UNKNOWN;
44 }
45 static const struct {
46 const char *formatStr;
47 int32_t formatInt;
48 } FORMAT_MAP[] = {
49 {"ASN1", BSL_FORMAT_ASN1},
50 {"PEM", BSL_FORMAT_PEM},
51 {"PFX_COM", BSL_FORMAT_PFX_COM},
52 {"PKCS12", BSL_FORMAT_PKCS12},
53 {"OBJECT", BSL_FORMAT_OBJECT}
54 };
55
56 for (size_t i = 0; i < sizeof(FORMAT_MAP) / sizeof(FORMAT_MAP[0]); i++) {
57 if (strcmp(format, FORMAT_MAP[i].formatStr) == 0) {
58 return FORMAT_MAP[i].formatInt;
59 }
60 }
61
62 return BSL_FORMAT_UNKNOWN;
63 }
64
65 #ifdef HITLS_BSL_PEM
EAL_GetPemPubKeySymbol(int32_t type,BSL_PEM_Symbol * symbol)66 static int32_t EAL_GetPemPubKeySymbol(int32_t type, BSL_PEM_Symbol *symbol)
67 {
68 switch (type) {
69 case CRYPT_PUBKEY_SUBKEY:
70 symbol->head = BSL_PEM_PUB_KEY_BEGIN_STR;
71 symbol->tail = BSL_PEM_PUB_KEY_END_STR;
72 return CRYPT_SUCCESS;
73 #ifdef HITLS_CRYPTO_RSA
74 case CRYPT_PUBKEY_RSA:
75 symbol->head = BSL_PEM_RSA_PUB_KEY_BEGIN_STR;
76 symbol->tail = BSL_PEM_RSA_PUB_KEY_END_STR;
77 return CRYPT_SUCCESS;
78 #endif
79 default:
80 BSL_ERR_PUSH_ERROR(CRYPT_DECODE_NO_SUPPORT_TYPE);
81 return CRYPT_DECODE_NO_SUPPORT_TYPE;
82 }
83 }
84
EAL_GetPemPriKeySymbol(int32_t type,BSL_PEM_Symbol * symbol)85 static int32_t EAL_GetPemPriKeySymbol(int32_t type, BSL_PEM_Symbol *symbol)
86 {
87 switch (type) {
88 #ifdef HITLS_CRYPTO_ECDSA
89 case CRYPT_PRIKEY_ECC:
90 symbol->head = BSL_PEM_EC_PRI_KEY_BEGIN_STR;
91 symbol->tail = BSL_PEM_EC_PRI_KEY_END_STR;
92 return CRYPT_SUCCESS;
93 #endif
94 #ifdef HITLS_CRYPTO_RSA
95 case CRYPT_PRIKEY_RSA:
96 symbol->head = BSL_PEM_RSA_PRI_KEY_BEGIN_STR;
97 symbol->tail = BSL_PEM_RSA_PRI_KEY_END_STR;
98 return CRYPT_SUCCESS;
99 #endif
100 case CRYPT_PRIKEY_PKCS8_UNENCRYPT:
101 symbol->head = BSL_PEM_PRI_KEY_BEGIN_STR;
102 symbol->tail = BSL_PEM_PRI_KEY_END_STR;
103 return CRYPT_SUCCESS;
104 case CRYPT_PRIKEY_PKCS8_ENCRYPT:
105 symbol->head = BSL_PEM_P8_PRI_KEY_BEGIN_STR;
106 symbol->tail = BSL_PEM_P8_PRI_KEY_END_STR;
107 return CRYPT_SUCCESS;
108 default:
109 BSL_ERR_PUSH_ERROR(CRYPT_DECODE_NO_SUPPORT_TYPE);
110 return CRYPT_DECODE_NO_SUPPORT_TYPE;
111 }
112 }
113 #endif // HITLS_BSL_PEM
114
115 #ifdef HITLS_CRYPTO_KEY_DECODE
CRYPT_EAL_ParseAsn1PriKey(int32_t type,BSL_Buffer * encode,const BSL_Buffer * pwd,CRYPT_EAL_PkeyCtx ** ealPriKey)116 int32_t CRYPT_EAL_ParseAsn1PriKey(int32_t type, BSL_Buffer *encode, const BSL_Buffer *pwd,
117 CRYPT_EAL_PkeyCtx **ealPriKey)
118 {
119 (void)pwd;
120 switch (type) {
121 #ifdef HITLS_CRYPTO_ECDSA
122 case CRYPT_PRIKEY_ECC:
123 return ParseEccPrikeyAsn1Buff(encode->data, encode->dataLen, NULL, ealPriKey);
124 #endif
125 #ifdef HITLS_CRYPTO_RSA
126 case CRYPT_PRIKEY_RSA:
127 return ParseRsaPrikeyAsn1Buff(encode->data, encode->dataLen, NULL, BSL_CID_UNKNOWN,
128 ealPriKey);
129 #endif
130 case CRYPT_PRIKEY_PKCS8_UNENCRYPT:
131 return ParsePk8PriKeyBuff(encode, ealPriKey);
132 #ifdef HITLS_CRYPTO_KEY_EPKI
133 case CRYPT_PRIKEY_PKCS8_ENCRYPT:
134 return ParsePk8EncPriKeyBuff(encode, pwd, ealPriKey);
135 #endif
136 default:
137 BSL_ERR_PUSH_ERROR(CRYPT_DECODE_NO_SUPPORT_TYPE);
138 return CRYPT_DECODE_NO_SUPPORT_TYPE;
139 }
140 }
141
142 #ifdef HITLS_BSL_PEM
CRYPT_EAL_ParsePemPriKey(int32_t type,BSL_Buffer * encode,const BSL_Buffer * pwd,CRYPT_EAL_PkeyCtx ** ealPriKey)143 int32_t CRYPT_EAL_ParsePemPriKey(int32_t type, BSL_Buffer *encode, const BSL_Buffer *pwd,
144 CRYPT_EAL_PkeyCtx **ealPriKey)
145 {
146 BSL_PEM_Symbol symbol = {0};
147 int32_t ret = EAL_GetPemPriKeySymbol(type, &symbol);
148 if (ret != CRYPT_SUCCESS) {
149 return ret;
150 }
151 BSL_Buffer asn1 = {0};
152 ret = BSL_PEM_DecodePemToAsn1((char **)&(encode->data), &(encode->dataLen), &symbol, &(asn1.data),
153 &(asn1.dataLen));
154 if (ret != BSL_SUCCESS) {
155 BSL_ERR_PUSH_ERROR(ret);
156 return ret;
157 }
158 ret = CRYPT_EAL_ParseAsn1PriKey(type, &asn1, pwd, ealPriKey);
159 BSL_SAL_Free(asn1.data);
160 if (ret != CRYPT_SUCCESS) {
161 BSL_ERR_PUSH_ERROR(ret);
162 }
163 return ret;
164 }
165 #endif // HITLS_BSL_PEM
166
CRYPT_EAL_ParseUnknownPriKey(int32_t type,BSL_Buffer * encode,const BSL_Buffer * pwd,CRYPT_EAL_PkeyCtx ** ealPriKey)167 int32_t CRYPT_EAL_ParseUnknownPriKey(int32_t type, BSL_Buffer *encode, const BSL_Buffer *pwd,
168 CRYPT_EAL_PkeyCtx **ealPriKey)
169 {
170 #ifdef HITLS_BSL_PEM
171 bool isPem = BSL_PEM_IsPemFormat((char *)(encode->data), encode->dataLen);
172 if (isPem) {
173 return CRYPT_EAL_ParsePemPriKey(type, encode, pwd, ealPriKey);
174 }
175 #endif
176 return CRYPT_EAL_ParseAsn1PriKey(type, encode, pwd, ealPriKey);
177 }
178
CRYPT_EAL_PriKeyParseBuff(BSL_ParseFormat format,int32_t type,BSL_Buffer * encode,const BSL_Buffer * pwd,CRYPT_EAL_PkeyCtx ** ealPriKey)179 int32_t CRYPT_EAL_PriKeyParseBuff(BSL_ParseFormat format, int32_t type, BSL_Buffer *encode, const BSL_Buffer *pwd,
180 CRYPT_EAL_PkeyCtx **ealPriKey)
181 {
182 if (encode == NULL || encode->data == NULL || encode->dataLen == 0 || ealPriKey == NULL) {
183 BSL_ERR_PUSH_ERROR(CRYPT_INVALID_ARG);
184 return CRYPT_INVALID_ARG;
185 }
186
187 switch (format) {
188 case BSL_FORMAT_ASN1:
189 return CRYPT_EAL_ParseAsn1PriKey(type, encode, pwd, ealPriKey);
190 #ifdef HITLS_BSL_PEM
191 case BSL_FORMAT_PEM:
192 return CRYPT_EAL_ParsePemPriKey(type, encode, pwd, ealPriKey);
193 #endif // HITLS_BSL_PEM
194 case BSL_FORMAT_UNKNOWN:
195 return CRYPT_EAL_ParseUnknownPriKey(type, encode, pwd, ealPriKey);
196 default:
197 return CRYPT_DECODE_NO_SUPPORT_FORMAT;
198 }
199 }
200
CRYPT_EAL_ParseAsn1PubKey(int32_t type,BSL_Buffer * encode,CRYPT_EAL_PkeyCtx ** ealPubKey)201 int32_t CRYPT_EAL_ParseAsn1PubKey(int32_t type, BSL_Buffer *encode, CRYPT_EAL_PkeyCtx **ealPubKey)
202 {
203 switch (type) {
204 case CRYPT_PUBKEY_SUBKEY_WITHOUT_SEQ:
205 return CRYPT_EAL_ParseAsn1SubPubkey(encode->data, encode->dataLen, (void **)ealPubKey, false);
206 case CRYPT_PUBKEY_SUBKEY:
207 return CRYPT_EAL_ParseAsn1SubPubkey(encode->data, encode->dataLen, (void **)ealPubKey, true);
208 default:
209 #ifdef HITLS_CRYPTO_RSA
210 return ParseRsaPubkeyAsn1Buff(encode->data, encode->dataLen, NULL, ealPubKey, BSL_CID_UNKNOWN);
211 #else
212 return CRYPT_DECODE_NO_SUPPORT_TYPE;
213 #endif
214 }
215 }
216
217 #ifdef HITLS_BSL_PEM
CRYPT_EAL_ParsePemPubKey(int32_t type,BSL_Buffer * encode,CRYPT_EAL_PkeyCtx ** ealPubKey)218 int32_t CRYPT_EAL_ParsePemPubKey(int32_t type, BSL_Buffer *encode, CRYPT_EAL_PkeyCtx **ealPubKey)
219 {
220 BSL_PEM_Symbol symbol = {0};
221 int32_t ret = EAL_GetPemPubKeySymbol(type, &symbol);
222 if (ret != CRYPT_SUCCESS) {
223 return ret;
224 }
225 BSL_Buffer asn1 = {0};
226 ret = BSL_PEM_DecodePemToAsn1((char **)&(encode->data), &(encode->dataLen), &symbol, &(asn1.data), &(asn1.dataLen));
227 if (ret != BSL_SUCCESS) {
228 BSL_ERR_PUSH_ERROR(ret);
229 return ret;
230 }
231 ret = CRYPT_EAL_ParseAsn1PubKey(type, &asn1, ealPubKey);
232 BSL_SAL_Free(asn1.data);
233 if (ret != CRYPT_SUCCESS) {
234 BSL_ERR_PUSH_ERROR(ret);
235 }
236 return ret;
237 }
238
239 #endif // HITLS_BSL_PEM
CRYPT_EAL_ParseUnknownPubKey(int32_t type,BSL_Buffer * encode,CRYPT_EAL_PkeyCtx ** ealPubKey)240 int32_t CRYPT_EAL_ParseUnknownPubKey(int32_t type, BSL_Buffer *encode, CRYPT_EAL_PkeyCtx **ealPubKey)
241 {
242 #ifdef HITLS_BSL_PEM
243 bool isPem = BSL_PEM_IsPemFormat((char *)(encode->data), encode->dataLen);
244 if (isPem) {
245 return CRYPT_EAL_ParsePemPubKey(type, encode, ealPubKey);
246 }
247 #endif
248 return CRYPT_EAL_ParseAsn1PubKey(type, encode, ealPubKey);
249 }
250
CRYPT_EAL_PubKeyParseBuff(BSL_ParseFormat format,int32_t type,BSL_Buffer * encode,CRYPT_EAL_PkeyCtx ** ealPubKey)251 int32_t CRYPT_EAL_PubKeyParseBuff(BSL_ParseFormat format, int32_t type, BSL_Buffer *encode,
252 CRYPT_EAL_PkeyCtx **ealPubKey)
253 {
254 if (encode == NULL || encode->data == NULL || encode->dataLen == 0 || ealPubKey == NULL) {
255 BSL_ERR_PUSH_ERROR(CRYPT_INVALID_ARG);
256 return CRYPT_INVALID_ARG;
257 }
258
259 switch (format) {
260 case BSL_FORMAT_ASN1:
261 return CRYPT_EAL_ParseAsn1PubKey(type, encode, ealPubKey);
262 #ifdef HITLS_BSL_PEM
263 case BSL_FORMAT_PEM:
264 return CRYPT_EAL_ParsePemPubKey(type, encode, ealPubKey);
265 #endif // HITLS_BSL_PEM
266 case BSL_FORMAT_UNKNOWN:
267 return CRYPT_EAL_ParseUnknownPubKey(type, encode, ealPubKey);
268 default:
269 return CRYPT_DECODE_NO_SUPPORT_FORMAT;
270 }
271 }
272
CRYPT_EAL_UnKnownKeyParseBuff(BSL_ParseFormat format,const BSL_Buffer * pwd,BSL_Buffer * encode,CRYPT_EAL_PkeyCtx ** ealPKey)273 int32_t CRYPT_EAL_UnKnownKeyParseBuff(BSL_ParseFormat format, const BSL_Buffer *pwd, BSL_Buffer *encode,
274 CRYPT_EAL_PkeyCtx **ealPKey)
275 {
276 int32_t ret;
277 for (int32_t type = CRYPT_PRIKEY_PKCS8_UNENCRYPT; type <= CRYPT_PRIKEY_ECC; type++) {
278 ret = CRYPT_EAL_PriKeyParseBuff(format, type, encode, pwd, ealPKey);
279 if (ret == CRYPT_SUCCESS) {
280 return ret;
281 }
282 }
283
284 for (int32_t type = CRYPT_PUBKEY_SUBKEY; type <= CRYPT_PUBKEY_SUBKEY_WITHOUT_SEQ; type++) {
285 ret = CRYPT_EAL_PubKeyParseBuff(format, type, encode, ealPKey);
286 if (ret == CRYPT_SUCCESS) {
287 return ret;
288 }
289 }
290
291 return CRYPT_DECODE_NO_SUPPORT_TYPE;
292 }
293
CRYPT_EAL_DecodeBuffKey(int32_t format,int32_t type,BSL_Buffer * encode,const uint8_t * pwd,uint32_t pwdlen,CRYPT_EAL_PkeyCtx ** ealPKey)294 int32_t CRYPT_EAL_DecodeBuffKey(int32_t format, int32_t type, BSL_Buffer *encode,
295 const uint8_t *pwd, uint32_t pwdlen, CRYPT_EAL_PkeyCtx **ealPKey)
296 {
297 BSL_Buffer pwdBuffer = {(uint8_t *)(uintptr_t)pwd, pwdlen};
298 switch (type) {
299 case CRYPT_PRIKEY_PKCS8_UNENCRYPT:
300 case CRYPT_PRIKEY_PKCS8_ENCRYPT:
301 #ifdef HITLS_CRYPTO_ECDSA
302 case CRYPT_PRIKEY_ECC:
303 #endif
304 #ifdef HITLS_CRYPTO_RSA
305 case CRYPT_PRIKEY_RSA:
306 #endif
307 return CRYPT_EAL_PriKeyParseBuff(format, type, encode, &pwdBuffer, ealPKey);
308 case CRYPT_PUBKEY_SUBKEY_WITHOUT_SEQ:
309 case CRYPT_PUBKEY_SUBKEY:
310 #ifdef HITLS_CRYPTO_RSA
311 case CRYPT_PUBKEY_RSA:
312 #endif
313 return CRYPT_EAL_PubKeyParseBuff(format, type, encode, ealPKey);
314 case CRYPT_ENCDEC_UNKNOW:
315 return CRYPT_EAL_UnKnownKeyParseBuff(format, &pwdBuffer, encode, ealPKey);
316 default:
317 BSL_ERR_PUSH_ERROR(CRYPT_DECODE_NO_SUPPORT_TYPE);
318 return CRYPT_DECODE_NO_SUPPORT_TYPE;
319 }
320 }
321
322 #ifdef HITLS_BSL_SAL_FILE
CRYPT_EAL_PriKeyParseFile(BSL_ParseFormat format,int32_t type,const char * path,const BSL_Buffer * pwd,CRYPT_EAL_PkeyCtx ** ealPriKey)323 int32_t CRYPT_EAL_PriKeyParseFile(BSL_ParseFormat format, int32_t type, const char *path, const BSL_Buffer *pwd,
324 CRYPT_EAL_PkeyCtx **ealPriKey)
325 {
326 uint8_t *data = NULL;
327 uint32_t dataLen = 0;
328 int32_t ret = BSL_SAL_ReadFile(path, &data, &dataLen);
329 if (ret != BSL_SUCCESS) {
330 BSL_ERR_PUSH_ERROR(ret);
331 return ret;
332 }
333 BSL_Buffer encode = {data, dataLen};
334 ret = CRYPT_EAL_PriKeyParseBuff(format, type, &encode, pwd, ealPriKey);
335 BSL_SAL_Free(data);
336 return ret;
337 }
338
CRYPT_EAL_PubKeyParseFile(BSL_ParseFormat format,int32_t type,const char * path,CRYPT_EAL_PkeyCtx ** ealPubKey)339 int32_t CRYPT_EAL_PubKeyParseFile(BSL_ParseFormat format, int32_t type, const char *path, CRYPT_EAL_PkeyCtx **ealPubKey)
340 {
341 uint8_t *data = NULL;
342 uint32_t dataLen = 0;
343 int32_t ret = BSL_SAL_ReadFile(path, &data, &dataLen);
344 if (ret != BSL_SUCCESS) {
345 BSL_ERR_PUSH_ERROR(ret);
346 return ret;
347 }
348 BSL_Buffer encode = {data, dataLen};
349 ret = CRYPT_EAL_PubKeyParseBuff(format, type, &encode, ealPubKey);
350 BSL_SAL_Free(data);
351 return ret;
352 }
353
CRYPT_EAL_UnKnownKeyParseFile(BSL_ParseFormat format,const char * path,const BSL_Buffer * pwd,CRYPT_EAL_PkeyCtx ** ealKey)354 int32_t CRYPT_EAL_UnKnownKeyParseFile(BSL_ParseFormat format, const char *path, const BSL_Buffer *pwd,
355 CRYPT_EAL_PkeyCtx **ealKey)
356 {
357 uint8_t *data = NULL;
358 uint32_t dataLen = 0;
359 int32_t ret = BSL_SAL_ReadFile(path, &data, &dataLen);
360 if (ret != BSL_SUCCESS) {
361 BSL_ERR_PUSH_ERROR(ret);
362 return ret;
363 }
364 BSL_Buffer encode = {data, dataLen};
365 ret = CRYPT_EAL_UnKnownKeyParseBuff(format, pwd, &encode, ealKey);
366 BSL_SAL_Free(data);
367 return ret;
368 }
369
CRYPT_EAL_DecodeFileKey(int32_t format,int32_t type,const char * path,uint8_t * pwd,uint32_t pwdlen,CRYPT_EAL_PkeyCtx ** ealPKey)370 int32_t CRYPT_EAL_DecodeFileKey(int32_t format, int32_t type, const char *path,
371 uint8_t *pwd, uint32_t pwdlen, CRYPT_EAL_PkeyCtx **ealPKey)
372 {
373 BSL_Buffer pwdBuffer = {(uint8_t *)pwd, pwdlen};
374 if (path == NULL || strlen(path) > PATH_MAX_LEN) {
375 BSL_ERR_PUSH_ERROR(CRYPT_INVALID_ARG);
376 return CRYPT_INVALID_ARG;
377 }
378 switch (type) {
379 case CRYPT_PRIKEY_PKCS8_UNENCRYPT:
380 case CRYPT_PRIKEY_PKCS8_ENCRYPT:
381 #ifdef HITLS_CRYPTO_RSA
382 case CRYPT_PRIKEY_RSA:
383 #endif
384 #ifdef HITLS_CRYPTO_ECDSA
385 case CRYPT_PRIKEY_ECC:
386 #endif
387 return CRYPT_EAL_PriKeyParseFile(format, type, path, &pwdBuffer, ealPKey);
388 case CRYPT_PUBKEY_SUBKEY_WITHOUT_SEQ:
389 case CRYPT_PUBKEY_SUBKEY:
390 #ifdef HITLS_CRYPTO_RSA
391 case CRYPT_PUBKEY_RSA:
392 return CRYPT_EAL_PubKeyParseFile(format, type, path, ealPKey);
393 #endif
394 case CRYPT_ENCDEC_UNKNOW:
395 return CRYPT_EAL_UnKnownKeyParseFile(format, path, &pwdBuffer, ealPKey);
396 default:
397 BSL_ERR_PUSH_ERROR(CRYPT_DECODE_NO_SUPPORT_TYPE);
398 return CRYPT_DECODE_NO_SUPPORT_TYPE;
399 }
400 }
401 #endif // HITLS_BSL_SAL_FILE
402
403 #endif // HITLS_CRYPTO_KEY_DECODE
404
CRYPT_EAL_GetEncodeType(const char * type)405 int32_t CRYPT_EAL_GetEncodeType(const char *type)
406 {
407 if (type == NULL) {
408 return CRYPT_ENCDEC_UNKNOW;
409 }
410 static const struct {
411 const char *typeStr;
412 int32_t typeInt;
413 } TYPE_MAP[] = {
414 {"PRIKEY_PKCS8_UNENCRYPT", CRYPT_PRIKEY_PKCS8_UNENCRYPT},
415 {"PRIKEY_PKCS8_ENCRYPT", CRYPT_PRIKEY_PKCS8_ENCRYPT},
416 {"PRIKEY_RSA", CRYPT_PRIKEY_RSA},
417 {"PRIKEY_ECC", CRYPT_PRIKEY_ECC},
418 {"PUBKEY_SUBKEY", CRYPT_PUBKEY_SUBKEY},
419 {"PUBKEY_RSA", CRYPT_PUBKEY_RSA},
420 {"PUBKEY_SUBKEY_WITHOUT_SEQ", CRYPT_PUBKEY_SUBKEY_WITHOUT_SEQ}
421 };
422
423 for (size_t i = 0; i < sizeof(TYPE_MAP) / sizeof(TYPE_MAP[0]); i++) {
424 if (strcmp(type, TYPE_MAP[i].typeStr) == 0) {
425 return TYPE_MAP[i].typeInt;
426 }
427 }
428
429 return CRYPT_ENCDEC_UNKNOW;
430 }
431
432 #ifdef HITLS_CRYPTO_KEY_ENCODE
433
CRYPT_EAL_EncodeAsn1PriKey(CRYPT_EAL_LibCtx * libCtx,const char * attrName,CRYPT_EAL_PkeyCtx * ealPriKey,const CRYPT_EncodeParam * encodeParam,int32_t type,BSL_Buffer * encode)434 int32_t CRYPT_EAL_EncodeAsn1PriKey(CRYPT_EAL_LibCtx *libCtx, const char *attrName, CRYPT_EAL_PkeyCtx *ealPriKey,
435 const CRYPT_EncodeParam *encodeParam, int32_t type, BSL_Buffer *encode)
436 {
437 #ifndef HITLS_CRYPTO_KEY_EPKI
438 (void)libCtx;
439 (void)attrName;
440 (void)encodeParam;
441 #endif
442 switch (type) {
443 #ifdef HITLS_CRYPTO_ECDSA
444 case CRYPT_PRIKEY_ECC:
445 return EncodeEccPrikeyAsn1Buff(ealPriKey, NULL, encode);
446 #endif
447 #ifdef HITLS_CRYPTO_RSA
448 case CRYPT_PRIKEY_RSA:
449 return EncodeRsaPrikeyAsn1Buff(ealPriKey, CRYPT_PKEY_RSA, encode);
450 #endif
451 case CRYPT_PRIKEY_PKCS8_UNENCRYPT:
452 return EncodePk8PriKeyBuff(ealPriKey, encode);
453 #ifdef HITLS_CRYPTO_KEY_EPKI
454 case CRYPT_PRIKEY_PKCS8_ENCRYPT:
455 return EncodePk8EncPriKeyBuff(libCtx, attrName, ealPriKey, encodeParam, encode);
456 #endif
457 default:
458 BSL_ERR_PUSH_ERROR(CRYPT_ENCODE_NO_SUPPORT_FORMAT);
459 return CRYPT_ENCODE_NO_SUPPORT_FORMAT;
460 }
461 }
462
463 #ifdef HITLS_BSL_PEM
CRYPT_EAL_EncodePemPriKey(CRYPT_EAL_LibCtx * libCtx,const char * attrName,CRYPT_EAL_PkeyCtx * ealPriKey,const CRYPT_EncodeParam * encodeParam,int32_t type,BSL_Buffer * encode)464 int32_t CRYPT_EAL_EncodePemPriKey(CRYPT_EAL_LibCtx *libCtx, const char *attrName, CRYPT_EAL_PkeyCtx *ealPriKey,
465 const CRYPT_EncodeParam *encodeParam, int32_t type, BSL_Buffer *encode)
466 {
467 BSL_Buffer asn1 = {0};
468 int32_t ret = CRYPT_EAL_EncodeAsn1PriKey(libCtx, attrName, ealPriKey, encodeParam, type, &asn1);
469 if (ret != CRYPT_SUCCESS) {
470 BSL_ERR_PUSH_ERROR(ret);
471 return ret;
472 }
473 BSL_PEM_Symbol symbol = {0};
474 ret = EAL_GetPemPriKeySymbol(type, &symbol);
475 if (ret != CRYPT_SUCCESS) {
476 BSL_SAL_Free(asn1.data);
477 return ret;
478 }
479 ret = BSL_PEM_EncodeAsn1ToPem(asn1.data, asn1.dataLen, &symbol, (char **)&encode->data, &encode->dataLen);
480 BSL_SAL_Free(asn1.data);
481 if (ret != BSL_SUCCESS) {
482 BSL_ERR_PUSH_ERROR(ret);
483 }
484 return ret;
485 }
486 #endif // HITLS_BSL_PEM
487
CRYPT_EAL_PriKeyEncodeBuff(CRYPT_EAL_LibCtx * libCtx,const char * attrName,CRYPT_EAL_PkeyCtx * ealPriKey,const CRYPT_EncodeParam * encodeParam,BSL_ParseFormat format,int32_t type,BSL_Buffer * encode)488 int32_t CRYPT_EAL_PriKeyEncodeBuff(CRYPT_EAL_LibCtx *libCtx, const char *attrName, CRYPT_EAL_PkeyCtx *ealPriKey,
489 const CRYPT_EncodeParam *encodeParam, BSL_ParseFormat format, int32_t type, BSL_Buffer *encode)
490 {
491 if (ealPriKey == NULL || encode == NULL) {
492 BSL_ERR_PUSH_ERROR(CRYPT_INVALID_ARG);
493 return CRYPT_INVALID_ARG;
494 }
495
496 switch (format) {
497 case BSL_FORMAT_ASN1:
498 return CRYPT_EAL_EncodeAsn1PriKey(libCtx, attrName, ealPriKey, encodeParam, type, encode);
499 #ifdef HITLS_BSL_PEM
500 case BSL_FORMAT_PEM:
501 return CRYPT_EAL_EncodePemPriKey(libCtx, attrName, ealPriKey, encodeParam, type, encode);
502 #endif // HITLS_BSL_PEM
503 default:
504 BSL_ERR_PUSH_ERROR(CRYPT_ENCODE_NO_SUPPORT_FORMAT);
505 return CRYPT_ENCODE_NO_SUPPORT_FORMAT;
506 }
507 }
508
CRYPT_EAL_PubKeyEncodeBuff(CRYPT_EAL_PkeyCtx * ealPubKey,BSL_ParseFormat format,int32_t type,BSL_Buffer * encode)509 int32_t CRYPT_EAL_PubKeyEncodeBuff(CRYPT_EAL_PkeyCtx *ealPubKey,
510 BSL_ParseFormat format, int32_t type, BSL_Buffer *encode)
511 {
512 return CRYPT_EAL_EncodePubKeyBuffInternal(ealPubKey, format, type, true, encode);
513 }
514
ProviderEncodeBuffKeyInternal(CRYPT_EAL_LibCtx * libCtx,const char * attrName,CRYPT_EAL_PkeyCtx * ealPKey,const CRYPT_EncodeParam * encodeParam,int32_t format,int32_t type,BSL_Buffer * encode)515 static int32_t ProviderEncodeBuffKeyInternal(CRYPT_EAL_LibCtx *libCtx, const char *attrName, CRYPT_EAL_PkeyCtx *ealPKey,
516 const CRYPT_EncodeParam *encodeParam, int32_t format, int32_t type, BSL_Buffer *encode)
517 {
518 switch (type) {
519 case CRYPT_PRIKEY_PKCS8_UNENCRYPT:
520 case CRYPT_PRIKEY_PKCS8_ENCRYPT:
521 #ifdef HITLS_CRYPTO_RSA
522 case CRYPT_PRIKEY_RSA:
523 #endif
524 #ifdef HITLS_CRYPTO_ECDSA
525 case CRYPT_PRIKEY_ECC:
526 #endif
527 return CRYPT_EAL_PriKeyEncodeBuff(libCtx, attrName, ealPKey, encodeParam, format, type, encode);
528 case CRYPT_PUBKEY_SUBKEY:
529 #ifdef HITLS_CRYPTO_RSA
530 case CRYPT_PUBKEY_RSA:
531 #endif
532 return CRYPT_EAL_PubKeyEncodeBuff(ealPKey, format, type, encode);
533 default:
534 BSL_ERR_PUSH_ERROR(CRYPT_ENCODE_NO_SUPPORT_TYPE);
535 return CRYPT_ENCODE_NO_SUPPORT_TYPE;
536 }
537 }
538
CRYPT_EAL_ProviderEncodeBuffKey(CRYPT_EAL_LibCtx * libCtx,const char * attrName,CRYPT_EAL_PkeyCtx * ealPKey,const CRYPT_EncodeParam * encodeParam,const char * format,const char * type,BSL_Buffer * encode)539 int32_t CRYPT_EAL_ProviderEncodeBuffKey(CRYPT_EAL_LibCtx *libCtx, const char *attrName, CRYPT_EAL_PkeyCtx *ealPKey,
540 const CRYPT_EncodeParam *encodeParam, const char *format, const char *type, BSL_Buffer *encode)
541 {
542 int32_t encodeType = CRYPT_EAL_GetEncodeType(type);
543 int32_t encodeFormat = CRYPT_EAL_GetEncodeFormat(format);
544 return ProviderEncodeBuffKeyInternal(libCtx, attrName, ealPKey, encodeParam, encodeFormat, encodeType, encode);
545 }
546
CRYPT_EAL_EncodeBuffKey(CRYPT_EAL_PkeyCtx * ealPKey,const CRYPT_EncodeParam * encodeParam,int32_t format,int32_t type,BSL_Buffer * encode)547 int32_t CRYPT_EAL_EncodeBuffKey(CRYPT_EAL_PkeyCtx *ealPKey, const CRYPT_EncodeParam *encodeParam,
548 int32_t format, int32_t type, BSL_Buffer *encode)
549 {
550 return ProviderEncodeBuffKeyInternal(NULL, NULL, ealPKey, encodeParam, format, type, encode);
551 }
552
CRYPT_EAL_EncodeAsn1PubKey(CRYPT_EAL_PkeyCtx * ealPubKey,int32_t type,bool isComplete,BSL_Buffer * encode)553 static int32_t CRYPT_EAL_EncodeAsn1PubKey(CRYPT_EAL_PkeyCtx *ealPubKey,
554 int32_t type, bool isComplete, BSL_Buffer *encode)
555 {
556 switch (type) {
557 case CRYPT_PUBKEY_SUBKEY:
558 return CRYPT_EAL_EncodeAsn1SubPubkey(ealPubKey, isComplete, encode);
559 #ifdef HITLS_CRYPTO_RSA
560 case CRYPT_PUBKEY_RSA:
561 return EncodeRsaPubkeyAsn1Buff(ealPubKey, NULL, encode);
562 #endif
563 default:
564 BSL_ERR_PUSH_ERROR(CRYPT_ENCODE_NO_SUPPORT_TYPE);
565 return CRYPT_ENCODE_NO_SUPPORT_TYPE;
566 }
567 }
568
569 #ifdef HITLS_BSL_PEM
CRYPT_EAL_EncodePemPubKey(CRYPT_EAL_PkeyCtx * ealPubKey,int32_t type,bool isComplete,BSL_Buffer * encode)570 static int32_t CRYPT_EAL_EncodePemPubKey(CRYPT_EAL_PkeyCtx *ealPubKey,
571 int32_t type, bool isComplete, BSL_Buffer *encode)
572 {
573 BSL_Buffer asn1 = {0};
574 int32_t ret = CRYPT_EAL_EncodeAsn1PubKey(ealPubKey, type, isComplete, &asn1);
575 if (ret != CRYPT_SUCCESS) {
576 BSL_ERR_PUSH_ERROR(ret);
577 return ret;
578 }
579 BSL_PEM_Symbol symbol = {0};
580 ret = EAL_GetPemPubKeySymbol(type, &symbol);
581 if (ret != CRYPT_SUCCESS) {
582 BSL_SAL_Free(asn1.data);
583 return ret;
584 }
585 ret = BSL_PEM_EncodeAsn1ToPem(asn1.data, asn1.dataLen, &symbol, (char **)&encode->data, &encode->dataLen);
586 BSL_SAL_Free(asn1.data);
587 if (ret != BSL_SUCCESS) {
588 BSL_ERR_PUSH_ERROR(ret);
589 }
590 return ret;
591 }
592 #endif // HITLS_BSL_PEM
593
CRYPT_EAL_EncodePubKeyBuffInternal(CRYPT_EAL_PkeyCtx * ealPubKey,BSL_ParseFormat format,int32_t type,bool isComplete,BSL_Buffer * encode)594 int32_t CRYPT_EAL_EncodePubKeyBuffInternal(CRYPT_EAL_PkeyCtx *ealPubKey,
595 BSL_ParseFormat format, int32_t type, bool isComplete, BSL_Buffer *encode)
596 {
597 if (ealPubKey == NULL || encode == NULL) {
598 BSL_ERR_PUSH_ERROR(CRYPT_INVALID_ARG);
599 return CRYPT_INVALID_ARG;
600 }
601
602 switch (format) {
603 case BSL_FORMAT_ASN1:
604 return CRYPT_EAL_EncodeAsn1PubKey(ealPubKey, type, isComplete, encode);
605 #ifdef HITLS_BSL_PEM
606 case BSL_FORMAT_PEM:
607 return CRYPT_EAL_EncodePemPubKey(ealPubKey, type, isComplete, encode);
608 #endif // HITLS_BSL_PEM
609 default:
610 BSL_ERR_PUSH_ERROR(CRYPT_ENCODE_NO_SUPPORT_FORMAT);
611 return CRYPT_ENCODE_NO_SUPPORT_FORMAT;
612 }
613 }
614
615 #ifdef HITLS_BSL_SAL_FILE
CRYPT_EAL_PriKeyEncodeFile(CRYPT_EAL_LibCtx * libCtx,const char * attrName,CRYPT_EAL_PkeyCtx * ealPriKey,const CRYPT_EncodeParam * encodeParam,BSL_ParseFormat format,int32_t type,const char * path)616 int32_t CRYPT_EAL_PriKeyEncodeFile(CRYPT_EAL_LibCtx *libCtx, const char *attrName, CRYPT_EAL_PkeyCtx *ealPriKey,
617 const CRYPT_EncodeParam *encodeParam, BSL_ParseFormat format, int32_t type, const char *path)
618 {
619 BSL_Buffer encode = {0};
620 int32_t ret = CRYPT_EAL_PriKeyEncodeBuff(libCtx, attrName, ealPriKey, encodeParam, format, type, &encode);
621 if (ret != BSL_SUCCESS) {
622 BSL_ERR_PUSH_ERROR(ret);
623 return ret;
624 }
625 ret = BSL_SAL_WriteFile(path, encode.data, encode.dataLen);
626 if (ret != BSL_SUCCESS) {
627 BSL_ERR_PUSH_ERROR(ret);
628 }
629 BSL_SAL_Free(encode.data);
630 return ret;
631 }
632
CRYPT_EAL_PubKeyEncodeFile(CRYPT_EAL_PkeyCtx * ealPubKey,BSL_ParseFormat format,int32_t type,const char * path)633 int32_t CRYPT_EAL_PubKeyEncodeFile(CRYPT_EAL_PkeyCtx *ealPubKey, BSL_ParseFormat format, int32_t type, const char *path)
634 {
635 BSL_Buffer encode = {0};
636 int32_t ret = CRYPT_EAL_PubKeyEncodeBuff(ealPubKey, format, type, &encode);
637 if (ret != BSL_SUCCESS) {
638 BSL_ERR_PUSH_ERROR(ret);
639 return ret;
640 }
641 ret = BSL_SAL_WriteFile(path, encode.data, encode.dataLen);
642 if (ret != BSL_SUCCESS) {
643 BSL_ERR_PUSH_ERROR(ret);
644 }
645 BSL_SAL_FREE(encode.data);
646 return ret;
647 }
648
ProviderEncodeFileKeyInternal(CRYPT_EAL_LibCtx * libCtx,const char * attrName,CRYPT_EAL_PkeyCtx * ealPKey,const CRYPT_EncodeParam * encodeParam,int32_t format,int32_t type,const char * path)649 static int32_t ProviderEncodeFileKeyInternal(CRYPT_EAL_LibCtx *libCtx, const char *attrName, CRYPT_EAL_PkeyCtx *ealPKey,
650 const CRYPT_EncodeParam *encodeParam, int32_t format, int32_t type, const char *path)
651 {
652 if (path == NULL || strlen(path) > PATH_MAX_LEN) {
653 BSL_ERR_PUSH_ERROR(CRYPT_INVALID_ARG);
654 return CRYPT_INVALID_ARG;
655 }
656 switch (type) {
657 case CRYPT_PRIKEY_PKCS8_UNENCRYPT:
658 case CRYPT_PRIKEY_PKCS8_ENCRYPT:
659 #ifdef HITLS_CRYPTO_RSA
660 case CRYPT_PRIKEY_RSA:
661 #endif
662 #ifdef HITLS_CRYPTO_ECDSA
663 case CRYPT_PRIKEY_ECC:
664 #endif
665 return CRYPT_EAL_PriKeyEncodeFile(libCtx, attrName, ealPKey, encodeParam, format, type, path);
666 case CRYPT_PUBKEY_SUBKEY:
667 #ifdef HITLS_CRYPTO_RSA
668 case CRYPT_PUBKEY_RSA:
669 #endif
670 return CRYPT_EAL_PubKeyEncodeFile(ealPKey, format, type, path);
671 default:
672 BSL_ERR_PUSH_ERROR(CRYPT_ENCODE_NO_SUPPORT_TYPE);
673 return CRYPT_ENCODE_NO_SUPPORT_TYPE;
674 }
675 }
676
CRYPT_EAL_ProviderEncodeFileKey(CRYPT_EAL_LibCtx * libCtx,const char * attrName,CRYPT_EAL_PkeyCtx * ealPKey,const CRYPT_EncodeParam * encodeParam,const char * format,const char * type,const char * path)677 int32_t CRYPT_EAL_ProviderEncodeFileKey(CRYPT_EAL_LibCtx *libCtx, const char *attrName, CRYPT_EAL_PkeyCtx *ealPKey,
678 const CRYPT_EncodeParam *encodeParam, const char *format, const char *type, const char *path)
679 {
680 int32_t encodeType = CRYPT_EAL_GetEncodeType(type);
681 int32_t encodeFormat = CRYPT_EAL_GetEncodeFormat(format);
682 return ProviderEncodeFileKeyInternal(libCtx, attrName, ealPKey, encodeParam, encodeFormat, encodeType, path);
683 }
684
CRYPT_EAL_EncodeFileKey(CRYPT_EAL_PkeyCtx * ealPKey,const CRYPT_EncodeParam * encodeParam,int32_t format,int32_t type,const char * path)685 int32_t CRYPT_EAL_EncodeFileKey(CRYPT_EAL_PkeyCtx *ealPKey, const CRYPT_EncodeParam *encodeParam,
686 int32_t format, int32_t type, const char *path)
687 {
688 return ProviderEncodeFileKeyInternal(NULL, NULL, ealPKey, encodeParam, format, type, path);
689 }
690 #endif // HITLS_BSL_SAL_FILE
691
692 #endif // HITLS_CRYPTO_KEY_ENCODE
693
694 #endif // HITLS_CRYPTO_CODECSKEY
695