• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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