xref: /aosp_15_r20/external/mbedtls/tests/suites/test_suite_x509write.function (revision 62c56f9862f102b96d72393aff6076c951fb8148)
1/* BEGIN_HEADER */
2#include "mbedtls/bignum.h"
3#include "mbedtls/x509_crt.h"
4#include "mbedtls/x509_csr.h"
5#include "mbedtls/pem.h"
6#include "mbedtls/oid.h"
7#include "mbedtls/rsa.h"
8#include "mbedtls/asn1write.h"
9#include "mbedtls/pk.h"
10#include "md_psa.h"
11
12#if defined(MBEDTLS_RSA_C)
13int mbedtls_rsa_decrypt_func(void *ctx, size_t *olen,
14                             const unsigned char *input, unsigned char *output,
15                             size_t output_max_len)
16{
17    return mbedtls_rsa_pkcs1_decrypt((mbedtls_rsa_context *) ctx, NULL, NULL,
18                                     olen, input, output, output_max_len);
19}
20int mbedtls_rsa_sign_func(void *ctx,
21                          int (*f_rng)(void *, unsigned char *, size_t), void *p_rng,
22                          mbedtls_md_type_t md_alg, unsigned int hashlen,
23                          const unsigned char *hash, unsigned char *sig)
24{
25    return mbedtls_rsa_pkcs1_sign((mbedtls_rsa_context *) ctx, f_rng, p_rng,
26                                  md_alg, hashlen, hash, sig);
27}
28size_t mbedtls_rsa_key_len_func(void *ctx)
29{
30    return ((const mbedtls_rsa_context *) ctx)->len;
31}
32#endif /* MBEDTLS_RSA_C */
33
34#if defined(MBEDTLS_USE_PSA_CRYPTO) && \
35    defined(MBEDTLS_PEM_WRITE_C) && defined(MBEDTLS_X509_CSR_WRITE_C)
36static int x509_crt_verifycsr(const unsigned char *buf, size_t buflen)
37{
38    unsigned char hash[PSA_HASH_MAX_SIZE];
39    mbedtls_x509_csr csr;
40    int ret = 0;
41
42    mbedtls_x509_csr_init(&csr);
43
44    if (mbedtls_x509_csr_parse(&csr, buf, buflen) != 0) {
45        ret = MBEDTLS_ERR_X509_BAD_INPUT_DATA;
46        goto cleanup;
47    }
48
49    psa_algorithm_t psa_alg = mbedtls_md_psa_alg_from_type(csr.sig_md);
50    size_t hash_size = 0;
51    psa_status_t status = psa_hash_compute(psa_alg, csr.cri.p, csr.cri.len,
52                                           hash, PSA_HASH_MAX_SIZE, &hash_size);
53
54    if (status != PSA_SUCCESS) {
55        /* Note: this can't happen except after an internal error */
56        ret = MBEDTLS_ERR_X509_BAD_INPUT_DATA;
57        goto cleanup;
58    }
59
60    if (mbedtls_pk_verify_ext(csr.sig_pk, csr.sig_opts, &csr.pk,
61                              csr.sig_md, hash, mbedtls_md_get_size_from_type(csr.sig_md),
62                              csr.sig.p, csr.sig.len) != 0) {
63        ret = MBEDTLS_ERR_X509_CERT_VERIFY_FAILED;
64        goto cleanup;
65    }
66
67cleanup:
68
69    mbedtls_x509_csr_free(&csr);
70    return ret;
71}
72#endif /* MBEDTLS_USE_PSA_CRYPTO && MBEDTLS_PEM_WRITE_C && MBEDTLS_X509_CSR_WRITE_C */
73
74#if defined(MBEDTLS_X509_CSR_WRITE_C)
75
76/*
77 * The size of this temporary buffer is given by the sequence of functions
78 * called hereinafter:
79 * - mbedtls_asn1_write_oid()
80 *     - 8 bytes for MBEDTLS_OID_EXTENDED_KEY_USAGE raw value
81 *     - 1 byte for MBEDTLS_OID_EXTENDED_KEY_USAGE length
82 *     - 1 byte for MBEDTLS_ASN1_OID tag
83 * - mbedtls_asn1_write_len()
84 *     - 1 byte since we're dealing with sizes which are less than 0x80
85 * - mbedtls_asn1_write_tag()
86 *     - 1 byte
87 *
88 * This length is fine as long as this function is called using the
89 * MBEDTLS_OID_SERVER_AUTH OID. If this is changed in the future, then this
90 * buffer's length should be adjusted accordingly.
91 * Unfortunately there's no predefined max size for OIDs which can be used
92 * to set an overall upper boundary which is always guaranteed.
93 */
94#define EXT_KEY_USAGE_TMP_BUF_MAX_LENGTH    12
95
96static int csr_set_extended_key_usage(mbedtls_x509write_csr *ctx,
97                                      const char *oid, size_t oid_len)
98{
99    unsigned char buf[EXT_KEY_USAGE_TMP_BUF_MAX_LENGTH] = { 0 };
100    unsigned char *p = buf + sizeof(buf);
101    int ret;
102    size_t len = 0;
103
104    /*
105     * Following functions fail anyway if the temporary buffer is not large,
106     * but we set an extra check here to emphasize a possible source of errors
107     */
108    if (oid_len > EXT_KEY_USAGE_TMP_BUF_MAX_LENGTH) {
109        return MBEDTLS_ERR_X509_BAD_INPUT_DATA;
110    }
111
112    MBEDTLS_ASN1_CHK_ADD(len, mbedtls_asn1_write_oid(&p, buf, oid, oid_len));
113    MBEDTLS_ASN1_CHK_ADD(len, mbedtls_asn1_write_len(&p, buf, ret));
114    MBEDTLS_ASN1_CHK_ADD(len, mbedtls_asn1_write_tag(&p, buf,
115                                                     MBEDTLS_ASN1_CONSTRUCTED |
116                                                     MBEDTLS_ASN1_SEQUENCE));
117
118    ret = mbedtls_x509write_csr_set_extension(ctx,
119                                              MBEDTLS_OID_EXTENDED_KEY_USAGE,
120                                              MBEDTLS_OID_SIZE(MBEDTLS_OID_EXTENDED_KEY_USAGE),
121                                              0,
122                                              p,
123                                              len);
124
125    return ret;
126}
127#endif  /* MBEDTLS_X509_CSR_WRITE_C */
128
129/* Due to inconsistencies in the input size limits applied by different
130 * library functions, some write-parse tests may fail. */
131#define MAY_FAIL_GET_NAME       0x0001
132#define MAY_FAIL_DN_GETS        0x0002
133
134/* END_HEADER */
135
136/* BEGIN_DEPENDENCIES
137 * depends_on:MBEDTLS_FS_IO:MBEDTLS_PK_PARSE_C
138 * END_DEPENDENCIES
139 */
140
141/* BEGIN_CASE depends_on:MBEDTLS_PEM_WRITE_C:MBEDTLS_X509_CSR_WRITE_C */
142void x509_csr_check(char *key_file, char *cert_req_check_file, int md_type,
143                    int key_usage, int set_key_usage, int cert_type,
144                    int set_cert_type, int set_extension)
145{
146    mbedtls_pk_context key;
147    mbedtls_x509write_csr req;
148    unsigned char buf[4096];
149    int ret;
150#if !defined(MBEDTLS_USE_PSA_CRYPTO)
151    unsigned char check_buf[4000];
152    FILE *f;
153    size_t olen = 0;
154#endif /* !MBEDTLS_USE_PSA_CRYPTO */
155    size_t pem_len = 0, buf_index;
156    int der_len = -1;
157    const char *subject_name = "C=NL,O=PolarSSL,CN=PolarSSL Server 1";
158    mbedtls_test_rnd_pseudo_info rnd_info;
159    mbedtls_x509_san_list san_ip;
160    mbedtls_x509_san_list san_dns;
161    mbedtls_x509_san_list san_uri;
162    mbedtls_x509_san_list san_mail;
163    mbedtls_x509_san_list san_dn;
164    mbedtls_x509_san_list *san_list = NULL;
165    mbedtls_asn1_named_data *ext_san_dirname = NULL;
166
167    const char san_ip_name[] = { 0x7f, 0x00, 0x00, 0x01 }; // 127.0.0.1
168    const char *san_dns_name = "example.com";
169    const char *san_dn_name = "C=UK,O=Mbed TLS,CN=Mbed TLS directoryName SAN";
170    const char *san_mail_name = "[email protected]";
171    const char *san_uri_name = "http://pki.example.com";
172
173    san_mail.node.type = MBEDTLS_X509_SAN_RFC822_NAME;
174    san_mail.node.san.unstructured_name.p = (unsigned char *) san_mail_name;
175    san_mail.node.san.unstructured_name.len = strlen(san_mail_name);
176    san_mail.next = NULL;
177
178    san_dns.node.type = MBEDTLS_X509_SAN_DNS_NAME;
179    san_dns.node.san.unstructured_name.p = (unsigned char *) san_dns_name;
180    san_dns.node.san.unstructured_name.len = strlen(san_dns_name);
181    san_dns.next = &san_mail;
182
183    san_dn.node.type = MBEDTLS_X509_SAN_DIRECTORY_NAME;
184    TEST_ASSERT(mbedtls_x509_string_to_names(&ext_san_dirname,
185                                             san_dn_name) == 0);
186    san_dn.node.san.directory_name = *ext_san_dirname;
187    san_dn.next = &san_dns;
188
189    san_ip.node.type = MBEDTLS_X509_SAN_IP_ADDRESS;
190    san_ip.node.san.unstructured_name.p = (unsigned char *) san_ip_name;
191    san_ip.node.san.unstructured_name.len = sizeof(san_ip_name);
192    san_ip.next = &san_dn;
193
194    san_uri.node.type = MBEDTLS_X509_SAN_UNIFORM_RESOURCE_IDENTIFIER;
195    san_uri.node.san.unstructured_name.p = (unsigned char *) san_uri_name;
196    san_uri.node.san.unstructured_name.len = strlen(san_uri_name);
197    san_uri.next = &san_ip;
198
199    san_list = &san_uri;
200
201    memset(&rnd_info, 0x2a, sizeof(mbedtls_test_rnd_pseudo_info));
202
203    mbedtls_x509write_csr_init(&req);
204    mbedtls_pk_init(&key);
205    MD_OR_USE_PSA_INIT();
206
207    TEST_ASSERT(mbedtls_pk_parse_keyfile(&key, key_file, NULL,
208                                         mbedtls_test_rnd_std_rand, NULL) == 0);
209
210    mbedtls_x509write_csr_set_md_alg(&req, md_type);
211    mbedtls_x509write_csr_set_key(&req, &key);
212    TEST_ASSERT(mbedtls_x509write_csr_set_subject_name(&req, subject_name) == 0);
213    if (set_key_usage != 0) {
214        TEST_ASSERT(mbedtls_x509write_csr_set_key_usage(&req, key_usage) == 0);
215    }
216    if (set_cert_type != 0) {
217        TEST_ASSERT(mbedtls_x509write_csr_set_ns_cert_type(&req, cert_type) == 0);
218    }
219    if (set_extension != 0) {
220        TEST_ASSERT(csr_set_extended_key_usage(&req, MBEDTLS_OID_SERVER_AUTH,
221                                               MBEDTLS_OID_SIZE(MBEDTLS_OID_SERVER_AUTH)) == 0);
222
223        TEST_ASSERT(mbedtls_x509write_csr_set_subject_alternative_name(&req, san_list) == 0);
224    }
225
226    ret = mbedtls_x509write_csr_pem(&req, buf, sizeof(buf),
227                                    mbedtls_test_rnd_pseudo_rand, &rnd_info);
228    TEST_ASSERT(ret == 0);
229
230    pem_len = strlen((char *) buf);
231
232    for (buf_index = pem_len; buf_index < sizeof(buf); ++buf_index) {
233        TEST_ASSERT(buf[buf_index] == 0);
234    }
235
236#if defined(MBEDTLS_USE_PSA_CRYPTO)
237    // When using PSA crypto, RNG isn't controllable, so cert_req_check_file can't be used
238    (void) cert_req_check_file;
239    buf[pem_len] = '\0';
240    TEST_ASSERT(x509_crt_verifycsr(buf, pem_len + 1) == 0);
241#else
242    f = fopen(cert_req_check_file, "r");
243    TEST_ASSERT(f != NULL);
244    olen = fread(check_buf, 1, sizeof(check_buf), f);
245    fclose(f);
246
247    TEST_ASSERT(olen >= pem_len - 1);
248    TEST_ASSERT(memcmp(buf, check_buf, pem_len - 1) == 0);
249#endif /* MBEDTLS_USE_PSA_CRYPTO */
250
251    der_len = mbedtls_x509write_csr_der(&req, buf, sizeof(buf),
252                                        mbedtls_test_rnd_pseudo_rand,
253                                        &rnd_info);
254    TEST_ASSERT(der_len >= 0);
255
256    if (der_len == 0) {
257        goto exit;
258    }
259
260#if defined(MBEDTLS_USE_PSA_CRYPTO)
261    // When using PSA crypto, RNG isn't controllable, result length isn't
262    // deterministic over multiple runs, removing a single byte isn't enough to
263    // go into the MBEDTLS_ERR_ASN1_BUF_TOO_SMALL error case
264    der_len /= 2;
265#else
266    der_len -= 1;
267#endif
268    ret = mbedtls_x509write_csr_der(&req, buf, (size_t) (der_len),
269                                    mbedtls_test_rnd_pseudo_rand, &rnd_info);
270    TEST_ASSERT(ret == MBEDTLS_ERR_ASN1_BUF_TOO_SMALL);
271
272exit:
273    mbedtls_asn1_free_named_data_list(&ext_san_dirname);
274    mbedtls_x509write_csr_free(&req);
275    mbedtls_pk_free(&key);
276    MD_OR_USE_PSA_DONE();
277}
278/* END_CASE */
279
280/* BEGIN_CASE depends_on:MBEDTLS_PEM_WRITE_C:MBEDTLS_X509_CSR_WRITE_C:MBEDTLS_USE_PSA_CRYPTO */
281void x509_csr_check_opaque(char *key_file, int md_type, int key_usage,
282                           int cert_type)
283{
284    mbedtls_pk_context key;
285    mbedtls_svc_key_id_t key_id = MBEDTLS_SVC_KEY_ID_INIT;
286    psa_algorithm_t md_alg_psa, alg_psa;
287    mbedtls_x509write_csr req;
288    unsigned char buf[4096];
289    int ret;
290    size_t pem_len = 0;
291    const char *subject_name = "C=NL,O=PolarSSL,CN=PolarSSL Server 1";
292    mbedtls_test_rnd_pseudo_info rnd_info;
293
294    mbedtls_x509write_csr_init(&req);
295    MD_OR_USE_PSA_INIT();
296
297    memset(&rnd_info, 0x2a, sizeof(mbedtls_test_rnd_pseudo_info));
298
299    md_alg_psa = mbedtls_md_psa_alg_from_type((mbedtls_md_type_t) md_type);
300    TEST_ASSERT(md_alg_psa != MBEDTLS_MD_NONE);
301
302    mbedtls_pk_init(&key);
303    TEST_ASSERT(mbedtls_pk_parse_keyfile(&key, key_file, NULL,
304                                         mbedtls_test_rnd_std_rand, NULL) == 0);
305
306    if (mbedtls_pk_get_type(&key) == MBEDTLS_PK_ECKEY) {
307        alg_psa = PSA_ALG_ECDSA(md_alg_psa);
308    } else if (mbedtls_pk_get_type(&key) == MBEDTLS_PK_RSA) {
309        alg_psa = PSA_ALG_RSA_PKCS1V15_SIGN(md_alg_psa);
310    } else {
311        TEST_ASSUME(!"PK key type not supported in this configuration");
312    }
313
314    TEST_ASSERT(mbedtls_pk_wrap_as_opaque(&key, &key_id, alg_psa,
315                                          PSA_KEY_USAGE_SIGN_HASH,
316                                          PSA_ALG_NONE) == 0);
317
318    mbedtls_x509write_csr_set_md_alg(&req, md_type);
319    mbedtls_x509write_csr_set_key(&req, &key);
320    TEST_ASSERT(mbedtls_x509write_csr_set_subject_name(&req, subject_name) == 0);
321    if (key_usage != 0) {
322        TEST_ASSERT(mbedtls_x509write_csr_set_key_usage(&req, key_usage) == 0);
323    }
324    if (cert_type != 0) {
325        TEST_ASSERT(mbedtls_x509write_csr_set_ns_cert_type(&req, cert_type) == 0);
326    }
327
328    ret = mbedtls_x509write_csr_pem(&req, buf, sizeof(buf) - 1,
329                                    mbedtls_test_rnd_pseudo_rand, &rnd_info);
330
331    TEST_ASSERT(ret == 0);
332
333    pem_len = strlen((char *) buf);
334    buf[pem_len] = '\0';
335    TEST_ASSERT(x509_crt_verifycsr(buf, pem_len + 1) == 0);
336
337
338exit:
339    mbedtls_x509write_csr_free(&req);
340    mbedtls_pk_free(&key);
341    psa_destroy_key(key_id);
342    MD_OR_USE_PSA_DONE();
343}
344/* END_CASE */
345
346/* BEGIN_CASE depends_on:MBEDTLS_PEM_WRITE_C:MBEDTLS_X509_CRT_WRITE_C:MBEDTLS_X509_CRT_PARSE_C:MBEDTLS_MD_CAN_SHA1 */
347void x509_crt_check(char *subject_key_file, char *subject_pwd,
348                    char *subject_name, char *issuer_key_file,
349                    char *issuer_pwd, char *issuer_name,
350                    data_t *serial_arg, char *not_before, char *not_after,
351                    int md_type, int key_usage, int set_key_usage,
352                    char *ext_key_usage,
353                    int cert_type, int set_cert_type, int auth_ident,
354                    int ver, char *cert_check_file, int pk_wrap, int is_ca,
355                    char *cert_verify_file, int set_subjectAltNames)
356{
357    mbedtls_pk_context subject_key, issuer_key, issuer_key_alt;
358    mbedtls_pk_context *key = &issuer_key;
359
360    mbedtls_x509write_cert crt;
361    unsigned char buf[4096];
362    unsigned char check_buf[5000];
363    unsigned char *p, *end;
364    unsigned char tag, sz;
365#if defined(MBEDTLS_TEST_DEPRECATED) && defined(MBEDTLS_BIGNUM_C)
366    mbedtls_mpi serial_mpi;
367#endif
368    int ret, before_tag, after_tag;
369    size_t olen = 0, pem_len = 0, buf_index = 0;
370    int der_len = -1;
371    FILE *f;
372    mbedtls_test_rnd_pseudo_info rnd_info;
373#if defined(MBEDTLS_USE_PSA_CRYPTO)
374    mbedtls_svc_key_id_t key_id = MBEDTLS_SVC_KEY_ID_INIT;
375#endif
376    mbedtls_pk_type_t issuer_key_type;
377    mbedtls_x509_san_list san_ip;
378    mbedtls_x509_san_list san_dns;
379    mbedtls_x509_san_list san_uri;
380    mbedtls_x509_san_list san_mail;
381    mbedtls_x509_san_list san_dn;
382    mbedtls_asn1_named_data *ext_san_dirname = NULL;
383    const char san_ip_name[] = { 0x01, 0x02, 0x03, 0x04 };
384    const char *san_dns_name = "example.com";
385    const char *san_dn_name = "C=UK,O=Mbed TLS,CN=SubjectAltName test";
386    const char *san_mail_name = "[email protected]";
387    const char *san_uri_name = "http://pki.example.com";
388    mbedtls_x509_san_list *san_list = NULL;
389
390    if (set_subjectAltNames) {
391        san_mail.node.type = MBEDTLS_X509_SAN_RFC822_NAME;
392        san_mail.node.san.unstructured_name.p = (unsigned char *) san_mail_name;
393        san_mail.node.san.unstructured_name.len = strlen(san_mail_name);
394        san_mail.next = NULL;
395
396        san_dns.node.type = MBEDTLS_X509_SAN_DNS_NAME;
397        san_dns.node.san.unstructured_name.p = (unsigned char *) san_dns_name;
398        san_dns.node.san.unstructured_name.len = strlen(san_dns_name);
399        san_dns.next = &san_mail;
400
401        san_dn.node.type = MBEDTLS_X509_SAN_DIRECTORY_NAME;
402        TEST_ASSERT(mbedtls_x509_string_to_names(&ext_san_dirname,
403                                                 san_dn_name) == 0);
404        san_dn.node.san.directory_name = *ext_san_dirname;
405        san_dn.next = &san_dns;
406
407        san_ip.node.type = MBEDTLS_X509_SAN_IP_ADDRESS;
408        san_ip.node.san.unstructured_name.p = (unsigned char *) san_ip_name;
409        san_ip.node.san.unstructured_name.len = sizeof(san_ip_name);
410        san_ip.next = &san_dn;
411
412        san_uri.node.type = MBEDTLS_X509_SAN_UNIFORM_RESOURCE_IDENTIFIER;
413        san_uri.node.san.unstructured_name.p = (unsigned char *) san_uri_name;
414        san_uri.node.san.unstructured_name.len = strlen(san_uri_name);
415        san_uri.next = &san_ip;
416
417        san_list = &san_uri;
418    }
419
420    memset(&rnd_info, 0x2a, sizeof(mbedtls_test_rnd_pseudo_info));
421#if defined(MBEDTLS_TEST_DEPRECATED) && defined(MBEDTLS_BIGNUM_C)
422    mbedtls_mpi_init(&serial_mpi);
423#endif
424
425    mbedtls_pk_init(&subject_key);
426    mbedtls_pk_init(&issuer_key);
427    mbedtls_pk_init(&issuer_key_alt);
428    mbedtls_x509write_crt_init(&crt);
429    MD_OR_USE_PSA_INIT();
430
431    TEST_ASSERT(mbedtls_pk_parse_keyfile(&subject_key, subject_key_file,
432                                         subject_pwd, mbedtls_test_rnd_std_rand, NULL) == 0);
433
434    TEST_ASSERT(mbedtls_pk_parse_keyfile(&issuer_key, issuer_key_file,
435                                         issuer_pwd, mbedtls_test_rnd_std_rand, NULL) == 0);
436
437    issuer_key_type = mbedtls_pk_get_type(&issuer_key);
438
439#if defined(MBEDTLS_RSA_C) && defined(MBEDTLS_PK_RSA_ALT_SUPPORT)
440    /* For RSA PK contexts, create a copy as an alternative RSA context. */
441    if (pk_wrap == 1 && issuer_key_type == MBEDTLS_PK_RSA) {
442        TEST_ASSERT(mbedtls_pk_setup_rsa_alt(&issuer_key_alt,
443                                             mbedtls_pk_rsa(issuer_key),
444                                             mbedtls_rsa_decrypt_func,
445                                             mbedtls_rsa_sign_func,
446                                             mbedtls_rsa_key_len_func) == 0);
447
448        key = &issuer_key_alt;
449    }
450#endif
451
452#if defined(MBEDTLS_USE_PSA_CRYPTO)
453    /* For Opaque PK contexts, wrap key as an Opaque RSA context. */
454    if (pk_wrap == 2) {
455        psa_algorithm_t alg_psa, md_alg_psa;
456
457        md_alg_psa = mbedtls_md_psa_alg_from_type((mbedtls_md_type_t) md_type);
458        TEST_ASSERT(md_alg_psa != MBEDTLS_MD_NONE);
459
460        if (mbedtls_pk_get_type(&issuer_key) == MBEDTLS_PK_ECKEY) {
461            alg_psa = PSA_ALG_ECDSA(md_alg_psa);
462        } else if (mbedtls_pk_get_type(&issuer_key) == MBEDTLS_PK_RSA) {
463            alg_psa = PSA_ALG_RSA_PKCS1V15_SIGN(md_alg_psa);
464        } else {
465            TEST_ASSUME(!"PK key type not supported in this configuration");
466        }
467
468        TEST_ASSERT(mbedtls_pk_wrap_as_opaque(&issuer_key, &key_id, alg_psa,
469                                              PSA_KEY_USAGE_SIGN_HASH,
470                                              PSA_ALG_NONE) == 0);
471    }
472#endif /* MBEDTLS_USE_PSA_CRYPTO */
473
474    if (pk_wrap == 2) {
475        TEST_ASSERT(mbedtls_pk_get_type(&issuer_key) == MBEDTLS_PK_OPAQUE);
476    }
477
478    if (ver != -1) {
479        mbedtls_x509write_crt_set_version(&crt, ver);
480    }
481
482#if defined(MBEDTLS_TEST_DEPRECATED) && defined(MBEDTLS_BIGNUM_C)
483    TEST_ASSERT(mbedtls_mpi_read_binary(&serial_mpi, serial_arg->x,
484                                        serial_arg->len) == 0);
485    TEST_ASSERT(mbedtls_x509write_crt_set_serial(&crt, &serial_mpi) == 0);
486#else
487    TEST_ASSERT(mbedtls_x509write_crt_set_serial_raw(&crt, serial_arg->x,
488                                                     serial_arg->len) == 0);
489#endif
490    TEST_ASSERT(mbedtls_x509write_crt_set_validity(&crt, not_before,
491                                                   not_after) == 0);
492    mbedtls_x509write_crt_set_md_alg(&crt, md_type);
493    TEST_ASSERT(mbedtls_x509write_crt_set_issuer_name(&crt, issuer_name) == 0);
494    TEST_ASSERT(mbedtls_x509write_crt_set_subject_name(&crt, subject_name) == 0);
495    mbedtls_x509write_crt_set_subject_key(&crt, &subject_key);
496
497    mbedtls_x509write_crt_set_issuer_key(&crt, key);
498
499    if (crt.version >= MBEDTLS_X509_CRT_VERSION_3) {
500        /* For the CA case, a path length of -1 means unlimited. */
501        TEST_ASSERT(mbedtls_x509write_crt_set_basic_constraints(&crt, is_ca,
502                                                                (is_ca ? -1 : 0)) == 0);
503        TEST_ASSERT(mbedtls_x509write_crt_set_subject_key_identifier(&crt) == 0);
504        if (auth_ident) {
505            TEST_ASSERT(mbedtls_x509write_crt_set_authority_key_identifier(&crt) == 0);
506        }
507        if (set_key_usage != 0) {
508            TEST_ASSERT(mbedtls_x509write_crt_set_key_usage(&crt, key_usage) == 0);
509        }
510        if (set_cert_type != 0) {
511            TEST_ASSERT(mbedtls_x509write_crt_set_ns_cert_type(&crt, cert_type) == 0);
512        }
513        if (strcmp(ext_key_usage, "NULL") != 0) {
514            mbedtls_asn1_sequence exts[2];
515            memset(exts, 0, sizeof(exts));
516
517#define SET_OID(x, oid)                \
518    do {                               \
519        x.len = MBEDTLS_OID_SIZE(oid); \
520        x.p   = (unsigned char *) oid;   \
521        x.tag = MBEDTLS_ASN1_OID;      \
522    }                                  \
523    while (0)
524
525            if (strcmp(ext_key_usage, "serverAuth") == 0) {
526                SET_OID(exts[0].buf, MBEDTLS_OID_SERVER_AUTH);
527            } else if (strcmp(ext_key_usage, "codeSigning,timeStamping") == 0) {
528                SET_OID(exts[0].buf, MBEDTLS_OID_CODE_SIGNING);
529                exts[0].next = &exts[1];
530                SET_OID(exts[1].buf, MBEDTLS_OID_TIME_STAMPING);
531            }
532            TEST_ASSERT(mbedtls_x509write_crt_set_ext_key_usage(&crt, exts) == 0);
533        }
534    }
535
536    if (set_subjectAltNames) {
537        TEST_ASSERT(mbedtls_x509write_crt_set_subject_alternative_name(&crt, san_list) == 0);
538    }
539    ret = mbedtls_x509write_crt_pem(&crt, buf, sizeof(buf),
540                                    mbedtls_test_rnd_pseudo_rand, &rnd_info);
541    TEST_ASSERT(ret == 0);
542
543    pem_len = strlen((char *) buf);
544
545    // check that the rest of the buffer remains clear
546    for (buf_index = pem_len; buf_index < sizeof(buf); ++buf_index) {
547        TEST_ASSERT(buf[buf_index] == 0);
548    }
549
550    if (issuer_key_type != MBEDTLS_PK_RSA) {
551        mbedtls_x509_crt crt_parse, trusted;
552        uint32_t flags;
553
554        mbedtls_x509_crt_init(&crt_parse);
555        mbedtls_x509_crt_init(&trusted);
556
557        TEST_ASSERT(mbedtls_x509_crt_parse_file(&trusted,
558                                                cert_verify_file) == 0);
559        TEST_ASSERT(mbedtls_x509_crt_parse(&crt_parse,
560                                           buf, sizeof(buf)) == 0);
561
562        ret = mbedtls_x509_crt_verify(&crt_parse, &trusted, NULL, NULL, &flags,
563                                      NULL, NULL);
564
565        mbedtls_x509_crt_free(&crt_parse);
566        mbedtls_x509_crt_free(&trusted);
567
568        TEST_EQUAL(flags, 0);
569        TEST_EQUAL(ret, 0);
570    } else if (*cert_check_file != '\0') {
571        f = fopen(cert_check_file, "r");
572        TEST_ASSERT(f != NULL);
573        olen = fread(check_buf, 1, sizeof(check_buf), f);
574        fclose(f);
575        TEST_ASSERT(olen < sizeof(check_buf));
576
577        TEST_EQUAL(olen, pem_len);
578        TEST_ASSERT(olen >= pem_len - 1);
579        TEST_ASSERT(memcmp(buf, check_buf, pem_len - 1) == 0);
580    }
581
582    der_len = mbedtls_x509write_crt_der(&crt, buf, sizeof(buf),
583                                        mbedtls_test_rnd_pseudo_rand,
584                                        &rnd_info);
585    TEST_ASSERT(der_len >= 0);
586
587    if (der_len == 0) {
588        goto exit;
589    }
590
591    // Not testing against file, check date format
592    if (*cert_check_file == '\0') {
593        // UTC tag if before 2050, 2 digits less for year
594        if (not_before[0] == '2' && (not_before[1] > '0' || not_before[2] > '4')) {
595            before_tag = MBEDTLS_ASN1_GENERALIZED_TIME;
596        } else {
597            before_tag = MBEDTLS_ASN1_UTC_TIME;
598            not_before += 2;
599        }
600        if (not_after[0] == '2' && (not_after[1] > '0' || not_after[2] > '4')) {
601            after_tag = MBEDTLS_ASN1_GENERALIZED_TIME;
602        } else {
603            after_tag = MBEDTLS_ASN1_UTC_TIME;
604            not_after += 2;
605        }
606        end = buf + sizeof(buf);
607        for (p = end - der_len; p < end;) {
608            tag = *p++;
609            sz = *p++;
610            if (tag == MBEDTLS_ASN1_UTC_TIME || tag == MBEDTLS_ASN1_GENERALIZED_TIME) {
611                // Check correct tag and time written
612                TEST_ASSERT(before_tag == tag);
613                TEST_ASSERT(memcmp(p, not_before, sz - 1) == 0);
614                p += sz;
615                tag = *p++;
616                sz = *p++;
617                TEST_ASSERT(after_tag == tag);
618                TEST_ASSERT(memcmp(p, not_after, sz - 1) == 0);
619                break;
620            }
621            // Increment if long form ASN1 length
622            if (sz & 0x80) {
623                p += sz & 0x0F;
624            }
625            if (tag != (MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE)) {
626                p += sz;
627            }
628        }
629        TEST_ASSERT(p < end);
630    }
631
632#if defined(MBEDTLS_USE_PSA_CRYPTO)
633    // When using PSA crypto, RNG isn't controllable, result length isn't
634    // deterministic over multiple runs, removing a single byte isn't enough to
635    // go into the MBEDTLS_ERR_ASN1_BUF_TOO_SMALL error case
636    if (issuer_key_type != MBEDTLS_PK_RSA) {
637        der_len /= 2;
638    } else
639#endif
640    der_len -= 1;
641
642    ret = mbedtls_x509write_crt_der(&crt, buf, (size_t) (der_len),
643                                    mbedtls_test_rnd_pseudo_rand, &rnd_info);
644    TEST_ASSERT(ret == MBEDTLS_ERR_ASN1_BUF_TOO_SMALL);
645
646exit:
647    mbedtls_asn1_free_named_data_list(&ext_san_dirname);
648    mbedtls_x509write_crt_free(&crt);
649    mbedtls_pk_free(&issuer_key_alt);
650    mbedtls_pk_free(&subject_key);
651    mbedtls_pk_free(&issuer_key);
652#if defined(MBEDTLS_TEST_DEPRECATED) && defined(MBEDTLS_BIGNUM_C)
653    mbedtls_mpi_free(&serial_mpi);
654#endif
655#if defined(MBEDTLS_USE_PSA_CRYPTO)
656    psa_destroy_key(key_id);
657#endif
658    MD_OR_USE_PSA_DONE();
659}
660/* END_CASE */
661
662/* BEGIN_CASE depends_on:MBEDTLS_X509_CRT_WRITE_C */
663void x509_set_serial_check()
664{
665    mbedtls_x509write_cert ctx;
666    uint8_t invalid_serial[MBEDTLS_X509_RFC5280_MAX_SERIAL_LEN + 1];
667
668    USE_PSA_INIT();
669    memset(invalid_serial, 0x01, sizeof(invalid_serial));
670
671#if defined(MBEDTLS_TEST_DEPRECATED) && defined(MBEDTLS_BIGNUM_C)
672    mbedtls_mpi serial_mpi;
673
674    mbedtls_mpi_init(&serial_mpi);
675    TEST_EQUAL(mbedtls_mpi_read_binary(&serial_mpi, invalid_serial,
676                                       sizeof(invalid_serial)), 0);
677    TEST_EQUAL(mbedtls_x509write_crt_set_serial(&ctx, &serial_mpi),
678               MBEDTLS_ERR_X509_BAD_INPUT_DATA);
679#endif
680
681    TEST_EQUAL(mbedtls_x509write_crt_set_serial_raw(&ctx, invalid_serial,
682                                                    sizeof(invalid_serial)),
683               MBEDTLS_ERR_X509_BAD_INPUT_DATA);
684
685exit:
686#if defined(MBEDTLS_TEST_DEPRECATED) && defined(MBEDTLS_BIGNUM_C)
687    mbedtls_mpi_free(&serial_mpi);
688#else
689    ;
690#endif
691    USE_PSA_DONE();
692}
693/* END_CASE */
694
695/* BEGIN_CASE depends_on:MBEDTLS_X509_CREATE_C:MBEDTLS_X509_USE_C */
696void mbedtls_x509_string_to_names(char *name, char *parsed_name,
697                                  int result, int may_fail)
698{
699    int ret;
700    size_t len = 0;
701    mbedtls_asn1_named_data *names = NULL;
702    mbedtls_x509_name parsed, *parsed_cur, *parsed_prv;
703    unsigned char buf[1024], out[1024], *c;
704
705    USE_PSA_INIT();
706
707    memset(&parsed, 0, sizeof(parsed));
708    memset(out, 0, sizeof(out));
709    memset(buf, 0, sizeof(buf));
710    c = buf + sizeof(buf);
711
712    ret = mbedtls_x509_string_to_names(&names, name);
713    TEST_EQUAL(ret, result);
714
715    if (ret != 0) {
716        goto exit;
717    }
718
719    ret = mbedtls_x509_write_names(&c, buf, names);
720    TEST_LE_S(1, ret);
721
722    TEST_EQUAL(mbedtls_asn1_get_tag(&c, buf + sizeof(buf), &len,
723                                    MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE), 0);
724    ret = mbedtls_x509_get_name(&c, buf + sizeof(buf), &parsed);
725    if ((may_fail & MAY_FAIL_GET_NAME) && ret < 0) {
726        /* Validation inconsistency between mbedtls_x509_string_to_names() and
727         * mbedtls_x509_get_name(). Accept it for now. */
728        goto exit;
729    }
730    TEST_EQUAL(ret, 0);
731
732    ret = mbedtls_x509_dn_gets((char *) out, sizeof(out), &parsed);
733    if ((may_fail & MAY_FAIL_DN_GETS) && ret < 0) {
734        /* Validation inconsistency between mbedtls_x509_string_to_names() and
735         * mbedtls_x509_dn_gets(). Accept it for now. */
736        goto exit;
737    }
738    TEST_LE_S(1, ret);
739    TEST_ASSERT(strcmp((char *) out, parsed_name) == 0);
740
741exit:
742    mbedtls_asn1_free_named_data_list(&names);
743
744    parsed_cur = parsed.next;
745    while (parsed_cur != 0) {
746        parsed_prv = parsed_cur;
747        parsed_cur = parsed_cur->next;
748        mbedtls_free(parsed_prv);
749    }
750    USE_PSA_DONE();
751}
752/* END_CASE */
753
754/* BEGIN_CASE depends_on:MBEDTLS_X509_CSR_WRITE_C */
755void x509_set_extension_length_check()
756{
757    int ret = 0;
758
759    mbedtls_x509write_csr ctx;
760    mbedtls_x509write_csr_init(&ctx);
761
762    unsigned char buf[EXT_KEY_USAGE_TMP_BUF_MAX_LENGTH] = { 0 };
763    unsigned char *p = buf + sizeof(buf);
764
765    ret = mbedtls_x509_set_extension(&(ctx.MBEDTLS_PRIVATE(extensions)),
766                                     MBEDTLS_OID_EXTENDED_KEY_USAGE,
767                                     MBEDTLS_OID_SIZE(MBEDTLS_OID_EXTENDED_KEY_USAGE),
768                                     0,
769                                     p,
770                                     SIZE_MAX);
771    TEST_ASSERT(MBEDTLS_ERR_X509_BAD_INPUT_DATA == ret);
772}
773/* END_CASE */
774