将NASM和64位C代码一起编译并链接到引导加载程序中 [英] Compiling and linking NASM and 64-bit C code together into a bootloader

查看:368
本文介绍了将NASM和64位C代码一起编译并链接到引导加载程序中的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我制作了一个非常简单的1级引导加载程序,它执行两个主要任务:它从16位实模式切换到64位长模式,并且从硬盘读取接下来的几个用于启动基本内核的扇区. /p>

对于基本内核,我试图用C而不是汇编语言编写代码,对此我有一些疑问:

  1. 我应该如何编译和链接nasm文件和C文件?
  2. 编译文件时,应该编译为16位还是64位?因为我从16位切换到64位.
  3. 我如何将C或程序集中的更多文件添加到项目中?

我重写了这个问题,以使我的目标更加明确,因此,如果需要源代码,请告诉我添加它.

代码: https://github.com/LatKid/BasicBootloaderNASMC

解决方案

由于我还将nasm文件也与C文件链接在一起,因此它会从nasm目标文件中引发错误,这是在创建共享库时无法使用针对.text的重定位R_X86_64_16;用-fPIC重新编译

您的问题之一可能在该nasm汇编器文件中(在问题的初始版本中未显示).它应仅包含与位置无关的代码(PIC),因此无法生成目标文件,并带有重定位 R_X86_64_16(在您编辑的问题中,mov sp, main显然不是PIC,您应该使用 ELF ,然后是 objdump(1)& readelf(1)检查对象文件(和共享对象)和可执行文件.

一旦您的nasm代码生成了PIC目标文件,请链接gcc使用crt0 -lgcc-lc).

也许您需要了解更好的编译和链接.阅读Levine的书 链接器和加载器 ,Drepper的论文链接器脚本.另请参见对一个非常相关的问题的回答(可能与您的动机相似);那里的参考资料与您高度相关.

PS.您的问题缺乏动机和背景(它没有 MCVE ,但需要一个),可能有些 github GRUB ),然后将精力集中在OS代码上(应将其发布为免费软件,以获取一些反馈).

I made a very simple 1 stage bootloader that does two main things: it switches from 16 bit real mode to 64 bit long mode, and it read the next few sectors from the hard disk that are for initiating the basic kernel.

For the basic kernel, I am trying to write code in C instead of assembly, and I have some questions regarding that:

  1. How should I compile and link the nasm file and the C file?
  2. When compiling the files, should I compile to 16 bit or 64 bit? since I am switching from 16 to 64 bits.
  3. How would I add more files from either C or assembly to the project?

I rewrote the question to make my goal more clear, so if source code is needed tell me to add it.

Code: https://github.com/LatKid/BasicBootloaderNASMC

解决方案

since I am also linking a nasm file with the C file, it spits an error from the nasm object file, which is relocation R_X86_64_16 against .text' can not be used when making a shared object; recompile with -fPIC

One of your issues is probably inside that nasm assembler file (which you don't show in the initial version of your question). It should contain only position-independent code (PIC) so cannot produce an object file with relocation R_X86_64_16 (In your edited question, mov sp, main is obviously not PIC, you should use instruction pointer relative data access of x86-64, and you cannot define main both in your nasm file and in a C file, and you cannot mix 16 bits mode with 64 bits mode when linking).

Study ELF, then the x86-64 ABI to understand what kind of relocations are permitted in a PIC file (and what constraints an assembler file should follow to produce a PIC object file).

Use objdump(1) & readelf(1) to inspect object files (and shared objects and executables).

Once your nasm code produces a PIC object file, link with gcc and use gcc -v to understand what happens under the hoods (you'll see that extra libraries and object files, including crt0 ones, -lgcc and -lc, are used).

Perhaps you need to understand better compilation and linking. Read Levine's book Linkers and Loaders, Drepper's paper How To Write Shared Libraries, and -about compilation- the Dragon book.

You might want to link with gcc but use your own linker script. See also this answer to a very related question (probably with motivations similar to yours); the references there are highly relevant for you.

PS. Your question lacks motivation and context (it has no MCVE but needs one) and might be some XY problem. I guess you are on Linux. I strongly recommend publishing your actual full code -even buggy- (perhaps on github or gitlab or elsewhere) as free software to get potential help. I strongly recommend using an existing bootloader (probably GRUB) and focus your efforts on your OS code (which should be published as free software, to get some feedback).

这篇关于将NASM和64位C代码一起编译并链接到引导加载程序中的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆