NameBased SSL VirtualHosts
This problem occurs if you use multiple Name Based Virtual Hosts and SSL on a single IP-address. The Web-server does not know the name of the requested host until the SSL handshake is done, because the HTTP request headers are part of the encrypted content.
In reality, a Web-server like Apache will allow you to configure name-based SSL virtual hosts, but it will always use the configuration from the first-listed virtual host (on the selected IP address and port) to setup the encryption layer. See https://wiki.apache.org/httpd/NameBasedSSLVHosts for more information.
You can use one certificate for multiple virtual hosts if they are on the same domain using a Wildcard certificate like *.example.com
, which will work for one.example.com
and two.example.com
.
NameBased SSL VirtualHosts with SNI
The solution is an extension to the SSL protocol called Server Name Indication (SNI), which allows the client to include the requested hostname in the first message of its SSL handshake.
See https://wiki.apache.org/httpd/NameBasedSSLVHostsWithSNI for more information.
Apache needs to be built with OpenSSL (with the TLS Extensions option enable-tlsext
enabled; OpenSSL 0.9.8k and later has this enabled by default)
To check if your Apache installation supports SNI, take the following steps:
Enable NameVirtualHost for SSL in /etc/apache2/ports.conf
:
<IfModule mod_ssl.c>
NameVirtualHost *:443
Listen 443
</IfModule>
Create two SSL VirtualHosts in /etc/apache2/sites-available/default-ssl
<VirtualHost *:443>
ServerName www.example1.com
DocumentRoot /var/www/example1
SSLEngine on
SSLCertificateFile /etc/apache2/example1.com.cert
SSLCertificateKeyFile /etc/apache2/example1.com.key
</VirtualHost>
<VirtualHost *:443>
ServerName www.example2.com
DocumentRoot /var/www/example2
SSLEngine on
SSLCertificateFile /etc/apache2/example2.com.cert
SSLCertificateKeyFile /etc/apache2/example2.com.key
</VirtualHost>
Enable mod_ssl:
# a2enmod ssl
Enable the SSL site:
# a2ensite default-ssl
Restart Apache:
# /etc/init.d/apache2 restart
Now if you tail the Apache error log and you see the following message, it means SNI is builtin.
[warn] Init: Name-based SSL virtual hosts only work for clients with \
TLS server name indication support (RFC 4366)
Otherwise you will see an Apache startup a message like You should not use name-based virtual hosts in conjunction with SSL!!
Now if you signed your two certificates example1.com.cert
and example2.com.cert
with your CA certificate, added it to your Browser's trusted list and your Browser supports SNI, you should be able to access https://www.example1.com
and https://www.example2.com
without any complaints from your Browser.
NameBased SSL VirtualHosts with GnuTLS
GnuTLS is an LGPL-licensed implementation of Transport Layer Security, the successor to SSL. With GnuTLS you can create a single certificate valid for multiple domains and wildcard domains, like this:
DNS Name: example1.com
DNS Name: *.example1.com
DNS Name: example2.com
DNS Name: *.example2.com
DNS Name: example3.com
DNS Name: *.example3.com
See https://help.ubuntu.com/community/GnuTLS for a detailed guide on using GnuTLS.