1 /*
2 * Copyright (c) 2001-2019, Arm Limited and Contributors. All rights reserved.
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6
7
8 #include <stdio.h>
9 #include <stdlib.h>
10 #include <string.h>
11 #include <stdint.h>
12
13
14 #include <openssl/err.h>
15 #include <openssl/pem.h>
16 #include <openssl/opensslv.h>
17 #include <openssl/conf.h>
18 #include <openssl/x509v3.h>
19
20 #include "common_crypto_x509.h"
21 #include "common_crypto_asym.h"
22 #include "common_rsa_keypair.h"
23 #include "common_util_files.h"
24 #include "common_util_log.h"
25 #include "cc_crypto_boot_defs.h"
26 #include "cc_crypto_x509_defs.h"
27
28 #ifdef CC_SB_SUPPORT_IOT
29 #include "secdebug_defs.h"
30 #endif
31
32 #define X509_VER_3 2 /* version 3 certificate */
33 #define ENDLESS_VALIDITY 0xFFFFFFFE
34 #define MAX_OBJ_ID_LEN 15
35 #define EXT_PREFIX_LEN 16
36 #ifdef CC_SB_SUPPORT_IOT
37 #define MAX_EXT_VAL_LIST (CC_SB_MAX_CONTENT_CERT_BODY_SIZE_IN_BYTES)
38 #else
39 #define MAX_EXT_VAL_LIST 80 // additional data
40 #endif
41 #define MAX_EXT_INT_VAL_LEN 80
42
43 /* multiple each byte by 3 for: each byte has 2 character representaion + ":" */
44 #define MAX_EXT_VAL_LEN (MAX_EXT_VAL_LIST *3 + EXT_PREFIX_LEN)
45 #define CHAR_STR_LEN 6
46
47 #define OPEN_SSL_ERROR 0
48 #define IS_VALID_ENC_FLAG(encFlag) ((0 == (encFlag)) || (1 == (encFlag)) || (0xFF == (encFlag)))
49 #define IS_VALID_HBK(hbkType) ((CC_SB_HASH_BOOT_KEY_0_128B == (hbkType)) ||\
50 (CC_SB_HASH_BOOT_KEY_1_128B == (hbkType)) ||\
51 (CC_SB_HASH_BOOT_KEY_256B == (hbkType)) ||\
52 (CC_SB_HASH_BOOT_NOT_USED == (hbkType)))
53
54 const uint8_t *certType2Str[CC_X509_CERT_TYPE_MAX] = {NULL,
55 /*CC_X509_CERT_TYPE_KEY */ (uint8_t *)CC_X509_CERT_KEY_CERT,
56 /*CC_X509_CERT_TYPE_CONTENT */ (uint8_t *)CC_X509_CERT_CNT_CERT,
57 /*CC_X509_CERT_TYPE_ENABLER_DBG */ (uint8_t *)CC_X509_CERT_ENABLER_CERT,
58 /*CC_X509_CERT_TYPE_DEVELOPER_DBG */ (uint8_t *)CC_X509_CERT_DEVELOPER_CERT
59 };
60
61
62 /**
63 * @brief free X509 certificate
64 *
65 * @param[in/out] ppCertBuff - x.509 certificate
66 */
67 /*********************************************************/
CC_CommonX509Free(uint8_t ** ppCertBuff)68 void CC_CommonX509Free(uint8_t **ppCertBuff)
69 {
70 /* validate inputs */
71 if ((NULL == ppCertBuff) ||
72 (NULL == *ppCertBuff)) {
73 UTIL_LOG_ERR("ilegal input\n");
74 return;
75 }
76
77 UTIL_LOG_INFO("about to X509_free\n");
78 /* create the certificate buffer */
79 X509_free((X509 *)*ppCertBuff);
80 *ppCertBuff = NULL;
81 return;
82 }
83
84
85 /**
86 * @brief Creates X509 certificate and set its header fields
87 *
88 * @param[in/out] ppCertBuff - x.509 certificate
89 * @param[in] certType - certificate type
90 */
91 /*********************************************************/
CC_CommonX509CreateAndSetHeader(uint8_t ** ppCertBuff,CCX509CertType_t certType,CCX509CertHeaderParamsIn_t * pCertHeaderParams)92 int32_t CC_CommonX509CreateAndSetHeader(uint8_t **ppCertBuff,
93 CCX509CertType_t certType,CCX509CertHeaderParamsIn_t *pCertHeaderParams)
94 {
95 int32_t rc = 0;
96 long endDate = 0;
97 uint32_t serialNum = 0;
98 long notBefore = 0; /*X509_CURRENT_TIME*/
99 long notAfter = ENDLESS_VALIDITY;
100 char* pIssuerName = CC_X509_CERT_ISSUER_NAME;
101 const char* pSubjectName = certType2Str[certType];
102 X509 *plCert = NULL;
103 ASN1_TIME *pDummy = NULL;
104
105 /* validate inputs */
106 if ((NULL == ppCertBuff) ||
107 (certType >= CC_X509_CERT_TYPE_MAX) ) {
108 UTIL_LOG_ERR("ilegal input\n");
109 return(-1);
110 }
111
112 /* create the certificate buffer */
113 plCert = (X509 *)X509_new();
114 if (OPEN_SSL_ERROR == plCert) {
115 UTIL_LOG_ERR("failed to X509_new\n");
116 return 1;
117 }
118
119 /* set certificate version to V3 */
120 rc = X509_set_version(plCert, X509_VER_3);
121 if (OPEN_SSL_ERROR == rc) {
122 UTIL_LOG_ERR("failed to X509_set_version\n");
123 rc = 1;
124 goto END;
125 }
126 /* set certificate serial number */
127 if ( (NULL != pCertHeaderParams) && (pCertHeaderParams->setSerialNum) ) {
128 serialNum = pCertHeaderParams->serialNum;
129 } else {
130 rc = CC_CommonRandBytes(4, (int8_t *)&serialNum);
131 if (rc != 0) {
132 UTIL_LOG_ERR("failed to set CC_CommonRandBytes\n");
133 rc = 1;
134 goto END;
135 }
136 }
137
138 rc = ASN1_INTEGER_set(X509_get_serialNumber(plCert), serialNum);
139 if (OPEN_SSL_ERROR == rc) {
140 UTIL_LOG_ERR("failed to set X509_get_serialNumber\n");
141 rc = 1;
142 goto END;
143 }
144 /* set ecrtificate start time to current time, and end date according to input */
145 if ( (NULL != pCertHeaderParams) && (pCertHeaderParams->setNotBefore) ) {
146 notBefore = pCertHeaderParams->notBefore;
147 }
148 pDummy = X509_gmtime_adj(X509_get_notBefore(plCert), (long)notBefore );
149 if (NULL == pDummy) {
150 UTIL_LOG_ERR("failed set X509_get_notBefore\n");
151 rc = 1;
152 goto END;
153 }
154 if ( (NULL != pCertHeaderParams) && (pCertHeaderParams->setNotAfter) ) {
155 notAfter = pCertHeaderParams->notAfter;
156 }
157 pDummy = X509_gmtime_adj(X509_get_notAfter(plCert),(long)notAfter);
158 if (NULL == pDummy) {
159 UTIL_LOG_ERR("failed set X509_get_notAfter\n");
160 rc = 1;
161 goto END;
162 }
163
164 /* set subject name */
165 if ( (NULL != pCertHeaderParams) && (pCertHeaderParams->setSubjectName) ) {
166 pSubjectName = pCertHeaderParams->SubjectName;
167 }
168 rc = X509_NAME_add_entry_by_txt(X509_get_subject_name(plCert),
169 "CN", /* common name */
170 MBSTRING_ASC,
171 pSubjectName,
172 -1,
173 -1, 0);
174 if (OPEN_SSL_ERROR == rc) {
175 UTIL_LOG_ERR("failed to set X509_get_subject_name\n");
176 rc = 1;
177 goto END;
178 }
179
180 /* set issuer name */
181 if ( (NULL != pCertHeaderParams) && (pCertHeaderParams->setIssuerName) ) {
182 pIssuerName = pCertHeaderParams->IssuerName;
183 }
184 rc = X509_NAME_add_entry_by_txt(X509_get_issuer_name(plCert),
185 "CN",
186 MBSTRING_ASC,
187 pIssuerName,
188 -1,
189 -1, 0);
190 if (OPEN_SSL_ERROR == rc) {
191 UTIL_LOG_ERR("failed to set X509_get_issuer_name\n");
192 rc = 1;
193 goto END;
194 }
195
196
197
198 *ppCertBuff = (uint8_t *)plCert;
199 rc = 0;
200 UTIL_LOG_INFO("OK\n");
201
202 END:
203 if (rc != 0) {
204 if (plCert != NULL) {
205 X509_free(plCert);
206 }
207 *ppCertBuff = NULL;
208 }
209 return rc;
210 }
211
212
213 /**
214 * @brief Add ASN.1 critical integer extension to X.509V3 certificate
215 *
216 * @param[in/out] pCertBuff - x.509 certificate
217 * @param[in] certType - certificate type
218 * @param[in] extType - extension type
219 * @param[in] val - Extension value
220 */
221 /*********************************************************/
CC_CommonX509AddIntegerExtension(uint8_t * pCertBuff,CCX509CertType_t certType,CCX509ExtType_t extType,int32_t val)222 int32_t CC_CommonX509AddIntegerExtension(uint8_t *pCertBuff,
223 CCX509CertType_t certType,
224 CCX509ExtType_t extType,
225 int32_t val)
226
227 {
228 int32_t rc = 0;
229 int32_t nid = 0;
230 X509 *plCert = (X509 *)pCertBuff;
231 X509_EXTENSION *ext = NULL;
232 uint8_t objId[MAX_OBJ_ID_LEN];
233 uint8_t extValue[MAX_EXT_INT_VAL_LEN];
234 int32_t writtenBytes = 0;
235
236 /* validate inputs */
237 if (NULL == pCertBuff) {
238 UTIL_LOG_ERR("Illegal parameters \n");
239 return (-1);
240 }
241
242 /* create new object */
243 snprintf(objId, MAX_OBJ_ID_LEN, "2.20.%d.%d",certType,extType);
244 nid = OBJ_create(objId, "MyAlias", "My Test Alias Extension");
245 if (OPEN_SSL_ERROR == nid) {
246 UTIL_LOG_ERR("failed to OBJ_create\n");
247 ERR_print_errors_fp(stderr);
248 rc = 1;
249 goto END;
250 }
251 rc = X509V3_EXT_add_alias(nid, NID_netscape_comment);
252 if (OPEN_SSL_ERROR == nid) {
253 UTIL_LOG_ERR("failed to X509V3_EXT_add_alias\n");
254 ERR_print_errors_fp(stderr);
255 rc = 1;
256 goto END;
257 }
258 /* create the extension value */
259 writtenBytes = snprintf(extValue, MAX_EXT_INT_VAL_LEN, "critical,ASN1:INTEGER:0x%X",val);
260 /* build the extension */
261 ext = X509V3_EXT_conf_nid(NULL, NULL, nid, extValue);
262 if (OPEN_SSL_ERROR == ext) {
263 UTIL_LOG_ERR("failed to X509V3_EXT_conf_nid\n");
264 ERR_print_errors_fp(stderr);
265 rc = 1;
266 goto END;
267 }
268
269 /* Add the extension to the certificate */
270 rc = X509_add_ext(plCert, ext, -1);
271 if (OPEN_SSL_ERROR == rc) {
272 UTIL_LOG_ERR("failed to X509_add_ext\n");
273 ERR_print_errors_fp(stderr);
274 rc = 1;
275 goto END;
276 }
277 rc = 0;
278 UTIL_LOG_INFO("OK\n");
279
280 END:
281 X509_EXTENSION_free(ext);
282 return rc;
283 }
284
285
286 /**
287 * @brief Add critical DER extension to X.509V3 certificate
288 *
289 * @param[in/out] pCertBuff - x.509 certificate
290 * @param[in] certType - certificate tyoes
291 * @param[in] extType - extension type
292 * @param[in] pVal - Extension data
293 * @param[in] valLen - extension data length
294 */
295 /*********************************************************/
CC_CommonX509AddStringExtension(uint8_t * pCertBuff,CCX509CertType_t certType,CCX509ExtType_t extType,uint8_t * pVal,uint32_t valLen)296 int32_t CC_CommonX509AddStringExtension(uint8_t *pCertBuff,
297 CCX509CertType_t certType,
298 CCX509ExtType_t extType,
299 uint8_t *pVal,
300 uint32_t valLen)
301
302 {
303 int32_t rc = 0;
304 int32_t nid;
305 X509 *plCert = (X509 *)pCertBuff;
306 X509_EXTENSION *ext = NULL;
307 uint8_t objId[MAX_OBJ_ID_LEN];
308 uint8_t extValue[MAX_EXT_VAL_LEN];
309 int32_t writtenBytes = 0;
310 int32_t pValIdx = 0;
311
312 /* validate inputs */
313 if ((NULL == pCertBuff) ||
314 (NULL == pVal)||
315 (valLen > MAX_EXT_VAL_LIST)) {
316 UTIL_LOG_ERR("Illegal parameters \n");
317 return (-1);
318 }
319 /* create new object */
320 snprintf(objId, MAX_OBJ_ID_LEN, "2.20.%d.%d",certType,extType);
321 nid = OBJ_create(objId, "MyAlias", "My Test Alias Extension");
322 if (OPEN_SSL_ERROR == nid) {
323 UTIL_LOG_ERR("failed to OBJ_create\n");
324 ERR_print_errors_fp(stderr);
325 rc = 1;
326 goto END;
327 }
328
329 pValIdx = 0;
330 writtenBytes = snprintf(extValue, MAX_EXT_VAL_LEN, "critical,DER: %02X",pVal[pValIdx++]);
331 UTIL_LOG_INFO("writtenBytes %d, extValue %s\n",writtenBytes, extValue);
332 while (pValIdx < valLen) {
333 writtenBytes += snprintf((extValue+writtenBytes), CHAR_STR_LEN, ":%02X", pVal[pValIdx++]);
334 UTIL_LOG_INFO("writtenBytes %d, extValue %s\n",writtenBytes, extValue);
335 }
336
337 rc = X509V3_EXT_add_alias(nid, NID_netscape_comment); // if NID is unknown openssl ignores it. meaning it is not added to cert.
338 if (OPEN_SSL_ERROR == rc) {
339 UTIL_LOG_ERR("failed to X509V3_EXT_add_alias\n");
340 ERR_print_errors_fp(stderr);
341 rc = 1;
342 goto END;
343 }
344
345 ext = X509V3_EXT_conf_nid(NULL, NULL, nid, extValue);
346 if (OPEN_SSL_ERROR == ext) {
347 UTIL_LOG_ERR("failed to X509V3_EXT_conf_nid\n");
348 ERR_print_errors_fp(stderr);
349 rc = 1;
350 goto END;
351 }
352
353 /* Add the extension to the certificate */
354 rc = X509_add_ext(plCert, ext, -1);
355 if (OPEN_SSL_ERROR == rc) {
356 UTIL_LOG_ERR("failed to X509_add_ext\n");
357 ERR_print_errors_fp(stderr);
358 rc = 1;
359 goto END;
360 }
361 rc = 0;
362 UTIL_LOG_INFO("OK\n");
363
364 END:
365 if (ext != NULL) {
366 X509_EXTENSION_free(ext);
367 }
368 return rc;
369 }
370
371
372 /**
373 * @brief Add subject public key to the X509 certificate
374 * and sign the certificate
375 *
376 * @param[in/out] pCertBuff - x.509 certificate
377 * @param[in] pKeyPairFileName - key pair file name in PEM format
378 * @param[in] pKeyPairPwd - passphrase of key pair
379 */
380 /*********************************************************/
CC_CommonX509SetKeyAndSign(uint8_t * pCertBuff,uint8_t * pKeyPairFileName,uint8_t * pKeyPairPwd)381 int32_t CC_CommonX509SetKeyAndSign(uint8_t *pCertBuff,
382 uint8_t *pKeyPairFileName,
383 uint8_t *pKeyPairPwd)
384 {
385 int32_t rc = 0;
386 X509 *plCert = (X509 *)pCertBuff;
387 RSA *pRsaKeyPair = NULL;
388 uint8_t *pwd = NULL;
389 EVP_PKEY *pKey = NULL;
390 EVP_MD_CTX mdCtx;
391 EVP_PKEY_CTX *pKeyCtx = NULL;
392
393 /* validate inputs */
394 if ((NULL == pCertBuff) ||
395 (NULL == pKeyPairFileName)) {
396 UTIL_LOG_ERR("ilegal input\n");
397 return(-1);
398 }
399
400 /* get certificate Subject's RSA public and private key from key pair file */
401 /* parse the passphrase for a given file */
402 if (pKeyPairPwd != NULL) {
403 rc = CC_CommonGetPassphrase(pKeyPairPwd, &pwd);
404 if (rc != CC_COMMON_OK) {
405 UTIL_LOG_ERR("Failed to retrieve pwd\n");
406 goto END;
407 }
408 }
409 pRsaKeyPair = RSA_new();
410 if (NULL == pRsaKeyPair) {
411 UTIL_LOG_ERR("Failed RSA_new\n");
412 goto END;
413 }
414 rc = CC_CommonGetKeyPair(&pRsaKeyPair, pKeyPairFileName, pwd);
415 if (rc != CC_COMMON_OK) {
416 UTIL_LOG_ERR("CC_CommonGetKeyPair Cannot read RSA private key\n");
417 rc = 1;
418 goto END;
419 }
420 /* allocate an empty EVP_PKEY structure which
421 is used by OpenSSL to store private keys.*/
422 pKey = EVP_PKEY_new();
423 if (NULL == pKey) {
424 UTIL_LOG_ERR("failed to EVP_PKEY_new\n");
425 rc = 1;
426 goto END;
427 }
428 /*set the referenced key to RSA key*/
429 rc = EVP_PKEY_assign_RSA(pKey, pRsaKeyPair);
430 if (OPEN_SSL_ERROR == rc) {
431 UTIL_LOG_ERR("failed to EVP_PKEY_assign_RSA\n");
432 rc = 1;
433 goto END;
434 }
435
436
437 EVP_MD_CTX_init(&mdCtx);
438 rc = EVP_DigestSignInit(&mdCtx, &pKeyCtx, EVP_sha256(), NULL, pKey);
439 if (OPEN_SSL_ERROR == rc) {
440 UTIL_LOG_ERR("failed to EVP_DigestSignInit\n");
441 rc = 1;
442 goto END;
443 }
444 rc = EVP_PKEY_CTX_set_rsa_padding(pKeyCtx, RSA_PKCS1_PSS_PADDING);
445 if (rc <= OPEN_SSL_ERROR) {
446 UTIL_LOG_ERR("failed to EVP_PKEY_CTX_set_rsa_padding\n");
447 rc = 1;
448 goto END;
449 }
450 rc = EVP_PKEY_CTX_set_rsa_pss_saltlen(pKeyCtx, RSA_SALT_LEN);
451 if (rc <= OPEN_SSL_ERROR) {
452 UTIL_LOG_ERR("failed to EVP_PKEY_CTX_set_rsa_pss_saltlen\n");
453 rc = 1;
454 goto END;
455 }
456 rc = EVP_PKEY_CTX_set_rsa_mgf1_md(pKeyCtx, EVP_sha256());
457 if (rc <= OPEN_SSL_ERROR) {
458 UTIL_LOG_ERR("failed to EVP_PKEY_CTX_set_rsa_mgf1_md\n");
459 rc = 1;
460 goto END;
461 }
462 UTIL_LOG_INFO("about to X509_set_pubkey\n");
463 /*set the key into certificate*/
464 rc = X509_set_pubkey(plCert,pKey);
465 if (OPEN_SSL_ERROR == rc) {
466 UTIL_LOG_ERR("failed to X509_set_pubkey\n");
467 ERR_print_errors_fp(stderr);
468 rc = 1;
469 goto END;
470 }
471
472 UTIL_LOG_INFO("about to X509_sign_ctx\n");
473 rc = X509_sign_ctx(plCert, &mdCtx);
474 if (OPEN_SSL_ERROR == rc) {
475 UTIL_LOG_ERR("failed to X509_sign\n");
476 rc = 1;
477 goto END;
478 }
479 rc = 0;
480 UTIL_LOG_INFO("OK\n");
481
482 END:
483 EVP_MD_CTX_cleanup(&mdCtx);
484 if (pRsaKeyPair != NULL) {
485 RSA_free(pRsaKeyPair); // free pKey as well
486 }
487 if (pwd != NULL) {
488 free(pwd);
489 }
490 return rc;
491 }
492
493
494 /**
495 * @brief convert the x.509 certificate to DER format
496 *
497 * @param[in/out] ppCertBuff - x.509 certificate
498 * @param[out] pOutCertSize - certificate size in DER format
499 */
500 /*********************************************************/
CC_CommonX509ToDer(uint8_t ** ppCertBuff,uint32_t * pOutCertSize)501 int32_t CC_CommonX509ToDer(uint8_t **ppCertBuff,
502 uint32_t *pOutCertSize)
503 {
504 unsigned char *outBuff = NULL;
505 uint8_t *pPemCertData = NULL;
506
507 /* validate inputs */
508 if ((NULL == ppCertBuff) ||
509 (NULL == pOutCertSize)) {
510 UTIL_LOG_ERR("ilegal input\n");
511 return(-1);
512 }
513
514
515 *pOutCertSize = i2d_X509((X509 *)*ppCertBuff, &outBuff);
516 CC_CommonX509Free(ppCertBuff);
517 *ppCertBuff = outBuff;
518
519 UTIL_LOG_INFO("OK\n");
520
521 return 0;
522 }
523
524
525 #ifdef CC_SB_SUPPORT_IOT
526
527 /**
528 * @brief build package for the certificate
529 *
530 * @param[in] ppCertBuff - the x509 certificate in PEM format
531 * @param[in] certSize - certificate size
532 * @param[in] certType - certificate type
533 * @param[in] encFlag - indicates whether images were encrypted
534 * @param[in] hbkType - hbk type to use by target, in the verification
535 * @param[in] pAddData - additional data to add to package
536 * @param[in] addDataSize - length of additional data
537 * @param[in] outPkgFile - package file name to write the package to
538 */
539 /*********************************************************/
CC_CommonX509BuildCertPkg(uint8_t ** ppCertBuff,uint32_t certSize,uint8_t * pAddData,uint32_t addDataSize,uint8_t * outPkgFile)540 int32_t CC_CommonX509BuildCertPkg(uint8_t **ppCertBuff,
541 uint32_t certSize,
542 uint8_t *pAddData,
543 uint32_t addDataSize,
544 uint8_t *outPkgFile)
545 {
546 int32_t rc = 0;
547 FILE *fp = NULL;
548 uint8_t *pCertPkg = NULL;
549 uint32_t pkgBytesSize = 0;
550
551 UTIL_LOG_INFO("started\n");
552 /* check inputs */
553 if ((NULL == outPkgFile) ||
554 (NULL == ppCertBuff) || (NULL == *ppCertBuff) ||
555 (0 == certSize) ||
556 (certSize >= CC_X509_MAX_CERT_SIZE) ||
557 ((pAddData != NULL) && (0 == addDataSize)) ||
558 ((NULL == pAddData) && (addDataSize != 0))) {
559 UTIL_LOG_ERR("illegal input\n");
560 rc = (-1);
561 goto END;
562 }
563
564 /* calcultae package size */
565 pkgBytesSize = (certSize + addDataSize + 1); /* Adding 1 for "\0"*/
566
567 UTIL_LOG_INFO("openning certificate pkg file for writing\n");
568 fp = fopen(outPkgFile, "w");
569 if (NULL == fp) {
570 UTIL_LOG_ERR("failed to open %s\n", outPkgFile);
571 rc = (-1);
572 goto END;
573 }
574
575 UTIL_LOG_INFO("about to allocate memory for pkg:size %d, certSize %d, addDataSize %d\n",pkgBytesSize, certSize, addDataSize);
576
577 /* create the package buffer */
578 pCertPkg = (uint8_t *) malloc(pkgBytesSize);
579 if (pCertPkg == NULL){
580 UTIL_LOG_ERR("failed to allocate pkg\n");
581 rc = (-1);
582 goto END;
583 }
584 /* copy additional data to package */
585 if (pAddData != NULL) {
586 memcpy(&pCertPkg[0], pAddData, addDataSize);
587 }
588 /* copy certificate PEM to package */
589 memcpy(&pCertPkg[addDataSize], *ppCertBuff, certSize);
590
591
592 /* write out the package in binary format */
593 UTIL_LOG_INFO("writing pkg to file\n");
594 rc = CC_CommonUtilCopyBuffToBinFile(outPkgFile, pCertPkg, pkgBytesSize);
595 if (rc != 0) {
596 UTIL_LOG_ERR("failed to CC_CommonUtilCopyBuffToBinFile\n");
597 rc = 1;
598 goto END;
599 }
600 rc = 0;
601 UTIL_LOG_INFO("OK\n");
602
603 END:
604 if (fp != NULL){
605 fclose(fp);
606 }
607 if (pCertPkg != NULL) {
608 free(pCertPkg);
609 }
610 return rc;
611 }
612
613 #else
614 /**
615 * @brief build package for the certificate
616 *
617 * @param[in] ppCertBuff - the x509 certificate in PEM format
618 * @param[in] certSize - certificate size
619 * @param[in] certType - certificate type
620 * @param[in] encFlag - indicates whether images were encrypted
621 * @param[in] hbkType - hbk type to use by target, in the verification
622 * @param[in] pAddData - additional data to add to package
623 * @param[in] addDataSize - length of additional data
624 * @param[in] outPkgFile - package file name to write the package to
625 */
626 /*********************************************************/
CC_CommonX509BuildCertPkg(uint8_t ** ppCertBuff,uint32_t certSize,CCX509CertType_t certType,uint8_t encFlag,uint8_t hbkType,uint8_t * pAddData,uint32_t addDataSize,uint8_t * outPkgFile)627 int32_t CC_CommonX509BuildCertPkg(uint8_t **ppCertBuff,
628 uint32_t certSize,
629 CCX509CertType_t certType,
630 uint8_t encFlag,
631 uint8_t hbkType,
632 uint8_t *pAddData,
633 uint32_t addDataSize,
634 uint8_t *outPkgFile)
635 {
636 int32_t rc = 0;
637 FILE *fp = NULL;
638 uint8_t *pCertPkg = NULL;
639 uint32_t nextBlockOffset = 0;
640 uint32_t pkgBytesSize = 0;
641
642 UTIL_LOG_INFO("started\n");
643 /* check inputs */
644 if ((NULL == outPkgFile) ||
645 (NULL == ppCertBuff) || (NULL == *ppCertBuff) ||
646 (0 == certSize) ||
647 (certSize >= CC_X509_MAX_CERT_SIZE) ||
648 ((certType <= CC_X509_CERT_TYPE_MIN) || (certType >= CC_X509_CERT_TYPE_MAX)) ||
649 ((pAddData != NULL) && (0 == addDataSize)) ||
650 ((NULL == pAddData) && (addDataSize != 0)) ||
651 (!IS_VALID_ENC_FLAG(encFlag & 0xFF)) ||
652 (!IS_VALID_HBK(hbkType & 0xFF))) {
653 UTIL_LOG_ERR("illegal input\n");
654 rc = (-1);
655 goto END;
656 }
657
658 /* calcultae package size */
659 pkgBytesSize = (sizeof(CCX509PkgHeader_t) + addDataSize);
660
661 UTIL_LOG_INFO("openning certificate pkg file for writing\n");
662 fp = fopen(outPkgFile, "w");
663 if (NULL == fp) {
664 UTIL_LOG_ERR("failed to open %s\n", outPkgFile);
665 rc = (-1);
666 goto END;
667 }
668
669 pkgBytesSize += certSize + 1; /* Adding 1 for "\0"*/
670 UTIL_LOG_INFO("about to allocate memory for pkg:size %d, certSize %d, addDataSize %d\n",pkgBytesSize, certSize, addDataSize);
671
672 /* create the package buffer */
673 pCertPkg = (uint8_t *) malloc(pkgBytesSize);
674 if (pCertPkg == NULL){
675 UTIL_LOG_ERR("failed to allocate pkg\n");
676 rc = (-1);
677 goto END;
678 }
679 nextBlockOffset = sizeof(CCX509PkgHeader_t);
680 /* copy additional data to package */
681 if (pAddData != NULL) {
682 memcpy(&pCertPkg[nextBlockOffset], pAddData, addDataSize);
683 nextBlockOffset += addDataSize;
684 }
685 /* copy certificate PEM to package */
686 memcpy(&pCertPkg[nextBlockOffset], *ppCertBuff, certSize);
687
688 /* setting pkg header */
689 UTIL_LOG_INFO("setting pkg header\n");
690 ((CCX509PkgHeader_t *)pCertPkg)->pkgToken = CC_X509_CERT_PKG_TOKEN;
691 ((CCX509PkgHeader_t *)pCertPkg)->pkgVer = CC_X509_CERT_PKG_VERSION;
692 ((CCX509PkgHeader_t *)pCertPkg)->pkgFlags.pkgFlagsWord = 0;
693 ((CCX509PkgHeader_t *)pCertPkg)->pkgFlags.pkgFlagsBits.certType = certType & 0xFF;
694 ((CCX509PkgHeader_t *)pCertPkg)->pkgFlags.pkgFlagsBits.imageEnc = encFlag & 0xFF;
695 ((CCX509PkgHeader_t *)pCertPkg)->pkgFlags.pkgFlagsBits.hbkType = hbkType & 0xFF;
696 ((CCX509PkgHeader_t *)pCertPkg)->certInfo.certInfoWord = 0;
697 ((CCX509PkgHeader_t *)pCertPkg)->certInfo.certInfoBits.certOffset = (sizeof(CCX509PkgHeader_t)+addDataSize) & 0xFFFF;
698 ((CCX509PkgHeader_t *)pCertPkg)->certInfo.certInfoBits.certSize = certSize;
699
700
701
702 /* write out the package in binary format */
703 UTIL_LOG_INFO("writing pkg to file\n");
704 rc = CC_CommonUtilCopyBuffToBinFile(outPkgFile, pCertPkg, pkgBytesSize);
705 if (rc != 0) {
706 UTIL_LOG_ERR("failed to CC_CommonUtilCopyBuffToBinFile\n");
707 rc = 1;
708 goto END;
709 }
710 rc = 0;
711 UTIL_LOG_INFO("OK\n");
712
713 END:
714 if (fp != NULL){
715 fclose(fp);
716 }
717 if (pCertPkg != NULL) {
718 free(pCertPkg);
719 }
720 return rc;
721 }
722 #endif
723