noxxi / p5-io-socket-ssl

IO::Socket::SSL Perl Module
36 stars 59 forks source link

Enablement of SNI is erroneously sensitive to the the case of the inferred hostname #67

Closed ghost closed 6 years ago

ghost commented 6 years ago

This was discovered after assisting a person in #perl at Freenode, who was using the following URL for testing:

HTTPS://WWW.SPS-SERVICE.EU/6AV2124-0GC01-0AX0

Attempts to connect to this URL were resulting in a Can't connect to WWW.SPS-SERVICE.EU:443 (certificate verify failed) error. It was then discovered that the lower case form of this URL worked and, after further testing, that specifying anything other than www. as the first component of the hostname was enough to trigger the error. All of which should not happen, of course.

Eventually, I realised that the host in question requires SNI to be active, otherwise it reports an entirely different CN, against which verification is, indeed, impossible. For instance:

# openssl s_client -connect www.sps-service.eu:443 -servername WWW.SPS-SERVICE.EU </dev/null 2>&1 | grep '^subject'
subject=/OU=Domain Control Validated/CN=*.sps-service.eu

#  openssl s_client -connect www.sps-service.eu:443 </dev/null 2>&1 | grep '^subject'
subject=/C=DE/ST=Bayern/L=Muenchen/O=ispgateway/CN=webserver.ispgateway.de/emailAddress=hostmaster@ispgateway.de

Sure enough, after setting the $DEBUG level to 2, I was able to confirm that IO::Socket::SSL was not attempting to use SNI in the failing case (the first name component being anything other than lower-case www):

DEBUG: .../IO/Socket/SSL.pm:720: not using SNI because hostname is unknown

This is where the issue lies:

# grep -n 'host = undef' /usr/lib64/perl5/vendor_perl/5.24.3/IO/Socket/SSL.pm
712:            $host = undef if $host !~m{[a-z_]} or $host =~m{:};

Specifically, the above regular expression does not tolerate any names that contain upper-case characters, in which case SNI becomes impossible. Adjusting the regular expression to tolerate upper-case alphabetical characters, or adding the /i flag is enough for SNI to be correctly employed for all case-oriented permutations of this particular URL.

noxxi commented 6 years ago

Thanks for reporting the problem. It is fixed in c1e27da