Liunx 静态库 ,动态库
概述
库文件一般就是编译好的二进制文件,用于在链接阶段同目标代码一起生成可执行文件,或者运行可执行文件的时候被加载,以便调用库文件中的某段代码。
它与可执行文件相比:
相同之处是:两者都是编译好的二进制文件(本节中我们讨论的二进制文件,假设都是 Linux 上面最常见的 ELF 格式);
不同的是:库文件无法直接执行(直观上来看它的源代码中没有 main 函数,而只是一些函数模块的定义和实现,没有运行的入口主函数,所以无法直接执行)。
静态库
静态函数库 :在程序执行前,就加入到目标程序中去。
优点 :运行快,发布程序无需提供静态库,已经存在 app 中 ,移植方便。
缺点 :大,将需要使用的库文件添加到 app 中。升级库时需要到源文件中修改。
动态库
动态函数库 :程序在执行时,动态(临时)由目标程序去调用。
优点 :
1. 小 , 链接时不复制,程序运行时动态加载到内存,供程序调用。系统只调用一次,多个程序可以公用,节省内存。
2. 程序升级简单,因为 app 里面没有库的源代码,升级之后的库的名字不变,函数名以及参数不变,只是实现做了优化,就能加载成功。
缺点:运行慢 ,发布时需提供依赖的动态库。
制作
1. 静态库(格式 .a )
- 准备 .c / .cpp 文件。
- 执行: gcc xxxx.c -c
- ar rcs libxxx.a xxx.o
2. 动态库 (格式.so)
- 准备 .c / .cpp 文件
- 执行 : gcc -shared -fpic xxx.c -o libxxx.so
3. -shared 指定生成动态库
4. -fpic 标准 ,选项用于编译阶段,在生成目标文件时就该使用,与生成位置无关的代码
使用
1. 静态库
只需要给用户提供 .h 文件和 .a 文件即可
- gcc main.c -lxxx -L ./path/ -o main
2. -lxxx 对.a文件掐头去尾,如 libmount.a -> lmount
3. -L 指定查找库文件【.a文件】路径 。 - ./main
2. 动态库
- gcc main.c -lxxx -L ./path/ -o main
2. -lxxx 对.a文件掐头去尾,如 libmount.a -> lmount
3. -L 指定查找库文件【.a文件】路径 。 - ./main 直接运行会出现
- error while loading shared libraries: libmount.so: cannot open shared object file: No such file or directory
- 解决方法
- 使用 export LD_LIBRARY_PATH= “库文件路径” 可以临时生效。
- 将上面语句编写 shell 脚本
- 可以在.bashrc或.profile等文件中永久设置LD_LIBRARY_PATH环境变量:
echo ‘export LD_LIBRARY_PATH=/usr/local/lib’ >> ~/.bashrc