]>
Commit | Line | Data |
---|---|---|
453dfd8d | 1 | /* |
da1c088f | 2 | * Copyright 2016-2023 The OpenSSL Project Authors. All Rights Reserved. |
453dfd8d | 3 | * |
909f1a2e | 4 | * Licensed under the Apache License 2.0 (the "License"). You may not use |
440e5d80 RS |
5 | * this file except in compliance with the License. You can obtain a copy |
6 | * in the file LICENSE in the source distribution or at | |
453dfd8d | 7 | * https://www.openssl.org/source/license.html |
453dfd8d EK |
8 | */ |
9 | ||
10 | #include <string.h> | |
11 | ||
12 | #include <openssl/e_os2.h> | |
13 | #include <openssl/crypto.h> | |
14 | ||
176db6dc | 15 | #include "internal/nelem.h" |
453dfd8d | 16 | #include "ssl_test_ctx.h" |
20f8bc72 | 17 | #include "../testutil.h" |
453dfd8d | 18 | |
e0421bd8 | 19 | static const int default_app_data_size = 256; |
6dc99745 EK |
20 | /* Default set to be as small as possible to exercise fragmentation. */ |
21 | static const int default_max_fragment_size = 512; | |
e0421bd8 EK |
22 | |
23 | static int parse_boolean(const char *value, int *result) | |
24 | { | |
fba140c7 | 25 | if (OPENSSL_strcasecmp(value, "Yes") == 0) { |
e0421bd8 EK |
26 | *result = 1; |
27 | return 1; | |
28 | } | |
fba140c7 | 29 | else if (OPENSSL_strcasecmp(value, "No") == 0) { |
e0421bd8 EK |
30 | *result = 0; |
31 | return 1; | |
32 | } | |
019e47ce | 33 | TEST_error("parse_boolean given: '%s'", value); |
e0421bd8 EK |
34 | return 0; |
35 | } | |
36 | ||
37 | #define IMPLEMENT_SSL_TEST_BOOL_OPTION(struct_type, name, field) \ | |
38 | static int parse_##name##_##field(struct_type *ctx, const char *value) \ | |
39 | { \ | |
40 | return parse_boolean(value, &ctx->field); \ | |
41 | } | |
42 | ||
43 | #define IMPLEMENT_SSL_TEST_STRING_OPTION(struct_type, name, field) \ | |
44 | static int parse_##name##_##field(struct_type *ctx, const char *value) \ | |
45 | { \ | |
46 | OPENSSL_free(ctx->field); \ | |
47 | ctx->field = OPENSSL_strdup(value); \ | |
019e47ce | 48 | return TEST_ptr(ctx->field); \ |
e0421bd8 EK |
49 | } |
50 | ||
51 | #define IMPLEMENT_SSL_TEST_INT_OPTION(struct_type, name, field) \ | |
52 | static int parse_##name##_##field(struct_type *ctx, const char *value) \ | |
53 | { \ | |
54 | ctx->field = atoi(value); \ | |
55 | return 1; \ | |
56 | } | |
57 | ||
453dfd8d EK |
58 | /* True enums and other test configuration values that map to an int. */ |
59 | typedef struct { | |
60 | const char *name; | |
61 | int value; | |
62 | } test_enum; | |
63 | ||
64 | ||
65 | __owur static int parse_enum(const test_enum *enums, size_t num_enums, | |
66 | int *value, const char *name) | |
67 | { | |
68 | size_t i; | |
69 | for (i = 0; i < num_enums; i++) { | |
70 | if (strcmp(enums[i].name, name) == 0) { | |
71 | *value = enums[i].value; | |
72 | return 1; | |
73 | } | |
74 | } | |
75 | return 0; | |
76 | } | |
77 | ||
78 | static const char *enum_name(const test_enum *enums, size_t num_enums, | |
79 | int value) | |
80 | { | |
81 | size_t i; | |
82 | for (i = 0; i < num_enums; i++) { | |
83 | if (enums[i].value == value) { | |
84 | return enums[i].name; | |
85 | } | |
86 | } | |
87 | return "InvalidValue"; | |
88 | } | |
89 | ||
90 | ||
cc22cd54 | 91 | /* ExpectedResult */ |
453dfd8d EK |
92 | |
93 | static const test_enum ssl_test_results[] = { | |
94 | {"Success", SSL_TEST_SUCCESS}, | |
95 | {"ServerFail", SSL_TEST_SERVER_FAIL}, | |
96 | {"ClientFail", SSL_TEST_CLIENT_FAIL}, | |
97 | {"InternalError", SSL_TEST_INTERNAL_ERROR}, | |
df0fed9a | 98 | {"FirstHandshakeFailed", SSL_TEST_FIRST_HANDSHAKE_FAILED}, |
453dfd8d EK |
99 | }; |
100 | ||
101 | __owur static int parse_expected_result(SSL_TEST_CTX *test_ctx, const char *value) | |
102 | { | |
103 | int ret_value; | |
104 | if (!parse_enum(ssl_test_results, OSSL_NELEM(ssl_test_results), | |
105 | &ret_value, value)) { | |
106 | return 0; | |
107 | } | |
108 | test_ctx->expected_result = ret_value; | |
109 | return 1; | |
110 | } | |
111 | ||
a263f320 | 112 | const char *ssl_test_result_name(ssl_test_result_t result) |
453dfd8d EK |
113 | { |
114 | return enum_name(ssl_test_results, OSSL_NELEM(ssl_test_results), result); | |
115 | } | |
116 | ||
cc22cd54 | 117 | /* ExpectedClientAlert / ExpectedServerAlert */ |
453dfd8d EK |
118 | |
119 | static const test_enum ssl_alerts[] = { | |
120 | {"UnknownCA", SSL_AD_UNKNOWN_CA}, | |
a263f320 | 121 | {"HandshakeFailure", SSL_AD_HANDSHAKE_FAILURE}, |
d2b23cd2 | 122 | {"UnrecognizedName", SSL_AD_UNRECOGNIZED_NAME}, |
f4752e88 | 123 | {"NoRenegotiation", SSL_AD_NO_RENEGOTIATION}, |
ce2cdac2 EK |
124 | {"BadCertificate", SSL_AD_BAD_CERTIFICATE}, |
125 | {"NoApplicationProtocol", SSL_AD_NO_APPLICATION_PROTOCOL}, | |
43a0f273 | 126 | {"CertificateRequired", SSL_AD_CERTIFICATE_REQUIRED}, |
453dfd8d EK |
127 | }; |
128 | ||
129 | __owur static int parse_alert(int *alert, const char *value) | |
130 | { | |
131 | return parse_enum(ssl_alerts, OSSL_NELEM(ssl_alerts), alert, value); | |
132 | } | |
133 | ||
134 | __owur static int parse_client_alert(SSL_TEST_CTX *test_ctx, const char *value) | |
135 | { | |
9f48bbac | 136 | return parse_alert(&test_ctx->expected_client_alert, value); |
453dfd8d EK |
137 | } |
138 | ||
139 | __owur static int parse_server_alert(SSL_TEST_CTX *test_ctx, const char *value) | |
140 | { | |
9f48bbac | 141 | return parse_alert(&test_ctx->expected_server_alert, value); |
453dfd8d EK |
142 | } |
143 | ||
144 | const char *ssl_alert_name(int alert) | |
145 | { | |
146 | return enum_name(ssl_alerts, OSSL_NELEM(ssl_alerts), alert); | |
147 | } | |
148 | ||
9f48bbac | 149 | /* ExpectedProtocol */ |
453dfd8d EK |
150 | |
151 | static const test_enum ssl_protocols[] = { | |
582a17d6 | 152 | {"TLSv1.3", TLS1_3_VERSION}, |
453dfd8d EK |
153 | {"TLSv1.2", TLS1_2_VERSION}, |
154 | {"TLSv1.1", TLS1_1_VERSION}, | |
155 | {"TLSv1", TLS1_VERSION}, | |
156 | {"SSLv3", SSL3_VERSION}, | |
74726750 EK |
157 | {"DTLSv1", DTLS1_VERSION}, |
158 | {"DTLSv1.2", DTLS1_2_VERSION}, | |
453dfd8d EK |
159 | }; |
160 | ||
161 | __owur static int parse_protocol(SSL_TEST_CTX *test_ctx, const char *value) | |
162 | { | |
163 | return parse_enum(ssl_protocols, OSSL_NELEM(ssl_protocols), | |
9f48bbac | 164 | &test_ctx->expected_protocol, value); |
453dfd8d EK |
165 | } |
166 | ||
167 | const char *ssl_protocol_name(int protocol) | |
168 | { | |
169 | return enum_name(ssl_protocols, OSSL_NELEM(ssl_protocols), protocol); | |
170 | } | |
171 | ||
cc22cd54 | 172 | /* VerifyCallback */ |
a263f320 EK |
173 | |
174 | static const test_enum ssl_verify_callbacks[] = { | |
175 | {"None", SSL_TEST_VERIFY_NONE}, | |
176 | {"AcceptAll", SSL_TEST_VERIFY_ACCEPT_ALL}, | |
0c3eb279 | 177 | {"RetryOnce", SSL_TEST_VERIFY_RETRY_ONCE}, |
a263f320 EK |
178 | {"RejectAll", SSL_TEST_VERIFY_REJECT_ALL}, |
179 | }; | |
180 | ||
9f48bbac | 181 | __owur static int parse_client_verify_callback(SSL_TEST_CLIENT_CONF *client_conf, |
da085d27 | 182 | const char *value) |
a263f320 EK |
183 | { |
184 | int ret_value; | |
0c3eb279 | 185 | |
a263f320 EK |
186 | if (!parse_enum(ssl_verify_callbacks, OSSL_NELEM(ssl_verify_callbacks), |
187 | &ret_value, value)) { | |
188 | return 0; | |
189 | } | |
9f48bbac | 190 | client_conf->verify_callback = ret_value; |
a263f320 EK |
191 | return 1; |
192 | } | |
193 | ||
194 | const char *ssl_verify_callback_name(ssl_verify_callback_t callback) | |
195 | { | |
196 | return enum_name(ssl_verify_callbacks, OSSL_NELEM(ssl_verify_callbacks), | |
197 | callback); | |
198 | } | |
199 | ||
5c753de6 | 200 | /* ServerName */ |
5c753de6 TS |
201 | |
202 | static const test_enum ssl_servername[] = { | |
81fc33c9 | 203 | {"None", SSL_TEST_SERVERNAME_NONE}, |
5c753de6 TS |
204 | {"server1", SSL_TEST_SERVERNAME_SERVER1}, |
205 | {"server2", SSL_TEST_SERVERNAME_SERVER2}, | |
d2b23cd2 | 206 | {"invalid", SSL_TEST_SERVERNAME_INVALID}, |
5c753de6 TS |
207 | }; |
208 | ||
9f48bbac | 209 | __owur static int parse_servername(SSL_TEST_CLIENT_CONF *client_conf, |
5c753de6 TS |
210 | const char *value) |
211 | { | |
212 | int ret_value; | |
213 | if (!parse_enum(ssl_servername, OSSL_NELEM(ssl_servername), | |
214 | &ret_value, value)) { | |
215 | return 0; | |
216 | } | |
9f48bbac | 217 | client_conf->servername = ret_value; |
5c753de6 TS |
218 | return 1; |
219 | } | |
220 | ||
d2b23cd2 EK |
221 | __owur static int parse_expected_servername(SSL_TEST_CTX *test_ctx, |
222 | const char *value) | |
223 | { | |
224 | int ret_value; | |
225 | if (!parse_enum(ssl_servername, OSSL_NELEM(ssl_servername), | |
226 | &ret_value, value)) { | |
227 | return 0; | |
228 | } | |
229 | test_ctx->expected_servername = ret_value; | |
230 | return 1; | |
231 | } | |
232 | ||
5c753de6 TS |
233 | const char *ssl_servername_name(ssl_servername_t server) |
234 | { | |
235 | return enum_name(ssl_servername, OSSL_NELEM(ssl_servername), | |
236 | server); | |
237 | } | |
238 | ||
9f48bbac | 239 | /* ServerNameCallback */ |
d2b23cd2 EK |
240 | |
241 | static const test_enum ssl_servername_callbacks[] = { | |
242 | {"None", SSL_TEST_SERVERNAME_CB_NONE}, | |
243 | {"IgnoreMismatch", SSL_TEST_SERVERNAME_IGNORE_MISMATCH}, | |
244 | {"RejectMismatch", SSL_TEST_SERVERNAME_REJECT_MISMATCH}, | |
a9c0d8be DB |
245 | {"ClientHelloIgnoreMismatch", |
246 | SSL_TEST_SERVERNAME_CLIENT_HELLO_IGNORE_MISMATCH}, | |
247 | {"ClientHelloRejectMismatch", | |
248 | SSL_TEST_SERVERNAME_CLIENT_HELLO_REJECT_MISMATCH}, | |
249 | {"ClientHelloNoV12", SSL_TEST_SERVERNAME_CLIENT_HELLO_NO_V12}, | |
d2b23cd2 EK |
250 | }; |
251 | ||
9f48bbac EK |
252 | __owur static int parse_servername_callback(SSL_TEST_SERVER_CONF *server_conf, |
253 | const char *value) | |
d2b23cd2 EK |
254 | { |
255 | int ret_value; | |
256 | if (!parse_enum(ssl_servername_callbacks, | |
257 | OSSL_NELEM(ssl_servername_callbacks), &ret_value, value)) { | |
258 | return 0; | |
259 | } | |
9f48bbac | 260 | server_conf->servername_callback = ret_value; |
d2b23cd2 EK |
261 | return 1; |
262 | } | |
263 | ||
264 | const char *ssl_servername_callback_name(ssl_servername_callback_t callback) | |
265 | { | |
266 | return enum_name(ssl_servername_callbacks, | |
267 | OSSL_NELEM(ssl_servername_callbacks), callback); | |
268 | } | |
269 | ||
5c753de6 | 270 | /* SessionTicketExpected */ |
5c753de6 | 271 | |
81fc33c9 | 272 | static const test_enum ssl_session_ticket[] = { |
5c753de6 TS |
273 | {"Ignore", SSL_TEST_SESSION_TICKET_IGNORE}, |
274 | {"Yes", SSL_TEST_SESSION_TICKET_YES}, | |
275 | {"No", SSL_TEST_SESSION_TICKET_NO}, | |
5c753de6 TS |
276 | }; |
277 | ||
81fc33c9 | 278 | __owur static int parse_session_ticket(SSL_TEST_CTX *test_ctx, const char *value) |
5c753de6 TS |
279 | { |
280 | int ret_value; | |
81fc33c9 | 281 | if (!parse_enum(ssl_session_ticket, OSSL_NELEM(ssl_session_ticket), |
5c753de6 TS |
282 | &ret_value, value)) { |
283 | return 0; | |
284 | } | |
285 | test_ctx->session_ticket_expected = ret_value; | |
286 | return 1; | |
287 | } | |
288 | ||
81fc33c9 | 289 | const char *ssl_session_ticket_name(ssl_session_ticket_t server) |
5c753de6 | 290 | { |
81fc33c9 EK |
291 | return enum_name(ssl_session_ticket, |
292 | OSSL_NELEM(ssl_session_ticket), | |
5c753de6 TS |
293 | server); |
294 | } | |
453dfd8d | 295 | |
439db0c9 MC |
296 | /* CompressionExpected */ |
297 | ||
b6611753 | 298 | IMPLEMENT_SSL_TEST_BOOL_OPTION(SSL_TEST_CTX, test, compression_expected) |
439db0c9 | 299 | |
a84e5c9a TS |
300 | /* SessionIdExpected */ |
301 | ||
302 | static const test_enum ssl_session_id[] = { | |
303 | {"Ignore", SSL_TEST_SESSION_ID_IGNORE}, | |
304 | {"Yes", SSL_TEST_SESSION_ID_YES}, | |
305 | {"No", SSL_TEST_SESSION_ID_NO}, | |
306 | }; | |
307 | ||
308 | __owur static int parse_session_id(SSL_TEST_CTX *test_ctx, const char *value) | |
309 | { | |
310 | int ret_value; | |
311 | if (!parse_enum(ssl_session_id, OSSL_NELEM(ssl_session_id), | |
312 | &ret_value, value)) { | |
313 | return 0; | |
314 | } | |
315 | test_ctx->session_id_expected = ret_value; | |
316 | return 1; | |
317 | } | |
318 | ||
319 | const char *ssl_session_id_name(ssl_session_id_t server) | |
320 | { | |
321 | return enum_name(ssl_session_id, | |
322 | OSSL_NELEM(ssl_session_id), | |
323 | server); | |
324 | } | |
325 | ||
cc22cd54 | 326 | /* Method */ |
74726750 EK |
327 | |
328 | static const test_enum ssl_test_methods[] = { | |
329 | {"TLS", SSL_TEST_METHOD_TLS}, | |
330 | {"DTLS", SSL_TEST_METHOD_DTLS}, | |
08e49012 | 331 | {"QUIC", SSL_TEST_METHOD_QUIC} |
74726750 EK |
332 | }; |
333 | ||
334 | __owur static int parse_test_method(SSL_TEST_CTX *test_ctx, const char *value) | |
335 | { | |
336 | int ret_value; | |
337 | if (!parse_enum(ssl_test_methods, OSSL_NELEM(ssl_test_methods), | |
338 | &ret_value, value)) { | |
339 | return 0; | |
340 | } | |
341 | test_ctx->method = ret_value; | |
342 | return 1; | |
343 | } | |
344 | ||
345 | const char *ssl_test_method_name(ssl_test_method_t method) | |
346 | { | |
347 | return enum_name(ssl_test_methods, OSSL_NELEM(ssl_test_methods), method); | |
348 | } | |
349 | ||
cc22cd54 | 350 | /* NPN and ALPN options */ |
ce2cdac2 | 351 | |
9f48bbac EK |
352 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_CLIENT_CONF, client, npn_protocols) |
353 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_SERVER_CONF, server, npn_protocols) | |
354 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_CTX, test, expected_npn_protocol) | |
355 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_CLIENT_CONF, client, alpn_protocols) | |
356 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_SERVER_CONF, server, alpn_protocols) | |
357 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_CTX, test, expected_alpn_protocol) | |
ce2cdac2 | 358 | |
ea1ecd98 EK |
359 | /* SRP options */ |
360 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_CLIENT_CONF, client, srp_user) | |
361 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_SERVER_CONF, server, srp_user) | |
362 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_CLIENT_CONF, client, srp_password) | |
363 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_SERVER_CONF, server, srp_password) | |
364 | ||
df0fed9a TS |
365 | /* Session Ticket App Data options */ |
366 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_CTX, test, expected_session_ticket_app_data) | |
367 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_SERVER_CONF, server, session_ticket_app_data) | |
368 | ||
cc22cd54 | 369 | /* Handshake mode */ |
590ed3d7 EK |
370 | |
371 | static const test_enum ssl_handshake_modes[] = { | |
372 | {"Simple", SSL_TEST_HANDSHAKE_SIMPLE}, | |
373 | {"Resume", SSL_TEST_HANDSHAKE_RESUME}, | |
fe7dd553 MC |
374 | {"RenegotiateServer", SSL_TEST_HANDSHAKE_RENEG_SERVER}, |
375 | {"RenegotiateClient", SSL_TEST_HANDSHAKE_RENEG_CLIENT}, | |
9b92f161 MC |
376 | {"KeyUpdateServer", SSL_TEST_HANDSHAKE_KEY_UPDATE_SERVER}, |
377 | {"KeyUpdateClient", SSL_TEST_HANDSHAKE_KEY_UPDATE_CLIENT}, | |
9d75dce3 | 378 | {"PostHandshakeAuth", SSL_TEST_HANDSHAKE_POST_HANDSHAKE_AUTH}, |
590ed3d7 EK |
379 | }; |
380 | ||
381 | __owur static int parse_handshake_mode(SSL_TEST_CTX *test_ctx, const char *value) | |
382 | { | |
383 | int ret_value; | |
384 | if (!parse_enum(ssl_handshake_modes, OSSL_NELEM(ssl_handshake_modes), | |
385 | &ret_value, value)) { | |
386 | return 0; | |
387 | } | |
388 | test_ctx->handshake_mode = ret_value; | |
389 | return 1; | |
390 | } | |
391 | ||
392 | const char *ssl_handshake_mode_name(ssl_handshake_mode_t mode) | |
393 | { | |
394 | return enum_name(ssl_handshake_modes, OSSL_NELEM(ssl_handshake_modes), | |
395 | mode); | |
396 | } | |
397 | ||
cc22cd54 MC |
398 | /* Renegotiation Ciphersuites */ |
399 | ||
400 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_CLIENT_CONF, client, reneg_ciphers) | |
401 | ||
9b92f161 MC |
402 | /* KeyUpdateType */ |
403 | ||
404 | static const test_enum ssl_key_update_types[] = { | |
405 | {"KeyUpdateRequested", SSL_KEY_UPDATE_REQUESTED}, | |
406 | {"KeyUpdateNotRequested", SSL_KEY_UPDATE_NOT_REQUESTED}, | |
407 | }; | |
408 | ||
409 | __owur static int parse_key_update_type(SSL_TEST_CTX *test_ctx, const char *value) | |
410 | { | |
411 | int ret_value; | |
412 | if (!parse_enum(ssl_key_update_types, OSSL_NELEM(ssl_key_update_types), | |
413 | &ret_value, value)) { | |
414 | return 0; | |
415 | } | |
416 | test_ctx->key_update_type = ret_value; | |
417 | return 1; | |
418 | } | |
419 | ||
cc22cd54 | 420 | /* CT Validation */ |
da085d27 EK |
421 | |
422 | static const test_enum ssl_ct_validation_modes[] = { | |
423 | {"None", SSL_TEST_CT_VALIDATION_NONE}, | |
424 | {"Permissive", SSL_TEST_CT_VALIDATION_PERMISSIVE}, | |
425 | {"Strict", SSL_TEST_CT_VALIDATION_STRICT}, | |
426 | }; | |
427 | ||
428 | __owur static int parse_ct_validation(SSL_TEST_CLIENT_CONF *client_conf, | |
429 | const char *value) | |
430 | { | |
431 | int ret_value; | |
432 | if (!parse_enum(ssl_ct_validation_modes, OSSL_NELEM(ssl_ct_validation_modes), | |
433 | &ret_value, value)) { | |
434 | return 0; | |
435 | } | |
436 | client_conf->ct_validation = ret_value; | |
437 | return 1; | |
438 | } | |
439 | ||
440 | const char *ssl_ct_validation_name(ssl_ct_validation_t mode) | |
441 | { | |
442 | return enum_name(ssl_ct_validation_modes, OSSL_NELEM(ssl_ct_validation_modes), | |
443 | mode); | |
444 | } | |
445 | ||
9f48bbac EK |
446 | IMPLEMENT_SSL_TEST_BOOL_OPTION(SSL_TEST_CTX, test, resumption_expected) |
447 | IMPLEMENT_SSL_TEST_BOOL_OPTION(SSL_TEST_SERVER_CONF, server, broken_session_ticket) | |
83964ca0 | 448 | IMPLEMENT_SSL_TEST_BOOL_OPTION(SSL_TEST_CTX, test, use_sctp) |
b67cb09f | 449 | IMPLEMENT_SSL_TEST_BOOL_OPTION(SSL_TEST_CTX, test, compress_certificates) |
09d62b33 MT |
450 | IMPLEMENT_SSL_TEST_BOOL_OPTION(SSL_TEST_CTX, test, enable_client_sctp_label_bug) |
451 | IMPLEMENT_SSL_TEST_BOOL_OPTION(SSL_TEST_CTX, test, enable_server_sctp_label_bug) | |
590ed3d7 | 452 | |
767ccc3b | 453 | /* CertStatus */ |
767ccc3b MC |
454 | |
455 | static const test_enum ssl_certstatus[] = { | |
456 | {"None", SSL_TEST_CERT_STATUS_NONE}, | |
457 | {"GoodResponse", SSL_TEST_CERT_STATUS_GOOD_RESPONSE}, | |
458 | {"BadResponse", SSL_TEST_CERT_STATUS_BAD_RESPONSE} | |
459 | }; | |
460 | ||
461 | __owur static int parse_certstatus(SSL_TEST_SERVER_CONF *server_conf, | |
462 | const char *value) | |
463 | { | |
464 | int ret_value; | |
465 | if (!parse_enum(ssl_certstatus, OSSL_NELEM(ssl_certstatus), &ret_value, | |
466 | value)) { | |
467 | return 0; | |
468 | } | |
469 | server_conf->cert_status = ret_value; | |
470 | return 1; | |
471 | } | |
472 | ||
473 | const char *ssl_certstatus_name(ssl_cert_status_t cert_status) | |
474 | { | |
475 | return enum_name(ssl_certstatus, | |
476 | OSSL_NELEM(ssl_certstatus), cert_status); | |
477 | } | |
478 | ||
cc22cd54 | 479 | /* ApplicationData */ |
e0421bd8 EK |
480 | |
481 | IMPLEMENT_SSL_TEST_INT_OPTION(SSL_TEST_CTX, test, app_data_size) | |
482 | ||
cc22cd54 MC |
483 | |
484 | /* MaxFragmentSize */ | |
6dc99745 EK |
485 | |
486 | IMPLEMENT_SSL_TEST_INT_OPTION(SSL_TEST_CTX, test, max_fragment_size) | |
487 | ||
cf72c757 F |
488 | /* Maximum-Fragment-Length TLS extension mode */ |
489 | static const test_enum ssl_max_fragment_len_mode[] = { | |
490 | {"None", TLSEXT_max_fragment_length_DISABLED}, | |
491 | { "512", TLSEXT_max_fragment_length_512}, | |
492 | {"1024", TLSEXT_max_fragment_length_1024}, | |
493 | {"2048", TLSEXT_max_fragment_length_2048}, | |
494 | {"4096", TLSEXT_max_fragment_length_4096} | |
495 | }; | |
496 | ||
497 | __owur static int parse_max_fragment_len_mode(SSL_TEST_CLIENT_CONF *client_conf, | |
498 | const char *value) | |
499 | { | |
500 | int ret_value; | |
501 | ||
502 | if (!parse_enum(ssl_max_fragment_len_mode, | |
503 | OSSL_NELEM(ssl_max_fragment_len_mode), &ret_value, value)) { | |
504 | return 0; | |
505 | } | |
506 | client_conf->max_fragment_len_mode = ret_value; | |
507 | return 1; | |
508 | } | |
509 | ||
510 | const char *ssl_max_fragment_len_name(int MFL_mode) | |
511 | { | |
512 | return enum_name(ssl_max_fragment_len_mode, | |
513 | OSSL_NELEM(ssl_max_fragment_len_mode), MFL_mode); | |
514 | } | |
515 | ||
cc22cd54 MC |
516 | |
517 | /* Expected key and signature types */ | |
b93ad05d | 518 | |
7f5f35af | 519 | __owur static int parse_expected_key_type(int *ptype, const char *value) |
b93ad05d DSH |
520 | { |
521 | int nid; | |
7f5f35af | 522 | const EVP_PKEY_ASN1_METHOD *ameth; |
b93ad05d DSH |
523 | |
524 | if (value == NULL) | |
525 | return 0; | |
7f5f35af DSH |
526 | ameth = EVP_PKEY_asn1_find_str(NULL, value, -1); |
527 | if (ameth != NULL) | |
528 | EVP_PKEY_asn1_get0_info(&nid, NULL, NULL, NULL, NULL, ameth); | |
529 | else | |
530 | nid = OBJ_sn2nid(value); | |
b93ad05d DSH |
531 | if (nid == NID_undef) |
532 | nid = OBJ_ln2nid(value); | |
533 | #ifndef OPENSSL_NO_EC | |
534 | if (nid == NID_undef) | |
535 | nid = EC_curve_nist2nid(value); | |
536 | #endif | |
3f76339a MC |
537 | switch (nid) { |
538 | case NID_brainpoolP256r1tls13: | |
539 | nid = NID_brainpoolP256r1; | |
540 | break; | |
541 | case NID_brainpoolP384r1tls13: | |
542 | nid = NID_brainpoolP384r1; | |
543 | break; | |
544 | case NID_brainpoolP512r1tls13: | |
545 | nid = NID_brainpoolP512r1; | |
546 | break; | |
547 | } | |
b93ad05d DSH |
548 | if (nid == NID_undef) |
549 | return 0; | |
7f5f35af | 550 | *ptype = nid; |
b93ad05d DSH |
551 | return 1; |
552 | } | |
553 | ||
7f5f35af DSH |
554 | __owur static int parse_expected_tmp_key_type(SSL_TEST_CTX *test_ctx, |
555 | const char *value) | |
556 | { | |
557 | return parse_expected_key_type(&test_ctx->expected_tmp_key_type, value); | |
558 | } | |
559 | ||
560 | __owur static int parse_expected_server_cert_type(SSL_TEST_CTX *test_ctx, | |
561 | const char *value) | |
562 | { | |
563 | return parse_expected_key_type(&test_ctx->expected_server_cert_type, | |
564 | value); | |
565 | } | |
566 | ||
54b7f2a5 DSH |
567 | __owur static int parse_expected_server_sign_type(SSL_TEST_CTX *test_ctx, |
568 | const char *value) | |
569 | { | |
570 | return parse_expected_key_type(&test_ctx->expected_server_sign_type, | |
571 | value); | |
572 | } | |
573 | ||
7f5f35af DSH |
574 | __owur static int parse_expected_client_cert_type(SSL_TEST_CTX *test_ctx, |
575 | const char *value) | |
576 | { | |
577 | return parse_expected_key_type(&test_ctx->expected_client_cert_type, | |
578 | value); | |
579 | } | |
580 | ||
54b7f2a5 DSH |
581 | __owur static int parse_expected_client_sign_type(SSL_TEST_CTX *test_ctx, |
582 | const char *value) | |
583 | { | |
584 | return parse_expected_key_type(&test_ctx->expected_client_sign_type, | |
585 | value); | |
586 | } | |
587 | ||
cc22cd54 | 588 | |
ee5b6a42 | 589 | /* Expected signing hash */ |
ee5b6a42 DSH |
590 | |
591 | __owur static int parse_expected_sign_hash(int *ptype, const char *value) | |
592 | { | |
593 | int nid; | |
594 | ||
595 | if (value == NULL) | |
596 | return 0; | |
597 | nid = OBJ_sn2nid(value); | |
598 | if (nid == NID_undef) | |
599 | nid = OBJ_ln2nid(value); | |
600 | if (nid == NID_undef) | |
601 | return 0; | |
602 | *ptype = nid; | |
603 | return 1; | |
604 | } | |
605 | ||
606 | __owur static int parse_expected_server_sign_hash(SSL_TEST_CTX *test_ctx, | |
607 | const char *value) | |
608 | { | |
609 | return parse_expected_sign_hash(&test_ctx->expected_server_sign_hash, | |
610 | value); | |
611 | } | |
612 | ||
613 | __owur static int parse_expected_client_sign_hash(SSL_TEST_CTX *test_ctx, | |
614 | const char *value) | |
615 | { | |
4bb0b438 | 616 | return parse_expected_sign_hash(&test_ctx->expected_client_sign_hash, |
ee5b6a42 DSH |
617 | value); |
618 | } | |
619 | ||
2e21539b | 620 | __owur static int parse_expected_ca_names(STACK_OF(X509_NAME) **pnames, |
b4250010 DMSP |
621 | const char *value, |
622 | OSSL_LIB_CTX *libctx) | |
2e21539b DSH |
623 | { |
624 | if (value == NULL) | |
625 | return 0; | |
626 | if (!strcmp(value, "empty")) | |
627 | *pnames = sk_X509_NAME_new_null(); | |
628 | else | |
d8652be0 | 629 | *pnames = SSL_load_client_CA_file_ex(value, libctx, NULL); |
2e21539b DSH |
630 | return *pnames != NULL; |
631 | } | |
f15b50c4 DSH |
632 | __owur static int parse_expected_server_ca_names(SSL_TEST_CTX *test_ctx, |
633 | const char *value) | |
634 | { | |
6725682d SL |
635 | return parse_expected_ca_names(&test_ctx->expected_server_ca_names, value, |
636 | test_ctx->libctx); | |
f15b50c4 | 637 | } |
2e21539b DSH |
638 | __owur static int parse_expected_client_ca_names(SSL_TEST_CTX *test_ctx, |
639 | const char *value) | |
640 | { | |
6725682d SL |
641 | return parse_expected_ca_names(&test_ctx->expected_client_ca_names, value, |
642 | test_ctx->libctx); | |
2e21539b | 643 | } |
cc22cd54 | 644 | |
e1c7871d TS |
645 | /* ExpectedCipher */ |
646 | ||
647 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_CTX, test, expected_cipher) | |
648 | ||
32097b33 | 649 | /* Client and Server PHA */ |
9d75dce3 | 650 | |
32097b33 | 651 | IMPLEMENT_SSL_TEST_BOOL_OPTION(SSL_TEST_CLIENT_CONF, client, enable_pha) |
9d75dce3 | 652 | IMPLEMENT_SSL_TEST_BOOL_OPTION(SSL_TEST_SERVER_CONF, server, force_pha) |
cd4afec6 | 653 | IMPLEMENT_SSL_TEST_BOOL_OPTION(SSL_TEST_CLIENT_CONF, client, no_extms_on_reneg) |
9d75dce3 | 654 | |
4454c20f P |
655 | /* FIPS provider version limiting */ |
656 | IMPLEMENT_SSL_TEST_STRING_OPTION(SSL_TEST_CTX, test, fips_version) | |
657 | ||
453dfd8d | 658 | /* Known test options and their corresponding parse methods. */ |
453dfd8d | 659 | |
9f48bbac | 660 | /* Top-level options. */ |
453dfd8d EK |
661 | typedef struct { |
662 | const char *name; | |
663 | int (*parse)(SSL_TEST_CTX *test_ctx, const char *value); | |
664 | } ssl_test_ctx_option; | |
665 | ||
666 | static const ssl_test_ctx_option ssl_test_ctx_options[] = { | |
667 | { "ExpectedResult", &parse_expected_result }, | |
9f48bbac EK |
668 | { "ExpectedClientAlert", &parse_client_alert }, |
669 | { "ExpectedServerAlert", &parse_server_alert }, | |
670 | { "ExpectedProtocol", &parse_protocol }, | |
d2b23cd2 | 671 | { "ExpectedServerName", &parse_expected_servername }, |
81fc33c9 | 672 | { "SessionTicketExpected", &parse_session_ticket }, |
b6611753 | 673 | { "CompressionExpected", &parse_test_compression_expected }, |
a84e5c9a | 674 | { "SessionIdExpected", &parse_session_id }, |
74726750 | 675 | { "Method", &parse_test_method }, |
9f48bbac EK |
676 | { "ExpectedNPNProtocol", &parse_test_expected_npn_protocol }, |
677 | { "ExpectedALPNProtocol", &parse_test_expected_alpn_protocol }, | |
590ed3d7 | 678 | { "HandshakeMode", &parse_handshake_mode }, |
9b92f161 | 679 | { "KeyUpdateType", &parse_key_update_type }, |
9f48bbac | 680 | { "ResumptionExpected", &parse_test_resumption_expected }, |
e0421bd8 | 681 | { "ApplicationData", &parse_test_app_data_size }, |
6dc99745 | 682 | { "MaxFragmentSize", &parse_test_max_fragment_size }, |
b93ad05d | 683 | { "ExpectedTmpKeyType", &parse_expected_tmp_key_type }, |
7f5f35af | 684 | { "ExpectedServerCertType", &parse_expected_server_cert_type }, |
ee5b6a42 | 685 | { "ExpectedServerSignHash", &parse_expected_server_sign_hash }, |
54b7f2a5 | 686 | { "ExpectedServerSignType", &parse_expected_server_sign_type }, |
f15b50c4 | 687 | { "ExpectedServerCANames", &parse_expected_server_ca_names }, |
7f5f35af | 688 | { "ExpectedClientCertType", &parse_expected_client_cert_type }, |
ee5b6a42 | 689 | { "ExpectedClientSignHash", &parse_expected_client_sign_hash }, |
54b7f2a5 | 690 | { "ExpectedClientSignType", &parse_expected_client_sign_type }, |
2e21539b | 691 | { "ExpectedClientCANames", &parse_expected_client_ca_names }, |
83964ca0 | 692 | { "UseSCTP", &parse_test_use_sctp }, |
b67cb09f | 693 | { "CompressCertificates", &parse_test_compress_certificates }, |
09d62b33 MT |
694 | { "EnableClientSCTPLabelBug", &parse_test_enable_client_sctp_label_bug }, |
695 | { "EnableServerSCTPLabelBug", &parse_test_enable_server_sctp_label_bug }, | |
e1c7871d | 696 | { "ExpectedCipher", &parse_test_expected_cipher }, |
df0fed9a | 697 | { "ExpectedSessionTicketAppData", &parse_test_expected_session_ticket_app_data }, |
4454c20f | 698 | { "FIPSversion", &parse_test_fips_version }, |
9f48bbac EK |
699 | }; |
700 | ||
701 | /* Nested client options. */ | |
702 | typedef struct { | |
703 | const char *name; | |
704 | int (*parse)(SSL_TEST_CLIENT_CONF *conf, const char *value); | |
705 | } ssl_test_client_option; | |
706 | ||
707 | static const ssl_test_client_option ssl_test_client_options[] = { | |
708 | { "VerifyCallback", &parse_client_verify_callback }, | |
709 | { "ServerName", &parse_servername }, | |
710 | { "NPNProtocols", &parse_client_npn_protocols }, | |
711 | { "ALPNProtocols", &parse_client_alpn_protocols }, | |
da085d27 | 712 | { "CTValidation", &parse_ct_validation }, |
cc22cd54 | 713 | { "RenegotiateCiphers", &parse_client_reneg_ciphers}, |
ea1ecd98 EK |
714 | { "SRPUser", &parse_client_srp_user }, |
715 | { "SRPPassword", &parse_client_srp_password }, | |
cf72c757 | 716 | { "MaxFragmentLenExt", &parse_max_fragment_len_mode }, |
32097b33 | 717 | { "EnablePHA", &parse_client_enable_pha }, |
cd4afec6 | 718 | { "RenegotiateNoExtms", &parse_client_no_extms_on_reneg }, |
9f48bbac EK |
719 | }; |
720 | ||
721 | /* Nested server options. */ | |
722 | typedef struct { | |
723 | const char *name; | |
724 | int (*parse)(SSL_TEST_SERVER_CONF *conf, const char *value); | |
725 | } ssl_test_server_option; | |
726 | ||
727 | static const ssl_test_server_option ssl_test_server_options[] = { | |
728 | { "ServerNameCallback", &parse_servername_callback }, | |
729 | { "NPNProtocols", &parse_server_npn_protocols }, | |
730 | { "ALPNProtocols", &parse_server_alpn_protocols }, | |
731 | { "BrokenSessionTicket", &parse_server_broken_session_ticket }, | |
767ccc3b | 732 | { "CertStatus", &parse_certstatus }, |
ea1ecd98 EK |
733 | { "SRPUser", &parse_server_srp_user }, |
734 | { "SRPPassword", &parse_server_srp_password }, | |
9d75dce3 | 735 | { "ForcePHA", &parse_server_force_pha }, |
df0fed9a | 736 | { "SessionTicketAppData", &parse_server_session_ticket_app_data }, |
453dfd8d EK |
737 | }; |
738 | ||
b4250010 | 739 | SSL_TEST_CTX *SSL_TEST_CTX_new(OSSL_LIB_CTX *libctx) |
453dfd8d EK |
740 | { |
741 | SSL_TEST_CTX *ret; | |
019e47ce P |
742 | |
743 | /* The return code is checked by caller */ | |
744 | if ((ret = OPENSSL_zalloc(sizeof(*ret))) != NULL) { | |
6725682d | 745 | ret->libctx = libctx; |
019e47ce P |
746 | ret->app_data_size = default_app_data_size; |
747 | ret->max_fragment_size = default_max_fragment_size; | |
748 | } | |
453dfd8d EK |
749 | return ret; |
750 | } | |
751 | ||
9f48bbac EK |
752 | static void ssl_test_extra_conf_free_data(SSL_TEST_EXTRA_CONF *conf) |
753 | { | |
754 | OPENSSL_free(conf->client.npn_protocols); | |
755 | OPENSSL_free(conf->server.npn_protocols); | |
756 | OPENSSL_free(conf->server2.npn_protocols); | |
757 | OPENSSL_free(conf->client.alpn_protocols); | |
758 | OPENSSL_free(conf->server.alpn_protocols); | |
759 | OPENSSL_free(conf->server2.alpn_protocols); | |
d605fc3a | 760 | OPENSSL_free(conf->client.reneg_ciphers); |
ea1ecd98 EK |
761 | OPENSSL_free(conf->server.srp_user); |
762 | OPENSSL_free(conf->server.srp_password); | |
763 | OPENSSL_free(conf->server2.srp_user); | |
764 | OPENSSL_free(conf->server2.srp_password); | |
765 | OPENSSL_free(conf->client.srp_user); | |
766 | OPENSSL_free(conf->client.srp_password); | |
df0fed9a TS |
767 | OPENSSL_free(conf->server.session_ticket_app_data); |
768 | OPENSSL_free(conf->server2.session_ticket_app_data); | |
9f48bbac EK |
769 | } |
770 | ||
771 | static void ssl_test_ctx_free_extra_data(SSL_TEST_CTX *ctx) | |
453dfd8d | 772 | { |
9f48bbac EK |
773 | ssl_test_extra_conf_free_data(&ctx->extra); |
774 | ssl_test_extra_conf_free_data(&ctx->resume_extra); | |
775 | } | |
ce2cdac2 | 776 | |
9f48bbac EK |
777 | void SSL_TEST_CTX_free(SSL_TEST_CTX *ctx) |
778 | { | |
6725682d SL |
779 | if (ctx == NULL) |
780 | return; | |
9f48bbac | 781 | ssl_test_ctx_free_extra_data(ctx); |
ce2cdac2 EK |
782 | OPENSSL_free(ctx->expected_npn_protocol); |
783 | OPENSSL_free(ctx->expected_alpn_protocol); | |
df0fed9a | 784 | OPENSSL_free(ctx->expected_session_ticket_app_data); |
f15b50c4 | 785 | sk_X509_NAME_pop_free(ctx->expected_server_ca_names, X509_NAME_free); |
2e21539b | 786 | sk_X509_NAME_pop_free(ctx->expected_client_ca_names, X509_NAME_free); |
e1c7871d | 787 | OPENSSL_free(ctx->expected_cipher); |
4454c20f | 788 | OPENSSL_free(ctx->fips_version); |
453dfd8d EK |
789 | OPENSSL_free(ctx); |
790 | } | |
791 | ||
9f48bbac EK |
792 | static int parse_client_options(SSL_TEST_CLIENT_CONF *client, const CONF *conf, |
793 | const char *client_section) | |
453dfd8d EK |
794 | { |
795 | STACK_OF(CONF_VALUE) *sk_conf; | |
453dfd8d EK |
796 | int i; |
797 | size_t j; | |
798 | ||
019e47ce P |
799 | if (!TEST_ptr(sk_conf = NCONF_get_section(conf, client_section))) |
800 | return 0; | |
453dfd8d | 801 | |
9f48bbac EK |
802 | for (i = 0; i < sk_CONF_VALUE_num(sk_conf); i++) { |
803 | int found = 0; | |
804 | const CONF_VALUE *option = sk_CONF_VALUE_value(sk_conf, i); | |
805 | for (j = 0; j < OSSL_NELEM(ssl_test_client_options); j++) { | |
806 | if (strcmp(option->name, ssl_test_client_options[j].name) == 0) { | |
807 | if (!ssl_test_client_options[j].parse(client, option->value)) { | |
8fe3127c P |
808 | TEST_info("Bad value %s for option %s", |
809 | option->value, option->name); | |
9f48bbac EK |
810 | return 0; |
811 | } | |
812 | found = 1; | |
813 | break; | |
814 | } | |
815 | } | |
816 | if (!found) { | |
8fe3127c | 817 | TEST_info("Unknown test option: %s", option->name); |
9f48bbac EK |
818 | return 0; |
819 | } | |
820 | } | |
821 | ||
822 | return 1; | |
823 | } | |
824 | ||
825 | static int parse_server_options(SSL_TEST_SERVER_CONF *server, const CONF *conf, | |
826 | const char *server_section) | |
827 | { | |
828 | STACK_OF(CONF_VALUE) *sk_conf; | |
829 | int i; | |
830 | size_t j; | |
831 | ||
019e47ce P |
832 | if (!TEST_ptr(sk_conf = NCONF_get_section(conf, server_section))) |
833 | return 0; | |
453dfd8d EK |
834 | |
835 | for (i = 0; i < sk_CONF_VALUE_num(sk_conf); i++) { | |
836 | int found = 0; | |
837 | const CONF_VALUE *option = sk_CONF_VALUE_value(sk_conf, i); | |
9f48bbac EK |
838 | for (j = 0; j < OSSL_NELEM(ssl_test_server_options); j++) { |
839 | if (strcmp(option->name, ssl_test_server_options[j].name) == 0) { | |
840 | if (!ssl_test_server_options[j].parse(server, option->value)) { | |
8fe3127c P |
841 | TEST_info("Bad value %s for option %s", |
842 | option->value, option->name); | |
9f48bbac | 843 | return 0; |
453dfd8d EK |
844 | } |
845 | found = 1; | |
846 | break; | |
847 | } | |
848 | } | |
849 | if (!found) { | |
8fe3127c | 850 | TEST_info("Unknown test option: %s", option->name); |
9f48bbac EK |
851 | return 0; |
852 | } | |
853 | } | |
854 | ||
855 | return 1; | |
856 | } | |
857 | ||
6725682d | 858 | SSL_TEST_CTX *SSL_TEST_CTX_create(const CONF *conf, const char *test_section, |
b4250010 | 859 | OSSL_LIB_CTX *libctx) |
9f48bbac | 860 | { |
019e47ce P |
861 | STACK_OF(CONF_VALUE) *sk_conf = NULL; |
862 | SSL_TEST_CTX *ctx = NULL; | |
9f48bbac EK |
863 | int i; |
864 | size_t j; | |
865 | ||
019e47ce | 866 | if (!TEST_ptr(sk_conf = NCONF_get_section(conf, test_section)) |
6725682d | 867 | || !TEST_ptr(ctx = SSL_TEST_CTX_new(libctx))) |
019e47ce | 868 | goto err; |
9f48bbac EK |
869 | |
870 | for (i = 0; i < sk_CONF_VALUE_num(sk_conf); i++) { | |
871 | int found = 0; | |
872 | const CONF_VALUE *option = sk_CONF_VALUE_value(sk_conf, i); | |
873 | ||
874 | /* Subsections */ | |
875 | if (strcmp(option->name, "client") == 0) { | |
045fe731 | 876 | if (!parse_client_options(&ctx->extra.client, conf, option->value)) |
9f48bbac EK |
877 | goto err; |
878 | } else if (strcmp(option->name, "server") == 0) { | |
045fe731 | 879 | if (!parse_server_options(&ctx->extra.server, conf, option->value)) |
9f48bbac EK |
880 | goto err; |
881 | } else if (strcmp(option->name, "server2") == 0) { | |
045fe731 | 882 | if (!parse_server_options(&ctx->extra.server2, conf, option->value)) |
9f48bbac EK |
883 | goto err; |
884 | } else if (strcmp(option->name, "resume-client") == 0) { | |
045fe731 P |
885 | if (!parse_client_options(&ctx->resume_extra.client, conf, |
886 | option->value)) | |
9f48bbac EK |
887 | goto err; |
888 | } else if (strcmp(option->name, "resume-server") == 0) { | |
045fe731 P |
889 | if (!parse_server_options(&ctx->resume_extra.server, conf, |
890 | option->value)) | |
9f48bbac EK |
891 | goto err; |
892 | } else if (strcmp(option->name, "resume-server2") == 0) { | |
893 | if (!parse_server_options(&ctx->resume_extra.server2, conf, | |
894 | option->value)) | |
895 | goto err; | |
9f48bbac EK |
896 | } else { |
897 | for (j = 0; j < OSSL_NELEM(ssl_test_ctx_options); j++) { | |
898 | if (strcmp(option->name, ssl_test_ctx_options[j].name) == 0) { | |
899 | if (!ssl_test_ctx_options[j].parse(ctx, option->value)) { | |
8fe3127c P |
900 | TEST_info("Bad value %s for option %s", |
901 | option->value, option->name); | |
9f48bbac EK |
902 | goto err; |
903 | } | |
904 | found = 1; | |
905 | break; | |
906 | } | |
907 | } | |
908 | if (!found) { | |
8fe3127c | 909 | TEST_info("Unknown test option: %s", option->name); |
9f48bbac EK |
910 | goto err; |
911 | } | |
453dfd8d EK |
912 | } |
913 | } | |
914 | ||
915 | goto done; | |
916 | ||
917 | err: | |
918 | SSL_TEST_CTX_free(ctx); | |
919 | ctx = NULL; | |
920 | done: | |
921 | return ctx; | |
922 | } |