xp下用户程序空间分配(7):Heap
来源:互联网 发布:淘宝一手货源网 编辑:程序博客网 时间:2024/05/14 16:12
快乐虾
http://blog.csdn.net/lights_joy/
lights@hb165.com
本文适用于
Xp sp3
vs2008
欢迎转载,但请保留作者信息
我们都知道在程序里可以使用malloc在堆上分配内存,显然windows应该为这个Heap分配一块空间的,我们在主程序里用malloc分配一小块内存,看看指针指向哪里:
char* p = (char*)malloc(10);
得到一个指针:0x00b267b0
在内存块里面找,很容易就发现了目标:
基址
分配基址
分配保护
大小
状态
保护
类型
00b20000
00b20000
00000004
PAGE_READWRITE
00007000
00001000
MEM_COMMIT
00000004
PAGE_READWRITE
00020000
MEM_PRIVATE
00b27000
00b20000
00000004
PAGE_READWRITE
00009000
00002000
MEM_RESERVE
00000000
00020000
MEM_PRIVATE
从这里可以发现malloc采用的算法并不会在一开始就分配一块很大的内存,如果我们接着用:
p = (char*)malloc(0x10000);
分配一块64K的内存,这时可以发现又多了一块内存:
基址
分配基址
分配保护
大小
状态
保护
类型
00cd0000
00cd0000
00000004
PAGE_READWRITE
00012000
00001000
MEM_COMMIT
00000004
PAGE_READWRITE
00020000
MEM_PRIVATE
00ce2000
00cd0000
00000004
PAGE_READWRITE
000ee000
00002000
MEM_RESERVE
00000000
00020000
MEM_PRIVATE
而这块内存在第一次分配时是空闲的。
由此可以猜测,malloc可以分配得到的最大内存块应该取决于最大的空闲块。写段代码测试一下:
void block_test()
{
SYSTEM_INFO info;
MEMORY_BASIC_INFORMATION mi;
HANDLE hProcess;
DWORD dwAddr;
MEMORY_BASIC_INFORMATION miBlock[1000];
int nCount = 0, nMaxSize = 0;
char* p = NULL;
hProcess = GetCurrentProcess();
GetSystemInfo(&info);
dwAddr = (DWORD)info.lpMinimumApplicationAddress;
do
{
VirtualQueryEx(hProcess, (LPCVOID)dwAddr, &mi, sizeof(mi));
memcpy(&miBlock[nCount++], &mi, sizeof(mi));
dwAddr += mi.RegionSize;
if((mi.State & MEM_FREE) && mi.RegionSize > nMaxSize)
nMaxSize = mi.RegionSize;
} while(dwAddr < (DWORD)info.lpMaximumApplicationAddress);
p = malloc(nMaxSize);
………..
}
得到的nMaxSize = 0x34c1 0000,但是内存分配失败,么回事?跟踪一下malloc的执行过程,发现在执行过程中有这样的调整:
blockSize = sizeof(_CrtMemBlockHeader) + nSize + nNoMansLandSize;
经过这样的调整,blockSize就变成了0x34c1 0024,所以分配失败。
我们将这个大小略作调整:
p = malloc(nMaxSize – 0x24);
还是分配失败。
想想,如果windows要将一个空闲块用作heap,那么想必需要写入一些辅助信息,咱再把这个大小调小一点:
p = malloc(nMaxSize – 0x124);
哈哈,终于成功了!咱终于分配了885M的内存。
难怪windows要将这些系统DLL尽量往高处放!
趁热打铁,咱创建一个最简单的console application,这样就没有太多的DLL来进行干扰。再运行上面的代码,这样可以得到一个最大的内存块大小0x6c4d d000,期望能够直接分配,但是--------失败了!
考虑windows的内存块分配是以0x10000进行对齐的,尝试分配0x6c4d0000,这回可算成功了,哈哈,咱就有了1.8G的空间!但是malloc函数的执行过程超慢,过了足足十几秒才分配成功,不知道它到底还要做些什么工作。而且其它程序的运行就此变成蜗牛速度,呵呵。
顺带说一下,俺只有2G内存。
1 参考资料
xp下用户程序空间分配(6):加载用户DLL(2009-8-28)
xp下用户程序空间分配(5):加载系统DLL(2009-8-27)
xp下用户程序空间分配(4):加载主程序(2009-8-27)
xp下用户程序空间分配(3):加载文件(2009-8-26)
xp下用户程序空间分配(2):栈(2009-8-26)
xp下用户程序空间分配(1):大致框架(2009-8-26)
- xp下用户程序空间分配(7):Heap
- xp下用户程序空间分配(1):大致框架
- xp下用户程序空间分配(2):栈
- xp下用户程序空间分配(3):加载文件
- xp下用户程序空间分配(4):加载主程序
- xp下用户程序空间分配(8):MEM_MAPPED
- xp下用户程序空间分配(6):加载用户DLL
- xp下用户程序空间分配(5):加载系统DLL
- xp下用户程序空间分配(9):还剩下什么?
- lfs下selinux用户空间程序的安装(可选)
- 在XP环境下给Asp.net程序分配权限!
- 程序的内存分配 栈区(stack) 堆区(heap
- 创建临时表空间,表空间用户(分配权限)
- STM32启动时RAM空间堆(Heap)和栈(stack)的分配
- Oracle 创建用户,分配空间,用户授权
- 程序运行的空间分配
- heap stack 堆栈 全局变量 静态变量 进程空间 内存分配
- heap stack 堆栈 全局变量 静态变量 进程空间 内存分配
- Windows 消息机制
- 激励人生的10张海报
- Enable Skin support in your Symbian OS applications
- 宽字符跟ASCII——区别及测试
- 客户端无字体时的做法
- xp下用户程序空间分配(7):Heap
- VS2005把我弄晕了
- 在struts2.0中指定日期的输入输出格式
- DateTime 格式
- 2009-08-28
- 最近居然在研究openVMS
- 疑问:Perl读取UTF8编码的文件,显示乱码。
- Singleton
- e62最佳软件之UC浏览器,UCWEB 6.7正式版,免签名版下载