我是一名CS学生,刚刚在课堂上学习了基本的mips
(Patterson&Hennessy+spim
(,我正试图找到一种允许在调试过程中执行任意指令的mips
调试解决方案。
尝试使用gdb(所以您知道为什么不建议这样做(
推荐的mips
交叉编译工具链是qemu
和gdb
,请参阅mips.com文档和相关问答。
据我所知,gdb
的compile code
命令不支持mips-linux-gnu-gcc
,请参阅gdb文档("重新定位对象文件"(和相关问答。当尝试将compile code
与mips-linux-gnu-gcc
一起使用时,即使在过滤了mips-linux-gnu-gcc
无法识别的硬编码编译参数之后,我也会收到malloc
、mmap
的错误和无效内存错误(gdb
执行的自组织链接似乎出了问题(。
实际问题
lldb
有一个类似的命令expression
,请参阅lldb文档,我对将lldb
与qemu
结合使用很感兴趣。expression
命令也依赖于clang
,而不是gcc
,但clang中的交叉编译相对简单(clang -target mips-linux-gnu
"刚好有效"(。唯一的问题是qemu-mips -g
启动gdbserver
,而我找不到启动lldb-server
的选项。
我已经阅读了关于远程调试的lldb文档,并且可以选择remote-gdb-server
作为platform
。我找不到remote-gdb-server
的文档,但这个名称似乎暗示lldb
可以与gdbserver
兼容。
以下是我的尝试:
qemu-mips -g 1234 test
lldb test
(lldb) platform select remote-gdb-server
Platform: remote-gdb-server
Connected: no
(lldb) platform connect connect://localhost:1234
Platform: remote-gdb-server
Hostname: (null)
Connected: yes
(lldb) b main
Breakpoint 1: where = test`main + 16 at test.c:4, address = 0x00400530
(lldb) c
error: invalid process
有没有办法去
- 将
lldb
与gdbserver
一起使用,或 - 从
qemu-mips
启动lldb-server
,而不是从gdbserver
启动
以便在调试mips
代码时执行指令?
注意:我知道我可以使用qemu
系统仿真来在远程上运行lldb-server
。我曾尝试使用本指南虚拟化debian mips
,但netinstaller无法检测到我的网卡。从众多SO问答和在线论坛来看,解决这个问题似乎很难。所以现在我尽量避免整个系统的模拟。
YES
将LLDB与QEMU 一起使用
LLDB支持QEMU使用的GDB服务器,所以您可以对上一节做同样的事情,但需要进行一些命令修改,因为LLDB有一些不同于GDB的命令您可以运行QEMU来监听";GDB连接";在它开始执行任何代码来调试它之前。
qemu -s -S <harddrive.img>
将设置QEMU在端口1234上侦听,并等待与它的GDB连接。然后,从远程或本地shell:
lldb kernel.elf
(lldb) target create "kernel.elf"
Current executable set to '/home/user/osdev/kernel.elf' (x86_64).
(lldb) gdb-remote localhost:1234
Process 1 stopped
* thread #1, stop reason = signal SIGTRAP
frame #0: 0x000000000000fff0
-> 0xfff0: addb %al, (%rax)
0xfff2: addb %al, (%rax)
0xfff4: addb %al, (%rax)
0xfff6: addb %al, (%rax)
(如有必要,用远程IP/URL替换localhost。(然后开始执行:
(lldb) c
Process 1 resuming
设置断点:
(lldb) breakpoint set --name kmain
Breakpoint 1: where = kernel.elf`kmain, address = 0xffffffff802025d0
针对您的情况:
- qemu-mips-s-s检验
- lldb测试
- gdb远程本地主机:1234
这是我的,你可以参考:
############################################# gdb #############################################
QEMU_GDB_OPT := -S -gdb tcp::10001,ipv4
# 调试配置:-S -gdb tcp::10001,ipv4
qemudbg:
ifeq ($(BOOT_MODE),$(BOOT_LEGACY_MODE))
$(QEMU) $(QEMU_GDB_OPT) $(QEMU_ARGUMENT)
else
ifeq ($(BOOT_MODE),$(BOOT_GRUB2_MODE))
ifeq ($(EFI_BOOT_MODE),n)
$(QEMU) $(QEMU_GDB_OPT) $(QEMU_ARGUMENT) -cdrom $(KERNSRC)/$(OS_NAME).iso
else
$(QEMU) $(QEMU_GDB_OPT) $(QEMU_ARGUMENT) -bios $(BIOS_FW_DIR)/IA32_OVMF.fd -cdrom $(KERNSRC)/$(OS_NAME).iso
endif
endif
endif
# 连接gdb server: target remote localhost:10001
gdb:
$(GDB) $(KERNEL_ELF)
############################################# lldb #############################################
QEMU_LLDB_OPT := -s -S
LLDB := lldb
qemulldb:
ifeq ($(BOOT_MODE),$(BOOT_LEGACY_MODE))
$(QEMU) $(QEMU_LLDB_OPT) $(QEMU_ARGUMENT)
else
ifeq ($(BOOT_MODE),$(BOOT_GRUB2_MODE))
ifeq ($(EFI_BOOT_MODE),n)
$(QEMU) $(QEMU_LLDB_OPT) $(QEMU_ARGUMENT) -cdrom $(KERNSRC)/$(OS_NAME).iso
else
$(QEMU) $(QEMU_LLDB_OPT) $(QEMU_ARGUMENT) -bios $(BIOS_FW_DIR)/IA32_OVMF.fd -cdrom $(KERNSRC)/$(OS_NAME).iso
endif
endif
endif
lldb:
$(LLDB) $(KERNEL_ELF)