perf 如何采样内核堆栈?
Posted
技术标签:
【中文标题】perf 如何采样内核堆栈?【英文标题】:How does perf sample kernel stacks? 【发布时间】:2019-01-30 14:52:15 【问题描述】:据我所知 perf 能够为每个进程/线程采样一个完整的调用堆栈,即使它当前位于内核内部。由于我假设 perf 在用户空间中运行,我想知道它如何访问不同进程/线程的堆栈的内核部分。
目的是编写一个应用程序,可以对其他进程/线程的调用堆栈进行采样,即使它们当前位于内核中。
问候
【问题讨论】:
【参考方案1】:perf
由两部分组成。用户空间工具和perf_event_open
系统调用。
通常,堆栈采样是由内核通过系统调用完成的。您可以编写一个应用程序同时使用 perf_event_open
- 默认情况下包括内核示例 (exclude_kernel==0
)。
【讨论】:
根据手册,我必须设置一个 perf_event_attr 结构的参数,然后用 perf_event_open 打开一个文件描述符,然后通过 read 继续读取它。假设我的目标是获取挂起进程的调用堆栈,我应该订阅哪些事件类型以及我将如何解析读取的数据? 可以阅读也可以mmap
。要获取调用堆栈,您可以设置类似attr.sample_type = PERF_SAMPLE_IP | PERF_SAMPLE_TID | PERF_SAMPLE_TIME | PERF_SAMPLE_CPU | PERF_SAMPLE_CALLCHAIN
的内容。例如,您可以使用PERF_TYPE_HARDWARE
// PERF_COUNT_HW_CPU_CYCLES
。
PERF_COUNT_HW_CPU_CYCLES 会产生多少个事件?每次 CPU 做什么?对进程调度事件进行采样会更便宜吗?
录制速率由attr.sample_period
或attr.sample_freq
和attr.freq
相应设置决定。手册页包含所有详细信息。
注意:这是一项相当复杂的工作,我无法在答案中提供完整的教程,但我很乐意回答更多具体问题。以上是关于perf 如何采样内核堆栈?的主要内容,如果未能解决你的问题,请参考以下文章