(updated: Mar 09, 2019)
There are several very good articles about hardening OpenSSL ciphers. Over the years I’ve combined lessons learned from others, my own research of standards and best practices, and my own real-life experiences to come up with the OpenSSL cipher string that I’ve found works best. My goal with this string is to provide the best security while minimizing the length of the string. This updated is focused on OpenSSL version 1.1.1, which introduces support for TLSv1.3 and I am now including the the ChaCha20 and AES-CCM ciphers introduced in version 1.1.0.
You can test is on your OpenSSL installation
openssl ciphers -v 'ECDH+AESGCM+AES128:ECDH+AESGCM:ECDH+CHACHA20:ECDH+AES128:ECDH+AES:DHE+AES128:DHE+AES:!aNULL:!SHA1:!DSS'
It should result in the following cipher suites in the following order. You notice that the TLSv1.3 ciphers (the first three) do not follow the priority we defined to put AES128 above AES256.
TLS_AES_256_GCM_SHA384 TLS_CHACHA20_POLY1305_SHA256 TLS_AES_128_GCM_SHA256 ECDHE-ECDSA-AES128-GCM-SHA256 ECDHE-RSA-AES128-GCM-SHA256 ECDHE-ECDSA-AES256-GCM-SHA384 ECDHE-RSA-AES256-GCM-SHA384 ECDHE-ECDSA-CHACHA20-POLY1305 ECDHE-RSA-CHACHA20-POLY1305 ECDHE-ECDSA-AES128-CCM8 ECDHE-ECDSA-AES128-CCM ECDHE-ECDSA-AES128-SHA256 ECDHE-RSA-AES128-SHA256 ECDHE-ECDSA-AES256-CCM8 ECDHE-ECDSA-AES256-CCM ECDHE-ECDSA-AES256-SHA384 ECDHE-RSA-AES256-SHA384 DHE-RSA-AES128-GCM-SHA256 DHE-RSA-AES128-CCM8 DHE-RSA-AES128-CCM DHE-RSA-AES128-SHA256 DHE-RSA-AES256-GCM-SHA384 DHE-RSA-AES256-CCM8 DHE-RSA-AES256-CCM DHE-RSA-AES256-SHA256
- Only PFS cipher suites. ECDHE first, then DHE.
- AESGCM ciphers are preferred over everything else.
- AES-128 is preferred to AES-256. AES-256 provides little improvement to security, while AES-128 is faster making it less taxing in virtual server environments and more resistant to timing attacks.
- SHA1 ciphers are no longer used since it is not support by TLSv1.2.
You will notice for Apache there is a separate config entry for TLSv1.3 cipher suite order.
SSLEngine on SSLProtocol -All +TLSv1.2 +TLSv1.3 SSLCipherSuite ECDH+AESGCM+AES128:ECDH+AESGCM:ECDH+CHACHA20:ECDH+AES128:ECDH+AES:DHE+AES128:DHE+AES:!aNULL:!SHA1:!DSS SSLCipherSuite TLSv1.3 TLS_AES_128_GCM_SHA256:TLS_AES_256_GCM_SHA384:TLS_CHACHA20_POLY1305_SHA256 SSLHonorCipherOrder On
Currently, Nginx does not have a way to define cipher order for the TLSv1.3 ciphers.
ssl_prefer_server_ciphers On; ssl_protocols TLSv1.2 TLSv1.3; ssl_ciphers ECDH+AESGCM+AES128:ECDH+AESGCM:ECDH+CHACHA20:ECDH+AES128:ECDH+AES:DHE+AES128:DHE+AES:!aNULL:!SHA1:!DSS;
Ubuntu Support for OpenSSL 1.1.1
In order to use OpenSSL 1.1.1 on Ubuntu prior to version 18.10, you will need to add a 3rd-party repository for the service you want that supports the latest OpenSSL version. Ondřej Surý is a Debian developer and an important figure in the DNS community. He maintains many packages for Debian repository, including Apache, BIND, MariaDB, PHP etc. He is also one of the maintainers of the official certbot PPA.
If you are using Apache2 web server, for example, you can upgrade Apache2 to his repository, which includes OpenSSL 1.1.1, with the following commands:
add-apt-repository ppa:ondrej/apache2 apt update apt upgrade
more to come…