A Tricky “Could not create SSL/TLS secure channel”
My customer is attempting to setup a WCF service behind a SSL balancer. The WCF Service will not have a SSL certificate installed so it will be insecure transport between load balancer and the WCF service. The SSL device requires SSL connection and a client certificate.
Customer wrote a simple client application which could not make even an HTTP GET to the service page. The error was The request was aborted: Could not create SSL/TLS secure channel.
Looking at the Netmon traces I could see the following:
client test.org TLS TLS:TLS Rec Layer-1 HandShake: Client Hello.
test.org client TLS TLS:TLS Rec Layer-1 HandShake: Server Hello.; TLS Rec Layer-2 HandShake: Certificate.
client test.org TLS TLS:TLS Rec Layer-1 HandShake: Certificate. Client Key Exchange.; TLS Rec Layer-2 Cipher Change Spec; TLS Rec Layer-3 HandShake: Encrypted Handshake Message.
test.org 10.53.243.7 TLS TLS:TLS Rec Layer-1 Encrypted Alert // This is a Fatal Error: handshake failure
In our case, the customer was able to make the same request using IE. So I asked for IE traces to compare the differences.
client test.org TLS TLS:TLS Rec Layer-1 HandShake: Client Hello.
test.org client TLS TLS:TLS Rec Layer-1 HandShake: Server Hello.; TLS Rec Layer-2 HandShake: Certificate.
test.org client TLS TLS:Continued Data: 1328 Bytes
client test.org TLS TLS:TLS Rec Layer-1 HandShake: Certificate // THIS WAS MISSING IN THE FAILING TRACE
test.org client TLS TLS:TLS Rec Layer-1 Cipher Change Spec; TLS Rec Layer-2 HandShake: Encrypted Handshake Message.
+ Ethernet
+ Ipv4:
+ Tcp
TLSSSLData: Transport Layer Security (TLS) Payload Data
- TLS: TLS Rec Layer-1 HandShake: Certificate.
- TlsRecordLayer: TLS Rec Layer-1 HandShake:
ContentType: HandShake:
+ Version: TLS 1.0
- SSLHandshake: SSL HandShake Certificate(0x0B)
HandShakeType: Certificate(0x0B)
- Cert: 0x1
CertLength: 2700 (0xA8C)
- Certificates:
CertificateLength: 1392 (0x570)
+ X509Cert: Issuer: Entrust Certification Authority
- Certificates:
CertificateLength: 14241015 (0xD94CF7)
+ X509Cert: Issuer: , Subject:
Here the HandShake: Certificate is a client certificate the IE client had cached and was automatically sending to the SSL load balancer. Earlier that day the customer had selected the certificate so during our investigation I never noticed the requirement for client certificate.
We resolved this by modifying the customer's client.app.config from:
<wsHttpBinding>
<binding name="wsHttpBinding_IUnit">
<security mode="Transport">
<transport clientCredentialType="None" />
<message clientCredentialType="Certificate" />
</security>
</binding>
</wsHttpBinding>
To:
<wsHttpBinding>
<binding name="wsHttpBinding_IUnit">
<security mode="Transport">
<transport clientCredentialType="Certificate" />
</security>
</binding>
</wsHttpBinding>
More Details
Here’s the failure from inside the System.Net traces
System.Net.Sockets Verbose: 0 : [4272] 00000005 : 02 28 // This is a Fatal Error: handshake failure
DateTime=2015-02-27T17:46:24.5449298Z
System.Net.Sockets Verbose: 0 : [4272] Exiting Socket#19612312::Receive() -> Int32#2
DateTime=2015-02-27T17:46:24.5459298Z
System.Net Information: 0 : [4272] InitializeSecurityContext(credential = System.Net.SafeFreeCredential_SECURITY, context = 1b2a1360:1e8cf70, targetName = test.org, inFlags = ReplayDetect, SequenceDetect, Confidentiality, AllocateMemory, InitManualCredValidation)
DateTime=2015-02-27T17:46:24.5469298Z
System.Net Information: 0 : [4272] InitializeSecurityContext(In-Buffers count=2, Out-Buffer length=0, returned code=IllegalMessage).
DateTime=2015-02-27T17:46:24.5479298Z
System.Net.Sockets Verbose: 0 : [4272] Socket#19612312::Dispose()
DateTime=2015-02-27T17:46:24.6669298Z
System.Net Error: 0 : [4272] Exception in HttpWebRequest#32615199:: - The request was aborted: Could not create SSL/TLS secure channel..
DateTime=2015-02-27T17:46:24.6679298Z
System.Net Error: 0 : [4272] Exception in HttpWebRequest#32615199::GetResponse - The request was aborted: Could not create SSL/TLS secure channel..
DateTime=2015-02-27T17:46:24.6689298Z
Comments
Anonymous
June 11, 2015
I am seeing the same behavior with a non-web-service (custom) C# client that uses HttpWebRequest to access https:// resources. Instead of the expected Sockets.Receive() response (with the server cert message), I am also getting a 2-byte only response, and then the IllegalMessage just as you show in your System.Net traces. I am looking for the programmatic equivalent to your <wsHttpBinding> fix.Anonymous
June 14, 2015
Shaun, in our case the client was failing to send a client certificate. Does your service require a client certificate? If so you should be able to attach a client certificate to your HttpWebRequest. This is an older sample but should get you started support.microsoft.com/.../895971Anonymous
September 09, 2016
Saw this fix on Reddit, great for my issue in PowerShell being unable to Invoke-WebRequest, [Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12Invoke-WebRequest -Uri https://yourserver/webpage