xref: /aosp_15_r20/external/mbedtls/programs/x509/load_roots.c (revision 62c56f9862f102b96d72393aff6076c951fb8148)
1 /*
2  *  Root CA reading application
3  *
4  *  Copyright The Mbed TLS Contributors
5  *  SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
6  */
7 
8 #include "mbedtls/build_info.h"
9 
10 #include "mbedtls/platform.h"
11 
12 #if !defined(MBEDTLS_X509_CRT_PARSE_C) || !defined(MBEDTLS_FS_IO) ||  \
13     !defined(MBEDTLS_TIMING_C)
main(void)14 int main(void)
15 {
16     mbedtls_printf("MBEDTLS_X509_CRT_PARSE_C and/or MBEDTLS_FS_IO and/or "
17                    "MBEDTLS_TIMING_C not defined.\n");
18     mbedtls_exit(0);
19 }
20 #else
21 
22 #include "mbedtls/error.h"
23 #include "mbedtls/timing.h"
24 #include "mbedtls/x509_crt.h"
25 
26 #include <stdio.h>
27 #include <stdlib.h>
28 #include <string.h>
29 
30 #define DFL_ITERATIONS          1
31 #define DFL_PRIME_CACHE         1
32 
33 #define USAGE \
34     "\n usage: load_roots param=<>... [--] FILE...\n"   \
35     "\n acceptable parameters:\n"                       \
36     "    iterations=%%d        Iteration count (not including cache priming); default: 1\n"  \
37     "    prime=%%d             Prime the disk read cache? Default: 1 (yes)\n"  \
38     "\n"
39 
40 
41 /*
42  * global options
43  */
44 struct options {
45     const char **filenames;     /* NULL-terminated list of file names */
46     unsigned iterations;        /* Number of iterations to time */
47     int prime_cache;            /* Prime the disk read cache? */
48 } opt;
49 
50 
read_certificates(const char * const * filenames)51 int read_certificates(const char *const *filenames)
52 {
53     mbedtls_x509_crt cas;
54     int ret = 0;
55     const char *const *cur;
56 
57     mbedtls_x509_crt_init(&cas);
58 
59     for (cur = filenames; *cur != NULL; cur++) {
60         ret = mbedtls_x509_crt_parse_file(&cas, *cur);
61         if (ret != 0) {
62 #if defined(MBEDTLS_ERROR_C) || defined(MBEDTLS_ERROR_STRERROR_DUMMY)
63             char error_message[200];
64             mbedtls_strerror(ret, error_message, sizeof(error_message));
65             printf("\n%s: -0x%04x (%s)\n",
66                    *cur, (unsigned) -ret, error_message);
67 #else
68             printf("\n%s: -0x%04x\n",
69                    *cur, (unsigned) -ret);
70 #endif
71             goto exit;
72         }
73     }
74 
75 exit:
76     mbedtls_x509_crt_free(&cas);
77     return ret == 0;
78 }
79 
main(int argc,char * argv[])80 int main(int argc, char *argv[])
81 {
82     int exit_code = MBEDTLS_EXIT_FAILURE;
83     unsigned i, j;
84     struct mbedtls_timing_hr_time timer;
85     unsigned long ms;
86 
87 #if defined(MBEDTLS_USE_PSA_CRYPTO)
88     psa_status_t status = psa_crypto_init();
89     if (status != PSA_SUCCESS) {
90         mbedtls_fprintf(stderr, "Failed to initialize PSA Crypto implementation: %d\n",
91                         (int) status);
92         goto exit;
93     }
94 #endif /* MBEDTLS_USE_PSA_CRYPTO */
95 
96     if (argc <= 1) {
97         mbedtls_printf(USAGE);
98         goto exit;
99     }
100 
101     opt.filenames = NULL;
102     opt.iterations = DFL_ITERATIONS;
103     opt.prime_cache = DFL_PRIME_CACHE;
104 
105     for (i = 1; i < (unsigned) argc; i++) {
106         char *p = argv[i];
107         char *q = NULL;
108 
109         if (strcmp(p, "--") == 0) {
110             break;
111         }
112         if ((q = strchr(p, '=')) == NULL) {
113             break;
114         }
115         *q++ = '\0';
116 
117         for (j = 0; p + j < q; j++) {
118             if (argv[i][j] >= 'A' && argv[i][j] <= 'Z') {
119                 argv[i][j] |= 0x20;
120             }
121         }
122 
123         if (strcmp(p, "iterations") == 0) {
124             opt.iterations = atoi(q);
125         } else if (strcmp(p, "prime") == 0) {
126             opt.iterations = atoi(q) != 0;
127         } else {
128             mbedtls_printf("Unknown option: %s\n", p);
129             mbedtls_printf(USAGE);
130             goto exit;
131         }
132     }
133 
134     opt.filenames = (const char **) argv + i;
135     if (*opt.filenames == 0) {
136         mbedtls_printf("Missing list of certificate files to parse\n");
137         goto exit;
138     }
139 
140     mbedtls_printf("Parsing %u certificates", argc - i);
141     if (opt.prime_cache) {
142         if (!read_certificates(opt.filenames)) {
143             goto exit;
144         }
145         mbedtls_printf(" ");
146     }
147 
148     (void) mbedtls_timing_get_timer(&timer, 1);
149     for (i = 1; i <= opt.iterations; i++) {
150         if (!read_certificates(opt.filenames)) {
151             goto exit;
152         }
153         mbedtls_printf(".");
154     }
155     ms = mbedtls_timing_get_timer(&timer, 0);
156     mbedtls_printf("\n%u iterations -> %lu ms\n", opt.iterations, ms);
157     exit_code = MBEDTLS_EXIT_SUCCESS;
158 
159 exit:
160 #if defined(MBEDTLS_USE_PSA_CRYPTO)
161     mbedtls_psa_crypto_free();
162 #endif /* MBEDTLS_USE_PSA_CRYPTO */
163     mbedtls_exit(exit_code);
164 }
165 #endif /* necessary configuration */
166