2. 编写并运行Hello World引导扇区
任务目标
编写一个可直接引导的Hello World引导扇区程序,将其写入虚拟软盘镜像的首扇区,并通过QEMU验证启动后屏幕显示字符串。
环境依赖
- NASM汇编器(
nasm) - QEMU模拟器(
qemu-system-x86_64) - Linux/macOS终端环境
实现原理
BIOS在自检完成后,会将启动设备的第一个扇区(512字节)加载到内存地址0x7C00处,并跳转执行。引导扇区代码需以0x55AA作为结束标志(偏移510处为0x55,偏移511处为0xAA),BIOS才会将其识别为合法引导扇区。本案例使用BIOS中断int 0x10的0x0E功能(TTY字符输出)逐字符打印字符串,最后通过cli; hlt停机。
完整代码
; hello_boot.asm
[org 0x7C00] ; 告诉汇编器代码将被加载到0x7C00
mov si, msg ; SI指向要打印的字符串
call print_string ; 调用打印函数
cli ; 关闭中断
hlt ; 停机
print_string:
lodsb ; 加载SI指向的字符到AL,SI自增
or al, al ; 检查AL是否为0(字符串结束符)
jz .done ; 若为0则返回
mov ah, 0x0E ; BIOS TTY输出功能号
int 0x10 ; 调用BIOS视频中断
jmp print_string ; 继续下一个字符
.done:
ret
msg db 'Hello, World!', 0
times 510-($-$$) db 0 ; 填充至510字节
dw 0xAA55 ; 引导扇区结束标志(小端序写入)
编译与运行
# 1. 编译为二进制文件
nasm -f bin hello_boot.asm -o hello_boot.bin
# 2. 创建1.44MB软盘镜像(大小任意,QEMU可识别)
dd if=/dev/zero of=boot.img bs=512 count=2880
# 3. 将引导扇区写入镜像起始位置
dd if=hello_boot.bin of=boot.img bs=512 count=1 conv=notrunc
# 4. 用QEMU启动
qemu-system-x86_64 -drive format=raw,file=boot.img
验证方法
QEMU窗口启动后,屏幕左上角应显示Hello, World!字符串,且系统不再继续执行(无引导错误提示)。若使用echo $?检查QEMU退出码,手动关闭窗口时返回码非0属正常现象。
常见问题
- 屏幕无输出:确认
nasm编译无报错,且dd写入时使用了conv=notrunc(防止截断镜像)。 - 提示“Boot failed”:检查二进制文件最后两个字节是否为
55 AA,可用xxd hello_boot.bin | tail -1查看。 - 字符串乱码:确认代码中
[org 0x7C00]未被删除,否则内存引用地址会偏移。