【问题标题】:GRUB Multiboot header not found未找到 GRUB Multiboot 标头
【发布时间】:2015-02-28 21:37:30
【问题描述】:
在阅读了this question 和它的主要答案后,我在内核上运行了 readelf,并注意到我的 .text 部分位于 0x00101000 而不是 0x00100000。我还注意到上面的部分 .not.gnu.build-i 位于 .text 部分应该在的位置。有没有办法让我的 .text 部分位于正确的位置?我已经用align 4设置为1M了。
【问题讨论】:
标签:
linker
32-bit
osdev
grub
multiboot
【解决方案1】:
问题在于LD(或通过GCC 的LD)会自动在前4k 中放置一个注释部分(如果已生成)。如果将最终内核与 GCC 链接,则传递 -Wl,--build-id=none 选项。如果您使用 LD 直接链接最终的二进制文件,那么您可以传递它--build-id=none。
如果编写一个多重引导 ELF 对象,这个额外部分的存在可能会强制多重引导标头超出文件中的 8k 位置。这是因为 ELF 标头通常占用文件的前 4k 的最小值。为.note.gnu.build-id 和.multiboot 添加4k 部分现在超出了物理文件的8k 标记。这将导致像 GRUB 这样的多重引导加载程序认为您的 ELF 可执行文件没有多重引导头,因为它只查看文件的前 8k。
【解决方案2】:
您的链接器脚本(假设它与另一个问题中的相同)是问题所在:通过告诉它 4k 对齐部分并将multiboot 放在单独的部分中,您为其分配了 4k,所以@ 987654322@ 以 1M + 4k 的偏移量开始,这会导致您的问题。将其更改为以下内容:
SECTIONS
{
. = 1M;
.text ALIGN(4K) :
{
*(.multiboot)
*(.text)
}
[snip]