From dd51826b4ecd725032987690f6ee79d3f5614aab Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Tue, 27 Aug 2024 12:17:22 +0200 Subject: [PATCH 01/18] ssl_client1: Exit with an error status if the TLS connection failed Signed-off-by: Gilles Peskine --- programs/ssl/ssl_client1.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/programs/ssl/ssl_client1.c b/programs/ssl/ssl_client1.c index ee734b1ed1..e51bbd42a3 100644 --- a/programs/ssl/ssl_client1.c +++ b/programs/ssl/ssl_client1.c @@ -240,6 +240,9 @@ int main(void) } if (ret == MBEDTLS_ERR_SSL_PEER_CLOSE_NOTIFY) { + mbedtls_printf("The return value %d from mbedtls_ssl_read() means that the server\n" + "closed the connection first. We're ok with that.\n", + MBEDTLS_ERR_SSL_PEER_CLOSE_NOTIFY); break; } @@ -259,7 +262,9 @@ int main(void) mbedtls_ssl_close_notify(&ssl); - exit_code = MBEDTLS_EXIT_SUCCESS; + if (ret == 0 || ret == MBEDTLS_ERR_SSL_PEER_CLOSE_NOTIFY) { + exit_code = MBEDTLS_EXIT_SUCCESS; + } exit: From 478f6068b5e02a9fc719248d96591320c8a862bb Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Wed, 4 Sep 2024 16:04:42 +0200 Subject: [PATCH 02/18] Prepare to test SSL sample programs Signed-off-by: Gilles Peskine --- tests/opt-testcases/sample.sh | 6 ++++++ 1 file changed, 6 insertions(+) create mode 100644 tests/opt-testcases/sample.sh diff --git a/tests/opt-testcases/sample.sh b/tests/opt-testcases/sample.sh new file mode 100644 index 0000000000..05db6b8356 --- /dev/null +++ b/tests/opt-testcases/sample.sh @@ -0,0 +1,6 @@ +# Test that SSL sample programs can interoperate with OpenSSL and GnuTLS. + +# Copyright The Mbed TLS Contributors +# SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later + +: ${PROGRAMS_DIR:=../programs/ssl} From 6c798ef36d2eebee6261b8580b833ac0d7f76329 Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Wed, 4 Sep 2024 16:05:11 +0200 Subject: [PATCH 03/18] Allow test cases to use a specific port This is necessary for the SSL sample programs: they hard-code port 4433. Signed-off-by: Gilles Peskine --- tests/ssl-opt.sh | 21 +++++++++++++++++++-- 1 file changed, 19 insertions(+), 2 deletions(-) diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh index f856f5affd..acb34b383f 100755 --- a/tests/ssl-opt.sh +++ b/tests/ssl-opt.sh @@ -1410,7 +1410,16 @@ analyze_test_commands() { if [ -n "$PXY_CMD" ]; then CLI_CMD=$( echo "$CLI_CMD" | sed s/+SRV_PORT/$PXY_PORT/g ) else - CLI_CMD=$( echo "$CLI_CMD" | sed s/+SRV_PORT/$SRV_PORT/g ) + CLI_CMD=$( echo "$CLI_CMD" | sed s/+SRV_PORT/$THIS_SRV_PORT/g ) + fi + + # If the test forces a specific port and the server is OpenSSL or + # GnuTLS, override its port specification. + if [ "$THIS_SRV_PORT" != "$SRV_PORT" ]; then + case "$SRV_CMD" in + "$G_SRV"*|"$G_NEXT_SRV"*) SRV_CMD="$SRV_CMD -p $THIS_SRV_PORT";; + "$O_SRV"*|"$O_NEXT_SRV"*) SRV_CMD="$SRV_CMD -accept $THIS_SRV_PORT";; + esac fi # prepend valgrind to our commands if active @@ -1609,7 +1618,7 @@ do_run_test_once() { printf '# %s\n%s\n' "$NAME" "$SRV_CMD" > $SRV_OUT provide_input | $SRV_CMD >> $SRV_OUT 2>&1 & SRV_PID=$! - wait_server_start "$SRV_PORT" "$SRV_PID" + wait_server_start "$THIS_SRV_PORT" "$SRV_PID" printf '# %s\n%s\n' "$NAME" "$CLI_CMD" > $CLI_OUT # The client must be a subprocess of the script in order for killing it to @@ -1740,6 +1749,14 @@ run_test() { PXY_CMD="" fi + # Does this test force a specific port? + if [ "$1" = "-P" ]; then + THIS_SRV_PORT="$2" + shift 2 + else + THIS_SRV_PORT="$SRV_PORT" + fi + # get commands and client output SRV_CMD="$1" CLI_CMD="$2" From e6b8250a9402b4efc208d9701e5725e286a23c78 Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Wed, 4 Sep 2024 16:06:10 +0200 Subject: [PATCH 04/18] Test ssl_client1 Test ssl_client1 with both TLS 1.2 and TLS 1.3. Test against both OpenSSL and GnuTLS. Clean up compile-time requirements in ssl_client1.c: any certificate-based key exchange is ok, so don't insist on built-in RSA. Signed-off-by: Gilles Peskine --- programs/ssl/ssl_client1.c | 20 +++++++---------- tests/opt-testcases/sample.sh | 42 +++++++++++++++++++++++++++++++++++ tests/ssl-opt.sh | 10 +++++++++ 3 files changed, 60 insertions(+), 12 deletions(-) diff --git a/programs/ssl/ssl_client1.c b/programs/ssl/ssl_client1.c index e51bbd42a3..3d6e67c6a9 100644 --- a/programs/ssl/ssl_client1.c +++ b/programs/ssl/ssl_client1.c @@ -9,17 +9,14 @@ #include "mbedtls/platform.h" -#if !defined(MBEDTLS_BIGNUM_C) || !defined(MBEDTLS_ENTROPY_C) || \ - !defined(MBEDTLS_SSL_TLS_C) || !defined(MBEDTLS_SSL_CLI_C) || \ - !defined(MBEDTLS_NET_C) || !defined(MBEDTLS_RSA_C) || \ - !defined(MBEDTLS_PEM_PARSE_C) || !defined(MBEDTLS_CTR_DRBG_C) || \ - !defined(MBEDTLS_X509_CRT_PARSE_C) +#if !defined(MBEDTLS_ENTROPY_C) || !defined(MBEDTLS_CTR_DRBG_C) || \ + !defined(MBEDTLS_NET_C) || !defined(MBEDTLS_SSL_CLI_C) || \ + !defined(MBEDTLS_PEM_PARSE_C) || !defined(MBEDTLS_X509_CRT_PARSE_C) int main(void) { - mbedtls_printf("MBEDTLS_BIGNUM_C and/or MBEDTLS_ENTROPY_C and/or " - "MBEDTLS_SSL_TLS_C and/or MBEDTLS_SSL_CLI_C and/or " - "MBEDTLS_NET_C and/or MBEDTLS_RSA_C and/or " - "MBEDTLS_CTR_DRBG_C and/or MBEDTLS_X509_CRT_PARSE_C " + mbedtls_printf("MBEDTLS_ENTROPY_C and/or MBEDTLS_CTR_DRBG_C and/or " + "MBEDTLS_NET_C and/or MBEDTLS_SSL_CLI_C and/or " + "MBEDTLS_PEM_PARSE_C and/or MBEDTLS_X509_CRT_PARSE_C " "not defined.\n"); mbedtls_exit(0); } @@ -288,6 +285,5 @@ exit: mbedtls_exit(exit_code); } -#endif /* MBEDTLS_BIGNUM_C && MBEDTLS_ENTROPY_C && MBEDTLS_SSL_TLS_C && - MBEDTLS_SSL_CLI_C && MBEDTLS_NET_C && MBEDTLS_RSA_C && - MBEDTLS_PEM_PARSE_C && MBEDTLS_CTR_DRBG_C && MBEDTLS_X509_CRT_PARSE_C */ + +#endif /* configuration allows running this program */ diff --git a/tests/opt-testcases/sample.sh b/tests/opt-testcases/sample.sh index 05db6b8356..88bee47cad 100644 --- a/tests/opt-testcases/sample.sh +++ b/tests/opt-testcases/sample.sh @@ -4,3 +4,45 @@ # SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later : ${PROGRAMS_DIR:=../programs/ssl} + +requires_protocol_version tls12 +run_test "Sample: ssl_client1, openssl server, TLS 1.2" \ + -P 4433 \ + "$O_SRV -tls1_2" \ + "$PROGRAMS_DIR/ssl_client1" \ + 0 \ + -c "New, TLSv1.2, Cipher is" \ + -S "ERROR" \ + -C "error" + +requires_protocol_version tls12 +run_test "Sample: ssl_client1, gnutls server, TLS 1.2" \ + -P 4433 \ + "$G_SRV --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.2" \ + "$PROGRAMS_DIR/ssl_client1" \ + 0 \ + -s "Version: TLS1.2" \ + -c "Protocol version:TLS1.2" \ + -S "Error" \ + -C "error" + +requires_protocol_version tls13 +run_test "Sample: ssl_client1, openssl server, TLS 1.3" \ + -P 4433 \ + "$O_SRV -tls1_3" \ + "$PROGRAMS_DIR/ssl_client1" \ + 0 \ + -c "New, TLSv1.3, Cipher is" \ + -S "ERROR" \ + -C "error" + +requires_protocol_version tls13 +run_test "Sample: ssl_client1, gnutls server, TLS 1.3" \ + -P 4433 \ + "$G_SRV --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.3" \ + "$PROGRAMS_DIR/ssl_client1" \ + 0 \ + -s "Version: TLS1.3" \ + -c "Protocol version:TLS1.3" \ + -S "Error" \ + -C "error" diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh index acb34b383f..b210b6d343 100755 --- a/tests/ssl-opt.sh +++ b/tests/ssl-opt.sh @@ -491,6 +491,16 @@ detect_required_features() { requires_certificate_authentication;; esac + case " $CMD_LINE " in + *"programs/ssl/ssl_client1 "*) + requires_config_enabled MBEDTLS_CTR_DRBG_C + requires_config_enabled MBEDTLS_ENTROPY_C + requires_config_enabled MBEDTLS_PEM_PARSE_C + requires_config_enabled MBEDTLS_SSL_CLI_C + requires_certificate_authentication + ;; + esac + case "$CMD_LINE" in *[-_\ =]psk*|*[-_\ =]PSK*) :;; # No certificate requirement with PSK */server5*|\ From f8b373e8693d6e728f2b055971b2c5d0082df373 Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Wed, 4 Sep 2024 16:07:56 +0200 Subject: [PATCH 05/18] Test dtls_client Test against both OpenSSL and GnuTLS. Don't use a proxy. It's not particularly useful here, and would complicate figuring out port numbers. Clean up compile-time requirements in dtls_client.c: any certificate-based key exchange is ok, so don't insist on built-in RSA. Signed-off-by: Gilles Peskine --- programs/ssl/dtls_client.c | 24 +++++++++++------------- tests/opt-testcases/sample.sh | 28 ++++++++++++++++++++++++++++ tests/ssl-opt.sh | 13 +++++++++---- 3 files changed, 48 insertions(+), 17 deletions(-) diff --git a/programs/ssl/dtls_client.c b/programs/ssl/dtls_client.c index ddb3c34b91..903b28d11a 100644 --- a/programs/ssl/dtls_client.c +++ b/programs/ssl/dtls_client.c @@ -9,18 +9,17 @@ #include "mbedtls/platform.h" -#if !defined(MBEDTLS_SSL_CLI_C) || !defined(MBEDTLS_SSL_PROTO_DTLS) || \ - !defined(MBEDTLS_NET_C) || !defined(MBEDTLS_TIMING_C) || \ - !defined(MBEDTLS_ENTROPY_C) || !defined(MBEDTLS_CTR_DRBG_C) || \ - !defined(MBEDTLS_X509_CRT_PARSE_C) || !defined(MBEDTLS_RSA_C) || \ - !defined(MBEDTLS_PEM_PARSE_C) +#if !defined(MBEDTLS_ENTROPY_C) || !defined(MBEDTLS_CTR_DRBG_C) || \ + !defined(MBEDTLS_NET_C) || !defined(MBEDTLS_SSL_CLI_C) || \ + !defined(MBEDTLS_TIMING_C) || !defined(MBEDTLS_SSL_PROTO_DTLS) || \ + !defined(MBEDTLS_PEM_PARSE_C) || !defined(MBEDTLS_X509_CRT_PARSE_C) int main(void) { - mbedtls_printf("MBEDTLS_SSL_CLI_C and/or MBEDTLS_SSL_PROTO_DTLS and/or " - "MBEDTLS_NET_C and/or MBEDTLS_TIMING_C and/or " - "MBEDTLS_ENTROPY_C and/or MBEDTLS_CTR_DRBG_C and/or " - "MBEDTLS_X509_CRT_PARSE_C and/or MBEDTLS_RSA_C and/or " - "MBEDTLS_PEM_PARSE_C not defined.\n"); + mbedtls_printf("MBEDTLS_ENTROPY_C and/or MBEDTLS_CTR_DRBG_C and/or " + "MBEDTLS_NET_C and/or MBEDTLS_SSL_CLI_C and/or " + "MBEDTLS_TIMING_C and/or MBEDTLS_SSL_PROTO_DTLS and/or " + "MBEDTLS_PEM_PARSE_C and/or MBEDTLS_X509_CRT_PARSE_C " + "not defined.\n"); mbedtls_exit(0); } #else @@ -337,6 +336,5 @@ exit: mbedtls_exit(ret); } -#endif /* MBEDTLS_SSL_CLI_C && MBEDTLS_SSL_PROTO_DTLS && MBEDTLS_NET_C && - MBEDTLS_TIMING_C && MBEDTLS_ENTROPY_C && MBEDTLS_CTR_DRBG_C && - MBEDTLS_X509_CRT_PARSE_C && MBEDTLS_RSA_C && MBEDTLS_PEM_PARSE_C */ + +#endif /* configuration allows running this program */ diff --git a/tests/opt-testcases/sample.sh b/tests/opt-testcases/sample.sh index 88bee47cad..171bb4e22a 100644 --- a/tests/opt-testcases/sample.sh +++ b/tests/opt-testcases/sample.sh @@ -46,3 +46,31 @@ run_test "Sample: ssl_client1, gnutls server, TLS 1.3" \ -c "Protocol version:TLS1.3" \ -S "Error" \ -C "error" + +requires_protocol_version dtls12 +run_test "Sample: dtls_client, openssl server, DTLS 1.2" \ + -P 4433 \ + "$O_SRV -dtls1_2" \ + "$PROGRAMS_DIR/dtls_client" \ + 0 \ + -s "Echo this" \ + -s "DONE" \ + -c "Echo this" \ + -c "[1-9][0-9]* bytes written" \ + -c "[1-9][0-9]* bytes read" \ + -S "ERROR" \ + -C "error" + +requires_protocol_version dtls12 +run_test "Sample: dtls_client, gnutls server, DTLS 1.2" \ + -P 4433 \ + "$G_SRV -u --echo --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.2" \ + "$PROGRAMS_DIR/dtls_client" \ + 0 \ + -s "Server listening" \ + -s "[1-9][0-9]* bytes command:" \ + -c "Echo this" \ + -c "[1-9][0-9]* bytes written" \ + -c "[1-9][0-9]* bytes read" \ + -S "Error" \ + -C "error" diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh index b210b6d343..3a99e3007f 100755 --- a/tests/ssl-opt.sh +++ b/tests/ssl-opt.sh @@ -492,6 +492,7 @@ detect_required_features() { esac case " $CMD_LINE " in + *"programs/ssl/dtls_client "*|\ *"programs/ssl/ssl_client1 "*) requires_config_enabled MBEDTLS_CTR_DRBG_C requires_config_enabled MBEDTLS_ENTROPY_C @@ -1382,9 +1383,13 @@ skip_handshake_stage_check() { # Outputs: # * $CLI_CMD, $PXY_CMD, $SRV_CMD: may be tweaked. analyze_test_commands() { - # if the test uses DTLS but no custom proxy, add a simple proxy - # as it provides timing info that's useful to debug failures - if [ -z "$PXY_CMD" ] && [ "$DTLS" -eq 1 ]; then + # If the test uses DTLS, does not force a specific port, and does not + # specify a custom proxy, add a simple proxy. + # It provides timing info that's useful to debug failures. + if [ "$DTLS" -eq 1 ] && + [ "$THIS_SRV_PORT" = "$SRV_PORT" ] && + [ -z "$PXY_CMD" ] + then PXY_CMD="$P_PXY" case " $SRV_CMD " in *' server_addr=::1 '*) @@ -1751,7 +1756,7 @@ run_test() { esac fi - # does this test use a proxy? + # Does this test specify a proxy? if [ "X$1" = "X-p" ]; then PXY_CMD="$2" shift 2 From 37c374981c882f5f234ddfadcee6346c90b90837 Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Wed, 4 Sep 2024 16:30:32 +0200 Subject: [PATCH 06/18] Test ssl_server Test ssl_server with both TLS 1.2 and TLS 1.3. Test against both OpenSSL and GnuTLS. Clean up compile-time requirements in ssl_server.c: any certificate-based key exchange is ok, so don't insist on built-in RSA. Signed-off-by: Gilles Peskine --- programs/ssl/ssl_server.c | 23 +++++++----------- tests/opt-testcases/sample.sh | 44 +++++++++++++++++++++++++++++++++++ tests/ssl-opt.sh | 7 ++++++ 3 files changed, 60 insertions(+), 14 deletions(-) diff --git a/programs/ssl/ssl_server.c b/programs/ssl/ssl_server.c index 6becf8d913..c3bd8fc610 100644 --- a/programs/ssl/ssl_server.c +++ b/programs/ssl/ssl_server.c @@ -9,18 +9,15 @@ #include "mbedtls/platform.h" -#if !defined(MBEDTLS_BIGNUM_C) || !defined(MBEDTLS_PEM_PARSE_C) || \ - !defined(MBEDTLS_ENTROPY_C) || !defined(MBEDTLS_SSL_TLS_C) || \ - !defined(MBEDTLS_SSL_SRV_C) || !defined(MBEDTLS_NET_C) || \ - !defined(MBEDTLS_RSA_C) || !defined(MBEDTLS_CTR_DRBG_C) || \ - !defined(MBEDTLS_X509_CRT_PARSE_C) || !defined(MBEDTLS_FS_IO) +#if !defined(MBEDTLS_ENTROPY_C) || !defined(MBEDTLS_CTR_DRBG_C) || \ + !defined(MBEDTLS_NET_C) || !defined(MBEDTLS_SSL_SRV_C) || \ + !defined(MBEDTLS_PEM_PARSE_C) || !defined(MBEDTLS_X509_CRT_PARSE_C) int main(void) { - mbedtls_printf("MBEDTLS_BIGNUM_C and/or MBEDTLS_ENTROPY_C " - "and/or MBEDTLS_SSL_TLS_C and/or MBEDTLS_SSL_SRV_C and/or " - "MBEDTLS_NET_C and/or MBEDTLS_RSA_C and/or " - "MBEDTLS_CTR_DRBG_C and/or MBEDTLS_X509_CRT_PARSE_C " - "and/or MBEDTLS_PEM_PARSE_C not defined.\n"); + mbedtls_printf("MBEDTLS_ENTROPY_C and/or MBEDTLS_CTR_DRBG_C and/or " + "MBEDTLS_NET_C and/or MBEDTLS_SSL_SRV_C and/or " + "MBEDTLS_PEM_PARSE_C and/or MBEDTLS_X509_CRT_PARSE_C " + "not defined.\n"); mbedtls_exit(0); } #else @@ -356,7 +353,5 @@ exit: mbedtls_exit(ret); } -#endif /* MBEDTLS_BIGNUM_C && MBEDTLS_ENTROPY_C && - MBEDTLS_SSL_TLS_C && MBEDTLS_SSL_SRV_C && MBEDTLS_NET_C && - MBEDTLS_RSA_C && MBEDTLS_CTR_DRBG_C && MBEDTLS_X509_CRT_PARSE_C - && MBEDTLS_FS_IO && MBEDTLS_PEM_PARSE_C */ + +#endif /* configuration allows running this program */ diff --git a/tests/opt-testcases/sample.sh b/tests/opt-testcases/sample.sh index 171bb4e22a..82a95b8b9c 100644 --- a/tests/opt-testcases/sample.sh +++ b/tests/opt-testcases/sample.sh @@ -74,3 +74,47 @@ run_test "Sample: dtls_client, gnutls server, DTLS 1.2" \ -c "[1-9][0-9]* bytes read" \ -S "Error" \ -C "error" + +requires_protocol_version tls12 +run_test "Sample: ssl_server, openssl client, TLS 1.2" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_server" \ + "$O_CLI -tls1_2" \ + 0 \ + -s "Successful connection using: TLS-" \ + -c "New, TLSv1.2, Cipher is" \ + -S "error" \ + -C "ERROR" + +requires_protocol_version tls12 +run_test "Sample: ssl_server, gnutls client, TLS 1.2" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_server" \ + "$G_CLI --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.2 localhost" \ + 0 \ + -s "Successful connection using: TLS-" \ + -c "Description:.*TLS1.2" \ + -S "error" \ + -C "ERROR" + +requires_protocol_version tls13 +run_test "Sample: ssl_server, openssl client, TLS 1.3" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_server" \ + "$O_CLI -tls1_3" \ + 0 \ + -s "Successful connection using: TLS1-3-" \ + -c "New, TLSv1.3, Cipher is" \ + -S "error" \ + -C "ERROR" + +requires_protocol_version tls13 +run_test "Sample: ssl_server, gnutls client, TLS 1.3" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_server" \ + "$G_CLI --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.3 localhost" \ + 0 \ + -s "Successful connection using: TLS1-3-" \ + -c "Description:.*TLS1.3" \ + -S "error" \ + -C "ERROR" diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh index 3a99e3007f..7715254d07 100755 --- a/tests/ssl-opt.sh +++ b/tests/ssl-opt.sh @@ -500,6 +500,13 @@ detect_required_features() { requires_config_enabled MBEDTLS_SSL_CLI_C requires_certificate_authentication ;; + *"programs/ssl/ssl_server "*) + requires_config_enabled MBEDTLS_CTR_DRBG_C + requires_config_enabled MBEDTLS_ENTROPY_C + requires_config_enabled MBEDTLS_PEM_PARSE_C + requires_config_enabled MBEDTLS_SSL_SRV_C + requires_certificate_authentication + ;; esac case "$CMD_LINE" in From fab6099d4a0205e0b75f6b3fc136c75fba17d3a9 Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Wed, 4 Sep 2024 16:31:06 +0200 Subject: [PATCH 07/18] Test ssl_pthread_server Test ssl_pthread_server with both TLS 1.2 and TLS 1.3. Test against both OpenSSL and GnuTLS. In the server, flush more often. Otherwise, when stdout is redirected to a file, the server gets killed before it writes important information, such as the logs that we expect in the test cases. Clean up compile-time requirements in ssl_pthread_server.c: any certificate-based key exchange is ok, so don't insist on built-in RSA. Signed-off-by: Gilles Peskine --- programs/ssl/ssl_pthread_server.c | 37 +++++++++++++++----------- tests/opt-testcases/sample.sh | 44 +++++++++++++++++++++++++++++++ tests/ssl-opt.sh | 6 +++++ 3 files changed, 71 insertions(+), 16 deletions(-) diff --git a/programs/ssl/ssl_pthread_server.c b/programs/ssl/ssl_pthread_server.c index fcb8f2f4d5..7edf4a81b0 100644 --- a/programs/ssl/ssl_pthread_server.c +++ b/programs/ssl/ssl_pthread_server.c @@ -10,20 +10,21 @@ #include "mbedtls/platform.h" -#if !defined(MBEDTLS_BIGNUM_C) || !defined(MBEDTLS_ENTROPY_C) || \ - !defined(MBEDTLS_SSL_TLS_C) || !defined(MBEDTLS_SSL_SRV_C) || \ - !defined(MBEDTLS_NET_C) || !defined(MBEDTLS_RSA_C) || \ - !defined(MBEDTLS_CTR_DRBG_C) || !defined(MBEDTLS_X509_CRT_PARSE_C) || \ - !defined(MBEDTLS_FS_IO) || !defined(MBEDTLS_THREADING_C) || \ - !defined(MBEDTLS_THREADING_PTHREAD) || !defined(MBEDTLS_PEM_PARSE_C) +#if !defined(MBEDTLS_ENTROPY_C) || !defined(MBEDTLS_CTR_DRBG_C) || \ + !defined(MBEDTLS_NET_C) || !defined(MBEDTLS_SSL_SRV_C) || \ + !defined(MBEDTLS_PEM_PARSE_C) || !defined(MBEDTLS_X509_CRT_PARSE_C) int main(void) { - mbedtls_printf("MBEDTLS_BIGNUM_C and/or MBEDTLS_ENTROPY_C " - "and/or MBEDTLS_SSL_TLS_C and/or MBEDTLS_SSL_SRV_C and/or " - "MBEDTLS_NET_C and/or MBEDTLS_RSA_C and/or " - "MBEDTLS_CTR_DRBG_C and/or MBEDTLS_X509_CRT_PARSE_C and/or " - "MBEDTLS_THREADING_C and/or MBEDTLS_THREADING_PTHREAD " - "and/or MBEDTLS_PEM_PARSE_C not defined.\n"); + mbedtls_printf("MBEDTLS_ENTROPY_C and/or MBEDTLS_CTR_DRBG_C and/or " + "MBEDTLS_NET_C and/or MBEDTLS_SSL_SRV_C and/or " + "MBEDTLS_PEM_PARSE_C and/or MBEDTLS_X509_CRT_PARSE_C " + "not defined.\n"); + mbedtls_exit(0); +} +#elif !defined(MBEDTLS_THREADING_C) || !defined(MBEDTLS_THREADING_PTHREAD) +int main(void) +{ + mbedtls_printf("MBEDTLS_THREADING_PTHREAD not defined.\n"); mbedtls_exit(0); } #else @@ -123,6 +124,7 @@ static void *handle_ssl_connection(void *data) * 5. Handshake */ mbedtls_printf(" [ #%ld ] Performing the SSL/TLS handshake\n", thread_id); + fflush(stdout); while ((ret = mbedtls_ssl_handshake(&ssl)) != 0) { if (ret != MBEDTLS_ERR_SSL_WANT_READ && ret != MBEDTLS_ERR_SSL_WANT_WRITE) { @@ -138,6 +140,7 @@ static void *handle_ssl_connection(void *data) * 6. Read the HTTP Request */ mbedtls_printf(" [ #%ld ] < Read from client\n", thread_id); + fflush(stdout); do { len = sizeof(buf) - 1; @@ -170,6 +173,7 @@ static void *handle_ssl_connection(void *data) len = ret; mbedtls_printf(" [ #%ld ] %d bytes read\n=====\n%s\n=====\n", thread_id, len, (char *) buf); + fflush(stdout); if (ret > 0) { break; @@ -180,6 +184,7 @@ static void *handle_ssl_connection(void *data) * 7. Write the 200 Response */ mbedtls_printf(" [ #%ld ] > Write to client:\n", thread_id); + fflush(stdout); len = sprintf((char *) buf, HTTP_RESPONSE, mbedtls_ssl_get_ciphersuite(&ssl)); @@ -201,6 +206,7 @@ static void *handle_ssl_connection(void *data) len = ret; mbedtls_printf(" [ #%ld ] %d bytes written\n=====\n%s\n=====\n", thread_id, len, (char *) buf); + fflush(stdout); mbedtls_printf(" [ #%ld ] . Closing the connection...", thread_id); @@ -214,6 +220,7 @@ static void *handle_ssl_connection(void *data) } mbedtls_printf(" ok\n"); + fflush(stdout); ret = 0; @@ -442,6 +449,7 @@ reset: * 3. Wait until a client connects */ mbedtls_printf(" [ main ] Waiting for a remote connection\n"); + fflush(stdout); if ((ret = mbedtls_net_accept(&listen_fd, &client_fd, NULL, 0, NULL)) != 0) { @@ -483,7 +491,4 @@ exit: mbedtls_exit(ret); } -#endif /* MBEDTLS_BIGNUM_C && MBEDTLS_ENTROPY_C && - MBEDTLS_SSL_TLS_C && MBEDTLS_SSL_SRV_C && MBEDTLS_NET_C && - MBEDTLS_RSA_C && MBEDTLS_CTR_DRBG_C && MBEDTLS_THREADING_C && - MBEDTLS_THREADING_PTHREAD && MBEDTLS_PEM_PARSE_C */ +#endif /* configuration allows running this program */ diff --git a/tests/opt-testcases/sample.sh b/tests/opt-testcases/sample.sh index 82a95b8b9c..4684172c3b 100644 --- a/tests/opt-testcases/sample.sh +++ b/tests/opt-testcases/sample.sh @@ -118,3 +118,47 @@ run_test "Sample: ssl_server, gnutls client, TLS 1.3" \ -c "Description:.*TLS1.3" \ -S "error" \ -C "ERROR" + +requires_protocol_version tls12 +run_test "Sample: ssl_pthread_server, openssl client, TLS 1.2" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_pthread_server" \ + "$O_CLI -tls1_2" \ + 0 \ + -s "Successful connection using: TLS-" \ + -c "New, TLSv1.2, Cipher is" \ + -S "error" \ + -C "ERROR" + +requires_protocol_version tls12 +run_test "Sample: ssl_pthread_server, gnutls client, TLS 1.2" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_pthread_server" \ + "$G_CLI --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.2 localhost" \ + 0 \ + -s "Successful connection using: TLS-" \ + -c "Description:.*TLS1.2" \ + -S "error" \ + -C "ERROR" + +requires_protocol_version tls13 +run_test "Sample: ssl_pthread_server, openssl client, TLS 1.3" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_pthread_server" \ + "$O_CLI -tls1_3" \ + 0 \ + -s "Successful connection using: TLS1-3-" \ + -c "New, TLSv1.3, Cipher is" \ + -S "error" \ + -C "ERROR" + +requires_protocol_version tls13 +run_test "Sample: ssl_pthread_server, gnutls client, TLS 1.3" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_pthread_server" \ + "$G_CLI --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.3 localhost" \ + 0 \ + -s "Successful connection using: TLS1-3-" \ + -c "Description:.*TLS1.3" \ + -S "error" \ + -C "ERROR" diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh index 7715254d07..ca1b6ca6d6 100755 --- a/tests/ssl-opt.sh +++ b/tests/ssl-opt.sh @@ -500,6 +500,7 @@ detect_required_features() { requires_config_enabled MBEDTLS_SSL_CLI_C requires_certificate_authentication ;; + *"programs/ssl/ssl_pthread_server "*|\ *"programs/ssl/ssl_server "*) requires_config_enabled MBEDTLS_CTR_DRBG_C requires_config_enabled MBEDTLS_ENTROPY_C @@ -509,6 +510,11 @@ detect_required_features() { ;; esac + case " $CMD_LINE " in + *"programs/ssl/ssl_pthread_server "*) + requires_config_enabled MBEDTLS_THREADING_PTHREAD;; + esac + case "$CMD_LINE" in *[-_\ =]psk*|*[-_\ =]PSK*) :;; # No certificate requirement with PSK */server5*|\ From 2a0af359f1f22fd2ceef86ce6cd8104c69c18dec Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Wed, 4 Sep 2024 17:47:14 +0200 Subject: [PATCH 08/18] Test ssl_fork_server Test ssl_fork_server with both TLS 1.2 and TLS 1.3. Test against both OpenSSL and GnuTLS. In the server, flush more often. Otherwise, when stdout is redirected to a file, the server gets killed before it writes important information, such as the logs that we expect in the test cases. In the server, only write output for 10 seconds, not 100. That's enough time to start concurrent clients if desired. 100 seconds causes ssl-opt to take a very long time when the client actually listens to the whole input (which `gnutls-cli` does, but not `openssl s_client`). Clean up compile-time requirements in ssl_fork_server.c: any certificate-based key exchange is ok, so don't insist on built-in RSA. Signed-off-by: Gilles Peskine --- programs/ssl/ssl_fork_server.c | 35 ++++++++++++++------------- tests/opt-testcases/sample.sh | 44 ++++++++++++++++++++++++++++++++++ tests/ssl-opt.sh | 1 + 3 files changed, 63 insertions(+), 17 deletions(-) diff --git a/programs/ssl/ssl_fork_server.c b/programs/ssl/ssl_fork_server.c index f4822b7e68..0edadd4b74 100644 --- a/programs/ssl/ssl_fork_server.c +++ b/programs/ssl/ssl_fork_server.c @@ -9,22 +9,15 @@ #include "mbedtls/platform.h" -#if !defined(MBEDTLS_BIGNUM_C) || !defined(MBEDTLS_ENTROPY_C) || \ - !defined(MBEDTLS_SSL_TLS_C) || !defined(MBEDTLS_SSL_SRV_C) || \ - !defined(MBEDTLS_NET_C) || !defined(MBEDTLS_RSA_C) || \ - !defined(MBEDTLS_CTR_DRBG_C) || !defined(MBEDTLS_X509_CRT_PARSE_C) || \ - !defined(MBEDTLS_TIMING_C) || !defined(MBEDTLS_FS_IO) || \ - !defined(MBEDTLS_PEM_PARSE_C) -int main(int argc, char *argv[]) +#if !defined(MBEDTLS_ENTROPY_C) || !defined(MBEDTLS_CTR_DRBG_C) || \ + !defined(MBEDTLS_NET_C) || !defined(MBEDTLS_SSL_SRV_C) || \ + !defined(MBEDTLS_PEM_PARSE_C) || !defined(MBEDTLS_X509_CRT_PARSE_C) +int main(void) { - ((void) argc); - ((void) argv); - - mbedtls_printf("MBEDTLS_BIGNUM_C and/or MBEDTLS_ENTROPY_C " - "and/or MBEDTLS_SSL_TLS_C and/or MBEDTLS_SSL_SRV_C and/or " - "MBEDTLS_NET_C and/or MBEDTLS_RSA_C and/or " - "MBEDTLS_CTR_DRBG_C and/or MBEDTLS_X509_CRT_PARSE_C and/or " - "MBEDTLS_TIMING_C and/or MBEDTLS_PEM_PARSE_C not defined.\n"); + mbedtls_printf("MBEDTLS_ENTROPY_C and/or MBEDTLS_CTR_DRBG_C and/or " + "MBEDTLS_NET_C and/or MBEDTLS_SSL_SRV_C and/or " + "MBEDTLS_PEM_PARSE_C and/or MBEDTLS_X509_CRT_PARSE_C " + "not defined.\n"); mbedtls_exit(0); } #elif defined(_WIN32) @@ -225,6 +218,7 @@ int main(void) if (pid != 0) { mbedtls_printf(" ok\n"); mbedtls_net_close(&client_fd); + fflush(stdout); if ((ret = mbedtls_ctr_drbg_reseed(&ctr_drbg, (const unsigned char *) "parent", @@ -282,6 +276,7 @@ int main(void) } mbedtls_printf("pid %d: SSL handshake ok\n", pid); + fflush(stdout); /* * 6. Read the HTTP Request @@ -312,12 +307,14 @@ int main(void) mbedtls_printf("pid %d: mbedtls_ssl_read returned %d\n", pid, ret); break; } + fflush(stdout); break; } len = ret; mbedtls_printf("pid %d: %d bytes read\n\n%s", pid, len, (char *) buf); + fflush(stdout); if (ret > 0) { break; @@ -333,7 +330,7 @@ int main(void) len = sprintf((char *) buf, HTTP_RESPONSE, mbedtls_ssl_get_ciphersuite(&ssl)); - while (cnt++ < 100) { + while (cnt++ < 10) { while ((ret = mbedtls_ssl_write(&ssl, buf, len)) <= 0) { if (ret == MBEDTLS_ERR_NET_CONN_RESET) { mbedtls_printf( @@ -349,12 +346,16 @@ int main(void) } } len = ret; - mbedtls_printf("pid %d: %d bytes written\n\n%s\n", pid, len, (char *) buf); + mbedtls_printf("pid %d: %d bytes written (cnt=%d)\n\n%s\n", + pid, len, cnt, (char *) buf); + fflush(stdout); mbedtls_net_usleep(1000000); } mbedtls_ssl_close_notify(&ssl); + mbedtls_printf("pid %d: shutting down\n", pid); + fflush(stdout); goto exit; } diff --git a/tests/opt-testcases/sample.sh b/tests/opt-testcases/sample.sh index 4684172c3b..a74d597c28 100644 --- a/tests/opt-testcases/sample.sh +++ b/tests/opt-testcases/sample.sh @@ -119,6 +119,50 @@ run_test "Sample: ssl_server, gnutls client, TLS 1.3" \ -S "error" \ -C "ERROR" +requires_protocol_version tls12 +run_test "Sample: ssl_fork_server, openssl client, TLS 1.2" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_fork_server" \ + "$O_CLI -tls1_2" \ + 0 \ + -s "Successful connection using: TLS-" \ + -c "New, TLSv1.2, Cipher is" \ + -S "error" \ + -C "ERROR" + +requires_protocol_version tls12 +run_test "Sample: ssl_fork_server, gnutls client, TLS 1.2" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_fork_server" \ + "$G_CLI --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.2 localhost" \ + 0 \ + -s "Successful connection using: TLS-" \ + -c "Description:.*TLS1.2" \ + -S "error" \ + -C "ERROR" + +requires_protocol_version tls13 +run_test "Sample: ssl_fork_server, openssl client, TLS 1.3" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_fork_server" \ + "$O_CLI -tls1_3" \ + 0 \ + -s "Successful connection using: TLS1-3-" \ + -c "New, TLSv1.3, Cipher is" \ + -S "error" \ + -C "ERROR" + +requires_protocol_version tls13 +run_test "Sample: ssl_fork_server, gnutls client, TLS 1.3" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_fork_server" \ + "$G_CLI --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.3 localhost" \ + 0 \ + -s "Successful connection using: TLS1-3-" \ + -c "Description:.*TLS1.3" \ + -S "error" \ + -C "ERROR" + requires_protocol_version tls12 run_test "Sample: ssl_pthread_server, openssl client, TLS 1.2" \ -P 4433 \ diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh index ca1b6ca6d6..1b5931cb49 100755 --- a/tests/ssl-opt.sh +++ b/tests/ssl-opt.sh @@ -500,6 +500,7 @@ detect_required_features() { requires_config_enabled MBEDTLS_SSL_CLI_C requires_certificate_authentication ;; + *"programs/ssl/ssl_fork_server "*|\ *"programs/ssl/ssl_pthread_server "*|\ *"programs/ssl/ssl_server "*) requires_config_enabled MBEDTLS_CTR_DRBG_C From 9d104e9857faa1b366bdf2baaa08cc7a9fb56f05 Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Wed, 4 Sep 2024 16:51:50 +0200 Subject: [PATCH 09/18] Test dtls_server Test against both OpenSSL and GnuTLS. Don't use a proxy. It's not particularly useful here, and would complicate figuring out port numbers. Clean up compile-time requirements dtls_server.c: any certificate-based key exchange is ok, so don't insist on built-in RSA. Signed-off-by: Gilles Peskine --- programs/ssl/dtls_server.c | 28 +++++++++++++--------------- tests/opt-testcases/sample.sh | 24 ++++++++++++++++++++++++ tests/ssl-opt.sh | 3 ++- 3 files changed, 39 insertions(+), 16 deletions(-) diff --git a/programs/ssl/dtls_server.c b/programs/ssl/dtls_server.c index 732625e7fb..0a02694eb7 100644 --- a/programs/ssl/dtls_server.c +++ b/programs/ssl/dtls_server.c @@ -18,19 +18,19 @@ #define BIND_IP "::" #endif -#if !defined(MBEDTLS_SSL_SRV_C) || !defined(MBEDTLS_SSL_PROTO_DTLS) || \ - !defined(MBEDTLS_SSL_COOKIE_C) || !defined(MBEDTLS_NET_C) || \ - !defined(MBEDTLS_ENTROPY_C) || !defined(MBEDTLS_CTR_DRBG_C) || \ - !defined(MBEDTLS_X509_CRT_PARSE_C) || !defined(MBEDTLS_RSA_C) || \ - !defined(MBEDTLS_PEM_PARSE_C) || !defined(MBEDTLS_TIMING_C) - +#if !defined(MBEDTLS_ENTROPY_C) || !defined(MBEDTLS_CTR_DRBG_C) || \ + !defined(MBEDTLS_NET_C) || !defined(MBEDTLS_SSL_SRV_C) || \ + !defined(MBEDTLS_TIMING_C) || !defined(MBEDTLS_SSL_PROTO_DTLS) || \ + !defined(MBEDTLS_SSL_COOKIE_C) || \ + !defined(MBEDTLS_PEM_PARSE_C) || !defined(MBEDTLS_X509_CRT_PARSE_C) int main(void) { - printf("MBEDTLS_SSL_SRV_C and/or MBEDTLS_SSL_PROTO_DTLS and/or " - "MBEDTLS_SSL_COOKIE_C and/or MBEDTLS_NET_C and/or " - "MBEDTLS_ENTROPY_C and/or MBEDTLS_CTR_DRBG_C and/or " - "MBEDTLS_X509_CRT_PARSE_C and/or MBEDTLS_RSA_C and/or " - "MBEDTLS_PEM_PARSE_C and/or MBEDTLS_TIMING_C not defined.\n"); + mbedtls_printf("MBEDTLS_ENTROPY_C and/or MBEDTLS_CTR_DRBG_C and/or " + "MBEDTLS_NET_C and/or MBEDTLS_SSL_SRV_C and/or " + "MBEDTLS_TIMING_C and/or MBEDTLS_SSL_PROTO_DTLS and/or " + "MBEDTLS_SSL_COOKIE_C and/or " + "MBEDTLS_PEM_PARSE_C and/or MBEDTLS_X509_CRT_PARSE_C " + "not defined.\n"); mbedtls_exit(0); } #else @@ -402,7 +402,5 @@ exit: mbedtls_exit(ret); } -#endif /* MBEDTLS_SSL_SRV_C && MBEDTLS_SSL_PROTO_DTLS && - MBEDTLS_SSL_COOKIE_C && MBEDTLS_NET_C && MBEDTLS_ENTROPY_C && - MBEDTLS_CTR_DRBG_C && MBEDTLS_X509_CRT_PARSE_C && MBEDTLS_RSA_C - && MBEDTLS_PEM_PARSE_C && MBEDTLS_TIMING_C */ + +#endif /* configuration allows running this program */ diff --git a/tests/opt-testcases/sample.sh b/tests/opt-testcases/sample.sh index a74d597c28..7c5562ffbb 100644 --- a/tests/opt-testcases/sample.sh +++ b/tests/opt-testcases/sample.sh @@ -206,3 +206,27 @@ run_test "Sample: ssl_pthread_server, gnutls client, TLS 1.3" \ -c "Description:.*TLS1.3" \ -S "error" \ -C "ERROR" + +requires_protocol_version dtls12 +run_test "Sample: dtls_server, openssl client, DTLS 1.2" \ + -P 4433 \ + "$PROGRAMS_DIR/dtls_server" \ + "$O_CLI -dtls1_2" \ + 0 \ + -s "[1-9][0-9]* bytes read" \ + -s "[1-9][0-9]* bytes written" \ + -c "New, TLSv1.2, Cipher is" \ + -S "error" \ + -C "ERROR" + +requires_protocol_version dtls12 +run_test "Sample: dtls_server, gnutls client, DTLS 1.2" \ + -P 4433 \ + "$PROGRAMS_DIR/dtls_server" \ + "$G_CLI -u --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.2 localhost" \ + 0 \ + -s "[1-9][0-9]* bytes read" \ + -s "[1-9][0-9]* bytes written" \ + -c "Description:.*DTLS1.2" \ + -S "error" \ + -C "ERROR" diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh index 1b5931cb49..b32c63c8dc 100755 --- a/tests/ssl-opt.sh +++ b/tests/ssl-opt.sh @@ -500,6 +500,7 @@ detect_required_features() { requires_config_enabled MBEDTLS_SSL_CLI_C requires_certificate_authentication ;; + *"programs/ssl/dtls_server "*|\ *"programs/ssl/ssl_fork_server "*|\ *"programs/ssl/ssl_pthread_server "*|\ *"programs/ssl/ssl_server "*) @@ -1277,7 +1278,7 @@ wait_client_done() { # check if the given command uses dtls and sets global variable DTLS detect_dtls() { case "$1" in - *dtls=1*|*-dtls*|*-u*) DTLS=1;; + *dtls=1*|*-dtls*|*-u*|*/dtls_*) DTLS=1;; *) DTLS=0;; esac } From 6117a0cb8b6caa7786760aff446850328b0fbd43 Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Wed, 4 Sep 2024 23:32:42 +0200 Subject: [PATCH 10/18] Declare OpenSSL version dependency for TLS 1.3 test cases Signed-off-by: Gilles Peskine --- tests/opt-testcases/sample.sh | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/tests/opt-testcases/sample.sh b/tests/opt-testcases/sample.sh index 7c5562ffbb..73aad366de 100644 --- a/tests/opt-testcases/sample.sh +++ b/tests/opt-testcases/sample.sh @@ -27,9 +27,10 @@ run_test "Sample: ssl_client1, gnutls server, TLS 1.2" \ -C "error" requires_protocol_version tls13 +requires_openssl_tls1_3 run_test "Sample: ssl_client1, openssl server, TLS 1.3" \ -P 4433 \ - "$O_SRV -tls1_3" \ + "$O_NEXT_SRV -tls1_3" \ "$PROGRAMS_DIR/ssl_client1" \ 0 \ -c "New, TLSv1.3, Cipher is" \ @@ -98,10 +99,11 @@ run_test "Sample: ssl_server, gnutls client, TLS 1.2" \ -C "ERROR" requires_protocol_version tls13 +requires_openssl_tls1_3 run_test "Sample: ssl_server, openssl client, TLS 1.3" \ -P 4433 \ "$PROGRAMS_DIR/ssl_server" \ - "$O_CLI -tls1_3" \ + "$O_NEXT_CLI -tls1_3" \ 0 \ -s "Successful connection using: TLS1-3-" \ -c "New, TLSv1.3, Cipher is" \ @@ -142,10 +144,11 @@ run_test "Sample: ssl_fork_server, gnutls client, TLS 1.2" \ -C "ERROR" requires_protocol_version tls13 +requires_openssl_tls1_3 run_test "Sample: ssl_fork_server, openssl client, TLS 1.3" \ -P 4433 \ "$PROGRAMS_DIR/ssl_fork_server" \ - "$O_CLI -tls1_3" \ + "$O_NEXT_CLI -tls1_3" \ 0 \ -s "Successful connection using: TLS1-3-" \ -c "New, TLSv1.3, Cipher is" \ @@ -186,10 +189,11 @@ run_test "Sample: ssl_pthread_server, gnutls client, TLS 1.2" \ -C "ERROR" requires_protocol_version tls13 +requires_openssl_tls1_3 run_test "Sample: ssl_pthread_server, openssl client, TLS 1.3" \ -P 4433 \ "$PROGRAMS_DIR/ssl_pthread_server" \ - "$O_CLI -tls1_3" \ + "$O_NEXT_CLI -tls1_3" \ 0 \ -s "Successful connection using: TLS1-3-" \ -c "New, TLSv1.3, Cipher is" \ From 33aa202339681b8dddbbb1502ee565e84e2efdee Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Thu, 5 Sep 2024 13:05:49 +0200 Subject: [PATCH 11/18] Declare GnuTLS version dependency for TLS 1.3 test cases Signed-off-by: Gilles Peskine --- tests/opt-testcases/sample.sh | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/tests/opt-testcases/sample.sh b/tests/opt-testcases/sample.sh index 73aad366de..7a73cd6b6c 100644 --- a/tests/opt-testcases/sample.sh +++ b/tests/opt-testcases/sample.sh @@ -38,9 +38,10 @@ run_test "Sample: ssl_client1, openssl server, TLS 1.3" \ -C "error" requires_protocol_version tls13 +requires_gnutls_tls1_3 run_test "Sample: ssl_client1, gnutls server, TLS 1.3" \ -P 4433 \ - "$G_SRV --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.3" \ + "$G_NEXT_SRV --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.3" \ "$PROGRAMS_DIR/ssl_client1" \ 0 \ -s "Version: TLS1.3" \ @@ -111,10 +112,11 @@ run_test "Sample: ssl_server, openssl client, TLS 1.3" \ -C "ERROR" requires_protocol_version tls13 +requires_gnutls_tls1_3 run_test "Sample: ssl_server, gnutls client, TLS 1.3" \ -P 4433 \ "$PROGRAMS_DIR/ssl_server" \ - "$G_CLI --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.3 localhost" \ + "$G_NEXT_CLI --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.3 localhost" \ 0 \ -s "Successful connection using: TLS1-3-" \ -c "Description:.*TLS1.3" \ @@ -156,10 +158,11 @@ run_test "Sample: ssl_fork_server, openssl client, TLS 1.3" \ -C "ERROR" requires_protocol_version tls13 +requires_gnutls_tls1_3 run_test "Sample: ssl_fork_server, gnutls client, TLS 1.3" \ -P 4433 \ "$PROGRAMS_DIR/ssl_fork_server" \ - "$G_CLI --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.3 localhost" \ + "$G_NEXT_CLI --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.3 localhost" \ 0 \ -s "Successful connection using: TLS1-3-" \ -c "Description:.*TLS1.3" \ @@ -201,10 +204,11 @@ run_test "Sample: ssl_pthread_server, openssl client, TLS 1.3" \ -C "ERROR" requires_protocol_version tls13 +requires_gnutls_tls1_3 run_test "Sample: ssl_pthread_server, gnutls client, TLS 1.3" \ -P 4433 \ "$PROGRAMS_DIR/ssl_pthread_server" \ - "$G_CLI --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.3 localhost" \ + "$G_NEXT_CLI --priority=NORMAL:-VERS-TLS-ALL:+VERS-TLS1.3 localhost" \ 0 \ -s "Successful connection using: TLS1-3-" \ -c "Description:.*TLS1.3" \ From 8d64fe1c5631da29affc2ceac55fb2a164e2a957 Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Wed, 4 Sep 2024 23:33:36 +0200 Subject: [PATCH 12/18] Compatibiliy with older OpenSSL and GnuTLS GnuTLS 3.4.x doesn't allow repeated `-p PORT` arguments. OpenSSL 1.0.2 has different logs. For TLS 1.2 test cases, use a line that is present in logs from OpenSSL 1.0.2g, 3.3.0 and presumably all versions in between. Signed-off-by: Gilles Peskine --- tests/opt-testcases/sample.sh | 11 +++++------ tests/ssl-opt.sh | 6 +++++- 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/tests/opt-testcases/sample.sh b/tests/opt-testcases/sample.sh index 7a73cd6b6c..c85cd5b5d9 100644 --- a/tests/opt-testcases/sample.sh +++ b/tests/opt-testcases/sample.sh @@ -11,7 +11,7 @@ run_test "Sample: ssl_client1, openssl server, TLS 1.2" \ "$O_SRV -tls1_2" \ "$PROGRAMS_DIR/ssl_client1" \ 0 \ - -c "New, TLSv1.2, Cipher is" \ + -c "Protocol.*TLSv1.2" \ -S "ERROR" \ -C "error" @@ -56,7 +56,6 @@ run_test "Sample: dtls_client, openssl server, DTLS 1.2" \ "$PROGRAMS_DIR/dtls_client" \ 0 \ -s "Echo this" \ - -s "DONE" \ -c "Echo this" \ -c "[1-9][0-9]* bytes written" \ -c "[1-9][0-9]* bytes read" \ @@ -84,7 +83,7 @@ run_test "Sample: ssl_server, openssl client, TLS 1.2" \ "$O_CLI -tls1_2" \ 0 \ -s "Successful connection using: TLS-" \ - -c "New, TLSv1.2, Cipher is" \ + -c "Protocol.*TLSv1.2" \ -S "error" \ -C "ERROR" @@ -130,7 +129,7 @@ run_test "Sample: ssl_fork_server, openssl client, TLS 1.2" \ "$O_CLI -tls1_2" \ 0 \ -s "Successful connection using: TLS-" \ - -c "New, TLSv1.2, Cipher is" \ + -c "Protocol.*TLSv1.2" \ -S "error" \ -C "ERROR" @@ -176,7 +175,7 @@ run_test "Sample: ssl_pthread_server, openssl client, TLS 1.2" \ "$O_CLI -tls1_2" \ 0 \ -s "Successful connection using: TLS-" \ - -c "New, TLSv1.2, Cipher is" \ + -c "Protocol.*TLSv1.2" \ -S "error" \ -C "ERROR" @@ -223,7 +222,7 @@ run_test "Sample: dtls_server, openssl client, DTLS 1.2" \ 0 \ -s "[1-9][0-9]* bytes read" \ -s "[1-9][0-9]* bytes written" \ - -c "New, TLSv1.2, Cipher is" \ + -c "Protocol.*TLSv1.2" \ -S "error" \ -C "ERROR" diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh index b32c63c8dc..84d61fee90 100755 --- a/tests/ssl-opt.sh +++ b/tests/ssl-opt.sh @@ -1447,7 +1447,11 @@ analyze_test_commands() { # GnuTLS, override its port specification. if [ "$THIS_SRV_PORT" != "$SRV_PORT" ]; then case "$SRV_CMD" in - "$G_SRV"*|"$G_NEXT_SRV"*) SRV_CMD="$SRV_CMD -p $THIS_SRV_PORT";; + "$G_SRV"*|"$G_NEXT_SRV"*) + SRV_CMD=$( + printf %s "$SRV_CMD " | + sed -e "s/ -p $SRV_PORT / -p $THIS_SRV_PORT /" + );; "$O_SRV"*|"$O_NEXT_SRV"*) SRV_CMD="$SRV_CMD -accept $THIS_SRV_PORT";; esac fi From 3104685cc6840e05d68c184fff03beb339b20fbc Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Wed, 4 Sep 2024 23:36:14 +0200 Subject: [PATCH 13/18] ssl_server: Allow the client to close the connection first This is necessary when testing against OpenSSL 1.0.2g. In the server, flush more often. Otherwise, when stdout is redirected to a file, the server gets killed before it writes important information, such as the logs that we expect in the test cases. Signed-off-by: Gilles Peskine --- programs/ssl/ssl_server.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/programs/ssl/ssl_server.c b/programs/ssl/ssl_server.c index c3bd8fc610..aa06ad34be 100644 --- a/programs/ssl/ssl_server.c +++ b/programs/ssl/ssl_server.c @@ -312,16 +312,19 @@ reset: mbedtls_printf(" %d bytes written\n\n%s\n", len, (char *) buf); mbedtls_printf(" . Closing the connection..."); + fflush(stdout); while ((ret = mbedtls_ssl_close_notify(&ssl)) < 0) { if (ret != MBEDTLS_ERR_SSL_WANT_READ && - ret != MBEDTLS_ERR_SSL_WANT_WRITE) { + ret != MBEDTLS_ERR_SSL_WANT_WRITE && + ret != MBEDTLS_ERR_NET_CONN_RESET) { mbedtls_printf(" failed\n ! mbedtls_ssl_close_notify returned %d\n\n", ret); goto reset; } } mbedtls_printf(" ok\n"); + fflush(stdout); ret = 0; goto reset; From ff85e919145095181e8d83af40b48051fb7ac969 Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Thu, 5 Sep 2024 14:51:58 +0200 Subject: [PATCH 14/18] dtls_client: don't force the use of IPv6 Default to connecting to "localhost", like ssl_client1. Signed-off-by: Gilles Peskine --- programs/ssl/dtls_client.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/programs/ssl/dtls_client.c b/programs/ssl/dtls_client.c index 903b28d11a..8d7378a288 100644 --- a/programs/ssl/dtls_client.c +++ b/programs/ssl/dtls_client.c @@ -44,7 +44,7 @@ int main(void) #ifdef FORCE_IPV4 #define SERVER_ADDR "127.0.0.1" /* Forces IPv4 */ #else -#define SERVER_ADDR "::1" +#define SERVER_ADDR SERVER_NAME #endif #define MESSAGE "Echo this" From ca730a7c13e03058e43559dc96ffdcca8ce8805d Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Tue, 10 Sep 2024 00:03:18 +0200 Subject: [PATCH 15/18] Test SSL sample programs against each other and ssl_client2, ssl_server2 Signed-off-by: Gilles Peskine --- tests/opt-testcases/sample.sh | 135 +++++++++++++++++++++++++++++++++- 1 file changed, 134 insertions(+), 1 deletion(-) diff --git a/tests/opt-testcases/sample.sh b/tests/opt-testcases/sample.sh index c85cd5b5d9..bd800054fd 100644 --- a/tests/opt-testcases/sample.sh +++ b/tests/opt-testcases/sample.sh @@ -1,10 +1,23 @@ -# Test that SSL sample programs can interoperate with OpenSSL and GnuTLS. +# Test that SSL sample programs can interoperate with each other +# and with OpenSSL and GnuTLS. # Copyright The Mbed TLS Contributors # SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later : ${PROGRAMS_DIR:=../programs/ssl} +run_test "Sample: ssl_client1, ssl_server2" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_server2" \ + "$PROGRAMS_DIR/ssl_client1" \ + 0 \ + -s "[1-9][0-9]* bytes read" \ + -s "[1-9][0-9]* bytes written" \ + -c "[1-9][0-9]* bytes read" \ + -c "[1-9][0-9]* bytes written" \ + -S "error" \ + -C "error" + requires_protocol_version tls12 run_test "Sample: ssl_client1, openssl server, TLS 1.2" \ -P 4433 \ @@ -49,6 +62,22 @@ run_test "Sample: ssl_client1, gnutls server, TLS 1.3" \ -S "Error" \ -C "error" +# The server complains of extra data after it closes the connection +# because the client keeps sending data, so the server receives +# more application data when it expects a new handshake. We consider +# the test a success if both sides have sent and received application +# data, no matter what happens afterwards. +run_test "Sample: dtls_client, ssl_server2" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_server2 dtls=1 server_addr=localhost" \ + "$PROGRAMS_DIR/dtls_client" \ + 0 \ + -s "[1-9][0-9]* bytes read" \ + -s "[1-9][0-9]* bytes written" \ + -c "[1-9][0-9]* bytes read" \ + -c "[1-9][0-9]* bytes written" \ + -C "error" + requires_protocol_version dtls12 run_test "Sample: dtls_client, openssl server, DTLS 1.2" \ -P 4433 \ @@ -76,6 +105,30 @@ run_test "Sample: dtls_client, gnutls server, DTLS 1.2" \ -S "Error" \ -C "error" +run_test "Sample: ssl_server, ssl_client2" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_server" \ + "$PROGRAMS_DIR/ssl_client2" \ + 0 \ + -s "[1-9][0-9]* bytes read" \ + -s "[1-9][0-9]* bytes written" \ + -c "[1-9][0-9]* bytes read" \ + -c "[1-9][0-9]* bytes written" \ + -S "error" \ + -C "error" + +run_test "Sample: ssl_client1 with ssl_server" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_server" \ + "$PROGRAMS_DIR/ssl_client1" \ + 0 \ + -s "[1-9][0-9]* bytes read" \ + -s "[1-9][0-9]* bytes written" \ + -c "[1-9][0-9]* bytes read" \ + -c "[1-9][0-9]* bytes written" \ + -S "error" \ + -C "error" + requires_protocol_version tls12 run_test "Sample: ssl_server, openssl client, TLS 1.2" \ -P 4433 \ @@ -122,6 +175,30 @@ run_test "Sample: ssl_server, gnutls client, TLS 1.3" \ -S "error" \ -C "ERROR" +run_test "Sample: ssl_fork_server, ssl_client2" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_fork_server" \ + "$PROGRAMS_DIR/ssl_client2" \ + 0 \ + -s "[1-9][0-9]* bytes read" \ + -s "[1-9][0-9]* bytes written" \ + -c "[1-9][0-9]* bytes read" \ + -c "[1-9][0-9]* bytes written" \ + -S "error" \ + -C "error" + +run_test "Sample: ssl_client1 with ssl_fork_server" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_fork_server" \ + "$PROGRAMS_DIR/ssl_client1" \ + 0 \ + -s "[1-9][0-9]* bytes read" \ + -s "[1-9][0-9]* bytes written" \ + -c "[1-9][0-9]* bytes read" \ + -c "[1-9][0-9]* bytes written" \ + -S "error" \ + -C "error" + requires_protocol_version tls12 run_test "Sample: ssl_fork_server, openssl client, TLS 1.2" \ -P 4433 \ @@ -168,6 +245,30 @@ run_test "Sample: ssl_fork_server, gnutls client, TLS 1.3" \ -S "error" \ -C "ERROR" +run_test "Sample: ssl_pthread_server, ssl_client2" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_pthread_server" \ + "$PROGRAMS_DIR/ssl_client2" \ + 0 \ + -s "[1-9][0-9]* bytes read" \ + -s "[1-9][0-9]* bytes written" \ + -c "[1-9][0-9]* bytes read" \ + -c "[1-9][0-9]* bytes written" \ + -S "error" \ + -C "error" + +run_test "Sample: ssl_client1 with ssl_pthread_server" \ + -P 4433 \ + "$PROGRAMS_DIR/ssl_pthread_server" \ + "$PROGRAMS_DIR/ssl_client1" \ + 0 \ + -s "[1-9][0-9]* bytes read" \ + -s "[1-9][0-9]* bytes written" \ + -c "[1-9][0-9]* bytes read" \ + -c "[1-9][0-9]* bytes written" \ + -S "error" \ + -C "error" + requires_protocol_version tls12 run_test "Sample: ssl_pthread_server, openssl client, TLS 1.2" \ -P 4433 \ @@ -214,6 +315,38 @@ run_test "Sample: ssl_pthread_server, gnutls client, TLS 1.3" \ -S "error" \ -C "ERROR" +# The server complains of extra data after it closes the connection +# because the client keeps sending data, so the server receives +# more application data when it expects a new handshake. We consider +# the test a success if both sides have sent and received application +# data, no matter what happens afterwards. +run_test "Sample: dtls_client with dtls_server" \ + -P 4433 \ + "$PROGRAMS_DIR/dtls_server" \ + "$PROGRAMS_DIR/dtls_client" \ + 0 \ + -s "[1-9][0-9]* bytes read" \ + -s "[1-9][0-9]* bytes written" \ + -c "[1-9][0-9]* bytes read" \ + -c "[1-9][0-9]* bytes written" \ + -C "error" + +# The server complains of extra data after it closes the connection +# because the client keeps sending data, so the server receives +# more application data when it expects a new handshake. We consider +# the test a success if both sides have sent and received application +# data, no matter what happens afterwards. +run_test "Sample: ssl_client2, dtls_server" \ + -P 4433 \ + "$PROGRAMS_DIR/dtls_server" \ + "$PROGRAMS_DIR/ssl_client2 dtls=1" \ + 0 \ + -s "[1-9][0-9]* bytes read" \ + -s "[1-9][0-9]* bytes written" \ + -c "[1-9][0-9]* bytes read" \ + -c "[1-9][0-9]* bytes written" \ + -C "error" + requires_protocol_version dtls12 run_test "Sample: dtls_server, openssl client, DTLS 1.2" \ -P 4433 \ From 927f2f141898262232e5c638fbe6697e43390fc8 Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Wed, 11 Sep 2024 21:03:05 +0200 Subject: [PATCH 16/18] Note known issue about test cases skipped in TLS 1.3-only builds https://github.com/Mbed-TLS/mbedtls/issues/9560 Signed-off-by: Gilles Peskine --- tests/ssl-opt.sh | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh index 84d61fee90..3699f1789b 100755 --- a/tests/ssl-opt.sh +++ b/tests/ssl-opt.sh @@ -1812,7 +1812,10 @@ run_test() { # Check if we are trying to use an external tool which does not support ECDH EXT_WO_ECDH=$(use_ext_tool_without_ecdh_support "$SRV_CMD" "$CLI_CMD") - # Guess the TLS version which is going to be used + # Guess the TLS version which is going to be used. + # Note that this detection is wrong in some cases, which causes unduly + # skipped test cases in builds with TLS 1.3 but not TLS 1.2. + # https://github.com/Mbed-TLS/mbedtls/issues/9560 if [ "$EXT_WO_ECDH" = "no" ]; then TLS_VERSION=$(get_tls_version "$SRV_CMD" "$CLI_CMD") else From e6fd7d57ca871ed9cd2d0bec49344380526b95db Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Fri, 13 Sep 2024 18:15:13 +0200 Subject: [PATCH 17/18] Use OPENSSL_NEXT for a test case that uses IPv6 when available dtls_client connects to "localhost", which is usually IPv6 on modern systems. On our CI, $OPENSSL is OpenSSL 1.0.2g which doesn't support IPv6. Pitching dtls_client against $OPENSSL works on the CI at the moment, but only because the CI runs in Docker with default network settings which has IPv6 disabled. This would stop working if we changed the CI's Docker setup, and the test case is likely to fail on a developer machine. So switch the test case to using $OPENSSL_NEXT (which is a version of OpenSSL that has IPv6 support). Signed-off-by: Gilles Peskine --- tests/opt-testcases/sample.sh | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/tests/opt-testcases/sample.sh b/tests/opt-testcases/sample.sh index bd800054fd..8b2bc995a3 100644 --- a/tests/opt-testcases/sample.sh +++ b/tests/opt-testcases/sample.sh @@ -78,10 +78,20 @@ run_test "Sample: dtls_client, ssl_server2" \ -c "[1-9][0-9]* bytes written" \ -C "error" +# The dtls_client program connects to localhost. This test case fails on +# systems where the name "localhost" resolves to an IPv6 address, but +# the IPv6 connection is not possible. Possible reasons include: +# * OpenSSL is too old (IPv6 support was added in 1.1.0). +# * OpenSSL was built without IPv6 support. +# * A firewall blocks IPv6. +# +# To facilitate working with this test case, have it run with $OPENSSL_NEXT +# which is at least 1.1.1a. At the time it was introduced, this test case +# passed with OpenSSL 1.0.2g on an environment where IPv6 is disabled. requires_protocol_version dtls12 run_test "Sample: dtls_client, openssl server, DTLS 1.2" \ -P 4433 \ - "$O_SRV -dtls1_2" \ + "$O_NEXT_SRV -dtls1_2" \ "$PROGRAMS_DIR/dtls_client" \ 0 \ -s "Echo this" \ From 5bf54ca46f4c81bea9b47600c2c1c1a336a9c09f Mon Sep 17 00:00:00 2001 From: Gilles Peskine Date: Fri, 13 Sep 2024 23:08:48 +0200 Subject: [PATCH 18/18] Skip ssl_server in config-suite-b When building with `configs/config-suite-b.h`, the SSL I/O buffer size is 1024 bytes. Experimentally, this isn't quite enough for the test certificate that we use: the server aborts the handshake with `MBEDTLS_ERR_SSL_BUFFER_TOO_SMALL` raised from `mbedtls_ssl_write_certificate()`. State an ad hoc minimum output buffer size to skip testing `ssl_server` in `config-suite-b`. Signed-off-by: Gilles Peskine --- tests/ssl-opt.sh | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/tests/ssl-opt.sh b/tests/ssl-opt.sh index 3699f1789b..3315ba251b 100755 --- a/tests/ssl-opt.sh +++ b/tests/ssl-opt.sh @@ -509,6 +509,11 @@ detect_required_features() { requires_config_enabled MBEDTLS_PEM_PARSE_C requires_config_enabled MBEDTLS_SSL_SRV_C requires_certificate_authentication + # The actual minimum depends on the configuration since it's + # mostly about the certificate size. + # In config-suite-b.h, for the test certificates (server5.crt), + # 1024 is not enough. + requires_config_value_at_least MBEDTLS_SSL_OUT_CONTENT_LEN 2000 ;; esac