概述
(1) 标准头文件中函数的实现
Q: linux 下只找到c头文件,但没有找到具体的实现,编译的时候gcc是从哪里找具体的stdio.c和unistd.c等文件的?
平时写代码的时候直接include <xxx.h>,编译器从哪里去找相对应的xxx.c?
A: 头文件只是一句函数声明,实现的代码在标准库对应的.lib或者.so或者.dll,也就是静态或动态库文件里;
包含头文件用于编译,加上库用于链接。
实现已经编译进libc库里面了,glibc或者uclibc库。
一般可以在/lib或者/lib64下面找到libc.so.x
然后用readelf -s /lib64/libc.so.6 |grep " printf" 就可以发现这个库里面有这个编译好的函数了。链接时一般会链接到这一个printf函数上。
-------------
(2) linux 库文件(函数)的源码查看
-------------
(3) 查看 头文件搜索路径的方法
3.1)当前目录(仅双引号形式)
3.2)编译时指定的头文件目录(由gcc -I参数指定)
3.3)系统环境变量 CPLUS_INCLUDE_PATH(c++头文件)或 C_INCLUDE_PATH(c头文件)指定的目录
3.4)gcc默认目录:
/usr/include;/usr/local/include;/usr/lib/gcc/x86_64-linux-gnu/5/include(注:最后一个路径是gcc程序的库文件地址,各个用户的系统上可能不一样)
3.5)其他:
1》默认目录路径查看:
gcc的默认目录与安装gcc时指定的–prefix有关,该值可通过 gcc -v
查看;
另外 也可以通过 cpp -v 查看;
另外一种方法是用: strace 来跟踪系统调用access和open,看看是从哪里找的stdio.h和unistd.h;
比如:strace -f gcc 1.c 2>&1 | grep "stdio.h" (gcc 编译 1.c 时 的系统调用)
-------------
(4)库文件
头文件用于编译,库文件用于链接,编译通过了,还要链接通过。链接时库文件的查找顺序如下:
- 编译时指定的库文件目录(由
gcc -L
参数指定) - 环境变量
LIBRARY_PATH
指定的目录 - 系统默认目录:
/lib; /usr/lib; /usr/local/lib
一般用户安装的库会安装在/usr/local/lib,系统自带的库位于/lib; /usr/lib,用户自己编译的库可能就要使用-L参数指定了。
编译时通过了,还会有一个问题,就是运行动态库的使用。因为动态库是运行时加载的,所以还会有一个查找的顺序:
1> 编译时指定的动态库搜索路径(通过gcc 的参数"-Wl,-rpath,"指定。当指定多个动态库搜索路径时,路径之间用冒号:分隔)
2> 环境变量LD_LIBRARY_PATH指定的动态库搜索路径(路径之间用冒号:分隔)
3> 配置文件/etc/ld.so.conf中指定的动态库搜索路径
4> 默认的动态库搜索路径/lib:/usr/lib
特别注意,库文件的查找默认是不查找当前目录的,也就是说,即使使用的库位于同一个目录内,也需要指定才能指定。
-------------
(5) 编译常见的 缺少头文件错误:no such file
A: 解决方法:
5.1)安装相关的库或者包 / 软件包升级
头文件的默认搜索路径为(cpp -v 查看):/usr/include, /usr/local/include,
安装完后,再用 find / -type f -name "xxx" 搜索;
1》安装软件包: yum install -y xxx;
2》 软件包升级: yum update -y / apt-get update
5.2)从其他地方拷贝头文件到标准路径
find / -type f -name "xxx" 在本机搜索;
其他设备上存在,则从其他设备上拷贝;(最好从相同内核版本的设备上拷贝头文件)
网络上搜索下载;
注:某些 .h 文件可能是 ./configure 或者 其他编译过程中生成的;这样会直接搜索不到;
最后
以上就是苹果老师为你收集整理的linux C 头文件/库文件 FAQ的全部内容,希望文章能够帮你解决linux C 头文件/库文件 FAQ所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复