Issue with SNI/SSL and default_server

Heya,

I have a server with two domains using SSL on one IP via SNI. So far so
good, but the problem is that one of the site is marked as
default_server to catch all (then I do a redirect to the proper domain,
I left out some parts of the config below for conciseness).

The problem is, if you have a ssl server marked as default_server, it
seems to take over everything else, and domainb.com is not reachable via
SSL anymore.

server {
listen 80 default_server;
server_name domaina.com ;
}

server {
listen 443 ssl default_server;
server_name domaina.com ;
}

server {
listen 80;
server_name domainb.com;
}

server {
listen 443 ssl;
server_name domainb.com ;
}

The workaround I found is the following: I put the IP in the
server_name, and therefore can remove the default_server flag from the
ssl server (it’s not completely equivalent, but close enough for my
purposes). The problem is that it needs the server public IP in, which
isn’t ideal to have generic vhost templates in puppet:

server {
listen 80 default_server;
server_name domaina.com ;
}

server {
listen 443 ssl;
server_name domaina.com ;
}

server {
listen 80;
server_name domainb.com;
}

server {
listen 443 ssl;
server_name domainb.com ;
}

I am not sure whether this is a bug or an expected feature, which is why
I am writing here.

Cheers


Jordi Boggiano
@seldaek - http://nelm.io/jordi

I’ve had the same issues and did some testing.

The following causes the issue where the SSL certificate that is defined
in
the default_server block is being sent for requests that end up in
another
server block that has a different ssl_certificate defined. This only
happens
when adding the IP address as server_name.

Example of issue:
server {
listen 443 default_server ssl;
server_name _;
ssl_certificate /usr/local/nginx/conf/ssl/default.crt;
ssl_certificate_key /usr/local/nginx/conf/ssl/default.key;
location / { return 403; }
}

server {
listen 443 ssl;
server_name 1.2.3.4;
ssl_certificate /usr/local/nginx/conf/ssl/1.2.3.4.crt;
ssl_certificate_key /usr/local/nginx/conf/ssl/1.2.3.4.key;
location /test { return 401;}
}

When I access https://1.2.3.4/test , I receive a 401 error as expected,
but
the SSL certificate being sent is the one defined in default.crt

Working:

server {
listen 443 ssl;
server_name test.hostname.com;
ssl_certificate /usr/local/nginx/conf/ssl/1.2.3.4.crt;
ssl_certificate_key /usr/local/nginx/conf/ssl/1.2.3.4.key;
location /test { return 401;}
}

Now when accessing test.hostname.com which is an A record to 1.2.3.4 , I
get
served the correct certificate as defined in 1.2.3.4 – I’ve tested this
multiple times on Ubuntu 12.04 w/ nginx as configured:
nginx version: nginx/1.2.3
built by gcc 4.6.3 (Ubuntu/Linaro 4.6.3-1ubuntu5)
TLS SNI support enabled
configure arguments: --with-http_ssl_module --user=nobody --group=nobody

Can anybody test and confirm this besides us?

Posted at Nginx Forum:

I tested with latest stable versions of Firefox, Chrome, IE9 on Windows
7
x64. What you said makes sense to me but I have no way of verifying from
my
end. If you find out this is the case, please make note of it in the
documentation somewhere to save somebody else the frustration of
figuring
this out.

Thanks!

Posted at Nginx Forum:

On Aug 28, 2012, at 8:48 , bompus wrote:

I tested with latest stable versions of Firefox, Chrome, IE9 on Windows 7
x64. What you said makes sense to me but I have no way of verifying from my
end. If you find out this is the case, please make note of it in the
documentation somewhere to save somebody else the frustration of figuring
this out.

I’ve just tested using Firefox/MacOSX. It does not send a hostname in
SSL
handshake packet if the hostname is IP address.


Igor S.

On Aug 28, 2012, at 8:33 , bompus wrote:

server_name _;
location /test { return 401;}
server_name test.hostname.com;
TLS SNI support enabled
configure arguments: --with-http_ssl_module --user=nobody --group=nobody

What client do you use to test ?
It may not send a hostname in SSL hello request if the hostname is IP
address.


Igor S.

On Aug 21, 2012, at 16:58 , Jordi Boggiano wrote:

server {
server_name, and therefore can remove the default_server flag from the
listen 443 ssl;
server_name domainb.com ;
}

I am not sure whether this is a bug or an expected feature, which is why
I am writing here.

These configuration should be equal from nginx point of view,
since the first server becomes default_server anyway. Probably
the real configuration does not correspond to them.


Igor S.

Good to know. Thank you for checking on this. If you could add this
information to the documentation for SNI and/or SSL, that would be
helpful
for others.

Posted at Nginx Forum:

On Aug 28, 2012, at 9:25 , bompus wrote:

Good to know. Thank you for checking on this. If you could add this
information to the documentation for SNI and/or SSL, that would be helpful
for others.

We will add. BTW, using SNI for IP addresses is forbidden by RFC:

Currently, the only server names supported are DNS hostnames;
however, this does not imply any dependency of TLS on DNS, and other
name types may be added in the future (by an RFC that updates this
document).

Safari is the only browser in our tests which uses SNI for IP addresses.


Igor S.