Beispiel #1
0
        public IEnumerable <Variable> GetVariables(EVariableNamespace scope, params string[] names)
        {
            var command = new asapJson.JsonNode(new Dictionary <string, asapJson.JsonNode>());

            command.GetValue_Object()["command"] = new asapJson.JsonNode((int)ESendCommands.GetVariable);
            var data = command.GetValue_Object()["data"] = new asapJson.JsonNode(new Dictionary <string, asapJson.JsonNode>());

            data.GetValue_Object()["name"]  = new asapJson.JsonNode(names.Select(name => new asapJson.JsonNode(name)));
            data.GetValue_Object()["scope"] = new asapJson.JsonNode((int)scope);
            this.WriteMessage(command);


            var response = this.ReadMessage((node) => (int)(node.GetValue_Object()["command"].GetValue_Number()) == (int)ERecvCommands.VariablesList);

            var variables = response.GetValue_Object()["data"];

            if (variables.GetValueType() == JsonNode.EJType.Array) //Might be null if no variables found
            {
                foreach (var variable in variables.GetValue_Array())
                {
                    var name  = variable.GetValue_Object()["name"].GetValue_String();
                    var type  = variable.GetValue_Object()["type"].GetValue_String();
                    var value = "";
                    switch (type)
                    {
                    case "void":
                        yield return(new Variable()
                        {
                            Name = name, Value = value, VariableType = Variable.ValueType.ANY
                        });

                        break;

                    case "array":
                    {
                        value = VariableArrayToString(variable.GetValue_Object()["value"]);
                        var ns = (EVariableNamespace)variable.GetValue_Object()["ns"].GetValue_Number();    //Namespace the variable comes from
                        yield return(new Variable()
                            {
                                Name = name, Value = value, VariableType = Variable.ValueType.ARRAY, Namespace = ns
                            });
                    }
                    break;

                    default:
                    {
                        value = variable.GetValue_Object()["value"].GetValue_String();
                        var ns = (EVariableNamespace)variable.GetValue_Object()["ns"].GetValue_Number();    //Namespace the variable comes from
                        yield return(new Variable()
                            {
                                Name = name, Value = value, VariableType = Variable.ValueType.Parse(type), Namespace = ns
                            });
                    }
                    break;
                    }
                }
            }
        }
Beispiel #2
0
 public void UpdateBreakpoint(Breakpoint b)
 {
     {
         var command = new asapJson.JsonNode(new Dictionary <string, asapJson.JsonNode>());
         command.GetValue_Object()["command"] = new asapJson.JsonNode((int)ESendCommands.AddBreakpoint);
         command.GetValue_Object()["data"]    = b.Serialize();
         this.WriteMessage(command);
     }
 }
Beispiel #3
0
        public bool Perform(EOperation op)
        {
            switch (op)
            {
            case EOperation.Continue:
            {
                var node = new asapJson.JsonNode(new Dictionary <string, asapJson.JsonNode>());
                node.GetValue_Object()["command"] = new asapJson.JsonNode((int)ESendCommands.ContinueExecution);
                node.GetValue_Object()["data"]    = new asapJson.JsonNode((int)EStepType.Continue);
                this.WriteMessage(node);
                return(true);
            }

            case EOperation.StepInto:
            {
                var node = new asapJson.JsonNode(new Dictionary <string, asapJson.JsonNode>());
                node.GetValue_Object()["command"] = new asapJson.JsonNode((int)ESendCommands.ContinueExecution);
                node.GetValue_Object()["data"]    = new asapJson.JsonNode((int)EStepType.StepInto);
                this.WriteMessage(node);
                return(true);
            }

            case EOperation.StepOver:
            {
                var node = new asapJson.JsonNode(new Dictionary <string, asapJson.JsonNode>());
                node.GetValue_Object()["command"] = new asapJson.JsonNode((int)ESendCommands.ContinueExecution);
                node.GetValue_Object()["data"]    = new asapJson.JsonNode((int)EStepType.StepOver);
                this.WriteMessage(node);
                return(true);
            }

            case EOperation.StepOut:
            {
                var node = new asapJson.JsonNode(new Dictionary <string, asapJson.JsonNode>());
                node.GetValue_Object()["command"] = new asapJson.JsonNode((int)ESendCommands.ContinueExecution);
                node.GetValue_Object()["data"]    = new asapJson.JsonNode((int)EStepType.StepOut);
                this.WriteMessage(node);
                return(true);
            }

            default:
                this.LastError = "Not Implemented";
                return(false);
            }
        }
Beispiel #4
0
        public bool Attach()
        {
            if (this.Pipe != null && this.Pipe.IsConnected)
            {
                throw new InvalidOperationException();
            }
            if (this.Pipe != null)
            {
                this.Pipe.Dispose();
            }

            this.Pipe = new NamedPipeClientStream(".", @"ArmaDebugEnginePipeIface", PipeDirection.InOut, PipeOptions.Asynchronous, System.Security.Principal.TokenImpersonationLevel.None, System.IO.HandleInheritability.None);

            this.Breakpoints = new List <Breakpoint>();
            try
            {
                this.Pipe.Connect(1000);
                this.Pipe.ReadMode  = PipeTransmissionMode.Message;
                this.PipeReadThread = new Thread(Thread_ReadPipeMessage);
                this.PipeReadThread.Start();
            }
            catch (TimeoutException ex)
            {
                this.LastError = ex.Message;
                this.Pipe      = null;
                return(false);
            }

            var command = new asapJson.JsonNode(new Dictionary <string, asapJson.JsonNode>());

            command.GetValue_Object()["command"] = new asapJson.JsonNode((int)ESendCommands.GetVersionInfo);
            this.WriteMessage(command);
            var response = this.ReadMessage((node) => (int)(node.GetValue_Object()["command"].GetValue_Number()) == (int)ERecvCommands.VersionInfo);

            if (response.GetValue_Object()["gameType"].GetValueType() == JsonNode.EJType.String) //Might be null if init failed or attached too soon
            {
                var gameType = response.GetValue_Object()["gameType"].GetValue_String();
            }
            if (response.GetValue_Object()["gameVersion"].GetValueType() == JsonNode.EJType.String) //Might be null if init failed or attached too soon
            {
                var gameVersion = response.GetValue_Object()["gameVersion"].GetValue_String();
            }
            var arch    = response.GetValue_Object()["arch"].GetValue_String();
            var build   = response.GetValue_Object()["build"].GetValue_Number();
            var version = response.GetValue_Object()["version"].GetValue_String();

            if (build < MinimalDebuggerBuild)
            {
                this.LastError = "Unsupported Debugger build: " + build + " \nMinimal build required: " + MinimalDebuggerBuild;
                Detach();
                return(false);
            }
            return(true);
        }
Beispiel #5
0
        private void Thread_ReadPipeMessage()
        {
            try
            {
                var buffer = new byte[2048];
                while (this.Pipe.IsConnected)
                {
                    var builder = new StringBuilder();
                    do
                    {
                        var ammount = this.Pipe.Read(buffer, 0, buffer.Length);
                        for (int i = 0; i < ammount; i++)
                        {
                            builder.Append((char)buffer[i]);
                        }
                    } while (!this.Pipe.IsMessageComplete);
                    if (builder.Length > 0)
                    {
                        var node = new asapJson.JsonNode(builder.ToString(), true);
                        Logger.Log(NLog.LogLevel.Info, string.Format("RECV {0}", node.ToString()));
                        if (node.GetValue_Object().ContainsKey("exception"))
                        {
                            this.OnError?.Invoke(this, new OnErrorEventArgs()
                            {
                                Message = node.GetValue_Object()["exception"].GetValue_String()
                            });
                        }
                        else
                        {
                            switch ((ERecvCommands)node.GetValue_Object()["command"].GetValue_Number())
                            {
                            case ERecvCommands.HaltBreakpoint:
                            case ERecvCommands.HaltStep:
                            {
                                var callstack      = this.LastCallstack = node.GetValue_Object()["callstack"];
                                var instruction    = node.GetValue_Object()["instruction"];
                                var fileOffsetNode = instruction.GetValue_Object()["fileOffset"];
                                var line           = (int)fileOffsetNode.GetValue_Array()[0].GetValue_Number();
                                var col            = (int)fileOffsetNode.GetValue_Array()[2].GetValue_Number();
                                this.OnHalt?.Invoke(this, new OnHaltEventArgs()
                                    {
                                        DocumentPath = instruction.GetValue_Object()["filename"].GetValue_String(), Col = col, Line = line
                                    });
                            }
                            break;

                            case ERecvCommands.HaltError:
                            {
                                var callstack      = this.LastCallstack = node.GetValue_Object()["callstack"];
                                var error          = node.GetValue_Object()["error"];
                                var fileOffsetNode = error.GetValue_Object()["fileOffset"];
                                var errorMessage   = error.GetValue_Object()["message"];     //ToDo: display to user
                                var fileContent    = error.GetValue_Object()["content"];     //File content in case we don't have that file
                                var line           = (int)fileOffsetNode.GetValue_Array()[0].GetValue_Number();
                                var col            = (int)fileOffsetNode.GetValue_Array()[2].GetValue_Number();
                                this.OnHalt?.Invoke(this, new OnHaltEventArgs()
                                    {
                                        DocumentPath = error.GetValue_Object()["filename"].GetValue_String(), Col = col, Line = line
                                    });
                            }
                            break;

                            case ERecvCommands.HaltScriptAssert:
                            case ERecvCommands.HaltScriptHalt:
                            {
                                var callstack      = this.LastCallstack = node.GetValue_Object()["callstack"];
                                var error          = node.GetValue_Object()["halt"];
                                var fileOffsetNode = error.GetValue_Object()["fileOffset"];
                                var fileContent    = error.GetValue_Object()["content"];     //File content in case we don't have that file
                                var line           = (int)fileOffsetNode.GetValue_Array()[0].GetValue_Number();
                                var col            = (int)fileOffsetNode.GetValue_Array()[2].GetValue_Number();
                                this.OnHalt?.Invoke(this, new OnHaltEventArgs()
                                    {
                                        DocumentPath = error.GetValue_Object()["filename"].GetValue_String(), Col = col, Line = line
                                    });
                            }
                            break;

                            case ERecvCommands.ContinueExecution:
                            {
                                this.OnContinue?.Invoke(this, new OnContinueEventArgs()
                                    {
                                    });
                            }
                            break;

                            default:
                                this.Messages.Add(node);
                                break;
                            }
                        }
                    }
                    Thread.Sleep(10);
                }
            }
            catch (ObjectDisposedException) { }
        }