tlsv1 alert protocol version when connecting via SSL to OS X Server

How can I re-enable TLS 1.1 and 1.0 on server 5.3 with macOS 10.12.4 in the short term while I evaluate all the clients that aren't ready for TLS 1.2?

If you jump to the bottom, attempts to change comfiguration files have failed so far to restore backwards compatibility

SSLProtocol -all +TLSv1 +TLSv1.1 +TLSv1.2

After having updated our server to macOS 12.4 and the Server app to version 5.3, using curl to connect to a macOS server https site from a Linux machine ceased to work, issuing the following messages on the client side:

$ curl -v --insecure -o "output.file" https://myserver.domain/path/page.php
* About to connect() to myserver.domain port 443 (#0)
*   Trying 192.168.xxx.xxx... connected
* Connected to myserver.domain (192.168.xxx.xxx) port 443 (#0)
* successfully set certificate verify locations:
*   CAfile: none
  CApath: /etc/ssl/certs/
* SSLv3, TLS handshake, Client hello (1):
} [data not shown]
* error:1407742E:SSL routines:SSL23_GET_SERVER_HELLO:tlsv1 alert protocol version
* Closing connection #0

The connection worked well before the update of the macOS server. So it seems that the update switched off a connection option which curl relies on. I googled a lot, but I am still uncertain about what exactly the cause is.

The same curlcommand works when issued from another Mac. The linux machine has

$ curl --version
curl 7.19.0 (x86_64-suse-linux-gnu) libcurl/7.19.0 OpenSSL/0.9.8h zlib/1.2.3 libidn/1.10
Protocols: tftp ftp telnet dict ldap http file https ftps 
Features: GSS-Negotiate IDN IPv6 Largefile NTLM SSL libz 

while on the Mac client

$ curl --version
curl 7.51.0 (x86_64-apple-darwin16.0) libcurl/7.51.0 SecureTransport zlib/1.2.8
Protocols: dict file ftp ftps gopher http https imap imaps ldap ldaps pop3 pop3s rtsp smb smbs smtp smtps telnet tftp 
Features: AsynchDNS IPv6 Largefile GSS-API Kerberos SPNEGO NTLM NTLM_WB SSL libz UnixSockets 

Unfortunately, it is not an option to try updating curlon the Linux machine.

Some resources claim incompatible cipher suites to be the cause, but after some testing, I haven't been able to find a solution using the --ciphers option, and also I am not sure how to find a compatible cipher suite.

I have tried to find out what changed with macOS Server 5.3, but the Apple change log does not give me any hint about it. So the question is:

What has changed in macOS 12.4 and/or macOS Server 5.3 and how can I re-configure my macOS server so the curlconnection works again?

Update 1:

I have temporarily exposed port 443 to the public, so I could perform the SSL Labs tests. The results show that my macOS server supports only TLS 1.2 and nothing else any more. For several simulated clients, the test report Server sent fatal alert: protocol_version - including, for example, IE8-10/Win7 and Java7u25.

I have tried to reactivate TLS 1 and 1.1 in

  • /library/server/web/config/apache2/sites/0000_127.0.0.1_34543_myserver.domain.conf
  • /library/server/web/config/apache2/httpd.conf
  • /library/server/web/config/apache2/httpd_server_app.conf
  • /library/server/web/config/proxy/apache_serviceproxy.conf (multiple instances here)

changing

SSLProtocol -all +TLSv1.2

into

SSLProtocol -all +TLSv1 +TLSv1.1 +TLSv1.2

or even

SSLProtocol All

but it did not make a difference when fetching the URL with curl.

Update 2:

The service proxy error log shows

[datetime] [ssl:info] [pid n] [client x.x.x.x:38805] AH02008: SSL library error 1 in handshake (server myserver.domain:443)
[datetime] [ssl:info] [pid n] SSL Library Error: error:1408A10B:SSL routines:SSL3_GET_CLIENT_HELLO:wrong version number
[datetime] [ssl:info] [pid n] [client x.x.x.x:38805] AH01998: Connection closed to child 11 with abortive shutdown (server myserver.domain:443)

To me, it looks as if my attempts to activate TLS v1 do not work.

So the question is: How can I reactivate TLS v1 in macOS Server Apache?


curl 7.19.0 ... OpenSSL/0.9.8h

This is a very old (and unsupported) version of OpenSSL you are using here which has no support for modern protocols like TLS 1.2 and modern ECDHE ciphers. Chances are high that after the upgrade your server now requires such protocol and/or cipher and thus connecting with your old OpenSSL version will fail.

* SSLv3, TLS handshake, Client hello (1):

This might also indicate that your client is trying to use SSL 3.0, which is usually disabled today because it is an insecure protocol. You might try to enforce to use TLS 1.0 (which is supported by OpenSSL 0.9.8) by using curl -1 or curl --tls1 in the hope that the server still supports TLS 1.0 and has ciphers configured to be usable by the old OpenSSL version.


In order to re-enable TLSv1 (or other protocols), it is required to modify the proxy configuration in /Library/Server/Web/config/proxy/apache_serviceproxy.conf, adding the required protocol to the <VirtualHost *:443> section like so:

<VirtualHost *:443>
  ProxyPreserveHost On
 SetEnv proxy-chain-auth on
 RequestHeader set X-Forwarded-Proto "https"
 RequestHeader set X-Forwarded-Port "443"
 RequestHeader unset Proxy early
 <IfModule mod_ssl.c>
   SSLEngine On
   SSLCertificateFile "/etc/certificates/${CERT_ID}.cert.pem"
   SSLCertificateKeyFile "/etc/certificates/${CERT_ID}.key.pem"
   SSLCertificateChainFile "/etc/certificates/${CERT_ID}.chain.pem"
   SSLCipherSuite "HIGH:MEDIUM:!MD5:!RC4:!3DES"
   SSLProtocol -all +TLSv1 +TLSv1.1 +TLSv1.2
   SSLProxyEngine On
   SSLProxyProtocol -all +TLSv1.2
   SSLProxyCheckPeerCN off
   SSLProxyCheckPeerName off
 </IfModule>
 [...]
</VirtualHost>

According to my tests, SSLProxyProtocol need not be modified. Also, changes in the other files mentioned in the question do not have an effect, so they need not be touched.

Caveat: Upgrading your Server app will probably always overwrite /Library/Server/Web/config/proxy/apache_serviceproxy.conf. After an upgrade, you will have to reapply the modification.


Note: I have tried to move the changes to a separate custom configuration file apache_serviceproxy_customsites_myserver.domain.conf, which should stop Server upgrades from reverting these modifications. In addition to that, the protocol change could be limited to a specific domain. But that did not seem to work - still investigating why.


In order to make sure your modifications are used, it seems to be necessary to restart macOS (sudo shutdown -r), not only the webserver (sudo serveradmin stop/start web) in order to restart the proxy service.

A verification by the SSL Labs server test reports that TLS 1.0, 1.1 and 1.2 are now available, while SSL 2 and 3 are not.