Glibc中__errno_location两个定义的差异及errno宏调用时机咨询
Glibc中
__errno_location两个定义的差异及调用逻辑 两个定义的核心差异
- 所属组件不同:一个是位于
csu/errno-loc.c的libc.a静态库版本,另一个是位于nptl/errno-loc.c的libpthread.a静态库版本。 - 关联的线程局部变量不同:前者返回线程局部变量
__libc_errno的地址,后者返回线程局部变量errno的地址。 - 设计场景不同:
libc.a里的版本是为单线程程序提供的基础实现,libpthread.a里的版本则是适配多线程环境的专用实现——两者本质都是通过线程局部存储(TLS)保证每个线程拥有独立的errno值,避免多线程间的干扰,只是所属功能组件和变量命名有区别。
errno宏展开时的调用逻辑
- 完全由程序是否链接线程库决定:
- 如果程序未链接
libpthread(单线程程序),链接器会从libc.a中选取__errno_location的实现。 - 如果程序链接了
libpthread(哪怕实际未创建线程),链接器会优先使用libpthread.a中的版本——静态库链接时,后指定的库或满足依赖的库中的符号会被优先选用,libpthread提供的该符号会覆盖libc中的版本。
- 如果程序未链接
- 动态链接场景下:当程序加载
libpthread.so时,会自动替换__errno_location的实现,确保多线程环境下errno的线程安全性。
内容的提问来源于stack exchange,提问作者brian
相关产品推荐
相关产品推荐

