コード例 #1
0
 public void AnnounceToAll(EPacket packet, byte[] data, int channel)
 {
     foreach (var c in Clients)
     {
         Send(c.Identity, packet, data, channel);
     }
 }
コード例 #2
0
 public void CloseWrite(string channelName, Identity user, EPacket type)
 {
     if (!type.IsChunk())
     {
         LogUtils.LogNetwork("Error: Failed to stream non chunk: " + type);
     }
     else
     {
         NetworkCallAttribute networkCall;
         var index =
             GetCall(channelName, out networkCall);
         if (index == -1)
         {
             return;
         }
         byte[] buffer;
         GetPacket(type, index, out buffer);
         if (IsOwner && (user == Connection.ClientID))
         {
             Receive(Connection.ClientID, buffer);
         }
         else if (Connection.IsServer() && (user == Connection.ServerID))
         {
             Receive(Connection.ServerID, buffer);
         }
         else
         {
             Connection.Send(user, type, buffer, ID);
         }
     }
 }
コード例 #3
0
        public void Receive(ArraySegment <byte> buffer)
        {
            if (State == EConnectionState.Disconnected)
            {
                return;
            }

            EPacket eType = PacketReader.DecodePacketType(buffer.Array[buffer.Offset]);

            if (eType == EPacket.Persistence)
            {
                GameStatePersistence.Receive(buffer);
            }
            else
            {
                if (m_PackageReader == null)
                {
                    m_PackageReader = new PacketReader();
                }

                Packet packet = m_PackageReader.Read(new ByteReader(buffer));
                if (packet != null)
                {
                    m_PackageReader = null;
                    Dispatcher.Dispatch(State, packet);
                }
            }
        }
コード例 #4
0
        public virtual void Send(Identity receiver, EPacket type, byte[] data, int length, int channel)
        {
            if (receiver == null)
            {
                throw new ArgumentNullException(nameof(receiver));
            }

            if (data == null)
            {
                throw new ArgumentNullException(nameof(data));
            }

            var tmp = data.ToList();

            tmp.Insert(0, type.GetID());
            data    = tmp.ToArray();
            length += 1;

//            if ((IsClient() && receiver == ClientID && ClientID != null) || (IsServer() && receiver == ServerID && ServerID != null))
//            {
//                LogUtils.Debug("Server/Client sending to itself");
//                Receive(receiver, data, length, channel);
//                return;
//            }

            if (!receiver.IsValid())
            {
                LogUtils.LogError("Failed to send to invalid ID.");
                return;
            }

            LogUtils.LogNetwork("Sending packet: " + type + ", receiver: " + receiver + (receiver == ServerID ? " (Server)" : "") + ", ch: " + channel + ", size: " + data.Length);

            SendMethod sendType;

            if (type.IsUnreliable())
            {
                sendType = !type.IsInstant()
                    ? SendMethod.SEND_UNRELIABLE
                    : SendMethod.SEND_UNRELIABLE_NO_DELAY;
            }
            else
            {
                sendType = !type.IsInstant() ?
                           SendMethod.SEND_RELIABLE_WITH_BUFFERING:
                           SendMethod.SEND_RELIABLE;
            }

            if (OnPreSend(receiver, type, data, length, channel))
            {
                return;
            }

            if (!Provider.Write(receiver, data, (ulong)length, sendType, channel))
            {
                LogUtils.LogError("Failed to send data to " + receiver);
            }
        }
コード例 #5
0
ファイル: TestUtils.cs プロジェクト: evorios/BannerlordCoop
        public static ArraySegment <byte> MakeRaw(EPacket eType, byte[] payload)
        {
            Packet       packet = new Packet(eType, payload);
            MemoryStream stream = new MemoryStream();
            BinaryWriter writer = new BinaryWriter(stream);

            new PacketWriter(packet).Write(writer);
            return(stream.ToArray());
        }
コード例 #6
0
 protected override bool OnPreSend(Identity receiver, EPacket type, byte[] data, int length, int channel)
 {
     if (ServerID == ClientID)
     {
         _server.Receive(ServerID, data, length, channel);
         return(true);
     }
     return(false);
 }
コード例 #7
0
        protected override bool OnPreSend(Identity receiver, EPacket type, byte[] data, int length, int channel)
        {
            if (!IsSinglePlayer || receiver != ServerID)
            {
                return(false);
            }

            SinglePlayerConnection.Receive(ServerID, data, length, channel);
            return(true);
        }
コード例 #8
0
 private void GetPacket(EPacket type, int index, out int size, out byte[] packet, byte[] bytes, int length)
 {
     size      = 4 + length;
     packet    = bytes;
     packet[0] = (byte)type;
     packet[1] = (byte)index;
     byte[] buffer = BitConverter.GetBytes((ushort)length);
     packet[2] = buffer[0];
     packet[3] = buffer[1];
 }
コード例 #9
0
        private static void AssertIsPersistencePayload(ArraySegment <byte> buffer)
        {
            if (buffer.Array == null)
            {
                throw new ArgumentNullException(nameof(buffer));
            }

            EPacket eType = PacketReader.DecodePacketType(buffer.Array[buffer.Offset]);

            if (eType != EPacket.Persistence)
            {
                throw new ArgumentException(nameof(buffer));
            }
        }
コード例 #10
0
 public void CloseWrite(string channelName, ECall mode, EPacket type)
 {
     LogUtils.Debug(nameof(CloseWrite) + ": " + channelName);
     if (!type.IsChunk())
     {
         LogUtils.LogNetwork("Error: Failed to stream non chunk: " + type);
     }
     else
     {
         NetworkCallAttribute networkCall;
         var index =
             GetCall(channelName, out networkCall);
         if (index == -1)
         {
             return;
         }
         byte[] buffer;
         GetPacket(type, index, out buffer);
         Send(mode, type, buffer);
     }
 }
コード例 #11
0
        /// <summary>
        ///     Reads a <see cref="Packet" /> from the given reader. Returns null if the packet is fragmented and
        ///     parts are still missing.
        /// </summary>
        /// <param name="reader"></param>
        /// <returns>Serialized packet or null if the packet is fragmented and not yet complete.</returns>
        public Packet Read(ByteReader reader)
        {
            // 1 Byte header
            byte    header = reader.Binary.ReadByte();
            EPacket eType  = DecodePacketType(header);

            // 4 Bytes size of payload
            int iPayloadSize = reader.Binary.ReadInt32();

            // handle fragmented packages
            if ((header & Packet.BitMaskFragment_More) != Packet.BitMaskFragment_None)
            {
                if (m_FragmentedBuffer == null)
                {
                    m_FragmentedStream = new MemoryStream();
                    m_FragmentedBuffer = new BinaryWriter(m_FragmentedStream);
                }

                m_FragmentedBuffer.Write(reader.Binary.ReadBytes(iPayloadSize));
                return(null);
            }

            if ((header & Packet.BitMaskFragment_End) != Packet.BitMaskFragment_None)
            {
                if (m_FragmentedBuffer == null)
                {
                    throw new PacketSerializingException(
                              $"Package ({eType}) was flagged as END of a fragmented packet: got no START.");
                }

                m_FragmentedBuffer.Write(reader.Binary.ReadBytes(iPayloadSize));
                Done = true;
                return(new Packet(eType, m_FragmentedStream));
            }

            Done = true;
            return(new Packet(eType, reader.Binary.ReadBytes(iPayloadSize)));
        }
コード例 #12
0
 public static bool IsUpdate(this EPacket p)
 {
     return(GetAttr(p).IsUpdate);
 }
コード例 #13
0
 public static byte EncodePacketType(EPacket eType)
 {
     return((byte)(Convert.ToByte(eType) & Packet.BitMaskType));
 }
コード例 #14
0
 public Packet(EPacket eType, MemoryStream stream) : this(eType, stream.ToArray())
 {
 }
コード例 #15
0
 public Packet(EPacket eType, byte[] payload) : this(eType, new ArraySegment <byte>(payload))
 {
 }
コード例 #16
0
 public virtual void Send(Identity receiver, EPacket type, byte[] data, int channel)
 {
     Send(receiver, type, data, data.Length, channel);
 }
コード例 #17
0
 private static EPacketAttr GetAttr(EPacket p)
 {
     return((EPacketAttr)Attribute.GetCustomAttribute(ForValue(p), typeof(EPacketAttr)));
 }
コード例 #18
0
 public static bool IsChunk(this EPacket p)
 {
     return(GetAttr(p).IsChunk);
 }
コード例 #19
0
        public static void DTestArray()
        {
            string[]       strArray    = new string[5];
            int[]          intArray    = new int[5];
            StructField[]  structArray = new StructField[5];
            ClassField[]   classArray  = new ClassField[5];
            DocumentEnum[] enumArray   = new DocumentEnum[5];
            for (int i = 0; i < strArray.Length; i += 1)
            {
                strArray[i]    = i.ToString();
                intArray[i]    = i;
                enumArray[i]   = DocumentEnum.ID;
                structArray[i] = new StructField()
                {
                    PublicAge = i
                };
                classArray[i] = new ClassField()
                {
                    PublicAge = i
                };
            }
            //动态创建Action委托
            Delegate newMethod = EHandler.CreateMethod <ENull>((il) =>
            {
                EMethod method = typeof(Console);
                //从运行时获取数组并入栈到IL层临时变量
                EArray stringArrayModel = strArray;
                ELoop.For(stringArrayModel, (currentElement) =>
                {
                    method.ExecuteMethod <string>("WriteLine", currentElement);
                });

                EArray intArrayModel = intArray;
                ELoop.For(3, 5, 1, intArrayModel, (currentElement) =>
                {
                    method.ExecuteMethod <int>("WriteLine", currentElement);
                });

                EArray arrayModel = EArray.CreateArraySpecifiedLength <int>(10);
                arrayModel.StoreArray(5, 6);
                arrayModel.StoreArray(6, 6);
                arrayModel.StoreArray(7, 6);
                ELoop.For(0, 10, 1, arrayModel, (currentElement) =>
                {
                    method.ExecuteMethod <int>("WriteLine", currentElement);
                });
                //从运行时获取数组并入栈到IL层临时变量
                EArray structArrayModel = EArray.CreateArrayFromRuntimeArray(structArray);
                ELoop.For(structArrayModel, (currentElement) =>
                {
                    EModel model = EModel.CreateModelFromAction(currentElement, typeof(StructField));
                    model.LFieldValue("PublicAge");
                    method.ExecuteMethod <int>("WriteLine");
                });
                EArray classArrayModel = EArray.CreateArrayFromRuntimeArray(classArray);
                ELoop.For(classArrayModel, (currentElement) =>
                {
                    EModel model = EModel.CreateModelFromAction(currentElement, typeof(ClassField));
                    model.LFieldValue("PublicAge");
                    method.ExecuteMethod <int>("WriteLine");
                });
                EArray enumArrayModel = EArray.CreateArrayFromRuntimeArray(enumArray);
                ELoop.For(enumArrayModel, (currentElement) =>
                {
                    EModel model = EModel.CreateModelFromAction(currentElement, typeof(DocumentEnum));
                    model.Load();
                    EPacket.Packet(typeof(DocumentEnum));
                    method.ExecuteMethod <object>("WriteLine");
                });
            }).Compile();

            ((Action)newMethod)();
        }
コード例 #20
0
 public PacketHandlerAttribute(EConnectionState state, EPacket eType)
 {
     State = state;
     Type  = eType;
 }
コード例 #21
0
 public void Send(ECall mode, Vector3 point, float radius, EPacket type, byte[] packet)
 {
     Send(mode, point, radius, type, packet, packet.Length);
 }
コード例 #22
0
        internal override void Receive(Identity source, byte[] packet, int size, int channel)
        {
            base.Receive(source, packet, size, channel);
            var     net          = ((OffsetNet + Time.realtimeSinceStartup) - LastNet);
            EPacket parsedPacket = (EPacket)packet[0];

            StripPacketByte(ref packet, ref size);

            if (parsedPacket.IsUpdate())
            {
                if (source == ServerID)
                {
                    foreach (Channel ch in Receivers)
                    {
                        ch.Receive(source, packet, 0, size);
                    }
                }
                else
                {
                    if (Clients.All(client => client.Identity != source))
                    {
                        return;
                    }
                    foreach (Channel ch in Receivers.Where(ch => ch.ID == channel))
                    {
                        ch.Receive(source, packet, 0, size);
                    }
                }
                return;
            }

            PendingUser currentPending;

            switch (parsedPacket)
            {
            case EPacket.WORKSHOP:
            {
                //workshop list {none for now}
                List <ulong> workshoplist = new List <ulong>();

                byte[] args = new byte[1 + (workshoplist.Count * 8)];
                args[0] = (byte)workshoplist.Count;
                for (byte i = 0; i < workshoplist.Count; i = (byte)(i + 1))
                {
                    BitConverter.GetBytes(workshoplist[i]).CopyTo(args, (1 + (i * 8)));
                }
                Send(source, EPacket.WORKSHOP, args, args.Length, 0);
                return;
            }

            case EPacket.TICK:
            {
                object[] objects = { net };
                byte[]   buffer2 = ObjectSerializer.GetBytes(0, objects);
                Send(source, EPacket.TIME, buffer2, 0);
                return;
            }

            case EPacket.TIME:
                foreach (User c in Clients.Where(c => c.Identity == source))
                {
                    if (!(c.LastPing > 0f))
                    {
                        return;
                    }
                    c.LastNet = Time.realtimeSinceStartup;
                    c.Lag(Time.realtimeSinceStartup - c.LastPing);
                    c.LastPing = -1f;
                    return;
                }
                return;

            case EPacket.CONNECT:
            {
                if (_pendingPlayers.Any(p => p.Identity == source))
                {
                    Reject(source, ERejectionReason.ALREADY_PENDING);
                    return;
                }

                if (Clients.Any(c => c.Identity == source))
                {
                    Reject(source, ERejectionReason.ALREADY_CONNECTED);
                    return;
                }

                Type[] argTypes =
                {
                    // [0] name, [1] group, [2] version, [3] ping
                    typeof(string), typeof(ulong), typeof(string), typeof(float)
                };

                var args       = ObjectSerializer.GetObjects(0, 0, packet, argTypes);
                var playerName = (string)args[0];
                var group      = (ulong)args[1];
                var version    = (string)args[2];
                var ping       = (float)args[3];

                LogUtils.Log("Player connecting: " + playerName);
                if (version != GameInfo.VERSION)
                {
                    Reject(source, ERejectionReason.WRONG_VERSION);
                    return;
                }

                if ((Clients.Count + 1) > MultiplayerProvider.MultiplayerProvider.MAX_PLAYERS)
                {
                    Reject(source, ERejectionReason.SERVER_FULL);
                    return;
                }

                var pendingPlayer = new PendingUser(source, playerName, group, ping);
                _pendingPlayers.Add(pendingPlayer);
                if (Provider.SupportsAuthentification)
                {
                    Send(source, EPacket.VERIFY, new byte[] { }, 0, 0);
                    return;
                }
                pendingPlayer.HasAuthentication = true;
                Accept(pendingPlayer);
                return;
            }

            default:
                if (parsedPacket != EPacket.AUTHENTICATE)
                {
                    LogUtils.LogError("Failed to handle message: " + parsedPacket);
                    return;
                }

                currentPending = _pendingPlayers.FirstOrDefault(p => p.Identity == source);
                break;
            }

            if (currentPending == null)
            {
                Reject(source, ERejectionReason.NOT_PENDING);
            }
            else if ((Clients.Count + 1) > MultiplayerProvider.MultiplayerProvider.MAX_PLAYERS)
            {
                Reject(source, ERejectionReason.SERVER_FULL);
            }
            else
            {
                object[] args = ObjectSerializer.GetObjects(0, 0, packet, typeof(byte[]));
                if (!((ServerMultiplayerProvider)Provider).VerifyTicket(source, (byte[])args[0]))
                {
                    Reject(source, ERejectionReason.AUTH_VERIFICATION);
                }
            }
        }
コード例 #23
0
        public void Send(ECall mode, Vector3 point, float radius, EPacket type, byte[] packet, int size)
        {
            radius *= radius;
            switch (mode)
            {
            case ECall.Server:
                if (Connection.IsServer())
                {
                    Receive(Connection.ServerID, packet, 0, size);
                }
                else
                {
                    Connection.Send(Connection.ServerID, type, packet, size, ID);
                }
                break;

            case ECall.All:
                if (!(Connection.IsServer()))
                {
                    Connection.Send(Connection.ServerID, type, packet, size, ID);
                }
                foreach (User user in Connection.Clients)
                {
                    if ((user.Identity == Connection.ClientID) || (user.Player == null))
                    {
                        continue;
                    }
                    Vector3 vector = user.Player.transform.position - point;
                    if (vector.sqrMagnitude < radius)
                    {
                        Connection.Send(user.Identity, type, packet, size, ID);
                    }
                }
                if (Connection.IsServer())
                {
                    Receive(Connection.ServerID, packet, 0, size);
                }
                else
                {
                    Receive(Connection.ClientID, packet, 0, size);
                }
                break;

            case ECall.Others:
                if (!(Connection.IsServer()))
                {
                    Connection.Send(Connection.ServerID, type, packet, size, ID);
                }
                foreach (User user in Connection.Clients)
                {
                    if ((user.Identity == Connection.ClientID) || (user.Player == null))
                    {
                        continue;
                    }
                    Vector3 vector2 = user.Player.transform.position - point;
                    if (vector2.sqrMagnitude < radius)
                    {
                        Connection.Send(user.Identity, type, packet, size, ID);
                    }
                }
                break;

            case ECall.Owner:
                if (IsOwner)
                {
                    Receive(Owner, packet, 0, size);
                }
                else
                {
                    Connection.Send(Owner, type, packet, size, ID);
                }
                break;

            case ECall.NotOwner:
                if (!(Connection.IsServer()))
                {
                    Connection.Send(Connection.ServerID, type, packet, size, ID);
                }
                foreach (User user in Connection.Clients)
                {
                    if ((user.Identity == Owner) || (user.Player == null))
                    {
                        continue;
                    }
                    Vector3 vector3 = user.Player.transform.position - point;
                    if (vector3.sqrMagnitude < radius)
                    {
                        Connection.Send(user.Identity, type, packet, size, ID);
                    }
                }
                break;

            case ECall.Clients:
                foreach (User user in Connection.Clients)
                {
                    if ((user.Identity == Connection.ClientID) || (user.Player == null))
                    {
                        continue;
                    }
                    Vector3 vector4 = user.Player.transform.position - point;
                    if (vector4.sqrMagnitude < radius)
                    {
                        Connection.Send(user.Identity, type, packet, size, ID);
                    }
                }
                if (Connection.IsServer())
                {
                    Receive(Connection.ClientID, packet, 0, size);
                }
                break;

            case ECall.Peers:
                foreach (User user in Connection.Clients)
                {
                    if ((user.Identity == Connection.ClientID) || (user.Player == null))
                    {
                        continue;
                    }
                    Vector3 vector5 = user.Player.transform.position - point;
                    if (vector5.sqrMagnitude < radius)
                    {
                        Connection.Send(user.Identity, type, packet, size, ID);
                    }
                }
                break;
            }
        }
コード例 #24
0
 public static bool IsUnreliable(this EPacket p)
 {
     return(GetAttr(p).IsUnreliable);
 }
コード例 #25
0
 public static bool IsInstant(this EPacket p)
 {
     return(GetAttr(p).IsInstant);
 }
コード例 #26
0
        internal override void Receive(Identity id, byte[] packet, int size, int channel)
        {
            base.Receive(id, packet, size, channel);
            EPacket parsedPacket = (EPacket)packet[0];

            StripPacketByte(ref packet, ref size);

            if (parsedPacket.IsUpdate())
            {
                foreach (Channel ch in Receivers.Where(ch => ch.ID == channel))
                {
                    ch.Receive(id, packet, 0, size);
                }
                return;
            }

            if (id != ServerID)
            {
                return;
            }
            switch (parsedPacket)
            {
            case EPacket.WORKSHOP:
                //todo
                break;

            case EPacket.TICK:
            {
                var data = ObjectSerializer.GetBytes(0, Time.realtimeSinceStartup);
                Send(ServerID, EPacket.TIME, data, 0);
                break;
            }

            case EPacket.TIME:
            {
                object[] args = ObjectSerializer.GetObjects(0, 0, packet, typeof(float));
                LastNet   = Time.realtimeSinceStartup;
                OffsetNet = ((float)args[0]) + ((Time.realtimeSinceStartup - LastPing) / 2f);
                Lag(Time.realtimeSinceStartup - LastPing);
                break;
            }

            case EPacket.SHUTDOWN:
                Disconnect();
                break;

            case EPacket.CONNECTED:
            {
                {
                    Type[] argTypes =
                    {
                        //[0] id, [1] name, [2] group, [3] position, [4], angle, [5] channel
                        typeof(Identity), typeof(string), typeof(ulong), typeof(Vector3), typeof(Vector3),
                        typeof(int),      typeof(bool)
                    };

                    object[] args = ObjectSerializer.GetObjects(0, 0, packet, argTypes);
                    if (IsSinglePlayer)
                    {
                        return;
                    }
                    if (World.Loaded)
                    {
                        AddPlayer(Provider.Deserialilze((Identity)args[0]), (string)args[1], (ulong)args[2],
                                  (Vector3)args[3], (Vector3)args[4], (int)args[5], (bool)args[6]);
                    }
                    else
                    {
                        QueuePlayer(Provider.Deserialilze((Identity)args[0]), (string)args[1], (ulong)args[2],
                                    (Vector3)args[3], (Vector3)args[4], (int)args[5], (bool)args[6]);
                    }
                    break;
                }
            }

            case EPacket.VERIFY:
                LogUtils.Debug("Opening ticket");
                byte[] ticket = ((ClientMultiplayerProvider)Provider).OpenTicket();
                if (ticket == null)
                {
                    LogUtils.Debug("ticket equals null");
                    Disconnect();
                    break;
                }
                Send(ServerID, EPacket.AUTHENTICATE, ticket, ticket.Length, 0);
                break;

            case EPacket.DISCONNECTED:
            {
                //If singleplayer (local server) we will already do this at ServerConnection
                if (IsSinglePlayer)
                {
                    return;
                }
                object[] args  = ObjectSerializer.GetObjects(0, 0, packet, typeof(byte));
                var      index = (byte)args[0];

                var user = GetUser(index);

                PlayerQuitEvent @event = new PlayerQuitEvent(user.Player);
                EventManager.Instance.CallEvent(@event);

                RemovePlayer(index);
                break;
            }

            case EPacket.REJECTED:
            case EPacket.KICKED:
                Disconnect();
                break;

            case EPacket.ACCEPTED:
            {
                object[] args = ObjectSerializer.GetObjects(0, 0, packet, typeof(ulong), typeof(int));
                LogUtils.Debug("Setting MainPlayer channel to: " + (int)args[1]);
                ((ClientMultiplayerProvider)Provider).SetIdentity((ulong)args[0]);
                ((ClientMultiplayerProvider)Provider).AdvertiseGame(ServerID, _currentIp, _currentPort);
                ((ClientMultiplayerProvider)Provider).SetConnectInfo(_currentIp, _currentPort);
                IsFavoritedServer = ((ClientMultiplayerProvider)Provider).IsFavoritedServer(_currentIp, _currentPort);
                ((ClientMultiplayerProvider)Provider).FavoriteServer(_currentIp, _currentPort);
                break;
            }

            case EPacket.UPDATE_CHANNELS:
            {
                object[] args = ObjectSerializer.GetObjects(0, 0, packet, ChannelCount.GetType());
                ChannelCount = (int)args[0];
                break;
            }

            default:
                LogUtils.LogWarning("Couldn't handle packet: " + parsedPacket);
                break;
            }
        }
コード例 #27
0
 public static byte GetID(this EPacket p)
 {
     return((byte)p);
 }
コード例 #28
0
 private Packet(EPacket eType, ArraySegment <byte> payload)
 {
     Type    = eType;
     Payload = payload;
 }
コード例 #29
0
 private static MemberInfo ForValue(EPacket p)
 {
     return(typeof(EPacket).GetField(Enum.GetName(typeof(EPacket), p)));
 }
コード例 #30
0
 protected virtual bool OnPreSend(Identity receiver, EPacket type, byte[] data, int length, int channel)
 {
     return(false);
 }