枚举内存范围内的页面

kva*_*nck 4 c++ memory probe

我在 Visual Studio 2012 下的 Windows 上使用 C++。

我有一个开始和结束内存地址,需要在两个地址之间生成一个页面基地址/句柄列表。我考虑过手动探测页面的可能性,但认为必须有更好的方法来枚举它们。

这样的方式存在吗?

免责声明;最后的页句柄必须是基地址,这样当窗口页的大小添加到它们时,结果地址不会重叠到下一页。首选解决方案不是特定于平台的,并且与 32 位(带/不带 WOW64)兼容。

Joh*_*eek 6

VirtualQuery几乎是您唯一的选择。它应该相当有效:

该函数确定该区域中第一页的属性,然后扫描后续页面,直到它扫描整个页面范围或直到遇到具有一组不匹配属性的页面。

因此,您首先在您关心的范围的开头调用它,然后您将返回单个页面块。下一个调用将在该块之后立即开始,然后下一个调用,依此类推。

这是一个完全未经测试的函数,可以填充MEMORY_BASIC_INFORMATION结构数组:

int EnumVirtualAllocations(const void* ptr, size_t length, MEMORY_BASIC_INFORMATION* info, int size)
{
    const void* end = (const void*)((const char*)ptr + length);
    int index = 0;
    while (index < size && ptr < end &&
        VirtualQuery(ptr, &info[index], sizeof(*info)) == sizeof(*info))
    {
        MEMORY_BASIC_INFORMATION* i = &info[index];
        if (i->State != MEM_FREE) index++;
        ptr = (const void*)((const char*)(i->BaseAddress) + i->RegionSize);
    }
    return index;
}
Run Code Online (Sandbox Code Playgroud)