summaryrefslogtreecommitdiff
path: root/test/regression/nx_secure_test/nx_secure_x509_key_usage_test.c
blob: b7979a1afc1b376d983227595d550fb0503a2e74 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
/***************************************************************************/
/* Copyright (c) 2024 Microsoft Corporation                                */
/* Copyright (c) 2026 Eclipse ThreadX contributors                         */
/*                                                                         */
/* This program and the accompanying materials are made available under    */
/* the terms of the MIT License which is available at                      */
/* https://opensource.org/licenses/MIT.                                    */
/*                                                                         */
/* SPDX-License-Identifier: MIT                                            */
/***************************************************************************/

#include <stdio.h>

#include "nx_secure_tls_api.h"

#include "tls_test_utility.h"

static TX_THREAD thread_0;

void NX_SECURE_X509_KeyUsageTest();

static void    thread_0_entry(ULONG thread_input);

#define DEMO_STACK_SIZE 2048
static CHAR thread_stack[DEMO_STACK_SIZE];

#ifdef CTEST
void test_application_define(void *first_unused_memory);
void test_application_define(void *first_unused_memory)
#else
void nx_secure_x509_key_usage_test_application_define(void *first_unused_memory)
#endif
{

    /* Create the main thread.  */
    tx_thread_create(&thread_0, "thread 0", thread_0_entry, 0,
                     thread_stack, DEMO_STACK_SIZE,
                     4, 4, TX_NO_TIME_SLICE, TX_AUTO_START);
}

static void    thread_0_entry(ULONG thread_input)
{
    /* Print out test information banner.  */
    printf("NetX Secure Test:   X509 Key Usage Test...............................");

#ifndef NX_SECURE_DISABLE_X509
    NX_SECURE_X509_KeyUsageTest();

    printf("SUCCESS!\n");
#else
    printf("N/A\n");
#endif

    test_control_return(0);
}

#ifndef NX_SECURE_DISABLE_X509

static UCHAR server_packet_buffer[2000];

static NX_PACKET_POOL    pool_0;

#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)


static ULONG             packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];

#include "key_usage_certs.c"

static NX_SECURE_X509_CERT root_ca;
static NX_SECURE_X509_CERT ica_cert;
static NX_SECURE_X509_CERT revoked_cert;
static NX_SECURE_X509_CERT device_cert;

/*  Cryptographic routines. */
static CHAR crypto_metadata[16000];
extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;

/* Buffer space for certificate tests. */
static CHAR ica_buf1[8000];
static CHAR ica_buf2[3000];
static CHAR device_buf1[8000];
static CHAR device_buf2[3000];
static CHAR revoked_buf1[8000];
static CHAR revoked_buf2[3000];

TEST(NX_SECURE_X509, KeyUsageTest)
{

UINT status;
NX_PACKET *packet;
NX_SECURE_TLS_SESSION session;
UCHAR header_buffer[6];
UCHAR header_data[6];
USHORT header_size;
UINT message_length;
USHORT message_type;
const NX_SECURE_TLS_CIPHERSUITE_INFO *ciphersuite;
NX_SECURE_X509_CERTIFICATE_STORE *store;
NX_SECURE_X509_CERT **remote_certs;

    memset(&session, 0, sizeof(NX_SECURE_TLS_SESSION));

    status =  nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536,  (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
    EXPECT_EQ(NX_SUCCESS, status);

    status = _nx_secure_tls_session_reset(&session);
    EXPECT_EQ(NX_SUCCESS, status);

    /* Initialize the server session. */
    /* Create a TLS session.  */
    status =  nx_secure_tls_session_create(&session,
                                           &nx_crypto_tls_ciphers,
                                           crypto_metadata,
                                           sizeof(crypto_metadata));
    EXPECT_EQ(NX_SUCCESS, status);

    /* Setup our packet reassembly buffer. */
    status = _nx_secure_tls_session_packet_buffer_set(&session, server_packet_buffer, sizeof(server_packet_buffer));
    EXPECT_EQ(NX_SUCCESS, status);

    /* Setup TLS session as if we were in the middle of a handshake. */
    session.nx_secure_tls_protocol_version = NX_SECURE_TLS_VERSION_TLS_1_2;

    /* Initialize our certificates - NOTE: We don't need private keys because we aren't doing anything but chain verification. */
    status = _nx_secure_x509_certificate_initialize(&ica_cert, ica_cert_der, ica_cert_der_len, NX_NULL, 0, NX_NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
    EXPECT_EQ(NX_SUCCESS, status);
    status = _nx_secure_x509_certificate_initialize(&root_ca, root_ca_cert_der, root_ca_cert_der_len, NX_NULL, 0, NX_NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
    EXPECT_EQ(NX_SUCCESS, status);
    status = _nx_secure_x509_certificate_initialize(&device_cert, device_cert_der, device_cert_der_len, NX_NULL, 0, NX_NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
    EXPECT_EQ(NX_SUCCESS, status);
    status = _nx_secure_x509_certificate_initialize(&revoked_cert, revoked_cert_der, revoked_cert_der_len, NX_NULL, 0, NX_NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
    EXPECT_EQ(NX_SUCCESS, status);

    /* Add certificates to session. */
    status = _nx_secure_tls_trusted_certificate_add(&session, &root_ca);
    EXPECT_EQ(NX_SUCCESS, status);

    store = &session.nx_secure_tls_credentials.nx_secure_tls_certificate_store;
    remote_certs = &session.nx_secure_tls_credentials.nx_secure_tls_certificate_store.nx_secure_x509_remote_certificates;

    /* Add remote certificates as if we received a chain. */
    status = _nx_secure_x509_certificate_list_add(remote_certs, &ica_cert, NX_TRUE);
    EXPECT_EQ(NX_SUCCESS, status);
    ica_cert.nx_secure_x509_public_cipher_metadata_area = ica_buf1;
    ica_cert.nx_secure_x509_public_cipher_metadata_size = sizeof(ica_buf1);
    ica_cert.nx_secure_x509_hash_metadata_area = ica_buf2;
    ica_cert.nx_secure_x509_hash_metadata_size = sizeof(ica_buf2);
    ica_cert.nx_secure_x509_cipher_table = session.nx_secure_tls_crypto_table -> nx_secure_tls_x509_cipher_table;
    ica_cert.nx_secure_x509_cipher_table_size = session.nx_secure_tls_crypto_table -> nx_secure_tls_x509_cipher_table_size;

    status = _nx_secure_x509_certificate_list_add(remote_certs, &device_cert, NX_TRUE);
    EXPECT_EQ(NX_SUCCESS, status);
    device_cert.nx_secure_x509_public_cipher_metadata_area = device_buf1;
    device_cert.nx_secure_x509_public_cipher_metadata_size = sizeof(device_buf1);
    device_cert.nx_secure_x509_hash_metadata_area = device_buf2;
    device_cert.nx_secure_x509_hash_metadata_size = sizeof(device_buf2);
    device_cert.nx_secure_x509_cipher_table = session.nx_secure_tls_crypto_table -> nx_secure_tls_x509_cipher_table;
    device_cert.nx_secure_x509_cipher_table_size = session.nx_secure_tls_crypto_table -> nx_secure_tls_x509_cipher_table_size;


    status = _nx_secure_x509_certificate_list_add(remote_certs, &revoked_cert, NX_TRUE);
    EXPECT_EQ(NX_SUCCESS, status);
    revoked_cert.nx_secure_x509_public_cipher_metadata_area = revoked_buf1;
    revoked_cert.nx_secure_x509_public_cipher_metadata_size = sizeof(revoked_buf1);
    revoked_cert.nx_secure_x509_hash_metadata_area = revoked_buf2;
    revoked_cert.nx_secure_x509_hash_metadata_size = sizeof(revoked_buf2);
    revoked_cert.nx_secure_x509_cipher_table = session.nx_secure_tls_crypto_table -> nx_secure_tls_x509_cipher_table;
    revoked_cert.nx_secure_x509_cipher_table_size = session.nx_secure_tls_crypto_table -> nx_secure_tls_x509_cipher_table_size;


    /* Now do some chain verifications. */

    /* Check "device cert" - should FAIL because ICA does not have proper KeyUsage. */
    status = _nx_secure_x509_certificate_chain_verify(store, &device_cert, 0);
    EXPECT_EQ(NX_SECURE_X509_KEY_USAGE_ERROR, status);

    /* Check "revoked cert" - should PASS because root CA DOES have proper KeyUsage. */
    status = _nx_secure_x509_certificate_chain_verify(store, &revoked_cert, 0);
    EXPECT_EQ(NX_SUCCESS, status);

    /* Check CRLs. */

#ifndef NX_SECURE_X509_DISABLE_CRL
    /* Root CRL is good because root CA has proper KeyUsage, but revoked_cert is revoked. */
    status = _nx_secure_x509_crl_revocation_check(root_crl_der, root_crl_der_len, store, &revoked_cert);
    EXPECT_EQ(NX_SECURE_X509_CRL_CERTIFICATE_REVOKED, status);

    /* The ICA CRL is no good because ICA has improper KeyUsage. device_cert is OK, but CRL should fail. */
    status = nx_secure_x509_crl_revocation_check(ica_crl_der, ica_crl_der_len, store, &device_cert);
    EXPECT_EQ(NX_SECURE_X509_KEY_USAGE_ERROR, status);
#endif

    nx_secure_tls_session_delete(&session);

}
#endif