__attribute__((cleanup))
__attribute__((cleanup)) 是 GCC 和 Clang 提供的一个扩展属性,用于在变量超出作用域时自动调用指定的清理函数。它可以简化资源管理,使得在作用域结束时自动释放资源。使用这个属性时,编译器会在生成代码时将清理函数插入到变量作用域的结尾处,从而确保该清理操作会在作用域结束时执行,类似于 C++ 中的析构函数功能。
基本用法
#include <stdio.h>
void cleanup_int(void *p) {
int *i = (int *)p;
printf("Cleaning up: %d\n", *i);
}
int main() {
__attribute__((cleanup(cleanup_int))) int x = 10;
printf("Value of x: %d\n", x);
return 0;
}Value of x: 10
Cleaning up: 10在这个示例中,变量 x 在声明时加上了 __attribute__((cleanup(cleanup_int))),因此在 main 函数返回前,编译器会自动插入对 cleanup_int 函数的调用,并将 x 的地址传递给它,从而实现自动清理。
编译器的处理方式
插入清理代码:编译器会在变量的作用域结束处插入清理函数的调用。即使作用域中包含多条返回路径(如在
if或switch语句中提前退出),编译器也会在每条路径上都插入清理函数调用。传递指针:清理函数会接受指向变量的指针,这样就能在清理函数中对变量的内容进行访问和处理。
作用范围:
__attribute__((cleanup))只能用于具有自动存储类型的局部变量,即无法用于全局变量或静态局部变量,因为这些变量的生命周期不受作用域控制。
使用场景
这个属性特别适合用于在 C 中实现 RAII(资源获取即初始化)模式。例如,自动释放内存、文件句柄或锁,避免手动清理的繁琐,减少资源泄漏的风险。
注意事项
清理函数应考虑指针为
NULL的情况。该特性是编译器的扩展,因此不是标准 C 的一部分,使用时需要确保编译器的兼容性。
Last updated