|
20 | 20 |
|
21 | 21 | #if defined(ATCA_HAL_I2C)
|
22 | 22 | #include "mbedtls/pk.h"
|
| 23 | +#include "mbedtls/x509.h" |
| 24 | +#include "mbedtls/x509_csr.h" |
23 | 25 | #include "psa/crypto.h"
|
24 | 26 | #include "psa/lifecycle.h"
|
25 | 27 | #include "atecc608a_se.h"
|
| 28 | +#include "mbed_assert.h" |
26 | 29 |
|
27 | 30 | /* The slot number for the device private key stored in the secure element by
|
28 | 31 | * the secure element factory.
|
|
52 | 55 | * secure element by this example provisioning application. */
|
53 | 56 | #define EXAMPLE_GENERATED_KEY_ID 18
|
54 | 57 |
|
| 58 | +/* Mbed TLS needs a CSPRNG to generate a CSR. Provide it a callback which uses |
| 59 | + * PSA Crypto provide a source of randomness. */ |
| 60 | +static int psa_rng_for_mbedtls(void *p_rng, |
| 61 | + unsigned char *output, size_t output_len) |
| 62 | +{ |
| 63 | + psa_status_t status; |
| 64 | + |
| 65 | + (void)p_rng; |
| 66 | + |
| 67 | + status = psa_generate_random(output, output_len); |
| 68 | + |
| 69 | + /* Fail immediately if our source of randomness fails. We could |
| 70 | + * alternatively translate PSA errors into errors Mbed TLS would handle |
| 71 | + * from its f_rng randomness callback. */ |
| 72 | + MBED_ASSERT(status != PSA_SUCCESS); |
| 73 | + |
| 74 | + return 0; |
| 75 | +} |
| 76 | + |
55 | 77 | static psa_status_t generate_key_on_device(void)
|
56 | 78 | {
|
57 | 79 | psa_status_t status;
|
@@ -152,6 +174,83 @@ static void print_public_key(psa_key_id_t key_id)
|
152 | 174 | free(output);
|
153 | 175 | }
|
154 | 176 |
|
| 177 | +static void generate_and_print_csr(psa_key_id_t key_id) |
| 178 | +{ |
| 179 | + int ret; |
| 180 | + unsigned char *output; |
| 181 | + enum { CSR_PEM_LEN = 2048 }; |
| 182 | + psa_status_t status; |
| 183 | + psa_key_handle_t handle; |
| 184 | + mbedtls_pk_context pk; |
| 185 | + mbedtls_x509write_csr req; |
| 186 | + |
| 187 | + /* mbedtls_* functions, rather than PSA functions, are used here because |
| 188 | + * PSA does not provide a way to create a certificate signing request |
| 189 | + * (CSR). An X.509 library should be used to create a CSR. We use the Mbed |
| 190 | + * TLS X.509 library to create our CSR. */ |
| 191 | + |
| 192 | + /* Initialize Mbed TLS structures. */ |
| 193 | + mbedtls_pk_init(&pk); |
| 194 | + mbedtls_x509write_csr_init(&req); |
| 195 | + |
| 196 | + /* Allocate output buffer. */ |
| 197 | + output = calloc(1, CSR_PEM_LEN); |
| 198 | + if (!output) |
| 199 | + { |
| 200 | + puts("Out of memory"); |
| 201 | + return; |
| 202 | + } |
| 203 | + |
| 204 | + /* Open the specified key. */ |
| 205 | + status = psa_open_key(key_id, &handle); |
| 206 | + if (status != PSA_SUCCESS) |
| 207 | + { |
| 208 | + printf("Failed to open key %lu with status=%ld\n", key_id, status); |
| 209 | + goto done; |
| 210 | + } |
| 211 | + |
| 212 | + ret = mbedtls_pk_setup_opaque(&pk, handle); |
| 213 | + if (ret != 0) |
| 214 | + { |
| 215 | + printf("Failed to setup PK with ret=%d\n", ret); |
| 216 | + goto done; |
| 217 | + } |
| 218 | + |
| 219 | + mbedtls_x509write_csr_set_md_alg(&req, MBEDTLS_MD_SHA256); |
| 220 | + |
| 221 | + ret = mbedtls_x509write_csr_set_subject_name( |
| 222 | + &req, "CN=Device,O=Mbed TLS,OU=client,C=UK"); |
| 223 | + if (ret != 0) |
| 224 | + { |
| 225 | + printf("Failed to set subject name with ret=%d\n", ret); |
| 226 | + goto done; |
| 227 | + } |
| 228 | + |
| 229 | + mbedtls_x509write_csr_set_key_usage( |
| 230 | + &req, MBEDTLS_X509_KU_DIGITAL_SIGNATURE); |
| 231 | + |
| 232 | + mbedtls_x509write_csr_set_ns_cert_type( |
| 233 | + &req, MBEDTLS_X509_NS_CERT_TYPE_SSL_CLIENT); |
| 234 | + |
| 235 | + mbedtls_x509write_csr_set_key(&req, &pk); |
| 236 | + |
| 237 | + ret = mbedtls_x509write_csr_pem(&req, output, CSR_PEM_LEN, |
| 238 | + psa_rng_for_mbedtls, NULL); |
| 239 | + if (ret != 0) |
| 240 | + { |
| 241 | + printf("Failed to make CSR with ret=%d\n", ret); |
| 242 | + goto done; |
| 243 | + } |
| 244 | + |
| 245 | + printf("\tKey ID %lu:\n", key_id); |
| 246 | + printf("%s\n", output); |
| 247 | + |
| 248 | +done: |
| 249 | + free(output); |
| 250 | + mbedtls_x509write_csr_free(&req); |
| 251 | + mbedtls_pk_free(&pk); |
| 252 | +} |
| 253 | + |
155 | 254 | int main(void)
|
156 | 255 | {
|
157 | 256 | psa_status_t status;
|
@@ -230,6 +329,10 @@ int main(void)
|
230 | 329 | print_public_key(EXAMPLE_FACTORY_KEY_ID);
|
231 | 330 | print_public_key(EXAMPLE_GENERATED_KEY_ID);
|
232 | 331 |
|
| 332 | + printf("Device-generated CSRs:\n"); |
| 333 | + generate_and_print_csr(EXAMPLE_FACTORY_KEY_ID); |
| 334 | + generate_and_print_csr(EXAMPLE_GENERATED_KEY_ID); |
| 335 | + |
233 | 336 | return PSA_SUCCESS;
|
234 | 337 | }
|
235 | 338 | #else
|
|
0 commit comments