나는 게임에서 가상 메모리 주소의 값을 읽어 그것이 언제 로드되는지 알 수 있도록 C로 프로그램을 작성하려고 했습니다. Windows에서는 이 작업을 수행하기 쉽지만 Linux에서 수행하는 방법에 대한 많은 정보를 찾을 수 없는 것 같습니다.
제가 시도한 모든 솔루션이 작동하지 않거나 게임이 정지되는 원인이 되었습니다. 매 프레임마다 또는 최대한 가까운 주소를 읽을 수 있는 솔루션이 필요합니다.
이를 위해 어떤 접근 방식을 취할 수 있나요?
지금까지 나는 ptrace를 사용하고 /proc/mem에서 읽는 것을 시도했습니다. ptrace를 사용하면 프로그램이 정지되고 지금까지 /proc/mem에서 데이터를 읽는 작업이 수행되지 않았습니다.
편집: process_vm_readv 시스템 호출을 사용하기로 결정했고 게임은 더 이상 멈추지 않았지만 어떤 이유로 3640913997이라는 숫자가 출력되었습니다.
이것은 코드입니다
#include <stdio.h>
#include <sys/uio.h>
#include <stdint.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <sys/stat.h>
#include <sys/ptrace.h>
#include <errno.h>
#include <string.h>
#include <fcntl.h>
#include <stdlib.h>
#include <iostream>
struct StockPid
{
pid_t pid;
char buff[512];
FILE *pid_pipe;
} stockthepid;
void Func_StockPid(const char *processtarget)
{
stockthepid.pid_pipe = popen(processtarget, "r");
fgets(stockthepid.buff, 512, stockthepid.pid_pipe);
stockthepid.pid = strtoul(stockthepid.buff, NULL, 10);
if (stockthepid.pid == 0)
{
printf("Jet Set Radio isn't running. \n");
pclose(stockthepid.pid_pipe);
exit(-1);
}
else
{
printf("Jet Set Radio is running - PID NUMBER -> {%d} \n", stockthepid.pid);
pclose(stockthepid.pid_pipe);
}
}
void ReadProcessMemory(int pid) {
struct iovec in;
in.iov_base= (void *) 0x58FAAC;
in.iov_len = 4;
uint32_t foo;
struct iovec out;
out.iov_base = &foo;
out.iov_len = sizeof(foo);
do {
ssize_t nread = process_vm_readv(stockthepid.pid, &out, 1, &in, 1, 0);
if(nread == -1) {
printf("error %s");
} else if(nread != in.iov_len) {
printf("error: short read of %li bytes", (ssize_t)nread);
}
std::cout << foo << std::endl;
} while(true);
}
int main()
{
Func_StockPid("pidof -s jetsetradio.exe");
ReadProcessMemory(stockthepid.pid);
return 0;
}
다시 편집하세요 :): in.iov_len
2로 변경하면 예상한 숫자(61517)가 표시되지만 숫자는 절대 변경되지 않습니다.