简介
安装
systemtab
@H_404_6@sudo apt-get install systemtap
直接安装– 源码下载
–
./configure
–
make
–
sudo make -k -i install
内核调试信息
http://ddebs.ubuntu.com/pool/main/l/linux/
uname -r
查询内核版本信息
sudo dpkg -i linux-*_amd64.ddeb
内核源码查询
@H_404_6@http://kernel.ubuntu.com/git/ubuntu/ubuntu-trusty.git/refs/
火焰图
@H_404_6@https://github.com/brendangregg/FlameGraph
./stackcollapse-stap.pl ./trace.txt > trace.out
./flamegraph.pl ./trace.out > trace.svg
firefox ./trace.svg
systemtap 工作原理
systemtap 的核心思想是定义一个事件(event),以及给出处理该事件的句柄(Handler)。当一个特定的事件发生时,内核运行该处理句柄,就像快速调用一个子函数一样,处理完之后恢复到内核原始状态。这里有两个概念:
@H_404_6@Systemtap 工作原理是通过将脚本语句翻译成C语句,编译成内核模块。模块加载之后,将所有探测的事件以钩子的方式挂到内核上,当任何处理器上的某个事件发生时,相应钩子上句柄就会被执行。最后,当systemtap会话结束之后,钩子从内核上取下,移除模块。整个过程用一个命令 stap 就可以完成。
stap 基本语法
1. global变量才能在注入点执行
2. 辅助函数格式 function <name>[:<type>] ( <arg1>[:<type>],... ) { <stmts> }
3. print(str) - Print the value of str.
printf(fmt) - Print a string with formatting similar to the printf function in C.
sprintf(fmt) - Return a string with formatting similar to the sprintf function in C.
strlen(str) - Return the number of characters in str.
isinstr(str1,str2) - Return 1 if the str1 contains the str2.
strtol(str,base) - Convert a numerical value with the specified base stored in a string to an
integer.
exit() - Exit the running script.
probefunc() - Return the name of the function being probed.
execname() - Return the name of the current running process.
pid() - Return the process id of the current process.
pp() - Return current kernel function info.
uid() - Return the user ID of the current process.
cpu() - Return the cpu number the current process is exe
4. 元素存在 if ([4,"hello"] in foo) {}
5. 统计类型
arg<<< 3 # 相当于 arg += b
@count(g_value):所有统计操作的操作次数
@sum(g_value):所有统计操作的操作数的总和
@min(g_value):所有统计操作的操作数的最小值
@max(g_value):所有统计操作的操作数的最大值
@avg(g_value):所有统计操作的操作数的平均值
demo
打印open调用的执行时间
global time
probe syscall.open {
time[tid()] = gettimeofday_ns()
}
probe kernel.function("sys_open").return {
if(time[tid()]) {
printf("sys_open took %d ns to execute %s\n",gettimeofday_ns() - time[tid()],execname())
delete time[tid()]
}
}