Perf抓取CPU热点函数

背景:

为了查询应用运行卡顿的原因,使用perf工具查找哪几个函数占用了较多的CPU资源,然后优化占用CPU资源最多的几个函数。

Perf工具简介

Perf是Linux内核提供的性能分析工具,能够监控CPU性能计数器、跟踪内核和用户态事件,帮助定位热点函数、缓存命中率等问题。它支持多种分析模式,如采样(sampling)、统计(counting)和追踪(tracing)。


安装Perf工具

在大多数Linux发行版中,Perf可通过包管理器安装:

  • Debian/Ubuntu:
    sudo apt install linux-tools-common linux-tools-$(uname -r)
    

  • RHEL/CentOS:
    sudo yum install perf
    

如果遇到版本兼容性问题,需确保内核头文件与当前运行的内核版本一致。


基本使用流程

1. 采样CPU事件

通过perf record采集CPU执行样本,默认监控cycles(CPU时钟周期)事件:

sudo perf record -F 99 -g -p <PID>  # -F 99表示每秒采样99次,-g启用调用栈,-p指定进程ID
sudo perf record -F 99 -g -a        # 监控所有CPU

运行结束后生成perf.data文件。

2. 生成分析报告

使用perf report解析采样数据:

sudo perf report -n --stdio         # 文本模式查看
sudo perf report -g                 # 图形化交互模式

报告会显示热点函数及其调用栈,按CPU占用百分比排序。

3. 统计事件计数

直接统计特定事件的发生次数(不生成详细样本):

sudo perf stat -e cycles,instructions,cache-misses -p <PID>


高级功能

火焰图生成
  1. 使用perf script导出采样数据:
    sudo perf script > out.perf
    

  2. 通过FlameGraph工具生成SVG火焰图:
    git clone https://github.com/brendangregg/FlameGraph
    ./FlameGraph/stackcollapse-perf.pl out.perf | ./FlameGraph/flamegraph.pl > flame.svg
    

    火焰图直观展示函数调用栈宽度与CPU占用比例。
追踪特定函数

监控内核或用户态函数的调用:

sudo perf probe --add 'schedule'          # 添加内核函数追踪点
sudo perf trace -e probe:schedule -p <PID>  # 追踪调用

硬件事件监控

Perf支持多种硬件性能计数器(PMC):

sudo perf record -e branch-misses,LLC-load-misses -a  # 监控分支预测失败、LLC未命中


常见问题

符号表缺失

若报告中函数名显示为十六进制地址,需确保调试符号已安装:

  • 对于应用程序:编译时添加-g选项。
  • 对于内核:安装dbgsym包(Debian)或debuginfo包(RHEL)。
权限问题

部分性能事件需要CAP_PERFMONroot权限,可通过以下命令临时授权:

sudo sysctl kernel.perf_event_paranoid=-1

多线程分析

结合-t选项监控特定线程:

sudo perf record -t <TID> -g -e cycles


示例输出解读

perf report的典型输出片段:

60.12%  program  libc.so.6    [.] malloc
        |
        --- malloc
           |          
            --50.2%-- foo
                      bar

表示malloc占用了60.12%的CPU时间,其中50.2%由foo->bar调用路径触发。


注意事项

  • 采样频率过高(如-F 1000)可能导致显著性能开销。
  • 内核版本差异可能导致部分功能不可用(如eBPF集成)。
  • 虚拟机环境可能限制硬件性能计数器的访问。

通过合理配置事件和采样频率,Perf能够高效定位CPU热点,为性能优化提供数据支撑。

嵌入式工作中需要注意的是,如果终端控制台敲perf命令显示没有这个命令,那么需要自己拉源码编译然后下载到机器中,同时也需要修改内核配置,make kernel_menuconfig->Enable performance events and counters,这是因为 perf 依赖于内核的 perf_events 子系统来采集性能数据,如果内核没有编译支持这个功能,perf 就会报错。

内核未支持,敲perf会报类似的错误:

perf_event_open(..., PERF_FLAG_FD_CLOEXEC) failed with unexpected error 38 (Function not implemented)
...
No CONFIG_PERF_EVENTS=y kernel support configured?

最后总结下常见的perf命令:

perf stat

perf stat用于统计程序运行时的性能事件,如CPU周期、缓存命中率等。示例:

perf stat -e cycles,instructions,cache-misses ./your_program

perf record

perf record用于记录程序运行时的性能数据,生成perf.data文件。示例:

perf record -g ./your_program

perf report

perf report用于分析perf record生成的数据文件。示例:

perf report -n --stdio

perf top

perf top实时显示系统或进程的性能事件,类似于top命令。示例:

perf top -e cycles

perf list

perf list列出当前系统支持的所有性能事件。示例:

perf list

perf annotate

perf annotate对特定函数进行代码级性能分析。示例:

perf annotate -s function_name

perf script

perf script将perf.data转换为可读文本或其他格式。示例:

perf script -F comm,pid,time,event

perf trace

perf trace跟踪系统调用和信号。示例:

perf trace -e nanosleep ./your_program

perf probe

perf probe动态添加跟踪点。示例:

perf probe --add 'schedule'

perf mem

perf mem分析内存访问性能。示例:

perf mem record ./your_program

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值