systemtap调试linux内核源码,内核调试工具SystemTap:适合懒人的printk替代品
SystemTap是一个Linux调试和性能分析工具,可用于应用层和内核层的分析,但主要侧重内核层。SystemTab可以在不修改内核代码、不重复编译内核、不重启机器的情况下,收集运行内核的信息并使信息可视化。调试人员可以利用它绘制函数调用关系图,打印寄存器信息和调用栈,输出内核中指定变量(可以是局部变量)。它如同一个更加方便prink,方便调试人员观察内核行为,诊断错误异常,分析系统性能。在YAVIS开发过程中,我们使用SystemTap分析包发送和接收情况,并分析通信性能瓶颈。
SystemTap工作流程
SystemTap使用了Kprobe技术探测内核信息,辅以Relayfs向用户传递消息。
SystemTap首先将SystemTap脚本文件翻译成C源文件。这个C源文件实际上是一个内核模块,实现了脚本文件中描述的功能。接着SystemTap编译源文件获得二进制模块文件,并动态加载模块。模块被载入运行内核后,会报告脚本文件中指定的一些事件。事件会触发脚本文件中编写的处理函数,执行相关操作。一般操作内容是:收集所需信息,并通过标准输出打印给用户。SystemTap会话结束于用户发出中断信号,即Ctrl + C,内核模块将随之被安全卸载。
SystemTap提供了一些内置函数,帮助我们快速开发测试脚本。常用的内置函数如:
print(str) - 打印str的值
printf(fmt) - 如同C语言的printf函数
probefunc() - 返回当前探测函数的函数名
execname() - 返回当前进程的名字
pid() - 返回当前进程ID
uid() - 返回当前进程用户ID
cpu() - 返回运行当前进程的CPU号
另外一些内置功能以Tapset的形式出现。Tapset相当于SystemTap的库。它提供的功能不仅仅是函数,还包括一些预定义的探测点,如:
timer.ms(N) - 每N毫秒探测一次(用于性能测试)
begin - 探测模块加载时执行一次
当然,用户也可以开发自己的Tapset。
SystemTap的使用
在CentOS中SystemTap可以用下面命令安装升级:
sudo yum installsystemtapsystemtap-runtime
编写脚本后,使用这个命令执行:
stap
注意:如果探测的是模块,要确保模块被复制到/lib/modules//中,否则脚本解析时会在module处出错。
SystemTap脚本语言
SystemTap语言是一种与C语言和awk语言类似的脚本语言。限于篇幅,这里并不系统地介绍SystemTap语言,而是结合毕业设计的调试场景,使用例子说明SystemTap的语法特征和编程结构。
#!/usr/bin/stap
probe module("yavis").function("*").call {
printf("%s -> %s\n", thread_indent(1), probefunc())
}
probe module("yavis").function("*").return {
printf("%s -> %s\n", thread_indent(-1), probefunc());
}
上述代码的功能是输出YAVIS的代码调用关系图。第一行描述脚本采用的解释器是stap程序。第二行表示在yavis模块中所有函数中插入探针,并在这些函数调用时触发第三行的代码。第三行代码向标准输出打印一串信息,信息包括当前函数的名字,由内置的probefunc收集。第五至第七行代码与上面的类似,只是在函数返回时触发。这样,所有YAVIS模块的函数在调用时输出函数名,返回时再次输出函数名,同时由内置的thread_indent函数负责自动的缩进,最终绘制了整个YAVIS模块的函数调用关系图。
#!/usr/bin/stap
probe module("yavis").function("yavis_poll") {
if ($revt->type == 0) {
printf("-- package received --\n")
printf("revt.msg_len = %d\n", $revt->msg_len)
for (i = 0; i < $revt->msg_len; i++) {
printf("%x", $revt->rbuff[i])
}
printf("\n")
} else if ($sevt->type == 0) {
printf("-- package sent --\n");
}
}
probe module("yavis").function("yavis_tx") {
printf("-- sending package --\n");
printf("skb->len = %d\n", $skb->len)
for (j = 0; j < $skb->len; j++) {
printf("%x", $skb->data[j])
}
printf("\n")
}
上面这段脚本可以让我们在发送和接收过程中查看数据。注意结构体类型的数据,无论指针与否,一律使用->方式访问成员变量。
附注
systemtap可由包管理器直接安装。但是想探测较新版本的内核,建议手动编译git仓库中的最新版本systemtap。当然由于systemtap开发相对内核开发有些许置后,所以最新的systemtap一般没法探测最新版本的内核。具体能不能,留意stap --version命令的输出。
参考
[1] SystemTap: Instrumenting the Linux Kernel for Analyzing Performance and Functional Problems. IBM, 2009.
systemtap调试linux内核源码,内核调试工具SystemTap:适合懒人的printk替代品相关推荐
- 手机电脑自适应导航源码php,自适应各终端懒人网址导航源码 v2.0
自适应各终端懒人网址导航源码. V2.0版本是在原1.8版本的基础上修复和增加了些功能.推荐直接使用新版本,舍弃旧版本,后期会继续不定期更新. 测试环境: 宝塔Nginx -Tengine2.2.3的 ...
- java clone 源码_Java Clone方法之懒人实现
在Java的Object类中定义了(protected)clone()方法,如果自己的类需要clone方法的话需要实现Cloneable接口,并重写clone()方法和将方法访问级别改为(public ...
- 【转载】ubuntu下linux内核源码阅读工具和调试方法总结
http://blog.chinaunix.net/space.php?uid=20940095&do=blog&cuid=2377369 一 linux内核源码阅读工具 window ...
- SUSE Linux Enterprise Server 安装内核源码及部署crash调试环境,分析内核崩溃文件(基于sles 15.2)
实验环境: yg-net-static:~ # uname -a Linux yg-net-static 5.3.18-22-default #1 SMP Wed Jun 3 12:16:43 UTC ...
- Linux内核源码分析--内核启动之(3)Image内核启动(C语言部分)(Linux-3.0 ARMv7) 【转】...
原文地址:Linux内核源码分析--内核启动之(3)Image内核启动(C语言部分)(Linux-3.0 ARMv7) 作者:tekkamanninja 转自:http://blog.chinauni ...
- Linux内核移植之一:内核源码结构与Makefile分析
内容来自 韦东山<嵌入式Linux应用开发完全手册> 一.内核介绍 1.版本及其特点 Linux内核的版本号可以从源代码的顶层目录下的Makefile中看到,比如下面几行它们构成了Linu ...
- android 修改编译内核源码 对抗反调试
0×00 写在前面 攻防对立.程序调试与反调试之间的对抗是一个永恒的主题.在安卓逆向工程实践中,通过修改和编译安卓内核源码来对抗反调试是一种常见的方法.但网上关于此类的资料比较少,且都是基于AOSP ...
- 深入分析Linux内核源码oss.org.cn/kernel-book/
本html页面地址:http://oss.org.cn/kernel-book/ 深入分析Linux内核源码 前言 第一章 走进linux 1.1 GNU与Linux的成长 1.2 L ...
- ubuntu下wget下载Linux内核源码、make生成.config文件
根据资料,如果要调试Linux内核源码,需要自己编译内核源码:原因是,一般下载的内核并不是为调试而编译的,要在编译时开启 "Compile the kernel with debug inf ...
最新文章
- iOS开发-UISwipeGestureRecognizer滑动手势
- 配置DATAGUARD 时关于 LOG_FILE_NAME_CONVERT配置错误的解决
- 如何使用Java 8流快速替换列表中的元素
- JVM虚拟机-Class文件之魔数
- Android 原生 MediaPlayer 和 MediaCodec 的区别和联系(二)
- 别动我的代码!聊聊那些代码保护的艺术
- Google全球服务器根域名的IP地址
- c语言中一些公用的方法
- jQuery支持移动触摸设备的Lightbox插件
- 不知道前端课程学什么?这份完整的web前端课程大纲分享给你
- c语言中compar的用法,compare的用法知识整理
- easyUI动态加载combobox
- [Bullet3]常见物体和初始化
- 5分钟搭建私人Java博客系统——Tale
- java合并果子_合并果子(经典优先队列)
- PS教程:如何拼图调色出高大上的作品
- 强化学习--蒙特卡洛法
- 上传并下载excel表格
- vr虚拟现实技术的前景!对未来发展带来有利的趋势吗?
- 爬虫实战4:爬取猫眼电影排名Top100的详细数据保存到csv文件
热门文章
- 二叉树的创建及各种遍历
- mui toast自定义样式
- 【面试刷题复习】更新中 2021.8.30
- doris历程_Doris简史-为分析而生的11年
- [08001] Could not create connection to database server. Attempted reconnect 3 times. Giving up.解决办法
- 基于Python3-Pygame的植物大战僵尸小游戏
- No module named ‘win32gui‘ 的解决方法(踩坑之旅)
- WSL2安装GUI界面与音视频
- android预览界面显示不全,Android SurfaceView Camera 预览显示不全(画面拉伸)
- 盛科交换机配置命令_cisco2960交换机 清除配置的命令