mirror of
https://github.com/DragonOS-Community/DragonOS.git
synced 2025-06-18 08:06:32 +00:00
feat: 添加对内核引导协议的抽象 (#913)
* 添加multiboot header * head.S传参增加bootloader类型 * feat: 添加引导加载协议的抽象,并为multiboot2实现这个抽象. * 把framebuffer的映射地址改为从early ioremap和mmio pool分配 * riscv64能运行
This commit is contained in:
@ -1,12 +1,24 @@
|
||||
# 引导加载程序
|
||||
|
||||
## 原理
|
||||
## X86_64
|
||||
|
||||
  目前,DragonOS支持Legacy BIOS以及UEFI两种方式,进行启动引导。
|
||||
- [x] multiboot2
|
||||
|
||||
  在`head.S`的头部包含了Multiboot2引导头,里面标志了一些Multiboot2相关的特定信息,以及一些配置命令。
|
||||
## RISC-V 64
|
||||
|
||||
  在DragonOS的启动初期,会存储由GRUB2传来的magic number以及multiboot2_boot_info_addr。当系统进入`Start_Kernel`函数之后,将会把这两个信息保存到multiboot2驱动程序之中。信息的具体含义请参照Multiboot2 Specification进行理解,该部分难度不大,相信读者经过思考能理解其中的原理。
|
||||
DragonOS在RISC-V 64上,启动流程为:
|
||||
|
||||
opensbi --> uboot --> DragonStub --> kernel
|
||||
|
||||
这个启动流程,使得DragonOS内核与具体的硬件板卡解耦,能够以同一个二进制文件,在不同的硬件板卡上启动运行。
|
||||
|
||||
|
||||
## 内核启动回调
|
||||
|
||||
DragonOS对内核引导加载程序进行了抽象,体现为`BootCallbacks`这个trait。
|
||||
不同的引导加载程序,实现对应的callback,初始化内核bootParams或者是其他的一些数据结构。
|
||||
|
||||
内核启动时,自动根据引导加载程序的类型,注册回调。并且在适当的时候,会调用这些回调函数。
|
||||
|
||||
## 参考资料
|
||||
|
||||
|
@ -8,4 +8,3 @@
|
||||
:caption: 目录
|
||||
|
||||
bootloader
|
||||
multiboot2
|
||||
|
@ -1,46 +0,0 @@
|
||||
# Multiboot2支持模块
|
||||
|
||||
  Multiboot2支持模块提供对Multiboot2协议的支持。位于`kernel/driver/multiboot2`文件夹中。
|
||||
|
||||
  根据Multiboot2协议,操作系统能够从BootLoader处获得一些信息,比如基本的硬件信息以及ACPI表的起始地址等。
|
||||
|
||||
---
|
||||
|
||||
## 数据结构
|
||||
|
||||
  `kernel/driver/multiboot2/multiboot2.h`中按照Multiboot2协议的规定,定义了大部分的数据结构,具体细节可查看该文件: [DragonOS/multiboot2.h at master · fslongjin/DragonOS · GitHub](https://github.com/fslongjin/DragonOS/blob/master/kernel/driver/multiboot2/multiboot2.h)
|
||||
|
||||
---
|
||||
|
||||
## 迭代器
|
||||
|
||||
  由于Multiboot2的信息存储在自`multiboot2_boot_info_addr`开始的一段连续的内存空间之中,且不同类型的header的长度不同,因此设计了一迭代器`multiboot2_iter`。
|
||||
|
||||
### 函数原型
|
||||
|
||||
```c
|
||||
void multiboot2_iter(bool (*_fun)(const struct iter_data_t *, void *, unsigned int *),
|
||||
void *data, unsigned int *count)
|
||||
```
|
||||
|
||||
**_fun**
|
||||
|
||||
  指定的handler。当某个header的tag与该handler所处理的tag相同时,handler将处理该header,并返回true。
|
||||
|
||||
  其第一个参数为tag类型,第二个参数为返回的数据的指针,第三个值为计数(某些没有用到该值的地方,该值可以为空)
|
||||
|
||||
**data**
|
||||
|
||||
  传递给`_fun`的第二个参数,`_fun`函数将填充该指针所指向的内存区域,从而返回数据。
|
||||
|
||||
**count**
|
||||
|
||||
  当返回的**data**为一个列表时,通过该值来指示列表中有多少项。
|
||||
|
||||
---
|
||||
|
||||
## 迭代工作函数
|
||||
|
||||
  在模块中,按照我们需要获取不同类型的tag的需要,定义了一些迭代器工作函数。
|
||||
|
||||
|
Reference in New Issue
Block a user