Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

CF & OpenSSL #81

Open
wants to merge 5 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
113 changes: 113 additions & 0 deletions M2Mqtt/M2Mqtt.NetCF2.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,113 @@
<Project DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003" ToolsVersion="3.5">
<PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProductVersion>9.0.21022</ProductVersion>
<SchemaVersion>2.0</SchemaVersion>
<ProjectGuid>{8031328B-B554-4059-9CC4-0F712D054D92}</ProjectGuid>
<OutputType>Library</OutputType>
<AppDesignerFolder>Properties</AppDesignerFolder>
<RootNamespace>M2Mqtt.NetCF2</RootNamespace>
<AssemblyName>M2Mqtt.NetCF2</AssemblyName>
<ProjectTypeGuids>{4D628B5B-2FBC-4AA6-8C16-197242AEB884};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}</ProjectTypeGuids>
<PlatformFamilyName>WindowsCE</PlatformFamilyName>
<PlatformID>E2BECB1F-8C8C-41ba-B736-9BE7D946A398</PlatformID>
<OSVersion>5.0</OSVersion>
<DeployDirSuffix>M2Mqtt.NetCF2</DeployDirSuffix>
<TargetFrameworkVersion>v2.0</TargetFrameworkVersion>
<NativePlatformName>Windows CE</NativePlatformName>
<FormFactorID>
</FormFactorID>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<DebugSymbols>true</DebugSymbols>
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>bin\Debug\</OutputPath>
<DefineConstants>TRACE;DEBUG;WindowsCE,,COMPACT_FRAMEWORK,SSL</DefineConstants>
<NoStdLib>true</NoStdLib>
<NoConfig>true</NoConfig>
<ErrorReport>prompt</ErrorReport>
<FileAlignment>512</FileAlignment>
<WarningLevel>4</WarningLevel>
<GenerateSerializationAssemblies>Off</GenerateSerializationAssemblies>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<DebugType>pdbonly</DebugType>
<Optimize>true</Optimize>
<OutputPath>bin\Release\</OutputPath>
<DefineConstants>TRACE;WindowsCE,,COMPACT_FRAMEWORK,SSL</DefineConstants>
<NoStdLib>true</NoStdLib>
<NoConfig>true</NoConfig>
<ErrorReport>prompt</ErrorReport>
<FileAlignment>512</FileAlignment>
<WarningLevel>4</WarningLevel>
<GenerateSerializationAssemblies>Off</GenerateSerializationAssemblies>
</PropertyGroup>
<ItemGroup>
<Reference Include="mscorlib" />
<Reference Include="System" />
<Reference Include="System.Data" />
<Reference Include="System.Xml" />
</ItemGroup>
<ItemGroup>
<Compile Include="Exceptions\MqttClientException.cs" />
<Compile Include="Exceptions\MqttCommunicationException.cs" />
<Compile Include="Exceptions\MqttConnectionException.cs" />
<Compile Include="Exceptions\MqttTimeoutException.cs" />
<Compile Include="IMqttNetworkChannel.cs" />
<Compile Include="Internal\InternalEvent.cs" />
<Compile Include="Internal\MsgInternalEvent.cs" />
<Compile Include="Internal\MsgPublishedInternalEvent.cs" />
<Compile Include="Messages\MqttMsgBase.cs" />
<Compile Include="Messages\MqttMsgConnack.cs" />
<Compile Include="Messages\MqttMsgConnect.cs" />
<Compile Include="Messages\MqttMsgConnectEventArgs.cs" />
<Compile Include="Messages\MqttMsgContext.cs" />
<Compile Include="Messages\MqttMsgDisconnect.cs" />
<Compile Include="Messages\MqttMsgPingReq.cs" />
<Compile Include="Messages\MqttMsgPingResp.cs" />
<Compile Include="Messages\MqttMsgPuback.cs" />
<Compile Include="Messages\MqttMsgPubcomp.cs" />
<Compile Include="Messages\MqttMsgPublish.cs" />
<Compile Include="Messages\MqttMsgPublishedEventArgs.cs" />
<Compile Include="Messages\MqttMsgPublishEventArgs.cs" />
<Compile Include="Messages\MqttMsgPubrec.cs" />
<Compile Include="Messages\MqttMsgPubrel.cs" />
<Compile Include="Messages\MqttMsgSuback.cs" />
<Compile Include="Messages\MqttMsgSubscribe.cs" />
<Compile Include="Messages\MqttMsgSubscribedEventArgs.cs" />
<Compile Include="Messages\MqttMsgSubscribeEventArgs.cs" />
<Compile Include="Messages\MqttMsgUnsuback.cs" />
<Compile Include="Messages\MqttMsgUnsubscribe.cs" />
<Compile Include="Messages\MqttMsgUnsubscribedEventArgs.cs" />
<Compile Include="Messages\MqttMsgUnsubscribeEventArgs.cs" />
<Compile Include="MqttClient.cs" />
<Compile Include="MqttSecurity.cs" />
<Compile Include="Net\Fx.cs" />
<Compile Include="Net\MqttNetworkChannel.cs" />
<Compile Include="MqttSettings.cs" />
<Compile Include="Net\SslStream.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
<Compile Include="Session\MqttBrokerSession.cs" />
<Compile Include="Session\MqttClientSession.cs" />
<Compile Include="Session\MqttSession.cs" />
<Compile Include="Utility\Trace.cs" />
<Compile Include="Utility\QueueExtension.cs" />
</ItemGroup>
<Import Project="$(MSBuildBinPath)\Microsoft.CompactFramework.CSharp.targets" />
<ProjectExtensions>
<VisualStudio>
<FlavorProperties GUID="{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}">
<HostingProcess disable="1" />
</FlavorProperties>
</VisualStudio>
</ProjectExtensions>
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
Other similar extension points exist, see Microsoft.Common.targets.
<Target Name="BeforeBuild">
</Target>
<Target Name="AfterBuild">
</Target>
-->
</Project>
5 changes: 3 additions & 2 deletions M2Mqtt/M2Mqtt.NetCf35.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>..\bin\Debug\M2Mqtt.NetCf35\</OutputPath>
<DefineConstants>TRACE;DEBUG;WindowsCE,COMPACT_FRAMEWORK</DefineConstants>
<DefineConstants>TRACE;DEBUG;WindowsCE,COMPACT_FRAMEWORK,SSL</DefineConstants>
<NoStdLib>true</NoStdLib>
<NoConfig>true</NoConfig>
<ErrorReport>prompt</ErrorReport>
Expand All @@ -36,7 +36,7 @@
<DebugType>pdbonly</DebugType>
<Optimize>true</Optimize>
<OutputPath>..\bin\Release\M2Mqtt.NetCf35\</OutputPath>
<DefineConstants>TRACE;WindowsCE,COMPACT_FRAMEWORK</DefineConstants>
<DefineConstants>TRACE;WindowsCE,COMPACT_FRAMEWORK,SSL</DefineConstants>
<NoStdLib>true</NoStdLib>
<NoConfig>true</NoConfig>
<ErrorReport>prompt</ErrorReport>
Expand Down Expand Up @@ -90,6 +90,7 @@
<Compile Include="Net\Fx.cs" />
<Compile Include="Net\MqttNetworkChannel.cs" />
<Compile Include="MqttSettings.cs" />
<Compile Include="Net\SslStream.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
<Compile Include="Session\MqttBrokerSession.cs" />
<Compile Include="Session\MqttClientSession.cs" />
Expand Down
2 changes: 1 addition & 1 deletion M2Mqtt/MqttClient.cs
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ Paolo Patierno - initial API and implementation and/or initial documentation
// else other frameworks (.Net, .Net Compact, Mono, Windows Phone)
#else
using System.Collections.Generic;
#if (SSL && !(WINDOWS_APP || WINDOWS_PHONE_APP))
#if (SSL && !(WINDOWS_APP || WINDOWS_PHONE_APP||COMPACT_FRAMEWORK))
using System.Security.Authentication;
using System.Net.Security;
#endif
Expand Down
17 changes: 13 additions & 4 deletions M2Mqtt/Net/MqttNetworkChannel.cs
Original file line number Diff line number Diff line change
Expand Up @@ -17,11 +17,15 @@ 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
#if COMPACT_FRAMEWORK

#else
using System.Net.Security;
using System.Security.Authentication;
#endif
#endif
#endif
using System.Net.Sockets;
using System.Net;
using System.Security.Cryptography.X509Certificates;
Expand Down Expand Up @@ -235,20 +239,23 @@ public void Connect()
if (secure)
{
// create SSL stream
#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 = new SslStream(this.socket);
#else
this.netStream = new NetworkStream(this.socket);
this.sslStream = new SslStream(this.netStream, false, this.userCertificateValidationCallback, this.userCertificateSelectionCallback);
#endif

// server authentication (SSL/TLS handshake)
#if (MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3)
#if (MF_FRAMEWORK_VERSION_V4_2 || MF_FRAMEWORK_VERSION_V4_3 )
this.sslStream.AuthenticateAsClient(this.remoteHostName,
this.clientCert,
new X509Certificate[] { this.caCert },
SslVerification.CertificateRequired,
MqttSslUtility.ToSslPlatformEnum(this.sslProtocol));
#else
#if (COMPACT_FRAMEWORK)

#else
X509CertificateCollection clientCertificates = null;
// check if there is a client certificate to add to the collection, otherwise it's null (as empty)
Expand All @@ -260,6 +267,7 @@ public void Connect()
MqttSslUtility.ToSslPlatformEnum(this.sslProtocol),
false);

#endif
#endif
}
#endif
Expand Down Expand Up @@ -302,7 +310,7 @@ public int Receive(byte[] buffer)
{
// fixed scenario with socket closed gracefully by peer/broker and
// Read return 0. Avoid infinite loop.
read = this.sslStream.Read(buffer, idx, buffer.Length - idx);
read = this.sslStream.Read(ref buffer, idx, buffer.Length - idx);
if (read == 0)
return 0;
idx += read;
Expand Down Expand Up @@ -387,7 +395,8 @@ public void Accept()
// secure channel requested
if (secure)
{
#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.netStream = new NetworkStream(this.socket);
this.sslStream = new SslStream(this.netStream, false, this.userCertificateValidationCallback, this.userCertificateSelectionCallback);
Expand Down
141 changes: 141 additions & 0 deletions M2Mqtt/Net/SslStream.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,141 @@
using System.Net.Sockets;
using Microsoft.Win32;
using System.Globalization;
using System.Runtime.InteropServices;
using System.IO;
using System;
using System.Security.Cryptography.X509Certificates;

namespace uPLibrary.Networking.M2Mqtt
{
/// <summary>
/// OPEN SSL STREAM
/// </summary>
///
public class SslStream{

private IntPtr ssl ;
private IntPtr bio ;
private IntPtr ctx ;

private Socket socket;

[DllImport("ssleay32.dll")]
public static extern void SSL_load_error_strings();

[DllImport("ssleay32.dll")]
public static extern int SSL_library_init();

[DllImport("libeay32.dll")]
public static extern void ERR_load_BIO_strings();

[DllImport("libeay32.dll")]
public static extern void OPENSSL_add_all_algorithms_noconf();

[DllImport("ssleay32.dll")]
public static extern void SSL_CTX_free(IntPtr ctx);

[DllImport("libeay32.dll")]
public static extern void BIO_free_all(IntPtr bio);

[DllImport("ssleay32.dll")]
public static extern void SSL_shutdown(IntPtr ssl);

[DllImport("ssleay32.dll", EntryPoint="SSLv23_client_method")]
public static extern IntPtr SSLv23_client_method();

[DllImport("ssleay32.dll")]
public static extern IntPtr SSLv3_method();

[DllImport("ssleay32.dll")]
public static extern IntPtr SSLv23_method();

[DllImport("ssleay32.dll")]
public static extern IntPtr TLSv1_2_method();

[DllImport("ssleay32.dll")]
public static extern IntPtr SSL_CTX_new(IntPtr sslMethod);

[DllImport("ssleay32.dll")]
public static extern IntPtr SSL_new(IntPtr ctx);

[DllImport("ssleay32.dll")]
public static extern int SSL_set_fd(IntPtr ssl, IntPtr fd);

[DllImport("ssleay32.dll")]
public static extern int SSL_connect(IntPtr ssl);

[DllImport("ssleay32.dll")]
public static extern int SSL_get_error(IntPtr ssl, int ret);

[DllImport("libeay32.dll")]
public static extern int ERR_get_error();

[DllImport("ssleay32.dll")]
public static extern int SSL_read(IntPtr ssl, byte[] buffer, int length);

[DllImport("ssleay32.dll")]
public static extern int SSL_write(IntPtr ssl, byte[] buffer, int length);



/// <summary>
/// SSL Stream Constructor
/// </summary>
/// <param name="socket">Base socket</param>
public SslStream(Socket socket) {
SSL_library_init();
SSL_load_error_strings();
ERR_load_BIO_strings();
OPENSSL_add_all_algorithms_noconf();
this.socket = socket;
ctx = SSL_CTX_new(SSLv23_client_method());
ssl = SSL_new(ctx);
SSL_set_fd(ssl, socket.Handle);
int conStatus = SSL_connect(ssl);
if (conStatus != 1){
int errcode = SSL_get_error(ssl, conStatus);
throw new Exception("SSL handshake error");
}
}

/// <summary>
/// Read buffer
/// </summary>
/// <param name="buffer">Buffer to read</param>
/// <param name="length">Buffer lenght</param>
public int Read(ref byte[] buffer, int offset, int length)
{
return SSL_read(ssl, buffer,length);
}

/// <summary>
/// Write buffer
/// </summary>
/// <param name="buffer">Buffer to read</param>
/// <param name="length">Buffer lenght</param>
public int Write( byte[] buffer, int offset, int length)
{
return SSL_write(ssl, buffer, buffer.Length);
}
/// <summary>
/// Flush
/// </summary>
public int Flush()
{
return 0;
}

/// <summary>
/// Close SSL Stream
/// </summary>
/// <param name="buffer">Buffer to read</param>
/// <param name="length">Buffer lenght</param>
public void Close() {
SSL_shutdown(ssl);
BIO_free_all(bio);
SSL_CTX_free(ctx);
}

}
}
6 changes: 6 additions & 0 deletions M2Mqtt/Utility/QueueExtension.cs
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,12 @@ Paolo Patierno - initial API and implementation and/or initial documentation

using System;
using System.Collections;
using System.Runtime.CompilerServices;

namespace System.Runtime.CompilerServices
{
public class ExtensionAttribute : Attribute { }
}

namespace uPLibrary.Networking.M2Mqtt.Utility
{
Expand Down
6 changes: 6 additions & 0 deletions M2MqttVS2008.sln
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@ Microsoft Visual Studio Solution File, Format Version 10.00
# Visual Studio 2008
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "M2Mqtt.NetCf35", "M2Mqtt\M2Mqtt.NetCf35.csproj", "{194FEA1B-E67F-4FC0-AC47-CD71F7F060CC}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "M2Mqtt.NetCF2", "M2Mqtt\M2Mqtt.NetCF2.csproj", "{8031328B-B554-4059-9CC4-0F712D054D92}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Expand All @@ -13,6 +15,10 @@ Global
{194FEA1B-E67F-4FC0-AC47-CD71F7F060CC}.Debug|Any CPU.Build.0 = Debug|Any CPU
{194FEA1B-E67F-4FC0-AC47-CD71F7F060CC}.Release|Any CPU.ActiveCfg = Release|Any CPU
{194FEA1B-E67F-4FC0-AC47-CD71F7F060CC}.Release|Any CPU.Build.0 = Release|Any CPU
{8031328B-B554-4059-9CC4-0F712D054D92}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{8031328B-B554-4059-9CC4-0F712D054D92}.Debug|Any CPU.Build.0 = Debug|Any CPU
{8031328B-B554-4059-9CC4-0F712D054D92}.Release|Any CPU.ActiveCfg = Release|Any CPU
{8031328B-B554-4059-9CC4-0F712D054D92}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
Expand Down
Loading