一、kgdb介绍
linux下的模块开发,不可避免要用到kgdb来调试。
kgdb的调试环境需要一台开发机,一台目标机,其中代码运行在目标机上,开发机通过串口来调试目标机上的模块代码。
用vmware可以方便的使用管道来代替真正的串口,而且只用一台笔记本就可以玩起来,非常简单粗暴。
二、编译内核支持kgdb
2.1 修改内核代码
为了解决系统的一个bug,具体见下面的错误处理。
文件:linux-2.6.32/kernel/kgdb.c
2.2 设置内核编译参数
在一台虚拟机上下载内核源码,配置如下参数:
然后编译内核。(参考:http://blog.csdn.net/guowenyan001/article/details/38704775)
三、设置虚拟机命名管道
3.1 克隆上面编译的虚拟机
2个虚拟机一个作为开发机,一个作为目标机。
3.2 设置2个虚拟机的命名管道
虚拟机(右键) -> 设置 -> 串行端口
开发机:
目标机:
3.3 添加串行端口
如果没有串行端口,添加串行端口:虚拟机(右键) -> 设置 -> 添加 -> 串行端口(下一步) -> 使用主机上的物理串行端口(P)(下一步)。
向VMWare虚拟机添加一个串口设备(serial port):http://blog.csdn.net/liuhui_8989/article/details/9822455
3.4 测试串行端口
打开2个虚拟机:
一台机器上cat /dev/ttyS0,另一台机器上 echo "hello" > /dev/ttyS0,前一台机器上会出hello,则说明配置成功。
注意:
先cat,再echo。
ttyS0不行,就试试ttyS1。(我的就是ttyS1)
四、配置KGDB
4.1 修改开发机、目标机内核
在/boot/grub/grub.conf 中,启动选项最后添加 “kgdboc=ttyS1,115200”:
目标机上,应添加“kgdboc=ttyS1,115200 kgdbwait”。
4.2 查看是否成功
在目标机上输入“echo ttyS1 > /sys/module/kgdboc/parameters/kgdboc”;
在/var/log/messages文件中输出“kernel: kgdb: Registered I/O driver kgdboc.”;
说明配置成功。
五、简单使用
5.1 目标机上
在目标机上输入“echo g > /proc/sysrq-trigger”,显示:
表示目标机已经开始等待开发机的kgdb链接了。
5.2 开发机上
gdb /usr/src/linux-2.6.32/vmlinux
set remotebaud 115200
set debug remote 1 (输出调试信息,可有可无)
target remote /dev/ttyS1
目标机的内核已经break在wmb()上了。
出现上面蓝色框,说明成功了。
5.2 kgdbwait
可以在目标机内核配置文件,添加“kgdboc=ttyS1,115200 kgdbwait”,重启。
在启动时内核会打印一条:kgdb: Waiting for connection from remote gdb。
这时候可以用开发机的kgdb去连接目标机了。
六、错误
6.1 现象
target remote /dev/ttyS1时,会出现错误“trace API error 0x2”。
这是一个bug。
6.2 解决办法
编译内核前,给内核打一个补丁。
我打补丁没成功,直接改了内核代码linux-2.6.32/kernel/kdgb.c,删除了1005行和1049行:
参考:https://bugzilla.redhat.com/show_bug.cgi?format=multiple&id=710668
参考资料:
用KGDB进行内核调试 Vmware KGDB :http://blog.chinaunix.net/uid-25538637-id-261329.html
向VMWare虚拟机添加一个串口设备(serial port):http://blog.csdn.net/liuhui_8989/article/details/9822455
vmware环境下的kgdb环境配置和模块调试示例 (1):http://blog.csdn.net/majieyue/article/details/6967770
在VMware环境下,使用KGDB调试内核及内核模块---基于kernel 2.6.36 :http://blog.chinaunix.net/uid-20672257-id-2936794.html
官网:http://elinux.org/Kgdb