使用PageHeap.EXE或GFlags.EXE检查内存越界错误 (转)

2011-05-27 20:19 290人阅读 评论(0) 收藏 举报

microsoftdebuggingstructureoutputimagefile

必先利其器之一:使用PageHeap.EXE或GFlags.EXE检查内存越界错误
  Article last modified on 2002-6-3
  ----------------------------------------------------------------
  The information in this article applies to:
  - Microsoft Visual C++, 32-bit Editions, version 6.0, SP5
  ----------------------------------------------------------------
  我推荐使用PageHeap.Exe和Gflags.Exe,主要的原因还是因为当有人问内存越界的错误如何查出来的时候,国外的朋友经常会推荐这两个工具(highly recommend)。我用过之后,也觉得有些时候用用还是有好处的。
  
  PageHeap.Exe将针对某个指定的应用程序启用Page Heap标志,从而自动监视所有的malloc、new和heapAlloc的内存分配,找出内存错误。
  PageHeap.Exe的下载地点:
http://support.microsoft.com/default.aspx?scid=http://download.microsoft.com/download/vc60pro/Utility/6.0/WIN98/EN-US/PageHeap1.exe
  下面我们简单地给出PageHeap使用步骤:
  第一步:
  在命令行中运行PageHeap.Exe。如果你以前设置过启用Global Page Heap标志,那么你将看到一个列表,给出所有已经启用了的应用程序的名字,不含路径。
  如下所示:
  C:/>pageheap
  pgh.exe enabled
  testSplit.exe enabled
  第二步:
  编译一个小程序,其中有如下代码:
  void main()
  {
   int m_len = 5;
   char *m_p = (char *)HeapAlloc (GetProcessHeap (), HEAP_ZERO_MEMORY, m_len);
   m_p[m_len] = 0;
  
   HeapFree (GetProcessHeap (),0, m_p);
  }
  Build出一个Debug版本。运行之,你看不到有任何异常的报告。
  但其实m_p[m_len]=0这句话就是越界写了,因为只分配到了m_p[m_len-1]!这种情况就叫Dynamic memory overrun。用BoundsChecker是可以查到的。
  这时,表面上看不出任何问题,但是一颗定时炸弹已经埋下了。
  第三步:
  在命令行中运行PageHeap /enable YourApplicationName.exe 0x01。
  再运行一次不带参数的PageHeap,察看上面的命令是否生效。你的应用程序应该在启用的列表中。
  注意:千万不要在YourApplication.Exe前面加上路径!!
  0x01的含义在后面说明。
  第四步:
  再次运行你的程序。
  你将会注意到在Output窗口的加载各种DLL之前,多了几句话:
  Loaded exports for ‘C:/WINNT/System32/ntdll.dll‘
  Page heap: process 0x57C created heap @ 00130000 (00230000, flags 0x1)
  Loaded ‘C:/WINNT/system32/MFC42D.DLL‘, no matching symbolic information found.
  ..
  Loaded ‘C:/WINNT/system32/MSVCP60D.DLL‘, no matching symbolic information found.
  Page heap: process 0x57C created heap @ 00470000 (00570000, flags 0x1)
  Loaded exports for ‘C:/WINNT/system32/imm32.dll‘
  这就是Page Heap的监视机制在发挥作用!他告诉你你的堆00470000被创建出来了。
  然后程序退出后,Output窗口有这么几句话表明一定有什么错误发生了:
  Page heap: block @ 0015AFF8 is corrupted (reason 10)
  Page heap: reason: corrupted suffix pattern
  Page heap: process 0x57C destroyed heap @ 00471000 (00570000)
  The thread 0x8A8 has exited with code 0 (0x0).
  这说明在销毁堆00470000时遇到了麻烦,就是数据块0015AFF8被误用了,原因是误用了下标语法。看,说得多么清楚!也节省了许多翻来覆去查代码的工作!
  PageHeap的使用中有几点值得注意:
  1:启用PageHeap不能够影响正在运行中的应用程序。如果你需要启用一些正在运行且不能重启的程序的PageHeap,那请运行PageHeap启用后,重新启动机器。
  2:要想查看PageHeap把信息放到哪里了,请打开你的注册表,来到
   /HKEY_LOCAL_MACHINE/SOFTWARE/Microsoft/Windows NT
  /CurrentVersion/Image File Execution Options
  你将会看到你的应用程序也在这个项下面。你的应用程序的GlobalFlag被设置为了0x02000000,PageHeapFlags被设置为了0x01。
 
 3:PageHeap的原理是这样,它在已分配的内存的后面放上几个守护字节(Guard
Bytes),再跟上一个标记为PAGE_NOACCESS的内存页。这样,已分配内存的后面如果被重写了,那么守护字节就会被改变,于是当内存被释放
时,PageHeap就会引发一个AV(Access
Violation)。大体上就是这样。所以只有最后释放这块问题内存时,才会有PageHeap的报告!这就是PageHeap的局限性吧。
  参数0x01的含义:
  FLAGS hex value (0x...) has the following structure:
   B7-B0 Bit flags 1 - enable page heap
   01 - enable page heap. If zero normal heap is used.
   In 99% of the cases you will want this to be set.
   02 - collect stack traces (default on checked builds)
   04 - minimize memory impact
   08 - minimize randomly(1)/based on size range(0)
   10 - catch backward overruns
  看到了吗?你还可以设置参数为0x10,从而可以检查内存向前的越界写!
 
 Gflags.Exe是微软的Debugging Tools里面的工具。在Windows 2000的Resource
Kit中也可以找得到。我们也可以用它来完成和PageHeap相同的任务。当然,Gflags.EXE还能做许许多多其他的事情。这里我们就不介绍了,
总之物超所值。
  具体的使用办法是:
  1) 运行Gflags.Exe;
  2) 你将看到一个对话框。在”Image File”的编辑框中写下你的应用程序的名字,如YourApp.Exe。注意不要路径!
  3) 选择”Image File Options”的单选钮;
  4) 这时,你会看到对话框的内容突然一变。选中“Place heap
  allocations at ends of pages”前的复选框。
  5) 点击Apply按钮。
  这样,就达到了PageHeap的效果。现在运行你的程序,overwrite你的堆,就应该生成一个AV了!
  (预知详情请收听微软KB:SAMPLE: PageHeap1.exe Finds Heap Corruption and Memory Errors (Q264471) 你可以按照这篇文档所指引的步骤学习如何使用PageHeap)

时间: 2024-10-12 21:17:09

使用PageHeap.EXE或GFlags.EXE检查内存越界错误 (转)的相关文章

HSV做通道分离是出现的Vector内存越界错误

vector<Mat> hsvSplit; //因为我们读取的是彩色图,直方图均衡化需要在HSV空间做 split(imgHSV, hsvSplit); equalizeHist(hsvSplit[2], hsvSplit[2]); merge(hsvSplit, imgHSV); 用上面的代码做HSV通道分离的时候,出现Vector内存越界的情况 解决方案一: vector<Mat> hsvSplit; //因为我们读取的是彩色图,直方图均衡化需要在HSV空间做 hsvSplit

Android Monkey 脚本编写与检查内存泄露

一.Monkey脚本编写 1.Monkey脚本格式 脚本优势: 简单快捷,不需要接触任何工具,只需要一个记事本文件 脚本缺点: 实现坐标.按键等基本操作的相应步骤,顺序脚本无逻辑性 脚本源码: \development\cmds\monkey\src\com\android\commands\monkey\MonkeySourceScrip.java #头文件.控制monkey发送消息的参数 type=raw events count=10 speed=1.0 #以下为monkey命令 star

DICOM:dcmqrscp.exe与storescu.exe中C-STORE服务的差别

背景: 专栏中曾分别写过dcmqrscp.exe与storescu.exe工具包的介绍,但是并未深究两者之间的差别.dcmqrscp.exe工具是一个mini版PACS,可分别响应C-FIND.C-MOVE.C-GET.C-STORE等各种DIMSE服务,而storescu.exe工具是C-STORE服务使用者,可以看出这两个工具包都提供C-STORE SCU服务.前几天博友的一个问题使得重新研究了一下两者在实现C-STORE SCU服务上的差别.通过源码分析发现问题根源出在Presentati

在64位windows下使用instsrv.exe和srvany.exe创建windows服务

在64位windows下使用instsrv.exe和srvany.exe创建windows服务 在32位的windows下,包括windows7,windows xp以及windows 2003,都可以使用instsrv.exe和srvany.exe来创建自定义的windows服务.比如,我们有一个bat文件,用于将指定的程序作为服务进行启动,使用一般的工具都不可以进行此类工作,而使用由windows 2003的资源工具包windows toolkit中所带的instsrv就可以. 详细的用法这

在64位windows下使用instsrv.exe和srvany.exe创建windows服务[转]

本文转自:https://www.iflym.com/index.php/computer-use/201205020001.html 在32位的windows下,包括windows7,windows xp以及windows 2003,都可以使用instsrv.exe和srvany.exe来创建自定义的windows服务.比如,我们有一个bat文件,用于将指定的程序作为服务进行启动,使用一般的工具都不可以进行此类工作,而使用由windows 2003的资源工具包windows toolkit中所

DICOM医学图像处理:storescp.exe与storescu.exe源码剖析,学习C-STORE请求

背景: 上一篇专栏博文中针对PACS终端(或设备终端,如CT设备)与RIS系统之间worklist查询进行了介绍,并着重对比分析了DICOM3.0中各部分对DICOM网络通讯服务的定义.此次通过结合早些时间的博文DICOM医学图像处理:基于DCMTK工具包学习和分析worklist,对DCMTK开源库中提供的storescp.exe和storescu.exe工具的源码进行剖析,从底层深入了解C-STORE服务的触发及响应. 分析思路: storescp.exe和storescu.exe分别充当着

Windows10下python3和python2同时安装 python2.exe、python3.exe和pip2、pip3设置

1.添加python2到系统环境变量 打开,控制面板\系统和安全\系统,选择高级系统设置,环境变量,选择Path,点击编辑,新建,分别添加D:\Python\python27和D:\Python\python27\Scripts到环境变量. 注意:python3安装时可以选择自动添加到系统环境变量,如未选择,方法和python2添加过程相同. 2.修改python.exe名字为python2.exe和python3.exe 找到python2和python3的安装目录,修改python2.7.9

DICOM:DCMTK工具包分析之dcmqrscp.exe、dcmqridx.exe、dcmqrti.exe

背景: 新的一年开始,专栏会坚持下去,继续与大家相互交流学习.本篇博文再一次分析DCMTK自带的工具包dcmqrscp.exe(类似于一个单机版miniPACS),此次主要关注dcmqrscp.exe的数据库部分,通过使用dcmqridx.exe手动操作dcmqrscp.exe的数据库文件,直观了解数据库的记录内容:然后利用dcmqrti.exe查询dcmqrscp.exe的数据库文件,学习如何操作dcmqrscp.exe数据库. 单机版数据库: 单机版数据库就是只能运行在单机上,不提供网络功能

DICOM医学图形处理:storescp.exe与storescu.exe源码剖析,学习C-STORE请求(续)

背景: 上一篇博文中,在对storescp工具源文件storescp.cc和DcmSCP类的源文件scp.cc进行剖析后,得出了两者都可以实现响应C-ECHO和C-STORE(需要对DcmSCP类进行扩展)请求的功能.但是在对DcmSCP类进行扩展,期望模拟实现自己的storescp.exe工具时遇到了问题,客户端提示服务中断链接,而服务端显示保存失败,如下图所示.此次博文通过排除该问题再一次对storescp.cc和scp.cc进行对比,主要从Presentation Context.Abst