动态链接器(三) 动态链接的步骤和实现

来源:互联网 发布:知乎广告文案 编辑:程序博客网 时间:2024/05/21 05:58

大体步骤:动态链接器的自举(.dynamic段有关)装载共享对象(涉及全局符号表,符号优先级等) 重定位与初始化<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" />

1>gcc -Xlinker -rpath ./表示链接器在当前路径寻找共享对象

 

2>当共享库被装载到进程的地址空间,则同时它们中的符号都会被并入到全局符号表

 

3>完成自举以后,动态链接器可将可执行文件和链接器本身的符号都合并到一个符号表中,我们可以称它为全局符号表。

 

4>全局符号的介入:一个共享对象里面的全局符号被另一个共享对象的同名全局符号覆盖的现象又被称为全局符号的介入。

 

5>linux动态链接器这样处理:它定义了一个规则,那就是当一个符号需要被加入全局符号表时,如果相同的符号名已经存在,则加入的符号被忽略。(所以共享对象应该避免符号重名

 

6>stait func() 这种函数的写法是将函数编译成单元私有函数,确定不被其他的模块调用。即模块内部调用指令,无需处理.got.plt,可以加快调用速度。意味着不以跨模块模式产生代码?

 

7>linux在通过execve()系统调用被装载到进程的虚拟空间,将控制权交给动态链接器。对于静态链接程序的入口就是elf文件头里面的e_entry入口地址。对于动态链接来说,内核会分析动态链接器地址(在.interp段)。将动态链接器映射到进程地址空间,然后把控制权交给动态链接器。其实共享对象和可执行文件没有本质的区别,在windows里面也有一个叫做rundll32.exe工具可以直接.dll文件

 

8>linux的动态链接器是Glibc的一部分,它的源码位于Glibc的源代码的elf目录下面

关于动态链接器:

1>动态链接器本身应该是静态链接的,它本身不依赖任何共享对象

2>不一定必须是PIC,但是它是PIC的。带来很多好处

 

共享库组织

1>linux的共享库命名 libname.so.x.y.z  x主版本号, y次版本号 z发布版本号。

不同主版本号完全不兼容,改变了里面的借口。  此版本号增加新的接口,向下兼容。 发布版本号接口不变,仅是内部改动。

 

2>SO-NAME为名字建立软链接:使得所有依赖共享库的模块都是用SO-NAME,无需使用详细的版本号,提供了更新上的方便。

 

3>当共享库升级:如果没有进行主版本号升级,则直接用新版本的共享库替换掉旧版本,并修改SO-NAME软链接指向新版本; 但是如果进行了主版本号升级系统就会存在多个SO-NEME一个新一个旧的,这样也不会影响旧程序的运行

 

4>总之,SO-NAME表示一个库的接口,接口不向后兼容,SO-NAME就发生变化。

 

5>安装共享库后,linux中提供了ldconfig工具会搜索/lib /usr/lib所有共享库目录,然后更新所有的软链接。


原创粉丝点击