C/C++内存问题检查利器—Purify (二)
2003-12-11 11:37
609 查看
三、 示例
假设我们现在有这样一段程序:hello.c#include <stdio.h> #include <malloc.h> static char *helloWorld = "Hello, World"; main() { char *mystr = malloc(strlen(helloWorld)); strncpy(mystr, helloWorld, 12); printf("%s\n", mystr); } |
> purify gcc -g -o hello hello.c
Purify 2003.06.00 Solaris 2 (32-bit) Copyright (C) 1992-2002 Rational Software Corp.
All rights reserved.
Instrumenting: cckc6pUD.o Linking
记得加上“-g”的选项,不然,purify不能显示源程序。好了,现在在当前目录下产生了可执行文件——hello,在运行hello之前,我们还得注意,执行被Purify编译过的程序,有可能会出现X-Windows,所以请注意设置DISPLAY环境,如果你是在Windows的Telnet客户端下执行,那么你可以在Windows下装一个叫做Exceed的工具软件,它可以方便地把X-Window显示在你的Windows桌面上)
好了,我们现在执行hello程序,就可以看到下面的一个窗口:
我们可以看到Purify的报告中有两个内存错误,一个是ABR(Array Bounds Read)——数组越界读,一个是12个字节的Memory Leaked,展开小三角符号,我们可以看到更为详细报告:
展开ABR错误后,我们可以看到,ABR错误的产生是由printf产生的,而产生错误的内存是mystr。通过观察,我们马上可以发现为会什么会出现ABR错误,原因是C/C++中的字符串都是以“\0”结尾的,而我们分配字符串时,应该要比实际长度多一,以存放结束符,而我们以后面调用的strncpy只拷贝了字符串的有效内容,并没有在字符串最后加上一个结束符。而系统调用printf输出字符串内容直至遇到结束符,所以当其访问到12个长度时,还没有发现结束,于是继续向下访问,于是就出现了ABR错误。
好了,让我们再来看看Memory Leaked的报告信息:
我们可以看到,Purify指出了那块内存出现了内存泄露,泄露了多少个字节。通过Purify的报告,再加上我们对C/C++基础的了解,我们立马知道mystr是在堆上分配的内存,所以必须要我们自己手动释放,查看程序,我们发现我们忘了free ( mystr )。
好了,现在我们可以根据Purify报告修改我们的程序了:
#include <stdio.h> #include <malloc.h> static char *helloWorld = "Hello, World"; main() { char *mystr = malloc(strlen(helloWorld)+1); strncpy(mystr, helloWorld, 12); mystr[12]=”\0”; printf("%s\n", mystr); free(mystr); } |
四、 内存问题一览
下面是Purify所能检测到的内存信息表:[align=center]内存信息[/align] | [align=center]描述[/align] | [align=center]错误等级[/align] |
[align=center]ABR[/align] | [align=left]Array Bounds Read 数组越界读[/align] | [align=center]3级[/align] |
[align=center]ABW[/align] | [align=left]Array Bounds Write 数组越界写[/align] | [align=center]2级[/align] |
[align=center]BSR[/align] | [align=left]Beyond Stack Read 越栈读[/align] | [align=center]3级[/align] |
[align=center]BSW[/align] | [align=left]Beyond Stack Write 越栈写[/align] | [align=center]3级[/align] |
[align=center]COR[/align] | [align=left]Core Dump Imminent 非法操作[/align] | [align=center]1级[/align] |
[align=center]FIU[/align] | [align=left]File De.ors In Use 文件描述符被使用[/align] | [align=center]4级[/align] |
[align=center]FMM[/align] | [align=left]Freeing Mismatched Memory 释放错误内存[/align] | [align=center]2级[/align] |
[align=center]FMR[/align] | [align=left]Free Memory Read 对已释放内存读[/align] | [align=center]3级[/align] |
[align=center]FMW[/align] | [align=left]Free Memory Write 对已释放内存写[/align] | [align=center]2级[/align] |
[align=center]FNH[/align] | [align=left]Freeing Non Heap Memory 释放非堆内存[/align] | [align=center]2级[/align] |
[align=center]FUM[/align] | [align=left]Freeing Unallocated Memory 释放了没有分配的内存[/align] | [align=center]2级[/align] |
[align=center]IPR[/align] | [align=left]Invalid Pointer Read 非法指针读[/align] | [align=center]1级[/align] |
[align=center]IPW[/align] | [align=left]Invalid Pointer Write 非法指针写[/align] | [align=center]1级[/align] |
[align=center]MAF[/align] | [align=left]Malloc Failure 分配内存失败[/align] | [align=center]4级[/align] |
[align=center]MIU[/align] | [align=left]Memory In-Use 内存正在使用[/align] | [align=center]4级[/align] |
[align=center]MLK[/align] | [align=left]Memory Leak 内存泄露[/align] | [align=center]3级[/align] |
[align=center]MRE[/align] | [align=left]Malloc Reentrancy Error remalloc错[/align] | [align=center]2级[/align] |
[align=center]MSE[/align] | [align=left]Memory Segment Error 内存段错[/align] | [align=center]3级[/align] |
[align=center]NPR[/align] | [align=left]Null Pointer Read 空指针读[/align] | [align=center]1级[/align] |
[align=center]NPW[/align] | [align=left]Null Pointer Write 空指针写[/align] | [align=center]1级[/align] |
[align=center]PAR[/align] | [align=left]Bad Parameter 错误的参数[/align] | [align=center]3级[/align] |
[align=center]PLK[/align] | [align=left]Potential Leak 潜在的内存泄露[/align] | [align=center]3级[/align] |
[align=center]SBR[/align] | [align=left]Stack Array Bounds Read 栈数组越界读[/align] | [align=center]3级[/align] |
[align=center]SBW[/align] | [align=left]Stack Array Bounds Write 栈数级越界写[/align] | [align=center]2级[/align] |
[align=center]SIG[/align] | [align=left]Signal 信号[/align] | [align=center]4级[/align] |
[align=center]SOF[/align] | [align=left]Stack Overflow 栈溢出[/align] | [align=center]3级[/align] |
[align=center]UMC[/align] | [align=left]Uninitialized Memory Copy 对未初始化的内存进行拷贝[/align] | [align=center]3级[/align] |
[align=center]UMR[/align] | [align=left]Uninitialized Memory Read 对未初始化的内存读[/align] | [align=center]3级[/align] |
[align=center]WPF[/align] | [align=left]Watchpoint Free 释放被监控的内存[/align] | [align=center]4级[/align] |
[align=center]WPM[/align] | [align=left]Watchpoint Malloc 被监控的内存分配[/align] | [align=center]4级[/align] |
[align=center]WPN[/align] | [align=left]Watchpoint Entry 被监控的内存[/align] | [align=center]4级[/align] |
[align=center]WPR[/align] | [align=left]Watchpoint Read 被监控的内存读[/align] | [align=center]4级[/align] |
[align=center]WPW[/align] | [align=left]Watchpoint Write 被监控的内存写[/align] | [align=center]4级[/align] |
[align=center]WPX[/align] | [align=left]Watchpoint Exit 退出被监控的内存[/align] | [align=center]4级[/align] |
[align=center]ZPR[/align] | [align=left]Zero Page Read 零页面读[/align] | [align=center]1级[/align] |
[align=center]ZPW[/align] | [align=left]Zero Page Write 零页面写[/align] | [align=center]1级[/align] |
相关文章推荐
- C/C++内存问题检查利器—Purify (四)
- C/C++内存问题检查利器—Purify (二)
- C/C++内存问题检查利器—Purify (四)
- C/C++内存问题检查利器—Purify (五)
- C/C++内存问题检查利器—Purify (三)
- C/C++内存问题检查利器—Purify (五)
- C/C++内存问题检查利器—Purify (一)
- C/C++内存问题检查利器—Purify (一)
- C/C++内存问题检查利器——Purify
- C/C++内存问题检查利器—Purify (五)
- C/C++内存问题检查利器—Purify (一)
- C/C++内存问题检查利器—Purify(三)
- C/C++内存问题检查利器—Purify (二)
- C/C++内存问题检查利器—Purify (二)
- C/C++内存问题检查利器—Purify (一)
- C/C++内存问题检查利器—Purify (一)
- C/C++内存问题检查利器—Purify (二)
- C/C++内存问题检查利器—Purify (三)
- C/C++内存问题检查利器—Purify (三)
- C/C++内存问题检查利器—Purify (二)