微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

ReadProcessMemory仅适用于断点

如何解决ReadProcessMemory仅适用于断点

我开始创建一个进程,记录它是否失败,然后进行while循环以等待找到窗口。

PROCESS_informatION p;
STARTUPINFO s;
ZeroMemory(&s,sizeof(s));
s.cb = sizeof(s);
ZeroMemory(&p,sizeof(p));
if (!CreateProcessA("D:\\SteamLibrary\\steamapps\\common\\Fallout 4\\Wolf4SDL.exe","",NULL,FALSE,&s,&p))
{
    _MESSAGE("CreateProcess Failed (%d).",GetLastError());
}
//wait for the process to start
while (FindWindowA(NULL,"Wolfenstein 3D") == NULL);

然后为两个进程设置vars-x64,即64位地址。 “ addr”是一个指针。 addrOff是静态偏移量。

HANDLE procHandle = p.hProcess;
unsigned long long addr;
unsigned long long addrOff = 0x00000001401a7718;
SIZE_T NumberOfBytesToRead = sizeof(addr); 
SIZE_T NumberOfBytesActuallyRead;

现在阅读,以及一些基本的调试消息

ReadProcessMemory(procHandle,(LPCVOID)(addrOff),&addr,NumberOfBytesToRead,&NumberOfBytesActuallyRead);
_MESSAGE("addr: %p",addr);
_MESSAGE("numBytesRead: %d",NumberOfBytesActuallyRead);

这就是问题所在-如果我在其中放置一个断点,addr将具有用于读取的静态偏移量的适当值。如果我不这样做,addr的值为0x0000000000000000。在这两种情况下,NumberOfBytesActuallyRead的值都将为8。即使不查看我的日志,该过程也已存在并说明了原因-但是查看我的日志可以确认这一点。

不用说,这几乎不可能调试该问题。现在,我想到一个奇怪的地方-我在示例中注意到,人们只是在使用偏移量的情况下将偏移量添加到基址中。因此,在我的addrOff值包含基地址的情况下,我在两种情况下都检查了基地址-它们都相同。并且为了完整起见,提供了基地址代码

unsigned long long dwBase = -1;

EnumProcessModules(procHandle,hModules,&cModules);
hModules = new HMODULE[cModules / sizeof(HMODULE)];

if (EnumProcessModules(procHandle,cModules / sizeof(HMODULE),&cModules)) {
    for (size_t i = 0; i < cModules / sizeof(HMODULE); i++) {
        if (GetModuleBaseName(procHandle,hModules[i],szBuf,sizeof(szBuf))) {
            if (std::string("Wolf4SDL.exe").compare(szBuf) == 0) {
                dwBase = (unsigned long long)hModules[i];
                break;
            }
        }
    }
}

解决方法

这很简单。

读取的变量仍为0。

使用断点时,查看代码并按Continue的时间就是其他进程设置变量的时间。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。