mirror of
				https://github.com/drwetter/testssl.sh.git
				synced 2025-10-31 13:55:25 +01:00 
			
		
		
		
	Merge branch '3.2' into diffing_openssls
This commit is contained in:
		| @@ -12,6 +12,7 @@ | |||||||
| * Improved compatibility with Open/LibreSSL versions not supporting TLS 1.0-1.1 anymore | * Improved compatibility with Open/LibreSSL versions not supporting TLS 1.0-1.1 anymore | ||||||
| * Renamed PFS/perfect forward secrecy --> FS/forward secrecy | * Renamed PFS/perfect forward secrecy --> FS/forward secrecy | ||||||
| * Cipher list straightening | * Cipher list straightening | ||||||
|  | * Support RFC 9150 cipher suites | ||||||
| * Improved mass testing | * Improved mass testing | ||||||
| * Better align colors of ciphers with standard cipherlists | * Better align colors of ciphers with standard cipherlists | ||||||
| * Save a few cycles for ROBOT | * Save a few cycles for ROBOT | ||||||
| @@ -23,13 +24,16 @@ | |||||||
| * Test for STARTTLS injection vulnerabilities (SMTP, POP3, IMAP) | * Test for STARTTLS injection vulnerabilities (SMTP, POP3, IMAP) | ||||||
| * STARTTLS: XMPP server support, plus new set of OpenSSL-bad binaries | * STARTTLS: XMPP server support, plus new set of OpenSSL-bad binaries | ||||||
| * Several code improvements to STARTTLS, also better detection when no STARTTLS is offered | * Several code improvements to STARTTLS, also better detection when no STARTTLS is offered | ||||||
|  | * Renegotiation checks more reliable against different servers | ||||||
| * STARTTLS on active directory service support | * STARTTLS on active directory service support | ||||||
| * Security fixes: DNS and other input from servers | * Security fixes: DNS and other input from servers | ||||||
| * Don't penalize missing trust in rating when CA not in Java store | * Don't penalize missing trust in rating when CA not in Java store | ||||||
| * Added support for certificates with EdDSA signatures and public keys | * Added support for certificates with EdDSA signatures and public keys | ||||||
| * Extract CA list shows supported certification authorities sent by the server | * Extract CA list shows supported certification authorities sent by the server | ||||||
|  | * Wildcard certificates: detection and warning | ||||||
| * TLS 1.2 and TLS 1.3 sig algs added | * TLS 1.2 and TLS 1.3 sig algs added | ||||||
| * Check for ffdhe groups | * Check for ffdhe groups | ||||||
|  | * Check for three KEMs in draft-kwiatkowski-tls-ecdhe-mlkem/draft-tls-westerbaan-xyber768d00 | ||||||
| * Show server supported signature algorithms | * Show server supported signature algorithms | ||||||
| * --add-ca can also now be a directory with \*.pem files | * --add-ca can also now be a directory with \*.pem files | ||||||
| * Warning of 398 day limit for certificates issued after 2020/9/1 | * Warning of 398 day limit for certificates issued after 2020/9/1 | ||||||
| @@ -41,6 +45,7 @@ | |||||||
| * DNS via proxy improvements | * DNS via proxy improvements | ||||||
| * Client simulation runs in wide mode which is even better readable | * Client simulation runs in wide mode which is even better readable | ||||||
| * Added --reqheader to support custom headers in HTTP requests | * Added --reqheader to support custom headers in HTTP requests | ||||||
|  | * Search for more HTTP security headers on the server | ||||||
| * Test for support for RFC 8879 certificate compression | * Test for support for RFC 8879 certificate compression | ||||||
| * Deprecating --fast and --ssl-native (warning but still av) | * Deprecating --fast and --ssl-native (warning but still av) | ||||||
| * Compatible to GNU grep 3.8 | * Compatible to GNU grep 3.8 | ||||||
|   | |||||||
| @@ -1,21 +1,25 @@ | |||||||
|  |  | ||||||
| ### Contributions / participation | ### Contributing / participating | ||||||
|  |  | ||||||
| is always welcome, here @ github or via e-mail. | Contributing / participating is always welcome! | ||||||
|  |  | ||||||
| Note please the following | Please note the following: | ||||||
|  |  | ||||||
| * Please read at least the [coding convention](https://github.com/testssl/testssl.sh/Coding_Convention.md). | * Please read the [coding convention](https://github.com/testssl/testssl.sh/blob/3.2/Coding_Convention.md). | ||||||
| * One PR per feature or bug fix or improvement. Please do not mix issues. | * If you have something new and/or bigger which you like to contribute, better open an issue first before you get frustrated. | ||||||
| * Document your PR, both in the PR and/or commit message and in the code. | * Please one pull request per feature or bug fix or improvement. Please do not mix issues. | ||||||
|  | * Documentation pays off in the long run. So please your document your code and the pull request and/or commit message. | ||||||
| * Please test your changes thoroughly as reliability is important for this project. You may want to check different servers with different settings. | * Please test your changes thoroughly as reliability is important for this project. You may want to check different servers with different settings. | ||||||
| * Travis runs automatically when anything is committed/PR'd. You should check any complains from Travis. Beforehand you can check with `prove -v`. | * GitHub actions are running automatically when anything is committed. You should see any complains. Beforehand you can check with `prove -v` from the "root dir" of this project. | ||||||
| * If it's a new feature please consider writing a unit test for it. You can use e.g. `t/20_baseline_ipv4_http.t` as a template. The general documentation for [Test::More](https://perldoc.perl.org/Test/More.html) is a good start. | * If it's a new feature, please consider writing a unit test for it. You can use e.g. `t/10_baseline_ipv4_http.t` or `t/61_diff_testsslsh.t` as a template. The general documentation for [Test::More](https://perldoc.perl.org/Test/More.html) is a good start. | ||||||
| * If it's a new feature it would need to be documented in the appropriate section in `help()` and in `~/doc/testssl.1.md` | * If it's a new feature, it would need to be documented in the appropriate section in `help()` and in `~/doc/testssl.1.md` | ||||||
|  |  | ||||||
| For questions just open an issue or feel free to send me an e-mail. | If you're interested in contributing and wonder how you can help, you can search for different tags in the issues (somewhat increasing degree of difficulty): | ||||||
|  | * [documentation](https://github.com/testssl/testssl.sh/issues?q=is:issue%20state:open%20label:documentation) | ||||||
|  | * [good first issue](https://github.com/testssl/testssl.sh/issues?q=is:issue%20state:open%20label:%22good%20first%20issue%22) | ||||||
|  | * [help wanted](https://github.com/testssl/testssl.sh/issues?q=is:issue%20state:open%20label:%22help%20wanted%22) | ||||||
|  | * [for grabs](https://github.com/testssl/testssl.sh/issues?q=is:issue%20state:open%20label:%22good%20first%20issue%22) | ||||||
|  |  | ||||||
|  | For questions just open an issue.  Thanks for reading this! | ||||||
|  |  | ||||||
| #### Patches via e-mail |  | ||||||
|  |  | ||||||
| Of course it is fine when you want to send in patches to use e-mail. For the address please grep for SWCONTACT in testssl.sh . |  | ||||||
| Let me know how you like them to be attributed. |  | ||||||
|   | |||||||
| @@ -10,7 +10,7 @@ for some new / advanced cipher suites and/or features which are not in the | |||||||
| official branch like (old version of the) CHACHA20+POLY1305 and CAMELLIA 256 bit ciphers. | official branch like (old version of the) CHACHA20+POLY1305 and CAMELLIA 256 bit ciphers. | ||||||
|  |  | ||||||
| The (stripped) binaries this directory are all compiled from my openssl snapshot | The (stripped) binaries this directory are all compiled from my openssl snapshot | ||||||
| (https://github.com/drwetter/openssl-1.0.2.bad) which adds a few bits to Peter | (https://github.com/testssl/openssl-1.0.2.bad) which adds a few bits to Peter | ||||||
| Mosman's openssl fork (https://github.com/PeterMosmans/openssl). Thx a bunch, Peter! | Mosman's openssl fork (https://github.com/PeterMosmans/openssl). Thx a bunch, Peter! | ||||||
| The few bits are IPv6 support (except IPV6 proxy) and some STARTTLS backports. | The few bits are IPv6 support (except IPV6 proxy) and some STARTTLS backports. | ||||||
|  |  | ||||||
| @@ -71,11 +71,11 @@ Compilation instructions | |||||||
| If you want to compile OpenSSL yourself, here are the instructions: | If you want to compile OpenSSL yourself, here are the instructions: | ||||||
|  |  | ||||||
| 1.) | 1.) | ||||||
|     git git clone https://github.com/drwetter/openssl-1.0.2-bad |     git git clone https://github.com/testssl/openssl-1.0.2-bad | ||||||
|     cd openssl |     cd openssl | ||||||
|  |  | ||||||
|  |  | ||||||
| 2.) configure the damned thing. Options I used (see https://github.com/drwetter/testssl.sh/blob/master/utils/make-openssl.sh) | 2.) configure the damned thing. Options I used (see https://github.com/testssl/testssl.sh/blob/master/utils/make-openssl.sh) | ||||||
|  |  | ||||||
| **for 64Bit including Kerberos ciphers:** | **for 64Bit including Kerberos ciphers:** | ||||||
|  |  | ||||||
|   | |||||||
| @@ -607,4 +607,4 @@ All native Windows platforms emulating Linux are known to be slow\. | |||||||
| .SH "BUGS" | .SH "BUGS" | ||||||
| Probably\. Current known ones and interface for filing new ones: https://testssl\.sh/bugs/ \. | Probably\. Current known ones and interface for filing new ones: https://testssl\.sh/bugs/ \. | ||||||
| .SH "SEE ALSO" | .SH "SEE ALSO" | ||||||
| \fBciphers\fR(1), \fBopenssl\fR(1), \fBs_client\fR(1), \fBx509\fR(1), \fBverify\fR(1), \fBocsp\fR(1), \fBcrl\fR(1), \fBbash\fR(1) and the websites https://testssl\.sh/ and https://github\.com/drwetter/testssl\.sh/ \. | \fBciphers\fR(1), \fBopenssl\fR(1), \fBs_client\fR(1), \fBx509\fR(1), \fBverify\fR(1), \fBocsp\fR(1), \fBcrl\fR(1), \fBbash\fR(1) and the websites https://testssl\.sh/ and https://github\.com/testssl/testssl\.sh/ \. | ||||||
|   | |||||||
| @@ -681,7 +681,7 @@ from. That helps us to get bugfixes, other feedback and more contributions.</p> | |||||||
|  |  | ||||||
| <h2 id="SEE-ALSO">SEE ALSO</h2> | <h2 id="SEE-ALSO">SEE ALSO</h2> | ||||||
|  |  | ||||||
| <p><span class="man-ref"><code>ciphers</code><span class="s">(1)</span></span>, <span class="man-ref"><code>openssl</code><span class="s">(1)</span></span>, <span class="man-ref"><code>s_client</code><span class="s">(1)</span></span>, <span class="man-ref"><code>x509</code><span class="s">(1)</span></span>, <span class="man-ref"><code>verify</code><span class="s">(1)</span></span>, <span class="man-ref"><code>ocsp</code><span class="s">(1)</span></span>, <span class="man-ref"><code>crl</code><span class="s">(1)</span></span>, <span class="man-ref"><code>bash</code><span class="s">(1)</span></span> and the websites https://testssl.sh/ and https://github.com/drwetter/testssl.sh/ .</p> | <p><span class="man-ref"><code>ciphers</code><span class="s">(1)</span></span>, <span class="man-ref"><code>openssl</code><span class="s">(1)</span></span>, <span class="man-ref"><code>s_client</code><span class="s">(1)</span></span>, <span class="man-ref"><code>x509</code><span class="s">(1)</span></span>, <span class="man-ref"><code>verify</code><span class="s">(1)</span></span>, <span class="man-ref"><code>ocsp</code><span class="s">(1)</span></span>, <span class="man-ref"><code>crl</code><span class="s">(1)</span></span>, <span class="man-ref"><code>bash</code><span class="s">(1)</span></span> and the websites https://testssl.sh/ and https://github.com/testssl/testssl.sh/ .</p> | ||||||
|  |  | ||||||
|   <ol class='man-decor man-foot man foot'> |   <ol class='man-decor man-foot man foot'> | ||||||
|     <li class='tl'></li> |     <li class='tl'></li> | ||||||
|   | |||||||
| @@ -587,4 +587,4 @@ Probably. Current known ones and interface for filing new ones: https://testssl. | |||||||
|  |  | ||||||
| ## SEE ALSO | ## SEE ALSO | ||||||
|  |  | ||||||
| `ciphers`(1), `openssl`(1), `s_client`(1), `x509`(1), `verify`(1), `ocsp`(1), `crl`(1), `bash`(1) and the websites https://testssl.sh/ and https://github.com/drwetter/testssl.sh/ . | `ciphers`(1), `openssl`(1), `s_client`(1), `x509`(1), `verify`(1), `ocsp`(1), `crl`(1), `bash`(1) and the websites https://testssl.sh/ and https://github.com/testssl/testssl.sh/ . | ||||||
|   | |||||||
| @@ -1,7 +1,7 @@ | |||||||
|  |  | ||||||
| # data we need for socket based handshakes | # data we need for socket based handshakes | ||||||
| # see #807 and #806 (especially | # see #807 and #806 (especially | ||||||
| # https://github.com/drwetter/testssl.sh/issues/806#issuecomment-318686374) | # https://github.com/testssl/testssl.sh/issues/806#issuecomment-318686374) | ||||||
|  |  | ||||||
| # 7 ciphers defined for TLS 1.3 in RFCs 8446 and 9150 | # 7 ciphers defined for TLS 1.3 in RFCs 8446 and 9150 | ||||||
| readonly TLS13_CIPHER=" | readonly TLS13_CIPHER=" | ||||||
|   | |||||||
| @@ -1,6 +1,6 @@ | |||||||
| #!/usr/bin/env perl | #!/usr/bin/env perl | ||||||
|  |  | ||||||
| # disabled as IPv6 is not supported by Travis, see https://github.com/drwetter/testssl.sh/issues/1177 | # disabled as IPv6 wasn't supported by Travis CI and isn't by GH action, see https://github.com/testssl/testssl.sh/issues/1177 | ||||||
|  |  | ||||||
| # Just a functional test, whether there are any problems on the client side | # Just a functional test, whether there are any problems on the client side | ||||||
| # Probably we could also inspect the JSON for any problems for | # Probably we could also inspect the JSON for any problems for | ||||||
|   | |||||||
| @@ -3,11 +3,10 @@ | |||||||
| # Baseline diff test against testssl.sh (csv output) | # Baseline diff test against testssl.sh (csv output) | ||||||
| # | # | ||||||
| # We don't use a full run yet and only the certificate section. | # We don't use a full run yet and only the certificate section. | ||||||
| # There we would need to blacklist at least: | # There we would need to blacklist more, like: | ||||||
| # cert_serialNumber, cert_fingerprintSHA1, cert_fingerprintSHA256, cert | # cert_serialNumber, cert_fingerprintSHA1, cert_fingerprintSHA256, cert | ||||||
| # cert_expirationStatus, cert_notBefore, cert_notAfter, cert_caIssuers, intermediate_cert | # cert_expirationStatus, cert_notBefore, cert_notAfter, cert_caIssuers, intermediate_cert | ||||||
| # | # | ||||||
| # help is appreciated here |  | ||||||
|  |  | ||||||
| use strict; | use strict; | ||||||
| use Test::More; | use Test::More; | ||||||
| @@ -16,55 +15,54 @@ use Text::Diff; | |||||||
|  |  | ||||||
| my $tests = 0; | my $tests = 0; | ||||||
| my $prg="./testssl.sh"; | my $prg="./testssl.sh"; | ||||||
| my $master_socket_csv="./t/baseline_data/default_testssl.csvfile"; | my $baseline_csv="./t/baseline_data/default_testssl.csvfile"; | ||||||
| my $socket_csv="tmp.csv"; | my $cat_csv="tmp.csv"; | ||||||
| my $check2run="-p -s -P --fs -h -U -c -q --ip=one --color 0 --csvfile $socket_csv"; | my $check2run="-p -s -P --fs -h -U -c -q --ip=one --color 0 --csvfile $cat_csv"; | ||||||
| #my $check2run="-p --color 0 --csvfile $socket_csv"; |  | ||||||
| my $uri="testssl.sh"; | my $uri="testssl.sh"; | ||||||
| my $diff=""; | my $diff=""; | ||||||
|  |  | ||||||
| die "Unable to open $prg" unless -f $prg; | die "Unable to open $prg" unless -f $prg; | ||||||
| die "Unable to open $master_socket_csv" unless -f $master_socket_csv; | die "Unable to open $baseline_csv" unless -f $baseline_csv; | ||||||
|  |  | ||||||
|  |  | ||||||
| # Provide proper start conditions | # Provide proper start conditions | ||||||
| unlink "tmp.csv"; | unlink $cat_csv; | ||||||
|  |  | ||||||
| # Title | my @args=("$prg", "$check2run", "$uri", "2>&1"); | ||||||
| printf "\n%s\n", "Diff unit test IPv4 against \"$uri\""; |  | ||||||
|  |  | ||||||
| #1 run | #1 run | ||||||
| `$prg $check2run $uri 2>&1`; | printf "\n%s\n", "Diff unit test (IPv4) against \"$uri\""; | ||||||
|  | printf "@args\n"; | ||||||
|  | system("@args") == 0 | ||||||
|  |      or die ("FAILED: \"@args\" "); | ||||||
|  |  | ||||||
| $diff = diff $socket_csv, $master_socket_csv; | $cat_csv=`cat $cat_csv`; | ||||||
|  | $baseline_csv=`cat $baseline_csv`; | ||||||
| $socket_csv=`cat tmp.csv`; |  | ||||||
| $master_socket_csv=`cat $master_socket_csv`; |  | ||||||
|  |  | ||||||
| # Filter for changes that are allowed to occur | # Filter for changes that are allowed to occur | ||||||
| $socket_csv=~ s/HTTP_clock_skew.*\n//g; | $cat_csv      =~ s/HTTP_clock_skew.*\n//g; | ||||||
| $master_socket_csv=~ s/HTTP_clock_skew.*\n//g; | $baseline_csv =~ s/HTTP_clock_skew.*\n//g; | ||||||
|  |  | ||||||
| # DROWN |  | ||||||
| $socket_csv=~ s/censys.io.*\n//g; |  | ||||||
| $master_socket_csv=~ s/censys.io.*\n//g; |  | ||||||
|  |  | ||||||
| # HTTP time | # HTTP time | ||||||
| $socket_csv=~ s/HTTP_headerTime.*\n//g; | $cat_csv      =~ s/HTTP_headerTime.*\n//g; | ||||||
| $master_socket_csv=~ s/HTTP_headerTime.*\n//g; | $baseline_csv =~ s/HTTP_headerTime.*\n//g; | ||||||
|  |  | ||||||
| # Compare the differences to the master file -- and print differences if there were detected. | # DROWN | ||||||
|  | $cat_csv      =~ s/censys.io.*\n//g; | ||||||
|  | $baseline_csv =~ s/censys.io.*\n//g; | ||||||
|  |  | ||||||
|  | $diff = diff \$cat_csv, \$baseline_csv; | ||||||
|  |  | ||||||
|  | # Compare the differences to the baseline file -- and print differences if there were detected. | ||||||
| # | # | ||||||
| cmp_ok($socket_csv, "eq", $master_socket_csv, "Check whether CSV output matches master file from $uri") or | ok($cat_csv eq $baseline_csv, "Check whether CSV output matches baseline file from $uri") or | ||||||
|      diag ("\n%s\n", "$diff"); |      diag ("\n%s\n", "$diff"); | ||||||
|  |  | ||||||
| $tests++; |  | ||||||
|  |  | ||||||
| unlink "tmp.csv"; | unlink "tmp.csv"; | ||||||
|  |  | ||||||
|  | $tests++; | ||||||
| done_testing($tests); | done_testing($tests); | ||||||
| printf "\n"; | printf "\n"; | ||||||
|  |  | ||||||
|  |  | ||||||
| #  vim:ts=5:sw=5:expandtab | # vim:ts=5:sw=5:expandtab | ||||||
|  |  | ||||||
|   | |||||||
| @@ -70,7 +70,7 @@ | |||||||
| "FS_TLS13_sig_algs","testssl.sh/81.169.166.184","443","INFO","RSA-PSS-RSAE+SHA256 RSA-PSS-RSAE+SHA384 RSA-PSS-RSAE+SHA512","","" | "FS_TLS13_sig_algs","testssl.sh/81.169.166.184","443","INFO","RSA-PSS-RSAE+SHA256 RSA-PSS-RSAE+SHA384 RSA-PSS-RSAE+SHA512","","" | ||||||
| "HTTP_status_code","testssl.sh/81.169.166.184","443","INFO","200 OK ('/')","","" | "HTTP_status_code","testssl.sh/81.169.166.184","443","INFO","200 OK ('/')","","" | ||||||
| "HTTP_clock_skew","testssl.sh/81.169.166.184","443","INFO","0 seconds from localtime","","" | "HTTP_clock_skew","testssl.sh/81.169.166.184","443","INFO","0 seconds from localtime","","" | ||||||
| "HTTP_headerTime","testssl.sh/81.169.166.184","443","INFO","1654006271","","" | "HTTP_headerTime","testssl.sh/81.169.166.184","443","INFO","1737570310","","" | ||||||
| "HSTS_time","testssl.sh/81.169.166.184","443","OK","362 days (=31337000 seconds) > 15552000 seconds","","" | "HSTS_time","testssl.sh/81.169.166.184","443","OK","362 days (=31337000 seconds) > 15552000 seconds","","" | ||||||
| "HSTS_subdomains","testssl.sh/81.169.166.184","443","INFO","only for this domain","","" | "HSTS_subdomains","testssl.sh/81.169.166.184","443","INFO","only for this domain","","" | ||||||
| "HSTS_preload","testssl.sh/81.169.166.184","443","INFO","domain is NOT marked for preloading","","" | "HSTS_preload","testssl.sh/81.169.166.184","443","INFO","domain is NOT marked for preloading","","" | ||||||
| @@ -81,6 +81,8 @@ | |||||||
| "X-Frame-Options","testssl.sh/81.169.166.184","443","OK","DENY","","" | "X-Frame-Options","testssl.sh/81.169.166.184","443","OK","DENY","","" | ||||||
| "X-Content-Type-Options","testssl.sh/81.169.166.184","443","OK","nosniff","","" | "X-Content-Type-Options","testssl.sh/81.169.166.184","443","OK","nosniff","","" | ||||||
| "Content-Security-Policy","testssl.sh/81.169.166.184","443","OK","script-src 'unsafe-inline'; style-src 'unsafe-inline' 'self'; object-src 'self'; base-uri 'none'; form-action 'none'; img-src 'self' ; default-src 'self'; frame-ancestors 'self'; upgrade-insecure-requests;","","" | "Content-Security-Policy","testssl.sh/81.169.166.184","443","OK","script-src 'unsafe-inline'; style-src 'unsafe-inline' 'self'; object-src 'self'; base-uri 'none'; form-action 'none'; img-src 'self' ; default-src 'self'; frame-ancestors 'self'; upgrade-insecure-requests;","","" | ||||||
|  | "Cross-Origin-Opener-Policy","testssl.sh/81.169.166.184","443","INFO","same-origin-allow-popups","","" | ||||||
|  | "Cross-Origin-Resource-Policy","testssl.sh/81.169.166.184","443","INFO","same-site","","" | ||||||
| "banner_reverseproxy","testssl.sh/81.169.166.184","443","INFO","--","","CWE-200" | "banner_reverseproxy","testssl.sh/81.169.166.184","443","INFO","--","","CWE-200" | ||||||
| "heartbleed","testssl.sh/81.169.166.184","443","OK","not vulnerable, no heartbeat extension","CVE-2014-0160","CWE-119" | "heartbleed","testssl.sh/81.169.166.184","443","OK","not vulnerable, no heartbeat extension","CVE-2014-0160","CWE-119" | ||||||
| "CCS","testssl.sh/81.169.166.184","443","OK","not vulnerable","CVE-2014-0224","CWE-310" | "CCS","testssl.sh/81.169.166.184","443","OK","not vulnerable","CVE-2014-0224","CWE-310" | ||||||
| @@ -95,7 +97,7 @@ | |||||||
| "SWEET32","testssl.sh/81.169.166.184","443","OK","not vulnerable","CVE-2016-2183 CVE-2016-6329","CWE-327" | "SWEET32","testssl.sh/81.169.166.184","443","OK","not vulnerable","CVE-2016-2183 CVE-2016-6329","CWE-327" | ||||||
| "FREAK","testssl.sh/81.169.166.184","443","OK","not vulnerable","CVE-2015-0204","CWE-310" | "FREAK","testssl.sh/81.169.166.184","443","OK","not vulnerable","CVE-2015-0204","CWE-310" | ||||||
| "DROWN","testssl.sh/81.169.166.184","443","OK","not vulnerable on this host and port","CVE-2016-0800 CVE-2016-0703","CWE-310" | "DROWN","testssl.sh/81.169.166.184","443","OK","not vulnerable on this host and port","CVE-2016-0800 CVE-2016-0703","CWE-310" | ||||||
| "DROWN_hint","testssl.sh/81.169.166.184","443","INFO","Make sure you don't use this certificate elsewhere with SSLv2 enabled services, see https://search.censys.io/search?resource=hosts&virtual_hosts=INCLUDE&q=31B44391529821C6A77F3C78B02D716A07F99B8FDB342BF5A78F263C25375968","CVE-2016-0800 CVE-2016-0703","CWE-310" | "DROWN_hint","testssl.sh/81.169.166.184","443","INFO","Make sure you don't use this certificate elsewhere with SSLv2 enabled services, see https://search.censys.io/search?resource=hosts&virtual_hosts=INCLUDE&q=5B4BC205947AED96ECB1879F2668F7F69D696C143BA8D1C69DBB4DC873C92AE9","CVE-2016-0800 CVE-2016-0703","CWE-310" | ||||||
| "LOGJAM","testssl.sh/81.169.166.184","443","OK","not vulnerable, no DH EXPORT ciphers,","CVE-2015-4000","CWE-310" | "LOGJAM","testssl.sh/81.169.166.184","443","OK","not vulnerable, no DH EXPORT ciphers,","CVE-2015-4000","CWE-310" | ||||||
| "LOGJAM-common_primes","testssl.sh/81.169.166.184","443","OK","--","CVE-2015-4000","CWE-310" | "LOGJAM-common_primes","testssl.sh/81.169.166.184","443","OK","--","CVE-2015-4000","CWE-310" | ||||||
| "BEAST_CBC_TLS1","testssl.sh/81.169.166.184","443","MEDIUM","ECDHE-RSA-AES256-SHA ECDHE-RSA-AES128-SHA DHE-RSA-CAMELLIA256-SHA DHE-RSA-CAMELLIA128-SHA DHE-RSA-AES256-SHA DHE-RSA-AES128-SHA AES256-SHA","CVE-2011-3389","CWE-20" | "BEAST_CBC_TLS1","testssl.sh/81.169.166.184","443","MEDIUM","ECDHE-RSA-AES256-SHA ECDHE-RSA-AES128-SHA DHE-RSA-CAMELLIA256-SHA DHE-RSA-CAMELLIA128-SHA DHE-RSA-AES256-SHA DHE-RSA-AES128-SHA AES256-SHA","CVE-2011-3389","CWE-20" | ||||||
|   | |||||||
							
								
								
									
										249
									
								
								testssl.sh
									
									
									
									
									
								
							
							
						
						
									
										249
									
								
								testssl.sh
									
									
									
									
									
								
							| @@ -122,7 +122,7 @@ trap "child_error" USR1 | |||||||
| 
 | 
 | ||||||
| ########### Internal definitions | ########### Internal definitions | ||||||
| # | # | ||||||
| declare -r VERSION="3.2rc3" | declare -r VERSION="3.2rc4" | ||||||
| declare -r SWCONTACT="dirk aet testssl dot sh" | declare -r SWCONTACT="dirk aet testssl dot sh" | ||||||
| [[ "$VERSION" =~ dev|rc|beta ]] && \ | [[ "$VERSION" =~ dev|rc|beta ]] && \ | ||||||
|      SWURL="https://testssl.sh/dev/" || |      SWURL="https://testssl.sh/dev/" || | ||||||
| @@ -248,6 +248,7 @@ OPENSSL2=${OPENSSL2:-/usr/bin/openssl}  # This will be openssl version >=1.1.1 ( | |||||||
| OPENSSL2_HAS_TLS_1_3=false              # If we run with supplied binary AND $OPENSSL2 supports TLS 1.3 this will be set to true | OPENSSL2_HAS_TLS_1_3=false              # If we run with supplied binary AND $OPENSSL2 supports TLS 1.3 this will be set to true | ||||||
| OSSL_SHORTCUT=${OSSL_SHORTCUT:-true}    # If you don't want automagically switch from $OPENSSL to $OPENSSL2 for TLS 1.3-only hosts, set this to false | OSSL_SHORTCUT=${OSSL_SHORTCUT:-true}    # If you don't want automagically switch from $OPENSSL to $OPENSSL2 for TLS 1.3-only hosts, set this to false | ||||||
| OPENSSL_LOCATION="" | OPENSSL_LOCATION="" | ||||||
|  | OPENSSL_NOTIMEOUT=""                    # Needed for renegotiation tests | ||||||
| IKNOW_FNAME=false | IKNOW_FNAME=false | ||||||
| FIRST_FINDING=true                      # is this the first finding we are outputting to file? | FIRST_FINDING=true                      # is this the first finding we are outputting to file? | ||||||
| JSONHEADER=true                         # include JSON headers and footers in HTML file, if one is being created | JSONHEADER=true                         # include JSON headers and footers in HTML file, if one is being created | ||||||
| @@ -582,8 +583,6 @@ tmln_out()   { printf -- "%b" "$1\n"; } | |||||||
| out()   { printf -- "%b" "$1"; html_out "$(html_reserved "$1")"; } | out()   { printf -- "%b" "$1"; html_out "$(html_reserved "$1")"; } | ||||||
| outln() { printf -- "%b" "$1\n"; html_out "$(html_reserved "$1")\n"; } | outln() { printf -- "%b" "$1\n"; html_out "$(html_reserved "$1")\n"; } | ||||||
| 
 | 
 | ||||||
| #TODO: Still no shell injection safe but if just run it from the cmd line: that's fine |  | ||||||
| 
 |  | ||||||
| # Color print functions, see also https://www.tldp.org/HOWTO/Bash-Prompt-HOWTO/x329.html | # Color print functions, see also https://www.tldp.org/HOWTO/Bash-Prompt-HOWTO/x329.html | ||||||
| tm_liteblue()   { [[ "$COLOR" -ge 2 ]] && { "$COLORBLIND" && tm_out "\033[0;32m$1" || tm_out "\033[0;34m$1"; } || tm_out "$1"; tm_off; }    # not yet used | tm_liteblue()   { [[ "$COLOR" -ge 2 ]] && { "$COLORBLIND" && tm_out "\033[0;32m$1" || tm_out "\033[0;34m$1"; } || tm_out "$1"; tm_off; }    # not yet used | ||||||
| pr_liteblue()   { tm_liteblue "$1"; [[ "$COLOR" -ge 2 ]] && { "$COLORBLIND" && html_out "<span style=\"color:#008817;\">$(html_reserved "$1")</span>" || html_out "<span style=\"color:#0000ee;\">$(html_reserved "$1")</span>"; } || html_out "$(html_reserved "$1")"; } | pr_liteblue()   { tm_liteblue "$1"; [[ "$COLOR" -ge 2 ]] && { "$COLORBLIND" && html_out "<span style=\"color:#008817;\">$(html_reserved "$1")</span>" || html_out "<span style=\"color:#0000ee;\">$(html_reserved "$1")</span>"; } || html_out "$(html_reserved "$1")"; } | ||||||
| @@ -3127,11 +3126,13 @@ emphasize_stuff_in_headers(){ | |||||||
|           -e "s/X-Powered-By/${yellow}X-Powered-By${off}/g" \ |           -e "s/X-Powered-By/${yellow}X-Powered-By${off}/g" \ | ||||||
|           -e "s/X-UA-Compatible/${yellow}X-UA-Compatible${off}/g" \ |           -e "s/X-UA-Compatible/${yellow}X-UA-Compatible${off}/g" \ | ||||||
|           -e "s/Link/${yellow}Link${off}/g" \ |           -e "s/Link/${yellow}Link${off}/g" \ | ||||||
|  |           -e "s/X-DNS-Prefetch-Control/${yellow}X-DNS-Prefetch-Control${off}/g" \ | ||||||
|           -e "s/X-Rack-Cache/${yellow}X-Rack-Cache${off}/g" \ |           -e "s/X-Rack-Cache/${yellow}X-Rack-Cache${off}/g" \ | ||||||
|           -e "s/X-Runtime/${yellow}X-Runtime${off}/g" \ |           -e "s/X-Runtime/${yellow}X-Runtime${off}/g" \ | ||||||
|           -e "s/X-Pingback/${yellow}X-Pingback${off}/g" \ |           -e "s/X-Pingback/${yellow}X-Pingback${off}/g" \ | ||||||
|           -e "s/X-Permitted-Cross-Domain-Policies/${yellow}X-Permitted-Cross-Domain-Policies${off}/g" \ |           -e "s/X-Permitted-Cross-Domain-Policies/${yellow}X-Permitted-Cross-Domain-Policies${off}/g" \ | ||||||
|           -e "s/X-AspNet-Version/${yellow}X-AspNet-Version${off}/g" \ |           -e "s/X-AspNet-Version/${yellow}X-AspNet-Version${off}/g" \ | ||||||
|  |           -e "s/X-AspNetMvc-Version/${yellow}X-AspNetMvc-Version${off}/g" \ | ||||||
|           -e "s/x-note/${yellow}x-note${off}/g" \ |           -e "s/x-note/${yellow}x-note${off}/g" \ | ||||||
|           -e "s/x-global-transaction-id/${yellow}x-global-transaction-id${off}/g" \ |           -e "s/x-global-transaction-id/${yellow}x-global-transaction-id${off}/g" \ | ||||||
|           -e "s/X-Global-Transaction-ID/${yellow}X-Global-Transaction-ID${off}/g" \ |           -e "s/X-Global-Transaction-ID/${yellow}X-Global-Transaction-ID${off}/g" \ | ||||||
| @@ -3141,7 +3142,7 @@ emphasize_stuff_in_headers(){ | |||||||
|      if "$do_html"; then |      if "$do_html"; then | ||||||
|           if [[ $COLOR -ge 2 ]]; then |           if [[ $COLOR -ge 2 ]]; then | ||||||
|                html_out "$(tm_out "$1" | sed -e 's/\&/\&/g' \ |                html_out "$(tm_out "$1" | sed -e 's/\&/\&/g' \ | ||||||
|                     -e 's/</\</g' -e 's/>/\>/g' -e 's/"/\"/g' -e "s/'/\'/g" \ |                     -e 's/</\</g' -e 's/>/\>/g' -e 's/\"/\"/g' -e "s/\'/\'/g" \ | ||||||
|                     -e "s/\([0-9]\)/${html_brown}\1${html_off}/g" \ |                     -e "s/\([0-9]\)/${html_brown}\1${html_off}/g" \ | ||||||
|                     -e "s/Unix/${html_yellow}Unix${html_off}/g" \ |                     -e "s/Unix/${html_yellow}Unix${html_off}/g" \ | ||||||
|                     -e "s/Debian/${html_yellow}Debian${html_off}/g" \ |                     -e "s/Debian/${html_yellow}Debian${html_off}/g" \ | ||||||
| @@ -3177,18 +3178,19 @@ emphasize_stuff_in_headers(){ | |||||||
|                     -e "s/Link/${html_yellow}Link${html_off}/g" \ |                     -e "s/Link/${html_yellow}Link${html_off}/g" \ | ||||||
|                     -e "s/X-Runtime/${html_yellow}X-Runtime${html_off}/g" \ |                     -e "s/X-Runtime/${html_yellow}X-Runtime${html_off}/g" \ | ||||||
|                     -e "s/X-Rack-Cache/${html_yellow}X-Rack-Cache${html_off}/g" \ |                     -e "s/X-Rack-Cache/${html_yellow}X-Rack-Cache${html_off}/g" \ | ||||||
|  |                     -e "s/X-DNS-Prefetch-Control/${html_yellow}X-DNS-Prefetch-Control${html_off}/g" \ | ||||||
|                     -e "s/X-Pingback/${html_yellow}X-Pingback${html_off}/g" \ |                     -e "s/X-Pingback/${html_yellow}X-Pingback${html_off}/g" \ | ||||||
|                     -e "s/X-Permitted-Cross-Domain-Policies/${html_yellow}X-Permitted-Cross-Domain-Policies${html_off}/g" \ |                     -e "s/X-Permitted-Cross-Domain-Policies/${html_yellow}X-Permitted-Cross-Domain-Policies${html_off}/g" \ | ||||||
|                     -e "s/X-AspNet-Version/${html_yellow}X-AspNet-Version${html_off}/g")" \ |                     -e "s/X-AspNet-Version/${html_yellow}X-AspNet-Version${html_off}/g" \ | ||||||
|  |                     -e "s/X-AspNetMvc-Version/${html_yellow}X-AspNetMvc-Version${html_off}/g" \ | ||||||
|                     -e "s/x-note/${html_yellow}x-note${html_off}/g" \ |                     -e "s/x-note/${html_yellow}x-note${html_off}/g" \ | ||||||
|                     -e "s/X-Global-Transaction-ID/${html_yellow}X-Global-Transaction-ID${html_off}/g" \ |                     -e "s/X-Global-Transaction-ID/${html_yellow}X-Global-Transaction-ID${html_off}/g" \ | ||||||
|                     -e "s/x-global-transaction-id/${html_yellow}x-global-transaction-id${html_off}/g" \ |                     -e "s/x-global-transaction-id/${html_yellow}x-global-transaction-id${html_off}/g" \ | ||||||
|                     -e "s/Alt-Svc/${html_yellow}Alt-Svc${html_off}/g" \ |                     -e "s/Alt-Svc/${html_yellow}Alt-Svc${html_off}/g" \ | ||||||
|                     -e "s/system-wsgw-management-loopback/${html_yellow}system-wsgw-management-loopback${html_off}/g" |                     -e "s/system-wsgw-management-loopback/${html_yellow}system-wsgw-management-loopback${html_off}/g" \ | ||||||
| #FIXME: this is double code. The pattern to emphasize would fit better into |                )" | ||||||
| # one function. | #FIXME: this is double code. The pattern to emphasize headers should be better in one single function | ||||||
| # Also we need another function like run_other_header as otherwise "Link" "Alt-Svc" will never be found. | # And: It matches case sensitive headers only which won't detect all banners. (sed ignorecase is not a/v for OpenBSD sed) | ||||||
| # And: I matches case sensitive only which might not detect all banners. (sed ignorecase is not possible w/ BSD sed) |  | ||||||
|           else |           else | ||||||
|                html_out "$(html_reserved "$1")" |                html_out "$(html_reserved "$1")" | ||||||
|           fi |           fi | ||||||
| @@ -3435,16 +3437,22 @@ run_security_headers() { | |||||||
| 
 | 
 | ||||||
|      pr_bold " Security headers             " |      pr_bold " Security headers             " | ||||||
|      # X-XSS-Protection is useless and at worst harmful, see https://news.ycombinator.com/item?id=20472947 |      # X-XSS-Protection is useless and at worst harmful, see https://news.ycombinator.com/item?id=20472947 | ||||||
|  |      # Expect-CT is deprecated, see https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Expect-CT | ||||||
|      for header_and_svrty in "X-Frame-Options OK" \ |      for header_and_svrty in "X-Frame-Options OK" \ | ||||||
|                              "X-Content-Type-Options OK" \ |                              "X-Content-Type-Options OK" \ | ||||||
|                              "Content-Security-Policy OK" \ |                              "Content-Security-Policy OK" \ | ||||||
|                              "X-Content-Security-Policy OK" \ |                              "X-Content-Security-Policy INFO" \ | ||||||
|                              "X-WebKit-CSP OK" \ |                              "X-WebKit-CSP INFO" \ | ||||||
|                              "Content-Security-Policy-Report-Only OK" \ |                              "Content-Security-Policy-Report-Only OK" \ | ||||||
|                              "Expect-CT OK" \ |                              "Expect-CT INFO" \ | ||||||
|                              "Permissions-Policy OK" \ |                              "Permissions-Policy OK" \ | ||||||
|  |                              "Cross-Origin-Opener-Policy INFO" \ | ||||||
|  |                              "Cross-Origin-Resource-Policy INFO" \ | ||||||
|  |                              "Cross-Origin-Embedder-Policy INFO" \ | ||||||
|                              "X-XSS-Protection INFO" \ |                              "X-XSS-Protection INFO" \ | ||||||
|                              "Access-Control-Allow-Origin INFO" \ |                              "Access-Control-Allow-Origin INFO" \ | ||||||
|  |                              "Access-Control-Allow-Credentials INFO" \ | ||||||
|  |                              "Permissions-Policy INFO" \ | ||||||
|                              "Upgrade INFO" \ |                              "Upgrade INFO" \ | ||||||
|                              "X-Served-By INFO" \ |                              "X-Served-By INFO" \ | ||||||
|                              "Referrer-Policy INFO" \ |                              "Referrer-Policy INFO" \ | ||||||
| @@ -11250,6 +11258,12 @@ npn_pre(){ | |||||||
|           fileout "NPN" "WARN" "not tested $OPENSSL doesn't support NPN/SPDY" |           fileout "NPN" "WARN" "not tested $OPENSSL doesn't support NPN/SPDY" | ||||||
|           return 7 |           return 7 | ||||||
|      fi |      fi | ||||||
|  |      if "$TLS13_ONLY"; then | ||||||
|  |           # https://github.com/openssl/openssl/issues/3665 | ||||||
|  |           pr_warning "There's no such thing as NPN on TLS 1.3-only hosts" | ||||||
|  |           fileout "NPN" "WARN" "not possible for TLS 1.3-only hosts" | ||||||
|  |           return 6 | ||||||
|  |      fi | ||||||
|      return 0 |      return 0 | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| @@ -11273,16 +11287,24 @@ alpn_pre(){ | |||||||
| run_npn() { | run_npn() { | ||||||
|      local tmpstr |      local tmpstr | ||||||
|      local -i ret=0 |      local -i ret=0 | ||||||
|  |      local proto="" | ||||||
|      local jsonID="NPN" |      local jsonID="NPN" | ||||||
| 
 | 
 | ||||||
|      [[ -n "$STARTTLS" ]] && return 0 |      [[ -n "$STARTTLS" ]] && return 0 | ||||||
|      "$FAST" && return 0 |      "$FAST" && return 0 | ||||||
|      pr_bold " NPN/SPDY   " |      pr_bold " NPN/SPDY   " | ||||||
|  | 
 | ||||||
|      if ! npn_pre; then |      if ! npn_pre; then | ||||||
|           outln |           outln | ||||||
|           return 0 |           return 0 | ||||||
|      fi |      fi | ||||||
|      $OPENSSL s_client $(s_client_options "-connect $NODEIP:$PORT $BUGS $SNI -nextprotoneg "$NPN_PROTOs"") </dev/null 2>$ERRFILE >$TMPFILE | 
 | ||||||
|  |      # TLS 1.3 s_client doesn't support -nextprotoneg when connecting with TLS 1.3. So we need to make sure it won't be used | ||||||
|  |      # TLS13_ONLY is tested here again, just to be sure, see npn_pre | ||||||
|  |      if "$HAS_TLS13" && ! $TLS13_ONLY ]] ; then | ||||||
|  |            proto="-no_tls1_3" | ||||||
|  |      fi | ||||||
|  |      $OPENSSL s_client $(s_client_options "$proto -connect $NODEIP:$PORT $BUGS $SNI -nextprotoneg "$NPN_PROTOs"") </dev/null 2>$ERRFILE >$TMPFILE | ||||||
|      [[ $? -ne 0 ]] && ret=1 |      [[ $? -ne 0 ]] && ret=1 | ||||||
|      tmpstr="$(grep -a '^Protocols' $TMPFILE | sed 's/Protocols.*: //')" |      tmpstr="$(grep -a '^Protocols' $TMPFILE | sed 's/Protocols.*: //')" | ||||||
|      if [[ -z "$tmpstr" ]] || [[ "$tmpstr" == " " ]]; then |      if [[ -z "$tmpstr" ]] || [[ "$tmpstr" == " " ]]; then | ||||||
| @@ -17152,7 +17174,7 @@ run_ticketbleed() { | |||||||
| # | # | ||||||
| run_renego() { | run_renego() { | ||||||
|      local legacycmd="" proto="$OPTIMAL_PROTO" |      local legacycmd="" proto="$OPTIMAL_PROTO" | ||||||
|      local sec_renego sec_client_renego |      local sec_renego | ||||||
|      local -i ret=0 |      local -i ret=0 | ||||||
|      local cve="" |      local cve="" | ||||||
|      local cwe="CWE-310" |      local cwe="CWE-310" | ||||||
| @@ -17244,110 +17266,113 @@ run_renego() { | |||||||
|      elif [[ "$CLIENT_AUTH" == required ]] && [[ -z "$MTLS" ]]; then |      elif [[ "$CLIENT_AUTH" == required ]] && [[ -z "$MTLS" ]]; then | ||||||
|           prln_warning "not having provided client certificate and private key file, the client x509-based authentication prevents this from being tested" |           prln_warning "not having provided client certificate and private key file, the client x509-based authentication prevents this from being tested" | ||||||
|           fileout "$jsonID" "WARN" "not having provided client certificate and private key file, the client x509-based authentication prevents this from being tested" |           fileout "$jsonID" "WARN" "not having provided client certificate and private key file, the client x509-based authentication prevents this from being tested" | ||||||
|           sec_client_renego=1 |  | ||||||
|      else |      else | ||||||
|           # We will need $ERRFILE for mitigation detection |           # We will need $ERRFILE for mitigation detection | ||||||
|           if [[ $ERRFILE =~ dev.null ]]; then |           if [[ $ERRFILE =~ dev.null ]]; then | ||||||
|                ERRFILE=$TEMPDIR/errorfile.txt || exit $ERR_FCREATE |                ERRFILE=$TEMPDIR/errorfile.txt || exit $ERR_FCREATE | ||||||
|                # cleanup previous run if any (multiple IP) |  | ||||||
|                rm -f $ERRFILE |  | ||||||
|                restore_errfile=1 |                restore_errfile=1 | ||||||
|           else |           else | ||||||
|                restore_errfile=0 |                restore_errfile=0 | ||||||
|           fi |           fi | ||||||
|           # We need up to two tries here, as some LiteSpeed servers don't answer on "R" and block. Thus first try in the background |           [[ "$SERVICE" != HTTP ]] && ssl_reneg_attempts=1 | ||||||
|           # msg enables us to look deeper into it while debugging |           # We try again if server is HTTP. This could be either a node.js server or something else. | ||||||
|           echo R | $OPENSSL s_client $(s_client_options "$proto $BUGS $legacycmd $STARTTLS -connect $NODEIP:$PORT $PROXY $SNI") >$TMPFILE 2>>$ERRFILE & |           # Mitigations (default values) for: | ||||||
|           wait_kill $! $HEADER_MAXSLEEP |           # - node.js allows 3x R and then blocks. So then 4x should be tested. | ||||||
|           if [[ $? -eq 3 ]]; then |           # - F5 BIG-IP ADS allows 5x R and then blocks. So then 6x should be tested. | ||||||
|                pr_svrty_good "likely not vulnerable (OK)"; outln ", timed out"        # it hung |           # - Stormshield allows 9x and then blocks. So then 10x should be tested. | ||||||
|                fileout "$jsonID" "OK" "likely not vulnerable (timed out)" "$cve" "$cwe" |           # This way we save a couple seconds as we weeded out the ones which are more robust | ||||||
|                sec_client_renego=1 |           # Amount of times tested before breaking is set in SSL_RENEG_ATTEMPTS. | ||||||
|           else | 
 | ||||||
|                # second try in the foreground as we are sure now it won't hang |           # Clear the log to not get the content of previous run before the execution of the new one. | ||||||
|                (echo R; sleep 1) | $OPENSSL s_client $(s_client_options "$proto $legacycmd $STARTTLS $BUGS -connect $NODEIP:$PORT $PROXY $SNI") >$TMPFILE 2>>$ERRFILE |           # (Used in the loop tests before s_client invocation) | ||||||
|                sec_client_renego=$? |           echo -n > $TMPFILE | ||||||
|                # 0 means client is renegotiating & doesn't return an error --> vuln! |           echo -n > $ERRFILE | ||||||
|                # 1 means client tried to renegotiating but the server side errored then. You still see RENEGOTIATING in the output |           # RENEGOTIATING wait loop watchdog file | ||||||
|                if tail -5 $TMPFILE| grep -qa '^closed'; then |           touch $TEMPDIR/allowed_to_loop | ||||||
|                     # Exemption from above: server closed the connection but return value was zero |           # If we dont wait for the session to be established on slow server, we will try to re-negotiate | ||||||
|                     # See https://github.com/testssl/testssl.sh/issues/1725 and referenced issue @haproxy |           # too early losing all the attempts before the session establishment as OpenSSL will not buffer them | ||||||
|                     sec_client_renego=1 |           # (only the first will be till the establishement of the session). | ||||||
|  |           (j=0; while [[ $(grep -ac '^SSL-Session:' $TMPFILE) -ne 1 ]] && [[ $j -lt 30 ]]; do sleep $ssl_reneg_wait; ((j++)); done; \ | ||||||
|  |                # Connection could be closed by the server with 0 return value. We do one more iteration to not close | ||||||
|  |                # s_client STDIN too early as the close could come at any time and race with the tear down of s_client. | ||||||
|  |                # See https://github.com/drwetter/testssl.sh/issues/2590 | ||||||
|  |                # In this case the added iteration is harmless as it will just spin in backgroup | ||||||
|  |                for ((i=0; i <= ssl_reneg_attempts; i++ )); do sleep $ssl_reneg_wait; echo R 2>/dev/null; k=0; \ | ||||||
|  |                    # 0 means client is renegotiating & doesn't return an error --> vuln! | ||||||
|  |                    # 1 means client tried to renegotiating but the server side errored then. You still see RENEGOTIATING in the output | ||||||
|  |                    # Exemption from above: server closed the connection but return value was zero | ||||||
|  |                    # See https://github.com/drwetter/testssl.sh/issues/1725 and referenced issue @haproxy | ||||||
|  |                    while [[ $(grep -ac '^RENEGOTIATING' $ERRFILE) -ne $((i+1)) ]] && [[ -f $TEMPDIR/allowed_to_loop ]] \ | ||||||
|  |                          && [[ $(tail -1 $ERRFILE | grep -acE '^(RENEGOTIATING|depth|verify|notAfter)') -eq 1 ]] \ | ||||||
|  |                          && [[ $k -lt 120 ]]; \ | ||||||
|  |                        do sleep $ssl_reneg_wait; ((k++)); if (tail -5 $TMPFILE| grep -qa '^closed'); then break; fi; done; \ | ||||||
|  |                done) | \ | ||||||
|  |                $OPENSSL_NOTIMEOUT s_client $(s_client_options "$proto $legacycmd $STARTTLS $BUGS -connect $NODEIP:$PORT $PROXY $SNI") >$TMPFILE 2>$ERRFILE & | ||||||
|  |           pid=$! | ||||||
|  |           ( sleep $((ssl_reneg_attempts*3+3)) && kill $pid && touch $TEMPDIR/was_killed ) >&2 2>/dev/null & | ||||||
|  |           watcher=$! | ||||||
|  |           # Trick to get the return value of the openssl command, output redirection and a timeout. | ||||||
|  |           # Yes, some target hang/block after some tries (some LiteSpeed servers don't answer at all on "R" and block). | ||||||
|  |           wait $pid | ||||||
|  |           tmp_result=$? | ||||||
|  |           pkill -HUP -P $watcher | ||||||
|  |           wait $watcher | ||||||
|  |           # Stop any background wait loop | ||||||
|  |           rm -f $TEMPDIR/allowed_to_loop | ||||||
|  |           # If we are here, we have done the loop. Count the effective renego attempts. | ||||||
|  |           # It could be less than the numbers of "for" iterations (minus one) in case of late server close. | ||||||
|  |           loop_reneg=$(grep -ac '^RENEGOTIATING' $ERRFILE) | ||||||
|  |           # As above, some servers close the connection and return value is zero | ||||||
|  |           if (tail -5 $TMPFILE | grep -qa '^closed'); then | ||||||
|  |                tmp_result=1 | ||||||
|  |           fi | ||||||
|  |           # timeout reached ? | ||||||
|  |           if [[ -f $TEMPDIR/was_killed ]]; then | ||||||
|  |                tmp_result=2 | ||||||
|  |                rm -f $TEMPDIR/was_killed | ||||||
|  |           fi | ||||||
|  |           if [[ $tmp_result -eq 1 ]] && [[ loop_reneg -eq 1 ]]; then | ||||||
|  |                tmp_result=3 | ||||||
|  |           fi | ||||||
|  |           if [[ $SERVICE != HTTP ]]; then | ||||||
|  |                # theoretic possible case | ||||||
|  |                if [[ $loop_reneg -eq 2 ]]; then | ||||||
|  |                     tmp_result=0 | ||||||
|                fi |                fi | ||||||
|                case "$sec_client_renego" in |                case $tmp_result in | ||||||
|                     0)   # We try again if server is HTTP. This could be either a node.js server or something else. |                     0) pr_svrty_medium "VULNERABLE (NOT ok)"; outln ", potential DoS threat" | ||||||
|                          # Mitigations (default values) for: |                        fileout "$jsonID" "MEDIUM" "VULNERABLE, potential DoS threat" "$cve" "$cwe" "$hint" | ||||||
|                          # - node.js allows 3x R and then blocks. So then 4x should be tested. |                        ;; | ||||||
|                          # - F5 BIG-IP ADS allows 5x R and then blocks. So then 6x should be tested. |                     1|3) prln_svrty_good "not vulnerable (OK)" | ||||||
|                          # - Stormshield allows 9x and then blocks. So then 10x should be tested. |                        fileout "$jsonID" "OK" "not vulnerable" "$cve" "$cwe" | ||||||
|                          # This way we save a couple seconds as we weeded out the ones which are more robust |                        ;; | ||||||
|                          # Amount of times tested before breaking is set in SSL_RENEG_ATTEMPTS. |                     2) pr_svrty_good "likely not vulnerable (OK)"; outln ", timed out ($((${ssl_reneg_attempts}*3+3))s)"        # it hung | ||||||
|                          if [[ $SERVICE != HTTP ]]; then |                        fileout "$jsonID" "OK" "likely not vulnerable (timed out)" "$cve" "$cwe" | ||||||
|                               pr_svrty_medium "VULNERABLE (NOT ok)"; outln ", potential DoS threat" |                        ;; | ||||||
|                               fileout "$jsonID" "MEDIUM" "VULNERABLE, potential DoS threat" "$cve" "$cwe" "$hint" |                     *) prln_warning "FIXME (bug): $sec_client_renego" | ||||||
|                          else |                        fileout "$jsonID" "DEBUG" "FIXME (bug) $sec_client_renego - Please report" "$cve" "$cwe" | ||||||
|                               # Clear the log to not get the content of previous run before the execution of the new one. |                        ret=1 | ||||||
|                               echo -n > $TMPFILE |                        ;; | ||||||
|                               #RENEGOTIATING wait loop watchdog file |                esac | ||||||
|                               touch $TEMPDIR/allowed_to_loop |           else | ||||||
|                               # If we dont wait for the session to be established on slow server, we will try to re-negotiate |                case $tmp_result in | ||||||
|                               # too early losing all the attempts before the session establishment as OpenSSL will not buffer them |                     0) pr_svrty_high "VULNERABLE (NOT ok)"; outln ", DoS threat ($ssl_reneg_attempts attempts)" | ||||||
|                               # (only the first will be till the establishement of the session). |                        fileout "$jsonID" "HIGH" "VULNERABLE, DoS threat" "$cve" "$cwe" "$hint" | ||||||
|                               (j=0; while [[ $(grep -ac '^SSL-Session:' $TMPFILE) -ne 1 ]] && [[ $j -lt 30 ]]; do sleep $ssl_reneg_wait; ((j++)); done; \ |                        ;; | ||||||
|                                    for ((i=0; i < ssl_reneg_attempts; i++ )); do sleep $ssl_reneg_wait; echo R; k=0; \ |                     1) pr_svrty_good "not vulnerable (OK)"; outln " -- mitigated (disconnect after $loop_reneg/$ssl_reneg_attempts attempts)" | ||||||
|                                        while [[ $(grep -ac '^RENEGOTIATING' $ERRFILE) -ne $((i+3)) ]] && [[ -f $TEMPDIR/allowed_to_loop ]] \ |                        fileout "$jsonID" "OK" "not vulnerable, mitigated" "$cve" "$cwe" | ||||||
|                                              && [[ $(tail -n1 $ERRFILE |grep -acE '^(RENEGOTIATING|depth|verify|notAfter)') -eq 1 ]] \ |                        ;; | ||||||
|                                              && [[ $k -lt 120 ]]; \ |                     3) prln_svrty_good "not vulnerable (OK)" | ||||||
|                                            do sleep $ssl_reneg_wait; ((k++)); if (tail -5 $TMPFILE| grep -qa '^closed'); then sleep 1; break; fi; done; \ |                        fileout "$jsonID" "OK" "not vulnerable" "$cve" "$cwe" | ||||||
|                                    done) | \ |                        ;; | ||||||
|                                    $OPENSSL s_client $(s_client_options "$proto $legacycmd $STARTTLS $BUGS -connect $NODEIP:$PORT $PROXY $SNI") >$TMPFILE 2>>$ERRFILE & |                     2) pr_svrty_good "not vulnerable (OK)"; \ | ||||||
|                               pid=$! |                           outln " -- mitigated ($loop_reneg successful reneg within ${ssl_reneg_attempts} in $((${ssl_reneg_attempts}*3+3))s(timeout))" | ||||||
|                               ( sleep $((ssl_reneg_attempts*3)) && kill $pid && touch $TEMPDIR/was_killed ) >&2 2>/dev/null & |                        fileout "$jsonID" "OK" "not vulnerable, mitigated" "$cve" "$cwe" | ||||||
|                               watcher=$! |                        ;; | ||||||
|                               # Trick to get the return value of the openssl command, output redirection and a timeout. |                     *) prln_warning "FIXME (bug): $sec_client_renego ($ssl_reneg_attempts tries)" | ||||||
|                               # Yes, some target hang/block after some tries. |                        fileout "$jsonID" "DEBUG" "FIXME (bug $ssl_reneg_attempts tries) $sec_client_renego" "$cve" "$cwe" | ||||||
|                               wait $pid |                        ret=1 | ||||||
|                               tmp_result=$? |                        ;; | ||||||
|                               pkill -HUP -P $watcher |  | ||||||
|                               wait $watcher |  | ||||||
|                               rm -f $TEMPDIR/allowed_to_loop |  | ||||||
|                               # If we are here, we have done two successful renegotiation (-2) and do the loop |  | ||||||
|                               loop_reneg=$(($(grep -ac '^RENEGOTIATING' $ERRFILE)-2)) |  | ||||||
|                               # As above, some servers close the connection and return value is zero |  | ||||||
|                               if (tail -5 $TMPFILE| grep -qa '^closed'); then |  | ||||||
|                                    tmp_result=1 |  | ||||||
|                               fi |  | ||||||
|                               if [[ -f $TEMPDIR/was_killed ]]; then |  | ||||||
|                                    tmp_result=2 |  | ||||||
|                                    rm -f $TEMPDIR/was_killed |  | ||||||
|                               fi |  | ||||||
|                               case $tmp_result in |  | ||||||
|                                    0) pr_svrty_high "VULNERABLE (NOT ok)"; outln ", DoS threat ($ssl_reneg_attempts attempts)" |  | ||||||
|                                       fileout "$jsonID" "HIGH" "VULNERABLE, DoS threat" "$cve" "$cwe" "$hint" |  | ||||||
|                                       ;; |  | ||||||
|                                    1) pr_svrty_good "not vulnerable (OK)"; outln " -- mitigated (disconnect after $loop_reneg/$ssl_reneg_attempts attempts)" |  | ||||||
|                                       fileout "$jsonID" "OK" "not vulnerable, mitigated" "$cve" "$cwe" |  | ||||||
|                                       ;; |  | ||||||
|                                    2) pr_svrty_good "not vulnerable (OK)"; \ |  | ||||||
|                                            outln " -- mitigated ($loop_reneg successful reneg within ${ssl_reneg_attempts} in $((${ssl_reneg_attempts}*3))s(timeout))" |  | ||||||
|                                       fileout "$jsonID" "OK" "not vulnerable, mitigated" "$cve" "$cwe" |  | ||||||
|                                       ;; |  | ||||||
|                                    *) prln_warning "FIXME (bug): $sec_client_renego ($ssl_reneg_attempts tries)" |  | ||||||
|                                       fileout "$jsonID" "DEBUG" "FIXME (bug $ssl_reneg_attempts tries) $sec_client_renego" "$cve" "$cwe" |  | ||||||
|                                       ret=1 |  | ||||||
|                                       ;; |  | ||||||
|                               esac |  | ||||||
|                          fi |  | ||||||
|                          ;; |  | ||||||
|                     1) |  | ||||||
|                          prln_svrty_good "not vulnerable (OK)" |  | ||||||
|                          fileout "$jsonID" "OK" "not vulnerable" "$cve" "$cwe" |  | ||||||
|                          ;; |  | ||||||
|                     *) |  | ||||||
|                          prln_warning "FIXME (bug): $sec_client_renego" |  | ||||||
|                          fileout "$jsonID" "DEBUG" "FIXME (bug) $sec_client_renego - Please report" "$cve" "$cwe" |  | ||||||
|                          ret=1 |  | ||||||
|                          ;; |  | ||||||
|                esac |                esac | ||||||
|           fi |           fi | ||||||
|      fi |      fi | ||||||
| @@ -20523,6 +20548,8 @@ find_openssl_binary() { | |||||||
|           fi |           fi | ||||||
|      fi |      fi | ||||||
| 
 | 
 | ||||||
|  |      OPENSSL_NOTIMEOUT=$OPENSSL | ||||||
|  | 
 | ||||||
|      if ! "$do_mass_testing"; then |      if ! "$do_mass_testing"; then | ||||||
|           if [[ -n $OPENSSL_TIMEOUT ]]; then |           if [[ -n $OPENSSL_TIMEOUT ]]; then | ||||||
|                OPENSSL="$TIMEOUT_CMD $OPENSSL_TIMEOUT $OPENSSL" |                OPENSSL="$TIMEOUT_CMD $OPENSSL_TIMEOUT $OPENSSL" | ||||||
| @@ -20685,7 +20712,7 @@ single check as <options>  ("$PROG_NAME URI" does everything except -E and -g): | |||||||
|      -e, --each-cipher             checks each local cipher remotely |      -e, --each-cipher             checks each local cipher remotely | ||||||
|      -E, --cipher-per-proto        checks those per protocol |      -E, --cipher-per-proto        checks those per protocol | ||||||
|      -s, --std, --categories       tests standard cipher categories by strength |      -s, --std, --categories       tests standard cipher categories by strength | ||||||
|      -f, --fs, --nsa               checks forward secrecy settings |      -f, --fs, --forward-secrecy   checks forward secrecy settings | ||||||
|      -p, --protocols               checks TLS/SSL protocols (including SPDY/HTTP2) |      -p, --protocols               checks TLS/SSL protocols (including SPDY/HTTP2) | ||||||
|      -g, --grease                  tests several server implementation bugs like GREASE and size limitations |      -g, --grease                  tests several server implementation bugs like GREASE and size limitations | ||||||
|      -S, --server-defaults         displays the server's default picks and certificate info |      -S, --server-defaults         displays the server's default picks and certificate info | ||||||
|   | |||||||
| @@ -69,7 +69,7 @@ testv6_patch() { | |||||||
|      else |      else | ||||||
|           echo |           echo | ||||||
|           echo "no IPv6 patch (Fedora) detected!!  -- Press ^C and dl & apply from" |           echo "no IPv6 patch (Fedora) detected!!  -- Press ^C and dl & apply from" | ||||||
|           echo "https://github.com/drwetter/testssl.sh/blob/master/bin/fedora-dirk-ipv6.diff" |           echo "https://github.com/testssl/testssl.sh/blob/master/bin/fedora-dirk-ipv6.diff" | ||||||
|           echo "or press any key to ignore" |           echo "or press any key to ignore" | ||||||
|           echo |           echo | ||||||
|           read a |           read a | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user
	 Dirk
					Dirk