diff --git a/websocket-sharp.userprefs b/websocket-sharp.userprefs
new file mode 100644
index 00000000..beeb6c0a
--- /dev/null
+++ b/websocket-sharp.userprefs
@@ -0,0 +1,12 @@
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/websocket-sharp/AssemblyInfo.cs b/websocket-sharp/AssemblyInfo.cs
new file mode 100644
index 00000000..89a8f31a
--- /dev/null
+++ b/websocket-sharp/AssemblyInfo.cs
@@ -0,0 +1,27 @@
+using System.Reflection;
+using System.Runtime.CompilerServices;
+
+// Information about this assembly is defined by the following attributes.
+// Change them to the values specific to your project.
+
+[assembly: AssemblyTitle("websocket-sharp")]
+[assembly: AssemblyDescription("A C# implementation of a WebSocket protocol client")]
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("websocket-sharp.dll")]
+[assembly: AssemblyCopyright("sta.blockhead")]
+[assembly: AssemblyTrademark("")]
+[assembly: AssemblyCulture("")]
+
+// The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}".
+// The form "{Major}.{Minor}.*" will automatically update the build and revision,
+// and "{Major}.{Minor}.{Build}.*" will update just the revision.
+
+[assembly: AssemblyVersion("1.0.0.*")]
+
+// The following attributes are used to specify the signing key for the assembly,
+// if desired. See the Mono documentation for more information about signing.
+
+//[assembly: AssemblyDelaySign(false)]
+//[assembly: AssemblyKeyFile("")]
+
diff --git a/websocket-sharp/Ext.cs b/websocket-sharp/Ext.cs
new file mode 100644
index 00000000..901ccaeb
--- /dev/null
+++ b/websocket-sharp/Ext.cs
@@ -0,0 +1,51 @@
+#region MIT License
+/**
+ * Ext.cs
+ *
+ * The MIT License
+ *
+ * Copyright (c) 2010 sta.blockhead
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+#endregion
+
+using System;
+using System.Collections.Generic;
+
+namespace WebSocketSharp
+{
+ public static class Ext
+ {
+ public static bool EqualsWithSaveTo(this int asbyte, char c, List dist)
+ {
+ byte b = (byte)asbyte;
+ dist.Add(b);
+ return b == Convert.ToByte(c);
+ }
+
+ public static void NotEqualsDo(this string a, string b, Action action)
+ {
+ if (a != b)
+ {
+ action(a);
+ }
+ }
+ }
+}
diff --git a/websocket-sharp/IWsStream.cs b/websocket-sharp/IWsStream.cs
new file mode 100644
index 00000000..43b17b1b
--- /dev/null
+++ b/websocket-sharp/IWsStream.cs
@@ -0,0 +1,41 @@
+#region MIT License
+/**
+ * IWsStream.cs
+ *
+ * The MIT License
+ *
+ * Copyright (c) 2010 sta.blockhead
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+#endregion
+
+using System;
+
+namespace WebSocketSharp
+{
+ public interface IWsStream : IDisposable
+ {
+ void Close();
+ int Read(byte[] buffer, int offset, int size);
+ int ReadByte();
+ void Write(byte[] buffer, int offset, int count);
+ void WriteByte(byte value);
+ }
+}
diff --git a/websocket-sharp/WebSocket.cs b/websocket-sharp/WebSocket.cs
new file mode 100644
index 00000000..af88a1b2
--- /dev/null
+++ b/websocket-sharp/WebSocket.cs
@@ -0,0 +1,450 @@
+#region MIT License
+/**
+ * WebSocket.cs
+ *
+ * A C# implementation of a WebSocket protocol client.
+ * This code derived from WebSocket.java (http://github.com/adamac/Java-WebSocket-client).
+ *
+ * The MIT License
+ *
+ * Copyright (c) 2009 Adam MacBeth
+ * Copyright (c) 2010 sta.blockhead
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+#endregion
+
+#if NOTIFY
+using Notifications;
+#endif
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Net;
+using System.Net.Security;
+using System.Net.Sockets;
+using System.Text;
+using System.Threading;
+
+namespace WebSocketSharp
+{
+ public delegate void MessageEventHandler(object sender, string eventdata);
+
+ public class WebSocket : IDisposable
+ {
+ private Uri uri;
+ public string Url
+ {
+ get
+ {
+ return uri.ToString();
+ }
+ }
+
+ private volatile WsState readyState;
+ public WsState ReadyState
+ {
+ get
+ {
+ return readyState;
+ }
+
+ private set
+ {
+ switch (value)
+ {
+ case WsState.OPEN:
+ if (OnOpen != null)
+ {
+ OnOpen(this, EventArgs.Empty);
+ }
+ goto default;
+ case WsState.CLOSING:
+ case WsState.CLOSED:
+ close(value);
+ break;
+ default:
+ readyState = value;
+ break;
+ }
+ }
+ }
+
+ private StringBuilder unTransmittedBuffer;
+ public String UnTransmittedBuffer
+ {
+ get { return unTransmittedBuffer.ToString(); }
+ }
+
+ private long bufferedAmount;
+ public long BufferedAmount
+ {
+ get { return bufferedAmount; }
+ }
+
+ private string protocol;
+ public string Protocol
+ {
+ get { return protocol; }
+ }
+
+ private TcpClient tcpClient;
+ private NetworkStream netStream;
+ private SslStream sslStream;
+ private IWsStream wsStream;
+ private Thread msgThread;
+#if NOTIFY
+ private Notification msgNf;
+ public Notification MsgNf
+ {
+ get { return msgNf; }
+ }
+#endif
+ public event EventHandler OnOpen;
+ public event MessageEventHandler OnMessage;
+ public event MessageEventHandler OnError;
+ public event EventHandler OnClose;
+
+ public WebSocket(string url)
+ : this(url, String.Empty)
+ {
+ }
+
+ public WebSocket(string url, string protocol)
+ {
+ this.uri = new Uri(url);
+ string scheme = uri.Scheme;
+
+ if (scheme != "ws" && scheme != "wss")
+ {
+ throw new ArgumentException("Unsupported scheme: " + scheme);
+ }
+
+ this.readyState = WsState.CONNECTING;
+ this.unTransmittedBuffer = new StringBuilder();
+ this.bufferedAmount = 0;
+ this.protocol = protocol;
+ }
+
+ public void Connect()
+ {
+ createConnection();
+ doHandshake();
+
+ this.msgThread = new Thread(new ThreadStart(message));
+ msgThread.IsBackground = true;
+ msgThread.Start();
+ }
+
+ public void Send(string data)
+ {
+ if (readyState == WsState.CONNECTING)
+ {
+ throw new InvalidOperationException("Handshake not complete.");
+ }
+
+ byte[] dataBuffer = Encoding.UTF8.GetBytes(data);
+
+ try
+ {
+ wsStream.WriteByte(0x00);
+ wsStream.Write(dataBuffer, 0, dataBuffer.Length);
+ wsStream.WriteByte(0xff);
+ }
+ catch (Exception e)
+ {
+ unTransmittedBuffer.Append(data);
+ bufferedAmount += dataBuffer.Length;
+
+ if (OnError != null)
+ {
+ OnError(this, e.Message);
+ }
+#if DEBUG
+ Console.WriteLine("WS: Error @Send: {0}", e.Message);
+#endif
+ }
+ }
+
+ public void Close()
+ {
+ ReadyState = WsState.CLOSING;
+ }
+
+ public void Dispose()
+ {
+ Close();
+ }
+
+ private void close(WsState state)
+ {
+#if DEBUG
+ Console.WriteLine("WS: Info @close: Current thread IsBackground: {0}", Thread.CurrentThread.IsBackground);
+#endif
+ if (readyState == WsState.CLOSING ||
+ readyState == WsState.CLOSED)
+ {
+ return;
+ }
+
+ readyState = state;
+
+ if (OnClose != null)
+ {
+ OnClose(this, EventArgs.Empty);
+ }
+
+ if (wsStream != null && tcpClient.Connected)
+ {
+ try
+ {
+ wsStream.WriteByte(0xff);
+ wsStream.WriteByte(0x00);
+ }
+ catch (Exception e)
+ {
+#if DEBUG
+ Console.WriteLine("WS: Error @close: {0}", e.Message);
+#endif
+ }
+ }
+
+ if (!(Thread.CurrentThread.IsBackground) &&
+ msgThread != null && msgThread.IsAlive)
+ {
+ msgThread.Join();
+ }
+
+ if (wsStream != null)
+ {
+ wsStream.Dispose();
+ wsStream = null;
+ }
+
+ if (tcpClient != null)
+ {
+ tcpClient.Close();
+ tcpClient = null;
+ }
+ }
+
+ private void createConnection()
+ {
+ string scheme = uri.Scheme;
+ string host = uri.DnsSafeHost;
+ int port = uri.Port;
+
+ if (port <= 0)
+ {
+ if (scheme == "wss")
+ {
+ port = 443;
+ }
+ else
+ {
+ port = 80;
+ }
+ }
+
+ this.tcpClient = new TcpClient(host, port);
+ this.netStream = tcpClient.GetStream();
+
+ if (scheme == "wss")
+ {
+ this.sslStream = new SslStream(netStream);
+ sslStream.AuthenticateAsClient(host);
+ this.wsStream = new WsStream(sslStream);
+ }
+ else
+ {
+ this.wsStream = new WsStream(netStream);
+ }
+ }
+
+ private void doHandshake()
+ {
+ string path = uri.PathAndQuery;
+ string host = uri.DnsSafeHost;
+ string origin = "http://" + host;
+
+ int port = ((IPEndPoint)tcpClient.Client.RemoteEndPoint).Port;
+ if (port != 80)
+ {
+ host += ":" + port;
+ }
+
+ string subprotocol = protocol != String.Empty
+ ? String.Format("Sec-WebSocket-Protocol: {0}\r\n", protocol)
+ : protocol;
+
+ string request = "GET " + path + " HTTP/1.1\r\n" +
+ "Upgrade: WebSocket\r\n" +
+ "Connection: Upgrade\r\n" +
+ subprotocol +
+ "Host: " + host + "\r\n" +
+ "Origin: " + origin + "\r\n" +
+ "\r\n";
+#if DEBUG
+ Console.WriteLine("WS: Info @doHandshake: Handshake from client: \n{0}", request);
+#endif
+ byte[] sendBuffer = Encoding.UTF8.GetBytes(request);
+ wsStream.Write(sendBuffer, 0, sendBuffer.Length);
+
+ string[] response;
+ List rawdata = new List();
+
+ while (true)
+ {
+ if (wsStream.ReadByte().EqualsWithSaveTo('\r', rawdata) &&
+ wsStream.ReadByte().EqualsWithSaveTo('\n', rawdata) &&
+ wsStream.ReadByte().EqualsWithSaveTo('\r', rawdata) &&
+ wsStream.ReadByte().EqualsWithSaveTo('\n', rawdata))
+ {
+ break;
+ }
+ }
+
+ response = Encoding.UTF8.GetString(rawdata.ToArray())
+ .Replace("\r\n", "\n").Replace("\n\n", "\n")
+ .Split('\n');
+#if DEBUG
+ Console.WriteLine("WS: Info @doHandshake: Handshake from server:");
+ foreach (string s in response)
+ {
+ Console.WriteLine("{0}", s);
+ }
+#endif
+ Action action = s => { throw new IOException("Invalid handshake response: " + s); };
+ response[0].NotEqualsDo("HTTP/1.1 101 Web Socket Protocol Handshake", action);
+ response[1].NotEqualsDo("Upgrade: WebSocket", action);
+ response[2].NotEqualsDo("Connection: Upgrade", action);
+
+ for (int i = 3; i < response.Length; i++)
+ {
+ if (response[i].Contains("WebSocket-Protocol:"))
+// if (response[i].Contains("Sec-WebSocket-Protocol:"))
+ {
+ int j = response[i].IndexOf(":");
+ protocol = response[i].Substring(j + 1).Trim();
+ }
+ }
+#if DEBUG
+ Console.WriteLine("WS: Info @doHandshake: Sub protocol: {0}", protocol);
+#endif
+
+ ReadyState = WsState.OPEN;
+ }
+
+ private void message()
+ {
+#if DEBUG
+ Console.WriteLine("WS: Info @message: Current thread IsBackground: {0}", Thread.CurrentThread.IsBackground);
+#endif
+ string data;
+#if NOTIFY
+ this.msgNf = new Notification();
+ msgNf.AddHint("append", "allowed");
+#endif
+ while (readyState == WsState.OPEN)
+ {
+ while (readyState == WsState.OPEN && netStream.DataAvailable)
+ {
+ data = receive();
+
+ if (OnMessage != null && data != null)
+ {
+ OnMessage(this, data);
+ }
+ }
+ }
+#if DEBUG
+ Console.WriteLine("WS: Info @message: Exit message method.");
+#endif
+ }
+
+ private string receive()
+ {
+ try
+ {
+ byte frame_type = (byte)wsStream.ReadByte();
+ byte b;
+
+ if ((frame_type & 0x80) == 0x80)
+ {
+ // Skip data frame
+ int len = 0;
+ int b_v;
+
+ do
+ {
+ b = (byte)wsStream.ReadByte();
+ b_v = b & 0x7f;
+ len = len * 128 + b_v;
+ }
+ while ((b & 0x80) == 0x80);
+
+ for (int i = 0; i < len; i++)
+ {
+ wsStream.ReadByte();
+ }
+
+ if (frame_type == 0xff && len == 0)
+ {
+ ReadyState = WsState.CLOSED;
+#if DEBUG
+ Console.WriteLine("WS: Info @receive: Server start closing handshake.");
+#endif
+ }
+ }
+ else if (frame_type == 0x00)
+ {
+ List raw_data = new List();
+
+ while (true)
+ {
+ b = (byte)wsStream.ReadByte();
+
+ if (b == 0xff)
+ {
+ break;
+ }
+
+ raw_data.Add(b);
+ }
+
+ return Encoding.UTF8.GetString(raw_data.ToArray());
+ }
+ }
+ catch (Exception e)
+ {
+ if (OnError != null)
+ {
+ OnError(this, e.Message);
+ }
+
+ ReadyState = WsState.CLOSED;
+#if DEBUG
+ Console.WriteLine("WS: Error @receive: {0}", e.Message);
+#endif
+ }
+
+ return null;
+ }
+ }
+}
diff --git a/websocket-sharp/WsState.cs b/websocket-sharp/WsState.cs
new file mode 100644
index 00000000..0de3717e
--- /dev/null
+++ b/websocket-sharp/WsState.cs
@@ -0,0 +1,40 @@
+#region MIT License
+/**
+ * WsState.cs
+ *
+ * The MIT License
+ *
+ * Copyright (c) 2010 sta.blockhead
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+#endregion
+
+using System;
+
+namespace WebSocketSharp
+{
+ public enum WsState
+ {
+ CONNECTING,
+ OPEN,
+ CLOSING,
+ CLOSED
+ }
+}
diff --git a/websocket-sharp/WsStream.cs b/websocket-sharp/WsStream.cs
new file mode 100644
index 00000000..112c6ac9
--- /dev/null
+++ b/websocket-sharp/WsStream.cs
@@ -0,0 +1,90 @@
+#region MIT License
+/**
+ * WsStream.cs
+ *
+ * The MIT License
+ *
+ * Copyright (c) 2010 sta.blockhead
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+#endregion
+
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Net.Security;
+using System.Net.Sockets;
+using System.Reflection;
+
+namespace WebSocketSharp
+{
+ public class WsStream : IWsStream
+ where T : Stream
+ {
+ private T innerStream;
+
+ public WsStream(T innerStream)
+ {
+ if (innerStream == null)
+ {
+ throw new ArgumentNullException("innerStream");
+ }
+
+ Type streamType = innerStream.GetType();
+ if (streamType != typeof(NetworkStream) &&
+ streamType != typeof(SslStream))
+ {
+ throw new ArgumentException("Unsupported Stream type: " + streamType.ToString());
+ }
+
+ this.innerStream = innerStream;
+ }
+
+ public void Close()
+ {
+ innerStream.Close();
+ }
+
+ public void Dispose()
+ {
+ innerStream.Dispose();
+ }
+
+ public int Read(byte[] buffer, int offset, int size)
+ {
+ return innerStream.Read(buffer, offset, size);
+ }
+
+ public int ReadByte()
+ {
+ return innerStream.ReadByte();
+ }
+
+ public void Write(byte[] buffer, int offset, int count)
+ {
+ innerStream.Write(buffer, offset, count);
+ }
+
+ public void WriteByte(byte value)
+ {
+ innerStream.WriteByte(value);
+ }
+ }
+}
diff --git a/websocket-sharp/bin/Debug/websocket-sharp.dll b/websocket-sharp/bin/Debug/websocket-sharp.dll
new file mode 100755
index 00000000..ed2265f0
Binary files /dev/null and b/websocket-sharp/bin/Debug/websocket-sharp.dll differ
diff --git a/websocket-sharp/bin/Debug/websocket-sharp.dll.mdb b/websocket-sharp/bin/Debug/websocket-sharp.dll.mdb
new file mode 100644
index 00000000..cf42014a
Binary files /dev/null and b/websocket-sharp/bin/Debug/websocket-sharp.dll.mdb differ
diff --git a/websocket-sharp/bin/Debug_Ubuntu/websocket-sharp.dll b/websocket-sharp/bin/Debug_Ubuntu/websocket-sharp.dll
new file mode 100755
index 00000000..136168f1
Binary files /dev/null and b/websocket-sharp/bin/Debug_Ubuntu/websocket-sharp.dll differ
diff --git a/websocket-sharp/bin/Debug_Ubuntu/websocket-sharp.dll.mdb b/websocket-sharp/bin/Debug_Ubuntu/websocket-sharp.dll.mdb
new file mode 100644
index 00000000..1e0f6326
Binary files /dev/null and b/websocket-sharp/bin/Debug_Ubuntu/websocket-sharp.dll.mdb differ
diff --git a/websocket-sharp/bin/Release/websocket-sharp.dll b/websocket-sharp/bin/Release/websocket-sharp.dll
new file mode 100755
index 00000000..453793f6
Binary files /dev/null and b/websocket-sharp/bin/Release/websocket-sharp.dll differ
diff --git a/websocket-sharp/bin/Release_Ubuntu/websocket-sharp.dll b/websocket-sharp/bin/Release_Ubuntu/websocket-sharp.dll
new file mode 100755
index 00000000..0d8c2695
Binary files /dev/null and b/websocket-sharp/bin/Release_Ubuntu/websocket-sharp.dll differ
diff --git a/websocket-sharp/websocket-sharp.csproj b/websocket-sharp/websocket-sharp.csproj
new file mode 100644
index 00000000..5d91eaf0
--- /dev/null
+++ b/websocket-sharp/websocket-sharp.csproj
@@ -0,0 +1,67 @@
+
+
+
+ Debug
+ AnyCPU
+ 9.0.21022
+ 2.0
+ {B357BAC7-529E-4D81-A0D2-71041B19C8DE}
+ Library
+ WebSocketSharp
+ websocket-sharp
+ v3.5
+
+
+ true
+ full
+ false
+ bin\Debug
+ DEBUG
+ prompt
+ 4
+ false
+
+
+ none
+ false
+ bin\Release
+ prompt
+ 4
+ false
+
+
+ true
+ full
+ false
+ bin\Debug_Ubuntu
+ DEBUG,NOTIFY
+ prompt
+ 4
+ false
+
+
+ none
+ false
+ bin\Release_Ubuntu
+ prompt
+ 4
+ false
+ NOTIFY
+
+
+
+
+
+ notify-sharp
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/websocket-sharp/websocket-sharp.pidb b/websocket-sharp/websocket-sharp.pidb
new file mode 100644
index 00000000..143f5902
Binary files /dev/null and b/websocket-sharp/websocket-sharp.pidb differ
diff --git a/wsclient/AssemblyInfo.cs b/wsclient/AssemblyInfo.cs
new file mode 100644
index 00000000..ade05a55
--- /dev/null
+++ b/wsclient/AssemblyInfo.cs
@@ -0,0 +1,27 @@
+using System.Reflection;
+using System.Runtime.CompilerServices;
+
+// Information about this assembly is defined by the following attributes.
+// Change them to the values specific to your project.
+
+[assembly: AssemblyTitle("wsclient")]
+[assembly: AssemblyDescription("")]
+[assembly: AssemblyConfiguration("")]
+[assembly: AssemblyCompany("")]
+[assembly: AssemblyProduct("")]
+[assembly: AssemblyCopyright("")]
+[assembly: AssemblyTrademark("")]
+[assembly: AssemblyCulture("")]
+
+// The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}".
+// The form "{Major}.{Minor}.*" will automatically update the build and revision,
+// and "{Major}.{Minor}.{Build}.*" will update just the revision.
+
+[assembly: AssemblyVersion("1.0.*")]
+
+// The following attributes are used to specify the signing key for the assembly,
+// if desired. See the Mono documentation for more information about signing.
+
+//[assembly: AssemblyDelaySign(false)]
+//[assembly: AssemblyKeyFile("")]
+
diff --git a/wsclient/bin/Debug/websocket-sharp.dll b/wsclient/bin/Debug/websocket-sharp.dll
new file mode 100755
index 00000000..ed2265f0
Binary files /dev/null and b/wsclient/bin/Debug/websocket-sharp.dll differ
diff --git a/wsclient/bin/Debug/websocket-sharp.dll.mdb b/wsclient/bin/Debug/websocket-sharp.dll.mdb
new file mode 100644
index 00000000..cf42014a
Binary files /dev/null and b/wsclient/bin/Debug/websocket-sharp.dll.mdb differ
diff --git a/wsclient/bin/Debug/wsclient.exe b/wsclient/bin/Debug/wsclient.exe
new file mode 100755
index 00000000..d942ac3b
Binary files /dev/null and b/wsclient/bin/Debug/wsclient.exe differ
diff --git a/wsclient/bin/Debug/wsclient.exe.mdb b/wsclient/bin/Debug/wsclient.exe.mdb
new file mode 100644
index 00000000..168fde3d
Binary files /dev/null and b/wsclient/bin/Debug/wsclient.exe.mdb differ
diff --git a/wsclient/bin/Debug_Ubuntu/websocket-sharp.dll b/wsclient/bin/Debug_Ubuntu/websocket-sharp.dll
new file mode 100755
index 00000000..136168f1
Binary files /dev/null and b/wsclient/bin/Debug_Ubuntu/websocket-sharp.dll differ
diff --git a/wsclient/bin/Debug_Ubuntu/websocket-sharp.dll.mdb b/wsclient/bin/Debug_Ubuntu/websocket-sharp.dll.mdb
new file mode 100644
index 00000000..1e0f6326
Binary files /dev/null and b/wsclient/bin/Debug_Ubuntu/websocket-sharp.dll.mdb differ
diff --git a/wsclient/bin/Debug_Ubuntu/wsclient.exe b/wsclient/bin/Debug_Ubuntu/wsclient.exe
new file mode 100755
index 00000000..c1eeab09
Binary files /dev/null and b/wsclient/bin/Debug_Ubuntu/wsclient.exe differ
diff --git a/wsclient/bin/Debug_Ubuntu/wsclient.exe.mdb b/wsclient/bin/Debug_Ubuntu/wsclient.exe.mdb
new file mode 100644
index 00000000..5682925e
Binary files /dev/null and b/wsclient/bin/Debug_Ubuntu/wsclient.exe.mdb differ
diff --git a/wsclient/bin/Release/websocket-sharp.dll b/wsclient/bin/Release/websocket-sharp.dll
new file mode 100755
index 00000000..453793f6
Binary files /dev/null and b/wsclient/bin/Release/websocket-sharp.dll differ
diff --git a/wsclient/bin/Release/wsclient.exe b/wsclient/bin/Release/wsclient.exe
new file mode 100755
index 00000000..67dc78c6
Binary files /dev/null and b/wsclient/bin/Release/wsclient.exe differ
diff --git a/wsclient/bin/Release_Ubuntu/websocket-sharp.dll b/wsclient/bin/Release_Ubuntu/websocket-sharp.dll
new file mode 100755
index 00000000..0d8c2695
Binary files /dev/null and b/wsclient/bin/Release_Ubuntu/websocket-sharp.dll differ
diff --git a/wsclient/bin/Release_Ubuntu/wsclient.exe b/wsclient/bin/Release_Ubuntu/wsclient.exe
new file mode 100755
index 00000000..d4156b85
Binary files /dev/null and b/wsclient/bin/Release_Ubuntu/wsclient.exe differ
diff --git a/wsclient/wsclient.cs b/wsclient/wsclient.cs
new file mode 100644
index 00000000..5f00a7bb
--- /dev/null
+++ b/wsclient/wsclient.cs
@@ -0,0 +1,77 @@
+using Notifications;
+using System;
+using System.Threading;
+using WebSocketSharp;
+
+namespace Example
+{
+ public class Program
+ {
+ public static void Main(string[] args)
+ {
+ //using (WebSocket ws = new WebSocket("ws://localhost:8000/"))
+ using (WebSocket ws = new WebSocket("ws://localhost:8000/", "chat"))
+ {
+ /*ws.OnOpen += (o, e) =>
+ {
+ //Do something.
+ };
+ */
+ ws.OnMessage += (o, e) =>
+ {
+#if LINUX
+ #if NOTIFY
+ ws.MsgNf.Summary = "[WebSocket] Message";
+ ws.MsgNf.Body = e;
+ ws.MsgNf.IconName = "notification-message-im";
+ ws.MsgNf.Show();
+ #else
+ Notification nf = new Notification("[WebSocket] Message",
+ e,
+ "notification-message-im");
+ nf.Show();
+ #endif
+#else
+ Console.WriteLine(e);
+#endif
+ };
+
+ ws.OnError += (o, e) =>
+ {
+#if LINUX
+ Notification nf = new Notification("[WebSocket] Error",
+ e,
+ "notification-network-disconnected");
+ nf.Show();
+#else
+ Console.WriteLine("Error: ", e);
+#endif
+ };
+ /*ws.OnClose += (o, e) =>
+ {
+ //Do something.
+ };
+ */
+ ws.Connect();
+
+ Thread.Sleep(500);
+ Console.WriteLine("\nType \"exit\" to exit.\n");
+
+ string data;
+ while (true)
+ {
+ Thread.Sleep(500);
+
+ Console.Write("> ");
+ data = Console.ReadLine();
+ if (data == "exit")
+ {
+ break;
+ }
+
+ ws.Send(data);
+ }
+ }
+ }
+ }
+}
diff --git a/wsclient/wsclient.csproj b/wsclient/wsclient.csproj
new file mode 100644
index 00000000..bb8f71af
--- /dev/null
+++ b/wsclient/wsclient.csproj
@@ -0,0 +1 @@
+
Debug
AnyCPU
9.0.21022
2.0
{52805AEC-EFB1-4F42-BB8E-3ED4E692C568}
Exe
WsClient
wsclient
v3.5
true
full
false
bin\Debug
DEBUG
prompt
4
true
none
false
bin\Release
prompt
4
true
true
full
false
bin\Debug_Ubuntu
DEBUG,LINUX,NOTIFY
prompt
4
true
none
false
bin\Release_Ubuntu
LINUX,NOTIFY
prompt
4
true
notify-sharp
{B357BAC7-529E-4D81-A0D2-71041B19C8DE}
websocket-sharp
\ No newline at end of file
diff --git a/wsclient/wsclient.pidb b/wsclient/wsclient.pidb
new file mode 100644
index 00000000..8270c3e4
Binary files /dev/null and b/wsclient/wsclient.pidb differ