这里笔记一个非常简单的例子来介绍下如何在linux下编译和使用动态库。
首先建立3个文件:【 functions.c functions.h hellofunc.c 】,内容如下:
CONTENTS
functions.h:
#ifndef FUNCTIONS_H_ #define FUNCTIONS_H_ int add(int a, int b); #endif /* FUNCTIONS_H_ */
functions.c:
#include "functions.h" int add(int a, int b) { return a+b; }
hellofunc.c:
#include <stdio.h> #include "functions.h" int main(void) { int a = 10; int b = 20; int c = add(a,b); printf("%d add %d is %d\n", a,b,c); return 0; }
动态库:
这里我们将functions.c编译成动态库,输入命令:
$ gcc functions.c -fPIC -shared -o libfunc.so
然后我们编译hellofunc.c,并且链接刚刚编译好的动态库,输入命令:
$ gcc hellofunc.c -L. -lfunc -o hellofunc
成功后,我们用ldd看下:
$ ldd hellofunc linux-vdso.so.1 => (0x00007ffc8de96000) libfunc.so => not found libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f119dea8000) /lib64/ld-linux-x86-64.so.2 (0x00007f119e28d000)
可以发现这里动态库没有找到,有两种方式可以解决:
第一种是用root权限把刚刚编译好的linfunc.so拷贝到/usr/lib目录下,然后执行ldconfig,这样的效果是永久的。
第二种是修改下LD_LIBRARY_PATH变量,这种方式不需要root权限,而且效果时临时的。
我们这里使用第二种方式,输入命令,将本地路径添加到LD_LIBRARY_PATH中:
$ export LD_LIBRARY_PATH=.:$LD_LIBRARY_PATH
再次执行ldd,就可以发现动态库已经找到了。
cstriker1407@cstriker1407-x64:~/projects/HelloSo/src$ ldd hellofunc linux-vdso.so.1 => (0x00007ffd893cc000) libfunc.so => ./libfunc.so (0x00007f380ef98000) libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f380ebb5000) /lib64/ld-linux-x86-64.so.2 (0x00007f380f19c000) cstriker1407@cstriker1407-x64:~/projects/HelloSo/src$ ./hellofunc 10 add 20 is 30
静态库:
编译出一个.o文件并将其打包成静态库:
$ gcc -c functions.c $ ar -rcs libfunc.a functions.o $ ls functions.c functions.h functions.o hellofunc.c libfunc.a
用静态库链接:
$ gcc hellofunc.c -L. -lfunc -static -o hellofunc2
对比下文件大小并执行:
$ du -chs hellofunc* 12K hellofunc 860K hellofunc2 4.0K hellofunc.c 876K 总用量 $ ./hellofunc2 10 add 20 is 30
发表评论