查基址這個東西就是找一個偏移嘛。
這次用的程序是1.0原版的植物大戰僵屍。
找了個簡單點的數據就是陽光,直接搜2次就能找到這個int變量。
然后查對於這個地址的內存訪問。
找到的里面有個偏移,再對之前計算的那個進行查找,然后查看內存訪問,最后結果如下:
陽光 = [[基地址+0x768] + 5560]
基地址0x6a9ec0
然后就是寫代碼修改陽光的問題了,主要就是先獲取進程pid然后OpenProcess,然后對內存進行讀寫。
貼代碼:
#include<stdio.h>
#include<Windows.h>
#include<TlHelp32.h>
#define NAME "mspaint.exx" //要修改的進程名
DWORD GetPid(char* szName){
HANDLE hprocessSnap = NULL;
PROCESSENTRY32 pe32 = {0};
hprocessSnap = CreateToolhelp32Snapshot(
TH32CS_SNAPPROCESS,
0);//捕捉所有進程的快照
if (hprocessSnap == INVALID_HANDLE_VALUE){
//快照失敗
return 0;
}
//初始化pe32結構體
pe32.dwSize = sizeof(PROCESSENTRY32);
if (Process32First(hprocessSnap, &pe32)){
do{
if (!strcmp(szName, pe32.szExeFile)){
printf("Process Found, PID: %d \n", (int)pe32.th32ProcessID);
return (int)pe32.th32ProcessID;
}
//遍歷查找進程名
}while (Process32Next(hprocessSnap, &pe32));
}else{
CloseHandle(hprocessSnap);
}
return 0;
}
void main()
{
DWORD pid = GetPid("popcapgame1.exe"); // 獲取進程pid
//獲取進程句柄
HANDLE hProcess;
hProcess = OpenProcess(PROCESS_ALL_ACCESS,FALSE,pid);
printf("%x \n", hProcess);
if (hProcess == NULL)
{
printf("fail to open process \n");
CloseHandle(hProcess);
return;
}
//CloseHandle(hProcess);
// 獲取模塊地址
DWORD modaddr = NULL;
MODULEENTRY32 modentry;
HANDLE hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, pid);
modentry.dwSize = sizeof(MODULEENTRY32); // 初始化一下
Module32First(hSnapshot, &modentry);
do{
if (!strcmp(modentry.szModule, "popcapgame1.exe")){
modaddr = (DWORD)(modentry.hModule);
printf("Module Found, addr: %x \n", modaddr);
CloseHandle(hSnapshot);
break;
}
//遍歷查找進程名
}while (Module32Next(hSnapshot, &modentry));
// 讀陽光數據
/*
183fc4f8 + 5560
[[基地址+0x768] + 5560]
基地址0x6a9ec0
*/
DWORD pObj = modaddr; // 有的時候偏移要用,但是這次直接是固定基地址所以不用管
pObj = NULL;
printf("pobj: %x \n", pObj);
int a = ReadProcessMemory(hProcess, (LPCVOID)(pObj+0x6a9ec0), &pObj, 4, 0);
printf("pobj: %x \n", pObj);
ReadProcessMemory(hProcess, (LPCVOID)(pObj+0x768), &pObj, 4, 0);
printf("pobj: %x \n", pObj);
DWORD pSun = pObj+0x5560;
int sun = 0;
int max_sun = 9999;
ReadProcessMemory(hProcess, (LPCVOID)(pSun), &sun, 4, 0);
printf("sun: %d \n", sun);
while(1)
{
Sleep(1000);
ReadProcessMemory(hProcess, (LPCVOID)(pSun), &sun, 4, 0);
WriteProcessMemory(hProcess, (LPVOID)(pSun), &max_sun, 4, 0); // 陽光拉滿
printf("sun: %d \n", sun);
}
CloseHandle(hProcess);
return;
}
P.S.中間查模塊的代碼其實用不到,因為基址是寫死的,不是相對於模塊的偏移。
