.Net實現游戲修改器
static extern bool ReadProcessMemory;
[DllImport]
static extern bool WriteProcessMemory;
名字很直觀:讀/寫進程內存。
兩個方法簽名基本相同,我這里簡單解釋一下:
hProcess :進程句柄
lpBaseAddress:基地址,也就是起始地址
lpBuffer:從基地址起讀取或要寫入的內存值
nSize:讀取或寫入的數量,單位是字節
lpNumberOfBytesRead、 lpNumberOfBytesWritten:用作傳出,表示實際讀取或寫入的數量
好了!開始實戰吧!
創建一個C#的Windows forms項目
在窗體上我這樣布局:
為類添加如下幾個成員:
| 以下為引用的內容: List private List bool isFirstSearch = true;//是否是第一次搜索 Process _selectedProcess;//所選進程 還要獲取有窗體的進程并列出來,讓使用者選擇需要的進程 private void RefreshProcessList { listBox1.Items.Clear; _windowedProcesses.Clear; textBox2.Enabled = false;//在沒得到唯一的地址前不能寫入 foreach ) { if //進程有窗口 { if )//窗體名不為空。因為有些時候會有一些進程如iexplorer.exe ,它有窗口,但窗口沒名稱且沒顯示。所以應該排除一下 { listBox1.Items.Add; _windowedProcesses.Add; } } } } 于是可以在我們的窗體裝載和單擊刷新按鈕時調用該方法 private void Form1_Load { RefreshProcessList; } private void btnRefreshPList_Click { RefreshProcessList; }
為什么要區別是否是第一次搜索?因為第一次搜索是在整個進程可訪問內存范圍內查找,而之后的查找是基于第一次找到的地址。這樣做不是唯一的,但是最好的方法。
private void button1_Click { if return; if { uint baseAddr = 0x00010000; uint endAddr = 0x7ffeffff; for ) { var addrs = CreateAddrList, int.Parse); if _addrList.AddRange; } isFirstSearch = false; } else { RefreshAddrList); } label2.Text = "找到結果”+ _addrList.Count.ToString + "個"; if textBox2.Enabled = true; } |
很明顯CreateAddrList是第一次查找掉用的方法,RefreshAddrList是之后查找調用的方法。在第一次查找中,我們以4KB作一次跳躍。為什么查找的地址范圍如此本文開始已作說明,這里就不再贅述。
没有评论:
发表评论