一、简单说明:
cleanup作为__attribute__属性中的一个可选属性值
其作用是当其声明的变量离开了其生命周期,那么
会自动调用你所指定的销毁函数
二、例子:
#include <stdio.h> #include <stdlib.h> #include <string.h> void destroy_string(char **str) { printf("final str : %s ", *str); free(*str); } int main(int argc, char **argv) { char *str __attribute__ ((__cleanup__(destroy_string))) = NULL; str = (char*)malloc((sizeof(char)) * 100); strcpy(str, "hello world!"); printf("current str : %s ", str); return 0; }
执行结果:
current str : hello world!
final str : hello world!
再通过
valgrind --tool=memcheck --leak-check=full 检测内存是否有泄漏
==6298== All heap blocks were freed -- no leaks are possible
可以看到内存是被正确释放了
三、原理:
其实这个释放代码的操作,是将人工编写的方式转交给了编译器实现。
可以通过gcc -S main.c查看
call printf movl $0, %ebx leaq -32(%rbp), %rax movq %rax, %rdi call destroy_string
其中在main函数里有一段这个函数,会发现在调用完printf函数后,会继续调用destroy_string这个销毁函数
但是这个销毁函数调用并不是我们代码明确编写的,因此这个是由编译器隐含添加的。