perf report: Cache failed lookups of inlined frames
[linux-2.6-microblaze.git] / tools / perf / util / srcline.c
1 #include <inttypes.h>
2 #include <stdio.h>
3 #include <stdlib.h>
4 #include <string.h>
5
6 #include <linux/kernel.h>
7
8 #include "util/dso.h"
9 #include "util/util.h"
10 #include "util/debug.h"
11 #include "util/callchain.h"
12 #include "srcline.h"
13
14 #include "symbol.h"
15
16 bool srcline_full_filename;
17
18 static const char *dso__name(struct dso *dso)
19 {
20         const char *dso_name;
21
22         if (dso->symsrc_filename)
23                 dso_name = dso->symsrc_filename;
24         else
25                 dso_name = dso->long_name;
26
27         if (dso_name[0] == '[')
28                 return NULL;
29
30         if (!strncmp(dso_name, "/tmp/perf-", 10))
31                 return NULL;
32
33         return dso_name;
34 }
35
36 static int inline_list__append(struct symbol *symbol, char *srcline,
37                                struct inline_node *node)
38 {
39         struct inline_list *ilist;
40
41         ilist = zalloc(sizeof(*ilist));
42         if (ilist == NULL)
43                 return -1;
44
45         ilist->symbol = symbol;
46         ilist->srcline = srcline;
47
48         if (callchain_param.order == ORDER_CALLEE)
49                 list_add_tail(&ilist->list, &node->val);
50         else
51                 list_add(&ilist->list, &node->val);
52
53         return 0;
54 }
55
56 /* basename version that takes a const input string */
57 static const char *gnu_basename(const char *path)
58 {
59         const char *base = strrchr(path, '/');
60
61         return base ? base + 1 : path;
62 }
63
64 static char *srcline_from_fileline(const char *file, unsigned int line)
65 {
66         char *srcline;
67
68         if (!file)
69                 return NULL;
70
71         if (!srcline_full_filename)
72                 file = gnu_basename(file);
73
74         if (asprintf(&srcline, "%s:%u", file, line) < 0)
75                 return NULL;
76
77         return srcline;
78 }
79
80 #ifdef HAVE_LIBBFD_SUPPORT
81
82 /*
83  * Implement addr2line using libbfd.
84  */
85 #define PACKAGE "perf"
86 #include <bfd.h>
87
88 struct a2l_data {
89         const char      *input;
90         u64             addr;
91
92         bool            found;
93         const char      *filename;
94         const char      *funcname;
95         unsigned        line;
96
97         bfd             *abfd;
98         asymbol         **syms;
99 };
100
101 static int bfd_error(const char *string)
102 {
103         const char *errmsg;
104
105         errmsg = bfd_errmsg(bfd_get_error());
106         fflush(stdout);
107
108         if (string)
109                 pr_debug("%s: %s\n", string, errmsg);
110         else
111                 pr_debug("%s\n", errmsg);
112
113         return -1;
114 }
115
116 static int slurp_symtab(bfd *abfd, struct a2l_data *a2l)
117 {
118         long storage;
119         long symcount;
120         asymbol **syms;
121         bfd_boolean dynamic = FALSE;
122
123         if ((bfd_get_file_flags(abfd) & HAS_SYMS) == 0)
124                 return bfd_error(bfd_get_filename(abfd));
125
126         storage = bfd_get_symtab_upper_bound(abfd);
127         if (storage == 0L) {
128                 storage = bfd_get_dynamic_symtab_upper_bound(abfd);
129                 dynamic = TRUE;
130         }
131         if (storage < 0L)
132                 return bfd_error(bfd_get_filename(abfd));
133
134         syms = malloc(storage);
135         if (dynamic)
136                 symcount = bfd_canonicalize_dynamic_symtab(abfd, syms);
137         else
138                 symcount = bfd_canonicalize_symtab(abfd, syms);
139
140         if (symcount < 0) {
141                 free(syms);
142                 return bfd_error(bfd_get_filename(abfd));
143         }
144
145         a2l->syms = syms;
146         return 0;
147 }
148
149 static void find_address_in_section(bfd *abfd, asection *section, void *data)
150 {
151         bfd_vma pc, vma;
152         bfd_size_type size;
153         struct a2l_data *a2l = data;
154
155         if (a2l->found)
156                 return;
157
158         if ((bfd_get_section_flags(abfd, section) & SEC_ALLOC) == 0)
159                 return;
160
161         pc = a2l->addr;
162         vma = bfd_get_section_vma(abfd, section);
163         size = bfd_get_section_size(section);
164
165         if (pc < vma || pc >= vma + size)
166                 return;
167
168         a2l->found = bfd_find_nearest_line(abfd, section, a2l->syms, pc - vma,
169                                            &a2l->filename, &a2l->funcname,
170                                            &a2l->line);
171
172         if (a2l->filename && !strlen(a2l->filename))
173                 a2l->filename = NULL;
174 }
175
176 static struct a2l_data *addr2line_init(const char *path)
177 {
178         bfd *abfd;
179         struct a2l_data *a2l = NULL;
180
181         abfd = bfd_openr(path, NULL);
182         if (abfd == NULL)
183                 return NULL;
184
185         if (!bfd_check_format(abfd, bfd_object))
186                 goto out;
187
188         a2l = zalloc(sizeof(*a2l));
189         if (a2l == NULL)
190                 goto out;
191
192         a2l->abfd = abfd;
193         a2l->input = strdup(path);
194         if (a2l->input == NULL)
195                 goto out;
196
197         if (slurp_symtab(abfd, a2l))
198                 goto out;
199
200         return a2l;
201
202 out:
203         if (a2l) {
204                 zfree((char **)&a2l->input);
205                 free(a2l);
206         }
207         bfd_close(abfd);
208         return NULL;
209 }
210
211 static void addr2line_cleanup(struct a2l_data *a2l)
212 {
213         if (a2l->abfd)
214                 bfd_close(a2l->abfd);
215         zfree((char **)&a2l->input);
216         zfree(&a2l->syms);
217         free(a2l);
218 }
219
220 #define MAX_INLINE_NEST 1024
221
222 static struct symbol *new_inline_sym(struct dso *dso,
223                                      struct symbol *base_sym,
224                                      const char *funcname)
225 {
226         struct symbol *inline_sym;
227         char *demangled = NULL;
228
229         if (dso) {
230                 demangled = dso__demangle_sym(dso, 0, funcname);
231                 if (demangled)
232                         funcname = demangled;
233         }
234
235         if (base_sym && strcmp(funcname, base_sym->name) == 0) {
236                 /* reuse the real, existing symbol */
237                 inline_sym = base_sym;
238                 /* ensure that we don't alias an inlined symbol, which could
239                  * lead to double frees in inline_node__delete
240                  */
241                 assert(!base_sym->inlined);
242         } else {
243                 /* create a fake symbol for the inline frame */
244                 inline_sym = symbol__new(base_sym ? base_sym->start : 0,
245                                          base_sym ? base_sym->end : 0,
246                                          base_sym ? base_sym->binding : 0,
247                                          funcname);
248                 if (inline_sym)
249                         inline_sym->inlined = 1;
250         }
251
252         free(demangled);
253
254         return inline_sym;
255 }
256
257 static int inline_list__append_dso_a2l(struct dso *dso,
258                                        struct inline_node *node,
259                                        struct symbol *sym)
260 {
261         struct a2l_data *a2l = dso->a2l;
262         struct symbol *inline_sym = new_inline_sym(dso, sym, a2l->funcname);
263         char *srcline = NULL;
264
265         if (a2l->filename)
266                 srcline = srcline_from_fileline(a2l->filename, a2l->line);
267
268         return inline_list__append(inline_sym, srcline, node);
269 }
270
271 static int addr2line(const char *dso_name, u64 addr,
272                      char **file, unsigned int *line, struct dso *dso,
273                      bool unwind_inlines, struct inline_node *node,
274                      struct symbol *sym)
275 {
276         int ret = 0;
277         struct a2l_data *a2l = dso->a2l;
278
279         if (!a2l) {
280                 dso->a2l = addr2line_init(dso_name);
281                 a2l = dso->a2l;
282         }
283
284         if (a2l == NULL) {
285                 pr_warning("addr2line_init failed for %s\n", dso_name);
286                 return 0;
287         }
288
289         a2l->addr = addr;
290         a2l->found = false;
291
292         bfd_map_over_sections(a2l->abfd, find_address_in_section, a2l);
293
294         if (!a2l->found)
295                 return 0;
296
297         if (unwind_inlines) {
298                 int cnt = 0;
299
300                 if (node && inline_list__append_dso_a2l(dso, node, sym))
301                         return 0;
302
303                 while (bfd_find_inliner_info(a2l->abfd, &a2l->filename,
304                                              &a2l->funcname, &a2l->line) &&
305                        cnt++ < MAX_INLINE_NEST) {
306
307                         if (a2l->filename && !strlen(a2l->filename))
308                                 a2l->filename = NULL;
309
310                         if (node != NULL) {
311                                 if (inline_list__append_dso_a2l(dso, node, sym))
312                                         return 0;
313                                 // found at least one inline frame
314                                 ret = 1;
315                         }
316                 }
317         }
318
319         if (file) {
320                 *file = a2l->filename ? strdup(a2l->filename) : NULL;
321                 ret = *file ? 1 : 0;
322         }
323
324         if (line)
325                 *line = a2l->line;
326
327         return ret;
328 }
329
330 void dso__free_a2l(struct dso *dso)
331 {
332         struct a2l_data *a2l = dso->a2l;
333
334         if (!a2l)
335                 return;
336
337         addr2line_cleanup(a2l);
338
339         dso->a2l = NULL;
340 }
341
342 static struct inline_node *addr2inlines(const char *dso_name, u64 addr,
343                                         struct dso *dso, struct symbol *sym)
344 {
345         struct inline_node *node;
346
347         node = zalloc(sizeof(*node));
348         if (node == NULL) {
349                 perror("not enough memory for the inline node");
350                 return NULL;
351         }
352
353         INIT_LIST_HEAD(&node->val);
354         node->addr = addr;
355
356         addr2line(dso_name, addr, NULL, NULL, dso, true, node, sym);
357         return node;
358 }
359
360 #else /* HAVE_LIBBFD_SUPPORT */
361
362 static int filename_split(char *filename, unsigned int *line_nr)
363 {
364         char *sep;
365
366         sep = strchr(filename, '\n');
367         if (sep)
368                 *sep = '\0';
369
370         if (!strcmp(filename, "??:0"))
371                 return 0;
372
373         sep = strchr(filename, ':');
374         if (sep) {
375                 *sep++ = '\0';
376                 *line_nr = strtoul(sep, NULL, 0);
377                 return 1;
378         }
379
380         return 0;
381 }
382
383 static int addr2line(const char *dso_name, u64 addr,
384                      char **file, unsigned int *line_nr,
385                      struct dso *dso __maybe_unused,
386                      bool unwind_inlines __maybe_unused,
387                      struct inline_node *node __maybe_unused,
388                      struct symbol *sym __maybe_unused)
389 {
390         FILE *fp;
391         char cmd[PATH_MAX];
392         char *filename = NULL;
393         size_t len;
394         int ret = 0;
395
396         scnprintf(cmd, sizeof(cmd), "addr2line -e %s %016"PRIx64,
397                   dso_name, addr);
398
399         fp = popen(cmd, "r");
400         if (fp == NULL) {
401                 pr_warning("popen failed for %s\n", dso_name);
402                 return 0;
403         }
404
405         if (getline(&filename, &len, fp) < 0 || !len) {
406                 pr_warning("addr2line has no output for %s\n", dso_name);
407                 goto out;
408         }
409
410         ret = filename_split(filename, line_nr);
411         if (ret != 1) {
412                 free(filename);
413                 goto out;
414         }
415
416         *file = filename;
417
418 out:
419         pclose(fp);
420         return ret;
421 }
422
423 void dso__free_a2l(struct dso *dso __maybe_unused)
424 {
425 }
426
427 static struct inline_node *addr2inlines(const char *dso_name, u64 addr,
428                                         struct dso *dso __maybe_unused,
429                                         struct symbol *sym)
430 {
431         FILE *fp;
432         char cmd[PATH_MAX];
433         struct inline_node *node;
434         char *filename = NULL;
435         size_t len;
436         unsigned int line_nr = 0;
437
438         scnprintf(cmd, sizeof(cmd), "addr2line -e %s -i %016"PRIx64,
439                   dso_name, addr);
440
441         fp = popen(cmd, "r");
442         if (fp == NULL) {
443                 pr_err("popen failed for %s\n", dso_name);
444                 return NULL;
445         }
446
447         node = zalloc(sizeof(*node));
448         if (node == NULL) {
449                 perror("not enough memory for the inline node");
450                 goto out;
451         }
452
453         INIT_LIST_HEAD(&node->val);
454         node->addr = addr;
455
456         while (getline(&filename, &len, fp) != -1) {
457                 char *srcline;
458
459                 if (filename_split(filename, &line_nr) != 1) {
460                         free(filename);
461                         goto out;
462                 }
463
464                 srcline = srcline_from_fileline(filename, line_nr);
465                 if (inline_list__append(sym, srcline, node) != 0)
466                         goto out;
467
468                 filename = NULL;
469         }
470
471 out:
472         pclose(fp);
473
474         return node;
475 }
476
477 #endif /* HAVE_LIBBFD_SUPPORT */
478
479 /*
480  * Number of addr2line failures (without success) before disabling it for that
481  * dso.
482  */
483 #define A2L_FAIL_LIMIT 123
484
485 char *__get_srcline(struct dso *dso, u64 addr, struct symbol *sym,
486                   bool show_sym, bool show_addr, bool unwind_inlines)
487 {
488         char *file = NULL;
489         unsigned line = 0;
490         char *srcline;
491         const char *dso_name;
492
493         if (!dso->has_srcline)
494                 goto out;
495
496         dso_name = dso__name(dso);
497         if (dso_name == NULL)
498                 goto out;
499
500         if (!addr2line(dso_name, addr, &file, &line, dso,
501                        unwind_inlines, NULL, sym))
502                 goto out;
503
504         srcline = srcline_from_fileline(file, line);
505         free(file);
506
507         if (!srcline)
508                 goto out;
509
510         dso->a2l_fails = 0;
511
512         return srcline;
513
514 out:
515         if (dso->a2l_fails && ++dso->a2l_fails > A2L_FAIL_LIMIT) {
516                 dso->has_srcline = 0;
517                 dso__free_a2l(dso);
518         }
519
520         if (!show_addr)
521                 return (show_sym && sym) ?
522                             strndup(sym->name, sym->namelen) : NULL;
523
524         if (sym) {
525                 if (asprintf(&srcline, "%s+%" PRIu64, show_sym ? sym->name : "",
526                                         addr - sym->start) < 0)
527                         return SRCLINE_UNKNOWN;
528         } else if (asprintf(&srcline, "%s[%" PRIx64 "]", dso->short_name, addr) < 0)
529                 return SRCLINE_UNKNOWN;
530         return srcline;
531 }
532
533 void free_srcline(char *srcline)
534 {
535         if (srcline && strcmp(srcline, SRCLINE_UNKNOWN) != 0)
536                 free(srcline);
537 }
538
539 char *get_srcline(struct dso *dso, u64 addr, struct symbol *sym,
540                   bool show_sym, bool show_addr)
541 {
542         return __get_srcline(dso, addr, sym, show_sym, show_addr, false);
543 }
544
545 struct inline_node *dso__parse_addr_inlines(struct dso *dso, u64 addr,
546                                             struct symbol *sym)
547 {
548         const char *dso_name;
549
550         dso_name = dso__name(dso);
551         if (dso_name == NULL)
552                 return NULL;
553
554         return addr2inlines(dso_name, addr, dso, sym);
555 }
556
557 void inline_node__delete(struct inline_node *node)
558 {
559         struct inline_list *ilist, *tmp;
560
561         list_for_each_entry_safe(ilist, tmp, &node->val, list) {
562                 list_del_init(&ilist->list);
563                 free_srcline(ilist->srcline);
564                 /* only the inlined symbols are owned by the list */
565                 if (ilist->symbol && ilist->symbol->inlined)
566                         symbol__delete(ilist->symbol);
567                 free(ilist);
568         }
569
570         free(node);
571 }
572
573 void inlines__tree_insert(struct rb_root *tree, struct inline_node *inlines)
574 {
575         struct rb_node **p = &tree->rb_node;
576         struct rb_node *parent = NULL;
577         const u64 addr = inlines->addr;
578         struct inline_node *i;
579
580         while (*p != NULL) {
581                 parent = *p;
582                 i = rb_entry(parent, struct inline_node, rb_node);
583                 if (addr < i->addr)
584                         p = &(*p)->rb_left;
585                 else
586                         p = &(*p)->rb_right;
587         }
588         rb_link_node(&inlines->rb_node, parent, p);
589         rb_insert_color(&inlines->rb_node, tree);
590 }
591
592 struct inline_node *inlines__tree_find(struct rb_root *tree, u64 addr)
593 {
594         struct rb_node *n = tree->rb_node;
595
596         while (n) {
597                 struct inline_node *i = rb_entry(n, struct inline_node,
598                                                  rb_node);
599
600                 if (addr < i->addr)
601                         n = n->rb_left;
602                 else if (addr > i->addr)
603                         n = n->rb_right;
604                 else
605                         return i;
606         }
607
608         return NULL;
609 }
610
611 void inlines__tree_delete(struct rb_root *tree)
612 {
613         struct inline_node *pos;
614         struct rb_node *next = rb_first(tree);
615
616         while (next) {
617                 pos = rb_entry(next, struct inline_node, rb_node);
618                 next = rb_next(&pos->rb_node);
619                 rb_erase(&pos->rb_node, tree);
620                 inline_node__delete(pos);
621         }
622 }