20170805Windows12_3_虚拟内存页面区块/内存信息
2017-08-05 23:17
197 查看
虚拟内存页面区块/内存信息:
如何提高内存扫描的效率:
1:之前做的,都是直接扫描进程内存的前面2G内存空间,要扫描完,需要一定的时间,而且,可能扫描出来的重复数据比较多,后面,提到了先获取进程的堆块空间,然后扫描,但是实际上,这样提高效率的可能性不高,Windows的内存管理,是按照页面管理的,大部分CPU的页面大小都是64KB。2:为了提高内存扫描的速度,需要获取Windows里面页面区域的属性,我们可以使用VirtualQueryEx这个函数来获取。
VirtualQueryEx( _In_ HANDLE hProcess, _In_opt_ LPCVOID lpAddress, _Out_writes_bytes_to_(dwLength, return) PMEMORY_BASIC_INFORMATION lpBuffer, _In_ SIZE_T dwLength );
参数:
1:HANDLE,制定进程的句柄,这表明其拥有查询其他进程的能力。
2:addr:内存地址
3:回写的参数,调用成功后,他会对lpBuffer进行填充。
4:MEMORY_BASIC_INFORMATION的大小,size。
3:回写内容:
typedef struct _MEMORY_BASIC_INFORMATION { PVOID BaseAddress; PVOID AllocationBase; DWORD AllocationProtect; SIZE_T RegionSize; DWORD State; DWORD Protect; DWORD Type; } MEMORY_BASIC_INFORMATION, *PMEMORY_BASIC_INFORMATION;
内容:
1:BaseAddress:回写的首地址,即页面的首地址
2:RegionSize:页面的大小,从基址开始,的大小
3:State,虚拟内存的状态:总共有三种可能的状态:MEM_COMMIT(0x1000):代表已经进行提交,MEM_FREE(0x10000):内存还未使用,MEM_RESERVE(0x2000):保留,已经有人用了,但是未加载进物理内存。
4:Protect:page的一个操作权限,这个操作权限是作用于物理内存,虚拟内存没有这样的权限,包括读写,执行等。
5:Type:MEM_IMAGE:印象,映射,是exe或者dll加载时候的状态,MEM_MAPPED:映射的一个区段,虚拟内存往物理内存映射的时候,存在一个区段,区目。目前还未学习到。MEM_PRIVATE:
4:获取页面属性示例:
#include <windows.h> #include <tchar.h> int main() { DWORD hProcessID = GetCurrentProcessId(); HANDLE hProcess = OpenProcess(PROCESS_QUERY_INFORMATION, FALSE, hProcessID); MEMORY_BASIC_INFORMATION mbi; DWORD dwAddr = 0x0; while (sizeof(mbi) == VirtualQueryEx(hProcess, (LPVOID)dwAddr, &mbi, sizeof(mbi))) { _tprintf(TEXT("BaseAddr:0x%x Size:0x%x State:0x%x\r\n"), mbi.BaseAddress, mbi.RegionSize, mbi.State); dwAddr += (DWORD)mbi.RegionSize; } return 0; }
5:从上面可以看出,很多的State都是0x10000,标识其没有被使用过,排除这些未使用的内存区块,就可以大大提高内存扫描的速度。
动态获取系统内存信息:
1:所有的内存是和我们系统相关的,当需要使用的时候,虚拟内存就加载到物理内存。2:除了前面学的页面大小,分配颗粒之外,在SystemInfo里面还存储了用户区域的开始以及结束的地址,用户区域的开始以及结束地址可以被获取出来。动态获取会使程序的收缩性变得更强。
3:
#include <iostream> #include <windows.h> #include <tchar.h> int main() { setlocale(LC_ALL, "chs"); SYSTEM_INFO sysInfo; GetSystemInfo(&sysInfo); _tprintf(TEXT("页面大小:%d\r\n"), sysInfo.dwPageSize); _tprintf(TEXT("分配颗粒:%d\r\n"), sysInfo.dwAllocationGranularity); _tprintf(TEXT("用户区开始地址:0x%x\r\n"), sysInfo.lpMinimumApplicationAddress); _tprintf(TEXT("用户区最大地址:0x%x\r\n"), sysInfo.lpMaximumApplicationAddress); return 0; }
4:在32位下和64位下,我们可以发现四个数据都是一样的,在MSDN里面有说明,如果要获取64位实现同样的功能,需要调用GetNativeSystemInfo()函数。在这之前,也必须辨别当前程序是32位韩式64位。
相关文章推荐
- 20170805Windows12_3_虚拟内存页面区块/内存信息
- 20170805Windows12_3_虚拟内存页面区块/内存信息
- 20170805Windows12_3_虚拟内存页面区块/内存信息
- 20170805Windows12_3_虚拟内存页面区块/内存信息
- 20170805Windows12_3_虚拟内存页面区块/内存信息
- 20170805Windows12_3_虚拟内存页面区块/内存信息
- 20170805Windows12_3_虚拟内存页面区块/内存信息
- 20170805Windows12_3_虚拟内存页面区块/内存信息
- 基于visual c++之windows核心编程代码分析(6)分配和释放可读可写的虚拟内存页面
- 20170722Windows12_1_虚拟内存
- 20170722Windows12_1_虚拟内存
- 20170722Windows12_1_虚拟内存
- 20170722Windows12_1_虚拟内存
- 20170805Windows12_4_获取系统内存大小及空间内存
- 20170805Windows12_4_获取系统内存大小及空间内存
- 20170805Windows12_4_获取系统内存大小及空间内存
- 20170805Windows12_4_获取系统内存大小及空间内存
- VFP9获得Windows虚拟内存(页面值)大小
- 20170805Windows12_4_获取系统内存大小及空间内存
- 20170805Windows12_4_获取系统内存大小及空间内存