美文网首页GNU C LIB
mallochook内存分配回调(glibc-3-内存)

mallochook内存分配回调(glibc-3-内存)

作者: YBHello | 来源:发表于2018-04-29 08:38 被阅读0次

概述:glibc提供的mallochook机制是通过重新指定内存管理的回调函数指针来实现自定义的内存管理方式。

1. 原型

       #include <malloc.h>

       void *(*__malloc_hook)(size_t size, const void *caller);

       void *(*__realloc_hook)(void *ptr, size_t size, const void *caller);

       void *(*__memalign_hook)(size_t alignment, size_t size,
                                const void *caller);

       void (*__free_hook)(void *ptr, const void *caller);

       void (*__malloc_initialize_hook)(void);

       void (*__after_morecore_hook)(void);

将这些函数地址指向自定义的函数,在调用对应的malloc等函数的时候,将会被自动调用到自定义的函数。

2. 范例

#include <stdio.h>
#include <stdlib.h>
#include <assert.h>
#include <malloc.h>

typedef void *(*malloc_hook_fun_t)(size_t size, const void *caller);
typedef void  (*free_hook_fun_t)(void *ptr, const void *caller);

void replace_hook(void);
void restore_hook(void);

malloc_hook_fun_t old_malloc_hook = NULL;
free_hook_fun_t old_free_hook = NULL;

int replaced = 0;

void *my_malloc_fun(size_t size, const void *caller)
{

        restore_hook();

        void *ret = malloc(size);

        printf("+%p:[%p]\n", caller - 1, ret);

        replace_hook();


        return ret;
}

void my_free_fun(void *ptr, const void *caller)
{
        restore_hook();

        printf("-%p:[%p]\n", caller - 1, ptr);

        free(ptr);

        replace_hook();
}

void replace_hook(void)
{
        assert(!replaced);
        replaced = 1;

        old_malloc_hook = __malloc_hook;
        old_free_hook = __free_hook;

        __malloc_hook = my_malloc_fun;
        __free_hook = my_free_fun;

}

void restore_hook(void)
{
        assert(replaced);
        replaced = 0;
        __malloc_hook = old_malloc_hook;
        __free_hook = old_free_hook;
}

int main(int argc, char **argv)
{
        replace_hook();

        char *p = malloc(100);

        free(p);

        restore_hook();

        return 0;
}
  1. 定义old_malloc_hookold_free_hook用来保存库自带的内存分配函数。当进行实际内存管理时,恢复回来进行实际的内存分配和释放;
  2. 定义replace_hookrestore_hook函数,方便进行回调函数的替换和恢复;
  3. 定义my_malloc_funmy_free_fun来替换自带的内存分配、释放函数,用于自定义的内存记录、追踪。

3. 编译

$ gcc malloc_hook.c -g

  1. 编译会有告警,告警信息是:不建议使用这些回调函数。对于单线程使用替换回调,是一种可行的方式,对于多线程的话,就会导致竞争,不适合使用回调函数。如果说是要进行内存泄漏扫描,可以考虑使用一个叫做valgrind的工具。
  2. 使用-g参数是为了后续将输出的转换为代码行号。

4. 运行结果

  1. 执行结果
$ ./a.out
+0x400808:[0x1c19010]
-0x400818:[0x1c19010]
  1. 地址转换结果
$ addr2line -f -e a.out -a 0x400808
0x0000000000400808
main
/home/centos/gnuc/c3/jianshu_malloc_hook.c:68

$ addr2line -f -e a.out -a 0x400818
0x0000000000400818
main
/home/centos/gnuc/c3/jianshu_malloc_hook.c:70

通过执行输出打印的调用地址,然后将地址转换层代码位置,这就和之前的 mtrace 的功能类似了。

5. 结论

  1. malloc_hook回调机制适用于单线程,可以通过重新定义内存处理函数来进行内存的记录、追踪和管理等功能。
  2. 对于多线程,malloc_hook机制会出现竞争,不建议使用。如果是调试阶段,可以考虑使用valgrind来进行内存追踪。

相关文章

  • mallochook内存分配回调(glibc-3-内存)

    概述:glibc提供的mallochook机制是通过重新指定内存管理的回调函数指针来实现自定义的内存管理方式。 1...

  • JVM(6)性能调优

    1、内存分配相关调优 1.1、最大与最小堆内存设置 Java 应用程序在运行时,首先会被分配 -Xms 指定的内存...

  • Java知识图谱

    Java基础 JVM JVM内存模型和结构 GC原理&内存分配策略 性能调优:Thread Dump class ...

  • java的垃圾回收#垃圾回收算法

    java之所以能够实现自动内存分配,是因为jvm帮我们完成了两件事 帮助对象分配内存 帮助回收分配给对象的内存 回...

  • Android性能调优篇之内存泄露

    开篇废话 通过我之前的两篇文章 Android性能调优篇之探索JVM内存分配 Android性能调优篇之探索垃圾回...

  • Java中四种引用

    Java内存管理包括内存分配和内存回收。 内存分配:程序员通过new对象,JVM会自动为该对象分配内存。 内存回收...

  • Java编程语言:java中四种引用!欢迎补充

    Java内存管理包括内存分配和内存回收。 内存分配:程序员通过new对象,JVM会自动为该对象分配内存。 内存回收...

  • javascript内存管理

    内存声明周期 分配你所需要的内存 使用分配的内存(读写) 不再需要时释放内存 内存分配 javascript在声明...

  • (二)C语言之动态内存分配

    (二)C语言之动态内存分配 一、静态内存分配 定义是指定分配的内存长度就是静态内存分配,是在栈内存中分配 二、C语...

  • 《C语言》malloc函数使用

    动态分配、静态分配 静态分配:计算机随机自动分配内存,周期结束后自动释放内存动态分配:手动分配内存,手动释放内存 ...

网友评论

    本文标题:mallochook内存分配回调(glibc-3-内存)

    本文链接:https://www.haomeiwen.com/subject/qjkolftx.html