4. ftrace的挂载与接口:debugfs/tracefs的挂载,核心文件节点详解
ftrace 作为内核内置的跟踪器,其用户态交互接口主要通过虚拟文件系统(VFS)暴露。正确挂载 debugfs 或 tracefs 是使用 ftrace 的第一步。本章将详细解析挂载流程、核心文件节点的功能及其在异常定位中的实际用途。
4.1 文件系统挂载:debugfs 与 tracefs
早期内核版本中,ftrace 完全依赖于 debugfs。从内核 3.x 开始,ftrace 拥有了独立的 tracefs,专门用于管理跟踪相关文件,避免了与 debugfs 中其他调试信息的混杂。
| 特性 | debugfs | tracefs |
|---|---|---|
| 挂载点 | /sys/kernel/debug |
/sys/kernel/tracing |
| 依赖 | 需内核开启 CONFIG_DEBUG_FS |
需内核开启 CONFIG_TRACING |
| 文件内容 | 包含所有调试信息(gpio、clk、regmap 等) | 仅包含 ftrace 相关接口文件 |
| 推荐用法 | 兼容旧脚本,或需要同时访问其他 debugfs 节点 | 新系统首选,结构清晰,权限管理更独立 |
# 挂载 tracefs(推荐)
mount -t tracefs tracefs /sys/kernel/tracing
# 挂载 debugfs(兼容方式)
mount -t debugfs debugfs /sys/kernel/debug
# 此时 ftrace 文件位于 /sys/kernel/debug/tracing
挂载成功后,所有 ftrace 控制文件将出现在 /sys/kernel/tracing/ 目录下。如果使用 debugfs,则路径为 /sys/kernel/debug/tracing/。以下所有接口说明均以 /sys/kernel/tracing/ 为基准。
4.2 核心文件节点详解
ftrace 的接口文件数量众多,但异常定位中最常用的核心节点不超过 10 个。下面按照“配置 -> 过滤 -> 启停 -> 读取”的流程逐一解析。
4.2.1 available_tracers:可用跟踪器列表
该文件为只读,列出当前内核编译支持的跟踪器类型。读取该文件可以快速确认内核是否包含了所需的跟踪功能。
# cat /sys/kernel/tracing/available_tracers
function_graph function nop
常见跟踪器说明:
- nop:空跟踪器,不记录任何事件,用于关闭跟踪。
- function:函数调用跟踪器,记录每个内核函数的调用入口。
- function_graph:函数调用图跟踪器,记录函数的调用链、嵌套深度和执行时间。
function_graph 未出现在列表中,说明内核未开启 CONFIG_FUNCTION_GRAPH_TRACER,此时无法使用函数调用图功能进行异常定位。
4.2.2 current_tracer:当前激活的跟踪器
读写文件,用于设置或查询当前正在使用的跟踪器。写入 function_graph 即可激活函数调用图跟踪。
# 设置当前跟踪器为 function_graph
echo function_graph > /sys/kernel/tracing/current_tracer
# 验证设置
# cat /sys/kernel/tracing/current_tracer
function_graph
4.2.3 set_ftrace_filter:函数过滤白名单
这是异常定位中最强大的过滤接口。通过写入函数名或通配符,可以精确控制哪些函数被跟踪,从而大幅降低跟踪噪声。
| 操作 | 命令示例 | 效果 |
|---|---|---|
| 添加单个函数 | echo do_sys_open > set_ftrace_filter |
仅跟踪 do_sys_open |
| 添加通配符 | echo 'ext4_*' > set_ftrace_filter |
跟踪所有以 ext4_ 开头的函数 |
| 追加过滤 | echo do_sys_open >> set_ftrace_filter |
在已有过滤列表中添加新函数 |
| 清空过滤 | echo > set_ftrace_filter |
移除所有过滤,跟踪所有函数(慎用) |
function_graph 会跟踪内核中所有函数的调用,导致系统严重卡顿甚至触发 hung task 检测。在异常定位时,务必先通过 set_ftrace_filter 缩小跟踪范围。
4.2.4 set_ftrace_notrace:函数黑名单
与 set_ftrace_filter 相反,该文件用于排除不需要跟踪的函数。常用于跳过一些高频调用函数(如 __do_softirq、ktime_get),以减少跟踪数据量。
# 排除 ktime_get 和本地时钟中断处理函数
echo 'ktime_get' > set_ftrace_notrace
echo 'hrtimer_interrupt' >> set_ftrace_notrace
4.2.5 trace:跟踪输出缓冲区
只读文件,以人类可读的文本格式输出当前跟踪缓冲区的内容。这是异常定位时最常查看的文件。
# cat /sys/kernel/tracing/trace
# tracer: function_graph
#
# CPU DURATION FUNCTION CALLS
# | | | | | | |
0) 0.125 us | do_sys_open();
0) 0.250 us | get_unused_fd_flags();
0) 0.375 us | do_filp_open();
0) 0.500 us | path_openat();
0) 0.625 us | get_empty_filp();
0) 1.000 us | __alloc_file();
0) 0.125 us | mnt_want_write();
0) 0.250 us | do_dentry_open();
0) 0.375 us | ext4_file_open();
0) 0.500 us | generic_file_open();
0) 0.625 us | mnt_drop_write();
0) 0.750 us | fd_install();
0) 1.500 us | } /* path_openat */
0) 2.000 us | } /* do_filp_open */
0) 2.500 us | } /* do_sys_open */
4.2.6 tracing_on:跟踪总开关
写入 0 或 1 控制跟踪的启停。与 current_tracer 不同,tracing_on 只控制数据是否写入缓冲区,而不卸载跟踪器。
# 停止跟踪(保留缓冲区内容)
echo 0 > /sys/kernel/tracing/tracing_on
# 读取当前缓冲区
cat /sys/kernel/tracing/trace
# 清空缓冲区并重新开始跟踪
echo 0 > /sys/kernel/tracing/trace
echo 1 > /sys/kernel/tracing/tracing_on
4.2.7 trace_options:跟踪选项配置
通过读写该文件,可以调整跟踪输出的格式和内容。异常定位中常用的选项包括:
funcgraph-proc:在输出中显示进程名和 PID。funcgraph-duration:显示函数执行耗时(默认开启)。funcgraph-abstime:显示绝对时间戳。funcgraph-overhead:标记耗时过长的函数。
# 启用进程信息显示
echo funcgraph-proc > /sys/kernel/tracing/trace_options
# 启用绝对时间戳
echo funcgraph-abstime >> /sys/kernel/tracing/trace_options
4.3 核心接口工作流程
下图展示了 ftrace 核心接口在异常定位中的协作关系:
4.4 实战:一次完整的异常定位配置序列
假设我们需要定位 ext4_file_open 函数在打开文件时的调用链和耗时,完整的配置序列如下:
# 1. 挂载 tracefs(如果尚未挂载)
mount -t tracefs tracefs /sys/kernel/tracing
# 2. 设置跟踪器为 function_graph
echo function_graph > /sys/kernel/tracing/current_tracer
# 3. 配置输出选项:显示进程名和绝对时间戳
echo funcgraph-proc > /sys/kernel/tracing/trace_options
echo funcgraph-abstime >> /sys/kernel/tracing/trace_options
# 4. 设置过滤:只跟踪 ext4_file_open 及其子调用
echo ext4_file_open > /sys/kernel/tracing/set_ftrace_filter
# 5. 清空旧缓冲区
echo 0 > /sys/kernel/tracing/trace
# 6. 确保跟踪已启动
echo 1 > /sys/kernel/tracing/tracing_on
# 7. 执行目标操作(例如打开一个 ext4 文件系统上的文件)
# 此处为模拟操作,实际场景中由应用程序触发
# 8. 停止跟踪
echo 0 > /sys/kernel/tracing/tracing_on
# 9. 读取跟踪结果
cat /sys/kernel/tracing/trace
function_graph 会尝试跟踪所有内核函数,导致系统响应变慢,甚至触发内核软锁检测(soft lockup)。在异常定位时,始终遵循“先过滤,后跟踪”的原则。
4.5 接口文件速查表
| 文件节点 | 访问权限 | 核心作用 | 异常定位中的典型用途 |
|---|---|---|---|
available_tracers |
只读 | 列出支持的跟踪器 | 确认 function_graph 是否可用 |
current_tracer |
读写 | 设置/查询当前跟踪器 | 激活 function_graph |
set_ftrace_filter |
读写 | 函数白名单过滤 | 缩小跟踪范围,聚焦可疑函数 |
set_ftrace_notrace |
读写 | 函数黑名单过滤 | 排除高频干扰函数 |
trace |
只读 | 输出跟踪缓冲区 | 查看函数调用图与耗时 |
tracing_on |
读写 | 跟踪启停开关 | 控制数据采集的起止 |
trace_options |
读写 | 配置输出格式 | 添加进程名、时间戳等信息 |