【发布时间】:2013-07-27 17:16:20
【问题描述】:
据我所知,x86 汇编代码在很大程度上受到有限数量的寄存器的限制。
当我了解到在 Linux 上创建 .so 文件时,必须为 gcc 指定 -fPIC 命令行参数才能创建与位置无关的代码,我一开始简直不敢相信。
据我所知,elf 文件格式支持重定位,就像 - 在我看来要好得多 - Windows DLL 系统的工作原理:在 Windows 上,如果有必要,链接器会重定位 DLL 中的所有偏移量。
我认为加载 SO 文件或 DLL 文件所需的时间,以及用于保存不同重定位的 .so 文件的内存量并不像始终缺少整个寄存器那样糟糕它指向 GOT 并具有所有这些间接跳转。
我也完全不关心 ALSR 等。对于我所考虑的应用程序,我只关心在库中尽可能优化代码。
1) 为什么 Linux 不支持像 Windows 那样能够生成性能更高的代码的更多动态库加载?
到目前为止,我还没有找到真正的解释。像这样的事情,重新定位代码会非常糟糕和缓慢(当然,对于在台式机上加载文字处理器,加载速度有多快很重要,我完全接受这一点。但是对于计算密集型服务器进程(不处理来自互联网的恶意数据),我想拥有我能得到的所有性能和寄存器!
2) 我可以在 Linux 上创建 NOT -fPIC 编译的 SO 文件吗?我可以离开 -fPIC 吗?是否有任何关于此主题的操作指南、手册或项目,并且可以不浪费整个寄存器并仍然动态加载库?
如果我在编译 .so 文件时只删除 -fPIC 会发生什么?
【问题讨论】:
-
你更关心IA32还是x86-64?任何答案都取决于这种区别。
-
我关心的是32位代码并调整了问题的标题
-
对于计算密集型程序,确实值得(出于多种原因)切换到 64 位 linux。
标签: linux assembly dll dynamic-linking relocation