ftrace中的Max Stack Tracer和Function_Profiler

(1) Max Stack Tracer 的使用
这个 tracer 记录内核函数的堆栈使用情况,需要使能CONFIG_STACK_TRACER,用户可以使用如下命令打开该 tracer:

# echo 1 > /proc/sys/kernel/stack_tracer_enabled
从此,ftrace 便留心记录内核函数的堆栈使用。输出在 stack_trace 文件中:
Depth Size Location (13 entries)
----- ---- --------
0) 3120 120 __accumulate_pelt_segments+0x8/0xd0
1) 3000 80 update_nohz_stats+0x10c/0x320
2) 2920 416 find_busiest_group+0x4e4/0xab0
3) 2504 272 load_balance+0x168/0x990
4) 2232 160 pick_next_task_fair+0x3ac/0x7e0
5) 2072 144 __schedule+0x108/0x950
6) 1928 16 schedule+0x2c/0x80
7) 1912 112 schedule_hrtimeout_range_clock+0xa0/0x130
8) 1800 16 poll_schedule_timeout.constprop.4+0x3c/0x70
9) 1784 624 do_select+0x45c/0x670
10) 1160 384 core_sys_select+0x194/0x320
11) 776 144 sys_pselect6+0x200/0x2b0
12) 632 632 syscall_common+0x24/0x34
从上例中可以看到内核堆栈最满的情况如下,有 13 层函数调用,堆栈使用大小为 3120 字节。此外还可以在 Location 这列中看到整个的
calling stack 情况。这在某些情况下,可以提供额外的 debug 信息,帮助开发人员定位问题。

(2)Ftrace_Function_Profiler
函数分析器提供有关内核函数调用的统计信息,适用于探索哪些内核函数正在使用并确定哪些是最慢的,我经常使用函数分析器作为了解给定工作负载的内核代码执行的起点,
特别是因为它高效且开销相对较低。使用它,我可以使用更昂贵的每个事件跟踪来识别要分析的函数。 它需要CONFIG_FUNCTION_PROFILER=y

函数分析器通过在每个内核函数开始时使用 compiled-in profiling calls 来工作。例如 gcc 的 -pg 选项,它插入 mcount() 调用以与 gprof 一起使用。
从 gcc 4.6 版开始,这个 mcount() 调用现在是 fentry()。 为每个内核函数添加调用看起来会花费大量开销,这对于可能很少使用的东西来说是一个问题,
但开销问题已经解决:当不使用时,这些调用通常会替换为快速 nop 指令, 并且仅在需要时切换到 fentry() 调用。

备注: 当开始 “ftracing” 一个内核函数的时候,该函数的代码实际上就已经发生变化了。内核将在程序集中插入一些额外的指令,使得函数调用时可以随时通知追踪程序。

下面演示了使用 /sys 中的 tracefs 接口的函数分析器。 作为参考,下面显示了函数分析器的原始未启用状态:
root@2k1000:/sys/kernel/debug/tracing# cat function_profile_enabled
0

这些列显示函数名称 (Function、后面的数字代表cpu)、调用次数 (Hit)、函数中的总时间 (Time)、平均函数时间 (Avg) 和标准偏差 (s^2)。

在分析期间,向分析的函数添加了少量开销。 如果 set_ftrace_filter 留空,所有内核函数都会被分析(正如我们之前看到的初始状态警告的那样:“所有函数已启用”)。
使用分析器时请记住这一点,并尝试使用函数过滤器来限制开销。

posted on 2023-02-01 17:59  lh03061238  阅读(117)  评论(0编辑  收藏  举报

导航