编译生成动态库、链接动态库生成可执行文件

折腾了一天编译、动态库的问题,整理一下(参考:https://blog.csdn.net/flyztek/article/details/73612469):

现有4个文件:

app.cc--应用程序

head.h--库头文件

source1.cc--库源文件1

source2.cc--库源文件2

其中,app.cc里包含了库的头文件,并用到了库里的方法:

// app.cc

#include "stdio.h"
#include "stdlib.h"

#include "head.h"

int main()
{
    source1();
    source2();
    return 0;
}

库头文件head.h里是库源文件1 source1.cc、库源文件2 source2.cc里方法的声明:

// head.h

void source1();
void source2();

库源文件1 source1.cc里定义了source1()函数:

// source1.cc

#include "stdio.h"
#include "stdlib.h"

#include "head.h"

void source1()
{
    printf("source1\n");
}

 库源文件1 source1.cc里定义了source1()函数:

// source2.cc

#include "stdio.h"
#include "stdlib.h"

#include "head.h"

void source2()
{
    printf("source2\n");
}

 

然后,重点来了!

想要应用程序正确执行,有三种方法:

一、直接编译3个源文件app.cc、source1.cc、source2.cc生成一个目标程序文件app

gcc app.cc source1.cc source2.cc -o app

然后执行app,可以正确执行

zhan@virtualBox:~/home/test_lib$ ./app 
source1
source2

二、编译库的2个源文件source1.cc、source2.cc为两个目标文件source1.o,source2.o:

zhan@virtualBox:~/home/test_lib$ gcc source1.cc -c
zhan@virtualBox:~/home/test_lib$ ls
app.cc  head.h  source1.cc  source1.o  source2.cc
zhan@virtualBox:~/home/test_lib$ gcc source2.cc -c
zhan@virtualBox:~/home/test_lib$ ls
app.cc  head.h  source1.cc  source1.o  source2.cc  source2.o

然后用ar命令将source1.o、source2.o创建成静态库文件,这里有两种方案:

1、第一种是分别创建两个静态库文件 libsource1.a、libsource2.a,

zhan@virtualBox:~/home/test_lib$ ar -cr libsource1.a source1.o
zhan@virtualBox:~/home/test_lib$ ar -cr libsource2.a source2.o
zhan@virtualBox:~/home/test_lib$ ls
app.cc  libsource1.a  source1.cc  source2.cc
head.h  libsource2.a  source1.o   source2.o

 然后链接两个静态库编译成应用app:

zhan@virtualBox:~/home/test_lib$ gcc app.cc -L. -lsource1 -lsource2 -o app
zhan@virtualBox:~/home/test_lib$ ls
app     head.h        libsource2.a  source1.o   source2.o
app.cc  libsource1.a  source1.cc    source2.cc
zhan@virtualBox:~/home/test_lib$ ./app
source1
source2

2、第二种是将两个目标文件source1.o,source2.o合并创建成一个静态库文件 libsource.a:

zhan@virtualBox:~/home/test_lib$ ar -cr libsource.a source1.o source2.o
zhan@virtualBox:~/home/test_lib$ ls
app.cc  head.h  libsource.a  source1.cc  source1.o  source2.cc  source2.o
zhan@virtualBox:~/home/test_lib$ gcc app.cc -L. -lsource -o app
zhan@virtualBox:~/home/test_lib$ ./app
source1
source2

三、编译库的2个源文件source1.cc、source2.cc为一个动态库文件source.so:

zhan@virtualBox:~/home/test_lib$ gcc source1.cc source2.cc -fPIC -shared -o libsource.so
zhan@virtualBox:~/home/test_lib$ ls
app.cc  head.h  libsource.so  source1.cc  source2.cc

然后生成app,生成时链接库文件:

zhan@virtualBox:~/home/test_lib$ gcc app.cc -L. -lsource -o app
zhan@virtualBox:~/home/test_lib$ ls
app  app.cc  head.h  libsource.so  source1.cc  source2.cc

执行生成的应用app:

zhan@virtualBox:~/home/test_lib$ ./app 
./app: error while loading shared libraries: libsource.so: cannot open shared object file: No such file or directory

此时却报错了,ldd命令查看app应用的库链接情况:

zhan@virtualBox:~/home/test_lib$ ldd app
	linux-vdso.so.1 =>  (0x00007ffd54b8a000)
	libsource.so => not found
	libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007fbe0a005000)
	/lib64/ld-linux-x86-64.so.2 (0x0000557f1caba000)

发现找不到库文件,此时有多种解决方案:

1、将刚刚生成的libsource.so库复制到/usr/lib目录里,然后执行ldconfig命令,再运行程序app就可以了:

zhan@virtualBox:~/home/test_lib$ sudo cp libsource.so  /usr/lib
zhan@virtualBox:~/home/test_lib$ ldd app	
    linux-vdso.so.1 =>  (0x00007ffc7c100000)
	libsource.so => /usr/lib/libsource.so (0x00007fc1f5106000)
	libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007fc1f4d3d000)
	/lib64/ld-linux-x86-64.so.2 (0x000055e2451c0000)
zhan@virtualBox:~/home/test_lib$ ./app 
source1
source2

2、将libsource.so库文件所在目录添加到/etc/ld.so.conf文件中:

zhan@virtualBox:~/home/test_lib$ sudo vim /etc/ld.so.conf
include /etc/ld.so.conf.d/*.conf
/home/test_lib
zhan@virtualBox:~/home/test_lib$ sudo ldconfig
zhan@virtualBox:~/home/test_lib$ ldd app
	linux-vdso.so.1 =>  (0x00007fffa93dc000)
	libsource.so => /home/test_lib/libsource.so (0x00007fada87ab000)
	libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007fada83c9000)
	/lib64/ld-linux-x86-64.so.2 (0x00005643a0cbf000)
zhan@virtualBox:~/home/test_lib$ ./app 
source1
source2

3、用export命令export一个指向libsource.so库文件所在目录的全局变量LD_LIBRARY_PATH, 然后运行程序的时候就会去这个目录中找共享库. (建议该方法只用于临时调试

zhan@virtualBox:~/home/test_lib$ export LD_LIBRARY_PATH=/home/test_lib:$LD_LIBRARY_PATH

zhan@virtualBox:~/home/test_lib$ ldd app
	linux-vdso.so.1 =>  (0x00007fffa93dc000)
	libsource.so => /home/test_lib/libsource.so (0x00007fada87ab000)
	libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007fada83c9000)
	/lib64/ld-linux-x86-64.so.2 (0x00005643a0cbf000)
zhan@virtualBox:~/home/test_lib$ ./app 
source1
source2

PS:

 也可以将二中的两个目标文件source1.o,source2.o合成为动态库文件libsource.so

zhan@virtualBox:~/home/test_lib$ ar -rc -o libsource.so source1.o source2.o
zhan@virtualBox:~/home/test_lib$ ls
app.cc  head.h  libsource.so  source1.cc  source1.o  source2.cc  source2.o
zhan@virtualBox:~/home/test_lib$ gcc app.cc -L. -lsource -o app
zhan@virtualBox:~/home/test_lib$ ldd app
	linux-vdso.so.1 =>  (0x00007ffcc5c9a000)
	libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f926e42b000)
	/lib64/ld-linux-x86-64.so.2 (0x0000560f56a62000)
zhan@virtualBox:~/home/test_lib$ ./app 
source1
source2

 

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值