Parent Directory
|
Revision Log
|
Patch
--- trunk/RomCheater/Docking/FloatingMemorySearcher.cs 2012/06/02 18:31:40 229 +++ trunk/RomCheater/Docking/FloatingMemorySearcher.cs 2012/06/02 19:12:20 230 @@ -12,6 +12,9 @@ using System.Diagnostics; using RomCheater.Docking.MemorySearch; using libWin32.Win32.Threading; +using System.Threading; +using RomCheater.Logging; +using System.IO; namespace RomCheater.Docking { @@ -42,8 +45,49 @@ radio_8bits.Checked = true; radiocompare_equal.Checked = true; radio_oldvalue.Checked = true; + chkRefreshResults.Checked = true; + } + public enum eListViewResults + { + SEARCH_RESULTS_LIST = 0x3000, + PATCH_RESULTS_LIST = 0x3001, + UKNOWN_RESULTS_LIST = 0x3001 + } + static int col_Found_Address = 0; + static int col_Found_Value = 1; + static int col_Found_Frozen = 2; + static int col_Added_Address = 0; + static int col_Added_Value = 1; + static int col_Added_Frozen = 2; + List<ListViewItem> ResultItems = new List<ListViewItem>(); + List<ListViewItem> AddedItems = new List<ListViewItem>(); + private bool _PatchedValue_NeedsUpdate; + bool PatchedValue_NeedsUpdate + { + get { if (_PatchedValue_NeedsUpdate) this.ThawResultsUpdate(); return _PatchedValue_NeedsUpdate; } + set { _PatchedValue_NeedsUpdate = value; if (value) this.ThawResultsUpdate(); } + } + private delegate ListViewItem ThreadSafe_GetResultItem(int index, int lv_type); + private ListViewItem GetResultItem(int index, int lv_type) + { + try + { + AddressValuePairList lv = null; + switch (lv_type) + { + case (int)eListViewResults.SEARCH_RESULTS_LIST: lv = lstResults; break; + case (int)eListViewResults.PATCH_RESULTS_LIST: lv = lstPatchList; break; + default: throw new IndexOutOfRangeException("Detected: " + Enum.GetName(typeof(eListViewResults), eListViewResults.UKNOWN_RESULTS_LIST) + " with value: " + lv_type.ToString("x4")); + } + ListViewItem item = new ListViewItem(); + item = (ListViewItem)lv.Items[index].Clone(); + return item; + } + catch (Exception) + { + return null; + } } - private void radiocompare_equal_CheckedChanged(object sender, EventArgs e) { //if (!radiocompare_between.Checked && !radiocompare_notbetween.Checked) @@ -217,15 +261,227 @@ ResultsUpdateWorkerThread.RunWorkerAsync(); } } - + private bool ShouldUpdateResults() + { + if (this.AcceptedProcess == null) return false; + if (SearchWorkerThread.IsBusy) return false; + //if (JokerSearchWorker.IsBusy) return false; + if (this.IsResultsUpdateFrozen) return false; + if (mnuAddedResults.Visible) return false; + if (mnuResults.Visible) return false; + if (Process.GetProcessById(this.AcceptedProcess.Id) == null) return false; + if (lstResults.Items.Count > 0) return true; + if (lstPatchList.Items.Count > 0) return true; + return false; + } private void ResultsUpdateWorkerThread_DoWork(object sender, DoWorkEventArgs e) { + Thread.Sleep(250); // keep thread from blocking + if (!this.ShouldUpdateResults()) return; + ////if (SearchArgs == null) return; + ////if (this.IsResultsUpdateFrozen) return; + ////// put thread to sleep for 500ms + ////System.Threading.Thread.Sleep(500); + //PCSX2MemoryProvider provider = new PCSX2MemoryProvider(this.SearchPCSX2ProcessPID, resultslog); + //byte[] buffered_mem = provider.GetMemory(); + //MemoryStream ms = new MemoryStream(buffered_mem); + //BinaryReader r_ms = new BinaryReader(ms); + + #region Update Results List + ResultItems = new List<ListViewItem>(); + //r_ms.BaseStream.Seek(0, SeekOrigin.Begin); + for (int i = 0; i < lstResults.Items.Count; i++) + { + if (this.lstResults.InvokeRequired) + { + ThreadSafe_GetResultItem _get_item = new ThreadSafe_GetResultItem(GetResultItem); + object item = this.lstResults.Invoke(_get_item, new object[] { i, (int)eListViewResults.SEARCH_RESULTS_LIST }); + if (item != null) + ResultItems.Add((ListViewItem)item); + } + else + { + ResultItems.Add(lstResults.Items[i]); + } + } + for (int i = 0; i < ResultItems.Count; i++) + { + if (ResultsUpdateWorkerThread.CancellationPending == true) + { + e.Cancel = true; + return; + } + uint Address = 0; + ResultDataType _result = (ResultDataType)ResultItems[i].Tag; + + Address = Convert.ToUInt32(ResultItems[i].SubItems[col_Found_Address].Text, 16); + //r_ms.BaseStream.Seek(Address, SeekOrigin.Begin); + Sojaner.MemoryScanner.ProcessMemoryReader reader = new Sojaner.MemoryScanner.ProcessMemoryReader(); + reader.ReadProcess = Process.GetProcessById(this.AcceptedProcess.Id); + if (reader.ReadProcess == null) { logger.Error.WriteLine("Could not attach to process: {0}", this.AcceptedProcess.Id); return; } + reader.OpenProcess(); + int bytesReadSize; + byte[] data; + uint bytesToRead = 0; + switch (_result.ValueType) + { + case SearchDataTypes._8bits: + bytesToRead = 1; + break; + case SearchDataTypes._16bits: + bytesToRead = 2; + break; + case SearchDataTypes._32bits: + bytesToRead = 4; + break; + case SearchDataTypes._64bits: + bytesToRead = 8; + break; + } + reader.ReadProcessMemory(Address, bytesToRead, out bytesReadSize, out data); + MemoryStream ms = new MemoryStream(data); + BinaryReader r_ms = new BinaryReader(ms); + switch (_result.ValueType) + { + case SearchDataTypes._8bits: + if (_result.IsUnsigned) { ResultItems[i].SubItems[col_Found_Value].Text = string.Format("0x{0:x2}", r_ms.ReadByte()); } + else { ResultItems[i].SubItems[col_Found_Value].Text = string.Format("0x{0:x2}", r_ms.ReadSByte()); } + break; + case SearchDataTypes._16bits: + if (_result.IsUnsigned) { ResultItems[i].SubItems[col_Found_Value].Text = string.Format("0x{0:x4}", r_ms.ReadUInt16()); } + else { ResultItems[i].SubItems[col_Found_Value].Text = string.Format("0x{0:x4}", r_ms.ReadInt16()); } + break; + case SearchDataTypes._32bits: + if (_result.IsUnsigned) { ResultItems[i].SubItems[col_Found_Value].Text = string.Format("0x{0:x8}", r_ms.ReadUInt32()); } + else { ResultItems[i].SubItems[col_Found_Value].Text = string.Format("0x{0:x8}", r_ms.ReadInt32()); } + break; + case SearchDataTypes._64bits: + if (_result.IsUnsigned) { ResultItems[i].SubItems[col_Found_Value].Text = string.Format("0x{0:x16}", r_ms.ReadUInt64()); } + else { ResultItems[i].SubItems[col_Found_Value].Text = string.Format("0x{0:x16}", r_ms.ReadInt64()); } + break; + } + r_ms.Close(); + reader.CloseHandle(); + Application.DoEvents(); + } + #endregion + + #region Update Added Results List + AddedItems = new List<ListViewItem>(); + //r_ms.BaseStream.Seek(0, SeekOrigin.Begin); + for (int i = 0; i < lstPatchList.Items.Count; i++) + { + if (this.lstResults.InvokeRequired) + { + ThreadSafe_GetResultItem _get_item = new ThreadSafe_GetResultItem(GetResultItem); + object item = this.lstResults.Invoke(_get_item, new object[] { i, (int)eListViewResults.PATCH_RESULTS_LIST }); + if (item != null) + AddedItems.Add((ListViewItem)item); + } + else + { + AddedItems.Add(lstPatchList.Items[i]); + } + + } + for (int i = 0; i < AddedItems.Count; i++) + { + if (ResultsUpdateWorkerThread.CancellationPending == true) + { + e.Cancel = true; + return; + } + uint Address = 0; + ResultDataType _result = (ResultDataType)AddedItems[i].Tag; + Address = Convert.ToUInt32(AddedItems[i].SubItems[col_Added_Address].Text, 16); + Sojaner.MemoryScanner.ProcessMemoryReader reader = new Sojaner.MemoryScanner.ProcessMemoryReader(); + reader.ReadProcess = Process.GetProcessById(this.AcceptedProcess.Id); + if (reader.ReadProcess == null) { logger.Error.WriteLine("Could not attach to process: {0}", this.AcceptedProcess.Id); return; } + reader.OpenProcess(); + int bytesReadSize; + byte[] data; + uint bytesToRead = 0; + switch (_result.ValueType) + { + case SearchDataTypes._8bits: + bytesToRead = 1; + break; + case SearchDataTypes._16bits: + bytesToRead = 2; + break; + case SearchDataTypes._32bits: + bytesToRead = 4; + break; + case SearchDataTypes._64bits: + bytesToRead = 8; + break; + } + reader.ReadProcessMemory(Address, bytesToRead, out bytesReadSize, out data); + MemoryStream ms = new MemoryStream(data); + BinaryReader r_ms = new BinaryReader(ms); + switch (_result.ValueType) + { + case SearchDataTypes._8bits: + if (_result.IsUnsigned) { AddedItems[i].SubItems[col_Added_Value].Text = string.Format("0x{0:x2}", r_ms.ReadByte()); } + else { AddedItems[i].SubItems[col_Added_Value].Text = string.Format("0x{0:x2}", r_ms.ReadSByte()); } + break; + case SearchDataTypes._16bits: + if (_result.IsUnsigned) { AddedItems[i].SubItems[col_Added_Value].Text = string.Format("0x{0:x4}", r_ms.ReadUInt16()); } + else { AddedItems[i].SubItems[col_Added_Value].Text = string.Format("0x{0:x4}", r_ms.ReadInt16()); } + break; + case SearchDataTypes._32bits: + if (_result.IsUnsigned) { AddedItems[i].SubItems[col_Added_Value].Text = string.Format("0x{0:x8}", r_ms.ReadUInt32()); } + else { AddedItems[i].SubItems[col_Added_Value].Text = string.Format("0x{0:x8}", r_ms.ReadInt32()); } + break; + case SearchDataTypes._64bits: + if (_result.IsUnsigned) { AddedItems[i].SubItems[col_Added_Value].Text = string.Format("0x{0:x16}", r_ms.ReadUInt64()); } + else { AddedItems[i].SubItems[col_Added_Value].Text = string.Format("0x{0:x16}", r_ms.ReadInt64()); } + break; + } + r_ms.Close(); + reader.CloseHandle(); + Application.DoEvents(); + } + #endregion + + } private void ResultsUpdateWorkerThread_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e) { + try + { + //if ((lstResults.SelectedItems.Count > 0) && !PatchedValue_NeedsUpdate ) return; + //if ((lstPatchList.SelectedItems.Count > 0) && !PatchedValue_NeedsUpdate) return; + if (!this.ShouldUpdateResults()) return; + if (ResultItems.Count > 0) + { + //lstResults.Items.Clear(); + //lstResults.Items.AddRange(ResultItems.ToArray()); + + for (int i = 0; i < ResultItems.Count; i++) + { + lstResults.Items[i].SubItems[new AVPColumnText(AVPColumnType.VALUE).ColumnIndex].Text = + ResultItems[i].SubItems[new AVPColumnText(AVPColumnType.VALUE).ColumnIndex].Text; + } + + } + if (AddedItems.Count > 0) + { + //lstPatchList.Items.Clear(); + //lstPatchList.Items.AddRange(AddedItems.ToArray()); + for (int i = 0; i < AddedItems.Count; i++) + { + lstPatchList.Items[i].SubItems[new AVPColumnText(AVPColumnType.VALUE).ColumnIndex].Text = + AddedItems[i].SubItems[new AVPColumnText(AVPColumnType.VALUE).ColumnIndex].Text; + } + + } + PatchedValue_NeedsUpdate = false; + } + catch { } } private void btnImportFile_Click(object sender, EventArgs e) @@ -389,5 +645,278 @@ ResultItem item = new ResultItem(state.Address, state.Value, state.Frozen, state.ValueType, state.IsUnsigned); this.AddToPatchList(item); } + + private void mnuItemAddToPatchList_Click(object sender, EventArgs e) + { + if (!(lstResults.SelectedItems.Count > 0)) return; + //if (SearchArgs == null) return; + + try + { + for (int i = 0; i < lstResults.SelectedIndices.Count; i++) + { + //ResultDataType result = (ResultDataType)lstResults.Items[selected_index].Tag; + ListViewItem item = lstResults.Items[lstResults.SelectedIndices[i]]; + this.AddToPatchList(item); + } + } + catch (Exception ex) + { + logger.Error.WriteLine(ex.ToString()); + } + } + + private void mnuItemRemoveResult_Click(object sender, EventArgs e) + { + if (!(lstPatchList.SelectedItems.Count > 0)) return; + //if (SearchArgs == null) return; + try + { + this.FreezeResultsUpdate(); + for (int i = 0; i < lstPatchList.SelectedIndices.Count; i++) + { + //lstPatchList.ThawItem(lstPatchList.SelectedIndices[i]); + lstPatchList.Items[lstPatchList.SelectedIndices[i]].Remove(); + } + this.ThawResultsUpdate(); + } + catch (Exception ex) + { + Debug.WriteLine(ex.ToString()); + } + } + private void PatchRange(bool SingleEntry) + { + //if (SearchArgs == null) return; + #region Patch Selected Address + // stop ResultsUpdate Thread + ResultsUpdateWorkerThread.CancelAsync(); + + List<ResultDataType> patch_list = new List<ResultDataType>(); + List<int> SelectedIndexes = new List<int>(); + + if (SingleEntry) + { + SelectedIndexes.Add(lstPatchList.SelectedIndices[0]); + } + else + { + foreach (int index in lstPatchList.SelectedIndices) + { + SelectedIndexes.Add(index); + } + } + //PCSX2MemoryProvider provider = new PCSX2MemoryProvider(this.SearchPCSX2ProcessPID, resultslog); + foreach (int index in SelectedIndexes) + { + if (SingleEntry) + { + SearchPatcher patcher = null; + uint Address = 0; + ListViewItem item = lstPatchList.Items[index]; + ResultDataType _result = (ResultDataType)item.Tag; + Address = Convert.ToUInt32(item.SubItems[col_Found_Address].Text, 16); + switch (_result.ValueType) + { + case SearchDataTypes._8bits: + if (_result.IsUnsigned) + { + byte value = Convert.ToByte(item.SubItems[col_Found_Value].Text, 16); + patcher = new SearchPatcher(this.AcceptedProcess.Id, Address, value); + timer_update_results.Enabled = false; + patcher.ShowDialog(); + timer_update_results.Enabled = true; + PatchedValue_NeedsUpdate = true; + if (!chkRefreshResults.Checked && !ResultsUpdateWorkerThread.IsBusy) + ResultsUpdateWorkerThread.RunWorkerAsync(); + } + else + { + sbyte value = Convert.ToSByte(item.SubItems[col_Found_Value].Text, 16); + patcher = new SearchPatcher(this.AcceptedProcess.Id, Address, value); + timer_update_results.Enabled = false; + patcher.ShowDialog(); + timer_update_results.Enabled = true; + PatchedValue_NeedsUpdate = true; + if (!chkRefreshResults.Checked && !ResultsUpdateWorkerThread.IsBusy) + ResultsUpdateWorkerThread.RunWorkerAsync(); + } + break; + case SearchDataTypes._16bits: + if (_result.IsUnsigned) + { + ushort value = Convert.ToUInt16(item.SubItems[col_Found_Value].Text, 16); + patcher = new SearchPatcher(this.AcceptedProcess.Id, Address, value); + timer_update_results.Enabled = false; + patcher.ShowDialog(); + timer_update_results.Enabled = true; + PatchedValue_NeedsUpdate = true; + if (!chkRefreshResults.Checked && !ResultsUpdateWorkerThread.IsBusy) + ResultsUpdateWorkerThread.RunWorkerAsync(); + } + else + { + short value = Convert.ToInt16(item.SubItems[col_Found_Value].Text, 16); + patcher = new SearchPatcher(this.AcceptedProcess.Id, Address, value); + timer_update_results.Enabled = false; + patcher.ShowDialog(); + timer_update_results.Enabled = true; + PatchedValue_NeedsUpdate = true; + if (!chkRefreshResults.Checked && !ResultsUpdateWorkerThread.IsBusy) + ResultsUpdateWorkerThread.RunWorkerAsync(); + } + break; + case SearchDataTypes._32bits: + if (_result.IsUnsigned) + { + uint value = Convert.ToUInt32(item.SubItems[col_Found_Value].Text, 16); + patcher = new SearchPatcher(this.AcceptedProcess.Id, Address, value); + timer_update_results.Enabled = false; + patcher.ShowDialog(); + timer_update_results.Enabled = true; + PatchedValue_NeedsUpdate = true; + if (!chkRefreshResults.Checked && !ResultsUpdateWorkerThread.IsBusy) + ResultsUpdateWorkerThread.RunWorkerAsync(); + } + else + { + int value = Convert.ToInt32(item.SubItems[col_Found_Value].Text, 16); + patcher = new SearchPatcher(this.AcceptedProcess.Id, Address, value); + timer_update_results.Enabled = false; + patcher.ShowDialog(); + timer_update_results.Enabled = true; + PatchedValue_NeedsUpdate = true; + if (!chkRefreshResults.Checked && !ResultsUpdateWorkerThread.IsBusy) + ResultsUpdateWorkerThread.RunWorkerAsync(); + } + break; + case SearchDataTypes._64bits: + if (_result.IsUnsigned) + { + ulong value = Convert.ToUInt32(item.SubItems[col_Found_Value].Text, 16); + patcher = new SearchPatcher(this.AcceptedProcess.Id, Address, value); + timer_update_results.Enabled = false; + patcher.ShowDialog(); + timer_update_results.Enabled = true; + PatchedValue_NeedsUpdate = true; + if (!chkRefreshResults.Checked && !ResultsUpdateWorkerThread.IsBusy) + ResultsUpdateWorkerThread.RunWorkerAsync(); + } + else + { + long value = Convert.ToInt32(item.SubItems[col_Found_Value].Text, 16); + patcher = new SearchPatcher(this.AcceptedProcess.Id, Address, value); + timer_update_results.Enabled = false; + patcher.ShowDialog(); + timer_update_results.Enabled = true; + PatchedValue_NeedsUpdate = true; + if (!chkRefreshResults.Checked && !ResultsUpdateWorkerThread.IsBusy) + ResultsUpdateWorkerThread.RunWorkerAsync(); + } + break; + } + } + else + { + + ListViewItem item = lstPatchList.Items[index]; + ResultDataType _result = (ResultDataType)item.Tag; + patch_list.Add(_result); + } + } + + if (patch_list.Count > 0) + { + SearchRangePatcher rangePatcher = new SearchRangePatcher(this.AcceptedProcess.Id, patch_list); + rangePatcher.ShowDialog(); + } + + #endregion + } + private void mnuItemPatchSelectedEntry_Click(object sender, EventArgs e) + { + if (!(lstPatchList.SelectedItems.Count == 1)) return; + PatchRange(true); + } + + private void mnuItemPatchSelectedRange_Click(object sender, EventArgs e) + { + if (!(lstPatchList.SelectedItems.Count >= 1)) return; + PatchRange(false); + } + + private void mnuItemFreezeSelectedPatches_Click(object sender, EventArgs e) + { + if (!(lstPatchList.SelectedItems.Count > 0)) return; + //if (SearchArgs == null) return; + try + { + lstPatchList.ProcessID = this.AcceptedProcess.Id; + this.FreezeResultsUpdate(); + for (int i = 0; i < lstPatchList.SelectedIndices.Count; i++) + { + lstPatchList.FreezeItem(lstPatchList.SelectedIndices[i]); + } + // force thaw and update + this.ThawResultsUpdate(); + this.Update(); + } + catch (Exception ex) + { + Debug.WriteLine(ex.ToString()); + } + } + + private void mnuItemThawSelectedPatches_Click(object sender, EventArgs e) + { + if (!(lstPatchList.SelectedItems.Count > 0)) return; + //if (SearchArgs == null) return; + try + { + lstPatchList.ProcessID = this.AcceptedProcess.Id; + this.FreezeResultsUpdate(); + for (int i = 0; i < lstPatchList.SelectedIndices.Count; i++) + { + lstPatchList.ThawItem(lstPatchList.SelectedIndices[i]); + } + // force thaw and update + this.ThawResultsUpdate(); + this.Update(); + } + catch (Exception ex) + { + Debug.WriteLine(ex.ToString()); + } + } + + private void SearchWorkerThread_DoWork(object sender, DoWorkEventArgs e) + { + + } + + private void SearchWorkerThread_ProgressChanged(object sender, ProgressChangedEventArgs e) + { + + } + + private void SearchWorkerThread_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e) + { + + } + + private void search_progress_updater_Tick(object sender, EventArgs e) + { + if ((this.AcceptedProcess ==null) || Process.GetProcessById(this.AcceptedProcess.Id) == null) + { + SearchWorkerThread.CancelAsync(); + //JokerSearchWorker.CancelAsync(); + ResultsUpdateWorkerThread.CancelAsync(); + } + } + + private void btnSearch_Click(object sender, EventArgs e) + { + this.FreezeResultsUpdate(); + } } }
ViewVC Help | |
Powered by ViewVC 1.1.22 |