connect icon indicating copy to clipboard operation
connect copied to clipboard

[BUG] TLS Hostname verification with a variable in the URL

Open elavy-harris opened this issue 2 years ago • 11 comments

Describe the bug Using the SSL Manager for a Destination, if

  1. the hostname for the URL is represented as a variable, e.g. ${Smile_CDR_Server_Address}, AND
  2. Hostname verification is enabled

then attempts to send a message fail.

ERROR MESSAGE: javax.net.ssl.SSLPeerUnverifiedException: Certificate for <${Smile_CDR_Server_Address}> doesn't match any of the subject alternative names: [*.harris-chr.com, harris-chr.com]

To Reproduce

  1. Create an entry in the Configuration Map, e.g. hostname, populated with the hostname of a remote server that will accept TLS.
  2. Create a Destination with SSL Manager enabled and Hostname verification enabled.
  3. Specify the Remote Address (if using a TCP Sender) to ${hostname}
  4. Send any message.
  5. See error.

Expected behavior TLS handshake should succeed, assuming that the rest of TLS is configured properly.

Actual behavior Hostname verification fails.

Screenshots If applicable, add screenshots to help explain your problem.

Environment (please complete the following information):

  • Connect Version 4.1.1

Workaround(s) Turn off Hostname verification. This, however, reduces security.

elavy-harris avatar Nov 02 '22 20:11 elavy-harris

Example destination:

Mirth Issue 5506.zip

elavy-harris avatar Nov 02 '22 20:11 elavy-harris

Lets rule out the simple things first - what is the literal URL for Smile_CDR_Server_Address?

ERROR MESSAGE: javax.net.ssl.SSLPeerUnverifiedException: Certificate for <${Smile_CDR_Server_Address}> doesn't match any of the subject alternative names: [*.harris-chr.com, harris-chr.com] would happen if, for example, ${Smile_CDR_Server_Address} was https://elavy.harris-smile.com . In other words, it isn't a substitution issue, it's literally a hostname mismatch AFTER substituting the correct values.

It'll be a few hours but I'll try to reproduce the results with your example. If this is an issue, it will impact me also.

jonbartels avatar Nov 03 '22 13:11 jonbartels

The literal URL is smilecdrdev.harris-chr.com. If I put that in the destination explicitly, in place of the map reference, hostname verification works.

elavy-harris avatar Dec 12 '22 15:12 elavy-harris

Do you have a full stack trace @elavy-harris ?

ChristopherSchultz avatar Feb 03 '23 19:02 ChristopherSchultz

Here's what shows up on the Error tab:

TCP Sender error
ERROR MESSAGE: javax.net.ssl.SSLPeerUnverifiedException: Certificate for <${Smile_CDR_Server_Address}> doesn't match any of the subject alternative names: [*.harris-chr.com, harris-chr.com]
javax.net.ssl.SSLHandshakeException: javax.net.ssl.SSLPeerUnverifiedException: Certificate for <${Smile_CDR_Server_Address}> doesn't match any of the subject alternative names: [*.harris-chr.com, harris-chr.com]
	at java.base/sun.security.ssl.Alert.createSSLException(Alert.java:131)
	at java.base/sun.security.ssl.TransportContext.fatal(TransportContext.java:353)
	at java.base/sun.security.ssl.TransportContext.fatal(TransportContext.java:296)
	at java.base/sun.security.ssl.TransportContext.fatal(TransportContext.java:291)
	at java.base/sun.security.ssl.CertificateMessage$T13CertificateConsumer.checkServerCerts(CertificateMessage.java:1357)
	at java.base/sun.security.ssl.CertificateMessage$T13CertificateConsumer.onConsumeCertificate(CertificateMessage.java:1232)
	at java.base/sun.security.ssl.CertificateMessage$T13CertificateConsumer.consume(CertificateMessage.java:1175)
	at java.base/sun.security.ssl.SSLHandshake.consume(SSLHandshake.java:392)
	at java.base/sun.security.ssl.HandshakeContext.dispatch(HandshakeContext.java:443)
	at java.base/sun.security.ssl.HandshakeContext.dispatch(HandshakeContext.java:421)
	at java.base/sun.security.ssl.TransportContext.dispatch(TransportContext.java:183)
	at java.base/sun.security.ssl.SSLTransport.decode(SSLTransport.java:172)
	at java.base/sun.security.ssl.SSLSocketImpl.decode(SSLSocketImpl.java:1506)
	at java.base/sun.security.ssl.SSLSocketImpl.readHandshakeRecord(SSLSocketImpl.java:1416)
	at java.base/sun.security.ssl.SSLSocketImpl.startHandshake(SSLSocketImpl.java:456)
	at java.base/sun.security.ssl.SSLSocketImpl.ensureNegotiated(SSLSocketImpl.java:921)
	at java.base/sun.security.ssl.SSLSocketImpl$AppOutputStream.write(SSLSocketImpl.java:1291)
	at java.base/java.io.BufferedOutputStream.flushBuffer(BufferedOutputStream.java:81)
	at java.base/java.io.BufferedOutputStream.flush(BufferedOutputStream.java:142)
	at java.base/java.io.DataOutputStream.flush(DataOutputStream.java:123)
	at com.mirth.connect.model.transmission.framemode.FrameStreamHandler.write(FrameStreamHandler.java:265)
	at com.mirth.connect.model.transmission.framemode.FrameStreamHandler.writeFrame(FrameStreamHandler.java:246)
	at com.mirth.connect.model.transmission.framemode.FrameStreamHandler.write(FrameStreamHandler.java:242)
	at com.mirth.connect.connectors.tcp.TcpDispatcher.send(TcpDispatcher.java:523)
	at com.mirth.connect.connectors.tcp.TcpDispatcher.send(TcpDispatcher.java:457)
	at com.mirth.connect.donkey.server.channel.DestinationConnector.handleSend(DestinationConnector.java:904)
	at com.mirth.connect.donkey.server.channel.DestinationConnector.run(DestinationConnector.java:730)
	at java.base/java.lang.Thread.run(Thread.java:829)
Caused by: java.security.cert.CertificateException: javax.net.ssl.SSLPeerUnverifiedException: Certificate for <${Smile_CDR_Server_Address}> doesn't match any of the subject alternative names: [*.harris-chr.com, harris-chr.com]
	at com.mirth.connect.plugins.ssl.server.e.b(SourceFile:137)
	at com.mirth.connect.plugins.ssl.server.e.checkServerTrusted(SourceFile:92)
	at java.base/sun.security.ssl.AbstractTrustManagerWrapper.checkServerTrusted(SSLContextImpl.java:1510)
	at java.base/sun.security.ssl.CertificateMessage$T13CertificateConsumer.checkServerCerts(CertificateMessage.java:1341)
	... 23 more
Caused by: javax.net.ssl.SSLPeerUnverifiedException: Certificate for <${Smile_CDR_Server_Address}> doesn't match any of the subject alternative names: [*.harris-chr.com, harris-chr.com]
	at org.apache.http.conn.ssl.DefaultHostnameVerifier.matchDNSName(DefaultHostnameVerifier.java:177)
	at org.apache.http.conn.ssl.DefaultHostnameVerifier.verify(DefaultHostnameVerifier.java:122)
	at com.mirth.connect.plugins.ssl.server.e.b(SourceFile:132)
	... 26 more

elavy-harris avatar Feb 03 '23 19:02 elavy-harris

FYI, I upgraded to 4.2.0 before producing the stack trace above.

elavy-harris avatar Feb 03 '23 19:02 elavy-harris

Thanks. I checked, and I don't see anywhere in Mirth where a hostname verifier is being created and handed an exact hostname, so it must be looking at the URL being contacted and/or the contents of the Host header being sent versus the CN/SAN of the server certificate.

Obviously, the effective hostname must be correct otherwise you'd be getting MalformedURLException or IOException/connection failure or whatever.

I'm (currently) at a loss as to why the connection would work but the hostname verifier would be convinced to use a non-token-replaced hostname for verification.

ChristopherSchultz avatar Feb 03 '23 22:02 ChristopherSchultz

Are you sending a custom Host header in your HTTP request?

ChristopherSchultz avatar Feb 03 '23 22:02 ChristopherSchultz

Oh. I'm also only viewing the source of the community edition. It's entirely possible that the SSL Manager Plug-in does things differently.

I would file a support case with NextGen as this is a paid-for plug-in.

ChristopherSchultz avatar Feb 03 '23 22:02 ChristopherSchultz

I am also running into this issue. We are using the SSL Manager Extension. Running Mirth 4.4.0. Is there any update on this issue?

mcswaip1 avatar Oct 25 '23 14:10 mcswaip1

@mcswaip1 This item is currently on the bubble for 4.5.0. At this point it looks about 50/50 if it will make it or not. 4.5 is tentatively scheduled for the end of January.

JackieK5 avatar Nov 16 '23 19:11 JackieK5