aboutsummaryrefslogtreecommitdiffstats
path: root/tools/perf/builtin-report.c
diff options
context:
space:
mode:
Diffstat (limited to 'tools/perf/builtin-report.c')
-rw-r--r--tools/perf/builtin-report.c82
1 files changed, 63 insertions, 19 deletions
diff --git a/tools/perf/builtin-report.c b/tools/perf/builtin-report.c
index 3d8c52220f1f..72d58421223d 100644
--- a/tools/perf/builtin-report.c
+++ b/tools/perf/builtin-report.c
@@ -59,12 +59,28 @@ static struct perf_header *header;
59 59
60static u64 sample_type; 60static u64 sample_type;
61 61
62static size_t ipchain__fprintf_graph_line(FILE *fp, int depth, int depth_mask) 62
63static size_t
64callchain__fprintf_left_margin(FILE *fp, int left_margin)
65{
66 int i;
67 int ret;
68
69 ret = fprintf(fp, " ");
70
71 for (i = 0; i < left_margin; i++)
72 ret += fprintf(fp, " ");
73
74 return ret;
75}
76
77static size_t ipchain__fprintf_graph_line(FILE *fp, int depth, int depth_mask,
78 int left_margin)
63{ 79{
64 int i; 80 int i;
65 size_t ret = 0; 81 size_t ret = 0;
66 82
67 ret += fprintf(fp, "%s", " "); 83 ret += callchain__fprintf_left_margin(fp, left_margin);
68 84
69 for (i = 0; i < depth; i++) 85 for (i = 0; i < depth; i++)
70 if (depth_mask & (1 << i)) 86 if (depth_mask & (1 << i))
@@ -79,12 +95,12 @@ static size_t ipchain__fprintf_graph_line(FILE *fp, int depth, int depth_mask)
79static size_t 95static size_t
80ipchain__fprintf_graph(FILE *fp, struct callchain_list *chain, int depth, 96ipchain__fprintf_graph(FILE *fp, struct callchain_list *chain, int depth,
81 int depth_mask, int count, u64 total_samples, 97 int depth_mask, int count, u64 total_samples,
82 int hits) 98 int hits, int left_margin)
83{ 99{
84 int i; 100 int i;
85 size_t ret = 0; 101 size_t ret = 0;
86 102
87 ret += fprintf(fp, "%s", " "); 103 ret += callchain__fprintf_left_margin(fp, left_margin);
88 for (i = 0; i < depth; i++) { 104 for (i = 0; i < depth; i++) {
89 if (depth_mask & (1 << i)) 105 if (depth_mask & (1 << i))
90 ret += fprintf(fp, "|"); 106 ret += fprintf(fp, "|");
@@ -123,7 +139,8 @@ static void init_rem_hits(void)
123 139
124static size_t 140static size_t
125__callchain__fprintf_graph(FILE *fp, struct callchain_node *self, 141__callchain__fprintf_graph(FILE *fp, struct callchain_node *self,
126 u64 total_samples, int depth, int depth_mask) 142 u64 total_samples, int depth, int depth_mask,
143 int left_margin)
127{ 144{
128 struct rb_node *node, *next; 145 struct rb_node *node, *next;
129 struct callchain_node *child; 146 struct callchain_node *child;
@@ -164,7 +181,8 @@ __callchain__fprintf_graph(FILE *fp, struct callchain_node *self,
164 * But we keep the older depth mask for the line seperator 181 * But we keep the older depth mask for the line seperator
165 * to keep the level link until we reach the last child 182 * to keep the level link until we reach the last child
166 */ 183 */
167 ret += ipchain__fprintf_graph_line(fp, depth, depth_mask); 184 ret += ipchain__fprintf_graph_line(fp, depth, depth_mask,
185 left_margin);
168 i = 0; 186 i = 0;
169 list_for_each_entry(chain, &child->val, list) { 187 list_for_each_entry(chain, &child->val, list) {
170 if (chain->ip >= PERF_CONTEXT_MAX) 188 if (chain->ip >= PERF_CONTEXT_MAX)
@@ -172,11 +190,13 @@ __callchain__fprintf_graph(FILE *fp, struct callchain_node *self,
172 ret += ipchain__fprintf_graph(fp, chain, depth, 190 ret += ipchain__fprintf_graph(fp, chain, depth,
173 new_depth_mask, i++, 191 new_depth_mask, i++,
174 new_total, 192 new_total,
175 cumul); 193 cumul,
194 left_margin);
176 } 195 }
177 ret += __callchain__fprintf_graph(fp, child, new_total, 196 ret += __callchain__fprintf_graph(fp, child, new_total,
178 depth + 1, 197 depth + 1,
179 new_depth_mask | (1 << depth)); 198 new_depth_mask | (1 << depth),
199 left_margin);
180 node = next; 200 node = next;
181 } 201 }
182 202
@@ -190,17 +210,19 @@ __callchain__fprintf_graph(FILE *fp, struct callchain_node *self,
190 210
191 ret += ipchain__fprintf_graph(fp, &rem_hits, depth, 211 ret += ipchain__fprintf_graph(fp, &rem_hits, depth,
192 new_depth_mask, 0, new_total, 212 new_depth_mask, 0, new_total,
193 remaining); 213 remaining, left_margin);
194 } 214 }
195 215
196 return ret; 216 return ret;
197} 217}
198 218
219
199static size_t 220static size_t
200callchain__fprintf_graph(FILE *fp, struct callchain_node *self, 221callchain__fprintf_graph(FILE *fp, struct callchain_node *self,
201 u64 total_samples) 222 u64 total_samples, int left_margin)
202{ 223{
203 struct callchain_list *chain; 224 struct callchain_list *chain;
225 bool printed = false;
204 int i = 0; 226 int i = 0;
205 int ret = 0; 227 int ret = 0;
206 228
@@ -208,17 +230,27 @@ callchain__fprintf_graph(FILE *fp, struct callchain_node *self,
208 if (chain->ip >= PERF_CONTEXT_MAX) 230 if (chain->ip >= PERF_CONTEXT_MAX)
209 continue; 231 continue;
210 232
211 if (!i++ && sort_by_sym_first) 233 if (!i++ && sort__first_dimension == SORT_SYM)
212 continue; 234 continue;
213 235
236 if (!printed) {
237 ret += callchain__fprintf_left_margin(fp, left_margin);
238 ret += fprintf(fp, "|\n");
239 ret += callchain__fprintf_left_margin(fp, left_margin);
240 ret += fprintf(fp, "---");
241
242 left_margin += 3;
243 printed = true;
244 } else
245 ret += callchain__fprintf_left_margin(fp, left_margin);
246
214 if (chain->sym) 247 if (chain->sym)
215 ret += fprintf(fp, " %s\n", chain->sym->name); 248 ret += fprintf(fp, " %s\n", chain->sym->name);
216 else 249 else
217 ret += fprintf(fp, " %p\n", 250 ret += fprintf(fp, " %p\n", (void *)(long)chain->ip);
218 (void *)(long)chain->ip);
219 } 251 }
220 252
221 ret += __callchain__fprintf_graph(fp, self, total_samples, 1, 1); 253 ret += __callchain__fprintf_graph(fp, self, total_samples, 1, 1, left_margin);
222 254
223 return ret; 255 return ret;
224} 256}
@@ -251,7 +283,7 @@ callchain__fprintf_flat(FILE *fp, struct callchain_node *self,
251 283
252static size_t 284static size_t
253hist_entry_callchain__fprintf(FILE *fp, struct hist_entry *self, 285hist_entry_callchain__fprintf(FILE *fp, struct hist_entry *self,
254 u64 total_samples) 286 u64 total_samples, int left_margin)
255{ 287{
256 struct rb_node *rb_node; 288 struct rb_node *rb_node;
257 struct callchain_node *chain; 289 struct callchain_node *chain;
@@ -271,7 +303,8 @@ hist_entry_callchain__fprintf(FILE *fp, struct hist_entry *self,
271 break; 303 break;
272 case CHAIN_GRAPH_ABS: /* Falldown */ 304 case CHAIN_GRAPH_ABS: /* Falldown */
273 case CHAIN_GRAPH_REL: 305 case CHAIN_GRAPH_REL:
274 ret += callchain__fprintf_graph(fp, chain, total_samples); 306 ret += callchain__fprintf_graph(fp, chain, total_samples,
307 left_margin);
275 case CHAIN_NONE: 308 case CHAIN_NONE:
276 default: 309 default:
277 break; 310 break;
@@ -316,8 +349,19 @@ hist_entry__fprintf(FILE *fp, struct hist_entry *self, u64 total_samples)
316 349
317 ret += fprintf(fp, "\n"); 350 ret += fprintf(fp, "\n");
318 351
319 if (callchain) 352 if (callchain) {
320 hist_entry_callchain__fprintf(fp, self, total_samples); 353 int left_margin = 0;
354
355 if (sort__first_dimension == SORT_COMM) {
356 se = list_first_entry(&hist_entry__sort_list, typeof(*se),
357 list);
358 left_margin = se->width ? *se->width : 0;
359 left_margin -= thread__comm_len(self->thread);
360 }
361
362 hist_entry_callchain__fprintf(fp, self, total_samples,
363 left_margin);
364 }
321 365
322 return ret; 366 return ret;
323} 367}