C 位置相关代码和位置无关代码之间的区别是什么?
位置相关代码和位置无关代码之间的区别是什么C 位置相关代码和位置无关代码之间的区别是什么?,c,C,位置相关代码和位置无关代码之间的区别是什么 还有,我们如何通过示例实现/调用我们自己的静态和动态库?在早期的计算机中,代码是位置相关的:每个程序都是为了加载到特定的地址并从该地址运行而构建的。为了同时使用不同的程序运行多个作业,操作员必须仔细安排作业,以便两个同时运行的作业不会运行需要相同加载地址的程序 例如,如果工资单程序和应收账款程序都构建为在地址32K处运行,则操作员不能同时运行这两个程序。有时,操作员会保留程序的多个版本,每个版本针对不同的加载地址构建,以扩展其选项 为了使事情更加灵活,
还有,我们如何通过示例实现/调用我们自己的静态和动态库?在早期的计算机中,代码是位置相关的:每个程序都是为了加载到特定的地址并从该地址运行而构建的。为了同时使用不同的程序运行多个作业,操作员必须仔细安排作业,以便两个同时运行的作业不会运行需要相同加载地址的程序 例如,如果工资单程序和应收账款程序都构建为在地址32K处运行,则操作员不能同时运行这两个程序。有时,操作员会保留程序的多个版本,每个版本针对不同的加载地址构建,以扩展其选项
为了使事情更加灵活,发明了位置无关的代码。与位置无关的代码可以从操作员选择加载它的任何地址运行。位置独立代码不仅用于协调用户级应用程序的工作,还用于操作系统内。位置独立代码可以在内存中加载的任何位置正确运行。这通常是通过对函数调用使用相对跳转来实现的,对于相对跳转,跳转地址是从代码流中的当前位置计算出来的,因此代码可能看起来像:“从当前位置跳转585字节”或“从该模块的基址跳转5745字节”,而不是“跳转到地址0x46fae55”。同样,对于引用内存地址的任何其他指令,必须相对于当前代码位置或运行时确定的基址进行写入
内存管理单元(MMU)和虚拟内存地址的使用使得位置无关代码几乎不再适用于可执行文件。但是,共享库必须作为位置独立的代码编写,因为它们可以映射到可执行文件地址空间中的任何位置。补充Lie Ryan的答案——这不是c编程语言的问题,而是系统架构的问题 例如,“英特尔x86分段体系结构”支持以.com格式半自动定位独立加载小型可执行文件,操作系统可将cs=ds=es=ss加载到2^16个不同的值 .exe格式OTOH引入了“重定位”,这意味着在可执行文件中有一个偏移数组(相对于二进制文件的加载地址),必须添加加载地址:例如
relocation_table: // list of values to be modified
0022, 0100, ...
.text
0020: xx yy 12 00 mov ax,[0x0012] <-- the "absolute address" 0012 is
// located at address 0022 in the binary -- that has to be added with the real
// location of the the "position-independent" code
relocation\u table://要修改的值列表
0022, 0100, ...
.文本
0020:xx yy 12 00 mov ax,[0x0012]很抱歉,您可以很容易地使用搜索引擎查找有关此的信息。请自己做研究。如果您有一个自己找不到答案的特定问题,请返回并发布在此处。还必须访问相对于代码位置的数据(例如相对于指令指针/程序计数器)。@Lie Ryan,但即使使用MMU,共享库仍然需要位置独立的代码,是吗?@fuzzxl:我已经澄清了最后一点paragraph@Lie«内存管理单元(MMU)和虚拟内存地址的使用使得位置无关代码对于可执行文件几乎过时»我不同意。PIE(位置独立可执行文件)是增强代码安全性的一种方法,因为注入的外壳代码可能对代码的位置做出更少的假设。现在并不是每个CPU都直接支持位置独立代码。