예제 #1
0
        private Packet?FilterSeverTargetCursorPacket(Packet rawPacket)
        {
            if (rawPacket.Id == PacketDefinitions.TargetCursor.Id)
            {
                TargetInfo?targetInfo = null;

                lock (nextTargetsLock)
                {
                    if (nextTargets.Count > 0)
                    {
                        targetInfo = nextTargets.Dequeue();
                        if (!targetInfo.HasValue)
                        {
                            var packet = packetRegistry.Materialize <TargetCursorPacket>(rawPacket);

                            server.CancelTarget(packet.CursorId);

                            return(null);
                        }
                    }
                }

                if (targetInfo.HasValue)
                {
                    var packet = packetRegistry.Materialize <TargetCursorPacket>(rawPacket);

                    server.TargetItem(packet.CursorId, targetInfo.Value.Id ?? 0, packet.CursorType,
                                      targetInfo.Value.Location, targetInfo.Value.ModelId);

                    return(null);
                }
            }

            return(rawPacket);
        }
예제 #2
0
        private Packet?FilterClientSpeech(Packet rawPacket)
        {
            string text = null;

            if (rawPacket.Id == PacketDefinitions.SpeechRequest.Id)
            {
                text = packetRegistry.Materialize <SpeechRequest>(rawPacket).Text;
            }
            else if (rawPacket.Id == PacketDefinitions.TalkRequest.Id)
            {
                text = packetRegistry.Materialize <TalkRequest>(rawPacket).Message;
            }

            if (text != null)
            {
                if (commandHandler.IsInvocationSyntax(text))
                {
                    eventSource.Publish(new CommandRequestedEvent(text));

                    Task.Run(() =>
                    {
                        logger.Info(text);
                        commandHandler.InvokeSyntax(text);
                    });

                    return(null);
                }

                logger.Info(text);
                eventSource.Publish(new SpeechRequestedEvent(text));
            }

            return(rawPacket);
        }
예제 #3
0
        private Packet?Filter(Packet rawPacket)
        {
            if (morphedModel.HasValue)
            {
                if (rawPacket.Id == PacketDefinitions.DrawGamePlayer.Id)
                {
                    var packet = packetRegistry.Materialize <DrawGamePlayerPacket>(rawPacket);
                    if (packet.PlayerId == api.Me.PlayerId)
                    {
                        packet.BodyType = morphedModel.Value;
                        packet.Serialize();

                        return(packet.RawPacket);
                    }
                }
                else if (rawPacket.Id == PacketDefinitions.DrawObject.Id)
                {
                    var packet = packetRegistry.Materialize <DrawObjectPacket>(rawPacket);
                    if (packet.Id == api.Me.PlayerId)
                    {
                        packet.Type = morphedModel.Value;

                        return(packet.RawPacket);
                    }
                }
            }

            return(rawPacket);
        }
예제 #4
0
        private Packet?FilterSentClientPackets(Packet rawPacket)
        {
            if (rawPacket.Id == PacketDefinitions.TargetCursor.Id)
            {
                var packet = packetRegistry.Materialize <TargetCursorPacket>(rawPacket);
                LastTargetId = packet.ClickedOnId;
            }
            else if (rawPacket.Id == PacketDefinitions.GetClientStatus.Id)
            {
                var packet = packetRegistry.Materialize <GetClientStatusRequest>(rawPacket);
                LastStatusId = packet.Id;
            }

            return(rawPacket);
        }
예제 #5
0
        private Packet?FilterServerPackets(Packet rawPacket)
        {
            if (rawPacket.Id == PacketDefinitions.OpenDialogBox.Id)
            {
                var packet    = packetRegistry.Materialize <OpenDialogBoxPacket>(rawPacket);
                var dialogBox = new DialogBox(packet.DialogId, packet.MenuId, packet.Question, packet.Responses);
                CurrentDialogBox = dialogBox;
                bool showDialogBox = ShowDialogBox;

                bool block = false;
                lock (blockedQuestionLock)
                {
                    if (!string.IsNullOrEmpty(blockedQuestion) && dialogBox.Question.IndexOf(blockedQuestion, StringComparison.Ordinal) >= 0)
                    {
                        blockedQuestion = null;
                        block           = true;
                    }
                }

                eventJournalSource.Publish(new DialogBoxOpenedEvent(dialogBox));
                DialogBoxOpened?.Invoke(dialogBox);

                if (!showDialogBox || block)
                {
                    return(null);
                }
            }

            return(rawPacket);
        }
예제 #6
0
        private Packet?FilterGumpMenuSelection(Packet rawPacket)
        {
            if (rawPacket.Id == PacketDefinitions.GumpMenuSelection.Id && nextBlockedCancellationGumpId.HasValue)
            {
                lock (gumpLock)
                {
                    var packet = packetRegistry.Materialize <GumpMenuSelectionRequest>(rawPacket);
                    var gumpId = nextBlockedCancellationGumpId.Value;
                    nextBlockedCancellationGumpId = null;
                    if (gumpId == packet.GumpTypeId)
                    {
                        return(null);
                    }
                }
            }

            return(rawPacket);
        }
예제 #7
0
        private Packet?FilterSentClientPackets(Packet rawPacket)
        {
            if (rawPacket.Id == PacketDefinitions.RequestSkills.Id)
            {
                var packet = packetRegistry.Materialize <SkillRequest>(rawPacket);
                lastSkill = packet.Skill;
            }

            return(rawPacket);
        }
예제 #8
0
        private static Packet?RedirectConnectToGameServer(Packet rawPacket)
        {
            if (rawPacket.Id == PacketDefinitions.ConnectToGameServer.Id)
            {
                var packet = PacketDefinitionRegistry.Materialize <ConnectToGameServerPacket>(rawPacket);
                packet.GameServerIp   = new byte[] { 0x7F, 0x00, 0x00, 0x01 };
                packet.GameServerPort = proxyLocalPort;
                rawPacket             = packet.RawPacket;
                needServerReconnect   = true;
            }

            return(rawPacket);
        }
예제 #9
0
        private Packet?PhantomsFilter(Packet rawPacket)
        {
            if (rawPacket.Id == PacketDefinitions.SingleClick.Id)
            {
                var packet = packetRegistry.Materialize <SingleClickRequest>(rawPacket);
                if (phantomIds.Contains(packet.ItemId))
                {
                    return(null);
                }
            }

            return(rawPacket);
        }
예제 #10
0
        private Packet?FilterClientTargetCursorPacket(Packet rawPacket)
        {
            if (rawPacket.Id != PacketDefinitions.TargetCursor.Id)
            {
                return(rawPacket);
            }

            var packet = PacketDefinitionRegistry.Materialize <TargetCursorPacket>(rawPacket);

            if (discardNextTargetLocationRequestIfEmpty)
            {
                discardNextTargetLocationRequestIfEmpty = false;
                if (packet.Location.X == 0xFFFF && packet.Location.Y == 0xFFFF &&
                    packet.ClickedOnId.Value == 0)
                {
                    return(null);
                }
            }

            if (packet.CursorId == new CursorId(0xDEADBEEF))
            {
                if (packet.Location.X == 0xFFFF && packet.Location.Y == 0xFFFF &&
                    packet.ClickedOnId.Value == 0)
                {
                    lastTargetInfo = null;
                    lastItemIdInfo = null;
                    receivedTargetInfoEvent.Set();
                    return(null);
                }

                switch (packet.CursorTarget)
                {
                case CursorTarget.Location:
                    lastTargetInfo = new TargetInfo(packet.Location, TargetType.Tile, packet.ClickedOnType.Value,
                                                    null);
                    break;

                case CursorTarget.Object:
                    lastTypeInfo   = packet.ClickedOnType;
                    lastItemIdInfo = packet.ClickedOnId;
                    lastTargetInfo = new TargetInfo(packet.Location, TargetType.Object, packet.ClickedOnType,
                                                    packet.ClickedOnId);
                    break;
                }

                receivedTargetInfoEvent.Set();
                return(null);
            }

            return(rawPacket);
        }
예제 #11
0
        private Packet?RedirectConnectToGameServer(Packet rawPacket)
        {
            if (rawPacket.Id == PacketDefinitions.ConnectToGameServer.Id)
            {
                var packet = packetRegistry.Materialize <ConnectToGameServerPacket>(rawPacket);
                serverEndpoint = new IPEndPoint(new IPAddress(packet.GameServerIp), packet.GameServerPort);

                packet.GameServerIp   = new byte[] { 0x7F, 0x00, 0x00, 0x01 };
                packet.GameServerPort = proxyLocalPort;
                rawPacket             = packet.RawPacket;
            }

            return(rawPacket);
        }
예제 #12
0
        private Packet?HandleRunUOProtocolExtension(Packet rawPacket)
        {
            if (rawPacket.Id == PacketDefinitions.RunUOProtocolExtension.Id)
            {
                var packet = packetRegistry.Materialize <RunUOProtocolExtensionPacket>(rawPacket);
                if (packet.Type == 0xFE)
                {
                    server.AnswerRazorNegitiation(0xFF);
                    return(null);
                }
            }

            return(rawPacket);
        }
예제 #13
0
        private void ServerLoop()
        {
            try
            {
                console.Info($"Headless connecting to {startConfig.ServerAddress}");

                while (true)
                {
                    lock (serverStreamLock)
                    {
                        if (serverStream == null)
                        {
                            serverStream = ConnectToServer();
                        }
                    }

                    while (serverStream.DataAvailable)
                    {
                        try
                        {
                            var packet = serverConnection.Receive(new NetworkStreamToPullStreamAdapter(serverStream));
                            if (packet.Id == PacketDefinitions.ConnectToGameServer.Id)
                            {
                                HandleConnectToGameServer(packetRegistry.Materialize <ConnectToGameServerPacket>(packet));
                            }
                            else
                            {
                                ServerConnectionOnPacketReceived(this, packet);
                            }
                        }
                        catch (EndOfStreamException ex)
                        {
                            console.Debug(ex.ToString());
                            // just swallow this exception, wait for the next batch
                        }
                    }
                    if (disconnectTokenSource.Token.IsCancellationRequested)
                    {
                        return;
                    }
                    Thread.Sleep(1);
                }
            }
            catch (Exception ex)
            {
                console.Debug(serverDiagnosticPullStream.Flush());
                console.Debug(ex.ToString());
                throw;
            }
        }
예제 #14
0
        private Packet?FilterBlockedServerPackets(Packet rawPacket)
        {
            if (rawPacket.Id == PacketDefinitions.OverallLightLevel.Id && enabled)
            {
                lastOverallLightLevelRawPacket = rawPacket.Clone();
                var lastOverallLightLevelPacket =
                    PacketDefinitionRegistry.Materialize <OverallLightLevelPacket>(lastOverallLightLevelRawPacket
                                                                                   .Value);
                this.player.LightLevel = lastOverallLightLevelPacket.Level;

                return(CreateFullLightLevelPacket());
            }

            return(rawPacket);
        }
예제 #15
0
        public void Publish <TPacket>(Packet rawPacket) where TPacket : MaterializedPacket
        {
            ImmutableList <Delegate> observerList;

            if (observers.TryGetValue(rawPacket.Id, out observerList))
            {
                var packet =
                    PacketDefinitionRegistry.Materialize <TPacket>(rawPacket);

                foreach (var observer in observerList)
                {
                    var observerAction = (Action <TPacket>)observer;
                    observerAction(packet);
                }
            }
        }
예제 #16
0
        private Packet?FilterServerPackets(Packet rawPacket)
        {
            if (rawPacket.Id == PacketDefinitions.OpenDialogBox.Id)
            {
                var packet    = PacketDefinitionRegistry.Materialize <OpenDialogBoxPacket>(rawPacket);
                var dialogBox = new DialogBox(packet.DialogId, packet.MenuId, packet.Question, packet.Responses);
                CurrentDialogBox = dialogBox;
                eventJournalSource.Publish(new DialogBoxOpenedEvent(dialogBox));

                if (!ShowDialogBox)
                {
                    return(null);
                }
            }

            return(rawPacket);
        }
예제 #17
0
        private Packet?FilterSendGumpMenuDialog(Packet rawPacket)
        {
            if (rawPacket.Id == PacketDefinitions.GeneralInformationPacket.Id && rawPacket.Payload[4] == 4)
            {
                var packet = new CloseGenericGumpPacket();
                packet.Deserialize(rawPacket);

                eventSource.Publish(new ServerRequestedGumpCloseEvent(packet.GumpTypeId));
            }
            if (rawPacket.Id == PacketDefinitions.SendGumpMenuDialog.Id)
            {
                var nextGumpNotVisible = false;

                lock (gumpLock)
                {
                    var packet = PacketDefinitionRegistry.Materialize <SendGumpMenuDialogPacket>(rawPacket);
                    var gump   = new Gump(packet.GumpId, packet.GumpTypeId, packet.Commands, packet.TextLines);
                    CurrentGump = gump;
                    eventSource.Publish(new GumpReceivedEvent(gump));

                    if (!showNextAwaitedGump)
                    {
                        currentGumpVisible  = false;
                        nextGumpNotVisible  = true;
                        showNextAwaitedGump = true;
                    }
                    else
                    {
                        currentGumpVisible = true;
                    }
                }

                gumpReceivedEvent.Set();

                if (nextGumpNotVisible)
                {
                    return(null);
                }
            }

            return(rawPacket);
        }
예제 #18
0
        private Packet?FilterItemShapes(Packet rawPacket)
        {
            if (enabled && rawPacket.Id == PacketDefinitions.ObjectInfo.Id)
            {
                var packet = PacketDefinitionRegistry.Materialize <ObjectInfoPacket>(rawPacket);

                foreach (var def in itemShapeShiftDefinitions)
                {
                    if (def.SourceSpec.Matches(packet.Type))
                    {
                        var newPacket =
                            new ObjectInfoPacket(packet.Id, def.TargetType, packet.Location, def.TargetColor ?? packet.Dye);

                        return(newPacket.RawPacket);
                    }
                }
            }

            return(rawPacket);
        }
예제 #19
0
        private Packet?FilterBlockedSounds(Packet rawPacket)
        {
            var sounds = filteredSounds;

            if (sounds != null)
            {
                if (rawPacket.Id == PacketDefinitions.PlaySoundEffect.Id)
                {
                    PlaySoundEffectPacket packet =
                        PacketDefinitionRegistry.Materialize <PlaySoundEffectPacket>(rawPacket);

                    var ev = new SoundEffectPlayedEvent(packet.Id, packet.Location);
                    eventJournalSource.Publish(ev);

                    if (sounds.Contains(packet.Id))
                    {
                        return(null);
                    }
                }
            }

            return(rawPacket);
        }
예제 #20
0
        public void Can_materialize_packet()
        {
            var packet = PacketDefinitionRegistry.Materialize <ConnectToGameServerPacket>(FakePackets.ConnectToGameServerPacket);

            packet.Should().NotBeNull();
        }