/// <summary> /// Incoming packets are pushed here for handling. /// </summary> protected unsafe override void HandlePacket(IPacketBase packet) { base.HandlePacket(packet); //Update state from the client if (packet is PushState) { var state = (PushState)packet; //Push their state if it's the correct world ID if (state.WorldID == WorldID) { LastState = state.State; } } //Move the user in to a new zone else if (packet is RequestZoneTransfer) { var request = (RequestZoneTransfer)packet; mWorld.ZoneManager.RequestZoneTransfer(this, request.ZoneID); } //Resolve names else if (packet is WhoisRequest) { var request = (WhoisRequest)packet; var response = PacketFactory.CreatePacket <WhoisResponse>(); response.WorldID = request.WorldID; var name = mWorld.GetNameForWorldID(request.WorldID); TextHelpers.StringToBuffer(name, response.Name, name.Length); DeferredSendPacket(response); } }
/// <summary> /// Updates this entity, flushes and handles any pending packets in the incoming queue. /// </summary> public void Update(TimeSpan dt) { //Handle all packets in the incoming queue IPacketBase packet = null; while (m_incomingQueue.TryDequeue(out packet)) { HandlePacket(packet); } //Send any packets that have been deferred foreach (CoalescedData p in m_deferredSendList) { SendPacket(p); } m_deferredSendList.Clear(); if (m_currentDeferredPacket.PacketCount > 0) { SendPacket(m_currentDeferredPacket); } //Reset the current deferred packet for next update m_currentDeferredPacket = PacketFactory.CreatePacket <CoalescedData>(); //Warn if any of the queues are getting swamped if (m_outgoingQueue.Count > 25) { Console.WriteLine("Outgoing queue swamped: " + m_outgoingQueue.Count); } if (m_incomingQueue.Count > 25) { Console.WriteLine("Incoming queue swamped: " + m_incomingQueue.Count); } }
/// <summary> /// Sends states of nearby enemies to each other /// </summary> public void PushNearbyEntities(ServerEntity entity) { const int minSqrDistance = 768 * 768; foreach (var e in mEntities.Values) { if (e.AuthState != EEntityAuthState.Authorised || e.WorldID == entity.WorldID) { //Skip unauthorised entities and don't send to self continue; } float xDiff = entity.LastState.X - e.LastState.X; float yDiff = entity.LastState.Y - e.LastState.Y; var sqrdistance = (xDiff * xDiff) + (yDiff * yDiff); if (sqrdistance > minSqrDistance) { continue; } //Add a push state into the coalesced data packet for this entity var state = PacketFactory.CreatePacket <PushState>(); state.WorldID = e.WorldID; state.State = e.LastState; entity.DeferredSendPacket(state); } }
/// <summary> /// Send a clock sync request, if there is not already one pending. /// </summary> public void SendClockSync() { if (!m_awaitingClockSyncResponse) { m_clockSyncSendTime = Environment.TickCount; m_awaitingClockSyncResponse = true; SendPacket(PacketFactory.CreatePacket <ClockSyncRequest>()); } }
public void CreatePacket(byte[] value, Type expectedType) { var streamMock = new MemoryStream(value); var factory = new PacketFactory(new PacketReader()); var result = factory.CreatePacket(streamMock); result.GetType().Should().Be(expectedType); }
/// <summary> /// Packet handler logic /// </summary> protected virtual void HandlePacket(IPacketBase packet) { //Send auth responses for an auth request if (packet is AuthRequest) { AuthResponse response = PacketFactory.CreatePacket <AuthResponse>(); //Tell them their world ID response.WorldID = WorldID; DeferredSendPacket(response); AuthState = EntityAuthState.Authorised; } //Update auth state and world ID else if (packet is AuthResponse) { AuthResponse response = (AuthResponse)packet; WorldID = response.WorldID; AuthState = EntityAuthState.Authorised; } //Unpack coalesced packets else if (packet is CoalescedData) { CoalescedData data = (CoalescedData)packet; unsafe { byte *ptr = data.DataBuffer; //Start deserializing packets from the buffer for (int i = 0; i < data.PacketCount; i++) { //Deserialize and advance pointer to next packet in the buffer ptr += DeserializePacket((IntPtr)ptr); } } } //Synchronise clocks else if (packet is ClockSyncResponse) { ClockSyncResponse response = (ClockSyncResponse)packet; int rtt = Environment.TickCount - m_clockSyncSendTime; m_roundTripTimes.Enqueue(rtt); if (m_roundTripTimes.Count > 10) { m_roundTripTimes.Dequeue(); } SyncClock(response.Time); m_awaitingClockSyncResponse = false; } else if (packet is ClockSyncRequest) { ClockSyncResponse response = PacketFactory.CreatePacket <ClockSyncResponse>(); response.Time = Environment.TickCount; SendPacket(response); } }
/// <summary> /// Send an authorisation request. /// </summary> public virtual void Authorise() { //Don't send multiple auths if (AuthState == EntityAuthState.Unauthorised) { AuthState = EntityAuthState.Authorising; DeferredSendPacket(PacketFactory.CreatePacket <AuthRequest>()); } }
/// <summary> /// Queues a packet to be send on the next update. Will coalesce these packets together. /// </summary> public void DeferredSendPacket(IPacketBase packet) { if (!m_currentDeferredPacket.TryAddPacket(packet)) { m_deferredSendList.Add(m_currentDeferredPacket); m_currentDeferredPacket = PacketFactory.CreatePacket <CoalescedData>(); m_currentDeferredPacket.TryAddPacket(packet); } }
public void TestInput() { Assert.Equal(6, PacketFactory.CreatePacket("D2FE28").VersionSum()); Assert.Equal(9, PacketFactory.CreatePacket("38006F45291200").VersionSum()); Assert.Equal(16, PacketFactory.CreatePacket("8A004A801A8002F478").VersionSum()); Assert.Equal(14, PacketFactory.CreatePacket("EE00D40C823060").VersionSum()); Assert.Equal(12, PacketFactory.CreatePacket("620080001611562C8802118E34").VersionSum()); Assert.Equal(23, PacketFactory.CreatePacket("C0015000016115A2E0802F182340").VersionSum()); Assert.Equal(31, PacketFactory.CreatePacket("A0016C880162017C3686B18A3D4780").VersionSum()); }
public void TestInputTwo() { Assert.Equal(3, PacketFactory.CreatePacket("C200B40A82").GetValue()); Assert.Equal(54, PacketFactory.CreatePacket("04005AC33890").GetValue()); Assert.Equal(7, PacketFactory.CreatePacket("880086C3E88112").GetValue()); Assert.Equal(9, PacketFactory.CreatePacket("CE00C43D881120").GetValue()); Assert.Equal(1, PacketFactory.CreatePacket("D8005AC2A8F0").GetValue()); Assert.Equal(0, PacketFactory.CreatePacket("F600BC2D8F").GetValue()); Assert.Equal(0, PacketFactory.CreatePacket("9C005AC2F8F0").GetValue()); Assert.Equal(1, PacketFactory.CreatePacket("9C0141080250320F1802104A08").GetValue()); }
public void ShouldThrowOnInvalidPacketId() { var streamMock = new MemoryStream(new byte[1] { 10 }); var factory = new PacketFactory(new PacketReader()); Exception exception = Assert.Throws <InvalidPacketException>(() => factory.CreatePacket(streamMock)); exception.Should().NotBeNull(); }
public void ImmidiateSend(string _action, object _payload, EventHandler <Packet> _callback = null, Action <bool> _completed = null) { if (!IsOpen()) { return; } var packet = PacketFactory.CreatePacket(_action, _payload); var request = new Request(packet, _callback, _completed, false); Send(request); }
private byte[] AuthResponse(AuthenticationResult result, Account account) { using (var builder = PacketFactory.CreatePacket("Authentication")) { builder.WriteInt32(result); builder.WriteInt16(0x0000); if (result == AuthenticationResult.Success) { builder.WriteInt32(account.AccountId); if (State == AuthClientState.SetGender) { builder.WriteByte(AuthOperationType.GenderSelect); } else if (State == AuthClientState.SetPin) { builder.WriteByte(AuthOperationType.PinSelect); } else { builder.WriteByte(account.Gender); } // Enables commands like /c, /ch, /m, /h (etc.), but disables trading builder.WriteBoolean(account.IsGameMaster); // Seems like 0x80 is a "MWLB" account - I doubt it... it disables attacking and allows GM fly // 0x40, 0x20 (and probably 0x10, 0x8, 0x4, 0x2, and 0x1) don't appear to confer any particular benefits, restrictions, or functionality // (Although I didn't test client GM commands or anything of the sort) builder.WriteByte(account.IsGameMaster ? 0x80 : 0x00); builder.WriteBoolean(account.IsGameMaster || account.IsGameMasterHelper); builder.WriteLengthString(account.UserName); builder.WriteByte(2); // TODO: quiet ban support? //builder.WriteByte(account.QuietBanReason); builder.WriteByte(0); //builder.WriteTimestamp(account.QuietBanTime); builder.WriteInt64(0); // TODO: Creation time builder.WriteTimestamp(account.CreationTime); builder.WriteInt32(0); } return(builder.ToByteArray()); } }
private byte[] WorldListResponse() { var worlds = _nexus.GetWorlds(); using (var builder = PacketFactory.CreatePacket("WorldListRequest")) { foreach (var world in worlds) { builder.WriteWorld(world); } return(builder.ToByteArray()); } }
protected override void Encode(IChannelHandlerContext context, SPacket message, List <object> output) { var packet = packetFactory.CreatePacket(message); if (string.IsNullOrEmpty(packet)) { logger.Debug("Empty packet, skipping it"); return; } output.Add(packet); logger.Debug($"Out [{message.GetType().Name}]: {packet}"); }
protected override void Decode(IChannelHandlerContext context, string message, List <object> output) { var packet = packetFactory.CreatePacket(message); if (packet is null) { logger.Debug("Failed to create typed packet, skipping it"); return; } output.Add(packet); logger.Debug($"In [{packet.GetType().Name}]: {message}"); }
public void SequencialSend(string _action, object _payload, EventHandler <Packet> _callback, Action <bool> _completed = null) { if (!IsOpen()) { return; } var packet = PacketFactory.CreatePacket(_action, _payload); var request = new Request(packet, _callback, _completed, true); roundTrips.Enqueue(request); if (roundTrips.Peek() == request) { Send(request); } }
public IPacket ReadPacket() { ushort type = ReadUInt16(); ReadByte(); // skipped byte int body_length = ReadInt32(); var start = this.BaseStream.Position; var p = PacketFactory.CreatePacket( packet_type: type, this ); for (; BaseStream.Position - start < body_length; ReadByte()) { ; } return(p); }
private void ReceivedPayload() { byte[] data = buffer.data; try { BitReader r = new BitReader(data, data.Length); byte id = r.ReadUInt8(); TPacket packet = packetFactory.CreatePacket(id); if (packet == null) { Log.Error($"No {typeof(TPacket).Name} for id: {id}"); return; } if (packet is ITokenPacket token) { packet.ReadTokenPacket(r); if (token.TokenResponse) { HandleTokenPacket(packet, token.Token); } else { HandlePacket(packet); } } else { try { packet.ReadPacket(r); HandlePacket(packet); } catch (Exception e) { Log.Error(e); Disconnect(); } } } finally { buffer.Reset(4); } }
static void Main(string[] args) { var testPacket = PacketFactory.CreatePacket <MessagePacket>(); testPacket.Message = "Something"; testPacket.Sender = "Someone"; var packetJson = testPacket.ToJson(); Console.WriteLine(packetJson); PacketFactory.JsonToPacket(packetJson, out IPacket testDeserialize); switch (testDeserialize.Type) { case PacketType.Message: HandleMessage(testDeserialize as MessagePacket); break; } Console.ReadLine(); }
public void PuzzelTwo() { Assert.Equal(277110354175, PacketFactory.CreatePacket(InputParser.ParseString("input_data/day16-1.txt").First()).GetValue()); }
public void PuzzelOne() { Assert.Equal(979, PacketFactory.CreatePacket(InputParser.ParseString("input_data/day16-1.txt").First()).VersionSum()); }
/// <summary> /// Completes an async event to receive data. /// </summary> /// <param name="result"></param> private void OnClientReceiveData(IAsyncResult result) { //log.Debug($"isAuth {isAuth}"); //log.Debug("OnClientReceiveData"); // Prevent invalid calls to this function.. if (!this._isRunning || result.IsCompleted == false || !(result.AsyncState is Socket)) { this.Stop(); return; } lock (syncLock) { Socket client = (result.AsyncState as Socket); // Attempt to end the async call.. int recvCount = 0; try { try { recvCount = client.EndReceive(result); } catch (Exception exception) { //log.Debug(exception.ToString()); this.Stop(); throw; // TODO: atleast log the exception. } if (recvCount == 0) { this.Stop(); return; } } catch (Exception ex) { this.Stop(); return; } // Read the current packet. byte[] recvData = new byte[recvCount]; Array.Copy(this._clientBuffer, 0, recvData, 0, recvCount); this._clientBacklog.AddRange(recvData); //this.SendToServerRaw(recvData); // Iterate through the whole packets, parse them and delete them from the buffer. while (true) { /* * L2Packet structure: | 2 byte size | 1 byte id | up to 65535 bytes for data (payload) | */ // If packet buffer is lesser than 3 bytes there is no valid packet for parsing (the minimum is atleast 3 bytes (2 bytes for size, 1 for id) if (this._clientBacklog.Count < 3) { break; } while (L2Injector._sgObjInit == false) { Thread.Sleep(20); } // Calculate the packet length by parsing the first 2 bytes. int packetSize = BitConverter.ToInt16(this._clientBacklog.ToArray(), 0); if (this._clientBacklog.Count < packetSize) { break; } byte[] receivedPacket = new byte[packetSize]; Array.Copy(this._clientBacklog.ToArray(), 0, receivedPacket, 0, packetSize); bool shouldDropPacket = false; this._clientBacklog.RemoveRange(0, packetSize); if (!isAuth && _isInit) { _gamePacketObfuscator.DeobfuscatePacketFromClient(receivedPacket); _secondaryGamePacketObfuscator?.DeobfuscatePacketFromClient(receivedPacket); try { if (!JUSTASNIFFER) { var packet = packetFactory.CreatePacket(receivedPacket, false); packet?.Parse(BotInstance.PlayerData); if (packet?.DropPacket == true && _gamePacketObfuscator is SGInGameCipher) { shouldDropPacket = true; //((SGInGameCipher)_gamePacketObfuscator).reverseCrypt(receivedPacket, ((SGInGameCipher)_gamePacketObfuscator).clientKeySend); } } if (JUSTASNIFFER) { log.Debug(string.Join(", ", receivedPacket.Select(b => string.Format("{0:X2} ", b)))); } //PacketParser.HandleOutgoingPacket(receivedPacket, this.data, this.logger); //CB gameguard id //b1 net ping id } catch (Exception ex) { log.Debug(ex.ToString()); throw; } if (!shouldDropPacket) { _secondaryGamePacketObfuscator?.ObfuscatePacketForServer(receivedPacket); _gamePacketObfuscator.ObfuscatePacketForServer(receivedPacket); } } else if (!_isInit) { if (_gamePacketObfuscator == null && receivedPacket.Length > 100) { int version = BitConverter.ToInt32(receivedPacket.ToArray(), 3); if (version >= 268 && version <= 272) { log.Debug($"Unsupported H5 client."); } //log.Debug(version); if (!JUSTASNIFFER) { BotInstance.Init(version, this); packetFactory = ProtocolFactory.CreatePacketFactory(version); } } if (L2Injector.IsSGLoaded() && _gamePacketObfuscator is LegacyInGameCipher) { _gamePacketObfuscator = new SGInGameCipher(new byte[1], 0); //placeholder args, since they are not needed in the alg //if (!JUSTASNIFFER) L2Injector.FillSGObject((SGInGameCipher)_gamePacketObfuscator); //((SGInGameCipher)_gamePacketObfuscator).reverseCrypt(receivedPacket,((SGInGameCipher)_gamePacketObfuscator).clientKeySend); //_gamePacketObfuscator.DeobfuscatePacketFromClient(receivedPacket); _isInit = true; } } //log.Debug("_0"); if (_secondaryGamePacketObfuscator == null && L2Injector.IsRpgClient() && _gamePacketObfuscator is LegacyInGameCipher) { _secondaryGamePacketObfuscator = new RpgInGameCipher(((LegacyInGameCipher)_gamePacketObfuscator).DynamicKeyBytes, 0); ((RpgInGameCipher)_secondaryGamePacketObfuscator).SecretKey = L2Injector.GetRpgSecretKey(); } // Send this packet to the server. //log.Debug("_1"); if (!shouldDropPacket) { this.SendToServerRaw(receivedPacket); } } // Begin listening for the next packet. this.Client_BeginReceive(); //log.Debug("_5"); } }
/** * single receive, run in the receiverThread, see {@link #start()} * <ul> * <li>Receives UDP packets from the network</li> * <li>Converts them to UDT packets</li> * <li>dispatches the UDT packets according to their destination ID.</li> * </ul> * @throws IOException */ protected void DoReceive() { EndPoint remotePoint = new IPEndPoint(IPAddress.Any, 0); while (!stopped) { try { try { //v.end(); //will block until a packet is received or timeout has expired int len = dgSocket.ReceiveFrom(dp, ref remotePoint); //v.begin(); Destination peer = new Destination(remotePoint); IUDTPacket packet = PacketFactory.CreatePacket(dp, len); lastPacket = packet; //handle connection handshake if (packet.IsConnectionHandshake()) { lock (lock_obj) { long id = packet.DestinationID; UDTSession session = null; sessions.TryGetValue(id, out session); if (session == null) { session = new ServerSession((IPEndPoint)remotePoint, this); AddSession(session.SocketID, session); //TODO need to check peer to avoid duplicate server session if (serverSocketMode) { FlashLogger.Info("Pooling new request."); sessionHandoff.Add(session); FlashLogger.Info("Request taken for processing."); } } peer.SocketID = ((ConnectionHandshake)packet).SocketID; session.Received(packet, peer); } } else { //dispatch to existing session long dest = packet.DestinationID; UDTSession session; if (dest == lastDestID) { session = lastSession; } else { // session = sessions.TryGetValue(dest, out session);//cd 获取session lastSession = session; lastDestID = dest; } if (session == null) { n++; if (n % 100 == 1) { FlashLogger.Warn("Unknown session <" + dest + "> requested from <" + peer + "> packet type " + packet); } } else { Console.WriteLine("收到包"); session.Received(packet, peer); } } } catch (SocketException ex) { if (ex.Message.Equals("socket closed") && stopped) { //cd //已经正常关闭 } else { FlashLogger.Info("SocketException: " + ex.Message); } } catch (Exception ste) { //can safely ignore... we will retry until the endpoint is stopped } } catch (Exception ex) { FlashLogger.Warn("Got: " + ex.Message, ex); } } }