Linux内核的调试需要有串口的支持,但是串口设备用的又比较少,相关附件也很难找到,于是用虚拟机模拟串口进行内核调试就显得非常方便。
通过虚拟机调试内核需要一台真实的物理机以及一台虚拟机。我们把该物理机叫做Host,虚拟机叫做Guest。下面我开始介绍如何通过虚拟机进行内核调试。
1. 在Host机器编译内核
编译内核的方法这里就不介绍了,网上相关内容很多,但需要注意的是,在编译选项中应该打开以下两个选项:- kernel hacking -> KGDB: kernel debugging with remote gdb -> KGDB: use kgdb over the serial port
-
kernel hacking -> Kernel Function Tracer
注意:编译完成之后不用安装。
2. 拷贝代码树
将Host机器上编译完成的内核连同源代码文件一同上传到Guest机器上,并且在Guest机器上安装新内核,安装的方法不再赘述。
3. 修改Grub
修改Guest机器上的Grub,/boot/grub/menu.lst,如下:
- title Ubuntu 8.04.4 LTS, kernel 2.6.27 Debug
-
root (hd0,0)
-
kernel /boot/vmlinuz root=UUID=9df62437-4366-42aa-9217-6af65365e24d ro quiet splash find_preseed=/preseed.cfg auto automatic-ubiquity noprompt priority=critical locale=en_US kgdboc=ttyS0,9600 kgdbwait
-
initrd /boot/initrd.img
-
quiet
重点是在kernel一行后边加上“kgdboc=ttyS0,9600 kgdbwait”,让内核停止在启动时,等待调试
4. 启动KVM虚拟机
使用以下参数启动Qemu:
- sudo qemu-system-x86_64 -hda ./images/Ubuntu_8.04_10.qcow2 -net nic,model=e1000,macaddr=DE:AD:BE:EF:91:10 -net nic,model=e1000,macaddr=DE:AD:BE:EF:15:10 -net tap -m 256 -vnc :10 -serial tcp::12345,server,nowait
重点是最后一个,将Guest OS的串口重定向到12345端口,之后的调试就需要链接该端口。
5. 开始gdb调试
启动VNC,选择3中设置的Grub项,启动调试,等待VNC中出现以下信息
- kgdb: Waiting for connection from remote gdb...
此时该内核就将自己挂起,等待远程调试。
6. 运行gdb程序
在Host源码目录下运行gdb:
输入以下调试命令,连接Guest OS内核:
- (gdb) target remote 10.0.7.8
如果连接正常,就可以看到内核停止在了kgdb_breakpoint()这个函数,此时就可以按照普通程序的调试方法对内核进行调试了。
阅读(2571) | 评论(0) | 转发(2) |