From 896fdebd1b6d7f6f7145acbcbbe88d796adda6c8 Mon Sep 17 00:00:00 2001 From: Daniel Baetz Date: Sun, 4 Aug 2019 01:38:05 +0200 Subject: [PATCH 1/3] v1.6.1.0 --- Example.Client/Program.cs | 22 +++--- Example.Server/Program.cs | 18 +++-- Exomia.Network/ClientBase.cs | 43 +++++------ Exomia.Network/Constants.cs | 4 +- Exomia.Network/DeserializePacketInfo.cs | 38 ++++++++++ Exomia.Network/Exomia.Network.csproj | 2 +- Exomia.Network/PacketInfo.cs | 60 +++++++++++++--- .../Serialization/Serialization.Tcp.cs | 71 +++++++++++-------- .../Serialization/Serialization.Udp.cs | 60 +++++++++------- Exomia.Network/ServerBase.cs | 50 +++++++------ Exomia.Network/TCP/TcpClientApm.cs | 4 +- Exomia.Network/TCP/TcpClientBase.cs | 2 +- Exomia.Network/TCP/TcpClientEap.cs | 4 +- Exomia.Network/TCP/TcpServerApmBase.cs | 5 +- Exomia.Network/TCP/TcpServerBase.cs | 2 +- Exomia.Network/TCP/TcpServerEapBase.cs | 4 +- Exomia.Network/UDP/UdpClientApm.cs | 4 +- Exomia.Network/UDP/UdpClientBase.cs | 1 + Exomia.Network/UDP/UdpClientEap.cs | 4 +- Exomia.Network/UDP/UdpServerApmBase.cs | 4 +- Exomia.Network/UDP/UdpServerBase.cs | 1 + Exomia.Network/UDP/UdpServerEapBase.cs | 4 +- 22 files changed, 258 insertions(+), 149 deletions(-) create mode 100644 Exomia.Network/DeserializePacketInfo.cs diff --git a/Example.Client/Program.cs b/Example.Client/Program.cs index a84f3ee..b22531a 100644 --- a/Example.Client/Program.cs +++ b/Example.Client/Program.cs @@ -8,20 +8,20 @@ #endregion -#define TCP +#define TCP9 +#if TCP +using Exomia.Network.TCP; +#else +using Exomia.Network.UDP; +#endif using System; using System.Diagnostics; using System.Linq; using System.Text; +using System.Threading; using System.Threading.Tasks; using Exomia.Network; -#if TCP -using Exomia.Network.TCP; - -#else -using Exomia.Network.UDP; -#endif namespace Example.Client { @@ -30,9 +30,9 @@ class Program private static async Task Main(string[] args) { #if TCP - TcpClientEap client = new TcpClientEap(8096); + TcpClientEap client = new TcpClientEap(512); #else - var client = new UdpClientEap(8096); + UdpClientEap client = new UdpClientEap(512); #endif client.Disconnected += (c, r) => { Console.WriteLine(r + " | Disconnected"); }; client.AddCommand( @@ -47,10 +47,10 @@ private static async Task Main(string[] args) Console.WriteLine(data + " -- OK"); return true; }); - + Thread.Sleep(100); Console.WriteLine(client.Connect("127.0.0.1", 3000) ? "CONNECTED" : "CONNECT FAILED"); - byte[] request = Encoding.UTF8.GetBytes(string.Join(" ", Enumerable.Range(1, 10_000))); + byte[] request = Encoding.UTF8.GetBytes(string.Join(" ", Enumerable.Range(1, 1_000))); Console.WriteLine(request.Length); for (int i = 0; i < 10; i++) { diff --git a/Example.Server/Program.cs b/Example.Server/Program.cs index da9b5b4..5da520c 100644 --- a/Example.Server/Program.cs +++ b/Example.Server/Program.cs @@ -8,17 +8,16 @@ #endregion -#define TCP +#define TCP9 -using System; -using System.Text; -using Exomia.Network; #if TCP using Exomia.Network.TCP; - #else using Exomia.Network.UDP; #endif +using System; +using System.Text; +using Exomia.Network; namespace Example.Server { @@ -45,8 +44,7 @@ private static void Main(string[] args) 45, (server1, client, data, responseid) => { string request = (string)data; - - //Console.WriteLine($"Request: {request}"); + Console.WriteLine($"Request: {request}"); byte[] buffer = Encoding.UTF8.GetBytes(DateTime.Now.ToLongDateString()); server1.SendTo(client, 45, buffer, 0, buffer.Length, responseid); return true; @@ -66,14 +64,14 @@ class Server : TcpServerEapBase class Server : UdpServerEapBase #endif { + public Server(ushort expectedMaxClient = 32, ushort expectedMaxPayloadSize = 512) + : base(expectedMaxClient, expectedMaxPayloadSize) { } + protected override bool CreateServerClient(out ServerClient serverClient) { serverClient = new ServerClient(); return true; } - - public Server(ushort expectedMaxClient = 32, ushort expectedMaxPayloadSize = 8096) - : base(expectedMaxClient, expectedMaxPayloadSize) { } } #if TCP diff --git a/Exomia.Network/ClientBase.cs b/Exomia.Network/ClientBase.cs index 36932ab..e7f2473 100644 --- a/Exomia.Network/ClientBase.cs +++ b/Exomia.Network/ClientBase.cs @@ -116,6 +116,11 @@ public abstract class ClientBase : IClient /// private readonly Dictionary> _taskCompletionSources; + /// + /// The listener count. + /// + private readonly byte _listenerCount; + /// /// The data received callbacks lock. /// @@ -176,8 +181,9 @@ public string ServerAddress /// /// Initializes a new instance of the class. /// - private protected ClientBase() + private protected ClientBase(byte listenerCount = 1) { + _listenerCount = listenerCount; _clientSocket = null; _dataReceivedCallbacks = new Dictionary(INITIAL_QUEUE_SIZE); _taskCompletionSources = @@ -224,7 +230,10 @@ public bool Connect(IPAddress[] ipAddresses, int port, int timeout = 10) if (result) { _state = RECEIVE_FLAG | SEND_FLAG; - ReceiveAsync(); + for (int i = 0; i < _listenerCount; i++) + { + ReceiveAsync(); + } if (SendConnect() == SendError.None) { _port = port; @@ -320,17 +329,11 @@ private protected void Disconnect(DisconnectReason reason) /// /// Deserialize data. /// - /// command id. - /// The data. - /// The offset. - /// The length. - /// The responseID. - private protected unsafe void DeserializeData(uint commandID, - byte[] data, - int offset, - int length, - uint responseID) + /// Information describing the deserialize packet. + private protected unsafe void DeserializeData(in DeserializePacketInfo deserializePacketInfo) { + uint commandID = deserializePacketInfo.CommandID; + uint responseID = deserializePacketInfo.ResponseID; if (responseID != 0) { TaskCompletionSource cs; @@ -348,9 +351,9 @@ private protected unsafe void DeserializeData(uint commandID, if (lockTaken) { _lockTaskCompletionSources.Exit(false); } } if (cs != null && !cs.TrySetResult( - new Packet(data, offset, length))) + new Packet(deserializePacketInfo.Data, 0, deserializePacketInfo.Length))) { - ByteArrayPool.Return(data); + ByteArrayPool.Return(deserializePacketInfo.Data); } return; } @@ -359,16 +362,16 @@ private protected unsafe void DeserializeData(uint commandID, case CommandID.PING: { PingPacket pingStruct; - fixed (byte* ptr = data) + fixed (byte* ptr = deserializePacketInfo.Data) { - pingStruct = *(PingPacket*)(ptr + offset); + pingStruct = *(PingPacket*)ptr; } Ping?.Invoke(pingStruct); break; } case CommandID.CONNECT: { - data.FromBytesUnsafe(offset, out ConnectPacket connectPacket); + deserializePacketInfo.Data.FromBytesUnsafe(out ConnectPacket connectPacket); fixed (byte* ptr = _connectChecksum) { if (SequenceEqual(connectPacket.Checksum, ptr, 16)) @@ -383,12 +386,12 @@ private protected unsafe void DeserializeData(uint commandID, if (commandID <= Constants.USER_COMMAND_LIMIT && _dataReceivedCallbacks.TryGetValue(commandID, out ClientEventEntry cee)) { - Packet packet = new Packet(data, offset, length); + Packet packet = new Packet(deserializePacketInfo.Data, 0, deserializePacketInfo.Length); ThreadPool.QueueUserWorkItem( x => { object res = cee._deserialize(in packet); - ByteArrayPool.Return(data); + ByteArrayPool.Return(packet.Buffer); if (res != null) { cee.Raise(this, res); } }); @@ -397,7 +400,7 @@ private protected unsafe void DeserializeData(uint commandID, break; } } - ByteArrayPool.Return(data); + ByteArrayPool.Return(deserializePacketInfo.Data); } #region Add & Remove diff --git a/Exomia.Network/Constants.cs b/Exomia.Network/Constants.cs index e424ace..e77263f 100644 --- a/Exomia.Network/Constants.cs +++ b/Exomia.Network/Constants.cs @@ -33,7 +33,7 @@ static class Constants /// /// The TCP maximum payload size. /// - internal const ushort TCP_PAYLOAD_SIZE_MAX = ushort.MaxValue - TCP_HEADER_OFFSET - 1 - 8189; + internal const ushort TCP_PAYLOAD_SIZE_MAX = 65535 - TCP_HEADER_OFFSET - 1 - 8189; /// /// Size of the UDP header. @@ -48,7 +48,7 @@ static class Constants /// /// The UDP maximum payload size. /// - internal const ushort UDP_PAYLOAD_SIZE_MAX = ushort.MaxValue - UDP_HEADER_OFFSET; + internal const ushort UDP_PAYLOAD_SIZE_MAX = 65507 - UDP_HEADER_OFFSET; /// /// The user command limit. diff --git a/Exomia.Network/DeserializePacketInfo.cs b/Exomia.Network/DeserializePacketInfo.cs new file mode 100644 index 0000000..86ab737 --- /dev/null +++ b/Exomia.Network/DeserializePacketInfo.cs @@ -0,0 +1,38 @@ +#region License + +// Copyright (c) 2018-2019, exomia +// All rights reserved. +// +// This source code is licensed under the BSD-style license found in the +// LICENSE file in the root directory of this source tree. + +#endregion + +namespace Exomia.Network +{ + /// + /// Information about the deserialize packet. + /// + struct DeserializePacketInfo + { + /// + /// Identifier for the command. + /// + public uint CommandID; + + /// + /// Identifier for the response. + /// + public uint ResponseID; + + /// + /// The data. + /// + public byte[] Data; + + /// + /// The length. + /// + public int Length; + } +} \ No newline at end of file diff --git a/Exomia.Network/Exomia.Network.csproj b/Exomia.Network/Exomia.Network.csproj index 247b182..6be47ad 100644 --- a/Exomia.Network/Exomia.Network.csproj +++ b/Exomia.Network/Exomia.Network.csproj @@ -4,7 +4,7 @@ exomia tcp / udp client and server Copyright © $([System.DateTime]::Now.Year) exomia - 1.6.0.0 + 1.6.1.0 https://raw.githubusercontent.com/exomia/network/master/LICENSE https://github.com/exomia/network true diff --git a/Exomia.Network/PacketInfo.cs b/Exomia.Network/PacketInfo.cs index 71240d0..0778374 100644 --- a/Exomia.Network/PacketInfo.cs +++ b/Exomia.Network/PacketInfo.cs @@ -10,17 +10,59 @@ namespace Exomia.Network { + /// + /// Information about the packet. + /// unsafe struct PacketInfo { - public int PacketID; - public uint CommandID; - public uint ResponseID; - public byte* Src; - public int ChunkLength; - public int ChunkOffset; - public int Length; - public bool IsChunked; + /// + /// Identifier for the packet. + /// + public int PacketID; + + /// + /// Identifier for the command. + /// + public uint CommandID; + + /// + /// Identifier for the response. + /// + public uint ResponseID; + + /// + /// Source for the. + /// + public byte* Src; + + /// + /// Length of the chunk. + /// + public int ChunkLength; + + /// + /// The chunk offset. + /// + public int ChunkOffset; + + /// + /// The length. + /// + public int Length; + + /// + /// True if this object is chunked. + /// + public bool IsChunked; + + /// + /// The compression mode. + /// public CompressionMode CompressionMode; - public int CompressedLength; + + /// + /// Length of the compressed. + /// + public int CompressedLength; } } \ No newline at end of file diff --git a/Exomia.Network/Serialization/Serialization.Tcp.cs b/Exomia.Network/Serialization/Serialization.Tcp.cs index bca7c07..09beb8f 100644 --- a/Exomia.Network/Serialization/Serialization.Tcp.cs +++ b/Exomia.Network/Serialization/Serialization.Tcp.cs @@ -96,38 +96,37 @@ internal static int SerializeTcp(in PacketInfo packetInfo, return Constants.TCP_HEADER_SIZE + offset + l + 1; } - internal static bool DeserializeTcp(CircularBuffer circularBuffer, - byte[] bufferWrite, - byte[] bufferRead, - int bytesTransferred, - BigDataHandler bigDataHandler, - out uint commandID, - out uint responseID, - out byte[] data, - out int dataLength) + internal static bool DeserializeTcp(CircularBuffer circularBuffer, + byte[] bufferWrite, + byte[] bufferRead, + int bytesTransferred, + BigDataHandler bigDataHandler, + out DeserializePacketInfo deserializePacketInfo) { int size = circularBuffer.Write(bufferWrite, 0, bytesTransferred); while (circularBuffer.PeekHeader( - 0, out byte packetHeader, out commandID, out dataLength, out ushort checksum) - && dataLength <= circularBuffer.Count - Constants.TCP_HEADER_SIZE) + 0, out byte packetHeader, out deserializePacketInfo.CommandID, out deserializePacketInfo.Length, + out ushort checksum) + && deserializePacketInfo.Length <= circularBuffer.Count - Constants.TCP_HEADER_SIZE) { - if (circularBuffer.PeekByte((Constants.TCP_HEADER_SIZE + dataLength) - 1, out byte b) && + if (circularBuffer.PeekByte( + (Constants.TCP_HEADER_SIZE + deserializePacketInfo.Length) - 1, out byte b) && b == Constants.ZERO_BYTE) { fixed (byte* ptr = bufferRead) { - circularBuffer.Read(ptr, dataLength, Constants.TCP_HEADER_SIZE); + circularBuffer.Read(ptr, deserializePacketInfo.Length, Constants.TCP_HEADER_SIZE); if (size < bytesTransferred) { circularBuffer.Write(bufferWrite, size, bytesTransferred - size); } - responseID = 0; + deserializePacketInfo.ResponseID = 0; int offset = 0; if ((packetHeader & Constants.RESPONSE_BIT_MASK) != 0) { - responseID = *(uint*)(ptr + offset); - offset = 4; + deserializePacketInfo.ResponseID = *(uint*)(ptr + offset); + offset = 4; } int l = 0; @@ -151,26 +150,34 @@ internal static bool DeserializeTcp(CircularBuffer circularBuffer, offset += 12; } - fixed (byte* dst = data = ByteArrayPool.Rent(dataLength)) + fixed (byte* dst = + deserializePacketInfo.Data = ByteArrayPool.Rent(deserializePacketInfo.Length)) { if (PayloadEncoding.Decode( - ptr + offset, dataLength - offset - 1, dst, out dataLength) == checksum) + ptr + offset, deserializePacketInfo.Length - offset - 1, dst, + out deserializePacketInfo.Length) == checksum) { if ((packetHeader & Constants.IS_CHUNKED_1_BIT) != 0) { - data = bigDataHandler.Receive(packetId, dst, dataLength, chunkOffset, cl); - dataLength = cl; - if (data != null) + deserializePacketInfo.Data = bigDataHandler.Receive( + packetId, dst, deserializePacketInfo.Length, chunkOffset, cl); + deserializePacketInfo.Length = cl; + if (deserializePacketInfo.Data != null) { switch (compressionMode) { case CompressionMode.Lz4: byte[] buffer = ByteArrayPool.Rent(l); - dataLength = LZ4Codec.Decode(data, 0, dataLength, buffer, 0, l); - if (dataLength != l) { throw new Exception("LZ4.Decode FAILED!"); } - ByteArrayPool.Return(data); - data = buffer; - dataLength = l; + deserializePacketInfo.Length = LZ4Codec.Decode( + deserializePacketInfo.Data, 0, deserializePacketInfo.Length, buffer, + 0, l); + if (deserializePacketInfo.Length != l) + { + throw new Exception("LZ4.Decode FAILED!"); + } + ByteArrayPool.Return(deserializePacketInfo.Data); + deserializePacketInfo.Data = buffer; + deserializePacketInfo.Length = l; return true; case CompressionMode.None: return true; @@ -190,8 +197,12 @@ internal static bool DeserializeTcp(CircularBuffer circularBuffer, byte[] buffer = ByteArrayPool.Rent(l); fixed (byte* bPtr = buffer) { - dataLength = LZ4Codec.Decode(dst, dataLength, bPtr, l); - if (dataLength != l) { throw new Exception("LZ4.Decode FAILED!"); } + deserializePacketInfo.Length = LZ4Codec.Decode( + dst, deserializePacketInfo.Length, bPtr, l); + if (deserializePacketInfo.Length != l) + { + throw new Exception("LZ4.Decode FAILED!"); + } } return true; default: @@ -210,8 +221,8 @@ internal static bool DeserializeTcp(CircularBuffer circularBuffer, } if (!skipped && !circularBuffer.SkipUntil(0, Constants.ZERO_BYTE)) { break; } } - data = null; - responseID = 0; + deserializePacketInfo.Data = null; + deserializePacketInfo.ResponseID = 0; return false; } } diff --git a/Exomia.Network/Serialization/Serialization.Udp.cs b/Exomia.Network/Serialization/Serialization.Udp.cs index 5069540..3eed811 100644 --- a/Exomia.Network/Serialization/Serialization.Udp.cs +++ b/Exomia.Network/Serialization/Serialization.Udp.cs @@ -87,29 +87,26 @@ internal static int SerializeUdp(in PacketInfo packetInfo, return Constants.UDP_HEADER_SIZE + offset + packetInfo.ChunkLength; } - internal static bool DeserializeUdp(byte[] buffer, - int bytesTransferred, - BigDataHandler bigDataHandler, - out uint commandID, - out uint responseID, - out byte[] data, - out int dataLength) + internal static bool DeserializeUdp(byte[] buffer, + int bytesTransferred, + BigDataHandler bigDataHandler, + out DeserializePacketInfo deserializePacketInfo) { fixed (byte* src = buffer) { byte packetHeader = *src; uint h2 = *(uint*)(src + 1); - commandID = h2 >> Constants.COMMAND_ID_SHIFT; - dataLength = (int)(h2 & Constants.DATA_LENGTH_MASK); - responseID = 0; + deserializePacketInfo.CommandID = h2 >> Constants.COMMAND_ID_SHIFT; + deserializePacketInfo.Length = (int)(h2 & Constants.DATA_LENGTH_MASK); + deserializePacketInfo.ResponseID = 0; - if (bytesTransferred == dataLength + Constants.UDP_HEADER_SIZE) + if (bytesTransferred == deserializePacketInfo.Length + Constants.UDP_HEADER_SIZE) { int offset = 0; if ((packetHeader & Constants.RESPONSE_BIT_MASK) != 0) { - responseID = *(uint*)(src + Constants.UDP_HEADER_SIZE); - offset = 4; + deserializePacketInfo.ResponseID = *(uint*)(src + Constants.UDP_HEADER_SIZE); + offset = 4; } int l = 0; @@ -126,24 +123,28 @@ internal static bool DeserializeUdp(byte[] buffer, int cl = *(int*)(src + Constants.UDP_HEADER_SIZE + offset + 8); byte[] bdb = bigDataHandler.Receive( *(int*)(src + Constants.UDP_HEADER_SIZE + offset), - src + Constants.UDP_HEADER_SIZE + offset + 12, dataLength - offset - 12, + src + Constants.UDP_HEADER_SIZE + offset + 12, deserializePacketInfo.Length - offset - 12, *(int*)(src + Constants.UDP_HEADER_SIZE + offset + 4), cl); - dataLength = cl; + deserializePacketInfo.Length = cl; if (bdb != null) { switch (compressionMode) { case CompressionMode.Lz4: fixed (byte* srcB = bdb) - fixed (byte* dst = data = ByteArrayPool.Rent(l)) + fixed (byte* dst = deserializePacketInfo.Data = ByteArrayPool.Rent(l)) { - dataLength = LZ4Codec.Decode(srcB, dataLength, dst, l); - if (dataLength != l) { throw new Exception("LZ4.Decode FAILED!"); } + deserializePacketInfo.Length = LZ4Codec.Decode( + srcB, deserializePacketInfo.Length, dst, l); + if (deserializePacketInfo.Length != l) + { + throw new Exception("LZ4.Decode FAILED!"); + } } return true; case CompressionMode.None: - data = bdb; + deserializePacketInfo.Data = bdb; return true; default: throw new ArgumentOutOfRangeException( @@ -153,21 +154,26 @@ internal static bool DeserializeUdp(byte[] buffer, } else { - dataLength -= offset; + deserializePacketInfo.Length -= offset; switch (compressionMode) { case CompressionMode.None: - fixed (byte* dst = data = ByteArrayPool.Rent(dataLength)) + fixed (byte* dst = deserializePacketInfo.Data = + ByteArrayPool.Rent(deserializePacketInfo.Length)) { - Mem.Cpy(dst, src + Constants.UDP_HEADER_SIZE + offset, dataLength); + Mem.Cpy( + dst, src + Constants.UDP_HEADER_SIZE + offset, deserializePacketInfo.Length); } return true; case CompressionMode.Lz4: - fixed (byte* dst = data = ByteArrayPool.Rent(l)) + fixed (byte* dst = deserializePacketInfo.Data = ByteArrayPool.Rent(l)) { - dataLength = LZ4Codec.Decode( - src + Constants.UDP_HEADER_SIZE + offset, dataLength, dst, l); - if (dataLength != l) { throw new Exception("LZ4.Decode FAILED!"); } + deserializePacketInfo.Length = LZ4Codec.Decode( + src + Constants.UDP_HEADER_SIZE + offset, deserializePacketInfo.Length, dst, l); + if (deserializePacketInfo.Length != l) + { + throw new Exception("LZ4.Decode FAILED!"); + } } return true; default: @@ -177,7 +183,7 @@ internal static bool DeserializeUdp(byte[] buffer, } } } - data = null; + deserializePacketInfo.Data = null; return false; } } diff --git a/Exomia.Network/ServerBase.cs b/Exomia.Network/ServerBase.cs index 5a37fce..c9aefb4 100644 --- a/Exomia.Network/ServerBase.cs +++ b/Exomia.Network/ServerBase.cs @@ -119,6 +119,11 @@ public event ClientCommandDataReceivedHandler ClientDataReceived /// private readonly Event> _clientDataReceived; + /// + /// The listener count. + /// + private readonly byte _listenerCount; + /// /// The clients lock. /// @@ -158,8 +163,10 @@ public int Port /// /// Initializes a new instance of the class. /// - private protected ServerBase() + /// (Optional) The listener count. + private protected ServerBase(byte listenerCount = 1) { + _listenerCount = listenerCount; _dataReceivedCallbacks = new Dictionary>(INITIAL_QUEUE_SIZE); _clients = new Dictionary(INITIAL_CLIENT_QUEUE_SIZE); @@ -195,7 +202,10 @@ public bool Run(int port) { _port = port; _state = RECEIVE_FLAG | SEND_FLAG; - ListenAsync(); + for (int i = 0; i < _listenerCount; i++) + { + ListenAsync(); + } return _isRunning = true; } return false; @@ -219,30 +229,30 @@ public bool Run(int port) /// /// Deserialize data. /// - /// Socket|Endpoint. - /// Identifier for the command. - /// The data. - /// The offset. - /// The length. - /// Identifier for the response. - private protected void DeserializeData(T arg0, - uint commandID, - byte[] data, - int offset, - int length, - uint responseID) + /// Socket|Endpoint. + /// Information describing the deserialize packet. + private protected void DeserializeData(T arg0, + in DeserializePacketInfo deserializePacketInfo) { + uint commandID = deserializePacketInfo.CommandID; + uint responseID = deserializePacketInfo.ResponseID; switch (commandID) { case CommandID.PING: { - SendTo(arg0, CommandID.PING, data, offset, length, responseID); + SendTo( + arg0, CommandID.PING, + deserializePacketInfo.Data, 0, deserializePacketInfo.Length, + responseID); break; } case CommandID.CONNECT: { InvokeClientConnected(arg0); - SendTo(arg0, CommandID.CONNECT, data, offset, length, responseID); + SendTo( + arg0, CommandID.CONNECT, + deserializePacketInfo.Data, 0, deserializePacketInfo.Length, + responseID); break; } case CommandID.DISCONNECT: @@ -263,19 +273,19 @@ private protected void DeserializeData(T arg0, { sClient.SetLastReceivedPacketTimeStamp(); - Packet packet = new Packet(data, offset, length); + Packet packet = new Packet(deserializePacketInfo.Data, 0, deserializePacketInfo.Length); ThreadPool.QueueUserWorkItem( x => { object res = scee._deserialize(in packet); - ByteArrayPool.Return(data); + ByteArrayPool.Return(packet.Buffer); if (res != null) { for (int i = _clientDataReceived.Count - 1; i >= 0; --i) { _clientDataReceived[i] - .Invoke(this, sClient, commandID, data, responseID); + .Invoke(this, sClient, commandID, res, responseID); } scee.Raise(this, sClient, res, responseID); } @@ -286,7 +296,7 @@ private protected void DeserializeData(T arg0, break; } } - ByteArrayPool.Return(data); + ByteArrayPool.Return(deserializePacketInfo.Data); } /// diff --git a/Exomia.Network/TCP/TcpClientApm.cs b/Exomia.Network/TCP/TcpClientApm.cs index 3b0e9b3..fe6c468 100644 --- a/Exomia.Network/TCP/TcpClientApm.cs +++ b/Exomia.Network/TCP/TcpClientApm.cs @@ -141,10 +141,10 @@ private void ReceiveAsyncCallback(IAsyncResult iar) if (Serialization.Serialization.DeserializeTcp( _circularBuffer, _bufferWrite, _bufferRead, bytesTransferred, _bigDataHandler, - out uint commandID, out uint responseID, out byte[] data, out int dataLength)) + out DeserializePacketInfo deserializePacketInfo)) { ReceiveAsync(); - DeserializeData(commandID, data, 0, dataLength, responseID); + DeserializeData(in deserializePacketInfo); return; } diff --git a/Exomia.Network/TCP/TcpClientBase.cs b/Exomia.Network/TCP/TcpClientBase.cs index a139376..d994730 100644 --- a/Exomia.Network/TCP/TcpClientBase.cs +++ b/Exomia.Network/TCP/TcpClientBase.cs @@ -38,7 +38,7 @@ private protected override ushort MaxPayloadSize /// Initializes a new instance of the class. /// /// (Optional) Size of the expected maximum payload. - protected TcpClientBase(ushort expectedMaxPayloadSize = Constants.TCP_PAYLOAD_SIZE_MAX) + private protected TcpClientBase(ushort expectedMaxPayloadSize = Constants.TCP_PAYLOAD_SIZE_MAX) { _maxPayloadSize = expectedMaxPayloadSize > 0 && expectedMaxPayloadSize < Constants.TCP_PAYLOAD_SIZE_MAX ? expectedMaxPayloadSize diff --git a/Exomia.Network/TCP/TcpClientEap.cs b/Exomia.Network/TCP/TcpClientEap.cs index cd2c443..d5da9a8 100644 --- a/Exomia.Network/TCP/TcpClientEap.cs +++ b/Exomia.Network/TCP/TcpClientEap.cs @@ -147,10 +147,10 @@ private void ReceiveAsyncCompleted(object sender, SocketAsyncEventArgs e) if (Serialization.Serialization.DeserializeTcp( _circularBuffer, e.Buffer, _bufferRead, bytesTransferred, _bigDataHandler, - out uint commandID, out uint responseID, out byte[] data, out int dataLength)) + out DeserializePacketInfo deserializePacketInfo)) { ReceiveAsync(); - DeserializeData(commandID, data, 0, dataLength, responseID); + DeserializeData(in deserializePacketInfo); return; } ReceiveAsync(); diff --git a/Exomia.Network/TCP/TcpServerApmBase.cs b/Exomia.Network/TCP/TcpServerApmBase.cs index ee9f90d..c00a1e3 100644 --- a/Exomia.Network/TCP/TcpServerApmBase.cs +++ b/Exomia.Network/TCP/TcpServerApmBase.cs @@ -193,11 +193,10 @@ private void ReceiveDataCallback(IAsyncResult iar) if (Serialization.Serialization.DeserializeTcp( state.CircularBuffer, state.BufferWrite, state.BufferRead, bytesTransferred, - _bigDataHandler, - out uint commandID, out uint responseID, out byte[] data, out int dataLength)) + _bigDataHandler, out DeserializePacketInfo packetInfo)) { ReceiveAsync(state); - DeserializeData(state.Socket, commandID, data, 0, dataLength, responseID); + DeserializeData(state.Socket, in packetInfo); return; } diff --git a/Exomia.Network/TCP/TcpServerBase.cs b/Exomia.Network/TCP/TcpServerBase.cs index 6783974..727d5f3 100644 --- a/Exomia.Network/TCP/TcpServerBase.cs +++ b/Exomia.Network/TCP/TcpServerBase.cs @@ -41,7 +41,7 @@ private protected override ushort MaxPayloadSize /// Initializes a new instance of the class. /// /// (Optional) Size of the expected maximum payload. - protected TcpServerBase(ushort expectedMaxPayloadSize = Constants.TCP_PAYLOAD_SIZE_MAX) + private protected TcpServerBase(ushort expectedMaxPayloadSize = Constants.TCP_PAYLOAD_SIZE_MAX) { _maxPayloadSize = expectedMaxPayloadSize > 0 && expectedMaxPayloadSize < Constants.TCP_PAYLOAD_SIZE_MAX ? expectedMaxPayloadSize diff --git a/Exomia.Network/TCP/TcpServerEapBase.cs b/Exomia.Network/TCP/TcpServerEapBase.cs index 2779c38..62b6d70 100644 --- a/Exomia.Network/TCP/TcpServerEapBase.cs +++ b/Exomia.Network/TCP/TcpServerEapBase.cs @@ -201,10 +201,10 @@ private void ReceiveAsyncCompleted(object sender, SocketAsyncEventArgs e) if (Serialization.Serialization.DeserializeTcp( state.CircularBuffer, e.Buffer, state.BufferRead, bytesTransferred, _bigDataHandler, - out uint commandID, out uint responseID, out byte[] data, out int dataLength)) + out DeserializePacketInfo deserializePacketInfo)) { ReceiveAsync(e); - DeserializeData(e.AcceptSocket, commandID, data, 0, dataLength, responseID); + DeserializeData(e.AcceptSocket, in deserializePacketInfo); return; } diff --git a/Exomia.Network/UDP/UdpClientApm.cs b/Exomia.Network/UDP/UdpClientApm.cs index dd7f5cf..19e93fc 100644 --- a/Exomia.Network/UDP/UdpClientApm.cs +++ b/Exomia.Network/UDP/UdpClientApm.cs @@ -136,9 +136,9 @@ private void ReceiveAsyncCallback(IAsyncResult iar) ClientStateObject state = (ClientStateObject)iar.AsyncState; if (Serialization.Serialization.DeserializeUdp( state.Buffer, bytesTransferred, _bigDataHandler, - out uint commandID, out uint responseID, out byte[] data, out int dataLength)) + out DeserializePacketInfo deserializePacketInfo)) { - DeserializeData(commandID, data, 0, dataLength, responseID); + DeserializeData(in deserializePacketInfo); } _clientStateObjectPool.Return(state); } diff --git a/Exomia.Network/UDP/UdpClientBase.cs b/Exomia.Network/UDP/UdpClientBase.cs index cb5eab0..40c026c 100644 --- a/Exomia.Network/UDP/UdpClientBase.cs +++ b/Exomia.Network/UDP/UdpClientBase.cs @@ -33,6 +33,7 @@ private protected override ushort MaxPayloadSize /// /// (Optional) Size of the expected maximum payload. private protected UdpClientBase(ushort expectedMaxPayloadSize = Constants.UDP_PAYLOAD_SIZE_MAX) + : base(4) { _maxPayloadSize = expectedMaxPayloadSize > 0 && expectedMaxPayloadSize < Constants.UDP_PAYLOAD_SIZE_MAX diff --git a/Exomia.Network/UDP/UdpClientEap.cs b/Exomia.Network/UDP/UdpClientEap.cs index 0fc206c..e639ad2 100644 --- a/Exomia.Network/UDP/UdpClientEap.cs +++ b/Exomia.Network/UDP/UdpClientEap.cs @@ -151,9 +151,9 @@ private void ReceiveAsyncCompleted(object sender, SocketAsyncEventArgs e) if (Serialization.Serialization.DeserializeUdp( e.Buffer, e.BytesTransferred, _bigDataHandler, - out uint commandID, out uint responseID, out byte[] data, out int dataLength)) + out DeserializePacketInfo deserializePacketInfo)) { - DeserializeData(commandID, data, 0, dataLength, responseID); + DeserializeData(in deserializePacketInfo); } } diff --git a/Exomia.Network/UDP/UdpServerApmBase.cs b/Exomia.Network/UDP/UdpServerApmBase.cs index 3d8280d..4b58959 100644 --- a/Exomia.Network/UDP/UdpServerApmBase.cs +++ b/Exomia.Network/UDP/UdpServerApmBase.cs @@ -157,9 +157,9 @@ private void ReceiveDataCallback(IAsyncResult iar) if (Serialization.Serialization.DeserializeUdp( state.Buffer, bytesTransferred, _bigDataHandler, - out uint commandID, out uint responseID, out byte[] data, out int dataLength)) + out DeserializePacketInfo deserializePacketInfo)) { - DeserializeData(state.EndPoint, commandID, data, 0, dataLength, responseID); + DeserializeData(state.EndPoint, in deserializePacketInfo); } _serverClientStateObjectPool.Return(state); diff --git a/Exomia.Network/UDP/UdpServerBase.cs b/Exomia.Network/UDP/UdpServerBase.cs index 96639f2..482dfb4 100644 --- a/Exomia.Network/UDP/UdpServerBase.cs +++ b/Exomia.Network/UDP/UdpServerBase.cs @@ -36,6 +36,7 @@ private protected override ushort MaxPayloadSize /// /// (Optional) Size of the expected maximum payload. private protected UdpServerBase(ushort expectedMaxPayloadSize = Constants.UDP_PAYLOAD_SIZE_MAX) + : base(16) { _maxPayloadSize = expectedMaxPayloadSize > 0 && expectedMaxPayloadSize < Constants.UDP_PAYLOAD_SIZE_MAX diff --git a/Exomia.Network/UDP/UdpServerEapBase.cs b/Exomia.Network/UDP/UdpServerEapBase.cs index 016a04d..24db22a 100644 --- a/Exomia.Network/UDP/UdpServerEapBase.cs +++ b/Exomia.Network/UDP/UdpServerEapBase.cs @@ -160,9 +160,9 @@ private void ReceiveFromAsyncCompleted(object sender, SocketAsyncEventArgs e) if (Serialization.Serialization.DeserializeUdp( e.Buffer, e.BytesTransferred, _bigDataHandler, - out uint commandID, out uint responseID, out byte[] data, out int dataLength)) + out DeserializePacketInfo deserializePacketInfo)) { - DeserializeData(e.RemoteEndPoint, commandID, data, 0, dataLength, responseID); + DeserializeData(e.RemoteEndPoint, in deserializePacketInfo); } _receiveEventArgsPool.Return(e); From 2298639846d43e0a546d92142909ca016ada7d73 Mon Sep 17 00:00:00 2001 From: Daniel Baetz Date: Mon, 5 Aug 2019 17:07:45 +0200 Subject: [PATCH 2/3] v1.6.2.0 --- Exomia.Network/ClientBase.cs | 25 ++++++++++++++++++++++++- Exomia.Network/DataReceivedHandler.cs | 11 +++++++++++ Exomia.Network/Exomia.Network.csproj | 2 +- 3 files changed, 36 insertions(+), 2 deletions(-) diff --git a/Exomia.Network/ClientBase.cs b/Exomia.Network/ClientBase.cs index e7f2473..4e61173 100644 --- a/Exomia.Network/ClientBase.cs +++ b/Exomia.Network/ClientBase.cs @@ -66,6 +66,15 @@ public abstract class ClientBase : IClient /// public event DisconnectedHandler Disconnected; + /// + /// Occurs when data from a client is received. + /// + public event CommandDataReceivedHandler DataReceived + { + add { _dataReceived.Add(value); } + remove { _dataReceived.Remove(value); } + } + /// /// called than a ping is received. /// @@ -121,6 +130,11 @@ public abstract class ClientBase : IClient /// private readonly byte _listenerCount; + /// + /// The client data received event handler. + /// + private readonly Event _dataReceived; + /// /// The data received callbacks lock. /// @@ -192,6 +206,8 @@ private protected ClientBase(byte listenerCount = 1) _lockTaskCompletionSources = new SpinLock(Debugger.IsAttached); _dataReceivedCallbacksLock = new SpinLock(Debugger.IsAttached); + _dataReceived = new Event(); + _responseID = 1; _bigDataHandler = new BigDataHandler(); @@ -393,7 +409,14 @@ private protected unsafe void DeserializeData(in DeserializePacketInfo deseriali object res = cee._deserialize(in packet); ByteArrayPool.Return(packet.Buffer); - if (res != null) { cee.Raise(this, res); } + if (res != null) + { + for (int i = _dataReceived.Count - 1; i >= 0; --i) + { + _dataReceived[i].Invoke(this, commandID, res); + } + cee.Raise(this, res); + } }); return; } diff --git a/Exomia.Network/DataReceivedHandler.cs b/Exomia.Network/DataReceivedHandler.cs index eeb5216..b6324ac 100644 --- a/Exomia.Network/DataReceivedHandler.cs +++ b/Exomia.Network/DataReceivedHandler.cs @@ -10,6 +10,17 @@ namespace Exomia.Network { + /// + /// Called than a client received data from the server. + /// + /// The client. + /// Identifier for the command. + /// The data. + /// + /// A bool. + /// + public delegate bool CommandDataReceivedHandler(IClient client,uint commandID, object data); + /// /// Called than a client received data from the server. /// diff --git a/Exomia.Network/Exomia.Network.csproj b/Exomia.Network/Exomia.Network.csproj index 6be47ad..f105ef0 100644 --- a/Exomia.Network/Exomia.Network.csproj +++ b/Exomia.Network/Exomia.Network.csproj @@ -4,7 +4,7 @@ exomia tcp / udp client and server Copyright © $([System.DateTime]::Now.Year) exomia - 1.6.1.0 + 1.6.2.0 https://raw.githubusercontent.com/exomia/network/master/LICENSE https://github.com/exomia/network true From 5b54a1965d356bb26f04e60cb31b4b70e5ec9a17 Mon Sep 17 00:00:00 2001 From: Daniel Baetz Date: Mon, 5 Aug 2019 17:08:30 +0200 Subject: [PATCH 3/3] updated wiki --- network.wiki | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/network.wiki b/network.wiki index 6619fed..082c608 160000 --- a/network.wiki +++ b/network.wiki @@ -1 +1 @@ -Subproject commit 6619fed1b6600e9c16766a40da5a0aedc0970a63 +Subproject commit 082c608e0a5fa69bf2b01742c822b6fe4e6a475c