I'm trying to configure HTTPS for nginx on Ubuntu 16.04. I've already set it up with listen 443 ssl statements, and told it where to find the certificate and private key files. After that I restarted the server with sudo service nginx restart.

Now when I curl https://my_ip_address, I get the following message:

curl: (35) gnutls_handshake() failed: Handshake failed

I've checked the two log files I know about, /var/log/nginx/access.log and /var/log/nginx/error.log; but it doesn't show any trace of anything from the request.

My question: Does anything get logged when the SSL handshake fails? If so where? In general, how to I troubleshoot problems like this, where there is an error in the SSL protocol before the HTTP request is sent to, or extracted by the server?

EDIT: I got it to work by removing the following lines from my config:

ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
ssl_prefer_server_ciphers on;
ssl_ecdh_curve secp384r1;
ssl_session_cache shared:SSL:10m;
ssl_session_tickets off;
ssl_stapling on;
ssl_stapling_verify on;
resolver valid=300s;
resolver_timeout 5s;

Update: The ssl_ecdh_curve secp384r1; line seemed to be causing the problem. Without it, everything works fine, but with it, the SSL handshake fails. Curiously, the error message is that there is "no shared cipher". I'm not sure what it does, so I just removed it. I also removed the ssl_stapling stuff because I don't know what it is for, and it was creating its own error messages

  • Perhaps a more verbose log setting would work. See nginx core module error_log. However, there may be something else wrong with your config revealed with a simple sudo nginx -t or post the relevant portions of the config in your question for more help. – Paul Sep 19 '16 at 21:24
  • 1
    I forgot to mention it is generally a good idea to check /var/log/syslog as you may identify other problems, though not necessarily related to this one. – Paul Sep 19 '16 at 21:34
  • error_log was already set to warn, and I changed it to alert, but still nothing. Could the error be happening in openssl before the request reaches nginx? – Michael Hewson Sep 19 '16 at 22:04
  • and nothing's showing up in my syslog, except for a bunch of UFW blocks that seem to be unrelated – Michael Hewson Sep 19 '16 at 22:06
  • 1
    My understanding is that to increase verbosity, you would go in the other direction. For example, debug would be most verbose. For me to guess what is going on, I would need to see the relevant parts of the config. Others may be able to diagnose without it, but I'm not quite that experienced. – Paul Sep 19 '16 at 22:08

As @Paul said, the solution was to raise the log level. I changed a line in my nginx.conf file, so it now reads as follows:

error_log  /var/log/nginx/error.log debug;

And now that the log level is higher, it logs ssl handshake errors:

2016/09/19 22:38:08 [info] 10114#10114: *2 SSL_do_handshake() failed (SSL: error:1408A0C1:SSL routines:ssl3_get_client_hello:no shared cipher) while SSL handshaking, client:, server:
  • 4
    As shown by the [info] heading, a log level of info would be sufficient, and would be a lot less noisy than debug. – Michael Hampton Sep 19 '16 at 22:59
  • @MichaelHampton for some reason my log (basically identical to the one in this post) differs in that it is being logged only from [debug] and not [info]. So for some it might be better to just start with the most verbose logging. – Marc Jun 19 '18 at 20:53

Actually you have used the option ssl_ecdh_curve to configure Diffie Hellman key exchange in Nginx but you have not provided a parameter file. Therefore you have to use the option ssl_dhparam and must create a file with openssl.

Create file:

openssl dhparam -out /etc/ssl/certs/dhparam.pem 4096

Use file and above Diffie Hellman configuration in Nginx:

ssl_dhparam                     /etc/ssl/certs/dhparam.pem;
ssl_ecdh_curve                  secp384r1;
  • I accepted my own answer because it answers the original question, but still gave you +1 for pointing this out. Just to note, I actually did have an ssl_dhparam in the config file but somehow it didn't end up in the code I posted. – Michael Hewson Oct 13 '16 at 23:00
  • If you want to finish work today, use the command: openssl dhparam -dsaparam -out /etc/ssl/certs/dhparam.pem 2048 – Aivils Štoss May 25 '20 at 7:43

You can check you nginx server config , there is a config line is : ssl_ciphers, the default value is : ssl_ciphers HIGH:!aNULL:!MD5; (http://nginx.org/en/docs/http/ngx_http_ssl_module.html#ssl_ciphers), but sometimes is not expect, in my case , nginx-ingress-controller default is less then default config, and the nginx debug log show error is :no shared cipher. when I add some ciphers in config file and reload nginx , the promeble was reloved.And you can reference this config template: https://mozilla.github.io/server-side-tls/ssl-config-generator/

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.