question

iSukhi-8842 avatar image
0 Votes"
iSukhi-8842 asked BREILPatrick-6942 commented

TCP TLS communication in Xamarin Forms Application

I want to establish connection between the client and server over TCP using TLS in my Xamarin forms Application. I am facing issues making a successful connection using certificate. Please guide me.

dotnet-xamarin
· 4
5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.

Hi, iSukhi-8842. First create a TcpClient, and then use SslStream to authenticate the connected client through the TLS protocol.

using (var tcpClient = new TcpClient("10.1.10.250", port))
using (var ssl = new SslStream(tcpClient.GetStream(), false, new RemoteCertificateValidationCallback(CertificateValidation)))
{
    ssl.AuthenticateAsClient("10.1.10.250", null, System.Security.Authentication.SslProtocols.Tls12, false);
    if (ssl.CanWrite)
    {
        ...
    }
    else
        throw new SocketException();
}

You could google with the keyword as Versatile Digital DNA Simple Client–Server in C# to check the related document to get how to write a client server in c#.

And here is the similar issue case, you could refer to the function code:
https://stackoverflow.com/questions/54914621/access-self-signed-x509certificates-in-xamarinforms-for-mqtt-tls-connection-to-a

0 Votes 0 ·

I tried your code and it is giving certificate mismatch exception.
Wha is certificate pinning?
Do i need to do it while doing local tcp communication?
I followed https://stackoverflow.com/questions/54914621/access-self-signed-x509certificates-in-xamarinforms-for-mqtt-tls-connection-to-a
for the reference.

0 Votes 0 ·

This is my code:

X509Certificate vCert;

     bool CertificateValidation(object sender, X509Certificate certificate, X509Chain chain, SslPolicyErrors certificateErrors)
     {if (vCert == null)
         { using (var waitHandle = new EventWaitHandle(false, EventResetMode.AutoReset))
             {Task.Run(async () =>
                 {
                 using (var assetStream = await Xamarin.Essentials.FileSystem.OpenAppPackageFileAsync("CA_Certificate.cer"))
                 using (var memStream = new MemoryStream())
                 {
                     assetStream.CopyTo(memStream);
                     vetaarCert = new X509Certificate(memStream.ToArray());
                     waitHandle.Set();
                 }
             });
             waitHandle.WaitOne();
         }
     }
     bool result = vCert.Equals(certificate) ? true : false;
     return result;
 }
0 Votes 0 ·

Could you post the details about the error log?

0 Votes 0 ·

1 Answer

JeremyKaiser-1025 avatar image
0 Votes"
JeremyKaiser-1025 answered BREILPatrick-6942 commented

I would say you could do it using MQTTnet but I am having similar issues connecting to aws.

private async Task OnConnectToIoTHubCommandAsync()
{
const string server = "sample.amazonaws.com";
const string clientId = "XXXXXXXXXXKELYG82g";
const string machineId = "XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXX";
const string topic = "helloServer" + machineId;

             byte[] caCertRawBytes;
             byte[] clientCertRawBytes;
    
             using (var stream = await FileSystem.OpenAppPackageFileAsync("AmazonRootCA1.crt"))
             {
                 using (var memoryStream = new MemoryStream())
                 {
                     stream.CopyTo(memoryStream);
                     caCertRawBytes = memoryStream.ToArray();
                 }
             }
    
             using (var stream = await FileSystem.OpenAppPackageFileAsync("Private.pfx"))
             {
                 using (var memoryStream = new MemoryStream())
                 {
                     stream.CopyTo(memoryStream);
                     clientCertRawBytes = memoryStream.ToArray();
                 }
             }
    
             var caCert = new X509Certificate(caCertRawBytes);
             var clientCert = new X509Certificate2(clientCertRawBytes, "PfxPassword"); 
    
             var source = new CancellationTokenSource();
             var token = source.Token;
    
             var mqttOptions = new MqttClientOptionsBuilder()
                                   .WithTcpServer(server, 8883)
                                   .WithTls(new MqttClientOptionsBuilderTlsParameters
                                   {
                                       UseTls = true,
                                       Certificates = new List<X509Certificate> { caCert, clientCert },
                                       AllowUntrustedCertificates = false,
                                       IgnoreCertificateChainErrors = false,
                                       IgnoreCertificateRevocationErrors = false,
                                   })
                                   .Build();
    
             // Create a new MQTT client.
             var mqttClient = new MqttFactory().CreateMqttClient();
             await mqttClient.ConnectAsync(mqttOptions, token);
             await Task.CompletedTask.ConfigureAwait(false);
         }

The output is an authentication failed see inner exception but the only thing in there is a System Exception exception and a timeout. I'm posting because my problem seems to be closely related to yours. The pfx file is a combination of the thing cert and the private key.

· 1
5 |1600 characters needed characters left characters exceeded

Up to 10 attachments (including images) can be used with a maximum of 3.0 MiB each and 30.0 MiB total.

I had the same problem while logging in.
By only putting the pfx in the list of certificates it works correctly, just clientCert for your example.



0 Votes 0 ·