diff --git a/NTRDebuggerTool.sln b/NTRDebuggerTool.sln index d2975f5..a5010af 100644 --- a/NTRDebuggerTool.sln +++ b/NTRDebuggerTool.sln @@ -1,8 +1,6 @@  Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio 14 -VisualStudioVersion = 14.0.23107.0 -MinimumVisualStudioVersion = 10.0.40219.1 +# Visual Studio 2012 Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "NTRDebuggerTool", "NTRDebuggerTool\NTRDebuggerTool.csproj", "{86AF1318-9584-4CDE-93BC-C2F0DCF958C5}" EndProject Global @@ -19,4 +17,7 @@ Global GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE EndGlobalSection + GlobalSection(Performance) = preSolution + HasPerformanceSessions = true + EndGlobalSection EndGlobal diff --git a/NTRDebuggerTool/App.config b/NTRDebuggerTool/App.config index 8e15646..5353446 100644 --- a/NTRDebuggerTool/App.config +++ b/NTRDebuggerTool/App.config @@ -1,6 +1,26 @@ - + - - - - \ No newline at end of file + +
+ + + + + + + + + + + + + + + + + + + + + + diff --git a/NTRDebuggerTool/Config.cs b/NTRDebuggerTool/Config.cs index a73a2db..a8b7ae9 100644 --- a/NTRDebuggerTool/Config.cs +++ b/NTRDebuggerTool/Config.cs @@ -233,7 +233,7 @@ private static void CreateConfigFile() #region XML Stuff - private static string ConfigFileDirectory = Directory.GetParent(Application.UserAppDataPath).FullName; + public static string ConfigFileDirectory = Directory.GetParent(Application.UserAppDataPath).FullName; private static string ConfigFilePath = ConfigFileDirectory + Path.DirectorySeparatorChar + "NTRDebuggerTool.config.xml"; private static XmlDocument ConfigFile; diff --git a/NTRDebuggerTool/ConsoleHelper.cs b/NTRDebuggerTool/ConsoleHelper.cs new file mode 100644 index 0000000..c283f77 --- /dev/null +++ b/NTRDebuggerTool/ConsoleHelper.cs @@ -0,0 +1,33 @@ +using System; +using System.Runtime.InteropServices; + +namespace NTRDebuggerTool +{ + class ConsoleHelper + { + [DllImport("kernel32.dll", SetLastError = true)] + static extern bool AllocConsole(); + + [DllImport("kernel32.dll")] + static extern IntPtr GetConsoleWindow(); + + [DllImport("user32.dll")] + static extern bool ShowWindow(IntPtr hWnd, int nCmdShow); + + const int SW_HIDE = 0; + const int SW_SHOW = 5; + + public static void EnableConsole() + { + IntPtr Handle = GetConsoleWindow(); + if (Handle == IntPtr.Zero) + { + AllocConsole(); + } + else + { + ShowWindow(Handle, SW_SHOW); + } + } + } +} diff --git a/NTRDebuggerTool/Debug.cs b/NTRDebuggerTool/Debug.cs index e01ff41..2bb1a98 100644 --- a/NTRDebuggerTool/Debug.cs +++ b/NTRDebuggerTool/Debug.cs @@ -3,38 +3,15 @@ using NTRDebuggerTool.Remote; using System; using System.Collections.Generic; -using System.Collections.ObjectModel; using System.IO; -using System.Runtime.InteropServices; using System.Threading; namespace NTRDebuggerTool { class Debug { - [DllImport("kernel32.dll", SetLastError = true)] - static extern bool AllocConsole(); - - [DllImport("kernel32.dll")] - static extern IntPtr GetConsoleWindow(); - - [DllImport("user32.dll")] - static extern bool ShowWindow(IntPtr hWnd, int nCmdShow); - - const int SW_HIDE = 0; - const int SW_SHOW = 5; - internal static void Execute() { - IntPtr Handle = GetConsoleWindow(); - if (Handle == IntPtr.Zero) - { - AllocConsole(); - } - else - { - ShowWindow(Handle, SW_SHOW); - } NTRRemoteConnection Conn = new NTRRemoteConnection(); Console.WriteLine("Connecting..."); Conn.IP = "192.168.1.29"; @@ -57,7 +34,7 @@ internal static void Execute() { Thread.Sleep(10); } - Dictionary> Procs = new Dictionary>(); + Dictionary> Procs = new Dictionary>(); foreach (string ProcFull in Conn.Processes) { string Proc = ProcFull.Split('|')[0]; diff --git a/NTRDebuggerTool/Forms/FormEnums/DataType.cs b/NTRDebuggerTool/Forms/FormEnums/DataType.cs index c37db51..043e68f 100644 --- a/NTRDebuggerTool/Forms/FormEnums/DataType.cs +++ b/NTRDebuggerTool/Forms/FormEnums/DataType.cs @@ -28,6 +28,18 @@ public static DataTypeExact GetValue(string key) { return Mapping[key]; } + + public static string GetKey(DataTypeExact value) + { + foreach (string key in Mapping.Keys) + { + if (Mapping[key] == value) + { + return key; + } + } + return null; + } } public enum DataTypeExact diff --git a/NTRDebuggerTool/Forms/MainForm.cs b/NTRDebuggerTool/Forms/MainForm.cs index 1479a79..6784b36 100644 --- a/NTRDebuggerTool/Forms/MainForm.cs +++ b/NTRDebuggerTool/Forms/MainForm.cs @@ -1,11 +1,12 @@ using NTRDebuggerTool.Forms.FormEnums; using NTRDebuggerTool.Objects; +using NTRDebuggerTool.Objects.Saving; using NTRDebuggerTool.Remote; using System; using System.Collections.Generic; using System.Diagnostics; +using System.IO; using System.Linq; -using System.Text.RegularExpressions; using System.Threading; using System.Windows.Forms; @@ -37,8 +38,6 @@ public partial class MainForm : Form internal bool FormEnabled = true; - private bool LoadAddresses = false; - private Thread EventDispatcherThread; private Thread ButtonStateThread; @@ -54,13 +53,8 @@ public partial class MainForm : Form internal SearchCriteria LastSearchCriteria; - private Regex HexRegex = new Regex("^[0-9A-F]+$", RegexOptions.Compiled | RegexOptions.IgnoreCase); - private Regex ParserRegex = new Regex("\\(\\*(?
.+)\\)(?(?:\\[[0-9A-F]+\\])?)", RegexOptions.Compiled | RegexOptions.IgnoreCase); - private Stopwatch LockValuesStopwatch = new Stopwatch(); - private Dictionary Pointers = new Dictionary(); - public MainForm(NTRRemoteConnection NTRConnection) { InitializeComponent(); @@ -255,7 +249,6 @@ private void GUIUpdateTimer_Tick(object sender, EventArgs e) { if (LockValuesStopwatch.ElapsedMilliseconds > Config.LockValuesDelay) { - Pointers.Clear(); for (int i = 0; i < ValuesGrid.Rows.Count; ++i) { if (ValuesGrid[0, i].Value is string) @@ -263,7 +256,6 @@ private void GUIUpdateTimer_Tick(object sender, EventArgs e) SetMemory(i); } } - Pointers.Clear(); LockValuesStopwatch.Restart(); } } @@ -273,6 +265,16 @@ private void GUIUpdateTimer_Tick(object sender, EventArgs e) ValuesGrid[1, PointerSearchRow].Value = ThreadEventDispatcher.FoundPointerAddress; ThreadEventDispatcher.FoundPointerAddress = null; } + + if (ThreadEventDispatcher.RefreshValueReturn.Count > 0) + { + MemoryDispatch MemoryDispatch; + while (ThreadEventDispatcher.RefreshValueReturn.TryDequeue(out MemoryDispatch)) + { + ValuesGrid[1, MemoryDispatch.Row].ToolTipText = MemoryDispatch.ResolvedAddress; + ValuesGrid[2, MemoryDispatch.Row].Value = GetDisplayForByteArray(MemoryDispatch.Value, MemoryDispatch.Type); + } + } } public string GetDisplayForByteArray(byte[] p) @@ -308,7 +310,7 @@ internal uint GetSearchMemorySize() return GetSearchMemorySize(ThreadEventDispatcher.CurrentSelectedDataType); } - private uint GetSearchMemorySize(DataTypeExact DataType) + internal uint GetSearchMemorySize(DataTypeExact DataType) { switch (DataType) { @@ -386,9 +388,7 @@ private void ValuesGrid_CellValueChanged(object sender, DataGridViewCellEventArg { if (e.RowIndex >= 0 && e.ColumnIndex == 2) { - Pointers.Clear(); SetMemory(e.RowIndex); - Pointers.Clear(); } } @@ -396,152 +396,37 @@ private void SetMemory(int RowIndex) { string TextAddress = (string)ValuesGrid[1, RowIndex].Value; - uint Address; + MemoryDispatch MemoryDispatch = new MemoryDispatch(); + MemoryDispatch.Row = RowIndex; + MemoryDispatch.TextAddress = TextAddress; + MemoryDispatch.Type = DataTypeExactTool.GetValue((string)ValuesGrid[3, RowIndex].Value); + MemoryDispatch.Value = GetByteArrayForDataType(MemoryDispatch.Type, (string)ValuesGrid[2, RowIndex].Value); - if (HexRegex.IsMatch(TextAddress)) - { - Address = BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString((string)ValuesGrid[1, RowIndex].Value).Reverse().ToArray(), 0); ; - } - else - { - Match TopMatch = ParserRegex.Match(TextAddress); - - if (!TopMatch.Success) - { - return; - } - - Address = ResolvePointer(TopMatch); - } - - if (IsValidMemoryAddress(Address) && !LoadAddresses) - { - ValuesGrid[1, RowIndex].ToolTipText = Utilities.GetStringFromByteArray(BitConverter.GetBytes(Address).Reverse().ToArray()); - uint ProcessID = BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(Processes.Text.Split('|')[0]), 0); - switch (DataTypeExactTool.GetValue((string)ValuesGrid[3, RowIndex].Value)) - { - case DataTypeExact.Bytes1: //1 Byte - NTRConnection.SendWriteMemoryPacket( - ProcessID, - Address, - (byte)uint.Parse((string)ValuesGrid[2, RowIndex].Value)); - break; - case DataTypeExact.Bytes2: //2 Bytes - NTRConnection.SendWriteMemoryPacket( - ProcessID, - Address, - ushort.Parse((string)ValuesGrid[2, RowIndex].Value)); - break; - case DataTypeExact.Bytes4: //4 Bytes - NTRConnection.SendWriteMemoryPacket( - ProcessID, - Address, - uint.Parse((string)ValuesGrid[2, RowIndex].Value)); - break; - case DataTypeExact.Bytes8: //8 Bytes - NTRConnection.SendWriteMemoryPacket( - ProcessID, - Address, - ulong.Parse((string)ValuesGrid[2, RowIndex].Value)); - break; - case DataTypeExact.Float: //Float - NTRConnection.SendWriteMemoryPacket( - ProcessID, - Address, - float.Parse((string)ValuesGrid[2, RowIndex].Value)); - break; - case DataTypeExact.Double: //Double - NTRConnection.SendWriteMemoryPacket( - ProcessID, - Address, - double.Parse((string)ValuesGrid[2, RowIndex].Value)); - break; - case DataTypeExact.Raw: //Raw Bytes - NTRConnection.SendWriteMemoryPacket( - ProcessID, - Address, - Utilities.GetByteArrayFromByteString((string)ValuesGrid[2, RowIndex].Value)); - break; - case DataTypeExact.Text: //Raw Bytes - NTRConnection.SendWriteMemoryPacket( - ProcessID, - Address, - System.Text.Encoding.Default.GetBytes((string)ValuesGrid[2, RowIndex].Value)); - break; - } - } + ThreadEventDispatcher.WriteAddress.Enqueue(MemoryDispatch); } - private uint ResolvePointer(Match Match) + private byte[] GetByteArrayForDataType(DataTypeExact DataType, string Value) { - string AddressString = Match.Groups["Address"].Value; - string OffsetString = Match.Groups["Offset"].Value; - - - uint Address; - - Match RecurseMatch = ParserRegex.Match(AddressString); - - if (RecurseMatch.Success) - { - Address = ResolvePointer(RecurseMatch); - } - else - { - uint Pointer = BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(AddressString).Reverse().ToArray(), 0); - if (!Pointers.ContainsKey(Pointer)) - { - byte[] Data = GetMemoryAtAddress(Processes.Text.Split('|')[0], AddressString, DataTypeExact.Bytes4); - - Address = BitConverter.ToUInt32(Data, 0); - Pointers[Pointer] = Address; - } - else if (!IsValidMemoryAddress(Pointer)) - { - return 0; - } - else - { - Address = Pointers[Pointer]; - } - } - - if (Address != 0 && !string.IsNullOrWhiteSpace(OffsetString)) + switch (DataType) { - OffsetString = OffsetString.Replace("[", "").Replace("]", ""); - Address += BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(OffsetString.PadLeft(8, '0')).Reverse().ToArray(), 0); + case DataTypeExact.Bytes1: //1 Byte + return new byte[] { (byte)uint.Parse(Value) }; + case DataTypeExact.Bytes2: //2 Bytes + return BitConverter.GetBytes(ushort.Parse(Value)); + case DataTypeExact.Bytes4: //4 Bytes + return BitConverter.GetBytes(uint.Parse(Value)); + case DataTypeExact.Bytes8: //8 Bytes + return BitConverter.GetBytes(ulong.Parse(Value)); + case DataTypeExact.Float: //Float + return BitConverter.GetBytes(float.Parse(Value)); + case DataTypeExact.Double: //Double + return BitConverter.GetBytes(double.Parse(Value)); + case DataTypeExact.Raw: //Raw Bytes + return Utilities.GetByteArrayFromByteString(Value); + case DataTypeExact.Text: //Raw Bytes + default: + return System.Text.Encoding.Default.GetBytes(Value); } - - return Address; - } - - private byte[] GetMemoryAtAddress(string ProcessID, string Address, DataTypeExact DataType) - { - return GetMemoryAtAddress(BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(ProcessID), 0), BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(Address).Reverse().ToArray(), 0), DataType); - } - - private byte[] GetMemoryAtAddress(uint ProcessID, string Address, DataTypeExact DataType) - { - return GetMemoryAtAddress(ProcessID, BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(Address).Reverse().ToArray(), 0), DataType); - } - - private byte[] GetMemoryAtAddress(string ProcessID, uint Address, DataTypeExact DataType) - { - return GetMemoryAtAddress(BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(ProcessID), 0), Address, DataType); - } - - private byte[] GetMemoryAtAddress(uint ProcessID, uint Address, DataTypeExact DataType) - { - SearchCriteria Criteria = new SearchCriteria(); - Criteria.ProcessID = ProcessID; - Criteria.DataType = DataType; - Criteria.StartAddress = Address; - Criteria.Length = Criteria.Size = GetSearchMemorySize(DataType); - Criteria.SearchType = SearchTypeBase.Unknown; - Criteria.SearchValue = new byte[] { 0 }; - NTRConnection.SearchCriteria.Add(Criteria); - NTRConnection.SendReadMemoryPacket(Criteria); - return Criteria.AddressesFound.Values.First(); } private void ValuesGrid_CellClick(object sender, DataGridViewCellEventArgs e) @@ -629,75 +514,68 @@ private void SearchButton_Click(object sender, EventArgs e) private void SaveButton_Click(object sender, EventArgs e) { - List addr = new List(); // 1 - List type = new List(); // 3 - + SaveManager sm = new SaveManager(); + sm.Init(); // Get a list of all saved addresses foreach (DataGridViewRow row in ValuesGrid.Rows) { - addr.Add(row.Cells[1].Value.ToString()); - type.Add( - (int)DataTypeExactTool.GetValue(row.Cells[3].Value.ToString()) - ); + if (row.Cells[1].Value is GateSharkCode) + { + // @TODO This will be different. + } + else + { + sm.codes.Add(new SaveCode(DataTypeExactTool.GetValue(row.Cells[3].Value.ToString()), row.Cells[1].Value.ToString())); + } } // Set the values - SaveManager sm = new SaveManager(); - sm.addr = addr.ToArray(); - sm.type = type.ToArray(); - String[] parts_ = Processes.Text?.Split('|'); + String[] parts_ = Processes.Text.Split('|'); if (parts_.Length < 2) return; - String game = parts_?[1] + @".xml"; + String game = Config.ConfigFileDirectory + Path.DirectorySeparatorChar + parts_[1] + @".xml"; + sm.titleId = parts_[1]; SaveManager.SaveToXml(game, sm); MessageBox.Show(@"Saved selected addresses to '" + game + "'"); } private void LoadButton_Click(object sender, EventArgs e) { - String[] parts_ = Processes.Text?.Split('|'); + String[] parts_ = Processes.Text.Split('|'); if (parts_.Length < 2) return; - String game = parts_?[1] + @".xml"; + String game = Config.ConfigFileDirectory + Path.DirectorySeparatorChar + parts_[1] + @".xml"; SaveManager sm = SaveManager.LoadFromXml(game); - sm.Init(); - String[] addr = sm.addr; - int[] type = sm.type; - if (addr.Length != type.Length) - { - MessageBox.Show(@"Invalid size of the savefile"); - } else if (addr.Length == 0 || type.Length == 0) + if (sm.titleId != parts_[1]) { - MessageBox.Show(@"No addresses found"); - } else + MessageBox.Show(@"Filename/TitleID Mismatch."); + } + else { - LoadAddresses = true; - - for (int i = 0; i < addr.Length; i++) + foreach (SaveCode code in sm.codes) { - - if (!IsInValues(addr[i])) + if (!IsInValues(code.address)) { int RowIndex = ValuesGrid.Rows.Add(); ValuesGrid[0, RowIndex].Value = null; - ValuesGrid[3, RowIndex].Value = DataTypeExactTool.GetValues()[type[i] - 1]; - ValuesGrid[1, RowIndex].Value = addr[i]; + ValuesGrid[3, RowIndex].Value = DataTypeExactTool.GetKey(code.type); + ValuesGrid[1, RowIndex].Value = code.address; // Read the memory - - - DataTypeExact DataType = DataTypeExactTool.GetValue((string)ValuesGrid[3, RowIndex].Value); - - byte[] Value = GetMemoryAtAddress(Processes.Text.Split('|')[0], (string) ValuesGrid[1, RowIndex].Value, DataType); - - ValuesGrid[2, RowIndex].Value = GetDisplayForByteArray(Value, DataType); + RefreshMemory(RowIndex); } - } - LoadAddresses = false; - - } } + private void RefreshMemory(int RowIndex) + { + ThreadEventDispatcher.CurrentSelectedProcess = Processes.Text.Split('|')[0]; + MemoryDispatch MemoryDispatch = new MemoryDispatch(); + MemoryDispatch.Row = RowIndex; + MemoryDispatch.TextAddress = (string)ValuesGrid[1, RowIndex].Value; + MemoryDispatch.Type = DataTypeExactTool.GetValue((string)ValuesGrid[3, RowIndex].Value); + ThreadEventDispatcher.RefreshValueAddresses.Enqueue(MemoryDispatch); + } + private void ComboSearchType_SelectedValueChanged(object sender, EventArgs e) { string CurrentDataType = ComboDataType.SelectedItem == null ? null : ComboDataType.SelectedItem.ToString(); @@ -822,37 +700,7 @@ private void ValuesGridContextMenuStrip_ItemClicked(object sender, ToolStripItem case "ValuesGridRefreshItem": foreach (DataGridViewCell Cell in ValuesGrid.SelectedCells) { - string TextAddress = (string)Cell.OwningRow.Cells[1].Value; - uint Address; - - if (HexRegex.IsMatch(TextAddress)) - { - Address = BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(TextAddress).Reverse().ToArray(), 0); ; - } - else - { - Match TopMatch = ParserRegex.Match(TextAddress); - - if (!TopMatch.Success) - { - return; - } - - Pointers.Clear(); - Address = ResolvePointer(TopMatch); - Pointers.Clear(); - } - - if (!IsValidMemoryAddress(Address) || Cell.OwningRow.Cells[3].Value == null) - { - continue; - } - - DataTypeExact DataType = DataTypeExactTool.GetValue((string)Cell.OwningRow.Cells[3].Value); - - byte[] Value = GetMemoryAtAddress(Processes.Text.Split('|')[0], Address, DataType); - - Cell.OwningRow.Cells[2].Value = GetDisplayForByteArray(Value, DataType); + RefreshMemory(Cell.RowIndex); } break; } @@ -885,7 +733,7 @@ private string ConvertCode(string Address) return Address; } - private bool IsValidMemoryAddress(uint Address) + internal bool IsValidMemoryAddress(uint Address) { return GetAddressSpaceForAddress(Address) != null; } diff --git a/NTRDebuggerTool/Forms/MainFormThreadEventDispatcher.cs b/NTRDebuggerTool/Forms/MainFormThreadEventDispatcher.cs index 19d7f09..0cb6bcf 100644 --- a/NTRDebuggerTool/Forms/MainFormThreadEventDispatcher.cs +++ b/NTRDebuggerTool/Forms/MainFormThreadEventDispatcher.cs @@ -1,7 +1,10 @@ using NTRDebuggerTool.Forms.FormEnums; using NTRDebuggerTool.Objects; using System; +using System.Collections.Concurrent; +using System.Collections.Generic; using System.Linq; +using System.Text.RegularExpressions; using System.Threading; using System.Windows.Forms; @@ -14,6 +17,9 @@ class MainFormThreadEventDispatcher internal bool DispatchSearch = false; internal bool DispatchConfig = false; internal string DispatchPointerSearch = null; + public ConcurrentQueue RefreshValueAddresses = new ConcurrentQueue(), + RefreshValueReturn = new ConcurrentQueue(), + WriteAddress = new ConcurrentQueue(); internal string CurrentSelectedProcess = ""; internal string CurrentMemoryRange = ""; @@ -23,6 +29,9 @@ class MainFormThreadEventDispatcher internal string FoundPointerAddress = null; private MainForm Form; + private Regex HexRegex = new Regex("^[0-9A-F]+$", RegexOptions.Compiled | RegexOptions.IgnoreCase); + private Regex ParserRegex = new Regex("\\(\\*(?
.+)\\)(?(?:\\[[0-9A-F]+\\])?)", RegexOptions.Compiled | RegexOptions.IgnoreCase); + private Dictionary Pointers = new Dictionary(); internal MainFormThreadEventDispatcher(MainForm Form) { @@ -60,6 +69,42 @@ internal void ThreadEventDispatcher() DispatchPointerSearch = null; DoPointerSearch(TempAddress); } + while (RefreshValueAddresses.Count > 0) + { + MemoryDispatch Row = new MemoryDispatch(); + RefreshValueAddresses.TryDequeue(out Row); + Row.Value = GetMemoryAtAddress(CurrentSelectedProcess, Row.TextAddress, Row.Type); + RefreshValueReturn.Enqueue(Row); + } + while (WriteAddress.Count > 0) + { + MemoryDispatch Row = new MemoryDispatch(); + WriteAddress.TryDequeue(out Row); + uint Address; + + if (HexRegex.IsMatch(Row.TextAddress)) + { + Address = BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(Row.TextAddress).Reverse().ToArray(), 0); ; + } + else + { + Match TopMatch = ParserRegex.Match(Row.TextAddress); + + if (!TopMatch.Success) + { + return; + } + + Address = ResolvePointer(TopMatch); + } + + if (Form.IsValidMemoryAddress(Address)) + { + Row.ResolvedAddress = Utilities.GetStringFromByteArray(BitConverter.GetBytes(Address).Reverse().ToArray()); + uint ProcessID = BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(CurrentSelectedProcess.Split('|')[0]), 0); + Form.NTRConnection.SendWriteMemoryPacket(ProcessID, Address, Row.Value); + } + } Thread.Sleep(100); } @@ -244,5 +289,77 @@ private byte[] GetValueForDataType(DataTypeExact CurrentSelectedDataType, string return System.Text.Encoding.Default.GetBytes(Value); } } + + private uint ResolvePointer(Match Match) + { + string AddressString = Match.Groups["Address"].Value; + string OffsetString = Match.Groups["Offset"].Value; + + + uint Address; + + Match RecurseMatch = ParserRegex.Match(AddressString); + + if (RecurseMatch.Success) + { + Address = ResolvePointer(RecurseMatch); + } + else + { + uint Pointer = BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(AddressString).Reverse().ToArray(), 0); + if (!Pointers.ContainsKey(Pointer)) + { + byte[] Data = GetMemoryAtAddress(CurrentSelectedProcess, AddressString, DataTypeExact.Bytes4); + + Address = BitConverter.ToUInt32(Data, 0); + Pointers[Pointer] = Address; + } + else if (!Form.IsValidMemoryAddress(Pointer)) + { + return 0; + } + else + { + Address = Pointers[Pointer]; + } + } + + if (Address != 0 && !string.IsNullOrWhiteSpace(OffsetString)) + { + OffsetString = OffsetString.Replace("[", "").Replace("]", ""); + Address += BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(OffsetString.PadLeft(8, '0')).Reverse().ToArray(), 0); + } + + return Address; + } + + internal byte[] GetMemoryAtAddress(string ProcessID, string Address, DataTypeExact DataType) + { + return GetMemoryAtAddress(BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(ProcessID), 0), BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(Address).Reverse().ToArray(), 0), DataType); + } + + internal byte[] GetMemoryAtAddress(uint ProcessID, string Address, DataTypeExact DataType) + { + return GetMemoryAtAddress(ProcessID, BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(Address).Reverse().ToArray(), 0), DataType); + } + + internal byte[] GetMemoryAtAddress(string ProcessID, uint Address, DataTypeExact DataType) + { + return GetMemoryAtAddress(BitConverter.ToUInt32(Utilities.GetByteArrayFromByteString(ProcessID), 0), Address, DataType); + } + + internal byte[] GetMemoryAtAddress(uint ProcessID, uint Address, DataTypeExact DataType) + { + SearchCriteria Criteria = new SearchCriteria(); + Criteria.ProcessID = ProcessID; + Criteria.DataType = DataType; + Criteria.StartAddress = Address; + Criteria.Length = Criteria.Size = Form.GetSearchMemorySize(DataType); + Criteria.SearchType = SearchTypeBase.Unknown; + Criteria.SearchValue = new byte[] { 0 }; + Form.NTRConnection.SearchCriteria.Add(Criteria); + Form.NTRConnection.SendReadMemoryPacket(Criteria); + return Criteria.AddressesFound.Values.First(); + } } } diff --git a/NTRDebuggerTool/NTRDebuggerTool.csproj b/NTRDebuggerTool/NTRDebuggerTool.csproj index aabd251..16a3956 100644 --- a/NTRDebuggerTool/NTRDebuggerTool.csproj +++ b/NTRDebuggerTool/NTRDebuggerTool.csproj @@ -9,8 +9,24 @@ Properties NTRDebuggerTool NTRDebuggerTool - v4.5 + v4.0 512 + false + + publish\ + true + Disk + false + Foreground + 7 + Days + false + false + true + 0 + 1.0.0.%2a + false + true AnyCPU @@ -27,11 +43,18 @@ pdbonly true bin\Release\ - TRACE + + prompt 4 + true + + False + Resources\log4net.dll + False + @@ -45,6 +68,7 @@ + Form @@ -69,8 +93,10 @@ PointerScanDialog.cs - + + + @@ -97,6 +123,7 @@ Resources.resx True + SettingsSingleFileGenerator Settings.Designer.cs @@ -113,7 +140,31 @@ + + + False + Microsoft .NET Framework 4.5 %28x86 and x64%29 + true + + + False + .NET Framework 3.5 SP1 Client Profile + false + + + False + .NET Framework 3.5 SP1 + false + + + + + + + + +