Sign up ×
Server Fault is a question and answer site for system and network administrators. It's 100% free, no registration required.

I am using Nginx as a proxy to 4 apache instances. My problem is that SSL negotiation takes a lot of time (600 ms). See this as an example:

Here is my Nginx Conf:

user www-data;
worker_processes  4;

events {
    worker_connections 2048;
    use epoll;

http {
    include       /etc/nginx/mime.types;
    default_type  application/octet-stream;
    access_log  /var/log/nginx/access.log;
    sendfile        on;
    keepalive_timeout  0;
    tcp_nodelay        on;
    gzip  on;
    gzip_proxied any;
    server_names_hash_bucket_size 128;


upstream abc {
     server weight=1;
     server weight=1;
     server weight=1;


server {
    listen   443;
    server_name  blah;

    keepalive_timeout 5;

    ssl  on;
    ssl_certificate  /blah.crt;
    ssl_certificate_key  /blah.key;
    ssl_session_cache  shared:SSL:10m;
    ssl_session_timeout  5m;
    ssl_protocols  SSLv2 SSLv3 TLSv1;
    ssl_ciphers RC4+RSA:+HIGH:+MEDIUM:+LOW:+SSLv2:+EXP;
    ssl_prefer_server_ciphers   on;

    location / { proxy_pass http://abc;

                 proxy_set_header X-Real-IP  $remote_addr;
                 proxy_set_header Host $host;
                 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;



The machine is a VPS on Linode with 1 G of RAM. Can anyone please tell why SSL Hand shake is taking ages?

share|improve this question

4 Answers 4

You need to disable "ephemeral diffie-hellman" ciphers. Browsers don't use them anyway, but openSSL will when used with tools like cURL or apachebench. So I am betting that is using them.

See this thread for more details.

I personally use these settings in nginx to force the fastest-but-still-secure SSL ciphers based on the server's preferences, and not the browsers:

Update 2014-01-13: This advice has changed given recent attacks on RC4, browser updates which protect against BEAST, and the more widespread availability of TLS v1.2 in clients and servers. Updated nginx TLS settings as recommended by CloudFlare:

ssl_protocols SSLv3 TLSv1 TLSv1.1 TLSv1.2;
ssl_prefer_server_ciphers on;

This supersedes the earlier advice in this answer, which was:

#only use secure TLSv1 and SSLv3, not insecure SSL2
ssl_protocols TLSv1 SSLv3;
#set up preference list, fastest first but disabling very slow or insecure encryption
ssl_ciphers RC4:AES128-SHA:TLSv1:SSLv3:!ADH:!aNULL:!DH:!EDH:!eNULL:!LOW:!SSLv2:!EXP:!NULL;
#use my preference list to determine encryption instead of clients
ssl_prefer_server_ciphers on;
share|improve this answer
RC4 is insecure and not suitable fr use in TLS. "While the RC4 algorithm is known to have a variety of cryptographic weaknesses (see [26] for an excellent survey), it has not been previously explored how these weaknesses can be exploited in the context of TLS. Here we show that new and recently discovered biases in the RC4 keystream do create serious vulnerabilities in TLS when using RC4 as its encryption algorithm." See On the Security of RC4 in TLS and WPA. –  jww Jan 7 '14 at 6:52
@noloader that Rc4 attack was announced years after my post; until very recently most cryptographers were recommending RC4 over AES because of the BEAST attack against TLS v1.0 and earlier. Now that most browsers protect against BEAST client-side, and there have been further attacks against RC4, the advice has changed. See this post for some good nginx settings for TLS v1.2: –  rmalayter Jan 14 '14 at 4:00
Oh my! Sorry about that. I did not think to check the dates. Sorry. –  jww Jan 14 '14 at 4:04

You may not have a good entropy source. Does /dev/urandom exist? If not Nginx will block on reading /dev/random.

What is the size of your key? Longer is slower.

Try straceing the processes to see what they are doing.

share|improve this answer
+1 Seems like a good possibility as urandom is often missing on VPSs –  Kyle Brandt Oct 21 '10 at 1:41

check that you're not waiting on DNS resolution somewhere.

share|improve this answer


ssl_protocols  SSLv2 SSLv3 TLSv1;


ssl_protocols  SSLv3 TLSv1 SSLv2;

Tries protocols in the order that they are listed.

share|improve this answer
Didn't really help. See -- negotiation still take >50% of the whole time. –  Paras Chopra Oct 20 '10 at 15:26
SSLv2 should NOT be used, it is insecure. At the time of this comment all major browser should support TLSv1 so SSLv3 should no longer be needed as well. (ideally it should be TLSv1 TLSv1.1 TLSv1.2 until most of the browsers adopt 1.1). –  KBeezie Dec 17 '12 at 7:50

Your Answer


By posting your answer, you agree to the privacy policy and terms of service.

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