From f5aa20ceb1fd90839933fe9e2e34d2e9b14bd896 Mon Sep 17 00:00:00 2001 From: David Cooper Date: Wed, 22 Apr 2020 12:31:45 -0400 Subject: [PATCH 1/8] Extended run_server_preference() This commit extends run_server_preference() to list every cipher supported by each protocol even in cases in which the server does not enforce a preference order. For protocols where the server enforces a cipher order the list of supported ciphers is ordered by server preference (as now). For protocols where the server does not enforce a cipher order, the ciphers are listed by encryption strength (as run_cipher_per_proto() does). In order to implement this, ciphers_by_strength() was extended to offer a non-wide mode. --- testssl.sh | 214 ++++++++++++++++++----------------------------------- 1 file changed, 72 insertions(+), 142 deletions(-) diff --git a/testssl.sh b/testssl.sh index 0fd691b..771f8a3 100755 --- a/testssl.sh +++ b/testssl.sh @@ -3970,7 +3970,7 @@ run_allciphers() { # are good or bad) and list them in order to encryption strength. ciphers_by_strength() { local proto="$1" proto_hex="$2" proto_text="$3" - local using_sockets="$4" + local using_sockets="$4" wide="$5" local ossl_ciphers_proto local -i nr_ciphers nr_ossl_ciphers nr_nonossl_ciphers success local n sslvers auth mac hexc sslv2_ciphers="" cipher @@ -3983,13 +3983,12 @@ ciphers_by_strength() { local id local has_dh_bits="$HAS_DH_BITS" - pr_underline "$(printf -- "%b" "$proto_text")" # for local problem if it happens out " " if ! "$using_sockets" && ! locally_supported "$proto"; then return 0 fi - outln + "$wide" && outln [[ $(has_server_protocol "${proto:1}") -eq 1 ]] && return 0 @@ -4006,7 +4005,7 @@ ciphers_by_strength() { ciphers_found[nr_ciphers]=false sigalg[nr_ciphers]="" ossl_supported[nr_ciphers]=${TLS_CIPHER_OSSL_SUPPORTED[i]} - if "$using_sockets" && ! "$has_dh_bits" && ( [[ ${kx[nr_ciphers]} == "Kx=ECDH" ]] || [[ ${kx[nr_ciphers]} == "Kx=DH" ]] || [[ ${kx[nr_ciphers]} == "Kx=EDH" ]] ); then + if "$using_sockets" && "$wide" && ! "$has_dh_bits" && ( [[ ${kx[nr_ciphers]} == "Kx=ECDH" ]] || [[ ${kx[nr_ciphers]} == "Kx=DH" ]] || [[ ${kx[nr_ciphers]} == "Kx=EDH" ]] ); then ossl_supported[nr_ciphers]=false fi if [[ ${#hexc} -eq 9 ]]; then @@ -4022,16 +4021,16 @@ ciphers_by_strength() { normalized_hexcode[nr_ciphers]="x${hexc:2:2}${hexc:7:2}${hexc:12:2}" fi if ( "$using_sockets" || "${TLS_CIPHER_OSSL_SUPPORTED[i]}" ); then - if [[ ${#hexc} -eq 9 ]] && [[ "$proto_text" != SSLv2 ]]; then - if [[ "$proto_text" == TLS\ 1.3 ]]; then + if [[ ${#hexc} -eq 9 ]] && [[ "$proto" != -ssl2 ]]; then + if [[ "$proto" == -tls1_3 ]]; then [[ "${hexc:2:2}" == 13 ]] && nr_ciphers+=1 - elif [[ "$proto_text" == TLS\ 1.2 ]]; then + elif [[ "$proto" == -tls1_2 ]]; then [[ "${hexc:2:2}" != 13 ]] && nr_ciphers+=1 elif [[ ! "${TLS_CIPHER_RFC_NAME[i]}" =~ SHA256 ]] && [[ ! "${TLS_CIPHER_RFC_NAME[i]}" =~ SHA384 ]] && \ [[ "${TLS_CIPHER_RFC_NAME[i]}" != *_CCM ]] && [[ "${TLS_CIPHER_RFC_NAME[i]}" != *_CCM_8 ]]; then nr_ciphers+=1 fi - elif [[ ${#hexc} -eq 14 ]] && [[ "$proto_text" == SSLv2 ]]; then + elif [[ ${#hexc} -eq 14 ]] && [[ "$proto" == -ssl2 ]]; then sslv2_ciphers+=", ${hexcode[nr_ciphers]}" nr_ciphers+=1 fi @@ -4049,9 +4048,9 @@ ciphers_by_strength() { ossl_ciphers_proto="-tls1" fi while read hexc n ciph[nr_ciphers] sslvers kx[nr_ciphers] auth enc[nr_ciphers] mac export2[nr_ciphers]; do - if [[ "$proto_text" == TLS\ 1.3 ]]; then + if [[ "$proto" == -tls1_3 ]]; then [[ "${ciph[nr_ciphers]}" == TLS13* ]] || [[ "${ciph[nr_ciphers]}" == TLS_* ]] || continue - elif [[ "$proto_text" == "TLS 1.2" ]]; then + elif [[ "$proto" == -tls1_2 ]]; then if [[ "${ciph[nr_ciphers]}" == TLS13* ]] || [[ "${ciph[nr_ciphers]}" == TLS_* ]]; then continue fi @@ -4073,11 +4072,11 @@ ciphers_by_strength() { sslv2_sockets "${sslv2_ciphers:2}" "true" if [[ $? -eq 3 ]] && [[ "$V2_HELLO_CIPHERSPEC_LENGTH" -ne 0 ]]; then supported_sslv2_ciphers="$(grep "Supported cipher: " "$TEMPDIR/$NODEIP.parse_sslv2_serverhello.txt")" - "$SHOW_SIGALGO" && s="$(read_sigalg_from_file "$HOSTCERT")" + "$wide" && "$SHOW_SIGALGO" && s="$(read_sigalg_from_file "$HOSTCERT")" for (( i=0 ; i>$ERRFILE >$TMPFILE - if sclient_connect_successful $? $TMPFILE; then - offered_proto[i]=$(get_protocol $TMPFILE) - offered_cipher[i]=$(get_cipher $TMPFILE) - [[ ${offered_cipher[i]} == "0000" ]] && offered_cipher[i]="" # Hack! - if [[ "$DISPLAY_CIPHERNAMES" =~ rfc ]] && [[ -n "${offered_cipher[i]}" ]]; then - offered_cipher[i]="$(openssl2rfc "${offered_cipher[i]}")" - [[ -z "${offered_cipher[i]}" ]] && offered_cipher[i]=$(get_cipher $TMPFILE) - fi - [[ $DEBUG -ge 2 ]] && tmln_out "Default cipher for ${offered_proto[i]}: ${offered_cipher[i]}" - else - offered_proto[i]="" - offered_cipher[i]="" - fi + out " (server order)" + cipher_pref_check "$proto_ossl" "$proto_hex" "$proto_txt" "$using_sockets" fi - [[ -n "${offered_cipher[i]}" ]] && add_tls_offered "$proto_ossl" yes - i=$((i + 1)) - done + else + if [[ "$proto_ossl" == ssl2 ]] || ( [[ "$proto_ossl" != tls1_3 ]] && ! "$has_cipher_order" ]] ) || \ + ( [[ "$proto_ossl" == tls1_3 ]] && ! "$has_tls13_cipher_order" ]] ); then + ciphers_by_strength "-$proto_ossl" "$proto_hex" "$proto_txt" "$using_sockets" "$WIDE" + else + cipher_pref_check "$proto_ossl" "$proto_hex" "$proto_txt" "$using_sockets" + fi + fi + done <<< "$(tm_out " ssl2 22 SSLv2\n ssl3 00 SSLv3\n tls1 01 TLSv1\n tls1_1 02 TLSv1.1\n tls1_2 03 TLSv1.2\n tls1_3 04 TLSv1.3\n")" + outln + outln - for i in 1 2 3 4 5 6; do - if [[ -n "${offered_cipher[i]}" ]]; then # cipher not empty - if [[ -z "$prev_cipher" ]] || [[ "$prev_cipher" != "${offered_cipher[i]}" ]]; then - [[ -n "$prev_cipher" ]] && outln - str_len=${#offered_cipher[i]} - out " " - if [[ "$COLOR" -le 2 ]]; then - out "${offered_cipher[i]}" - else - pr_cipher_quality "${offered_cipher[i]}" - fi - out ":" - if [[ "$DISPLAY_CIPHERNAMES" =~ openssl ]]; then - for (( 1; str_len < 30; str_len++ )); do - out " " - done - else - for (( 1; str_len < 51; str_len++ )); do - out " " - done - fi - else - out ", " # same cipher --> only print out protocol behind it - fi - out "${offered_proto[i]}" - prev_cipher="${offered_cipher[i]}" - fi - fileout "cipher_order_${offered_proto[i]}" "INFO" "${offered_cipher[i]} at ${offered_proto[i]} $limitedsense" - done - outln "\n No further cipher order check has been done as order is determined by the client" - outln - fi return $ret } From a86ccb6968f116ffc50c19f06b01a9d3021252f0 Mon Sep 17 00:00:00 2001 From: Dirk Wetter Date: Thu, 23 Apr 2020 14:11:33 +0200 Subject: [PATCH 2/8] First round of polish of David's PR to extend run_server_preference() See #1580. This commit brings: * If there's no cipher for a protocol it adds a "\n - \n" (also for run_cipher_per_proto() ) * further output improvements * Cipher order --> Cipher listing per protocol * make some conditional statement easier to read (at least for me) New open points: - cipher_pref_check() doesn't save to PROTOS_OFFERED (was there before) (just stumbled over this but how about we also use get_protocol() / parse_tls_serverhello() - do we want run_allciphers() to be started by default? - $WIDE per default for run_cipher_per_proto() ? - probably better not to display text in round square brackets when there's no cipher: Hexcode Cipher Suite Name (OpenSSL) KeyExch. Encryption Bits Cipher Suite Name (IANA/RFC) ----------------------------------------------------------------------------------------------------------------------------- SSLv2 (listed by strength) SSLv3 (server order) TLSv1 (server order) TLSv1.1 (server order) TLSv1.2 (server order) xc02c ECDHE-ECDSA-AES256-GCM-SHA384 ECDH 256 AESGCM 256 TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384 [..] - when a server has no preference at all it shows in wide mode: Has server cipher order? no (NOT ok) -- only for TLS 1.3 Negotiated protocol TLSv1.3 Negotiated cipher TLS_AES_256_GCM_SHA384, 253 bit ECDH (X25519) Cipher listing per protocol Hexcode Cipher Suite Name (OpenSSL) KeyExch. Encryption Bits Cipher Suite Name (IANA/RFC) ----------------------------------------------------------------------------------------------------------------------------- SSLv2 - SSLv3 - TLSv1 (no server order, thus listed by strength) xc014 ECDHE-RSA-AES256-SHA ECDH 521 AES 256 TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA [..] e.g. dev.testssl.sh --- testssl.sh | 44 ++++++++++++++++++++++++++++---------------- 1 file changed, 28 insertions(+), 16 deletions(-) diff --git a/testssl.sh b/testssl.sh index 771f8a3..37c4e57 100755 --- a/testssl.sh +++ b/testssl.sh @@ -3984,13 +3984,17 @@ ciphers_by_strength() { local has_dh_bits="$HAS_DH_BITS" # for local problem if it happens - out " " + "$wide" || out " " if ! "$using_sockets" && ! locally_supported "$proto"; then + pr_local_problem "Your $OPENSSL does not support $proto" + "$wide" && outln return 0 fi - "$wide" && outln - [[ $(has_server_protocol "${proto:1}") -eq 1 ]] && return 0 + if [[ $(has_server_protocol "${proto:1}") -eq 1 ]]; then + "$wide" && outln " - " + return 0 + fi # get a list of all the cipher suites to test nr_ciphers=0 @@ -4005,7 +4009,8 @@ ciphers_by_strength() { ciphers_found[nr_ciphers]=false sigalg[nr_ciphers]="" ossl_supported[nr_ciphers]=${TLS_CIPHER_OSSL_SUPPORTED[i]} - if "$using_sockets" && "$wide" && ! "$has_dh_bits" && ( [[ ${kx[nr_ciphers]} == "Kx=ECDH" ]] || [[ ${kx[nr_ciphers]} == "Kx=DH" ]] || [[ ${kx[nr_ciphers]} == "Kx=EDH" ]] ); then + if "$using_sockets" && "$wide" && ! "$has_dh_bits" && \ + ( [[ ${kx[nr_ciphers]} == "Kx=ECDH" ]] || [[ ${kx[nr_ciphers]} == "Kx=DH" ]] || [[ ${kx[nr_ciphers]} == "Kx=EDH" ]] ); then ossl_supported[nr_ciphers]=false fi if [[ ${#hexc} -eq 9 ]]; then @@ -4289,7 +4294,7 @@ run_cipher_per_proto() { outln neat_header while read proto proto_hex proto_text; do - pr_underline "$(printf -- "%b" "$proto_text")" + prln_underline "$(printf -- "%b" "$proto_text")" ciphers_by_strength "$proto" "$proto_hex" "$proto_text" "$using_sockets" "true" done <<< "$(tm_out " -ssl2 22 SSLv2\n -ssl3 00 SSLv3\n -tls1 01 TLS 1\n -tls1_1 02 TLS 1.1\n -tls1_2 03 TLS 1.2\n -tls1_3 04 TLS 1.3")" return 0 @@ -6527,23 +6532,32 @@ run_server_preference() { # TODO: Shouldn't say "Cipher order" if the server does not always impose an order. # TODO: In non-wide mode, need to distinguish between those order by server preference and those ordered by encryption strength. - pr_bold " Cipher order" - "$WIDE" && outln && neat_header + pr_bold " Cipher listing per protocol" + "$WIDE" && outln "\n" && neat_header while read proto_ossl proto_hex proto_txt; do if "$WIDE"; then pr_underline "$(printf -- "%b" "$proto_txt")" - if [[ "$proto_ossl" == ssl2 ]] || ( [[ "$proto_ossl" != tls1_3 ]] && ! "$has_cipher_order" ]] ) || \ - ( [[ "$proto_ossl" == tls1_3 ]] && ! "$has_tls13_cipher_order" ]] ); then + # TODO: If there's no cipher we should consider not displaying the text in the round brackets) + # the following takes care of that but only if we know the protocol is not supported + if [[ $(has_server_protocol "$proto_ossl") -eq 1 ]]; then + "$WIDE" && outln "\n - " + continue + fi + # TODO: Also the fact that a protocol is not supported seems not to be saved by cipher_pref_check() + # (./testssl.sh --wide -p -P -E vs ./testssl.sh --wide -P -E ) + if [[ "$proto_ossl" == ssl2 ]] || \ + ( [[ "$proto_ossl" != tls1_3 ]] && ! "$has_cipher_order" ]] ) || \ + ( [[ "$proto_ossl" == tls1_3 ]] && ! "$has_tls13_cipher_order" ]] ); then if [[ "$proto_ossl" == ssl2 ]]; then - out " (listed by strength)" + outln " (listed by strength)" elif [[ "$proto_ossl" == tls1_3 ]]; then - out " (no server order, thus listed by strength)" + outln " (no server order, thus listed by strength)" else - pr_svrty_high " (no server order, thus listed by strength)" + prln_svrty_high " (no server order, thus listed by strength)" fi ciphers_by_strength "-$proto_ossl" "$proto_hex" "$proto_txt" "$using_sockets" "$WIDE" else - out " (server order)" + outln " (server order)" cipher_pref_check "$proto_ossl" "$proto_hex" "$proto_txt" "$using_sockets" fi else @@ -6559,6 +6573,7 @@ run_server_preference() { outln return $ret + # end of run_server_preference() } # arg1: true if the list that is returned does not need to be ordered by preference. @@ -6663,8 +6678,6 @@ cipher_pref_check() { return 0 fi - [[ $(has_server_protocol "$p") -eq 1 ]] && return 0 - if ( [[ $p != tls1_3 ]] || "$HAS_TLS13" ) && ( [[ $p != ssl3 ]] || "$HAS_SSL3" ); then if [[ $p == tls1_2 ]] && "$SERVER_SIZE_LIMIT_BUG"; then order="$(check_tls12_pref "$WIDE")" @@ -6869,7 +6882,6 @@ cipher_pref_check() { order="$rfc_order" fi - "$WIDE" && outln if [[ -n "$order" ]]; then add_tls_offered "$p" yes if "$WIDE"; then From 3e54f4e4cd158c11975222798316776b19add659 Mon Sep 17 00:00:00 2001 From: Dirk Wetter Date: Fri, 24 Apr 2020 13:32:26 +0200 Subject: [PATCH 3/8] Further changes to run_server_preference() In order not to provide redundant information run_allciphers() is now not being run via default (1). Therefore run_server_preference() runs always in wide mode. In order to archieve that cipher_pref_check() was modified to accept a fifth argument whether it'll run in wide mode. As of now cipher_pref_check() is only called by run_server_preference(), so the code referring to non-wide mode in cipher_pref_check() may also be deleted in the future. To provide a better view the run_fs() section is now being run after run_server_preference(). (1) saves also 5-6 seconds --- testssl.sh | 75 +++++++++++++++++++++++------------------------------- 1 file changed, 32 insertions(+), 43 deletions(-) diff --git a/testssl.sh b/testssl.sh index 37c4e57..90c655c 100755 --- a/testssl.sh +++ b/testssl.sh @@ -6530,47 +6530,35 @@ run_server_preference() { "$FAST" && using_sockets=false [[ $TLS_NR_CIPHERS == 0 ]] && using_sockets=false - # TODO: Shouldn't say "Cipher order" if the server does not always impose an order. - # TODO: In non-wide mode, need to distinguish between those order by server preference and those ordered by encryption strength. - pr_bold " Cipher listing per protocol" - "$WIDE" && outln "\n" && neat_header + pr_bold " Cipher per protocol" + outln "\n" && neat_header while read proto_ossl proto_hex proto_txt; do - if "$WIDE"; then - pr_underline "$(printf -- "%b" "$proto_txt")" - # TODO: If there's no cipher we should consider not displaying the text in the round brackets) - # the following takes care of that but only if we know the protocol is not supported - if [[ $(has_server_protocol "$proto_ossl") -eq 1 ]]; then - "$WIDE" && outln "\n - " - continue - fi - # TODO: Also the fact that a protocol is not supported seems not to be saved by cipher_pref_check() - # (./testssl.sh --wide -p -P -E vs ./testssl.sh --wide -P -E ) - if [[ "$proto_ossl" == ssl2 ]] || \ - ( [[ "$proto_ossl" != tls1_3 ]] && ! "$has_cipher_order" ]] ) || \ - ( [[ "$proto_ossl" == tls1_3 ]] && ! "$has_tls13_cipher_order" ]] ); then - if [[ "$proto_ossl" == ssl2 ]]; then - outln " (listed by strength)" - elif [[ "$proto_ossl" == tls1_3 ]]; then - outln " (no server order, thus listed by strength)" - else - prln_svrty_high " (no server order, thus listed by strength)" - fi - ciphers_by_strength "-$proto_ossl" "$proto_hex" "$proto_txt" "$using_sockets" "$WIDE" + pr_underline "$(printf -- "%b" "$proto_txt")" + # TODO: If there's no cipher we should consider not displaying the text in the round brackets) + # the following takes care of that but only if we know the protocol is not supported + if [[ $(has_server_protocol "$proto_ossl") -eq 1 ]]; then + outln "\n - " + continue + fi + # TODO: Also the fact that a protocol is not supported seems not to be saved by cipher_pref_check() + # (./testssl.sh --wide -p -P -E vs ./testssl.sh --wide -P -E ) + if [[ "$proto_ossl" == ssl2 ]] || \ + ( [[ "$proto_ossl" != tls1_3 ]] && ! "$has_cipher_order" ]] ) || \ + ( [[ "$proto_ossl" == tls1_3 ]] && ! "$has_tls13_cipher_order" ]] ); then + if [[ "$proto_ossl" == ssl2 ]]; then + outln " (listed by strength)" + elif [[ "$proto_ossl" == tls1_3 ]]; then + outln " (no server order, thus listed by strength)" else - outln " (server order)" - cipher_pref_check "$proto_ossl" "$proto_hex" "$proto_txt" "$using_sockets" + prln_svrty_high " (no server order, thus listed by strength)" fi + ciphers_by_strength "-$proto_ossl" "$proto_hex" "$proto_txt" "$using_sockets" "true" else - if [[ "$proto_ossl" == ssl2 ]] || ( [[ "$proto_ossl" != tls1_3 ]] && ! "$has_cipher_order" ]] ) || \ - ( [[ "$proto_ossl" == tls1_3 ]] && ! "$has_tls13_cipher_order" ]] ); then - ciphers_by_strength "-$proto_ossl" "$proto_hex" "$proto_txt" "$using_sockets" "$WIDE" - else - cipher_pref_check "$proto_ossl" "$proto_hex" "$proto_txt" "$using_sockets" - fi + outln " (server order)" + cipher_pref_check "$proto_ossl" "$proto_hex" "$proto_txt" "$using_sockets" "true" fi done <<< "$(tm_out " ssl2 22 SSLv2\n ssl3 00 SSLv3\n tls1 01 TLSv1\n tls1_1 02 TLSv1.1\n tls1_2 03 TLSv1.2\n tls1_3 04 TLSv1.3\n")" outln - outln return $ret # end of run_server_preference() @@ -6658,6 +6646,7 @@ check_tls12_pref() { cipher_pref_check() { local p="$1" proto_hex="$2" proto="$3" local using_sockets="$4" + local wide="$5" # at the moment this is called ALWAYS via run_server_preference and ALWAYS w true local tested_cipher cipher order rfc_cipher rfc_order local overflow_probe_cipherlist="ALL:-ECDHE-RSA-AES256-GCM-SHA384:-AES128-SHA:-DES-CBC3-SHA" local -i i nr_ciphers nr_nonossl_ciphers num_bundles bundle_size bundle end_of_bundle success @@ -6680,11 +6669,11 @@ cipher_pref_check() { if ( [[ $p != tls1_3 ]] || "$HAS_TLS13" ) && ( [[ $p != ssl3 ]] || "$HAS_SSL3" ); then if [[ $p == tls1_2 ]] && "$SERVER_SIZE_LIMIT_BUG"; then - order="$(check_tls12_pref "$WIDE")" + order="$(check_tls12_pref "$wide")" [[ "${order:0:1}" == \ ]] && order="${order:1}" ciphers_found="$order" fi - if "$WIDE" || [[ -z "$order" ]]; then + if "$wide" || [[ -z "$order" ]]; then tested_cipher=""; order=""; nr_ciphers_found=0 while true; do if [[ $p != tls1_3 ]]; then @@ -6713,7 +6702,7 @@ cipher_pref_check() { order+="$cipher " tested_cipher+=":-"$cipher "$FAST" && break - if "$WIDE"; then + if "$wide"; then for (( i=0; i < TLS_NR_CIPHERS; i++ )); do [[ "$cipher" == ${TLS_CIPHER_OSSL_NAME[i]} ]] && break done @@ -6843,7 +6832,7 @@ cipher_pref_check() { for (( i=0; i < nr_ciphers; i++ )); do [[ "$cipher" == ${rfc_ciph[i]} ]] && ciphers_found2[i]=true && break done - if "$WIDE"; then + if "$wide"; then for (( i=0; i < TLS_NR_CIPHERS; i++ )); do [[ "$cipher" == ${TLS_CIPHER_RFC_NAME[i]} ]] && break done @@ -6884,7 +6873,7 @@ cipher_pref_check() { if [[ -n "$order" ]]; then add_tls_offered "$p" yes - if "$WIDE"; then + if "$wide"; then for (( i=0 ; i Date: Mon, 27 Apr 2020 15:32:43 +0200 Subject: [PATCH 4/8] rename $p --> $proto_ossl in cipher_pref_check() plus remove redundant quotes for that --- testssl.sh | 40 ++++++++++++++++++++-------------------- 1 file changed, 20 insertions(+), 20 deletions(-) diff --git a/testssl.sh b/testssl.sh index 90c655c..f9567af 100755 --- a/testssl.sh +++ b/testssl.sh @@ -6282,7 +6282,7 @@ run_server_preference() { "$SSL_NATIVE" && using_sockets=false outln - pr_headlineln " Testing server preferences " + pr_headlineln " Testing server's cipher preferences " outln pr_bold " Has server cipher order? " @@ -6644,7 +6644,7 @@ check_tls12_pref() { cipher_pref_check() { - local p="$1" proto_hex="$2" proto="$3" + local proto_ossl="$1" proto_hex="$2" proto="$3" local using_sockets="$4" local wide="$5" # at the moment this is called ALWAYS via run_server_preference and ALWAYS w true local tested_cipher cipher order rfc_cipher rfc_order @@ -6658,17 +6658,17 @@ cipher_pref_check() { local ciphers_found_with_sockets order=""; ciphers_found_with_sockets=false - if [[ $p == ssl3 ]] && ! "$HAS_SSL3" && ! "$using_sockets"; then + if [[ $proto_ossl == ssl3 ]] && ! "$HAS_SSL3" && ! "$using_sockets"; then out "\n SSLv3: "; pr_local_problem "$OPENSSL doesn't support \"s_client -ssl3\""; return 0 fi - if [[ $p == tls1_3 ]] && ! "$HAS_TLS13" && ! "$using_sockets"; then + if [[ $proto_ossl == tls1_3 ]] && ! "$HAS_TLS13" && ! "$using_sockets"; then out "\n TLSv1.3 "; pr_local_problem "$OPENSSL doesn't support \"s_client -tls1_3\""; return 0 fi - if ( [[ $p != tls1_3 ]] || "$HAS_TLS13" ) && ( [[ $p != ssl3 ]] || "$HAS_SSL3" ); then - if [[ $p == tls1_2 ]] && "$SERVER_SIZE_LIMIT_BUG"; then + if ( [[ $proto_ossl != tls1_3 ]] || "$HAS_TLS13" ) && ( [[ $proto_ossl != ssl3 ]] || "$HAS_SSL3" ); then + if [[ $proto_ossl == tls1_2 ]] && "$SERVER_SIZE_LIMIT_BUG"; then order="$(check_tls12_pref "$wide")" [[ "${order:0:1}" == \ ]] && order="${order:1}" ciphers_found="$order" @@ -6676,7 +6676,7 @@ cipher_pref_check() { if "$wide" || [[ -z "$order" ]]; then tested_cipher=""; order=""; nr_ciphers_found=0 while true; do - if [[ $p != tls1_3 ]]; then + if [[ $proto_ossl != tls1_3 ]]; then if [[ -n "$ciphers_found" ]]; then ciphers_to_test="" for cipher in $ciphers_found; do @@ -6695,7 +6695,7 @@ cipher_pref_check() { [[ -z "$ciphers_to_test" ]] && break ciphers_to_test="-ciphersuites ${ciphers_to_test:1}" fi - $OPENSSL s_client $(s_client_options "$STARTTLS -"$p" $BUGS $ciphers_to_test -connect $NODEIP:$PORT $PROXY $SNI") >$ERRFILE >$TMPFILE + $OPENSSL s_client $(s_client_options "$STARTTLS -"$proto_ossl" $BUGS $ciphers_to_test -connect $NODEIP:$PORT $PROXY $SNI") >$ERRFILE >$TMPFILE sclient_connect_successful $? $TMPFILE || break cipher=$(get_cipher $TMPFILE) [[ -z "$cipher" ]] && break @@ -6710,7 +6710,7 @@ cipher_pref_check() { normalized_hexcode[nr_ciphers_found]="$(normalize_ciphercode "${TLS_CIPHER_HEXCODE[i]}")" ciph[nr_ciphers_found]="${TLS_CIPHER_OSSL_NAME[i]}" kx[nr_ciphers_found]="${TLS_CIPHER_KX[i]}" - [[ "$p" == tls1_3 ]] && kx[nr_ciphers_found]="$(read_dhtype_from_file $TMPFILE)" + [[ $proto_ossl == tls1_3 ]] && kx[nr_ciphers_found]="$(read_dhtype_from_file $TMPFILE)" if ( [[ ${kx[nr_ciphers_found]} == Kx=ECDH ]] || [[ ${kx[nr_ciphers_found]} == Kx=DH ]] || [[ ${kx[nr_ciphers_found]} == Kx=EDH ]] ); then kx[nr_ciphers_found]+=" $(read_dhbits_from_file "$TMPFILE" quiet)" fi @@ -6739,9 +6739,9 @@ cipher_pref_check() { rfc_ciph[nr_nonossl_ciphers]="${TLS_CIPHER_RFC_NAME[i]}" index[nr_nonossl_ciphers]=$i # Only test ciphers that are relevant to the protocol. - if [[ "$p" == tls1_3 ]]; then - [[ "${hexc:2:2}" == "13" ]] && nr_nonossl_ciphers+=1 - elif [[ "$p" == tls1_2 ]]; then + if [[ $proto_ossl == tls1_3 ]]; then + [[ "${hexc:2:2}" == 13 ]] && nr_nonossl_ciphers+=1 + elif [[ $proto_ossl == tls1_2 ]]; then [[ "${hexc:2:2}" != 13 ]] && nr_nonossl_ciphers+=1 elif [[ ! "${TLS_CIPHER_RFC_NAME[i]}" =~ SHA256 ]] && \ [[ ! "${TLS_CIPHER_RFC_NAME[i]}" =~ SHA384 ]] && \ @@ -6756,7 +6756,7 @@ cipher_pref_check() { if [[ $nr_nonossl_ciphers -eq 0 ]]; then num_bundles=0 - elif [[ $p != tls1_2 ]] || ! "$SERVER_SIZE_LIMIT_BUG"; then + elif [[ $proto_ossl != tls1_2 ]] || ! "$SERVER_SIZE_LIMIT_BUG"; then num_bundles=1 bundle_size=$nr_nonossl_ciphers else @@ -6785,7 +6785,7 @@ cipher_pref_check() { i=${index[i]} ciphers_found[i]=true ciphers_found_with_sockets=true - if [[ $p != tls1_2 ]] || ! "$SERVER_SIZE_LIMIT_BUG"; then + if [[ $proto_ossl != tls1_2 ]] || ! "$SERVER_SIZE_LIMIT_BUG"; then # Throw out the results found so far and start over using just sockets bundle=$num_bundles for (( i=0; i < TLS_NR_CIPHERS; i++ )); do @@ -6808,9 +6808,9 @@ cipher_pref_check() { ciphers_found2[nr_ciphers]=false hexcode[nr_ciphers]="${hexc:2:2},${hexc:7:2}" rfc_ciph[nr_ciphers]="${TLS_CIPHER_RFC_NAME[i]}" - if [[ "$p" == "tls1_3" ]]; then + if [[ $proto_ossl == "tls1_3" ]]; then [[ "${hexc:2:2}" == "13" ]] && nr_ciphers+=1 - elif [[ "$p" == "tls1_2" ]]; then + elif [[ $proto_ossl == "tls1_2" ]]; then [[ "${hexc:2:2}" != "13" ]] && nr_ciphers+=1 elif [[ ! "${TLS_CIPHER_RFC_NAME[i]}" =~ SHA256 ]] && \ [[ ! "${TLS_CIPHER_RFC_NAME[i]}" =~ SHA384 ]] && \ @@ -6840,7 +6840,7 @@ cipher_pref_check() { normalized_hexcode[nr_ciphers_found]="$(normalize_ciphercode "${TLS_CIPHER_HEXCODE[i]}")" ciph[nr_ciphers_found]="${TLS_CIPHER_OSSL_NAME[i]}" kx[nr_ciphers_found]="${TLS_CIPHER_KX[i]}" - [[ "$p" == tls1_3 ]] && kx[nr_ciphers_found]="$(read_dhtype_from_file "$TEMPDIR/$NODEIP.parse_tls_serverhello.txt")" + [[ $proto_ossl == tls1_3 ]] && kx[nr_ciphers_found]="$(read_dhtype_from_file "$TEMPDIR/$NODEIP.parse_tls_serverhello.txt")" if ( [[ ${kx[nr_ciphers_found]} == Kx=ECDH ]] || [[ ${kx[nr_ciphers_found]} == Kx=DH ]] || [[ ${kx[nr_ciphers_found]} == Kx=EDH ]] ); then kx[nr_ciphers_found]+=" $(read_dhbits_from_file "$TEMPDIR/$NODEIP.parse_tls_serverhello.txt" quiet)" fi @@ -6872,12 +6872,12 @@ cipher_pref_check() { fi if [[ -n "$order" ]]; then - add_tls_offered "$p" yes + add_tls_offered "$proto_ossl" yes if "$wide"; then for (( i=0 ; i Date: Mon, 27 Apr 2020 16:51:45 +0200 Subject: [PATCH 5/8] Remember better protocol settings in ciphers_by_strength() / cipher_pref_check() ... in cases where the protcol section has not been run before. Also add " -\n" on the screen/html if protocol is not supported. Also for SSLv2 which can be supported but at the same time not offer any ciphers mention there will be an output on the screen. --- testssl.sh | 63 ++++++++++++++++++++++++++++++++++++++---------------- 1 file changed, 45 insertions(+), 18 deletions(-) diff --git a/testssl.sh b/testssl.sh index f9567af..e4c5ab0 100755 --- a/testssl.sh +++ b/testssl.sh @@ -259,6 +259,7 @@ APP_TRAF_KEY_INFO="" # Information about the application traf TLS13_ONLY=false # Does the server support TLS 1.3 ONLY? OSSL_SHORTCUT=${OSSL_SHORTCUT:-false} # Hack: if during the scan turns out the OpenSSL binary suports TLS 1.3 would be a better choice, this enables it. TLS_EXTENSIONS="" +V2_HELLO_CIPHERSPEC_LENGTH=0 declare -r NPN_PROTOs="spdy/4a2,spdy/3,spdy/3.1,spdy/2,spdy/1,http/1.1" # alpn_protos needs to be space-separated, not comma-seperated, including odd ones observed @ facebook and others, old ones like h2-17 omitted as they could not be found declare -r ALPN_PROTOs="h2 spdy/3.1 http/1.1 grpc-exp h2-fb spdy/1 spdy/2 spdy/3 stun.turn stun.nat-discovery webrtc c-webrtc ftp" @@ -4045,7 +4046,7 @@ ciphers_by_strength() { # The OpenSSL ciphers function, prior to version 1.1.0, could only understand -ssl2, -ssl3, and -tls1. if [[ "$OSSL_NAME" =~ LibreSSL ]]; then ossl_ciphers_proto="" - elif [[ "$proto" == -ssl2 ]] || [[ "$proto" == -ssl3 ]] || \ + elif [[ $proto == -ssl2 ]] || [[ $proto == -ssl3 ]] || \ [[ $OSSL_VER_MAJOR.$OSSL_VER_MINOR == 1.1.0* ]] || [[ $OSSL_VER_MAJOR.$OSSL_VER_MINOR == 1.1.1* ]] || \ [[ $OSSL_VER_MAJOR.$OSSL_VER_MINOR == 3.0.0* ]]; then ossl_ciphers_proto="$proto" @@ -4072,23 +4073,32 @@ ciphers_by_strength() { done < <(actually_supported_osslciphers 'ALL:COMPLEMENTOFALL:@STRENGTH' 'ALL' "$ossl_ciphers_proto -V") fi - if [[ "$proto" == -ssl2 ]]; then + if [[ $proto == -ssl2 ]]; then if "$using_sockets"; then sslv2_sockets "${sslv2_ciphers:2}" "true" - if [[ $? -eq 3 ]] && [[ "$V2_HELLO_CIPHERSPEC_LENGTH" -ne 0 ]]; then - supported_sslv2_ciphers="$(grep "Supported cipher: " "$TEMPDIR/$NODEIP.parse_sslv2_serverhello.txt")" - "$wide" && "$SHOW_SIGALGO" && s="$(read_sigalg_from_file "$HOSTCERT")" - for (( i=0 ; i$TMPFILE 2>$ERRFILE Date: Mon, 27 Apr 2020 17:08:43 +0200 Subject: [PATCH 6/8] Renaming proto variables in cipher_pref_check() ... to be consistent with ciphers_by_strength: - proto --> proto_text - proto_ossl --> proto --- testssl.sh | 46 +++++++++++++++++++++++----------------------- 1 file changed, 23 insertions(+), 23 deletions(-) diff --git a/testssl.sh b/testssl.sh index e4c5ab0..fe29a31 100755 --- a/testssl.sh +++ b/testssl.sh @@ -4088,7 +4088,7 @@ ciphers_by_strength() { fi done else - outln " protocol support with no cipher " + outln " protocol supported with no cipher " fi else add_tls_offered ssl2 no @@ -6667,7 +6667,7 @@ check_tls12_pref() { # At the moment only called from run_server_preference() cipher_pref_check() { - local proto_ossl="$1" proto_hex="$2" proto="$3" + local proto="$1" proto_hex="$2" proto_text="$3" local using_sockets="$4" local wide="$5" # at the moment always = true local tested_cipher cipher order rfc_cipher rfc_order @@ -6681,17 +6681,17 @@ cipher_pref_check() { local ciphers_found_with_sockets order=""; ciphers_found_with_sockets=false - if [[ $proto_ossl == ssl3 ]] && ! "$HAS_SSL3" && ! "$using_sockets"; then + if [[ $proto == ssl3 ]] && ! "$HAS_SSL3" && ! "$using_sockets"; then out "\n SSLv3: "; pr_local_problem "$OPENSSL doesn't support \"s_client -ssl3\""; return 0 fi - if [[ $proto_ossl == tls1_3 ]] && ! "$HAS_TLS13" && ! "$using_sockets"; then + if [[ $proto == tls1_3 ]] && ! "$HAS_TLS13" && ! "$using_sockets"; then out "\n TLSv1.3 "; pr_local_problem "$OPENSSL doesn't support \"s_client -tls1_3\""; return 0 fi - if ( [[ $proto_ossl != tls1_3 ]] || "$HAS_TLS13" ) && ( [[ $proto_ossl != ssl3 ]] || "$HAS_SSL3" ); then - if [[ $proto_ossl == tls1_2 ]] && "$SERVER_SIZE_LIMIT_BUG"; then + if ( [[ $proto != tls1_3 ]] || "$HAS_TLS13" ) && ( [[ $proto != ssl3 ]] || "$HAS_SSL3" ); then + if [[ $proto == tls1_2 ]] && "$SERVER_SIZE_LIMIT_BUG"; then order="$(check_tls12_pref "$wide")" [[ "${order:0:1}" == \ ]] && order="${order:1}" ciphers_found="$order" @@ -6699,7 +6699,7 @@ cipher_pref_check() { if "$wide" || [[ -z "$order" ]]; then tested_cipher=""; order=""; nr_ciphers_found=0 while true; do - if [[ $proto_ossl != tls1_3 ]]; then + if [[ $proto != tls1_3 ]]; then if [[ -n "$ciphers_found" ]]; then ciphers_to_test="" for cipher in $ciphers_found; do @@ -6718,7 +6718,7 @@ cipher_pref_check() { [[ -z "$ciphers_to_test" ]] && break ciphers_to_test="-ciphersuites ${ciphers_to_test:1}" fi - $OPENSSL s_client $(s_client_options "$STARTTLS -"$proto_ossl" $BUGS $ciphers_to_test -connect $NODEIP:$PORT $PROXY $SNI") >$ERRFILE >$TMPFILE + $OPENSSL s_client $(s_client_options "$STARTTLS -"$proto" $BUGS $ciphers_to_test -connect $NODEIP:$PORT $PROXY $SNI") >$ERRFILE >$TMPFILE sclient_connect_successful $? $TMPFILE || break cipher=$(get_cipher $TMPFILE) [[ -z "$cipher" ]] && break @@ -6733,7 +6733,7 @@ cipher_pref_check() { normalized_hexcode[nr_ciphers_found]="$(normalize_ciphercode "${TLS_CIPHER_HEXCODE[i]}")" ciph[nr_ciphers_found]="${TLS_CIPHER_OSSL_NAME[i]}" kx[nr_ciphers_found]="${TLS_CIPHER_KX[i]}" - [[ $proto_ossl == tls1_3 ]] && kx[nr_ciphers_found]="$(read_dhtype_from_file $TMPFILE)" + [[ $proto == tls1_3 ]] && kx[nr_ciphers_found]="$(read_dhtype_from_file $TMPFILE)" if ( [[ ${kx[nr_ciphers_found]} == Kx=ECDH ]] || [[ ${kx[nr_ciphers_found]} == Kx=DH ]] || [[ ${kx[nr_ciphers_found]} == Kx=EDH ]] ); then kx[nr_ciphers_found]+=" $(read_dhbits_from_file "$TMPFILE" quiet)" fi @@ -6762,9 +6762,9 @@ cipher_pref_check() { rfc_ciph[nr_nonossl_ciphers]="${TLS_CIPHER_RFC_NAME[i]}" index[nr_nonossl_ciphers]=$i # Only test ciphers that are relevant to the protocol. - if [[ $proto_ossl == tls1_3 ]]; then + if [[ $proto == tls1_3 ]]; then [[ "${hexc:2:2}" == 13 ]] && nr_nonossl_ciphers+=1 - elif [[ $proto_ossl == tls1_2 ]]; then + elif [[ $proto == tls1_2 ]]; then [[ "${hexc:2:2}" != 13 ]] && nr_nonossl_ciphers+=1 elif [[ ! "${TLS_CIPHER_RFC_NAME[i]}" =~ SHA256 ]] && \ [[ ! "${TLS_CIPHER_RFC_NAME[i]}" =~ SHA384 ]] && \ @@ -6779,7 +6779,7 @@ cipher_pref_check() { if [[ $nr_nonossl_ciphers -eq 0 ]]; then num_bundles=0 - elif [[ $proto_ossl != tls1_2 ]] || ! "$SERVER_SIZE_LIMIT_BUG"; then + elif [[ $proto != tls1_2 ]] || ! "$SERVER_SIZE_LIMIT_BUG"; then num_bundles=1 bundle_size=$nr_nonossl_ciphers else @@ -6808,7 +6808,7 @@ cipher_pref_check() { i=${index[i]} ciphers_found[i]=true ciphers_found_with_sockets=true - if [[ $proto_ossl != tls1_2 ]] || ! "$SERVER_SIZE_LIMIT_BUG"; then + if [[ $proto != tls1_2 ]] || ! "$SERVER_SIZE_LIMIT_BUG"; then # Throw out the results found so far and start over using just sockets bundle=$num_bundles for (( i=0; i < TLS_NR_CIPHERS; i++ )); do @@ -6831,9 +6831,9 @@ cipher_pref_check() { ciphers_found2[nr_ciphers]=false hexcode[nr_ciphers]="${hexc:2:2},${hexc:7:2}" rfc_ciph[nr_ciphers]="${TLS_CIPHER_RFC_NAME[i]}" - if [[ $proto_ossl == "tls1_3" ]]; then + if [[ $proto == tls1_3 ]]; then [[ "${hexc:2:2}" == "13" ]] && nr_ciphers+=1 - elif [[ $proto_ossl == "tls1_2" ]]; then + elif [[ $proto == tls1_2 ]]; then [[ "${hexc:2:2}" != "13" ]] && nr_ciphers+=1 elif [[ ! "${TLS_CIPHER_RFC_NAME[i]}" =~ SHA256 ]] && \ [[ ! "${TLS_CIPHER_RFC_NAME[i]}" =~ SHA384 ]] && \ @@ -6863,7 +6863,7 @@ cipher_pref_check() { normalized_hexcode[nr_ciphers_found]="$(normalize_ciphercode "${TLS_CIPHER_HEXCODE[i]}")" ciph[nr_ciphers_found]="${TLS_CIPHER_OSSL_NAME[i]}" kx[nr_ciphers_found]="${TLS_CIPHER_KX[i]}" - [[ $proto_ossl == tls1_3 ]] && kx[nr_ciphers_found]="$(read_dhtype_from_file "$TEMPDIR/$NODEIP.parse_tls_serverhello.txt")" + [[ $proto == tls1_3 ]] && kx[nr_ciphers_found]="$(read_dhtype_from_file "$TEMPDIR/$NODEIP.parse_tls_serverhello.txt")" if ( [[ ${kx[nr_ciphers_found]} == Kx=ECDH ]] || [[ ${kx[nr_ciphers_found]} == Kx=DH ]] || [[ ${kx[nr_ciphers_found]} == Kx=EDH ]] ); then kx[nr_ciphers_found]+=" $(read_dhbits_from_file "$TEMPDIR/$NODEIP.parse_tls_serverhello.txt" quiet)" fi @@ -6895,31 +6895,31 @@ cipher_pref_check() { fi if [[ -n "$order" ]]; then - add_tls_offered "$proto_ossl" yes + add_tls_offered "$proto" yes if "$wide"; then for (( i=0 ; i Date: Mon, 27 Apr 2020 17:12:25 +0200 Subject: [PATCH 7/8] Rename add_tls_offered --> add_proto_offered ... last but not least SSLv2 and SSLv3 are no TLS protocols --- testssl.sh | 188 ++++++++++++++++++++++++++--------------------------- 1 file changed, 94 insertions(+), 94 deletions(-) diff --git a/testssl.sh b/testssl.sh index fe29a31..a85be9d 100755 --- a/testssl.sh +++ b/testssl.sh @@ -4077,7 +4077,7 @@ ciphers_by_strength() { if "$using_sockets"; then sslv2_sockets "${sslv2_ciphers:2}" "true" if [[ $? -eq 3 ]] ; then - add_tls_offered ssl2 yes + add_proto_offered ssl2 yes if [[ "$V2_HELLO_CIPHERSPEC_LENGTH" -ne 0 ]]; then supported_sslv2_ciphers="$(grep "Supported cipher: " "$TEMPDIR/$NODEIP.parse_sslv2_serverhello.txt")" "$wide" && "$SHOW_SIGALGO" && s="$(read_sigalg_from_file "$HOSTCERT")" @@ -4091,14 +4091,14 @@ ciphers_by_strength() { outln " protocol supported with no cipher " fi else - add_tls_offered ssl2 no + add_proto_offered ssl2 no "$wide" && outln " - " fi else $OPENSSL s_client $STARTTLS $BUGS -connect $NODEIP:$PORT $PROXY -ssl2 >$TMPFILE 2>$ERRFILE comes from run_prototest_openssl fileout "$jsonID" "HIGH" "$supported_no_ciph1" - add_tls_offered ssl3 yes + add_proto_offered ssl3 yes ;; 7) if "$using_sockets" ; then # can only happen in debug mode @@ -5153,10 +5153,10 @@ run_protocols() { fileout "$jsonID" "LOW" "offered (deprecated)" latest_supported="0301" latest_supported_string="TLSv1.0" - add_tls_offered tls1 yes + add_proto_offered tls1 yes ;; # nothing wrong with it -- per se 1) out "not offered" - add_tls_offered tls1 no + add_proto_offered tls1 no if [[ -z $latest_supported ]]; then outln fileout "$jsonID" "INFO" "not offered" # neither good or bad @@ -5166,7 +5166,7 @@ run_protocols() { fi ;; 2) pr_svrty_medium "not offered" - add_tls_offered tls1 no + add_proto_offered tls1 no if [[ "$DETECTED_TLS_VERSION" == 0300 ]]; then [[ $DEBUG -ge 1 ]] && tm_out " -- downgraded" outln @@ -5187,19 +5187,19 @@ run_protocols() { ;; 3) out "not offered, " fileout "$jsonID" "OK" "not offered" - add_tls_offered tls1 no + add_proto_offered tls1 no pr_warning "TLS downgraded to STARTTLS plaintext"; outln fileout "$jsonID" "WARN" "TLS downgraded to STARTTLS plaintext" ;; 4) out "likely not offered, " fileout "$jsonID" "INFO" "likely not offered" - add_tls_offered tls1 no + add_proto_offered tls1 no pr_warning "received 4xx/5xx after STARTTLS handshake"; outln "$debug_recomm" fileout "$jsonID" "WARN" "received 4xx/5xx after STARTTLS handshake${debug_recomm}" ;; 5) outln "$supported_no_ciph1" # protocol detected but no cipher --> comes from run_prototest_openssl fileout "$jsonID" "INFO" "$supported_no_ciph1" - add_tls_offered tls1 yes + add_proto_offered tls1 yes ;; 7) if "$using_sockets" ; then # can only happen in debug mode @@ -5231,10 +5231,10 @@ run_protocols() { fileout "$jsonID" "LOW" "offered (deprecated)" latest_supported="0302" latest_supported_string="TLSv1.1" - add_tls_offered tls1_1 yes + add_proto_offered tls1_1 yes ;; # nothing wrong with it 1) out "not offered" - add_tls_offered tls1_1 no + add_proto_offered tls1_1 no if [[ -z $latest_supported ]]; then outln fileout "$jsonID" "INFO" "is not offered" # neither good or bad @@ -5244,7 +5244,7 @@ run_protocols() { fi ;; 2) out "not offered" - add_tls_offered tls1_1 no + add_proto_offered tls1_1 no if [[ "$DETECTED_TLS_VERSION" == "$latest_supported" ]]; then [[ $DEBUG -ge 1 ]] && tm_out " -- downgraded" outln @@ -5268,19 +5268,19 @@ run_protocols() { ;; 3) out "not offered, " fileout "$jsonID" "OK" "not offered" - add_tls_offered tls1_1 no + add_proto_offered tls1_1 no pr_warning "TLS downgraded to STARTTLS plaintext"; outln fileout "$jsonID" "WARN" "TLS downgraded to STARTTLS plaintext" ;; 4) out "likely not offered, " fileout "$jsonID" "INFO" "is not offered" - add_tls_offered tls1_1 no + add_proto_offered tls1_1 no pr_warning "received 4xx/5xx after STARTTLS handshake"; outln "$debug_recomm" fileout "$jsonID" "WARN" "received 4xx/5xx after STARTTLS handshake${debug_recomm}" ;; 5) outln "$supported_no_ciph1" # protocol detected but no cipher --> comes from run_prototest_openssl fileout "$jsonID" "INFO" "$supported_no_ciph1" - add_tls_offered tls1_1 yes + add_proto_offered tls1_1 yes ;; 7) if "$using_sockets" ; then # can only happen in debug mode @@ -5342,9 +5342,9 @@ run_protocols() { fileout "$jsonID" "OK" "offered" latest_supported="0303" latest_supported_string="TLSv1.2" - add_tls_offered tls1_2 yes + add_proto_offered tls1_2 yes ;; # GCM cipher in TLS 1.2: very good! - 1) add_tls_offered tls1_2 no + 1) add_proto_offered tls1_2 no if "$offers_tls13"; then out "not offered" else @@ -5362,7 +5362,7 @@ run_protocols() { fileout "$jsonID" "CRITICAL" "connection failed rather than downgrading to $latest_supported_string" fi ;; - 2) add_tls_offered tls1_2 no + 2) add_proto_offered tls1_2 no pr_svrty_medium "not offered and downgraded to a weaker protocol" if [[ "$tls12_detected_version" == 0300 ]]; then detected_version_string="SSLv3" @@ -5390,19 +5390,19 @@ run_protocols() { ;; 3) out "not offered, " fileout "$jsonID" "INFO" "not offered" - add_tls_offered tls1_2 no + add_proto_offered tls1_2 no pr_warning "TLS downgraded to STARTTLS plaintext"; outln fileout "$jsonID" "WARN" "TLS downgraded to STARTTLS plaintext" ;; 4) out "likely "; pr_svrty_medium "not offered, " fileout "$jsonID" "MEDIUM" "not offered" - add_tls_offered tls1_2 no + add_proto_offered tls1_2 no pr_warning "received 4xx/5xx after STARTTLS handshake"; outln "$debug_recomm" fileout "$jsonID" "WARN" "received 4xx/5xx after STARTTLS handshake${debug_recomm}" ;; 5) outln "$supported_no_ciph1" # protocol detected, but no cipher --> comes from run_prototest_openssl fileout "$jsonID" "INFO" "$supported_no_ciph1" - add_tls_offered tls1_2 yes + add_proto_offered tls1_2 yes ;; 7) if "$using_sockets" ; then # can only happen in debug mode @@ -5496,7 +5496,7 @@ run_protocols() { fi latest_supported="0304" latest_supported_string="TLSv1.3" - add_tls_offered tls1_3 yes + add_proto_offered tls1_3 yes ;; 1) pr_svrty_low "not offered" if [[ -z $latest_supported ]]; then @@ -5506,7 +5506,7 @@ run_protocols() { prln_svrty_critical " -- connection failed rather than downgrading to $latest_supported_string" fileout "$jsonID" "CRITICAL" "connection failed rather than downgrading to $latest_supported_string" fi - add_tls_offered tls1_3 no + add_proto_offered tls1_3 no ;; 2) if [[ "$DETECTED_TLS_VERSION" == 0300 ]]; then detected_version_string="SSLv3" @@ -5529,23 +5529,23 @@ run_protocols() { prln_svrty_critical " -- server responded with version number ${DETECTED_TLS_VERSION:0:2}.${DETECTED_TLS_VERSION:2:2}" fileout "$jsonID" "CRITICAL" "server responded with version number ${DETECTED_TLS_VERSION:0:2}.${DETECTED_TLS_VERSION:2:2}" fi - add_tls_offered tls1_3 no + add_proto_offered tls1_3 no ;; 3) out "not offered " fileout "$jsonID" "INFO" "not offered" - add_tls_offered tls1_3 no + add_proto_offered tls1_3 no pr_warning "TLS downgraded to STARTTLS plaintext"; outln fileout "$jsonID" "WARN" "TLS downgraded to STARTTLS plaintext" ;; 4) out "likely not offered, " fileout "$jsonID" "INFO" "not offered" - add_tls_offered tls1_3 no + add_proto_offered tls1_3 no pr_warning "received 4xx/5xx after STARTTLS handshake"; outln "$debug_recomm" fileout "$jsonID" "WARN" "received 4xx/5xx after STARTTLS handshake${debug_recomm}" ;; 5) outln "$supported_no_ciph1" # protocol detected but no cipher --> comes from run_prototest_openssl fileout "$jsonID" "INFO" "$supported_no_ciph1" - add_tls_offered tls1_3 yes + add_proto_offered tls1_3 yes ;; 7) if "$using_sockets" ; then # can only happen in debug mode @@ -6330,14 +6330,14 @@ run_server_preference() { "ephemeralkey" sclient_success=$? if [[ $sclient_success -eq 0 ]]; then - add_tls_offered tls1_3 yes + add_proto_offered tls1_3 yes elif [[ $sclient_success -eq 2 ]]; then sclient_success=0 # 2: downgraded case $DETECTED_TLS_VERSION in - 0303) add_tls_offered tls1_2 yes ;; - 0302) add_tls_offered tls1_1 yes ;; - 0301) add_tls_offered tls1 yes ;; - 0300) add_tls_offered ssl3 yes ;; + 0303) add_proto_offered tls1_2 yes ;; + 0302) add_proto_offered tls1_1 yes ;; + 0301) add_proto_offered tls1 yes ;; + 0300) add_proto_offered ssl3 yes ;; esac fi if [[ $sclient_success -eq 0 ]] ; then @@ -6895,7 +6895,7 @@ cipher_pref_check() { fi if [[ -n "$order" ]]; then - add_tls_offered "$proto" yes + add_proto_offered "$proto" yes if "$wide"; then for (( i=0 ; i$TMPFILE 2>$ERRFILE $TMPFILE 2>$ERRFILE $TMPFILE 2>$ERRFILE /dev/null)") debugme tm_out " ($lines lines) " - add_tls_offered ssl2 yes + add_proto_offered ssl2 yes if [[ "$lines" -gt 1 ]]; then nr_ciphers_detected=$((V2_HELLO_CIPHERSPEC_LENGTH / 3)) if [[ 0 -eq "$nr_ciphers_detected" ]]; then @@ -16684,7 +16684,7 @@ run_beast(){ $OPENSSL s_client $(s_client_options "-state -"${proto}" $STARTTLS $BUGS -connect $NODEIP:$PORT $PROXY $SNI") 2>>$ERRFILE >$TMPFILE $TMPFILE 2>>$ERRFILE if sclient_auth $? $TMPFILE; then all_failed=false - add_tls_offered "${proto/-/}" yes + add_proto_offered "${proto/-/}" yes break fi done @@ -19479,11 +19479,11 @@ determine_optimal_proto() { tmp=${tmp/\./_} tmp=${tmp/v/} tmp="$(tolower $tmp)" - add_tls_offered "${tmp}" yes + add_proto_offered "${tmp}" yes debugme echo "one proto determined: $tmp" OPTIMAL_PROTO="" else - add_tls_offered "${proto/-/}" yes + add_proto_offered "${proto/-/}" yes OPTIMAL_PROTO="$proto" fi all_failed=false From 680aff48e4c999a859c2af4862968537f646c632 Mon Sep 17 00:00:00 2001 From: Dirk Wetter Date: Mon, 27 Apr 2020 17:19:30 +0200 Subject: [PATCH 8/8] Update documentation related to extended run_server_preference() --- doc/testssl.1 | 9 +++------ doc/testssl.1.html | 8 +++----- doc/testssl.1.md | 8 +++----- 3 files changed, 9 insertions(+), 16 deletions(-) diff --git a/doc/testssl.1 b/doc/testssl.1 index a8e8626..460996d 100644 --- a/doc/testssl.1 +++ b/doc/testssl.1 @@ -46,10 +46,10 @@ Any OpenSSL or LibreSSL version is needed as a helper\. Unlike previous versions 2) standard cipher categories to give you upfront an idea for the ciphers supported . .P -3) checks forward secrecy: ciphers and elliptical curves +3) server's cipher preferences (server order) . .P -4) server preferences (server order) +4) forward secrecy: ciphers and elliptical curves . .P 5) server defaults (certificate info, TLS extensions, session information) @@ -61,10 +61,7 @@ Any OpenSSL or LibreSSL version is needed as a helper\. Unlike previous versions 7) vulnerabilities . .P -8) testing each of 370 preconfigured ciphers -. -.P -9) client simulation +8) client simulation . .SH "OPTIONS AND PARAMETERS" Options are either short or long options\. Any long or short option requiring a value can be called with or without an equal sign\. E\.g\. \fBtestssl\.sh \-t=smtp \-\-wide \-\-openssl=/usr/bin/openssl \fR (short options with equal sign) is equivalent to \fBtestssl\.sh \-\-starttls smtp \-\-wide \-\-openssl /usr/bin/openssl \fR (long option without equal sign)\. Some command line options can also be preset via ENV variables\. \fBWIDE=true OPENSSL=/usr/bin/openssl testssl\.sh \-\-starttls=smtp \fR would be the equivalent to the aforementioned examples\. Preference has the command line over any environment variables\. diff --git a/doc/testssl.1.html b/doc/testssl.1.html index 5a6c392..4746b25 100644 --- a/doc/testssl.1.html +++ b/doc/testssl.1.html @@ -123,9 +123,9 @@ linked OpenSSL binaries for major operating systems are supplied in ./bin/

2) standard cipher categories to give you upfront an idea for the ciphers supported

-

3) checks forward secrecy: ciphers and elliptical curves

+

3) server's cipher preferences (server order)

-

4) server preferences (server order)

+

4) forward secrecy: ciphers and elliptical curves

5) server defaults (certificate info, TLS extensions, session information)

@@ -133,9 +133,7 @@ linked OpenSSL binaries for major operating systems are supplied in ./bin/

7) vulnerabilities

-

8) testing each of 370 preconfigured ciphers

- -

9) client simulation

+

8) client simulation

OPTIONS AND PARAMETERS

diff --git a/doc/testssl.1.md b/doc/testssl.1.md index 8f29a92..ac54ec4 100644 --- a/doc/testssl.1.md +++ b/doc/testssl.1.md @@ -42,9 +42,9 @@ linked OpenSSL binaries for major operating systems are supplied in `./bin/`. 2) standard cipher categories to give you upfront an idea for the ciphers supported -3) checks forward secrecy: ciphers and elliptical curves +3) server's cipher preferences (server order?) -4) server preferences (server order) +4) forward secrecy: ciphers and elliptical curves 5) server defaults (certificate info, TLS extensions, session information) @@ -52,9 +52,7 @@ linked OpenSSL binaries for major operating systems are supplied in `./bin/`. 7) vulnerabilities -8) testing each of 370 preconfigured ciphers - -9) client simulation +8) client simulation ## OPTIONS AND PARAMETERS