概述
一、 需求
在Linux内核开发过程中不可避免地地会面对如何调试内核的问题。比如printk() 是调试内核代码时最常用的一种技术,但是这种调试方法需要对问题产生的点有个大概的感知,这样才能有的放矢地在合适的代码处添加打印信息。
但是很多情况下,我们对问题产生的原因毫无头绪,也就不可能在茫茫的代码中添加printk,这时候我们就依赖于GDB构建Linux内核调试环境。本文以Linux 4.1.15为例,介绍调试环境的搭建过程。
二、 原理
参考内核文档:
linux/Documentation/gdb-kernel-debugging.txt
GDB调试过程中需要加载符号信息,即lx-symbols命令,该命令是实现在内核自带python脚本:/linux/scripts/gdb/vmlinux-gdb.py,这也是”build gdb 7.2+ (recommended: 7.4+) with python supportenabled”的原因。
三、 在虚拟机上搭建调试环境
1. 检查虚拟机上已安装的GDB和python
[admin@local /home/elvis]
$whichgdb
/usr/bin/gdb
[admin@local /home/elvis]
$/usr/bin/gdb-v
GNUgdb (GDB) Red Hat Enterprise Linux (7.0.1-37.el5)
Copyright(C) 2009 Free Software Foundation, Inc.
LicenseGPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
Thisis free software: you are free to change and redistribute it.
Thereis NO WARRANTY, to the extent permitted by law. Type "show copying"
and"show warranty" for details.
ThisGDB was configured as "x86_64-redhat-linux-gnu".
Forbug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>.
[admin@local /home/elvis]
$which python
/usr/bin/python
[admin@local /home/elvis]
$/usr/bin/python-org--version
Python2.5.4
2. 注意事项
l 内核文档建议选择GDB 7.4+,但是实际的编译调试过程中发现让GDB加载python脚本需要auto-load功能,GDB 7.5+以后版本才支持该功能。
l /linux/scripts/gdb/vmlinux-gdb.py脚本使用了python的一个新功能dictionary comprehensions,该功能只能到Python 2.7之后才支持。详情参考https://docs.python.org/2/whatsnew/2.7.html- new-features-added-to-python-2-7-maintenance-releases
l 由于开发机器上现有的Python 2.5.4版本过低,并且安装在非标准目录/usr/xx,在GDB编译过程中会报错,该问题的workaround方法是:
[admin@local /home/elvis/linux]
$mv /usr/bin/python /usr/bin/python-org
[admin@local /home/elvis/linux]
$cp /usr/python-2.7/bin/python /usr/bin/python
该方法只是将Python 2.7替换掉原有的Python。如有其它更好办法,请更新此文档。
3. Build GDB withPython Support
由于开发机上已经安装GDB 7.0.1,为了不影响公用该开发机其它项目的编译,最好自己编译一个仅供自己使用的GDB。这里选择的是支持auto-load功能的GDB 7.5。
首先,编译之前需要检查几个事项:
(1) python是否支持Dictionary Comprehension功能
[admin@local /home/elvis/gdb-7.5]
$python
Python2.7 (r27, May 27 2013, 20:02:53)
[GCC4.1.2 20080704 (Red Hat 4.1.2-46)] on linux2
Type"help", "copyright", "credits" or"license" for more information.
>>>d = {n: True for n in range(5)}
>>>d
{0:True, 1: True, 2: True, 3: True, 4: True}
>>>
如果d正常打印未告警,说明支持Dictionary Comprehension语法。
(2) 编译GDB过程中需要使用到动态链接库libpython2.7.*.so。动态链接库程序ld.so加载动态库时,搜索的是一个缓存文件/etc/ld.so.cache,这是一个二进制文件,用vim打开确认一下路径中包含libpython2.7.so.1.0,如果未包含该动态库,请将路径“/usr/python-2.7/lib/”添加到/etc/ld.so.conf之后,键入命令ldconfig更新缓存文件ld.so.cache。
[admin@local /home/elvis/gdb-7.5]
$sudo ldconfig
(3) Build GDB with Python Support
[admin@local /home/elvis]
$tar zxvf gdb-7.5.tar.gz
$cd gdb-7.5
再次检查GDB编译所需的头文件和链接选项,与目标Python路径是否一致:
[admin@local /home/elvis/gdb-7.5]
$python ./gdb/python/python-config.py--includes
-I/usr/python-2.7/include/python2.7
-I/usr/python-2.7/include/python2.7
[admin@local /home/elvis/gdb-7.5]
$python ./gdb/python/python-config.py--ldflags
-lpthread-ldl -lutil -lm -lpython2.7 -Xlinker -export-dynamic
检查完成之后开始编译:
$mkdirbin
$cdbin/
$../configure--with-python
$make
4. 检查编译后的GDB是否支持linux自带的vmlinux-gdb.py脚本。
[admin@local /home/elvis/linux]
$/home/elvis/gdb-7.5/bin/gdb/gdb
GNU gdb(GDB) 7.5
Copyright(C) 2012 Free Software Foundation, Inc.
LicenseGPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This isfree software: you are free to change and redistribute it.
There isNO WARRANTY, to the extent permitted by law. Type "show copying"
and"show warranty" for details.
This GDBwas configured as "x86_64-unknown-linux-gnu".
For bugreporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>.
(gdb) set debug auto-load on --->To demo “auto-load” function. No need for daily use
(gdb) set auto-load safe-path . --->Set current Directory as safe-path
auto-load:Updating directories of ".".
auto-load:Using directory ".".
auto-load:And canonicalized as "/elvis/linux".
(gdb) file ./build/vmlinux --->Load Linux kernel Symbols
Readingsymbols from /elvis/linux/build/vmlinux...done.
auto-load:Attempted file "/elvis/linux/build/vmlinux-gdb.gdb" does not exist.
auto-load:Expanded $-variables to"/usr/local/lib/debug:/usr/local/share/gdb/auto-load".
auto-load:Searching 'set auto-load scripts-directory' path"$debugdir:$datadir/auto-load".
auto-load:Attempted file "/usr/local/lib/debug/elvis/linux/build/vmlinux-gdb.gdb"does not exist.
auto-load:Attempted file "/usr/local/share/gdb/auto-load/elvis/linux/build/vmlinux-gdb.gdb"does not exist.
auto-load:Attempted file "/elvis/linux/build/vmlinux-gdb.py" exists.
auto-load:Loading Python script "/elvis/linux/build/vmlinux-gdb.py" byextension for objfile "/elvis/linux/build/vmlinux".
auto-load:Matching file "/elvis/linux/build/vmlinux-gdb.py" to pattern"."
auto-load:Not matched - pattern ".".
auto-load:Matching file "/elvis/linux/build/vmlinux-gdb.py" to pattern"/elvis/linux"
auto-load:Matched - file "/elvis/linux" to pattern "/elvis/linux".
auto-load:File "/elvis/linux/build/vmlinux-gdb.py" matches directory"/elvis/linux".
(gdb)apropos lx
functionlx_current -- Return current task
functionlx_module -- Find module by name and return the module variable
functionlx_per_cpu -- Return per-cpu variable
functionlx_task_by_pid -- Find Linux task by PID and return the task_struct variable
functionlx_thread_info -- Calculate Linux thread_info from task variable
lx-dmesg-- Print Linux kernel log buffer
lx-lsmod-- List currently loaded modules
lx-symbols-- (Re-)load symbols of Linux kernel and currently loaded modules
(gdb)
至此,GDB的环境搭建部分已经完成。
四. Qemu虚拟机环境
Qemu环境准备:需要在qemu的启动选项里面加上”-s”即可:
#!/bin/bash
……
echoStarting VM ...
set -x
$TRACE$QEMU $*
-s
-m ${MEM_MB}
-smp cpus=${CPUS}
-nodefconfig -nodefaults -no-user-config
-parallel none
-vga none
-display none
-bootmenu=off
……
最后
以上就是踏实帽子为你收集整理的通过GDB调试内核(Kernel)和模块(Module)一、 需求二、 原理三、 在虚拟机上搭建调试环境四. Qemu虚拟机环境的全部内容,希望文章能够帮你解决通过GDB调试内核(Kernel)和模块(Module)一、 需求二、 原理三、 在虚拟机上搭建调试环境四. Qemu虚拟机环境所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复