调试Bootloader时GDB报“Cannot find bounds of current function”错误求助
问题分析与解决建议
一、GDB "Cannot find bounds of current function" 错误解决
这个错误源于实模式下GDB的符号解析限制,以及BIOS中断执行后的上下文追踪问题:
- 核心原因:执行
int指令进入BIOS代码后,GDB没有BIOS的符号表,中断返回后无法识别用户代码的函数边界;同时你的汇编函数缺少栈帧初始化,GDB无法自动追踪函数范围。 - 修复方法:
- 给汇编函数添加栈帧结构:在
check_a20_status开头加上push %bp; mov %sp, %bp,结尾加上pop %bp,帮助GDB识别函数起止点。 - 调试中断时跳过BIOS代码:执行到
int指令前,用b *$pc+2在中断返回后的下一条指令设置断点,再输入c跳过BIOS执行流程,回到自己的代码后再单步调试。 - 优化
.gdbinit:添加set print asm-demangle off避免符号解析混乱,保持架构设置set architecture i8086不变。
- 给汇编函数添加栈帧结构:在
二、A20线禁用的代码错误
你当前误用了视频服务中断int $0x10,而非控制A20线的BIOS中断:
- 错误代码:
movw $0x2400, %ax; int $0x10是调用视频中断关闭显示,和A20线无关。 - 正确写法:使用
int $0x15的0x24子功能控制A20:; 禁用A20线 movw $0x2400, %ax int $0x15 - 备选方案:若QEMU的BIOS不支持
int 15h 2400h,可改用键盘控制器端口(0x60/0x64)直接操作硬件禁用A20,这是更可靠的底层方法。
三、A20状态检测逻辑修正
你的检测代码缺少关键的对比逻辑,无法正确判断A20状态,修正后的示例:
check_a20_status: push %bp mov %sp, %bp push %cx push %bx xorw %ax, %ax movw %ax, %ds movw $ES_EDGE_ADDR, %ax movw %ax, %es ; 保存低内存原始值 movw %ds:0x0, %cx ; 写入测试值到低内存(0x0000:0x0000) movw $A20_TEST_VALUE, %ds:0x0 ; 写入不同值到1MB边界地址(0xFFFF:0x0010) movw $0x1234, %es:0x0010 ; 读取低内存值 movw %ds:0x0, %ax ; 恢复低内存原始值 movw %cx, %ds:0x0 ; 对比判断:ax不等于测试值则A20已启用,否则禁用 cmpw $A20_TEST_VALUE, %ax je a20_disabled ; 此处可通过寄存器返回状态(比如al=1表示启用,al=0表示禁用) a20_disabled: pop %bx pop %cx pop %bp ret
四、Makefile与调试环境优化
- 简化
obj目标的编译参数,避免重复定义:obj: $(CC) $(CFLAGS) -Wl,-Ttext=0x7c00 -o boot.out $(BOOT_SRC) - QEMU启动参数添加
-boot c明确从硬盘启动,确保Bootloader被正确加载到0x7c00地址:debug: image qemu-system-i386 -drive file=boot.bin,format=raw -nographic -serial mon:stdio -gdb tcp::$(GDB_PORT) -S -boot c
内容的提问来源于stack exchange,提问作者user15980977
相关产品推荐
相关产品推荐

