Microsoft Spider Solitaire에서이 전체 기본/정적 포인터를 테스트하고 있습니다. 그래서 플레이어가 사용한 "이동"양의 기본 포인터를 얻었고, 엔진은 "SpiderSolitaire.exe + B5F78"이라고 알려줍니다. 이제는 SpiderSolitaire.exe의 시작 주소가 무엇인지 파악하는 방법에 착수했습니다. 물론 프로그램이 시작될 때마다이 주소가 변경됩니다. SpiderSolitaire.exe의 시작 주소를 어떻게 찾을 수있어서 오프셋을 추가하고 "이동"값의 실제 주소를 얻을 수 있습니까? (물론 C++에서)?C++에서 프로세스의 시작/기본 주소를 얻는 방법은 무엇입니까?
4
A
답변
1
실행 파일에서 IMAGE_OPTIONAL_HEADER 구조를 살펴보아야합니다. 이 위대한 가이드를 읽어 보시기 바랍니다 : http://msdn.microsoft.com/en-us/library/ms809762.aspx
2
다음은 주어진 프로세스의 기본 주소를 찾는 코드입니다.
이 코드는 멀티 바이트 문자 집합을 사용합니다. VS2012에서이 속성은 속성> 구성 속성> 프로젝트 기본값> 문자 집합> 다중 바이트 문자 집합 사용에서 설정합니다.
#define _CRT_SECURE_NO_WARNINGS
#define UNINITIALIZED 0xFFFFFFFF
#include <iostream>
#include <iomanip>
#include <Windows.h>
#include <TlHelp32.h> //PROCESSENTRY
/* The name of the process */
const char* processName_ = "REPLACETHIS.exe" ;
void main(void)
{
DWORD processID_ = NULL ;
DWORD processBaseAddress_ = UNINITIALIZED;
/* Get the process ID */
{
PROCESSENTRY32 processEntry_ ; // Entry into process you wish to inject to
HANDLE hProcSnapshot_ = NULL ;
/* Takes a snapshot of the system's processes */
hProcSnapshot_ = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0) ; //?
/* While process has not been found, keep looking for it */
while(!processID_)
{
/* If a process on the system exists */
if(Process32First(hProcSnapshot_, &processEntry_)) //?
{
/* Check all processes in the system's processes snapshot */
do
{
/* Compare the name of the process to the one we want */
if(!strcmp(processEntry_.szExeFile, processName_)) //?
{
/* Save the processID and break out */
processID_ = processEntry_.th32ProcessID ;
break ;
}
}
while(Process32Next(hProcSnapshot_, &processEntry_)) ;
}
/* Didnt find process, sleep for a bit */
if(!processID_)
{
system("CLS") ;
std::cout << "Make sure " << processName_ << " is running." << std::endl ;
Sleep(200) ;
}
}
/* Process found */
std::cout << "Found Process: " << processName_ << std::endl ;
}
/* Find Base Address of process */
{
HANDLE moduleSnapshotHandle_ = INVALID_HANDLE_VALUE;
MODULEENTRY32 moduleEntry_;
/* Take snapshot of all the modules in the process */
moduleSnapshotHandle_ = CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, processID_);
/* Snapshot failed */
if(moduleSnapshotHandle_ == INVALID_HANDLE_VALUE)
{
std::cout << "Module Snapshot error" << std::endl ;
return ;
}
/* Size the structure before usage */
moduleEntry_.dwSize = sizeof(MODULEENTRY32);
/* Retrieve information about the first module */
if(!Module32First(moduleSnapshotHandle_, &moduleEntry_))
{
std::cout << "First module not found" << std::endl ;
CloseHandle(moduleSnapshotHandle_);
return ;
}
/* Find base address */
while(processBaseAddress_ == UNINITIALIZED)
{
/* Find module of the executable */
do
{
/* Compare the name of the process to the one we want */
if(!strcmp(moduleEntry_.szModule, processName_)) //?
{
/* Save the processID and break out */
processBaseAddress_ = (unsigned int)moduleEntry_.modBaseAddr ;
break ;
}
} while(Module32Next(moduleSnapshotHandle_, &moduleEntry_));
if(processBaseAddress_ == UNINITIALIZED)
{
system("CLS") ;
std::cout << "Failed to find module" << processName_ << std::endl ;
Sleep(200) ;
}
}
/* Found module and base address successfully */
std::cout << "Base Address: " << std::hex << processBaseAddress_ << std::dec << std::endl ;
CloseHandle(moduleSnapshotHandle_);
}
4
다른 방법으로는 Visual Studio 2015로 작성되었지만 이전 버전과의 호환성이 있어야합니다.
#define PSAPI_VERSION 1
#include <windows.h>
#include <tchar.h>
#include <stdio.h>
#include <psapi.h>
// To ensure correct resolution of symbols, add Psapi.lib to TARGETLIBS
#pragma comment(lib, "psapi.lib")
void GetBaseAddressByName(DWORD processId, TCHAR *processName)
{
TCHAR szProcessName[MAX_PATH] = TEXT("<unknown>");
HANDLE hProcess = OpenProcess(PROCESS_QUERY_INFORMATION |
PROCESS_VM_READ,
FALSE, processId);
if (NULL != hProcess)
{
HMODULE hMod;
DWORD cbNeeded;
if (EnumProcessModulesEx(hProcess, &hMod, sizeof(hMod),
&cbNeeded, LIST_MODULES_32BIT | LIST_MODULES_64BIT))
{
GetModuleBaseName(hProcess, hMod, szProcessName,
sizeof(szProcessName)/sizeof(TCHAR));
if (!_tcsicmp(processName, szProcessName)) {
_tprintf(TEXT("0x%p\n"), hMod);
}
}
}
CloseHandle(hProcess);
}
int main(void)
{
DWORD aProcesses[1024];
DWORD cbNeeded;
DWORD cProcesses;
// Get the list of process identifiers.
if (!EnumProcesses(aProcesses, sizeof(aProcesses), &cbNeeded))
return 1;
// Calculate how many process identifiers were returned.
cProcesses = cbNeeded/sizeof(DWORD);
// Check the names of all the processess (Case insensitive)
for (int i = 0; i < cProcesses; i++) {
GetBaseAddressByName(aProcesses[i], TEXT("SpiderSolitaire.exe"));
}
return 0;
}
+0
'if (NULL! = hProcess)'비교 순서가 나의 날을 만들었습니다. –
외부에서 또는 DLL을 주입 할 수 있습니까? – Blood
외부에서. WriteMemoryProcess를 사용하여 프로세스 메모리에 씁니다. – ZimZim
WriteProcessMemory * – ZimZim