GNU C中主线程是否调用构造函数?实测结果合规性求证
动态库构造函数的线程ID与main线程一致是GNU C的正常特性吗?
这完全是GNU C和动态链接机制下的正常行为,原因很直接:
- 动态库中被
__attribute__((constructor))标记的函数,会在动态库被加载时执行。 - 像你代码里的场景,main.c编译时直接链接了libhello.so,这种情况下动态库会在程序启动阶段、main函数执行前(或执行初期)由程序的主线程(也就是main线程)负责加载,构造函数自然就在main线程中运行,线程ID和main线程完全一致是必然结果。
哪怕后续在子线程里调用动态库的hello()函数,构造函数也不会再次执行——它只会在加载时运行一次,而且是在触发加载操作的那个线程里执行。
补充一个对比场景:如果改成在子线程里手动调用dlopen("libhello.so", RTLD_NOW)加载动态库,那构造函数就会在调用dlopen的子线程中执行,此时输出的线程ID就会和子线程一致。
你的代码参考
hello.c
#include <stdint.h> #include <pthread.h> #include <stdio.h> void __attribute__((constructor)) func(void) { uint64_t thread_id = pthread_self(); printf("in constructor, thread id: %lu\n", thread_id); return; } void hello(void) { printf("hello\n"); return; }
main.c
#include <stdio.h> #include <stdlib.h> #include <stdint.h> #include <pthread.h> #include <hello.h> void *start_routine(void *arg) { hello(); return NULL; } int main(void) { uint64_t thread_id = pthread_self(); printf("in main function, thread id: %lu\n", thread_id); uint64_t new_thread_id; pthread_create(&new_thread_id, NULL, start_routine, NULL); pthread_join(new_thread_id, NULL); return 0; }
内容的提问来源于stack exchange,提问作者hyunseo welcome
相关产品推荐
相关产品推荐

