AfxCheckMemory
BOOL AfxCheckMemory( ); // 检查当前分配的所有内存的完整性
返回值:如果没有内存错误,则为非零值;否则为0。
说明:
这个函数使自由内存池有效并在需要时输出错误信息。如果这个函数没有检测到内存冲突,它什么也不输出。
当前在堆中分配的所有内存块都会被检查,包括那些用 new分配的内存,但是不包括那些用直接调用内存分配函数分配的内存,例如malloc函数或者Windows的GlobalAlloc函数。如果发现有内存块存在错误,就会在调试器上输出错误信息。
如果你在程序模块中包含了下面的程序行:
#define new DEBUG_NEW
后面对AfxCheckMemory的调用都会显示发生内存分配的文件名和行号。
注意:
如果你的模块中包含了一个或多个串行化类的实现,那么你必须在最后一个IMPLEMENT_SERIAL宏之后包含#define程序行。这个函数仅在MFC的调试版本中起作用。
示例:
// AfxCheckMemory的例子
CAge* pcage = new CAge( 21 ); // CAge 是从 CObject.继承而来的
Age* page = new Age( 22 ); // Age 不是从 CObject.继承的
*(((char*) pcage) - 1) = 99; // 破坏前面的保护字节
*(((char*) page) - 1) = 99; // 破坏前面的保护字节
AfxCheckMemory();
程序的结果如下:
memory check error at $0067495F = $63, should be $FD
DAMAGE: before Non-Object block at $00674960
Non-Object allocated at file test02.cxx(48)
Non-Object located at $00674960 is 2 bytes long
memory check error at $00674905 = $63, should be $FD
DAMAGE: before Object block at $00674906
Object allocated at file test02.cxx(47)
Object located at $00674906 is 6 bytes long
AfxDump
void AfxDump(const CObject* pOb); // 如果在调试器内调用,则转存对象的状态
参数: pOb 指向由CObject继承的类的对象的指针。
说明:
在调试器中调用这个函数以在调试时转储对象的状态。AfxDump调用一个对象的Dump函数并且将信息发送到afxDump变量指定的位置。AfxDump仅能在MFC的调试版本中使用。
你的程序代码不应该调用AfxDump,而是应该调用适当对象的Dump成员函数。
AfxDumpStack
void AFXAPI AfxDumpStack(DWORD dwTarget = AFX_STACK_DUMP_TARGET_DEFAULT); // 生成当前栈的一个映像,该函数通常被静态链接
参数: dwTarget 指出转储输出的目标。其取值可以用位或操作符(|)组合起来,可能值如下: · AFX_STACK_DUMP_TARGET_TRACE 通过TRACE宏输出。TRACE仅仅在调试版本中产生输出,在发行版本中不产生输出。同时,TRACE可以被重定向到调试器以外的目标。
· AFX_STACK_DUMP_TARGET_DEFAULT 将转储输出发送到缺省目标。对于调试版本,输出发送给TRACE宏。在发行版本中,输出发送到剪贴板。
· AFX_STACK_DUMP_TARGET_CLIPBOARD 输出仅发送到剪贴板。数据将按CF_TEXT格式以普通文本的形式放在剪贴板上。
· AFX_STACK_DUMP_TARGET_BOTH 同时将输出发送到剪贴板和TRACE宏。
· AFX_STACK_DUMP_TARGET_ODS 通过Win32函数OutputDebugString()直接将输出发送的调试器。如果连接了调试器,它在调试版本和发行版本中都会产生调试器输出。AFX_STACK_DUMP_TARGET_ODS 通常到达调试器(如果连接了调试器),并且不能被重定向。
说明:
这个全局函数可以被用来生成当前栈的一个映象。下面的例子反映了MFC对话框应用程序中按钮处理函数调用AfxDumpStack所产生的单行调试输出:
=== begin AfxDumpStack output ===
...
BFF928E0: WINDOWS\SYSTEM\KERNERL32.DLL! UTUnRegister + 2492 bytes
=== end AfxDumpStack() output ===
BFF928E0: 最近一次函数调用的返回地址
WINDOWS\SYSTEM\KERNEL32.DLL! 包含函数调用的模块的完整路径名
UTUnRegister 调用的函数原型
+ 2492 bytes 以字节为单位的从函数原型地址(这个例子中为UTUnregister)到返回地址(这个例子中为BEF928E0)的偏移
AfxDumpStack在MFC库的调试版本和非调试版本中都可以使用。但是,这个函数通常是静态连接的,即使你的可执行文件以共享DLL的方式使用MFC。
在共享库的实现中,可以在MFCS42.LIB库(以及它的变化形式)中找到这个函数。
为了成功地使用这个函数:
· 在你的路径中必须包含IMAGEHLP.DLL文件。如果你没有这个DLL文件,这个函数会显示一条错误信息。IMAGEHLP.DLL是随Win32 SDK和Windows一起发售的可散发的DLL。在C:\[Windows]\system[32]下查找它。有关IMAGEHLP提供的函数集的介绍可以参考“可移植的可执行文件的操作”一文。
· 具有栈框架的模块必须包含调试信息。如果它不包含调试信息,这个函数仍然会生成对栈的跟踪,但是这种跟踪是很简略的。
AfxEnableMemoryTracking
BOOL AfxEnableMemoryTracking(BOOL bTrack); // 打开或关闭内存跟踪
返回值:以前的跟踪允许状态设置。
参数: bTrack 将这个值设为TRUE时就打开了内存跟踪特性。如果是FALSE则将其关闭。
说明:
诊断内存跟踪通常在MFC的调试版本中有效。利用这个函数对你的代码中正确分配内存的部分禁止跟踪。
有关AfxEnableMemoryTracking的更多信息请参见《Visual C++程序员指南》中的“MFC调试支持”。
注意:这个函数仅在MFC的调试版本中起作用。
AfxIsMemoryBlock
BOOL AfxIsMemoryBlock( const void* p, UINT nBytes, LONG* plRequestNumber = NULL ); // 检验一个内存块是否被正确的分配
返回值:
如果内存块是现在分配的,并且其长度也是正确的,则返回非零值。否则为0。
参数: p 指向将被测试的内存块。
nBytes 包含了以字节为单位的内存块长度。
plRequestNumber 指向一个长整数,它将被设为内存块的分配系列号码。由plRequestNumber指向的这个变量只有当AfxIsMemoryBlock返回非零值时才会被填充。
说明:
检测一个内存地址,确保它代表了一个由new的诊断版本分配的活动的内存块。它同时也检验指定的大小是否与最初分配的大小相符。如果这个函数返回非零值,分配的系列号码将在plRequestNumber中返回。这个号码代表了这个内存块相对于其它所有内存分配的顺序。
示例:
// AfxIsMemoryBlock的例子
CAge* pcage = new CAge( 21 ); // CAge is derived from CObject.
ASSERT( AfxIsMemoryBlock( pcage, sizeof( CAge ) ) )
AfxIsValidString
BOOL AfxIsValidString( LPCSTR lpsz, int nLength = -1 ); // 检验一个字符串指针是否有效
如果给定的指针指向一个给定大小的字符串则返回非零值,否则返回0。
参数: lpsz 要测试的指针。
nLength 指定要测试的字符串的长度,以字节为单位。如果值为-1,表示字符串是以null结尾的。
说明:
使用这个函数来确定指向字符串的指针是否有效。
AfxSetAllocHook
AFX_ALLOC_HOOK AfxSetAllocHook( AFX_ALLOC_HOOK pfnAllocHook ); // 允许在每次进行内存分配事调用一个函数
如果你希望允许分配,则返回非零值。否则返回0。
参数: pfnAllocHook 指定要调用的函数名。参考关于分配函数的原型的说明。
说明:
这个函数设置一个钩子,使每次分配内存之前都会调用一个指定的函数。微软基础类库中的调试内存分配函数能够调用一个用户定义的钩子函数,使用户能够监控内存分配并控制是否允许分配内存。内存分配的钩子函数的原型如下:
BOOL AFXAPI AllocHook( size_t nSize, BOOL bObject, LONG lRequestNumber );
nSize 计划分配的内存大小。
bObject 如果是要为一个CObject派生类对象分配内存则为TRUE,否则为FALSE。
lRequestNumber 内存分配的系列号。
注意,AFXAPI调用约定意味着调用者必须从栈中清除参数。
AfxDoForAllClasses
void AFXAPI AfxDoForAllClasses(
void (* pfn)(const CRuntimeClass* pClass, void* pContext),
void* pContext
); //对所有从CObject继承的支持运行时检查的类执行一个特定的功能
参数: pfn 指向每个类都会调用的重复函数。这个参数是一个指向CRuntimeClass对象的指针以及指向调用者提供给函数的附加数据的void指针。
pContext 指向调用者提供给重复函数的可选数据的指针。这个指针可以是NULL。
说明:
在应用程序的内存空间中,为所有从CObject继承的可串行化的类调用指定的重复函数。从CObject继承的可串行化的类是以DECLARE_SERIAL宏继承的。每次调用指定的重复函数时,都会将在pContext中传递给AfxDoForAllClasses的指针传递给重复函数。
注意:这个函数仅在MFC的调试版本中起作用。
AfxDoForAllObjects
void AfxDoForAllObjects(
void (* pfn)(CObject* pObject, void* pContext),
void* pContext
); // 对所有从CObject继承的用new分配内存对象执行一个指定的功能
参数:pfn 指向每个对象都执行的重复函数。函数的参数是一个指向CObject的指针以及指向调用者提供给函数的附加数据的void指针。
pContext 指向调用者提供给函数的附加数据的指针。这个指针可以为NULL。
说明:
对每个用new分配的从CObject继承的对象执行指定的重复函数。栈、全局变量或嵌入对象不包括在内。每次调用指定的重复函数时,都会将在pContext中传递给AfxDoForAllObjects的指针传递给重复函数。
注意:这个函数仅在MFC的调试版本中起作用。
from:http://hi.baidu.com/ice_water/blog/item/7cef04f73475c42a720eec98.html
posted on 2010-11-25 15:06
我风 阅读(1361)
评论(0) 编辑 收藏 引用