如何让GCC将所有符号导出到输出文件

如何让GCC将所有符号导出到输出文件,c,gcc,elf,relocation,C,Gcc,Elf,Relocation,我正在开发一个操作系统,在设置分页之前,我需要加载一些模块。因此,由于此时未设置分页,我需要将程序中的所有符号重新定位到该物理地址。我的问题是,不是所有的符号都可以在符号表中找到,也不是所有的重新定位信息都可以在rel.text中找到。如何让GCC导出所有符号数据?实际上,您的问题是关于链接器的。答案取决于你使用的链接器 如果它是gcc下的标准链接器ld,请尝试“-Wl,-r”选项。当然,需要重新定位的任何内容都将在重新定位表中。不然怎么装呢?无论是否启用分页,重新定位的工作原理都是完全相同的—

我正在开发一个操作系统,在设置分页之前,我需要加载一些模块。因此,由于此时未设置分页,我需要将程序中的所有符号重新定位到该物理地址。我的问题是,不是所有的符号都可以在符号表中找到,也不是所有的重新定位信息都可以在rel.text中找到。如何让GCC导出所有符号数据?

实际上,您的问题是关于链接器的。答案取决于你使用的链接器


如果它是gcc下的标准链接器
ld
,请尝试“-Wl,-r”选项。

当然,需要重新定位的任何内容都将在重新定位表中。不然怎么装呢?无论是否启用分页,重新定位的工作原理都是完全相同的——二进制文件中的绝对位置条目都会列出一个偏移量,然后由加载软件进行处理。没有搬迁,其他一切都应该很好

请注意,符号表本身对于解析重定位没有意义,因为它只给出符号的位置

您是否在思考操作系统本身中的符号?如果是这样的话,那么就需要以适当的方式从操作系统中导出符号。Linux有EXPORT_SYMBOL(name),它在内核内部构建一个符号表。[请注意,这不是由
gcc
ld
生成的符号,而是由宏构建并在内核中处理的符号

编辑以澄清,因为我在“评论”中空间不足:
有两种类型的“重定位”:内部重定位——您对自己模块中的内容有绝对引用,例如指向字符串的指针、指向函数的指针、用于switch语句的跳转表等等——这些应该只是一个将当前值与二进制实际位置的偏移量相加的问题(当然是虚拟地址)。另一个是“外部引用”,例如当您的模块调用时,比如说
spinlock()
-这不是在模块内部实现的,因此它将有一个“外部引用”。在这种情况下,将有一个带有“spinlock”的重定位条目作为对spinlock的调用在模块中的位置的名称和偏移量。现在您显然需要一个符号表来查找内核中“spinlock”的位置[如果您想变得非常复杂,请允许moduels引用其他模块,但我会先让一个模块加载OK!].

重新定位表必须包含足够的信息,以便将可执行文件重新定位到任意位置。这些信息不需要覆盖所有符号。例如,您的局部变量没有重新定位。您是否尝试使用-fPIC编译与位置无关的代码?我有点困惑,因为我认为符号索引存储在r中eloc_信息。重定位条目中唯一的其他数据是要应用重定位的WAE地址。因此,您必须通过查看符号表并找到该符号的值来获取相对偏移量的地址,对吗?我不能100%确定您要解决的问题(我正要乘雪橇去上班,所以今晚必须给你回电)。我对我的原始回答做了一个编辑,试图澄清两起搬迁事件。如果这还不包括在内,那么请更详细地解释,也许可以举个例子,说明你正试图解决的问题。