Skip to content

第一章:应用程序与基本执行环境

内存布局

下面图“数据存储器”应该是 Data Memory. image.png|500

Qemu 启动流程

  • Step 1:
    • Qemu CPU pc set to 0x1000,执行神秘指令,使得待会儿能跳转到 0x80000000
0x0000000000001000 in ?? ()
(gdb) x/10i $pc
=> 0x1000:      auipc   t0,0x0
   0x1004:      addi    a2,t0,40
   0x1008:      csrr    a0,mhartid
   0x100c:      ld      a1,32(t0)
   0x1010:      ld      t0,24(t0)
   0x1014:      jr      t0 # 这里 t0 值已经变成 0x80000000
   0x1018:      unimp
   0x101a:      0x8000
   0x101c:      unimp
   0x101e:      unimp
  • Step 2: 0x80000000
    • 这里是 RUSTSBI,会执行很多指令。所以实操时在 0x80200000 打了个断点快速过去.
0x0000000080000000 in ?? ()
(gdb) x/10i $pc
=> 0x80000000:  auipc   ra,0x2
   0x80000004:  jalr    834(ra)
   0x80000008:  auipc   ra,0x0
   0x8000000c:  jalr    116(ra)
   0x80000010:  j       0x80001690
   0x80000014:  unimp
   0x80000016:  addi    sp,sp,-80
   0x80000018:  sd      ra,72(sp)
   0x8000001a:  ld      a1,40(a0)
   0x8000001c:  ld      a2,32(a0)
  • Step 3: 0x80200000 自己的 Rust 程序
(gdb) x/5i $pc
=> 0x80200000:  li      ra,100
   0x80200004:  unimp
   0x80200006:  unimp
   0x80200008:  unimp
   0x8020000a:  unimp

RustSBI is what?

SBI 是 RISC-V Supervisor Binary Interface 规范的缩写,OpenSBI 是RISC-V官方用C语言开发的SBI参考实现;RustSBI 是用Rust语言实现的SBI。

BIOS 是 Basic Input/Output System,作用是引导计算机系统的启动以及硬件测试,并向OS提供硬件抽象层。

机器上电之后,会从ROM中读取引导代码,引导整个计算机软硬件系统的启动。而整个启动过程是分为多个阶段的,现行通用的多阶段引导模型为:

ROM -> LOADER -> RUNTIME -> BOOTLOADER -> OS

Loader 要干的事情,就是内存初始化,以及加载 Runtime 和 BootLoader 程序。而Loader自己也是一段程序,常见的Loader就包括 BIOS 和 UEFI,后者是前者的继任者。

Runtime 固件程序是为了提供运行时服务(runtime services),它是对硬件最基础的抽象,对OS提供服务,当我们要在同一套硬件系统中运行不同的操作系统,或者做硬件级别的虚拟化时,就离不开Runtime服务的支持。SBI就是RISC-V架构的Runtime规范。

BootLoader 要干的事情包括文件系统引导、网卡引导、操作系统启动配置项设置、操作系统加载等等。常见的 BootLoader 包括GRUB,U-Boot,LinuxBoot等。

而 BIOS/UEFI 的大多数实现,都是 Loader、Runtime、BootLoader 三合一的,所以不能粗暴的认为 SBI 跟 BIOS/UEFI 有直接的可比性。

如果把BIOS当做一个泛化的术语使用,而不是指某个具体实现的话,那么可以认为 SBI 是 BIOS 的组成部分之一。