public void SendPacket(IPacket packet, PacketDeliveryMethod method) { #if DEBUG Packets.CheckRegistered(packet); #endif Server.OnLocalPacket(packet); }
public void Update(double t) { elapsed -= t; if (elapsed <= 0.0) { elapsed = sendTime; lock (reliableSend) { while (reliableSend.Count > 0) { var dw = new NetDataWriter(); if (reliableSend.Count > 255) { dw.Put((byte)255); } else { dw.Put((byte)reliableSend.Count); } for (int i = 0; (i < 255 && reliableSend.Count > 0); i++) { Packets.Write(dw, reliableSend.Dequeue()); } Client.Send(dw, DeliveryMethod.ReliableOrdered); } } } }
public void SendPacket(IPacket packet, PacketDeliveryMethod method) { var om = new NetDataWriter(); Packets.Write(om, packet); method.ToLiteNetLib(out DeliveryMethod mt, out byte ch); client.FirstPeer?.Send(om, ch, mt); }
public void SendPacketWithEvent(IPacket packet, Action onAck, PacketDeliveryMethod method) { var m = new NetDataWriter(); m.Put((byte)1); Packets.Write(m, packet); method.ToLiteNetLib(out var mtd, out var channel); Client.SendWithDeliveryEvent(m, channel, mtd, onAck); }
void BeginAuthentication(NetPeer peer) { var msg = new NetDataWriter(); msg.Put((byte)1); Packets.Write(msg, new AuthenticationPacket() { Type = AuthenticationKind.GUID }); peer.Send(msg, DeliveryMethod.ReliableOrdered); peer.Tag = TagConnecting; }
public void SendPacket(IPacket packet, PacketDeliveryMethod method) { method.ToLiteNetLib(out DeliveryMethod mt, out byte ch); if (mt == DeliveryMethod.ReliableOrdered) { lock (reliableLock) { reliableSend.Enqueue(packet); } } else { var m = new NetDataWriter(); m.Put((byte)1); Packets.Write(m, packet); Client.Send(m, ch, mt); } }
void NetworkThread() { sw = Stopwatch.StartNew(); var listener = new EventBasedNetListener(); client = new NetManager(listener) { UnconnectedMessagesEnabled = true, IPv6Enabled = true, NatPunchEnabled = true, ChannelsCount = 3 }; listener.NetworkReceiveUnconnectedEvent += (remote, msg, type) => { if (type == UnconnectedMessageType.Broadcast) { return; } if (msg.GetInt() == 0) { lock (srvinfo) { foreach (var info in srvinfo) { if (info.EndPoint.Equals(remote)) { var t = sw.ElapsedMilliseconds; info.Ping = (int)(t - info.LastPingTime); if (info.Ping < 0) { info.Ping = 0; } } } } } else if (ServerFound != null) { var info = new LocalServerInfo(); info.EndPoint = remote; info.Unique = msg.GetInt(); info.Name = msg.GetString(); info.Description = msg.GetString(); info.DataVersion = msg.GetString(); info.CurrentPlayers = msg.GetInt(); info.MaxPlayers = msg.GetInt(); info.LastPingTime = sw.ElapsedMilliseconds; NetDataWriter writer = new NetDataWriter(); writer.Put(LNetConst.PING_MAGIC); client.SendUnconnectedMessage(writer, remote); lock (srvinfo) { bool add = true; for (int i = 0; i < srvinfo.Count; i++) { if (srvinfo[i].Unique == info.Unique) { add = false; //Prefer IPv6 if (srvinfo[i].EndPoint.AddressFamily != AddressFamily.InterNetwork && info.EndPoint.AddressFamily == AddressFamily.InterNetwork) { srvinfo[i].EndPoint = info.EndPoint; } break; } } if (add) { srvinfo.Add(info); mainThread.QueueUIThread(() => ServerFound?.Invoke(info)); } } } msg.Recycle(); }; listener.NetworkReceiveEvent += (peer, reader, method) => { try { var packetCount = reader.GetByte(); //reliable packets can be merged if (packetCount > 1) { FLLog.Debug("Net", $"Received {packetCount} merged packets"); } for (int i = 0; i < packetCount; i++) { var pkt = Packets.Read(reader); if (connecting) { if (pkt is AuthenticationPacket) { var auth = (AuthenticationPacket)pkt; FLLog.Info("Net", "Authentication Packet Received"); if (auth.Type == AuthenticationKind.Token) { FLLog.Info("Net", "Token"); var str = reader.GetString(); mainThread.QueueUIThread(() => AuthenticationRequired(str)); } else if (auth.Type == AuthenticationKind.GUID) { FLLog.Info("Net", "GUID"); SendPacket(new AuthenticationReplyPacket() { Guid = this.UUID }, PacketDeliveryMethod.ReliableOrdered); } } else if (pkt is LoginSuccessPacket) { FLLog.Info("Client", "Login success"); connecting = false; } else { client.DisconnectAll(); } } else { packets.Enqueue(pkt); } } } catch (Exception e) { FLLog.Error("Client", "Error reading packet"); client.DisconnectAll(); } }; listener.PeerDisconnectedEvent += (peer, info) => { mainThread.QueueUIThread(() => { Disconnected?.Invoke(info.Reason.ToString()); }); }; client.Start(); while (running) { if (Interlocked.Read(ref localPeerRequests) > 0) { Interlocked.Decrement(ref localPeerRequests); var dw = new NetDataWriter(); dw.Put(LNetConst.BROADCAST_KEY); client.SendBroadcast(dw, LNetConst.DEFAULT_PORT); } //ping servers lock (srvinfo) { foreach (var inf in srvinfo) { var nowMs = sw.ElapsedMilliseconds; if (nowMs - inf.LastPingTime > 2000) //ping every 2 seconds? { inf.LastPingTime = nowMs; var om = new NetDataWriter(); om.Put(LNetConst.PING_MAGIC); client.SendUnconnectedMessage(om, inf.EndPoint); } } } //events client.PollEvents(); Thread.Sleep(1); } client.DisconnectAll(); client.Stop(); }
void NetThread() { EventBasedNetListener listener = new EventBasedNetListener(); int unique = Environment.TickCount; listener.ConnectionRequestEvent += request => { if (Server.ConnectedPeersCount > MaxConnections) { request.Reject(); } else { request.AcceptIfKey(AppIdentifier); } }; listener.PeerConnectedEvent += peer => { FLLog.Info("Server", $"Connected: {peer.EndPoint}"); BeginAuthentication(peer); }; listener.PeerDisconnectedEvent += (peer, info) => { FLLog.Info("Server", $"Disconnected: {peer.EndPoint}"); if (peer.Tag is Player player) { player.Disconnected(); lock (game.ConnectedPlayers) { game.ConnectedPlayers.Remove(player); } } }; listener.NetworkReceiveUnconnectedEvent += (point, reader, type) => { try { if (type == UnconnectedMessageType.Broadcast) { if (!reader.TryGetString(out string str)) { return; } if (str != LNetConst.BROADCAST_KEY) { return; } var dw = new NetDataWriter(); dw.Put((int)1); dw.Put(unique); dw.Put(game.ServerName); dw.Put(game.ServerDescription); dw.Put(game.GameData.DataVersion); dw.Put(Server.ConnectedPeersCount); dw.Put(MaxConnections); Server.SendUnconnectedMessage(dw, point); } else if (type == UnconnectedMessageType.BasicMessage) { if (!reader.TryGetUInt(out uint magic)) { return; } if (magic != LNetConst.PING_MAGIC) { return; } var dw = new NetDataWriter(); dw.Put((int)0); Server.SendUnconnectedMessage(dw, point); } } finally { reader.Recycle(); } }; listener.NetworkReceiveEvent += (peer, reader, channel, method) => { try { var pkt = Packets.Read(reader); if (peer.Tag == TagConnecting) { if (pkt is AuthenticationReplyPacket) { var auth = (AuthenticationReplyPacket)pkt; if (auth.Guid == Guid.Empty) { var dw = new NetDataWriter(); dw.Put("bad GUID"); peer.Disconnect(dw); } else { var p = new Player(new RemotePacketClient(peer), game, auth.Guid); peer.Tag = p; Task.Run(() => p.DoAuthSuccess()); lock (game.ConnectedPlayers) { game.ConnectedPlayers.Add(p); } } } else { var dw = new NetDataWriter(); dw.Put("Invalid packet"); peer.Disconnect(dw); } } else { var player = (Player)peer.Tag; //Task.Run(() => player.ProcessPacket(pkt)); player.ProcessPacket(pkt); } } catch (Exception) { throw; var dw = new NetDataWriter(); dw.Put("Packet processing error"); peer.Disconnect(dw); if (peer.Tag is Player p) { p.Disconnected(); } } finally { reader.Recycle(); } }; listener.DeliveryEvent += (peer, data) => { if (data is Action onAck) { onAck(); } }; Server = new NetManager(listener); Server.IPv6Mode = IPv6Mode.SeparateSocket; Server.UnconnectedMessagesEnabled = true; Server.BroadcastReceiveEnabled = true; Server.ChannelsCount = 3; Server.UnsyncedEvents = true; Server.Start(Port); FLLog.Info("Server", "Listening on port " + Port); var sw = Stopwatch.StartNew(); var last = 0.0; ServerLoop sendLoop = null; sendLoop = new ServerLoop((time) => { foreach (var p in Server.ConnectedPeerList) { if (p.Tag is Player player) { (player.Client as RemotePacketClient)?.Update(time.TotalSeconds); } } if (!running) { sendLoop.Stop(); } }); sendLoop.Start(); Server.Stop(); }