blob: bfc3e062bd4ab40139caefc594de2ecc11a972ba [file] [log] [blame]
Raef Coles8ff6df52021-07-21 12:42:15 +01001/* BEGIN_HEADER */
2#include "mbedtls/lms.h"
Raef Coles8ff6df52021-07-21 12:42:15 +01003
4/* END_HEADER */
5
6/* BEGIN_DEPENDENCIES
Raef Coles1b43a742022-10-13 09:44:27 +01007 * depends_on:MBEDTLS_LMS_C
Raef Coles8ff6df52021-07-21 12:42:15 +01008 * END_DEPENDENCIES
9 */
10
Raef Coles5127e852022-10-07 10:35:56 +010011/* BEGIN_CASE depends_on:MBEDTLS_LMS_PRIVATE */
Gilles Peskine449bd832023-01-11 14:50:10 +010012void lms_sign_verify_test(data_t *msg, data_t *seed)
Raef Coles8ff6df52021-07-21 12:42:15 +010013{
Raef Coles01c71a12022-08-31 15:55:00 +010014 mbedtls_lms_public_t pub_ctx;
15 mbedtls_lms_private_t priv_ctx;
Raef Colese9479a02022-09-01 16:06:35 +010016 unsigned char sig[MBEDTLS_LMS_SIG_LEN(MBEDTLS_LMS_SHA256_M32_H10, MBEDTLS_LMOTS_SHA256_N32_W8)];
Raef Coles8ff6df52021-07-21 12:42:15 +010017
Gilles Peskine449bd832023-01-11 14:50:10 +010018 mbedtls_lms_public_init(&pub_ctx);
19 mbedtls_lms_private_init(&priv_ctx);
Raef Coles8ff6df52021-07-21 12:42:15 +010020
Raef Colesf5919e22022-09-02 16:05:10 +010021 /* Allocation failure isn't a test failure, since it likely just means
22 * there's not enough memory to run the test.
23 */
Gilles Peskine449bd832023-01-11 14:50:10 +010024 TEST_EQUAL(mbedtls_lms_generate_private_key(&priv_ctx, MBEDTLS_LMS_SHA256_M32_H10,
25 MBEDTLS_LMOTS_SHA256_N32_W8,
26 mbedtls_test_rnd_std_rand, NULL,
27 seed->x, seed->len), 0);
Raef Coles8ff6df52021-07-21 12:42:15 +010028
Gilles Peskine449bd832023-01-11 14:50:10 +010029 TEST_EQUAL(mbedtls_lms_calculate_public_key(&pub_ctx, &priv_ctx), 0);
Raef Coles8ff6df52021-07-21 12:42:15 +010030
Gilles Peskine449bd832023-01-11 14:50:10 +010031 TEST_EQUAL(mbedtls_lms_sign(&priv_ctx, mbedtls_test_rnd_std_rand, NULL,
32 msg->x, msg->len, sig, sizeof(sig),
33 NULL), 0);
Raef Coles8ff6df52021-07-21 12:42:15 +010034
Gilles Peskine449bd832023-01-11 14:50:10 +010035 TEST_EQUAL(mbedtls_lms_verify(&pub_ctx, msg->x, msg->len, sig,
36 sizeof(sig)), 0);
Raef Coles8ff6df52021-07-21 12:42:15 +010037
38exit:
Gilles Peskine449bd832023-01-11 14:50:10 +010039 mbedtls_lms_public_free(&pub_ctx);
40 mbedtls_lms_private_free(&priv_ctx);
Raef Coles8ff6df52021-07-21 12:42:15 +010041}
42/* END_CASE */
43
Raef Coles5127e852022-10-07 10:35:56 +010044/* BEGIN_CASE depends_on:MBEDTLS_LMS_PRIVATE */
Gilles Peskine449bd832023-01-11 14:50:10 +010045void lms_sign_verify_null_msg_test(data_t *seed)
Raef Coles9c9027b2022-09-02 18:26:31 +010046{
47 mbedtls_lms_public_t pub_ctx;
48 mbedtls_lms_private_t priv_ctx;
49 unsigned char sig[MBEDTLS_LMS_SIG_LEN(MBEDTLS_LMS_SHA256_M32_H10, MBEDTLS_LMOTS_SHA256_N32_W8)];
Raef Coles9c9027b2022-09-02 18:26:31 +010050
Gilles Peskine449bd832023-01-11 14:50:10 +010051 mbedtls_lms_public_init(&pub_ctx);
52 mbedtls_lms_private_init(&priv_ctx);
Raef Coles9c9027b2022-09-02 18:26:31 +010053
54 /* Allocation failure isn't a test failure, since it likely just means
55 * there's not enough memory to run the test.
56 */
Gilles Peskine449bd832023-01-11 14:50:10 +010057 TEST_EQUAL(mbedtls_lms_generate_private_key(&priv_ctx, MBEDTLS_LMS_SHA256_M32_H10,
58 MBEDTLS_LMOTS_SHA256_N32_W8,
59 mbedtls_test_rnd_std_rand, NULL,
60 seed->x, seed->len), 0);
Raef Coles9c9027b2022-09-02 18:26:31 +010061
Gilles Peskine449bd832023-01-11 14:50:10 +010062 TEST_EQUAL(mbedtls_lms_calculate_public_key(&pub_ctx, &priv_ctx), 0);
Raef Coles9c9027b2022-09-02 18:26:31 +010063
Gilles Peskine449bd832023-01-11 14:50:10 +010064 TEST_EQUAL(mbedtls_lms_sign(&priv_ctx, mbedtls_test_rnd_std_rand, NULL,
65 NULL, 0, sig, sizeof(sig),
66 NULL), 0);
Raef Coles9c9027b2022-09-02 18:26:31 +010067
Gilles Peskine449bd832023-01-11 14:50:10 +010068 TEST_EQUAL(mbedtls_lms_verify(&pub_ctx, NULL, 0, sig,
69 sizeof(sig)), 0);
Raef Coles9c9027b2022-09-02 18:26:31 +010070
71exit:
Gilles Peskine449bd832023-01-11 14:50:10 +010072 mbedtls_lms_public_free(&pub_ctx);
73 mbedtls_lms_private_free(&priv_ctx);
Raef Coles9c9027b2022-09-02 18:26:31 +010074}
75/* END_CASE */
76
77/* BEGIN_CASE */
Gilles Peskine449bd832023-01-11 14:50:10 +010078void lms_verify_test(data_t *msg, data_t *sig, data_t *pub_key,
79 int expected_rc)
Raef Coles8ff6df52021-07-21 12:42:15 +010080{
Raef Coles01c71a12022-08-31 15:55:00 +010081 mbedtls_lms_public_t ctx;
Raef Coles0dc604e2022-10-10 17:35:26 +010082 unsigned int size;
83 unsigned char *tmp_sig = NULL;
Raef Coles8ff6df52021-07-21 12:42:15 +010084
Gilles Peskine449bd832023-01-11 14:50:10 +010085 mbedtls_lms_public_init(&ctx);
Raef Coles8ff6df52021-07-21 12:42:15 +010086
Gilles Peskine449bd832023-01-11 14:50:10 +010087 TEST_EQUAL(mbedtls_lms_import_public_key(&ctx, pub_key->x, pub_key->len), 0);
Raef Coles8ff6df52021-07-21 12:42:15 +010088
Gilles Peskine449bd832023-01-11 14:50:10 +010089 TEST_EQUAL(mbedtls_lms_verify(&ctx, msg->x, msg->len, sig->x, sig->len), expected_rc);
Raef Coles0dc604e2022-10-10 17:35:26 +010090
91 /* Test negative cases if the input data is valid */
Gilles Peskine449bd832023-01-11 14:50:10 +010092 if (expected_rc == 0) {
93 if (msg->len >= 1) {
Raef Coles90e13fc2022-10-11 12:48:18 +010094 /* Altering first message byte must cause verification failure */
95 msg->x[0] ^= 1;
Gilles Peskine449bd832023-01-11 14:50:10 +010096 TEST_EQUAL(mbedtls_lms_verify(&ctx, msg->x, msg->len, sig->x, sig->len),
Raef Coles90e13fc2022-10-11 12:48:18 +010097 MBEDTLS_ERR_LMS_VERIFY_FAILED);
98 msg->x[0] ^= 1;
Raef Coles0dc604e2022-10-10 17:35:26 +010099
Raef Coles90e13fc2022-10-11 12:48:18 +0100100 /* Altering last message byte must cause verification failure */
101 msg->x[msg->len - 1] ^= 1;
Gilles Peskine449bd832023-01-11 14:50:10 +0100102 TEST_EQUAL(mbedtls_lms_verify(&ctx, msg->x, msg->len, sig->x, sig->len),
Raef Coles90e13fc2022-10-11 12:48:18 +0100103 MBEDTLS_ERR_LMS_VERIFY_FAILED);
104 msg->x[msg->len - 1] ^= 1;
105 }
Raef Coles0dc604e2022-10-10 17:35:26 +0100106
Gilles Peskine449bd832023-01-11 14:50:10 +0100107 if (sig->len >= 1) {
Raef Coles90e13fc2022-10-11 12:48:18 +0100108 /* Altering first signature byte must cause verification failure */
109 sig->x[0] ^= 1;
Gilles Peskine449bd832023-01-11 14:50:10 +0100110 TEST_EQUAL(mbedtls_lms_verify(&ctx, msg->x, msg->len, sig->x, sig->len),
Raef Coles90e13fc2022-10-11 12:48:18 +0100111 MBEDTLS_ERR_LMS_VERIFY_FAILED);
112 sig->x[0] ^= 1;
Raef Coles0dc604e2022-10-10 17:35:26 +0100113
Raef Coles90e13fc2022-10-11 12:48:18 +0100114 /* Altering last signature byte must cause verification failure */
115 sig->x[sig->len - 1] ^= 1;
Gilles Peskine449bd832023-01-11 14:50:10 +0100116 TEST_EQUAL(mbedtls_lms_verify(&ctx, msg->x, msg->len, sig->x, sig->len),
Raef Coles90e13fc2022-10-11 12:48:18 +0100117 MBEDTLS_ERR_LMS_VERIFY_FAILED);
118 sig->x[sig->len - 1] ^= 1;
119 }
Raef Coles0dc604e2022-10-10 17:35:26 +0100120
121 /* Signatures of all sizes must not verify, whether shorter or longer */
Gilles Peskine449bd832023-01-11 14:50:10 +0100122 for (size = 0; size < sig->len; size++) {
123 if (size == sig->len) {
Raef Coles0dc604e2022-10-10 17:35:26 +0100124 continue;
Gilles Peskine449bd832023-01-11 14:50:10 +0100125 }
Raef Coles0dc604e2022-10-10 17:35:26 +0100126
Gilles Peskine449bd832023-01-11 14:50:10 +0100127 ASSERT_ALLOC(tmp_sig, size);
128 if (tmp_sig != NULL) {
129 memcpy(tmp_sig, sig->x, MIN(size, sig->len));
130 }
Raef Coles0dc604e2022-10-10 17:35:26 +0100131
Gilles Peskine449bd832023-01-11 14:50:10 +0100132 TEST_EQUAL(mbedtls_lms_verify(&ctx, msg->x, msg->len, tmp_sig, size),
Raef Coles0dc604e2022-10-10 17:35:26 +0100133 MBEDTLS_ERR_LMS_VERIFY_FAILED);
Gilles Peskine449bd832023-01-11 14:50:10 +0100134 mbedtls_free(tmp_sig);
Raef Coles0dc604e2022-10-10 17:35:26 +0100135 tmp_sig = NULL;
136 }
137 }
Raef Coles8ff6df52021-07-21 12:42:15 +0100138
139exit:
Gilles Peskine449bd832023-01-11 14:50:10 +0100140 mbedtls_free(tmp_sig);
141 mbedtls_lms_public_free(&ctx);
Raef Coles8ff6df52021-07-21 12:42:15 +0100142}
143/* END_CASE */
144
Raef Coles370cc432022-10-07 16:07:33 +0100145/* BEGIN_CASE */
Gilles Peskine449bd832023-01-11 14:50:10 +0100146void lms_import_export_test(data_t *pub_key, int expected_import_rc)
Raef Coles8ff6df52021-07-21 12:42:15 +0100147{
Raef Coles01c71a12022-08-31 15:55:00 +0100148 mbedtls_lms_public_t ctx;
Raef Colesd6adcb62022-10-11 15:34:56 +0100149 size_t exported_pub_key_buf_size = 0;
150 size_t exported_pub_key_size = 0;
151 unsigned char *exported_pub_key = NULL;
Raef Coles8ff6df52021-07-21 12:42:15 +0100152
Raef Colesbe3bdd82022-10-07 12:04:24 +0100153 mbedtls_lms_public_init(&ctx);
Gilles Peskine449bd832023-01-11 14:50:10 +0100154 TEST_EQUAL(mbedtls_lms_import_public_key(&ctx, pub_key->x, pub_key->len),
155 expected_import_rc);
Raef Coles8ff6df52021-07-21 12:42:15 +0100156
Gilles Peskine449bd832023-01-11 14:50:10 +0100157 if (expected_import_rc == 0) {
Raef Colesd6adcb62022-10-11 15:34:56 +0100158 exported_pub_key_buf_size = MBEDTLS_LMS_PUBLIC_KEY_LEN(MBEDTLS_LMS_SHA256_M32_H10);
Gilles Peskine449bd832023-01-11 14:50:10 +0100159 ASSERT_ALLOC(exported_pub_key, exported_pub_key_buf_size);
Raef Colesd6adcb62022-10-11 15:34:56 +0100160
Gilles Peskine449bd832023-01-11 14:50:10 +0100161 TEST_EQUAL(mbedtls_lms_export_public_key(&ctx, exported_pub_key,
162 exported_pub_key_buf_size,
163 &exported_pub_key_size), 0);
Raef Colesd6adcb62022-10-11 15:34:56 +0100164
Gilles Peskine449bd832023-01-11 14:50:10 +0100165 TEST_EQUAL(exported_pub_key_size,
166 MBEDTLS_LMS_PUBLIC_KEY_LEN(MBEDTLS_LMS_SHA256_M32_H10));
167 ASSERT_COMPARE(pub_key->x, pub_key->len,
168 exported_pub_key, exported_pub_key_size);
Raef Colesd6adcb62022-10-11 15:34:56 +0100169 mbedtls_free(exported_pub_key);
170 exported_pub_key = NULL;
171
172 /* Export into too-small buffer should fail */
173 exported_pub_key_buf_size = MBEDTLS_LMS_PUBLIC_KEY_LEN(MBEDTLS_LMS_SHA256_M32_H10) - 1;
Gilles Peskine449bd832023-01-11 14:50:10 +0100174 ASSERT_ALLOC(exported_pub_key, exported_pub_key_buf_size);
175 TEST_EQUAL(mbedtls_lms_export_public_key(&ctx, exported_pub_key,
176 exported_pub_key_buf_size, NULL),
177 MBEDTLS_ERR_LMS_BUFFER_TOO_SMALL);
Raef Colesd6adcb62022-10-11 15:34:56 +0100178 mbedtls_free(exported_pub_key);
179 exported_pub_key = NULL;
Raef Coles6b2c5732022-10-13 09:41:39 +0100180
181 /* Export into too-large buffer should succeed */
182 exported_pub_key_buf_size = MBEDTLS_LMS_PUBLIC_KEY_LEN(MBEDTLS_LMS_SHA256_M32_H10) + 1;
Gilles Peskine449bd832023-01-11 14:50:10 +0100183 ASSERT_ALLOC(exported_pub_key, exported_pub_key_buf_size);
184 TEST_EQUAL(mbedtls_lms_export_public_key(&ctx, exported_pub_key,
185 exported_pub_key_buf_size,
186 &exported_pub_key_size),
187 0);
188 ASSERT_COMPARE(pub_key->x, pub_key->len,
189 exported_pub_key, exported_pub_key_size);
Raef Coles6b2c5732022-10-13 09:41:39 +0100190 mbedtls_free(exported_pub_key);
191 exported_pub_key = NULL;
Raef Colesd6adcb62022-10-11 15:34:56 +0100192 }
Raef Coles8ff6df52021-07-21 12:42:15 +0100193
194exit:
Gilles Peskine449bd832023-01-11 14:50:10 +0100195 mbedtls_free(exported_pub_key);
196 mbedtls_lms_public_free(&ctx);
Raef Coles8ff6df52021-07-21 12:42:15 +0100197}
198/* END_CASE */