[NF] Add Bot-Utils and rewrite code
This commit is contained in:
parent
90aebbe8be
commit
819e3db228
@ -51,7 +51,7 @@ using System.Collections;
|
|||||||
// (it's ambiguos with uPLibrary.Networking.M2Mqtt.Utility.Trace)
|
// (it's ambiguos with uPLibrary.Networking.M2Mqtt.Utility.Trace)
|
||||||
using MqttUtility = uPLibrary.Networking.M2Mqtt.Utility;
|
using MqttUtility = uPLibrary.Networking.M2Mqtt.Utility;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Net.Security;
|
//using System.Net.Security;
|
||||||
|
|
||||||
namespace uPLibrary.Networking.M2Mqtt
|
namespace uPLibrary.Networking.M2Mqtt
|
||||||
{
|
{
|
||||||
|
@ -1,472 +1,472 @@
|
|||||||
/*
|
/*
|
||||||
Copyright (c) 2013, 2014 Paolo Patierno
|
Copyright (c) 2013, 2014 Paolo Patierno
|
||||||
|
|
||||||
All rights reserved. This program and the accompanying materials
|
|
||||||
are made available under the terms of the Eclipse Public License v1.0
|
|
||||||
and Eclipse Distribution License v1.0 which accompany this distribution.
|
|
||||||
|
|
||||||
The Eclipse Public License is available at
|
|
||||||
http://www.eclipse.org/legal/epl-v10.html
|
|
||||||
and the Eclipse Distribution License is available at
|
|
||||||
http://www.eclipse.org/org/documents/edl-v10.php.
|
|
||||||
|
|
||||||
Contributors:
|
|
||||||
Paolo Patierno - initial API and implementation and/or initial documentation
|
|
||||||
*/
|
|
||||||
|
|
||||||
#if SSL
|
|
||||||
#if (MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
|
|
||||||
using Microsoft.SPOT.Net.Security;
|
|
||||||
#else
|
|
||||||
using System.Net.Security;
|
|
||||||
using System.Security.Authentication;
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
using System.Net.Sockets;
|
|
||||||
using System.Net;
|
|
||||||
using System.Security.Cryptography.X509Certificates;
|
|
||||||
using System;
|
|
||||||
using System.Security.Authentication;
|
|
||||||
using System.Net.Security;
|
|
||||||
|
|
||||||
namespace uPLibrary.Networking.M2Mqtt
|
All rights reserved. This program and the accompanying materials
|
||||||
{
|
are made available under the terms of the Eclipse Public License v1.0
|
||||||
/// <summary>
|
and Eclipse Distribution License v1.0 which accompany this distribution.
|
||||||
/// Channel to communicate over the network
|
|
||||||
/// </summary>
|
The Eclipse Public License is available at
|
||||||
public class MqttNetworkChannel : IMqttNetworkChannel
|
http://www.eclipse.org/legal/epl-v10.html
|
||||||
{
|
and the Eclipse Distribution License is available at
|
||||||
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
http://www.eclipse.org/org/documents/edl-v10.php.
|
||||||
private readonly RemoteCertificateValidationCallback userCertificateValidationCallback;
|
|
||||||
private readonly LocalCertificateSelectionCallback userCertificateSelectionCallback;
|
Contributors:
|
||||||
#endif
|
Paolo Patierno - initial API and implementation and/or initial documentation
|
||||||
// remote host information
|
*/
|
||||||
private string remoteHostName;
|
|
||||||
private IPAddress remoteIpAddress;
|
#if SSL
|
||||||
private int remotePort;
|
#if (MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
|
||||||
|
using Microsoft.SPOT.Net.Security;
|
||||||
// socket for communication
|
#else
|
||||||
private Socket socket;
|
using System.Net.Security;
|
||||||
// using SSL
|
using System.Security.Authentication;
|
||||||
private bool secure;
|
#endif
|
||||||
|
#endif
|
||||||
// CA certificate (on client)
|
using System.Net.Sockets;
|
||||||
private X509Certificate caCert;
|
using System.Net;
|
||||||
// Server certificate (on broker)
|
using System.Security.Cryptography.X509Certificates;
|
||||||
private X509Certificate serverCert;
|
using System;
|
||||||
// client certificate (on client)
|
//using System.Security.Authentication;
|
||||||
private X509Certificate clientCert;
|
//using System.Net.Security;
|
||||||
|
|
||||||
// SSL/TLS protocol version
|
namespace uPLibrary.Networking.M2Mqtt
|
||||||
private MqttSslProtocols sslProtocol;
|
{
|
||||||
|
/// <summary>
|
||||||
/// <summary>
|
/// Channel to communicate over the network
|
||||||
/// Remote host name
|
/// </summary>
|
||||||
/// </summary>
|
public class MqttNetworkChannel : IMqttNetworkChannel
|
||||||
public string RemoteHostName { get { return this.remoteHostName; } }
|
{
|
||||||
|
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
||||||
/// <summary>
|
private readonly RemoteCertificateValidationCallback userCertificateValidationCallback;
|
||||||
/// Remote IP address
|
private readonly LocalCertificateSelectionCallback userCertificateSelectionCallback;
|
||||||
/// </summary>
|
#endif
|
||||||
public IPAddress RemoteIpAddress { get { return this.remoteIpAddress; } }
|
// remote host information
|
||||||
|
private string remoteHostName;
|
||||||
/// <summary>
|
private IPAddress remoteIpAddress;
|
||||||
/// Remote port
|
private int remotePort;
|
||||||
/// </summary>
|
|
||||||
public int RemotePort { get { return this.remotePort; } }
|
// socket for communication
|
||||||
|
private Socket socket;
|
||||||
#if SSL
|
// using SSL
|
||||||
// SSL stream
|
private bool secure;
|
||||||
private SslStream sslStream;
|
|
||||||
#if (!MF_FRAMEWORK_VERSION_V4_2 && !MF_FRAMEWORK_VERSION_V4_3)
|
// CA certificate (on client)
|
||||||
private NetworkStream netStream;
|
private X509Certificate caCert;
|
||||||
#endif
|
// Server certificate (on broker)
|
||||||
#endif
|
private X509Certificate serverCert;
|
||||||
|
// client certificate (on client)
|
||||||
/// <summary>
|
private X509Certificate clientCert;
|
||||||
/// Data available on the channel
|
|
||||||
/// </summary>
|
// SSL/TLS protocol version
|
||||||
public bool DataAvailable
|
private MqttSslProtocols sslProtocol;
|
||||||
{
|
|
||||||
get
|
/// <summary>
|
||||||
{
|
/// Remote host name
|
||||||
#if SSL
|
/// </summary>
|
||||||
#if (MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
|
public string RemoteHostName { get { return this.remoteHostName; } }
|
||||||
if (secure)
|
|
||||||
return this.sslStream.DataAvailable;
|
/// <summary>
|
||||||
else
|
/// Remote IP address
|
||||||
return (this.socket.Available > 0);
|
/// </summary>
|
||||||
#else
|
public IPAddress RemoteIpAddress { get { return this.remoteIpAddress; } }
|
||||||
if (secure)
|
|
||||||
return this.netStream.DataAvailable;
|
/// <summary>
|
||||||
else
|
/// Remote port
|
||||||
return (this.socket.Available > 0);
|
/// </summary>
|
||||||
#endif
|
public int RemotePort { get { return this.remotePort; } }
|
||||||
#else
|
|
||||||
return (this.socket.Available > 0);
|
#if SSL
|
||||||
#endif
|
// SSL stream
|
||||||
}
|
private SslStream sslStream;
|
||||||
}
|
#if (!MF_FRAMEWORK_VERSION_V4_2 && !MF_FRAMEWORK_VERSION_V4_3)
|
||||||
|
private NetworkStream netStream;
|
||||||
/// <summary>
|
#endif
|
||||||
/// Constructor
|
#endif
|
||||||
/// </summary>
|
|
||||||
/// <param name="socket">Socket opened with the client</param>
|
/// <summary>
|
||||||
public MqttNetworkChannel(Socket socket)
|
/// Data available on the channel
|
||||||
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
/// </summary>
|
||||||
: this(socket, false, null, MqttSslProtocols.None, null, null)
|
public bool DataAvailable
|
||||||
#else
|
{
|
||||||
: this(socket, false, null, MqttSslProtocols.None)
|
get
|
||||||
#endif
|
{
|
||||||
{
|
#if SSL
|
||||||
|
#if (MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
|
||||||
}
|
if (secure)
|
||||||
|
return this.sslStream.DataAvailable;
|
||||||
/// <summary>
|
else
|
||||||
/// Constructor
|
return (this.socket.Available > 0);
|
||||||
/// </summary>
|
#else
|
||||||
/// <param name="socket">Socket opened with the client</param>
|
if (secure)
|
||||||
/// <param name="secure">Secure connection (SSL/TLS)</param>
|
return this.netStream.DataAvailable;
|
||||||
/// <param name="serverCert">Server X509 certificate for secure connection</param>
|
else
|
||||||
/// <param name="sslProtocol">SSL/TLS protocol version</param>
|
return (this.socket.Available > 0);
|
||||||
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
#endif
|
||||||
/// <param name="userCertificateSelectionCallback">A RemoteCertificateValidationCallback delegate responsible for validating the certificate supplied by the remote party</param>
|
#else
|
||||||
/// <param name="userCertificateValidationCallback">A LocalCertificateSelectionCallback delegate responsible for selecting the certificate used for authentication</param>
|
return (this.socket.Available > 0);
|
||||||
public MqttNetworkChannel(Socket socket, bool secure, X509Certificate serverCert, MqttSslProtocols sslProtocol,
|
#endif
|
||||||
RemoteCertificateValidationCallback userCertificateValidationCallback,
|
}
|
||||||
LocalCertificateSelectionCallback userCertificateSelectionCallback)
|
}
|
||||||
#else
|
|
||||||
public MqttNetworkChannel(Socket socket, bool secure, X509Certificate serverCert, MqttSslProtocols sslProtocol)
|
/// <summary>
|
||||||
#endif
|
/// Constructor
|
||||||
{
|
/// </summary>
|
||||||
this.socket = socket;
|
/// <param name="socket">Socket opened with the client</param>
|
||||||
this.secure = secure;
|
public MqttNetworkChannel(Socket socket)
|
||||||
this.serverCert = serverCert;
|
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
||||||
this.sslProtocol = sslProtocol;
|
: this(socket, false, null, MqttSslProtocols.None, null, null)
|
||||||
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
#else
|
||||||
this.userCertificateValidationCallback = userCertificateValidationCallback;
|
: this(socket, false, null, MqttSslProtocols.None)
|
||||||
this.userCertificateSelectionCallback = userCertificateSelectionCallback;
|
#endif
|
||||||
#endif
|
{
|
||||||
}
|
|
||||||
|
}
|
||||||
/// <summary>
|
|
||||||
/// Constructor
|
/// <summary>
|
||||||
/// </summary>
|
/// Constructor
|
||||||
/// <param name="remoteHostName">Remote Host name</param>
|
/// </summary>
|
||||||
/// <param name="remotePort">Remote port</param>
|
/// <param name="socket">Socket opened with the client</param>
|
||||||
public MqttNetworkChannel(string remoteHostName, int remotePort)
|
/// <param name="secure">Secure connection (SSL/TLS)</param>
|
||||||
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
/// <param name="serverCert">Server X509 certificate for secure connection</param>
|
||||||
: this(remoteHostName, remotePort, false, null, null, MqttSslProtocols.None, null, null)
|
/// <param name="sslProtocol">SSL/TLS protocol version</param>
|
||||||
#else
|
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
||||||
: this(remoteHostName, remotePort, false, null, null, MqttSslProtocols.None)
|
/// <param name="userCertificateSelectionCallback">A RemoteCertificateValidationCallback delegate responsible for validating the certificate supplied by the remote party</param>
|
||||||
#endif
|
/// <param name="userCertificateValidationCallback">A LocalCertificateSelectionCallback delegate responsible for selecting the certificate used for authentication</param>
|
||||||
{
|
public MqttNetworkChannel(Socket socket, bool secure, X509Certificate serverCert, MqttSslProtocols sslProtocol,
|
||||||
}
|
RemoteCertificateValidationCallback userCertificateValidationCallback,
|
||||||
|
LocalCertificateSelectionCallback userCertificateSelectionCallback)
|
||||||
/// <summary>
|
#else
|
||||||
/// Constructor
|
public MqttNetworkChannel(Socket socket, bool secure, X509Certificate serverCert, MqttSslProtocols sslProtocol)
|
||||||
/// </summary>
|
#endif
|
||||||
/// <param name="remoteHostName">Remote Host name</param>
|
{
|
||||||
/// <param name="remotePort">Remote port</param>
|
this.socket = socket;
|
||||||
/// <param name="secure">Using SSL</param>
|
this.secure = secure;
|
||||||
/// <param name="caCert">CA certificate</param>
|
this.serverCert = serverCert;
|
||||||
/// <param name="clientCert">Client certificate</param>
|
this.sslProtocol = sslProtocol;
|
||||||
/// <param name="sslProtocol">SSL/TLS protocol version</param>
|
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
||||||
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
this.userCertificateValidationCallback = userCertificateValidationCallback;
|
||||||
/// <param name="userCertificateSelectionCallback">A RemoteCertificateValidationCallback delegate responsible for validating the certificate supplied by the remote party</param>
|
this.userCertificateSelectionCallback = userCertificateSelectionCallback;
|
||||||
/// <param name="userCertificateValidationCallback">A LocalCertificateSelectionCallback delegate responsible for selecting the certificate used for authentication</param>
|
#endif
|
||||||
public MqttNetworkChannel(string remoteHostName, int remotePort, bool secure, X509Certificate caCert, X509Certificate clientCert, MqttSslProtocols sslProtocol,
|
}
|
||||||
RemoteCertificateValidationCallback userCertificateValidationCallback,
|
|
||||||
LocalCertificateSelectionCallback userCertificateSelectionCallback)
|
/// <summary>
|
||||||
#else
|
/// Constructor
|
||||||
public MqttNetworkChannel(string remoteHostName, int remotePort, bool secure, X509Certificate caCert, X509Certificate clientCert, MqttSslProtocols sslProtocol)
|
/// </summary>
|
||||||
#endif
|
/// <param name="remoteHostName">Remote Host name</param>
|
||||||
{
|
/// <param name="remotePort">Remote port</param>
|
||||||
IPAddress remoteIpAddress = null;
|
public MqttNetworkChannel(string remoteHostName, int remotePort)
|
||||||
try
|
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
||||||
{
|
: this(remoteHostName, remotePort, false, null, null, MqttSslProtocols.None, null, null)
|
||||||
// check if remoteHostName is a valid IP address and get it
|
#else
|
||||||
remoteIpAddress = IPAddress.Parse(remoteHostName);
|
: this(remoteHostName, remotePort, false, null, null, MqttSslProtocols.None)
|
||||||
}
|
#endif
|
||||||
catch
|
{
|
||||||
{
|
}
|
||||||
}
|
|
||||||
|
/// <summary>
|
||||||
// in this case the parameter remoteHostName isn't a valid IP address
|
/// Constructor
|
||||||
if (remoteIpAddress == null)
|
/// </summary>
|
||||||
{
|
/// <param name="remoteHostName">Remote Host name</param>
|
||||||
IPHostEntry hostEntry = Dns.GetHostEntry(remoteHostName);
|
/// <param name="remotePort">Remote port</param>
|
||||||
if ((hostEntry != null) && (hostEntry.AddressList.Length > 0))
|
/// <param name="secure">Using SSL</param>
|
||||||
{
|
/// <param name="caCert">CA certificate</param>
|
||||||
// check for the first address not null
|
/// <param name="clientCert">Client certificate</param>
|
||||||
// it seems that with .Net Micro Framework, the IPV6 addresses aren't supported and return "null"
|
/// <param name="sslProtocol">SSL/TLS protocol version</param>
|
||||||
int i = 0;
|
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
||||||
while (hostEntry.AddressList[i] == null) i++;
|
/// <param name="userCertificateSelectionCallback">A RemoteCertificateValidationCallback delegate responsible for validating the certificate supplied by the remote party</param>
|
||||||
remoteIpAddress = hostEntry.AddressList[i];
|
/// <param name="userCertificateValidationCallback">A LocalCertificateSelectionCallback delegate responsible for selecting the certificate used for authentication</param>
|
||||||
}
|
public MqttNetworkChannel(string remoteHostName, int remotePort, bool secure, X509Certificate caCert, X509Certificate clientCert, MqttSslProtocols sslProtocol,
|
||||||
else
|
RemoteCertificateValidationCallback userCertificateValidationCallback,
|
||||||
{
|
LocalCertificateSelectionCallback userCertificateSelectionCallback)
|
||||||
throw new Exception("No address found for the remote host name");
|
#else
|
||||||
}
|
public MqttNetworkChannel(string remoteHostName, int remotePort, bool secure, X509Certificate caCert, X509Certificate clientCert, MqttSslProtocols sslProtocol)
|
||||||
}
|
#endif
|
||||||
|
{
|
||||||
this.remoteHostName = remoteHostName;
|
IPAddress remoteIpAddress = null;
|
||||||
this.remoteIpAddress = remoteIpAddress;
|
try
|
||||||
this.remotePort = remotePort;
|
{
|
||||||
this.secure = secure;
|
// check if remoteHostName is a valid IP address and get it
|
||||||
this.caCert = caCert;
|
remoteIpAddress = IPAddress.Parse(remoteHostName);
|
||||||
this.clientCert = clientCert;
|
}
|
||||||
this.sslProtocol = sslProtocol;
|
catch
|
||||||
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
{
|
||||||
this.userCertificateValidationCallback = userCertificateValidationCallback;
|
}
|
||||||
this.userCertificateSelectionCallback = userCertificateSelectionCallback;
|
|
||||||
#endif
|
// in this case the parameter remoteHostName isn't a valid IP address
|
||||||
}
|
if (remoteIpAddress == null)
|
||||||
|
{
|
||||||
/// <summary>
|
IPHostEntry hostEntry = Dns.GetHostEntry(remoteHostName);
|
||||||
/// Connect to remote server
|
if ((hostEntry != null) && (hostEntry.AddressList.Length > 0))
|
||||||
/// </summary>
|
{
|
||||||
public void Connect()
|
// check for the first address not null
|
||||||
{
|
// it seems that with .Net Micro Framework, the IPV6 addresses aren't supported and return "null"
|
||||||
this.socket = new Socket(IPAddressUtility.GetAddressFamily(this.remoteIpAddress), SocketType.Stream, ProtocolType.Tcp);
|
int i = 0;
|
||||||
// try connection to the broker
|
while (hostEntry.AddressList[i] == null) i++;
|
||||||
this.socket.Connect(new IPEndPoint(this.remoteIpAddress, this.remotePort));
|
remoteIpAddress = hostEntry.AddressList[i];
|
||||||
|
}
|
||||||
#if SSL
|
else
|
||||||
// secure channel requested
|
{
|
||||||
if (secure)
|
throw new Exception("No address found for the remote host name");
|
||||||
{
|
}
|
||||||
// create SSL stream
|
}
|
||||||
#if (MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
|
|
||||||
this.sslStream = new SslStream(this.socket);
|
this.remoteHostName = remoteHostName;
|
||||||
#else
|
this.remoteIpAddress = remoteIpAddress;
|
||||||
this.netStream = new NetworkStream(this.socket);
|
this.remotePort = remotePort;
|
||||||
this.sslStream = new SslStream(this.netStream, false, this.userCertificateValidationCallback, this.userCertificateSelectionCallback);
|
this.secure = secure;
|
||||||
#endif
|
this.caCert = caCert;
|
||||||
|
this.clientCert = clientCert;
|
||||||
// server authentication (SSL/TLS handshake)
|
this.sslProtocol = sslProtocol;
|
||||||
#if (MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
|
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 || COMPACT_FRAMEWORK)
|
||||||
this.sslStream.AuthenticateAsClient(this.remoteHostName,
|
this.userCertificateValidationCallback = userCertificateValidationCallback;
|
||||||
this.clientCert,
|
this.userCertificateSelectionCallback = userCertificateSelectionCallback;
|
||||||
new X509Certificate[] { this.caCert },
|
#endif
|
||||||
SslVerification.CertificateRequired,
|
}
|
||||||
MqttSslUtility.ToSslPlatformEnum(this.sslProtocol));
|
|
||||||
#else
|
/// <summary>
|
||||||
X509CertificateCollection clientCertificates = null;
|
/// Connect to remote server
|
||||||
// check if there is a client certificate to add to the collection, otherwise it's null (as empty)
|
/// </summary>
|
||||||
if (this.clientCert != null)
|
public void Connect()
|
||||||
clientCertificates = new X509CertificateCollection(new X509Certificate[] { this.clientCert });
|
{
|
||||||
|
this.socket = new Socket(IPAddressUtility.GetAddressFamily(this.remoteIpAddress), SocketType.Stream, ProtocolType.Tcp);
|
||||||
this.sslStream.AuthenticateAsClient(this.remoteHostName,
|
// try connection to the broker
|
||||||
clientCertificates,
|
this.socket.Connect(new IPEndPoint(this.remoteIpAddress, this.remotePort));
|
||||||
MqttSslUtility.ToSslPlatformEnum(this.sslProtocol),
|
|
||||||
false);
|
#if SSL
|
||||||
|
// secure channel requested
|
||||||
#endif
|
if (secure)
|
||||||
}
|
{
|
||||||
#endif
|
// create SSL stream
|
||||||
}
|
#if (MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
|
||||||
|
this.sslStream = new SslStream(this.socket);
|
||||||
/// <summary>
|
#else
|
||||||
/// Send data on the network channel
|
this.netStream = new NetworkStream(this.socket);
|
||||||
/// </summary>
|
this.sslStream = new SslStream(this.netStream, false, this.userCertificateValidationCallback, this.userCertificateSelectionCallback);
|
||||||
/// <param name="buffer">Data buffer to send</param>
|
#endif
|
||||||
/// <returns>Number of byte sent</returns>
|
|
||||||
public int Send(byte[] buffer)
|
// server authentication (SSL/TLS handshake)
|
||||||
{
|
#if (MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
|
||||||
#if SSL
|
this.sslStream.AuthenticateAsClient(this.remoteHostName,
|
||||||
if (this.secure)
|
this.clientCert,
|
||||||
{
|
new X509Certificate[] { this.caCert },
|
||||||
this.sslStream.Write(buffer, 0, buffer.Length);
|
SslVerification.CertificateRequired,
|
||||||
this.sslStream.Flush();
|
MqttSslUtility.ToSslPlatformEnum(this.sslProtocol));
|
||||||
return buffer.Length;
|
#else
|
||||||
}
|
X509CertificateCollection clientCertificates = null;
|
||||||
else
|
// check if there is a client certificate to add to the collection, otherwise it's null (as empty)
|
||||||
return this.socket.Send(buffer, 0, buffer.Length, SocketFlags.None);
|
if (this.clientCert != null)
|
||||||
#else
|
clientCertificates = new X509CertificateCollection(new X509Certificate[] { this.clientCert });
|
||||||
return this.socket.Send(buffer, 0, buffer.Length, SocketFlags.None);
|
|
||||||
#endif
|
this.sslStream.AuthenticateAsClient(this.remoteHostName,
|
||||||
}
|
clientCertificates,
|
||||||
|
MqttSslUtility.ToSslPlatformEnum(this.sslProtocol),
|
||||||
/// <summary>
|
false);
|
||||||
/// Receive data from the network
|
|
||||||
/// </summary>
|
#endif
|
||||||
/// <param name="buffer">Data buffer for receiving data</param>
|
}
|
||||||
/// <returns>Number of bytes received</returns>
|
#endif
|
||||||
public int Receive(byte[] buffer)
|
}
|
||||||
{
|
|
||||||
#if SSL
|
/// <summary>
|
||||||
if (this.secure)
|
/// Send data on the network channel
|
||||||
{
|
/// </summary>
|
||||||
// read all data needed (until fill buffer)
|
/// <param name="buffer">Data buffer to send</param>
|
||||||
int idx = 0, read = 0;
|
/// <returns>Number of byte sent</returns>
|
||||||
while (idx < buffer.Length)
|
public int Send(byte[] buffer)
|
||||||
{
|
{
|
||||||
// fixed scenario with socket closed gracefully by peer/broker and
|
#if SSL
|
||||||
// Read return 0. Avoid infinite loop.
|
if (this.secure)
|
||||||
read = this.sslStream.Read(buffer, idx, buffer.Length - idx);
|
{
|
||||||
if (read == 0)
|
this.sslStream.Write(buffer, 0, buffer.Length);
|
||||||
return 0;
|
this.sslStream.Flush();
|
||||||
idx += read;
|
return buffer.Length;
|
||||||
}
|
}
|
||||||
return buffer.Length;
|
else
|
||||||
}
|
return this.socket.Send(buffer, 0, buffer.Length, SocketFlags.None);
|
||||||
else
|
#else
|
||||||
{
|
return this.socket.Send(buffer, 0, buffer.Length, SocketFlags.None);
|
||||||
// read all data needed (until fill buffer)
|
#endif
|
||||||
int idx = 0, read = 0;
|
}
|
||||||
while (idx < buffer.Length)
|
|
||||||
{
|
/// <summary>
|
||||||
// fixed scenario with socket closed gracefully by peer/broker and
|
/// Receive data from the network
|
||||||
// Read return 0. Avoid infinite loop.
|
/// </summary>
|
||||||
read = this.socket.Receive(buffer, idx, buffer.Length - idx, SocketFlags.None);
|
/// <param name="buffer">Data buffer for receiving data</param>
|
||||||
if (read == 0)
|
/// <returns>Number of bytes received</returns>
|
||||||
return 0;
|
public int Receive(byte[] buffer)
|
||||||
idx += read;
|
{
|
||||||
}
|
#if SSL
|
||||||
return buffer.Length;
|
if (this.secure)
|
||||||
}
|
{
|
||||||
#else
|
// read all data needed (until fill buffer)
|
||||||
// read all data needed (until fill buffer)
|
int idx = 0, read = 0;
|
||||||
int idx = 0, read = 0;
|
while (idx < buffer.Length)
|
||||||
while (idx < buffer.Length)
|
{
|
||||||
{
|
// fixed scenario with socket closed gracefully by peer/broker and
|
||||||
// fixed scenario with socket closed gracefully by peer/broker and
|
// Read return 0. Avoid infinite loop.
|
||||||
// Read return 0. Avoid infinite loop.
|
read = this.sslStream.Read(buffer, idx, buffer.Length - idx);
|
||||||
read = this.socket.Receive(buffer, idx, buffer.Length - idx, SocketFlags.None);
|
if (read == 0)
|
||||||
if (read == 0)
|
return 0;
|
||||||
return 0;
|
idx += read;
|
||||||
idx += read;
|
}
|
||||||
}
|
return buffer.Length;
|
||||||
return buffer.Length;
|
}
|
||||||
#endif
|
else
|
||||||
}
|
{
|
||||||
|
// read all data needed (until fill buffer)
|
||||||
/// <summary>
|
int idx = 0, read = 0;
|
||||||
/// Receive data from the network channel with a specified timeout
|
while (idx < buffer.Length)
|
||||||
/// </summary>
|
{
|
||||||
/// <param name="buffer">Data buffer for receiving data</param>
|
// fixed scenario with socket closed gracefully by peer/broker and
|
||||||
/// <param name="timeout">Timeout on receiving (in milliseconds)</param>
|
// Read return 0. Avoid infinite loop.
|
||||||
/// <returns>Number of bytes received</returns>
|
read = this.socket.Receive(buffer, idx, buffer.Length - idx, SocketFlags.None);
|
||||||
public int Receive(byte[] buffer, int timeout)
|
if (read == 0)
|
||||||
{
|
return 0;
|
||||||
// check data availability (timeout is in microseconds)
|
idx += read;
|
||||||
if (this.socket.Poll(timeout * 1000, SelectMode.SelectRead))
|
}
|
||||||
{
|
return buffer.Length;
|
||||||
return this.Receive(buffer);
|
}
|
||||||
}
|
#else
|
||||||
else
|
// read all data needed (until fill buffer)
|
||||||
{
|
int idx = 0, read = 0;
|
||||||
return 0;
|
while (idx < buffer.Length)
|
||||||
}
|
{
|
||||||
}
|
// fixed scenario with socket closed gracefully by peer/broker and
|
||||||
|
// Read return 0. Avoid infinite loop.
|
||||||
/// <summary>
|
read = this.socket.Receive(buffer, idx, buffer.Length - idx, SocketFlags.None);
|
||||||
/// Close the network channel
|
if (read == 0)
|
||||||
/// </summary>
|
return 0;
|
||||||
public void Close()
|
idx += read;
|
||||||
{
|
}
|
||||||
#if SSL
|
return buffer.Length;
|
||||||
if (this.secure)
|
#endif
|
||||||
{
|
}
|
||||||
#if (!MF_FRAMEWORK_VERSION_V4_2 && !MF_FRAMEWORK_VERSION_V4_3)
|
|
||||||
this.netStream.Close();
|
/// <summary>
|
||||||
#endif
|
/// Receive data from the network channel with a specified timeout
|
||||||
this.sslStream.Close();
|
/// </summary>
|
||||||
}
|
/// <param name="buffer">Data buffer for receiving data</param>
|
||||||
this.socket.Close();
|
/// <param name="timeout">Timeout on receiving (in milliseconds)</param>
|
||||||
#else
|
/// <returns>Number of bytes received</returns>
|
||||||
this.socket.Close();
|
public int Receive(byte[] buffer, int timeout)
|
||||||
#endif
|
{
|
||||||
}
|
// check data availability (timeout is in microseconds)
|
||||||
|
if (this.socket.Poll(timeout * 1000, SelectMode.SelectRead))
|
||||||
/// <summary>
|
{
|
||||||
/// Accept connection from a remote client
|
return this.Receive(buffer);
|
||||||
/// </summary>
|
}
|
||||||
public void Accept()
|
else
|
||||||
{
|
{
|
||||||
#if SSL
|
return 0;
|
||||||
// secure channel requested
|
}
|
||||||
if (secure)
|
}
|
||||||
{
|
|
||||||
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
|
/// <summary>
|
||||||
|
/// Close the network channel
|
||||||
this.netStream = new NetworkStream(this.socket);
|
/// </summary>
|
||||||
this.sslStream = new SslStream(this.netStream, false, this.userCertificateValidationCallback, this.userCertificateSelectionCallback);
|
public void Close()
|
||||||
|
{
|
||||||
this.sslStream.AuthenticateAsServer(this.serverCert, false, MqttSslUtility.ToSslPlatformEnum(this.sslProtocol), false);
|
#if SSL
|
||||||
#endif
|
if (this.secure)
|
||||||
}
|
{
|
||||||
|
#if (!MF_FRAMEWORK_VERSION_V4_2 && !MF_FRAMEWORK_VERSION_V4_3)
|
||||||
return;
|
this.netStream.Close();
|
||||||
#else
|
#endif
|
||||||
return;
|
this.sslStream.Close();
|
||||||
#endif
|
}
|
||||||
}
|
this.socket.Close();
|
||||||
}
|
#else
|
||||||
|
this.socket.Close();
|
||||||
/// <summary>
|
#endif
|
||||||
/// IPAddress Utility class
|
}
|
||||||
/// </summary>
|
|
||||||
public static class IPAddressUtility
|
/// <summary>
|
||||||
{
|
/// Accept connection from a remote client
|
||||||
/// <summary>
|
/// </summary>
|
||||||
/// Return AddressFamily for the IP address
|
public void Accept()
|
||||||
/// </summary>
|
{
|
||||||
/// <param name="ipAddress">IP address to check</param>
|
#if SSL
|
||||||
/// <returns>Address family</returns>
|
// secure channel requested
|
||||||
public static AddressFamily GetAddressFamily(IPAddress ipAddress)
|
if (secure)
|
||||||
{
|
{
|
||||||
#if (!MF_FRAMEWORK_VERSION_V4_2 && !MF_FRAMEWORK_VERSION_V4_3)
|
#if !(MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
|
||||||
return ipAddress.AddressFamily;
|
|
||||||
#else
|
this.netStream = new NetworkStream(this.socket);
|
||||||
return (ipAddress.ToString().IndexOf(':') != -1) ?
|
this.sslStream = new SslStream(this.netStream, false, this.userCertificateValidationCallback, this.userCertificateSelectionCallback);
|
||||||
AddressFamily.InterNetworkV6 : AddressFamily.InterNetwork;
|
|
||||||
#endif
|
this.sslStream.AuthenticateAsServer(this.serverCert, false, MqttSslUtility.ToSslPlatformEnum(this.sslProtocol), false);
|
||||||
}
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
return;
|
||||||
/// MQTT SSL utility class
|
#else
|
||||||
/// </summary>
|
return;
|
||||||
public static class MqttSslUtility
|
#endif
|
||||||
{
|
}
|
||||||
#if (!MF_FRAMEWORK_VERSION_V4_2 && !MF_FRAMEWORK_VERSION_V4_3 && !COMPACT_FRAMEWORK)
|
}
|
||||||
public static SslProtocols ToSslPlatformEnum(MqttSslProtocols mqttSslProtocol)
|
|
||||||
{
|
/// <summary>
|
||||||
switch (mqttSslProtocol)
|
/// IPAddress Utility class
|
||||||
{
|
/// </summary>
|
||||||
case MqttSslProtocols.None:
|
public static class IPAddressUtility
|
||||||
return SslProtocols.None;
|
{
|
||||||
case MqttSslProtocols.SSLv3:
|
/// <summary>
|
||||||
return SslProtocols.Ssl3;
|
/// Return AddressFamily for the IP address
|
||||||
case MqttSslProtocols.TLSv1_0:
|
/// </summary>
|
||||||
return SslProtocols.Tls;
|
/// <param name="ipAddress">IP address to check</param>
|
||||||
/*case MqttSslProtocols.TLSv1_1:
|
/// <returns>Address family</returns>
|
||||||
return SslProtocols.Tls11;
|
public static AddressFamily GetAddressFamily(IPAddress ipAddress)
|
||||||
case MqttSslProtocols.TLSv1_2:
|
{
|
||||||
return SslProtocols.Tls12;*/
|
#if (!MF_FRAMEWORK_VERSION_V4_2 && !MF_FRAMEWORK_VERSION_V4_3)
|
||||||
default:
|
return ipAddress.AddressFamily;
|
||||||
throw new ArgumentException("SSL/TLS protocol version not supported");
|
#else
|
||||||
}
|
return (ipAddress.ToString().IndexOf(':') != -1) ?
|
||||||
}
|
AddressFamily.InterNetworkV6 : AddressFamily.InterNetwork;
|
||||||
#elif (MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
|
#endif
|
||||||
public static SslProtocols ToSslPlatformEnum(MqttSslProtocols mqttSslProtocol)
|
}
|
||||||
{
|
}
|
||||||
switch (mqttSslProtocol)
|
|
||||||
{
|
/// <summary>
|
||||||
case MqttSslProtocols.None:
|
/// MQTT SSL utility class
|
||||||
return SslProtocols.None;
|
/// </summary>
|
||||||
case MqttSslProtocols.SSLv3:
|
public static class MqttSslUtility
|
||||||
return SslProtocols.SSLv3;
|
{
|
||||||
case MqttSslProtocols.TLSv1_0:
|
#if (!MF_FRAMEWORK_VERSION_V4_2 && !MF_FRAMEWORK_VERSION_V4_3 && !COMPACT_FRAMEWORK)
|
||||||
return SslProtocols.TLSv1;
|
public static SslProtocols ToSslPlatformEnum(MqttSslProtocols mqttSslProtocol)
|
||||||
case MqttSslProtocols.TLSv1_1:
|
{
|
||||||
case MqttSslProtocols.TLSv1_2:
|
switch (mqttSslProtocol)
|
||||||
default:
|
{
|
||||||
throw new ArgumentException("SSL/TLS protocol version not supported");
|
case MqttSslProtocols.None:
|
||||||
}
|
return SslProtocols.None;
|
||||||
}
|
case MqttSslProtocols.SSLv3:
|
||||||
#endif
|
return SslProtocols.Ssl3;
|
||||||
}
|
case MqttSslProtocols.TLSv1_0:
|
||||||
}
|
return SslProtocols.Tls;
|
||||||
|
/*case MqttSslProtocols.TLSv1_1:
|
||||||
|
return SslProtocols.Tls11;
|
||||||
|
case MqttSslProtocols.TLSv1_2:
|
||||||
|
return SslProtocols.Tls12;*/
|
||||||
|
default:
|
||||||
|
throw new ArgumentException("SSL/TLS protocol version not supported");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#elif (MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
|
||||||
|
public static SslProtocols ToSslPlatformEnum(MqttSslProtocols mqttSslProtocol)
|
||||||
|
{
|
||||||
|
switch (mqttSslProtocol)
|
||||||
|
{
|
||||||
|
case MqttSslProtocols.None:
|
||||||
|
return SslProtocols.None;
|
||||||
|
case MqttSslProtocols.SSLv3:
|
||||||
|
return SslProtocols.SSLv3;
|
||||||
|
case MqttSslProtocols.TLSv1_0:
|
||||||
|
return SslProtocols.TLSv1;
|
||||||
|
case MqttSslProtocols.TLSv1_1:
|
||||||
|
case MqttSslProtocols.TLSv1_2:
|
||||||
|
default:
|
||||||
|
throw new ArgumentException("SSL/TLS protocol version not supported");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Binary file not shown.
Loading…
Reference in New Issue
Block a user