Skip to content

编译与运行

本指南介绍如何编译 NoobKernel 并在 QEMU 中运行。

Makefile 结构

项目使用模块化的 Makefile 结构:

Makefile          # 主 Makefile,定义全局变量和目标
rules.mk          # 编译规则模板
src/*/Makefile    # 各模块的 Makefile
scripts/kernel.ld # 链接脚本

主要变量

变量 说明 默认值
TOOL_PREFIX 工具链前缀 riscv64-unknown-elf-
ARCH 目标平台 QEMU
INIT_PROC 初始进程 usershell
GDB_PORT GDB 端口 15234

内核模块

当前启用的模块(MODULES 变量):

MODULES := boot misc mm hal trap task sync fs

待实现的模块: - syscall - 系统调用 - ipc - 进程间通信 - async - 异步机制

编译命令

编译内核

make

编译产物位于 build/QEMU/ 目录:

  • kernel - ELF 格式内核镜像
  • kernel.asm - 反汇编文件(带源码)
  • kernel.sym - 符号表

清理

make clean

删除当前架构的构建目录。

编译指定平台

make ARCH=QEMU

当前仅支持 QEMU virt 平台。

运行内核

直接运行

make run

内核将在 QEMU 中启动,日志输出到终端。

Ctrl+A 然后按 X 退出 QEMU。

QEMU 参数说明

QEMU_FLAGS = \
    -nographic                 # 无图形界面,使用终端输出
    -machine virt              # 使用 virt 虚拟机
    -m 128M                    # 128MB 内存
    -kernel $(TARGET)          # 加载内核镜像
    -drive file=fs.img,...     # 挂载磁盘镜像

调试内核

GDB 调试

make debug

此命令会: 1. 启动 QEMU(暂停状态,等待 GDB) 2. 自动连接 GDB

在 GDB 中:

# 继续执行
continue

# 设置断点
break main
break kerneltrap

# 查看寄存器
info registers

# 查看当前函数
backtrace

VSCode 调试

make vs-debug

然后在 VSCode 中按 F5 开始调试。

内核初始化流程

内核启动后会执行以下初始化:

main() @ src/boot/main.c
│
├── clear_bss()        # 清零 BSS 段
├── init_cpu()         # 初始化 CPU 结构
├── pm_init()          # 物理内存管理初始化
├── plic_init()        # PLIC 中断控制器初始化
├── trap_init()        # 中断处理初始化
├── timer_init()       # 定时器初始化
├── kvminit()          # 内核虚拟内存初始化
├── init_runq()        # 运行队列初始化
├── blk_init()         # 块设备初始化
├── bcache_init()      # 缓冲区缓存初始化
├── virtio_init()      # VirtIO 设备初始化
├── vfs_init()         # VFS 初始化
├── fd_table_init()    # 文件描述符表初始化
├── ramfs_init()       # RAM 文件系统初始化
├── vfs_mount_root()   # 挂载根文件系统
├── sched_enabled=true # 启用调度器
├── context_switch_to()# 切换到 idle 进程
└── sched_yield()      # 开始调度

常见问题

编译错误

找不到头文件:检查 include/ 目录结构是否完整。

链接错误:检查 scripts/kernel.ld 是否存在。

运行问题

QEMU 无输出: 1. 检查内核是否正确编译 2. 确认 SBI 正常启动(QEMU 默认使用 OpenSBI)

内核崩溃: 1. 查看 kernel.asm 分析崩溃位置 2. 使用 GDB 调试定位问题

下一步