摘要
火焰圖是分析應用效能問題很好的工具,只是網上的文章都是講述分析 C, C++ 等語言的,對Java 語言描述甚少,此處記錄一下自己使用火焰圖分析Java 棧的過程。
環境
Linux: centos6 jdk: 1.7
步驟
火焰圖是效能大神 brendangregg 創造的,我們使用的指令碼在他的github 上 https://github.com/brendangregg/FlameGraph.git , 將專案clone 到本地,進入到 FlameGraph 資料夾中,建立兩個檔案(檔案來自mik01aj 的gist,稍微修改了一下)
profile.sh:
#!/bin/sh
# Usage: ./profile.sh pid output.txt
PROFILED_PID=$1
OUTPUT_FILE=$2
echo "Getting stacktraces from process $PROFILED_PID... Will stop on ^C or when the process exits."
rm -f "$OUTPUT_FILE"
while true; do
jstack "$PROFILED_PID" >> "$OUTPUT_FILE" && sleep 0.01 || break
done
echo
echo "Done! Stacks saved to $OUTPUT_FILE"
gen.sh:
#!/bin/bash
# Usage: ./gen.sh collected-stacks.txt
TMPSTACKS=/tmp/flamegraph-stacks-collapsed.txt
TMPPALETTE=/tmp/flamegraph-palette.map
./stackcollapse-jstack.pl --no-include-tname $1 > $TMPSTACKS
# 1st run - hot: default
./flamegraph.pl --cp $TMPSTACKS > stacks.svg
# 2nd run - blue: I/O
cp palette.map $TMPPALETTE
cat $TMPPALETTE | grep -v '\.read' | grep -v '\.write' | grep -v 'socketRead' | grep -v 'socketWrite' | grep -v 'socketAccept' > palette.map
./flamegraph.pl --cp --colors=io $TMPSTACKS > stacks.svg
rm -f palette.map
echo "Done! Now see the output in stacks.svg"
然後將stacks.svg 下載到本地,使用瀏覽器開啟即可。
遇到的問題
本來參考了1 想使用perf
來生成取樣資訊,但是安裝了一大堆東西之後,取樣後的資料(取樣指令碼 perf record -F 99 -p 98498 -- sleep 30; ./jmaps
)一直報perf file's data size field is 0 which is unexpected.
, 也沒有找到解決辦法,加上 -v
之後會列印一個 couldn't open /proc/21847/status
的錯誤,不知道為什麼會讀取這個進行的狀態,應該說只讀取取樣程式的狀態就可以了。後來直接使用網上的命令perf record -F 99 -a -- sleep 30; ./jmaps
,可以取樣出來,但是生成的火焰圖無法看,是系統棧與java棧混在一起而且 Java 棧的資訊很模糊,不可用。
參考網址
- 使用linux perf工具生成java程式火焰圖
- Linux下用火焰圖進行效能分析
- perf CPU Sampling
- How to Install perf Tool on CentOS and Ubuntu
- gen.sh, profile.sh