每帧从程序中的虚拟内存地址读取值

每帧从程序中的虚拟内存地址读取值

我一直在尝试用 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),但该数字永远不会改变。

相关内容