linux下动态库与静态库的生成与使用

linux下动态库与静态库的生成与使用

定义

静态与动态的区分主要是在编译系统中的链接部分

  • 静态库在程序链接的时候会自动的链接到程序里,所以一旦编译完成,静态库就不需要了,静态库以.a结尾。
  • 动态库在编译时不会被连接到目标代码中,而是在程序运行时才被载入,动态库以.so结尾。

静态库相对于动态库来说更高的效率,但是消耗更多的空间。

生成

//hello.h
#ifndef _HELLO_H
#define _HELLO_H
void hello(const char* str);
#endif

//hello.c
#include <stdio.h>  
void hello(const char* name){  
    printf("hello %s! \n",name);  
}

//main.c
#include "hello.h"  
int main(){  
	hello("everyone");  
	return 0;  
} 

静态库

  • 生成静态库,将hello.c编译成hello.o文件,然后利用ar工具将hello.o文件打包成.a文件。注意的是静态库命名规范为lib[library_name].a。

    gcc - c hello.c
    ar crv libhello.a hello.o
    
  • 使用静态库,需要用-L参数指定静态库位置(不在默认文件夹时),-l参数指定静态库名(不加lib前缀和.a后缀)

    gcc -o hello main.c -L. -lhello
    

动态库

  • 生成动态库有两种方法,第一种,将hello.c编译成hello.o文件(动态库需加参数-fPIC,目的是为在多个程序间共享),然后生成动态库。第二种,将上述步骤合并为一条指令。

    //第一种
    gcc -fPIC hello.c
    gcc -shared -o libhello.so hello.o
    //第二种
    gcc -shared -fPIC -o libhello.so hello.c
    
  • 动态库的使用与静态库一致

    gcc -o hello main.c -L. -lhello
    

    PS:如果出现动态库或静态库无法找到的错误,可将其移至默认搜索目录下,/usr/lib或/lib, 并更新 ldconfig

动态库的使用

  • 编译时,库路径

    • 使用绝对路径或相对路径:gcc -o out test.c /home/libdy.so

    • 链接器在标准搜索路径寻找动态库,可通过选项-print-search-dirs查看

    • 使用-llibrary链接名为library的动态库时,除在标准搜索路径中查找,还会在选项-Ldir指定路径dir中查找

  • 动态加载时,库路径

    • 编译时使用的绝对路径或相对路径,可通过readelf -d ELF查看,或通过ldd ELF查看所依赖的库及路径
    • 编译时使用参数**-Wl,-rpath=dir**指定搜索路径,可通过readelf -d ELF查看
    • 环境变量 LD_LIBRARY_PATH 指定的动态库搜索路径
    • 配置文件 /etc/ld.so.conf 中指定的动态库搜索路径
    • 标准搜索路径

遇到的问题

Q:换了系统后,之前能链接的程序,现在链接报“未定义的引用”,但ldconfig -p能找到动态库,且链接时也指定了动态库

A:不同gcc版本对链接的过程有所不同,低版本中动态库可放置在可重定向文件之前,而高版本必须将动态库放置在可重定向文件之后。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值