轻量级前端框架助力开发者提升项目效率与性能
922
2022-09-06
linux 静态库与共享库
本文笔记学习自《Professional Assembly Language》
静态库
当我们将不同的函数写在不同的文件中,如果主程序调用这些函数,就需要相应的目标文件才能生成可执行文件。目标文件很多的话,不便于管理。我们可以将目标文件整合到一个存档文件中,编译器从存档文件挑选出需要的目标文件,这样的存档文件称之为库文件(library file)。 假设库文件的目标代码被编译到了主程序中,就称之为静态库文件(windows下对应着LIB文件)。 linux下有ar工具可以创建静态库文件。
ar - create, modify, and extract from archivesar [--plugin name] [-X32_64] [-]p[mod [relpos] [count]] archive [member...]
以计算圆的面积areafunc.s进行说明。 areafunc.s:
.section .text.type areafunc,@function.globl areafuncareafunc:pushl %ebp movl %esp,%ebp #store esp registerfldpi #store PI at st(0)filds 8(%ebp) #store first parameter at st(0) and PI moved to st(1) fmul %st(0),%st(0) fmul %st(1),%st(0) #make sure st(0) has current anwser.movl %ebp,%esppopl %ebp
areafunc.c:
#include
生成目标文件 gcc -c areafunc.s -o areafunc.o linux操作系统下的静态库文件通常命名为libx.a,x是自己的文件命名,.a表示这是一个静态库文件。 使用ar生成库文件liball.a: 下面我用所有的.o文件生成一个库文件。
[edemon@CentOS workspace]$ ls *.oareafunc.o area.o ftest.o movl.o mov.o quadtest.o[edemon@CentOS workspace]$ ar -r liball.a *.oar: creating liball.a[edemon@CentOS workspace]$ file liball.aliball.a: current ar archive[edemon@CentOS workspace]$ ar -t liball.a areafunc.oarea.oftest.omovl.omov.oquadtest.o
创建索引提高连接速度: ranlib liball.a 再介绍一个工具nm
nm - list symbols from object filesnm [-a|--debug-syms] [-g|--extern-only][--plugin name] [-B] [-C|--demangle[=style]] [-D|--dynamic] [-S|--print-size] [-s|--print-armap] [-A|-o|--print-file-name][--special-syms] [-n|-v|--numeric-sort] [-p|--no-sort] [-r|--reverse-sort] [--size-sort] [-u|--undefined-only] [-t radix|--radix=radix] [-P|--portability] [--target=bfdname] [-fformat|--format=format] [--defined-only] [-l|--line-numbers] [--no-demangle] [-V|--version] [-X 32_64] [--help] [objfile...]
可查看函数所在文件位置
[edemon@CentOS workspace]$ nm -s liball.a Archive index:areafunc in areafunc.oarea in area.omain in ftest.o_start in movl.o_start in mov.o_start in quadtest.oareafunc.o:00000000 T areafuncarea.o:00000000 T areaftest.o: U area00000000 T main00000000 d precision00000002 d reportmovl.o:00000000 T _start00000000 d valuemov.o:00000000 T _startquadtest.o:00000000 T _start00000000 d data100000014
使用静态库进行编译:
[edemon@CentOS workspace]$ gcc areafunc.c liball.a -o areafunc[edemon@CentOS workspace]$ ./areafunc result is 3.141593result is 314.159271
因为gcc是提取所需函数代码得到可执行文件,所以areafunc的大小并不会因为使用库文件编译而变大。
[edemon@CentOS workspace]$ gcc areafunc.c areafunc.o -o areafunc1[edemon@CentOS workspace]$ du -h areafunc areafunc18.0K areafunc8.0K areafunc1
共享库
和静态库文件不同,有一类存档文件的目标代码不被编译到可执行文件中,主程序不用把函数代码加入它的内存空间,这类存档文件称之为共享库文件。 Linux操作系统的命名格式为libx.so,其中x是自己的文件命名,.so表明这是共享库(windows下对应着DLL文件)。 静态编译(将函数代码连接到可执行文件)得到的可执行文件,我们使用objdump进行反汇编,可以查看函数调用的痕迹。 以areafunc为例:
[edemon@CentOS workspace]$ objdump -D areafunc > read[edemon@CentOS workspace]$ vim read#查找含有areafunc的地方:/areafunc345 8048432: e8 65 00 00 00 call 804849c
以共享库编译方式得到的可执行文件是不含有函数代码的。 共享库编译方式shell> gcc sourcefile -Ldir -llibname -o executefile -L 告诉编译器库文件在哪个位置(假设不在系统定义的位置) -l 后跟上库的名字(x) 生成共享库文件:
[edemon@CentOS workspace]$ gcc -shared -o libshared.so areafunc.o area.o ftest.o[edemon@CentOS workspace]$ file libshared.so libshared.so: ELF 32-bit LSB shared object, Intel 80386, version 1
生成可执行文件:
[edemon@CentOS workspace]$ gcc -o areafunc2 -L. -lshared areafunc.c[edemon@CentOS workspace]$ ./areafunc2result is 3.141593result is 314.159271
再次反汇编,查找函数areafunc的踪迹:
[edemon@CentOS workspace]$ objdump -D areafunc2 > read[edemon@CentOS workspace]$ vim read361 08048440
可以发现,函数的代码并没有在这份反汇编后的文件中。 ldd可查看依赖的共享库:
[edemon@CentOS workspace]$ ldd areafunc2 linux-gate.so.1 => (0x00bb1000) libshared.so (0x00395000) libc.so.6 => /lib/libc.so.6 (0x00397000) /lib/ld-linux.so.2 (0x001ee000)
可执行文件需要Linux动态加载器(/lib/ld-linux.so.2)自动加载所需的函数。 假设动态加载器找不到库文件的位置,怎么办? 系统文件/etc/ld.so.conf含有定位共享库文件位置的信息,我们改变它(增添位置信息),再使用ldconfig更新。还有一种添加库文件位置信息的方法,就是更改LD_LIBRARY_PATH变量,例如:
[edemon@CentOS workspace]$ echo $LD_LIBRARY_PATH /home/edemon/workspace/[edemon@CentOS workspace]$ export LD_LIBRARY_PATH="$LD_LIBRARY_PATH:/home/edemon/"[edemon@CentOS workspace]$ echo $LD_LIBRARY_PATH /home/edemon/workspace/:/home/edemon/
版权声明:本文内容由网络用户投稿,版权归原作者所有,本站不拥有其著作权,亦不承担相应法律责任。如果您发现本站中有涉嫌抄袭或描述失实的内容,请联系我们jiasou666@gmail.com 处理,核实后本网站将在24小时内删除侵权内容。
发表评论
暂时没有评论,来抢沙发吧~