How do I list the SSL/TLS cipher suites a particular website offers?
Solution 1
I wrote a bash script to test cipher suites. It gets a list of supported cipher suites from OpenSSL and tries to connect using each one. If the handshake is successful, it prints YES
. If the handshake isn't successful, it prints NO
, followed by the OpenSSL error text.
#!/usr/bin/env bash
# OpenSSL requires the port number.
SERVER=$1
DELAY=1
ciphers=$(openssl ciphers 'ALL:eNULL' | sed -e 's/:/ /g')
echo Obtaining cipher list from $(openssl version).
for cipher in ${ciphers[@]}
do
echo -n Testing $cipher...
result=$(echo -n | openssl s_client -cipher "$cipher" -connect $SERVER 2>&1)
if [[ "$result" =~ ":error:" ]] ; then
error=$(echo -n $result | cut -d':' -f6)
echo NO \($error\)
else
if [[ "$result" =~ "Cipher is ${cipher}" || "$result" =~ "Cipher :" ]] ; then
echo YES
else
echo UNKNOWN RESPONSE
echo $result
fi
fi
sleep $DELAY
done
Here's sample output showing 3 unsupported ciphers, and 1 supported cipher:
[@linux ~]$ ./test_ciphers 192.168.1.11:443
Obtaining cipher list from OpenSSL 0.9.8k 25 Mar 2009.
Testing ADH-AES256-SHA...NO (sslv3 alert handshake failure)
Testing DHE-RSA-AES256-SHA...NO (sslv3 alert handshake failure)
Testing DHE-DSS-AES256-SHA...NO (sslv3 alert handshake failure)
Testing AES256-SHA...YES
EDIT: Add flexibility as host and port are provided as parameter to the script
Solution 2
Nmap with ssl-enum-ciphers
There is no better or faster way to get a list of available ciphers from a network service. Plus, nmap will provide a strength rating of strong, weak, or unknown for each available cipher.
First, download the ssl-enum-ciphers.nse nmap script (explanation here). Then from the same directory as the script, run nmap as follows:
List ciphers supported by an HTTP server
$ nmap --script ssl-enum-ciphers -p 443 www.example.com
List ciphers supported by an IMAP server
$ nmap --script ssl-enum-ciphers -p 993 mail.example.com
Here is a snippet of output from a Dovecot IMAP server:
993/tcp open imaps
| ssl-enum-ciphers:
| SSLv3:
| ciphers:
| TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA - strong
| TLS_DHE_RSA_WITH_AES_128_CBC_SHA - strong
| TLS_DHE_RSA_WITH_AES_256_CBC_SHA - strong
| TLS_RSA_WITH_IDEA_CBC_SHA - weak
...
| TLSv1.0:
| ciphers:
| TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA - strong
| TLS_DHE_RSA_WITH_AES_128_CBC_SHA - strong
| TLS_DHE_RSA_WITH_AES_256_CBC_SHA - strong
| TLS_RSA_WITH_IDEA_CBC_SHA - weak
...
|_ least strength: weak
Nmap done: 1 IP address (1 host up) scanned in 1.03 seconds
Solution 3
Is there a tool that can test what SSL/TLS cipher suites a particular website offers?
Yes, you could use the online tool on SSL Labs' website to query the Public SSL Server Database.
Here is a snippet of information that it provides:
(screenshot from results of google.com)
Solution 4
sslscan is a nice little utility.
It tests connecting with TLS and SSL (and the build script can link with its own copy of OpenSSL so that obsolete SSL versions are checked as well) and reports about the server's cipher suites and certificate.
Example output for google.com
(trimmed down for readability):
$ sslscan google.com
Testing SSL server google.com on port 443
TLS renegotiation:
Secure session renegotiation supported
TLS Compression:
Compression disabled
Heartbleed:
TLS 1.2 not vulnerable to heartbleed
TLS 1.1 not vulnerable to heartbleed
TLS 1.0 not vulnerable to heartbleed
Supported Server Cipher(s):
Preferred TLSv1.2 128 bits ECDHE-RSA-AES128-GCM-SHA256 Curve P-256 DHE 256
Accepted TLSv1.2 128 bits ECDHE-RSA-AES128-SHA Curve P-256 DHE 256
Accepted TLSv1.2 128 bits ECDHE-RSA-RC4-SHA Curve P-256 DHE 256
Accepted TLSv1.2 128 bits AES128-GCM-SHA256
Accepted TLSv1.2 128 bits AES128-SHA
<snip>
Preferred TLSv1.1 128 bits ECDHE-RSA-AES128-SHA Curve P-256 DHE 256
Accepted TLSv1.1 128 bits ECDHE-RSA-RC4-SHA Curve P-256 DHE 256
Accepted TLSv1.1 128 bits AES128-SHA
<snip>
Preferred TLSv1.0 128 bits ECDHE-RSA-AES128-SHA Curve P-256 DHE 256
Accepted TLSv1.0 128 bits ECDHE-RSA-RC4-SHA Curve P-256 DHE 256
Accepted TLSv1.0 128 bits AES128-SHA
<snip>
Preferred SSLv3 128 bits RC4-SHA
Accepted SSLv3 128 bits RC4-MD5
<snip>
SSL Certificate:
Signature Algorithm: sha256WithRSAEncryption
RSA Key Strength: 2048
Subject: *.google.com
Altnames: DNS:*.google.com, DNS:*.android.com, <snip>
Issuer: Google Internet Authority G2
Not valid before: Apr 7 08:24:31 2016 GMT
Not valid after: Jun 30 08:20:00 2016 GMT
Solution 5
Since this is such a great reference thread for SSL scanning tools, I'll list CipherScan which was created a year ago and can also identify problems with key exchange ciphers. https://github.com/jvehent/cipherscan
If you want my fork which supports SNI and FreeBSD, the URL is https://github.com/oparoz/cipherscan
It's a script which calls openssl s_client
and supports using your own OpenSSL binary so that you can test upcoming features or new ciphers (chacha20+poly1305 per example).
It also lets you connect to any port you want and use starttlss.
Here is a typical output
# ./cipherscan -o ./openssl api.mycompany.com:443
...................
prio ciphersuite protocols pfs_keysize
1 DHE-RSA-AES256-GCM-SHA384 TLSv1.2 DH,4096bits
2 DHE-RSA-AES256-SHA256 TLSv1.2 DH,4096bits
3 ECDHE-RSA-AES256-GCM-SHA384 TLSv1.2 ECDH,P-384,384bits
4 ECDHE-RSA-AES256-SHA384 TLSv1.2 ECDH,P-384,384bits
5 DHE-RSA-AES128-GCM-SHA256 TLSv1.2 DH,4096bits
6 DHE-RSA-AES128-SHA256 TLSv1.2 DH,4096bits
7 ECDHE-RSA-AES128-GCM-SHA256 TLSv1.2 ECDH,P-384,384bits
8 ECDHE-RSA-AES128-SHA256 TLSv1.2 ECDH,P-384,384bits
9 DHE-RSA-CAMELLIA256-SHA TLSv1,TLSv1.1,TLSv1.2 DH,4096bits
10 DHE-RSA-AES256-SHA TLSv1,TLSv1.1,TLSv1.2 DH,4096bits
11 ECDHE-RSA-AES256-SHA TLSv1,TLSv1.1,TLSv1.2 ECDH,P-384,384bits
12 DHE-RSA-CAMELLIA128-SHA TLSv1,TLSv1.1,TLSv1.2 DH,4096bits
13 DHE-RSA-AES128-SHA TLSv1,TLSv1.1,TLSv1.2 DH,4096bits
14 ECDHE-RSA-AES128-SHA TLSv1,TLSv1.1,TLSv1.2 ECDH,P-384,384bits
15 CAMELLIA256-SHA TLSv1,TLSv1.1,TLSv1.2
16 AES256-SHA TLSv1,TLSv1.1,TLSv1.2
17 CAMELLIA128-SHA TLSv1,TLSv1.1,TLSv1.2
18 AES128-SHA TLSv1,TLSv1.1,TLSv1.2
Certificate: trusted, 4096 bit, sha256WithRSAEncryption signature
TLS ticket lifetime hint: 300
OCSP stapling: supported
And here are a list of options
-a | --allciphers Test all known ciphers individually at the end.
-b | --benchmark Activate benchmark mode.
-d | --delay Pause for n seconds between connections
-D | --debug Output ALL the information.
-h | --help Shows this help text.
-j | --json Output results in JSON format.
-o | --openssl path/to/your/openssl binary you want to use.
-v | --verbose Increase verbosity.
The json output is useful if you're calling this from other scripts.
Related videos on Youtube
ibustama
Updated on September 17, 2022Comments
-
ibustama over 1 year
I migrated a project from 1.1 to 1.2, then to 1.3, all of this, flawlessly. However, when I moved the version up to 1.4, I keep getting a
NoReverseMatch at /admin/<app_name>/<model_name>/ Reverse for 'app_list' with arguments '()' and keyword arguments '{'app_label': ''}' not found.
All other admin functionality seems to work fine, but every time I try to see a list, I get this NoReverseMatch error.
My url entry for the admin is:
(r'^admin/', include(admin.site.urls)),
Here's my traceback:
Template error: In template /home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/contrib/admin/templates/admin/change_list.html, error at line 44 Reverse for 'app_list' with arguments '()' and keyword arguments '{'app_label': ''}' not found. 34 : </script> 35 : {% endif %}{% endif %} 36 : {% endblock %} 37 : 38 : {% block bodyclass %}change-list{% endblock %} 39 : 40 : {% if not is_popup %} 41 : {% block breadcrumbs %} 42 : <div class="breadcrumbs"> 43 : <a href="{% url 'admin:index' %}">{% trans 'Home' %}</a> 44 : › <a href=" {% url 'admin:app_list' app_label=cl.opts.app_label %} ">{{ app_label|capfirst|escape }}</a> 45 : › {{ cl.opts.verbose_name_plural|capfirst }} 46 : </div> 47 : {% endblock %} 48 : {% endif %} 49 : 50 : {% block coltype %}flex{% endblock %} 51 : 52 : {% block content %} 53 : <div id="content-main"> 54 : {% block object-tools %} Traceback: File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/core/handlers/base.py" in get_response 136. response = response.render() File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/response.py" in render 104. self._set_content(self.rendered_content) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/response.py" in rendered_content 81. content = template.render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/base.py" in render 140. return self._render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/base.py" in _render 134. return self.nodelist.render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/base.py" in render 823. bit = self.render_node(node, context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/debug.py" in render_node 74. return node.render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/loader_tags.py" in render 123. return compiled_parent._render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/base.py" in _render 134. return self.nodelist.render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/base.py" in render 823. bit = self.render_node(node, context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/debug.py" in render_node 74. return node.render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/loader_tags.py" in render 123. return compiled_parent._render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/base.py" in _render 134. return self.nodelist.render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/base.py" in render 823. bit = self.render_node(node, context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/debug.py" in render_node 74. return node.render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/defaulttags.py" in render 281. return nodelist.render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/base.py" in render 823. bit = self.render_node(node, context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/debug.py" in render_node 74. return node.render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/loader_tags.py" in render 62. result = block.nodelist.render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/base.py" in render 823. bit = self.render_node(node, context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/debug.py" in render_node 74. return node.render(context) File "/home/ibustama/yalea/env-yalea/lib/python2.6/site-packages/django/template/defaulttags.py" in render 424. raise e Exception Type: NoReverseMatch at /admin/auth/user/ Exception Value: Reverse for 'app_list' with arguments '()' and keyword arguments '{'app_label': ''}' not found.
-
Admin over 14 yearsMaybe
gnutls-cli
? -
marianobianchi almost 12 yearsIt seems that you've forgot to include one app to your
INSTALLED_APPS
configuration. Did you follow these steps to use the admin pages? -
ibustama almost 12 yearsHi thanks, I did follow those steps. I thought that maybe I missed some new default apps on the settings file, and even checked the order. The problem remained the same. Anyways, I found the problem (and it was rather dumb), so I'll post the answer.
-
Admin almost 9 yearsAfter the title change, this question really isn't asking for a software-rec. Voting to reopen.
-
Admin almost 9 years@fixer1234 If it makes you happier, I've removed any occurrence of the word "tool". The core question is asking how to accomplish a specific task anyway; it's a minor rephrase and far from more open-ended "list of software" type questions.
-
Admin almost 9 years@Bob: I'm ecstatic. :-) Voting to reopen.
-
-
Jeremy Powell over 14 yearsOh yeah... for some reason I was thinking it was the other way around. Maybe I can find a pre-cobbled tool... :)
-
Jeremy Powell about 14 yearsThis is exactly what I was looking for! Thanks a lot!
-
Jeremy Powell over 13 yearsThis is fantastic. It's even more exactly what I was looking for.
-
Hubert Kario almost 13 yearsopenssl 1.0 needs a change:
if [[ "$result" =~ "Cipher :" ]] ; then
instead ofif [[ "$result" =~ "Cipher is " ]] ; then
I also test for SSL2 and secure renegotiation:echo -n Testing ssl2... result=$(echo -n | openssl s_client -ssl2 -connect $SERVER 2>&1) if [[ "$result" =~ "Cipher :" ]] ; then echo supported. INSECURE! else echo no support, OK fi echo -n Testing SSL secure renegotiation... echo -n "" | openssl s_client -connect $SERVER 2>&1 | grep 'Secure Renegotiation'
-
Hubert Kario almost 13 yearsUnfortunately it does support only HTTPS on standard port, can't use it to check POP3S, IMAPS or IMAP with TLS
-
Robert over 11 yearsThere is another, very sophisticated shell script available that uses sslscan and openssl: TLSSLed
-
Steven almost 11 years@HubertKario - later versions of openssl do not support the -ssl2 flag (although it is still listed in the help)
-
Giel almost 10 yearsIs there any way to use this script on IMAP with STARTTLS? STARTTLS on SMTP seems to work, but on IMAP the script doesn't even appear to run.
-
Olivier - interfaSys over 9 yearsI've listed below another script which only requires OpenSSL called CipherScan
-
Guillaume over 9 yearsCouple of things: you might be running the script in your nmap distro, rather than the one you downloaded. Check by renaming yours. Then check the "portrule" which in some versions checks for commonly used port numbers. Replace with
portrule = function() \n return true \n end
-
Iszi about 9 yearsAnd while it's great for public-facing sites, you can't use it for sites on networks that are isolated from the Internet.
-
indiv almost 9 years@RanPaul: You can install cygwin or msys to get the bash shell and then run this script as a bash script. I tried to write a native Windows script but there's a bug in
openssl s_client
that causes it to hang until a keypress, so that's not going to be possible. -
Redi almost 9 years
yum install sslscan
works on CentOS 6. -
Redi almost 9 years"big-SSLv3 config not supported, connection failed"
-
user5504603 over 8 years
sudo dnf install sslscan
on Fedora 22 as well. -
ThorSummoner over 8 yearsThe Debian nmap package appears to include the ssl-enum-ciphers script. :+1:
-
Clint Pachl over 8 yearsOne caveat is that older scripts, which may be included in your distro/package, list ciphers in alphabetical order, not server (or client) preferred order. See the above comment from @slim
-
insaner over 8 years@indiv this is awesome! I added a couple of tweaks for my usage, how can I best make those available for everyone?
-
indiv over 8 years@insaner: If they're substantial, I'd say to post them in a new answer. I don't have a good answer for what to do.
-
insaner over 8 years@indiv, here it is: superuser.com/a/1035879/316396
-
Xiao about 8 years
brew install sslscan
on OSX -
balu almost 8 years
sudo apt-get install sslscan
on Ubuntu (12.04 – so all later versions should be fine). -
balu almost 8 yearsUpdate: It should be noted that the official version of sslscan found in the Debian and Ubuntu repositories (currently 1.8.2 from 2009) does not support TLS v1.1 and 1.2, see bugs.launchpad.net/ubuntu/+source/sslscan/+bug/1372741. One should therefore use the version on GitHub that the OP linked to.
-
Marki almost 8 yearsYou are performing
openssl ciphers -tls1.1
andopenssl ciphers -tls1.2
however those params don't seem to exist... There is only-tls1
(at least on the platforms I have tried). -
Marki almost 8 years(There seem to be additional options in the form of
tls1_1
andtls1_2
but they are only shown on the master version of openssl and not even in 1.0.2 ....) -
Paul over 7 yearsYour answer was earlier, but Clint Pachl's answer explains
ssl-enum-ciphers
much more comprehensively. -
Admin over 7 yearsNote that this script probably won't tell you if a server supports cipher suites that OpenSSL doesn't support.
-
Dipendra Pokharel over 7 yearsNote that this script probably won't tell you if a server supports cipher suites that OpenSSL doesn't support.
-
bonsaiviking over 7 yearsIn the 2 years since this answer was written, Nmap has added support for STARTTLS over FTP, NNTP, IMAP, LDAP, POP3, PostgreSQL, SMTP, XMPP, VNC, and MS SQL, as well as many other improvements beyond simply listing supported ciphers.
-
John Yeary over 6 yearsThe suggestion from @Robert for TLSSLed was fantastic. It has been updated to 1.3 and has a lot more functionality. I have been using for security testing and must say that I am impressed.
-
eel ghEEz over 5 yearsSome Bash corrections, gist.github.com/ilatypov/488b4f35990a003052e422b4c108608f
-
eel ghEEz over 5 yearsSorry but Nmap's ssl cipher enum script shows some ciphers which openssl can't proceed with when connecting to imap.mail.yahoo.com:993.
-
Clint Pachl over 5 years@eelghEEz Works fine on OpenBSD 6.4 running nmap-7.70 compiled with openssl-2.8.2 (which is LibreSSL 2.8.2 on OpenBSD). Check
nmap -V
on your system. Maybe you have old libraries or disabled ciphers. To check the Yahoo IMAP server, skip host discovery with the-Pn
option. -
eel ghEEz over 5 years@ClintPachl The nmap script shows ciphers such as
TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA
but runningopenssl s_client -cipher EDH-RSA-DES-CBC3-SHA -connect imap.mail.yahoo.com:993 -no_ign_eof < /dev/null ; echo $?
showssslv3 alert handshake failure
. Usingopenssl
shows only 12 ciphers allowed by Yahoo IMAP on port 993: gist.github.com/ilatypov/488b4f35990a003052e422b4c108608f -
rakpan about 5 yearsA word of caution.. This could cause poorly written applications to crash. Read this document before you proceed using this tool nmap.org/book/legal-issues.html
-
garethTheRed almost 5 yearsThe version packaged with Debian 9 uses an older OpenSSL package, but that version doesn't support SSL2 or SSL3.
-
karafior almost 5 yearsA word of caution - this script does not work if the server expects a client side certificate.
-
Brent Bradburn almost 5 years'sslscan' seems to not work when behind a proxy.
-
Jakob over 4 yearsThis won't work with recent OpenSSL versions that use TLS 1.3 by default, because
s_client
wants-ciphersuites
instead of-cipher
. I changed the script accordingly (with some other tweaks) -
Zergatul over 4 yearsThis is great utility. nmap is just terrible for new users. It doesn't want to scan localhost, it has problems with custom ports.
-
Yan Foto over 4 yearsCaution: this script seems to be outdated, with no support for TLSv1.3!
-
FreeText about 4 yearsNote that it requires a FQDN; it won't test IP addresses. It seems you have to make an account for that...
-
FreeText about 4 yearsAs of Mar 2020, the sslscan version is 1.11.5 from the Ubuntu repositories, which includes support for TLS v1.1. and 1.2, but not TLS v1.3 because it is still using OpenSSL 1.0.2n (7 Dec 2017). I believe OpenSSL added TLS 1.3 support in v1.1.1.
-
FreeText about 4 yearsOpenSSL 1.1.1 does include TLS 1.1, 1.2 and 1.3 support. The parameters are
-tls1_1
,-tls1_2
and-tls1_3
. However,-tls1_2
, for example, returns more than you would expect. Try from your command line:openssl ciphers -v -tls1_2
-
Muhammad Taqi over 3 yearsI ran this on my two differetn sites, one returns a list of ciphers and other doesn't at all, what does it means?
-
fencekicker over 3 yearsDoes this nmap script really work with alternate ports? I have an HTTPS server listening on port 8000, I can connect to it using 'openssl s_client', while nmap run with '--script ssl-enum-ciphers' and '-p 8000' only gives some terse output saying the host is up, and the port to service mapping, and no cipher information.
-
Alexander about 3 yearsFor "OpenSSL version does not support SSLv2 / SSLv3" askubuntu.com/a/1176418/769834
-
Admin about 2 yearsnmap 7.92 supports TLSv1.3