1. QEMU RISC-V 环境搭建:从源码到第一个虚拟机
各位同学,咱们直接进入正题。做 RISC-V 开发,第一件事就是把环境搭起来。这一步要是没弄好,后面所有调试、分析、故障排查都无从谈起。我个人习惯是「源码编译 QEMU + 独立安装工具链」,这样可控性最强。
本章核心目标: 从零搭建一套可用的 QEMU RISC-V 开发环境,并成功启动第一个虚拟机。
1.1 为什么非要自己编译 QEMU?
你可能会问:apt install qemu-system 不香吗?嗯,这里要注意——发行版自带的 QEMU 版本通常比较老,而且很多调试功能没打开。我在项目中遇到过因为 QEMU 版本太低,导致 GDB 连不上模拟器的问题,查了整整两天。
自己编译的好处有三个:
- 版本可控:想用 7.2 还是 8.0,你说了算
- 调试符号全开:--enable-debug 编译出来的 QEMU 能输出更详细的日志
- 自定义设备:后面章节我们会往 QEMU 里加自定义外设,必须源码编译
1.2 编译 QEMU(RISC-V 目标)
先拉源码。我建议用 Git 克隆,方便后续切分支。
git clone https://gitlab.com/qemu-project/qemu.git
cd qemu
git checkout stable-8.0 # 我用的是 8.0,稳定且功能齐全
配置编译选项。这里我列一个「生产级」配置,既保证性能,又保留调试能力:
./configure \
--target-list=riscv64-softmmu \
--enable-debug \
--enable-debug-info \
--enable-kvm \
--enable-virtfs \
--enable-slirp
| 配置项 | 作用 | 我的建议 |
|---|---|---|
| --target-list=riscv64-softmmu | 只编译 RISC-V 64 位系统模拟 | 省时间,别全编译 |
| --enable-debug | 开启 QEMU 内部调试日志 | 必开,后面分析日志全靠它 |
| --enable-kvm | 支持 KVM 加速 | 有硬件虚拟化就开 |
| --enable-slirp | 用户态网络栈 | 方便虚拟机上网 |
注意: 编译依赖包别漏了。Ubuntu 下执行
sudo apt install ninja-build libglib2.0-dev libpixman-1-dev。我吃过亏,configure 通过了,make 到一半报错,就是因为缺 libpixman。
编译安装:
make -j$(nproc)
sudo make install
验证一下:
qemu-system-riscv64 --version
看到版本号输出,说明 QEMU 编译成功。
1.3 RISC-V 工具链安装
工具链我推荐两种方式,看你的场景选:
| 方式 | 适用场景 | 安装命令 |
|---|---|---|
| 发行版包管理器 | 快速验证、学习 | sudo apt install gcc-riscv64-linux-gnu |
| 源码编译(riscv-gnu-toolchain) | 生产环境、定制优化 | 见下方步骤 |
我个人倾向源码编译,因为可以控制 GCC 版本和 ABI 配置。但如果你只是跑个 Hello World,用包管理器就够了。
源码编译步骤:
git clone https://github.com/riscv-collab/riscv-gnu-toolchain
cd riscv-gnu-toolchain
./configure --prefix=/opt/riscv --enable-multilib
make -j$(nproc)
sudo make install
小技巧: 编译工具链很耗时,我一般用
screen 或 tmux 挂后台。曾经有一次编译到 90% 时 SSH 断了,心态崩了。从那以后,所有长时间编译我都用 tmux。
验证工具链:
/opt/riscv/bin/riscv64-unknown-linux-gnu-gcc --version
1.4 启动第一个 RISC-V 虚拟机
环境搭好了,咱们跑个真正的 RISC-V Linux 看看。你需要三个东西:
- OpenSBI:RISC-V 的底层固件,负责引导
- U-Boot:引导加载程序
- 根文件系统镜像:我用 Buildroot 生成的最小系统
下载预编译好的镜像(省时间):
wget https://github.com/riscv-software-src/opensbi/releases/download/v1.2/opensbi-1.2-rv64-binaries.tar.xz
tar xf opensbi-1.2-rv64-binaries.tar.xz
启动命令:
qemu-system-riscv64 \
-machine virt \
-cpu rv64 \
-m 2G \
-smp 2 \
-bios opensbi-1.2-rv64-binaries/share/opensbi/lp64/generic/firmware/fw_jump.bin \
-kernel u-boot.bin \
-drive file=rootfs.ext2,format=raw,id=hd0 \
-device virtio-blk-device,drive=hd0 \
-nographic
看到 OpenSBI 的启动日志,然后进入 U-Boot,最后出现 Linux 登录提示符——恭喜,你的第一个 RISC-V 虚拟机跑起来了!
关键输出: 你会看到类似
OpenSBI v1.2、Linux version 6.1.0 这样的日志。这些日志后面章节会反复分析,先混个眼熟。
1.5 本章知识结构图
下面这张图把整个环境搭建的流程串起来了,建议你保存下来对照操作:
1.6 常见问题与避坑
环境搭建这一步,我见过太多人卡住。列几个高频问题:
问题1:configure 报错 "glib-2.0 not found"
原因:缺 libglib2.0-dev。执行
原因:缺 libglib2.0-dev。执行
sudo apt install libglib2.0-dev 即可。
问题2:启动后黑屏,没有任何输出
原因:多半是 -bios 参数指向的 OpenSBI 文件不对,或者 -nographic 没加。检查文件路径,确认使用 fw_jump.bin 而非 fw_payload.bin。
原因:多半是 -bios 参数指向的 OpenSBI 文件不对,或者 -nographic 没加。检查文件路径,确认使用 fw_jump.bin 而非 fw_payload.bin。
问题3:编译 QEMU 时 make 卡住不动
我曾经在 4GB 内存的机器上编译,直接 OOM 了。建议至少 8GB 内存,或者用
我曾经在 4GB 内存的机器上编译,直接 OOM 了。建议至少 8GB 内存,或者用
make -j2 降低并行度。
1.7 验证环境是否就绪
最后,我建议你做一个快速自检。跑下面这条命令,如果能正常输出,说明环境基本没问题:
qemu-system-riscv64 -machine virt -cpu rv64 -m 256M -nographic -bios /dev/null
这条命令不会启动任何系统,但会输出 QEMU 的 monitor 提示符。看到 (qemu) 就对了。
环境就绪清单:
- ✅ QEMU 8.0 编译安装完成
- ✅ RISC-V 工具链可用(gcc、ld、objdump)
- ✅ OpenSBI 和 U-Boot 镜像已下载
- ✅ 根文件系统镜像已准备
- ✅ 能启动到 Linux 登录提示符