0 votes
by (120 points)

Hi I am evaluating Rebex TlsSocket to establish secured TLS1.2 MQTT connection with Aws IoT Hub. We have volume field devices and a successful trial should help us connect all the field devices with AWS IoT Hub.

I referred to this article and followed all steps https://forum.rebex.net/9807/how-to-use-tlssocket-directly?show=9807#q9807

Code:

this.tlsSocket = new TlsClientSocket();
tlsSocket.LogWriter = new Rebex.FileLogWriter(@"D:\log.txt",Rebex.LogLevel.Debug);
this.tlsSocket.Connect(new IPEndPoint(this.remoteIpAddress, this.remotePort));
tlsSocket.Parameters.Version = TlsVersion.TLS12;
//var cert = Certificate.LoadPfx("devicecert.pfx", "");
tlsSocket.Parameters.CertificateRequestHandler = CertificateRequestHandler.CreateRequestHandler(clientCert);
tlsSocket.Parameters.CertificateVerifier = CertificateVerifier.Default;
tlsSocket.ValidatingCertificate += new EventHandler<SslCertificateValidationEventArgs>(tlsSocket_ValidatingCertificate);

I am getting following error:

2023-05-23 00:12:00 INFO TlsSocket(54267293)[1] TLS: Performing client certificate authentication.
2023-05-23 00:12:00 DEBUG TlsSocket(54267293)[1] TLS: Error while processing TLS packet: System.Security.Cryptography.CryptographicException: Unable to create SHA256 hash using 楍牣獯景⁴湅慨据摥䌠祲瑰杯慲桰捩倠潲楶敤⁲ㅶ〮� (0x80090008).
   at ghric.xtdkc.wbbry(Byte[] p0, aippr p1)
   at Rebex.Security.Cryptography.AsymmetricKeyAlgorithm.SignHash(Byte[] hash, SignatureHashAlgorithm hashAlgorithm)
   at ghric.autbd.hwlnr(Byte[] p0, Int32 p1, Int32 p2, ivnfx p3)
   at ghric.autbd.fwlia(Byte[] p0, Int32 p1, Int32 p2)
   at ghric.yexzh.fcfxr(Byte[] p0, Int32 p1, Int32 p2)
   at ghric.yexzh.loqiv()
2023-05-23 00:12:01 INFO TlsSocket(54267293)[1] TLS: Fatal Alert:InternalError was sent.
2023-05-23 00:13:07 Opening log file.
2023-05-23 00:13:07 INFO FileLogWriter(1)[1] Info: Assembly: Rebex.Common R5.11 for .NET Compact Framework 3.5

My client Certificate file "devicecert.pfx does not have any password set. I am able to use same certificate on .NET 4.5 Windows to connect.

Applies to: Rebex TLS

1 Answer

0 votes
by (144k points)

PFX support is limited on .NET CF 3.5 on platforms that don't support SHA-2, which seems to be the case here.

As a workaround, load the certificate and the private key from files. To create those two files, load the PFX file on .NET 4.5 on Windows and convert it to a .cer/.pri file pair:

var cert = Certificate.LoadPfx("devicecert.pfx", password); 
cert.Save("devicecert.cer", CertificateFormat.Base64Der);
cert.SavePrivateKey("devicecert.key", password, PrivateKeyFormat.Base64Pkcs8, true);

Then, in .NET CF 3.5 application, load the certificate from those two files instead of the PFX:

var clientCert = Certificate.LoadDerWithKey("devicecert.cer", "devicecert.key", "password");
by (120 points)
Hi Lukas,

Thanks for troubleshooting this. But with patched Code, soon after TLS negotiate

-06-07 22:02:45.009 INFO TlsClientSocket(1)[6] TLS: Connection secured using cipher: TLS 1.2, RSA with ephemeral ECDH, AES with 128-bit key in GCM mode, AEAD.
2023-06-07 22:02:45.378 DEBUG TlsClientSocket(1)[3] TLS: Alert:CloseNotify was received.
2023-06-07 22:02:45.381 DEBUG TlsClientSocket(1)[3] TLS: Alert:CloseNotify was sent.

And the connection is closed. This behavior is same as https://forum.rebex.net/22322/rebex-tlssocket-on-netcf3-5?show=22326#c22326
by (144k points)
Hi, I noticed this as well and investigated a bit - the server closes the connection when it receives the client's message (sent in MqttClient.SendReceive method). If the client does not send any message, the server keeps waiting and does not close the connection. The most likely explanation is that the server did not like the message and therefore closed the connection. A server-side log would hopefully reveal what's going on and why the server closed the connection.

Do you have any code using .NET's SslStream that sends the same message and the connection does not get closed? We could look into it and determine where's the difference.
by (120 points)
Hi Lukas,

Added Test Application Win.zip to the SFTP location.

Interestingly .NET X509Certificate was not working but with X509Certificate2 everything works fine. I thought to share with you incase this of any help.

Also, do you think it might be timeout related issues? tls.Negotiate() with Rebex libraries takes some time.

Since we are connecting with AWS server, we may not have any log from there.
by (144k points)
Hi, the cause of the issue turned out to be quite simple - in the Rebex-based version of MqttNetworkChannel.Connect method, you were connecting to an IP address but did not pass the remote host name to the server. Try adding this line:

    tlsSocket.Parameters.CommonName = this.remoteHostName;

(Also remove "this.netStream.Close()" and "this.socket.Close();" from the Close method as well because those field are unused and would cause a NullReferenceException.)
by (120 points)
Hi Lukas
Thanks it works like a charm on the Patched code that we were working on in SFTP folder. Will be testing on the device and let you know the result.
...