perf和火焰图

安装

perf是linux下的一个性能分析工具,本文主要用来分析java热点代码。安装perf和perf-map-agent,perf-map-agent用来生成java方法和perf的映射。

# centos7 install perf
yum install perf
# install perf-map-agent
git clone https://github.com/jvm-profiling-tools/perf-map-agent.git
cd perf-map-agent
# cmake>=2.8.6
yum groupinstall "Development Tools"
yum install make
cmake .
make

分析java应用

查看java进程:

[root@node1 perf-map-agent]# jps -l
28369 simple-consumer-1.0-SNAPSHOT.jar
28951 sun.tools.jps.Jps
28348 simple-provider-1.0-SNAPSHOT.jar

一个prc示例,consumer通过spring boot提供了rest接口,500并发测试。


> 可以看到消费者28369cpu占用较高。

# 每秒99次 -g表示记录调用栈,sleep 30则是持续30秒。
perf record -F 99 -p 28369 -ag -- sleep 30

perf record 查看如下图

一堆看不懂的内核调用:

# 在之前安装的perf-map-agent路径下执行命令生成map文件
# 文件位置: /tmp/perf-28369.map
./bin/create-java-perf-map.sh 28369

应用启动添加jvm参数-XX:+PreserveFramePointer,这个参数支持 perf-map-agent将 perf 监控到的数据翻译成JVM 堆栈信息( Java 8 update 60 build 19)

此时再看perf record

可以看看到java栈信息,还是不够直观,使用FlameGraph生成火焰图:

火焰图

git clone https://github.com/brendangregg/FlameGraph.git
perf script | FlameGraph/stackcollapse-perf.pl | FlameGraph/flamegraph.pl > flameGraph.svg

  • y 轴表示调用栈,每一层都是一个函数。调用栈越深,火焰就越高
  • x 轴表示抽样数,如果一个函数在 x 轴占据的宽度越宽,就表示它被抽到的次数多,即执行的时间长。
  • 不用看颜色深浅,看顶层的哪个函数占据的宽度最大,就表示该函数可能存在性能问题。
    > 示例是在一个虚拟机跑的,网卡是性能瓶颈,从top命令sy的cup占用也可以看出来问题。可以通过 cat /proc/interrupts继续分析。


参考:
[1]. http://www.brendangregg.com/perf.html
[2].http://www.ruanyifeng.com/blog/2017/09/flame-graph.html
[3]. http://www.brendangregg.com/flamegraphs.html

CONTENTS