0%

抓ftrace

ftrace是一个非常好用的调试工具,特别是在调试性能相关的问题时。这里简单记录一下如何抓ftrace。

普通方法抓取ftrace

有关ftrace的介绍,可以参考官方文档ftrace。一般是使用如下命令来抓ftrace:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
cd /sys/kernel/debug/tracing/
# 关闭trace,并清空相关数据
echo 0 > tracing_on
echo > set_event
echo > trace
# 设置要抓取的event,根据实际需要更改
# 所有可用的event可以 cat available_events
echo "sched" >> set_event
echo "irq" >> set_event
# 设置buff,越大能抓的log越多,但越占用内存空间。如果log的大小超过buff,则覆盖最开始的log
# 注意这是每个CPU核心的buffer大小,实际使用的内存空间要乘以核心数
# 也可以 cat buffer_total_size_kb 查看总buffer大小
echo 20480 > buffer_size_kb
# 开启抓ftrace
echo 1 > tracing_on
# 复现到bug后停止
echo 0 > tracing_on
# 保存log
cat trace > /path/to/ftrace.log

但在实际的debug实践中,发行buffer的大小不太好控制。buffer设置太小,log容易被覆盖。但buffer设置太大,会占用较多的内存空间,影响其他程序的运行。而且一些嵌入式设备,内存很小。

trace-cmd

trace-cmd是ftrace的前端应用程序,其官网是trace-cmd.org/,源代码在trace-cmd.git

安装

对于常用的Linux发行版本,可以使用直接包管理器安装。例如Ubuntu使用如下命令安装:

1
sudo apt-get install trace-cmd

交叉编译

对于嵌入式Linux,一般来说需要交叉编译。可以参考如下命令:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
# 安装交叉编译工具链,或直接使用BSP提供的工具链
sudo apt-get install gcc-arm-linux-gnueabi
export CC=arm-linux-gnueabi-gcc
export CROSS_COMPILE=arm-linux-gnueabi-

# 创建相关目录
mkdir ~/trace
cd ~/trace

# 编译 libtraceevent
git clone https://git.kernel.org/pub/scm/libs/libtrace/libtraceevent.git
cd libtraceevent
make
make DESTDIR=~/trace/install install
sed -i -e 's@prefix=/usr/local@prefix=/home/pk/trace/install/usr/local@g' \
~/trace/install/usr/local/lib/x86_64-linux-gnu/pkgconfig/libtraceevent.pc

# 编译 libtracefs
cd ~/trace
git clone https://git.kernel.org/pub/scm/libs/libtrace/libtracefs.git
cd libtracefs
export PKG_CONFIG_PATH=~/trace/install/usr/local/lib/x86_64-linux-gnu/pkgconfig
make
make DESTDIR=~/trace/install install
sed -i -e 's@prefix=/usr/local@prefix=/home/pk/trace/install/usr/local@g' \
~/trace/install/usr/local/lib/x86_64-linux-gnu/pkgconfig/libtracefs.pc

# 编译trace-cmd
git clone https://git.kernel.org/pub/scm/utils/trace-cmd/trace-cmd.git
LDFLAGS=-static make
make DESTDIR=~/trace/install install

参考:交叉编译trace-cmd

子命令

trace-cmd支持的子命令如下。比较常用的有record、reset、report、stat、list。每个子命令都有很多选项,可以用命令trace-cmd command -h查看。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
trace-cmd version 2.9.1 (not-a-git-repo)

usage:
trace-cmd [COMMAND] ...

commands:
record - record a trace into a trace.dat file
set - set a ftrace configuration parameter
start - start tracing without recording into a file
extract - extract a trace from the kernel
stop - stop the kernel from recording trace data
restart - restart the kernel trace data recording
show - show the contents of the kernel tracing buffer
reset - disable all kernel tracing and clear the trace buffers
clear - clear the trace buffers
report - read out the trace stored in a trace.dat file
stream - Start tracing and read the output directly
profile - Start profiling and read the output directly
hist - show a histogram of the trace.dat information
stat - show the status of the running tracing (ftrace) system
split - parse a trace.dat file into smaller file(s)
options - list the plugin options available for trace-cmd report
listen - listen on a network socket for trace clients
agent - listen on a vsocket for trace clients
setup-guest - create FIFOs for tracing guest VMs
list - list the available events, plugins or options
restore - restore a crashed record
snapshot - take snapshot of running trace
stack - output, enable or disable kernel stack tracing
check-events - parse trace event formats
dump - read out the meta data from a trace file

trace-cmd示例

首先使用record子命令抓ftrace,然后用report命令转化为文本格式。也可以不转换,直接导入KernelShark分析。

1
2
3
4
5
6
7
8
9
10
11
12
13
# -m 设置buff的大小,-e 设置event,
# -o 输出到指定文件。对于空间比较小的嵌入式设备,可以保存到外挂的U盘
pi@pi4b:~ $ sudo trace-cmd record -m 40960 -e 'sched_*' -e 'irq_*' -o ./ftrace.dat
Hit Ctrl^C to stop recording
^CCPU0 data recorded at offset=0x5f7000
29159424 bytes in size
CPU1 data recorded at offset=0x21c6000
22093824 bytes in size
CPU2 data recorded at offset=0x36d8000
35000320 bytes in size
CPU3 data recorded at offset=0x5839000
39243776 bytes in size
pi@pi4b:~ $ trace-cmd report -i ftrace.dat > ftrace.log