mirror of
https://github.com/Kaveinator/NetickProForUnity.git
synced 2025-10-26 09:49:06 -07:00
Improved LiteNetLib transport performance by removing two needless data copies when sending and receiving a packet.
This commit is contained in:
@@ -6,7 +6,7 @@
|
||||
[assembly: AssemblyConfiguration("")]
|
||||
[assembly: AssemblyCompany("Karrar Rahim")]
|
||||
[assembly: AssemblyProduct("Netick")]
|
||||
[assembly: AssemblyCopyright("Karrar Rahim 2023")]
|
||||
[assembly: AssemblyCopyright("Karrar Rahim 2025")]
|
||||
[assembly: AssemblyTrademark("")]
|
||||
[assembly: AssemblyCulture("")]
|
||||
#endif
|
||||
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -1,13 +1,11 @@
|
||||
using LiteNetLib;
|
||||
using LiteNetLib.Utils;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using UnityEngine;
|
||||
using System.Net;
|
||||
using System.Net.Sockets;
|
||||
using System;
|
||||
using Netick.Unity;
|
||||
using UnityEngine.UIElements;
|
||||
|
||||
namespace Netick.Transport
|
||||
{
|
||||
@@ -22,7 +20,6 @@ namespace Netick.Transport
|
||||
public int MaxConnectAttempts = 10;
|
||||
[Tooltip("LiteNetLib internal logic update interval (in seconds).")]
|
||||
public float UpdateInterval = 0.015f;
|
||||
|
||||
public override NetworkTransport MakeTransportInstance() => new LiteNetLibTransport(this);
|
||||
}
|
||||
|
||||
@@ -33,50 +30,23 @@ namespace Netick.Transport
|
||||
public LiteNetLibTransport Transport;
|
||||
public NetPeer LNLPeer;
|
||||
public override IEndPoint EndPoint => LNLPeer.EndPoint.ToNetickEndPoint();
|
||||
|
||||
public override int Mtu => LNLPeer.Mtu;
|
||||
|
||||
public LNLConnection(LiteNetLibTransport transport)
|
||||
{
|
||||
Transport = transport;
|
||||
}
|
||||
|
||||
public unsafe override void Send(IntPtr ptr, int length)
|
||||
{
|
||||
SendLNL((byte*)ptr.ToPointer(), length, DeliveryMethod.Unreliable);
|
||||
}
|
||||
|
||||
public unsafe override void SendUserData(IntPtr ptr, int length, TransportDeliveryMethod transportDeliveryMethod)
|
||||
{
|
||||
SendLNL((byte*)ptr.ToPointer(), length, transportDeliveryMethod == TransportDeliveryMethod.Reliable ? DeliveryMethod.ReliableOrdered : DeliveryMethod.Unreliable);
|
||||
}
|
||||
|
||||
private unsafe void SendLNL(byte* ptr, int length, DeliveryMethod deliveryMethod)
|
||||
{
|
||||
if (Transport._bytes.Length < length)
|
||||
Transport._bytes = new byte[length];
|
||||
|
||||
for (int i = 0; i < length; i++)
|
||||
Transport._bytes[i] = ptr[i];
|
||||
LNLPeer.Send(Transport._bytes, 0, length, deliveryMethod);
|
||||
}
|
||||
public unsafe override void Send(IntPtr ptr, int length) => LNLPeer.Send(new ReadOnlySpan<byte>(ptr.ToPointer(), length), DeliveryMethod.Unreliable);
|
||||
public unsafe override void SendUserData(IntPtr ptr, int length, TransportDeliveryMethod method) => LNLPeer.Send(new ReadOnlySpan<byte>(ptr.ToPointer(), length), method == TransportDeliveryMethod.Unreliable ? DeliveryMethod.Unreliable : DeliveryMethod.ReliableOrdered);
|
||||
}
|
||||
|
||||
private LiteNetLibTransportProvider _provider;
|
||||
private NetManager _netManager;
|
||||
private BitBuffer _buffer;
|
||||
|
||||
private byte[] _bytes = new byte[2048];
|
||||
private readonly byte[] _connectionBytes = new byte[200];
|
||||
|
||||
private int _port;
|
||||
private Dictionary<NetPeer, LNLConnection> _clients = new();
|
||||
private Queue<LNLConnection> _freeClients = new();
|
||||
|
||||
// LAN Discovery
|
||||
private List<Session> _sessions = new();
|
||||
private NetDataWriter _writer = new NetDataWriter();
|
||||
private string _machineName;
|
||||
private BitBuffer _buffer;
|
||||
private byte[] _connectionBytes = new byte[200];
|
||||
private int _port;
|
||||
private Dictionary<NetPeer, LNLConnection> _clients;
|
||||
private Queue<LNLConnection> _freeClients;
|
||||
|
||||
public LiteNetLibTransport(LiteNetLibTransportProvider provider)
|
||||
{
|
||||
@@ -85,9 +55,10 @@ namespace Netick.Transport
|
||||
|
||||
public override void Init()
|
||||
{
|
||||
_clients = new(Engine.Config.MaxPlayers);
|
||||
_freeClients = new(Engine.Config.MaxPlayers);
|
||||
_buffer = new BitBuffer(createChunks: false);
|
||||
_netManager = new NetManager((INetEventListener)this) { AutoRecycle = true };
|
||||
_machineName = Environment.MachineName;
|
||||
_netManager = new NetManager(this) { AutoRecycle = true };
|
||||
_netManager.DisconnectTimeout = (int)(_provider.DisconnectTimeout * 1000);
|
||||
_netManager.ReconnectDelay = (int)(_provider.ReconnectInterval * 1000);
|
||||
_netManager.MaxConnectAttempts = _provider.MaxConnectAttempts;
|
||||
@@ -97,31 +68,23 @@ namespace Netick.Transport
|
||||
_freeClients.Enqueue(new LNLConnection(this));
|
||||
}
|
||||
|
||||
public override void PollEvents()
|
||||
{
|
||||
_netManager.PollEvents();
|
||||
}
|
||||
|
||||
public override void ForceUpdate()
|
||||
{
|
||||
_netManager.TriggerUpdate();
|
||||
}
|
||||
public override void PollEvents() => _netManager.PollEvents();
|
||||
public override void ForceUpdate() => _netManager.TriggerUpdate();
|
||||
|
||||
public override void Run(RunMode mode, int port)
|
||||
{
|
||||
_port = port;
|
||||
|
||||
if (mode == RunMode.Client)
|
||||
{
|
||||
_netManager.UnconnectedMessagesEnabled = true;
|
||||
_netManager.Start();
|
||||
}
|
||||
|
||||
else
|
||||
{
|
||||
_netManager.BroadcastReceiveEnabled = true;
|
||||
_netManager.Start(port);
|
||||
}
|
||||
|
||||
_port = port;
|
||||
}
|
||||
|
||||
public override void Shutdown()
|
||||
@@ -135,9 +98,7 @@ namespace Netick.Transport
|
||||
_netManager.Start();
|
||||
|
||||
if (connectionData == null)
|
||||
{
|
||||
_netManager.Connect(address, port, "");
|
||||
}
|
||||
else
|
||||
{
|
||||
_writer. Reset();
|
||||
@@ -159,9 +120,8 @@ namespace Netick.Transport
|
||||
return;
|
||||
}
|
||||
|
||||
int len = request.Data.AvailableBytes;
|
||||
request.Data.GetBytes(_connectionBytes, 0, len);
|
||||
bool accepted = NetworkPeer.OnConnectRequest(_connectionBytes, len, request.RemoteEndPoint.ToNetickEndPoint());
|
||||
request.Data.GetBytes(_connectionBytes, 0, request.Data.AvailableBytes);
|
||||
bool accepted = NetworkPeer.OnConnectRequest(_connectionBytes, request.Data.AvailableBytes, request.RemoteEndPoint.ToNetickEndPoint());
|
||||
|
||||
if (accepted)
|
||||
request.Accept();
|
||||
@@ -173,9 +133,8 @@ namespace Netick.Transport
|
||||
{
|
||||
var connection = _freeClients.Dequeue();
|
||||
connection.LNLPeer = peer;
|
||||
|
||||
_clients. Add(peer, connection);
|
||||
NetworkPeer.OnConnected(connection);
|
||||
NetworkPeer. OnConnected(connection);
|
||||
}
|
||||
|
||||
void INetEventListener.OnPeerDisconnected(NetPeer peer, DisconnectInfo disconnectInfo)
|
||||
@@ -200,18 +159,14 @@ namespace Netick.Transport
|
||||
NetworkPeer.OnConnectFailed(ConnectionFailedReason.Refused);
|
||||
return;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if (peer == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (_clients.ContainsKey(peer))
|
||||
{
|
||||
TransportDisconnectReason reason = disconnectInfo.Reason == DisconnectReason.Timeout ? TransportDisconnectReason.Timeout : TransportDisconnectReason.Shutdown;
|
||||
|
||||
NetworkPeer. OnDisconnected(_clients[peer], reason);
|
||||
_freeClients.Enqueue(_clients[peer]);
|
||||
_clients. Remove(peer);
|
||||
@@ -220,26 +175,15 @@ namespace Netick.Transport
|
||||
|
||||
unsafe void INetEventListener.OnNetworkReceive(NetPeer peer, NetPacketReader reader, byte channel, DeliveryMethod deliveryMethod)
|
||||
{
|
||||
if (_clients.TryGetValue(peer, out var c))
|
||||
if (!_clients.TryGetValue(peer, out var c))
|
||||
return;
|
||||
|
||||
fixed (byte* ptr = reader.RawData)
|
||||
{
|
||||
var len = reader.AvailableBytes;
|
||||
|
||||
if (_bytes.Length < reader.AvailableBytes)
|
||||
_bytes = new byte[reader.AvailableBytes];
|
||||
|
||||
reader. GetBytes(_bytes, 0, reader.AvailableBytes);
|
||||
|
||||
fixed(byte* ptr = _bytes)
|
||||
{
|
||||
_buffer. SetFrom(ptr, len, _bytes.Length);
|
||||
_buffer. SetFrom(ptr + reader.Position, reader.AvailableBytes, reader.RawData.Length);
|
||||
NetworkPeer.Receive(c, _buffer);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void INetEventListener.OnNetworkReceiveUnconnected(IPEndPoint remoteEndPoint, NetPacketReader reader, UnconnectedMessageType messageType)
|
||||
{
|
||||
}
|
||||
|
||||
void INetEventListener.OnNetworkError(IPEndPoint endPoint, SocketError socketError)
|
||||
{
|
||||
@@ -247,9 +191,8 @@ namespace Netick.Transport
|
||||
NetworkPeer.OnConnectFailed(ConnectionFailedReason.Refused);
|
||||
}
|
||||
|
||||
void INetEventListener.OnNetworkReceiveUnconnected(IPEndPoint remoteEndPoint, NetPacketReader reader, UnconnectedMessageType messageType) { }
|
||||
void INetEventListener.OnNetworkLatencyUpdate(NetPeer peer, int latency) { }
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "com.karrar.netick",
|
||||
"version": "0.12.67",
|
||||
"version": "0.12.68",
|
||||
"displayName": "Netick",
|
||||
"description": "A networking solution for Unity",
|
||||
"unity": "2021.3",
|
||||
|
||||
Reference in New Issue
Block a user