• Linux下发生几个字节内存泄露检测方法


    一.  简介

    Linux 环境下进行 C/C++ 开发过程中,经常会使用 malloc/calloc() 函数分配堆空间,常常因为疏忽,忘记释放堆内存。从而导致内存泄露问题。

    当发生肉眼可见大量的内存泄露时,可以使用 shell 命令来确认是否存在泄露。

    但是,当每次程序只是发生几个字节的内存泄露时,shell 命令可能无法察觉到内存泄露问题。

    这里介绍一种监测代码发生几个字节内存泄露的方法。

    二.  Linux下发生几个字节内存泄露排查方法一

    1. 检测方法实现思路:

    首先,在代码当前目录创建一个目录,存放调试log信息。

    其次,自定义堆空间申请与释放的函数,即对堆空间申请/释放函数进行封装。在自定义的堆申请函数中,创建一个以堆地址命令的文件。

    其次,在自定义的堆释放函数中,删除文件。

    最后,将这部分监测代码用来测试代码中是否存在内存泄露。

    注意: 这种方法只适用于单个 C/C++ 源文件,即对一个 C 文件中内存泄露问题的排查。

    2.  方法使用实例:

    下面介绍具体的监测方法。在源码当前目录创建一个目录文件,下面创建了一个 debug目录。C 代码实现如下:

    1. #include
    2. #include
    3. #include
    4. #define FILE_CONTENTS "./debug"
    5. char file_name[256] = {0};
    6. void* check_malloc(size_t size, const char* file, int line)
    7. {
    8. void* p = malloc(size);
    9. sprintf(file_name, "%s/%p.mem", FILE_CONTENTS, p);
    10. FILE* fp = fopen(file_name, "w");
    11. fprintf(fp, "[+%s line: %d]--->addr: %p, size: %ld\n", file, line, p, size);
    12. fflush(fp);
    13. fclose(fp);
    14. return p;
    15. }
    16. void check_free(void* p, const char* file, int line)
    17. {
    18. sprintf(file_name, "%s/%p.mem", FILE_CONTENTS, p);
    19. if(unlink(file_name) < 0) //file no exist
    20. {
    21. printf("double free: %p\n", p);
    22. return;
    23. }
    24. free(p);
    25. }
    26. #define malloc(size) check_malloc(size, __FILE__, __LINE__)
    27. #define free(p) check_free(p, __FILE__, __LINE__)
    28. int main(void)
    29. {
    30. char* p1 = (char*)malloc(20);
    31. char* p2 = (char*)malloc(30);
    32. free(p2);
    33. p2 = NULL;
    34. return 0;
    35. }

    使用上面代码即可对单个源码文件中代码进行内存泄露的排查。如下演示一下对下面一段代码的排查。

    操作如下:

    首先,在当前目录下,创建一个存放调试 log 信息的目录文件 debug。

    其次,将第一段代码添加到待调试代码中。进行编译,即输入 gcc -g main.c -o main.out 命令。

    最后,当存在内存泄露时会在 debug 文件中生成 相关文件。

    如下所示:在 debug 目录下生成了 调试 Log 信息。可以看出,在代码 main.c 的 38 行出现了内存泄露问题。如下:

  • 相关阅读:
    【PADS封装】2.4G PCB天线封装(量产用)
    灵魂拷问:Mybatis中 Dao接口和XML文件的SQL如何建立关联?
    6.Flask-APScheduler定时任务框架
    CentOS7.9 下修改MariaDB访问端口不能访问
    数据的分类分级
    产品经理常用软件汇总
    C++编程基础
    抓包整理外篇fiddler————了解工具栏[一]
    [C#] 允许当前应用程序通过防火墙
    【Azure 应用服务】部署Kafka Trigger Function到Azure Function服务中,解决自定义域名解析难题
  • 原文地址:https://blog.csdn.net/wojiaxiaohuang2014/article/details/127755363