谁运行linux的main()?

谁运行linux的main()?

在Linux 0.11中,我们可以看到有一个main.c和一个main()

根据我的理解,目标代码需要一个操作系统来运行它。

我的意思是,既然Linux 0.11是一个操作系统,那么谁在它前面运行它呢? DOS?

答案1

选择的名称main()只是出于熟悉和美观的原因;没有 C 运行时调用它,就像main()从用户态程序调用它一样。甚至有一条评论也说明了这一点init/main.c

void main(void)         /* This really IS void, no error here. */

main()函数是从以下位置调用的boot/head.s

after_page_tables:
        pushl $0                # These are the parameters to main :-)
        pushl $0
        pushl $0
        pushl $L6               # return address for main, if it decides to.
        pushl $_main
        jmp setup_paging
L6:
        jmp L6                  # main should never return here, but
                                # just in case, we know what happens

请注意如何将 的地址main压入堆栈,并setup_paging使用 调用jmp,而不是使用call,这意味着ret位于其末尾的 将从 的开头继续main()

答案2

Linux内核,特别是0.11时代,都是由硬件BIOS直接加载的。

基本上,BIOS 会查看(软盘的)引导扇区或硬盘的主引导记录,并加载该扇区。对于硬盘,MBR 然后加载“主分区”引导扇区。

这个加载的引导扇区有足够的信息来了解如何将内核加载到内存中,然后运行它。

对于旧的 0.11 磁盘,它实际上是一种软盘引导解决方案,内核位于一个磁盘上,根目录位于另一个磁盘上,因此引导系统非常非常简单。

当Linux处理硬盘时,启动过程仍然非常简单。它是如此简单,以至于可以创建诸如“loadlin”之类的工具,它是一个简单的 DOS 程序,可以加载 Linux 内核并启动到其中,模拟 BIOS 加载程序。这样就可以创建一个 DOS config.sys 菜单来启动 DOS 或 Linux;双引导的早期形式。

但从本质上讲,Linux 内核是从“裸机”加载并接管机器的。

答案3

函数main是C语言的一个特性。它究竟如何转换为计算机指令供CPU“从这里开始”基本上是编译器实现细节。在裸机上,您通常可以简单地依赖硬件在首次启动时在特定内存地址开始执行。 Linux 的早期版本依赖于 a.简单的 x86 引导加载程序;如今,该角色通常由 Grub 承担。反过来,这种行为取决于 BIOS 固件约定,但实际上,在每个级别,您都有一个计算机体系结构,其中包含如何启动程序的约定。

相关内容