。目标文件的类型
。可重定位目标文件
在linux下,经过预编译,编译,汇编之后生成的.o文件就是可重定位目标文件。
汇编器把可重定位目标文件分成多个节,其中有一个名为symtab的节,存储模块中定义和引用的函数和全局变量的信息。它不包括局部变量信息(局部变量运行时在栈中被管理)。
。可执行目标文件
可重定位目标模块链接之后生成可以执行文件,它还包含了一些初始化代码和程序的入口点信息,以及运行时代码/数据段的存储器映射地址等信息。
。共享目标文件(静态 /动态链接库)
当程序所调用的函数或者引用的数据分布在多个不同的可重定位目标模块时,链接这个程序时需要多个命令行参数,如果把多个可重定位目标模块组成一个大的文件以减少输入的命令行参数那么就不得不把许多用不上的数据和代码链接到可执行文件中。静态链接库容纳多个可执行目标文件,每次链接器只把用到的目标模块提取出来嵌入到可执行文件中。它避免了上述的2个缺点。
当多个可执行文件使用同一个静态链接库里的可重定位目标模块时,每个可只执行文件都有一份相同的可重定位目标模块的拷贝。浪费了存储空间,动态链接库可以在执行文件载入内存中时或者运行时与可执行目标文件链接,而且即使多个可执行文件使用了同一份动态链接库,内存中也 只有一份它的拷贝。它克服了静态链接库的缺点。
。静态链接
链接器的任务是生成可执行文件时对目标模块进行符号解析和重定位。
。符号解析
连接器把每个引用与输入的可重定位目标模块内的定义唯一地联系起来。并确保每个本地静态(static属性)变量有唯一名字。
有定义的全局符号称为强符号,没定义的称为弱符号。
Unix处理多处定义符号规则:
1、不允许多个强符号
2、如果有一个强符号与若干个弱符号,选择强符号。
3、如果有多个弱符号,随机选择一个。
。输入目标模块时的顺序十分重要,是引起链接错误的 原因之一(书)。
。重定位
。重定位节和符号定义
这个步骤合并各个可重定位目标模块的相同的节,并把地址赋给这些新的合并的节,也赋给输入的 可重位块的节。也赋给模块内定义的符号。
。重定位节中的符号引用
这个步骤通过重定位表目(因为汇编器不知道模块会被安排在那个运行时存储器位置所以它把不明确地址的引用放在重定位表目通知连接器重定位时处理)确定引用的绝对/PC相关地址。
。动态链接
。动态链接可以在程序载入时发生也可以在程序运行时发生 。因为程序载入或者运行之前并不知道动态链接库会被放在存储器的什么地方,所以用PIC的方法来确定程序中引用的动态链接库符号定义的地址。