04-常见内存错误以及valgrind使用

04-常见内存错误以及valgrind使用

代码段:

只读数据,因此对这一部分的数据,试图写只读数据,这个在编译的时候基本上可以检测。

数据段/BSS段:

未初始化直接访问,即使没有显示初始化,仍然会初始化为0

栈空间数据:

(1)局部变量,未初始化变量会给随机的初值,出现异常情况更诡异

(2)栈溢出:在栈中申请过大的局部变量

堆空间数据

内存泄露 (1)申请未释放(2)申请后,双重释放

对于所有的地址空间:

(1) 野指针的问题:未初始化指针,会访问这个指针指向的空间

(2) 越界访问:例如一个数据a[10] ,试图访问啊a【10】以及以后数据

(3) 非法的越权访问  例如:mmap的空间只读,但试图写

(4) 空间不在控制范围仍然去访问空间,例如返回局部变量地址,且后面访问这个空间

虽然在编程时尽量避免这些问题,但是一旦出现问题,要善于使用工具去检测我们的内存错误

可以使用工具

$Sudo apt-get install valgrind

$ valgrind --tool=memcheck--show-reachable=yes --read-var-info=yes --verbose --time-stamp=yes --leak-check=full--log-file=mycode.log ./valgrind_example01

如果要使用图形化的工具,需要安装QT 这个工具名字叫 Valkyrie
 
第一、自己在编程中,要避免一些常见的错误,第二、要善于使用工具去检测我们的内存错误。
 
测试例子:
[email protected]:~/wangyiStudy# ls
valgrind_example01.c
[email protected]:~/wangyiStudy#gcc -g -o valgrind_example01 valgrind_example01.c 
[email protected]:~/wangyiStudy# ls
valgrind_example01  valgrind_example01.c
[email protected]:~/wangyiStudy#valgrind --tool=memcheck --show-reachable=yes --read-var-info=yes --verbose--time-stamp=yes --leak-check=full --log-file=mycode.log ./valgrind_example01
[email protected]:~/wangyiStudy# ls
mycode.log  valgrind_example01  valgrind_example01.c


测试程序代码:valgrind_example01.c
[email protected]: # morevalgrind_example01.c
#include<stdio.h>
#include<stdlib.h>
int
main(void){
        int i[5];
        if(i[0] == 0)
            i[1] = 1;
        char *ptr1;
        *ptr1 = ‘c‘;
        char *ptr = malloc(100);
 
       free(ptr);
       free(ptr);
       return 0;
}

查看生成的日志:

[email protected]:~/wangyiStudy# moremycode.log

==00:00:00:03.1165282== HEAP SUMMARY:

==00:00:00:03.1165282==     in use at exit: 0 bytes in 0blocks

==00:00:00:03.1165282==   totalheap usage: 1 allocs, 2 frees, 100 bytes allocated      //一次申请,双重释放

==00:00:00:03.1165282==

==00:00:00:03.1165282== All heap blocks were freed -- no leaks are possible

==00:00:00:03.1165282==

==00:00:00:03.1165282== Use --track-origins=yes to see where uninitialised values come from

==00:00:00:03.1165282== ERROR SUMMARY: 3 errors from 3 contexts (suppressed: 0 from 0)

==00:00:00:03.1165282==

==00:00:00:03.1165282== 1 errors in context 1 of 3:

==00:00:00:03.1165282== Invalid free() / delete / delete[] / realloc()

==00:00:00:03.1165282==    at 0x4C2BDEC: free (in/usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)

==00:00:00:03.1165282==    by 0x4005BF: main(valgrind_example01.c:15)

==00:00:00:03.1165282==  Address 0x51fd040 is 0 bytes insidea block of size 100 free‘d

==00:00:00:03.1165282==    at 0x4C2BDEC: free (in/usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)

==00:00:00:03.1165282==    by 0x4005B3: main(valgrind_example01.c:14)

==00:00:00:03.1165282==

==00:00:00:03.1165282==

==00:00:00:03.1165282== 1 errors in context 2 of 3:

==00:00:00:03.1165282== Use of uninitialised value of size 8

==00:00:00:03.1165282==    at 0x400597: main(valgrind_example01.c:11)

==00:00:00:03.1165282==

==00:00:00:03.1165282==

==00:00:00:03.1165282== 1 errors in context 3 of 3:

==00:00:00:03.1165282== Conditional jump or move depends on
uninitialised value(s)    //未初始化

==00:00:00:03.1165282==    at 0x40058A: main (valgrind_example01.c:8)                            // 错误定位

==00:00:00:03.1165282==

==00:00:00:03.1165282== ERROR SUMMARY: 3 errors from 3 contexts(suppressed: 0 from 0)     // 总计 3 出错误

时间: 2024-09-28 05:06:04

04-常见内存错误以及valgrind使用的相关文章

C语言常见内存错误

C语言指针和内存泄露 常见的内存错误: 1.      内存分配未成功却使用了它. 如果指针p是函数的参数,要在函数的入口处用assert(p!=NULL)进行检查: 如果是用malloc来动态申请内存,应该用if(p==NULL)或if(p!=NULL)进行防错处理. 2.      内存分配成功,尚未初始化就使用它. 3.      内存分配成功并且初始化,但操作越界. 例如在使用数组时经常发生"多1"或"少1"操作. 4.      忘记释放内存造成内存泄露.

大内高手—常见内存错误

转自:http://blog.chinaunix.net/uid-23228758-id-4355524.html 随着诸如代码重构和单元测试等方法引入实践,调试技能渐渐弱化了,甚至有人主张废除调试器.这是有道理的,原因在于调试的代价往往太大了,特别是调试系统集成之后的BUG,一个BUG花了几天甚至数周时间并非罕见. 而这些难以定位的BUG基本上可以归为两类:内存错误和并发问题.而又以内存错误最为普遍,即使是久经沙场的老手,也有时也难免落入陷阱.前事不忘,后世之师,了解这些常见的错误,在编程时就

常见内存错误的几点总结

学习C语言以来一直没有注意到细节的控制,敲代码总是"无所顾忌"的.如今慢慢把程序写大写复杂了.在资源宝贵和的嵌入式中.这个问题越来越须要注意了--内存的管理..让编程慢慢走上正轨,慢慢走上可预见性吧,慢慢与机器融为一体,慢慢习惯于如梁肇新前辈所说以机器的思维方式思维吧!!! 1.返回局部变量地址将引起内存错误 2.暂时空间过大:操作系统在载入某个应用程序时,都将为其分配一定大小的栈空间,若申请过大的局部变量.可能会引起栈溢出问题. (PC机上Windows和Linux系统一般不必操心这

[草稿][C语言][内存分配]常见内存错误

1. 使用未分配成功的内存 解决案: ①在使用内存前检查指针是否为NULL ②参数是指针时,在函数入口处用assert进行判断 ③如果指针指向动态申请的内存,用if进行容错处理 2. 使用分配成功,但未初始化的内存 解决案: ①定义数组后一定要初始化 3. 内存泄漏 解决案: ①new/malloc和delete/free一定要成对出现 4. 使用已被释放的内存 解决按: ①不要返回指向栈内存的指针或引用 ②释放内存后,将指针置为NULL

C语言中常见的内存错误与解决方法

常见的错误 关于内存的一些知识已在内存分配中提及,现记录与分享常见的内存错误与对策. 类型 1:内存未分配成功,却使用了它. 方   法:在使用之前检查指针是否为NULL. 1)当指针p是函数的参数时,在函数入口处用语句assert(p!=NULL)进行断言检查. 2)当使用malloc或new来申请内存时,应该用if(p != NULL)进行防错检查. 类型 2:引用了尚未初始化的指针 原   因:内存的缺省初始值究竟是什么并没有统一的标准,在使用之前都进行初始化. 1)没有初始化的观念. 2

常见动态内存错误---内存泄漏

常见动态内存错误 编译器不能自动发现动态内存错误,动态内存错误通常只能在程序运行时才能被捕捉到,而且错误原因不容易查找,错误本身也不容易捕捉,改错难度较大. 1.动态内存分配失败却继续操作 内存不足等有可能导致动态内存分配失败,所以使用new请求分配动态内存后一定要检查返回地址是否为NULL. 如用if(p==NULL) 或 if(p!=NULL)进行检查,未检查前不要操作动态内存空间. 2.动态内存空间未初始化就进行读操作 C++标准并未规定动态内存空间的默认值,程序无法预知该默认值的具体指.

linux实用技巧:检测内存泄漏工具Valgrind

1.Valgrind简介 1.在我们编写C/C++的时候,最常见的错误之一就是内存泄露,这样的问题其实跟程序员的编程习惯密不可分.如果你在申请内存空间之后能够马上在合适的位置释放内存.会极大程度的避免内存泄漏的情况.但是人非圣贤,孰能无过.有时候我们确实忘记释放内存而导致了比较严重的错误,所以这个时候我们需要借助valgrind这个工具来判断内存泄漏. Valgrind 是一款 Linux下(支持 x86.x86_64和ppc32)程序的内存调试工具,它可以对编译后的二进制程序进行内存使用监测(

iOS开发 两个内存错误的一般处理方法

本文转载至 http://blog.sina.com.cn/s/blog_a843a8850101dxlj.html 由于iOS5.0之前没有自动应用计数机制,也没有Java那样的垃圾回收功能.我们都需要自己管理和控制对象的回收,这是一件很麻烦的事情,也是做iOS项目中最容易出现的问题.如果不掌握这些方法,调试这些问题几乎没有头绪. 1.EXC_BAD_ACCESS内存错误与NSZombieEnabledEXC_BAD_ACCESS是最常见的错误了,这个一般是访问了释放了的内存地址空间造成的.比

PHP编程中10个最常见的错误

PHP是一种非常流行的开源服务器端脚本语言,你在万维网看到的大多数网站都是使用php开发的.本篇经将为大家介绍PHP开发中10个最常见的问题,希望能够对朋友有所帮助. 错误1:foreach循环后留下悬挂指针 在foreach循环中,如果我们需要更改迭代的元素或是为了提高效率,运用引用是一个好办法: 1 2 3 4 5 $arr = array(1, 2, 3, 4); foreach ($arr as &$value) {     $value = $value * 2; } // $arr