|
1 | 1 | #!/bin/bash |
2 | 2 |
|
3 | 3 | BENCHMARKPATTERN="*benchmark*" |
4 | | -MKDIR=/bin/mkdir |
5 | | -BASENAME=/usr/bin/basename |
6 | | -DIRNAME=/usr/bin/dirname |
7 | | -FIND=/usr/bin/find |
8 | | -SED=/bin/sed |
9 | | -PERF=/usr/bin/perf |
10 | | -STACKCOLLASE=stackcollapse-perf.pl |
11 | | -FLAMEGRAPG=flamegraph.pl |
12 | | - |
13 | | -usage() |
14 | | -{ |
15 | | - echo |
16 | | - echo "--------------------------FlameGraph Generator---------------------------" |
17 | | - echo |
18 | | - echo "Usage: $0 [OPTION]..." |
19 | | - echo "This script generates FlameGraphs for benchmarks !!!" |
20 | | - echo "OPTIONS" |
21 | | - echo " -b, --benchmarkfile path Location of ROOT benchmark file" |
22 | | - echo " -a, --all Create all benchmarks." |
23 | | - echo " -d, --builddir path Create all benchmarks." |
24 | | - echo " -h, --help Display this help and exit" |
| 4 | +MKDIR=$(which mkdir) |
| 5 | +BASENAME=$(which basename) |
| 6 | +DIRNAME=$(which dirname) |
| 7 | +FIND=$(which find) |
| 8 | +SED=$(which sed) |
| 9 | +PERF=$(which perf) |
| 10 | +STACKCOLLAPSE=stackcollapse-perf.pl |
| 11 | +FLAMEGRAPH=flamegraph.pl |
| 12 | + |
| 13 | +usage() { |
| 14 | + echo |
| 15 | + echo "--------------------------FlameGraph Generator---------------------------" |
| 16 | + echo |
| 17 | + echo "Usage: $0 [OPTION]..." |
| 18 | + echo "This script generates FlameGraphs for benchmarks !!!" |
| 19 | + echo "OPTIONS" |
| 20 | + echo " -d, --builddir path Create all benchmarks." |
| 21 | + echo " -b, --benchmarkfile path Location of ROOT benchmark file" |
| 22 | + echo " -a, --all Create all benchmarks." |
| 23 | + echo " -c, --cpu Generate CPU FlameGraphs" |
| 24 | + echo " -m, --memory Generate Memory FlameGraphs" |
| 25 | + echo " -h, --help Display this help and exit" |
25 | 26 | } |
26 | 27 |
|
27 | | -usage_short() |
28 | | -{ |
29 | | -# echo "FlameGraph Generator" |
30 | | - echo "Usage: $0 -d | --builddir path [-b | --benchmarkfile filepath] [-a | --all] [-h | --help]" |
31 | | - exit 1 |
| 28 | +usage_short() { |
| 29 | + echo "Usage: $0 -d | --builddir path [-b | --benchmarkfile filepath] [-a | --all] [-c | --cpu] [-m | --memory] [-h | --help]" |
| 30 | + exit 1 |
32 | 31 | } |
33 | 32 |
|
34 | | -get_bm_fn() |
35 | | -{ |
36 | | - if [ ! -f $1 ] ; then |
37 | | - echo "Can't find the benchmark file" |
38 | | - exit 1 |
39 | | - else |
40 | | - bm_fn_full=$1 |
41 | | - bm_fn=`$BASENAME $bm_fn_full` |
42 | | - fi |
| 33 | +get_bm_fn() { |
| 34 | + if [ ! -f $1 ]; then |
| 35 | + echo "Can't find the benchmark file" |
| 36 | + exit 1 |
| 37 | + else |
| 38 | + bm_fn_full=$1 |
| 39 | + bm_fn=$($BASENAME $bm_fn_full) |
| 40 | + fi |
43 | 41 | } |
44 | 42 |
|
45 | | -get_build_dir() |
46 | | -{ |
47 | | - if [ ! -d $1 ] ; then |
48 | | - echo "Can't find the build directory. Exiting..." |
49 | | - exit 1 |
50 | | - else |
51 | | - build_dir=$1 |
52 | | - flamegraph_base_dir=$build_dir/FlameGraph |
53 | | - fi |
| 43 | +get_build_dir() { |
| 44 | + if [ ! -d $1 ]; then |
| 45 | + echo "Can't find the build directory. Exiting..." |
| 46 | + exit 1 |
| 47 | + else |
| 48 | + build_dir=$1 |
| 49 | + flamegraph_base_dir=$build_dir/FlameGraph |
| 50 | + fi |
54 | 51 | } |
55 | 52 |
|
56 | | -get_bm_fn_interactive() |
57 | | -{ |
58 | | - read -p "Enter benchmark filename: " bm_fn_full |
59 | | - if [ -z $bm_fn_full ] ; then |
60 | | - echo "You did not enter any filename. Exiting..." |
61 | | - exit 1 |
62 | | - fi |
63 | | - get_bm_fn $bm_fn_full |
| 53 | +get_bm_fn_interactive() { |
| 54 | + read -p "Enter benchmark filename: " bm_fn_full |
| 55 | + if [ -z $bm_fn_full ]; then |
| 56 | + echo "You did not enter any filename. Exiting..." |
| 57 | + exit 1 |
| 58 | + fi |
| 59 | + get_bm_fn $bm_fn_full |
64 | 60 | } |
65 | 61 |
|
66 | | -perf_record() |
67 | | -{ |
68 | | - $PERF record -F 50 --call-graph dwarf $1 --benchmark_filter=${2}$ |
| 62 | +perf_record_cpu() { |
| 63 | + $PERF record -F 50 --call-graph dwarf $1 --benchmark_filter=${2}$ |
69 | 64 | } |
70 | 65 |
|
71 | | -perf_script() |
72 | | -{ |
73 | | - $PERF script | stackcollapse-perf.pl | flamegraph.pl --title $1 > $2.svg |
| 66 | +perf_script_cpu() { |
| 67 | + $PERF script | stackcollapse-perf.pl | flamegraph.pl --title $1 >$2.svg |
74 | 68 | } |
75 | 69 |
|
76 | | -perf_rec_scr() |
77 | | -{ |
78 | | - perf_record $1 $2 |
79 | | - perf_script $2 $3 |
80 | | - # $PERF record --call-graph dwarf $1 | $PERF script | $STACKCOLLASE | $FLAMEGRAPG > $2 |
| 70 | +perf_record_mem() { |
| 71 | + $PERF record -F 50 -e page-faults --call-graph dwarf $1 --benchmark_filter=${2}$ |
81 | 72 | } |
82 | 73 |
|
83 | | -get_bm_files() |
84 | | -{ |
85 | | - bm_file_list=`$FIND $build_dir/root -iname "$BENCHMARKPATTERN" |grep -v "CMakeFiles"` |
| 74 | +perf_script_mem() { |
| 75 | + $PERF script | stackcollapse-perf.pl | flamegraph.pl --color=mem --title=$1 --countname="pages" >$2.svg |
86 | 76 | } |
87 | 77 |
|
88 | | -run_bm() |
89 | | -{ |
90 | | - for bm_fn_full in $bm_file_list |
91 | | - do |
92 | | - bm_fn=`$BASENAME $bm_fn_full` |
93 | | - bm_dn=`$DIRNAME $bm_fn_full` |
94 | | - bm_path=`echo "$bm_dn" | $SED -n "s|^$build_dir/||p"` |
95 | | - bm_sub_list=`$bm_fn_full --benchmark_list_tests` |
96 | | - outputdir_full=${flamegraph_base_dir}/$bm_path/$bm_fn |
97 | | - $MKDIR -p $outputdir_full |
98 | | - if [ $? -ne 0 ]; then |
99 | | - echo "Can't create directory $1. Exiting..." |
100 | | - exit 1 |
101 | | - fi |
102 | | - for bm in $bm_sub_list |
103 | | - do |
104 | | - bm_modified_fn=`echo "$bm" | $SED "s|[/:]|-|g"` #replacing all "/" and ":" with "-" |
105 | | - perf_rec_scr $bm_fn_full $bm ${outputdir_full}/${bm_modified_fn}_FlameGraph |
106 | | - done |
107 | | - done |
| 78 | +perf_rec_scr_cpu() { |
| 79 | + perf_record_cpu $1 $2 |
| 80 | + perf_script_cpu $2 $3 |
| 81 | +} |
| 82 | + |
| 83 | +perf_rec_scr_mem() { |
| 84 | + perf_record_mem $1 $2 |
| 85 | + perf_script_mem $2 $3 |
108 | 86 | } |
109 | 87 |
|
| 88 | +get_bm_files() { |
| 89 | + bm_file_list=$($FIND $build_dir/root -iname "$BENCHMARKPATTERN" | grep -v "CMakeFiles\|pyroot\|interpreter\|.csv") |
| 90 | +} |
| 91 | + |
| 92 | +run_bm() { |
| 93 | + for bm_fn_full in $bm_file_list; do |
| 94 | + bm_fn=$($BASENAME $bm_fn_full) |
| 95 | + bm_dn=$($DIRNAME $bm_fn_full) |
| 96 | + bm_path=$(echo "$bm_dn" | $SED -n "s|^$build_dir/||p") |
| 97 | + bm_sub_list=$($bm_fn_full --benchmark_list_tests) |
| 98 | + flamegraph_base_dir_mem=${flamegraph_base_dir}/FlameGraph_Memory |
| 99 | + flamegraph_base_dir_cpu=${flamegraph_base_dir}/FlameGraph_CPU |
| 100 | + outputdir_full_mem=${flamegraph_base_dir_mem}/$bm_path/$bm_fn |
| 101 | + outputdir_full_cpu=${flamegraph_base_dir_cpu}/$bm_path/$bm_fn |
| 102 | + if [ "$memory" = "y" ]; then |
| 103 | + $MKDIR -p $outputdir_full_mem |
| 104 | + if [ $? -ne 0 ]; then |
| 105 | + echo "Can't create directory $1. Exiting..." |
| 106 | + exit 1 |
| 107 | + fi |
| 108 | + fi |
| 109 | + if [ "$cpu" = "y" ]; then |
| 110 | + $MKDIR -p $outputdir_full_cpu |
| 111 | + if [ $? -ne 0 ]; then |
| 112 | + echo "Can't create directory $1. Exiting..." |
| 113 | + exit 1 |
| 114 | + fi |
| 115 | + fi |
| 116 | + for bm in $bm_sub_list; do |
| 117 | + bm_modified_fn=$(echo "$bm" | $SED "s|[/:]|-|g") #replacing all "/" and ":" with "-" |
| 118 | + if [ "$cpu"="y" ]; then |
| 119 | + perf_rec_scr_cpu $bm_fn_full $bm ${outputdir_full_cpu}/${bm_modified_fn}_FlameGraph |
| 120 | + fi |
| 121 | + if [ "$memory"="y" ]; then |
| 122 | + perf_rec_scr_mem $bm_fn_full $bm ${outputdir_full_mem}/${bm_modified_fn}_FlameGraph |
| 123 | + fi |
| 124 | + done |
| 125 | + done |
| 126 | +} |
110 | 127 |
|
111 | 128 | ##### Main ##### |
112 | 129 |
|
113 | 130 | [ $# -eq 0 ] && usage_short |
114 | 131 |
|
115 | 132 | while [ $# -gt 0 ]; do |
116 | | - case "$1" in |
117 | | - -b | --benchmarkfile ) |
118 | | - shift |
119 | | - get_bm_fn $1 |
120 | | - ;; |
121 | | - -d | --builddir ) |
122 | | - shift |
123 | | - get_build_dir $1 |
124 | | - ;; |
125 | | - |
126 | | - -a | --all ) |
127 | | - all=y |
128 | | - ;; |
129 | | - -h | --help ) |
130 | | - usage |
131 | | - exit |
132 | | - ;; |
133 | | - * ) |
134 | | - usage |
135 | | - exit 1 |
136 | | - ;; |
137 | | - esac |
138 | | - shift |
| 133 | + case "$1" in |
| 134 | + -b | --benchmarkfile) |
| 135 | + shift |
| 136 | + get_bm_fn $1 |
| 137 | + ;; |
| 138 | + -d | --builddir) |
| 139 | + shift |
| 140 | + get_build_dir $1 |
| 141 | + ;; |
| 142 | + |
| 143 | + -a | --all) |
| 144 | + all=y |
| 145 | + ;; |
| 146 | + -c | --cpu) |
| 147 | + cpu=y |
| 148 | + ;; |
| 149 | + -m | --memory) |
| 150 | + memory=y |
| 151 | + ;; |
| 152 | + -h | --help) |
| 153 | + usage |
| 154 | + exit |
| 155 | + ;; |
| 156 | + *) |
| 157 | + usage |
| 158 | + exit 1 |
| 159 | + ;; |
| 160 | + esac |
| 161 | + shift |
139 | 162 | done |
140 | 163 |
|
141 | | -if [ -z $build_dir ] ; then |
142 | | - echo "************* Rootbench Build dir is mandatory *****************" |
143 | | - usage_short |
| 164 | +if [ -z $build_dir ]; then |
| 165 | + echo "************* Rootbench Build dir is mandatory *****************" |
| 166 | + usage_short |
144 | 167 | fi |
145 | 168 |
|
146 | | -if [ "$all" = "y" ] ; then |
147 | | - get_bm_files |
148 | | - run_bm |
149 | | -else |
150 | | - if [ ! -z $bm_fn_full ] ; then |
151 | | - bm_file_list=$bm_fn_full |
| 169 | +if [ -z $cpu -a -z $memory ]; then |
| 170 | + echo "************* Please specify the type of the FlameGraphs *****************" |
| 171 | + usage_short |
| 172 | +fi |
| 173 | + |
| 174 | +if [ "$all" = "y" ]; then |
| 175 | + get_bm_files |
152 | 176 | run_bm |
153 | | - fi |
| 177 | +else |
| 178 | + if [ ! -z $bm_fn_full ]; then |
| 179 | + bm_file_list=$bm_fn_full |
| 180 | + run_bm |
| 181 | + fi |
154 | 182 | fi |
155 | 183 |
|
156 | 184 | exit $? |
0 commit comments