1. GCC的__attribute__((constructor))是什么?
如果你写过C/C++程序,可能遇到过这样的需求:在main函数执行前自动完成某些初始化工作。比如初始化全局变量、建立数据库连接或者注册信号处理器。这时候,GCC提供的__attribute__((constructor))特性就能派上用场了。
简单来说,这是一个GCC扩展语法(不是标准C++的一部分),它允许你标记一个函数,让这个函数在main()执行前自动调用。想象一下,这就像给你的程序装了个自动启动装置,不需要你手动触发就能在后台默默完成准备工作。
我第一次接触这个特性是在开发一个网络服务时。当时需要在程序启动时加载配置文件,如果放在main()里处理,代码会显得很臃肿。用了__attribute__((constructor))后,初始化代码变得干净利落,main()函数只需要关注核心逻辑就行。
2. 基础用法与工作原理
2.1 基本语法
使用这个特性非常简单,只需要在函数声明后加上__attribute__((constructor))即可:
void my_init() __attribute__((constructor));
void my_init() {
printf("这个函数会在main()之前执行\n");
}
你也可以直接在函数定义处添加属性:
void __attribute__((constructor)) my_init() {
printf("这个函数会在main()之前执行\n");
}
2.2 底层实现机制
你可能好奇这个魔法是怎么实现的。在Linux/ELF系统上,GCC会把这些构造函数放到特殊的ELF段中(通常是.ctors或.init_array段)。当程序启动时,动态链接器会扫描这些段并按顺序调用其中的函数。
我曾在调试一个复杂项目时用objdump查看过生成的二进制文件,确实能看到这些特殊段:
objdump -s -j .init_array my_program
输出会显示所有构造函数指针的列表。这种实现方式保证了构造函数能在main()前执行,而且不依赖任何运行时库的特殊处理。
2.3 执行顺序控制
当你有多个构造函数时,它们的执行顺序很重要。GCC允许你通过指定优先级来控制顺序:
void __attribute__((constructor(101))) init_first() {
printf("这个会先执行\n");
}
void __attribute__((constructor(1


4173

被折叠的 条评论
为什么被折叠?



