sh: select ARCH_NO_SYSDEV_OPS.
[pandora-kernel.git] / tools / perf / util / probe-finder.c
1 /*
2  * probe-finder.c : C expression to kprobe event converter
3  *
4  * Written by Masami Hiramatsu <mhiramat@redhat.com>
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
19  *
20  */
21
22 #include <sys/utsname.h>
23 #include <sys/types.h>
24 #include <sys/stat.h>
25 #include <fcntl.h>
26 #include <errno.h>
27 #include <stdio.h>
28 #include <unistd.h>
29 #include <getopt.h>
30 #include <stdlib.h>
31 #include <string.h>
32 #include <stdarg.h>
33 #include <ctype.h>
34 #include <dwarf-regs.h>
35
36 #include <linux/bitops.h>
37 #include "event.h"
38 #include "debug.h"
39 #include "util.h"
40 #include "symbol.h"
41 #include "probe-finder.h"
42
43 /* Kprobe tracer basic type is up to u64 */
44 #define MAX_BASIC_TYPE_BITS     64
45
46 /*
47  * Compare the tail of two strings.
48  * Return 0 if whole of either string is same as another's tail part.
49  */
50 static int strtailcmp(const char *s1, const char *s2)
51 {
52         int i1 = strlen(s1);
53         int i2 = strlen(s2);
54         while (--i1 >= 0 && --i2 >= 0) {
55                 if (s1[i1] != s2[i2])
56                         return s1[i1] - s2[i2];
57         }
58         return 0;
59 }
60
61 /* Line number list operations */
62
63 /* Add a line to line number list */
64 static int line_list__add_line(struct list_head *head, int line)
65 {
66         struct line_node *ln;
67         struct list_head *p;
68
69         /* Reverse search, because new line will be the last one */
70         list_for_each_entry_reverse(ln, head, list) {
71                 if (ln->line < line) {
72                         p = &ln->list;
73                         goto found;
74                 } else if (ln->line == line)    /* Already exist */
75                         return 1;
76         }
77         /* List is empty, or the smallest entry */
78         p = head;
79 found:
80         pr_debug("line list: add a line %u\n", line);
81         ln = zalloc(sizeof(struct line_node));
82         if (ln == NULL)
83                 return -ENOMEM;
84         ln->line = line;
85         INIT_LIST_HEAD(&ln->list);
86         list_add(&ln->list, p);
87         return 0;
88 }
89
90 /* Check if the line in line number list */
91 static int line_list__has_line(struct list_head *head, int line)
92 {
93         struct line_node *ln;
94
95         /* Reverse search, because new line will be the last one */
96         list_for_each_entry(ln, head, list)
97                 if (ln->line == line)
98                         return 1;
99
100         return 0;
101 }
102
103 /* Init line number list */
104 static void line_list__init(struct list_head *head)
105 {
106         INIT_LIST_HEAD(head);
107 }
108
109 /* Free line number list */
110 static void line_list__free(struct list_head *head)
111 {
112         struct line_node *ln;
113         while (!list_empty(head)) {
114                 ln = list_first_entry(head, struct line_node, list);
115                 list_del(&ln->list);
116                 free(ln);
117         }
118 }
119
120 /* Dwarf FL wrappers */
121 static char *debuginfo_path;    /* Currently dummy */
122
123 static const Dwfl_Callbacks offline_callbacks = {
124         .find_debuginfo = dwfl_standard_find_debuginfo,
125         .debuginfo_path = &debuginfo_path,
126
127         .section_address = dwfl_offline_section_address,
128
129         /* We use this table for core files too.  */
130         .find_elf = dwfl_build_id_find_elf,
131 };
132
133 /* Get a Dwarf from offline image */
134 static Dwarf *dwfl_init_offline_dwarf(int fd, Dwfl **dwflp, Dwarf_Addr *bias)
135 {
136         Dwfl_Module *mod;
137         Dwarf *dbg = NULL;
138
139         if (!dwflp)
140                 return NULL;
141
142         *dwflp = dwfl_begin(&offline_callbacks);
143         if (!*dwflp)
144                 return NULL;
145
146         mod = dwfl_report_offline(*dwflp, "", "", fd);
147         if (!mod)
148                 goto error;
149
150         dbg = dwfl_module_getdwarf(mod, bias);
151         if (!dbg) {
152 error:
153                 dwfl_end(*dwflp);
154                 *dwflp = NULL;
155         }
156         return dbg;
157 }
158
159 #if _ELFUTILS_PREREQ(0, 148)
160 /* This method is buggy if elfutils is older than 0.148 */
161 static int __linux_kernel_find_elf(Dwfl_Module *mod,
162                                    void **userdata,
163                                    const char *module_name,
164                                    Dwarf_Addr base,
165                                    char **file_name, Elf **elfp)
166 {
167         int fd;
168         const char *path = kernel_get_module_path(module_name);
169
170         pr_debug2("Use file %s for %s\n", path, module_name);
171         if (path) {
172                 fd = open(path, O_RDONLY);
173                 if (fd >= 0) {
174                         *file_name = strdup(path);
175                         return fd;
176                 }
177         }
178         /* If failed, try to call standard method */
179         return dwfl_linux_kernel_find_elf(mod, userdata, module_name, base,
180                                           file_name, elfp);
181 }
182
183 static const Dwfl_Callbacks kernel_callbacks = {
184         .find_debuginfo = dwfl_standard_find_debuginfo,
185         .debuginfo_path = &debuginfo_path,
186
187         .find_elf = __linux_kernel_find_elf,
188         .section_address = dwfl_linux_kernel_module_section_address,
189 };
190
191 /* Get a Dwarf from live kernel image */
192 static Dwarf *dwfl_init_live_kernel_dwarf(Dwarf_Addr addr, Dwfl **dwflp,
193                                           Dwarf_Addr *bias)
194 {
195         Dwarf *dbg;
196
197         if (!dwflp)
198                 return NULL;
199
200         *dwflp = dwfl_begin(&kernel_callbacks);
201         if (!*dwflp)
202                 return NULL;
203
204         /* Load the kernel dwarves: Don't care the result here */
205         dwfl_linux_kernel_report_kernel(*dwflp);
206         dwfl_linux_kernel_report_modules(*dwflp);
207
208         dbg = dwfl_addrdwarf(*dwflp, addr, bias);
209         /* Here, check whether we could get a real dwarf */
210         if (!dbg) {
211                 pr_debug("Failed to find kernel dwarf at %lx\n",
212                          (unsigned long)addr);
213                 dwfl_end(*dwflp);
214                 *dwflp = NULL;
215         }
216         return dbg;
217 }
218 #else
219 /* With older elfutils, this just support kernel module... */
220 static Dwarf *dwfl_init_live_kernel_dwarf(Dwarf_Addr addr __used, Dwfl **dwflp,
221                                           Dwarf_Addr *bias)
222 {
223         int fd;
224         const char *path = kernel_get_module_path("kernel");
225
226         if (!path) {
227                 pr_err("Failed to find vmlinux path\n");
228                 return NULL;
229         }
230
231         pr_debug2("Use file %s for debuginfo\n", path);
232         fd = open(path, O_RDONLY);
233         if (fd < 0)
234                 return NULL;
235
236         return dwfl_init_offline_dwarf(fd, dwflp, bias);
237 }
238 #endif
239
240 /* Dwarf wrappers */
241
242 /* Find the realpath of the target file. */
243 static const char *cu_find_realpath(Dwarf_Die *cu_die, const char *fname)
244 {
245         Dwarf_Files *files;
246         size_t nfiles, i;
247         const char *src = NULL;
248         int ret;
249
250         if (!fname)
251                 return NULL;
252
253         ret = dwarf_getsrcfiles(cu_die, &files, &nfiles);
254         if (ret != 0)
255                 return NULL;
256
257         for (i = 0; i < nfiles; i++) {
258                 src = dwarf_filesrc(files, i, NULL, NULL);
259                 if (strtailcmp(src, fname) == 0)
260                         break;
261         }
262         if (i == nfiles)
263                 return NULL;
264         return src;
265 }
266
267 /* Get DW_AT_comp_dir (should be NULL with older gcc) */
268 static const char *cu_get_comp_dir(Dwarf_Die *cu_die)
269 {
270         Dwarf_Attribute attr;
271         if (dwarf_attr(cu_die, DW_AT_comp_dir, &attr) == NULL)
272                 return NULL;
273         return dwarf_formstring(&attr);
274 }
275
276 /* Compare diename and tname */
277 static bool die_compare_name(Dwarf_Die *dw_die, const char *tname)
278 {
279         const char *name;
280         name = dwarf_diename(dw_die);
281         return name ? (strcmp(tname, name) == 0) : false;
282 }
283
284 /* Get callsite line number of inline-function instance */
285 static int die_get_call_lineno(Dwarf_Die *in_die)
286 {
287         Dwarf_Attribute attr;
288         Dwarf_Word ret;
289
290         if (!dwarf_attr(in_die, DW_AT_call_line, &attr))
291                 return -ENOENT;
292
293         dwarf_formudata(&attr, &ret);
294         return (int)ret;
295 }
296
297 /* Get type die */
298 static Dwarf_Die *die_get_type(Dwarf_Die *vr_die, Dwarf_Die *die_mem)
299 {
300         Dwarf_Attribute attr;
301
302         if (dwarf_attr_integrate(vr_die, DW_AT_type, &attr) &&
303             dwarf_formref_die(&attr, die_mem))
304                 return die_mem;
305         else
306                 return NULL;
307 }
308
309 /* Get a type die, but skip qualifiers */
310 static Dwarf_Die *__die_get_real_type(Dwarf_Die *vr_die, Dwarf_Die *die_mem)
311 {
312         int tag;
313
314         do {
315                 vr_die = die_get_type(vr_die, die_mem);
316                 if (!vr_die)
317                         break;
318                 tag = dwarf_tag(vr_die);
319         } while (tag == DW_TAG_const_type ||
320                  tag == DW_TAG_restrict_type ||
321                  tag == DW_TAG_volatile_type ||
322                  tag == DW_TAG_shared_type);
323
324         return vr_die;
325 }
326
327 /* Get a type die, but skip qualifiers and typedef */
328 static Dwarf_Die *die_get_real_type(Dwarf_Die *vr_die, Dwarf_Die *die_mem)
329 {
330         do {
331                 vr_die = __die_get_real_type(vr_die, die_mem);
332         } while (vr_die && dwarf_tag(vr_die) == DW_TAG_typedef);
333
334         return vr_die;
335 }
336
337 static int die_get_attr_udata(Dwarf_Die *tp_die, unsigned int attr_name,
338                               Dwarf_Word *result)
339 {
340         Dwarf_Attribute attr;
341
342         if (dwarf_attr(tp_die, attr_name, &attr) == NULL ||
343             dwarf_formudata(&attr, result) != 0)
344                 return -ENOENT;
345
346         return 0;
347 }
348
349 static bool die_is_signed_type(Dwarf_Die *tp_die)
350 {
351         Dwarf_Word ret;
352
353         if (die_get_attr_udata(tp_die, DW_AT_encoding, &ret))
354                 return false;
355
356         return (ret == DW_ATE_signed_char || ret == DW_ATE_signed ||
357                 ret == DW_ATE_signed_fixed);
358 }
359
360 static int die_get_byte_size(Dwarf_Die *tp_die)
361 {
362         Dwarf_Word ret;
363
364         if (die_get_attr_udata(tp_die, DW_AT_byte_size, &ret))
365                 return 0;
366
367         return (int)ret;
368 }
369
370 static int die_get_bit_size(Dwarf_Die *tp_die)
371 {
372         Dwarf_Word ret;
373
374         if (die_get_attr_udata(tp_die, DW_AT_bit_size, &ret))
375                 return 0;
376
377         return (int)ret;
378 }
379
380 static int die_get_bit_offset(Dwarf_Die *tp_die)
381 {
382         Dwarf_Word ret;
383
384         if (die_get_attr_udata(tp_die, DW_AT_bit_offset, &ret))
385                 return 0;
386
387         return (int)ret;
388 }
389
390 /* Get data_member_location offset */
391 static int die_get_data_member_location(Dwarf_Die *mb_die, Dwarf_Word *offs)
392 {
393         Dwarf_Attribute attr;
394         Dwarf_Op *expr;
395         size_t nexpr;
396         int ret;
397
398         if (dwarf_attr(mb_die, DW_AT_data_member_location, &attr) == NULL)
399                 return -ENOENT;
400
401         if (dwarf_formudata(&attr, offs) != 0) {
402                 /* DW_AT_data_member_location should be DW_OP_plus_uconst */
403                 ret = dwarf_getlocation(&attr, &expr, &nexpr);
404                 if (ret < 0 || nexpr == 0)
405                         return -ENOENT;
406
407                 if (expr[0].atom != DW_OP_plus_uconst || nexpr != 1) {
408                         pr_debug("Unable to get offset:Unexpected OP %x (%zd)\n",
409                                  expr[0].atom, nexpr);
410                         return -ENOTSUP;
411                 }
412                 *offs = (Dwarf_Word)expr[0].number;
413         }
414         return 0;
415 }
416
417 /* Return values for die_find callbacks */
418 enum {
419         DIE_FIND_CB_FOUND = 0,          /* End of Search */
420         DIE_FIND_CB_CHILD = 1,          /* Search only children */
421         DIE_FIND_CB_SIBLING = 2,        /* Search only siblings */
422         DIE_FIND_CB_CONTINUE = 3,       /* Search children and siblings */
423 };
424
425 /* Search a child die */
426 static Dwarf_Die *die_find_child(Dwarf_Die *rt_die,
427                                  int (*callback)(Dwarf_Die *, void *),
428                                  void *data, Dwarf_Die *die_mem)
429 {
430         Dwarf_Die child_die;
431         int ret;
432
433         ret = dwarf_child(rt_die, die_mem);
434         if (ret != 0)
435                 return NULL;
436
437         do {
438                 ret = callback(die_mem, data);
439                 if (ret == DIE_FIND_CB_FOUND)
440                         return die_mem;
441
442                 if ((ret & DIE_FIND_CB_CHILD) &&
443                     die_find_child(die_mem, callback, data, &child_die)) {
444                         memcpy(die_mem, &child_die, sizeof(Dwarf_Die));
445                         return die_mem;
446                 }
447         } while ((ret & DIE_FIND_CB_SIBLING) &&
448                  dwarf_siblingof(die_mem, die_mem) == 0);
449
450         return NULL;
451 }
452
453 struct __addr_die_search_param {
454         Dwarf_Addr      addr;
455         Dwarf_Die       *die_mem;
456 };
457
458 static int __die_search_func_cb(Dwarf_Die *fn_die, void *data)
459 {
460         struct __addr_die_search_param *ad = data;
461
462         if (dwarf_tag(fn_die) == DW_TAG_subprogram &&
463             dwarf_haspc(fn_die, ad->addr)) {
464                 memcpy(ad->die_mem, fn_die, sizeof(Dwarf_Die));
465                 return DWARF_CB_ABORT;
466         }
467         return DWARF_CB_OK;
468 }
469
470 /* Search a real subprogram including this line, */
471 static Dwarf_Die *die_find_real_subprogram(Dwarf_Die *cu_die, Dwarf_Addr addr,
472                                            Dwarf_Die *die_mem)
473 {
474         struct __addr_die_search_param ad;
475         ad.addr = addr;
476         ad.die_mem = die_mem;
477         /* dwarf_getscopes can't find subprogram. */
478         if (!dwarf_getfuncs(cu_die, __die_search_func_cb, &ad, 0))
479                 return NULL;
480         else
481                 return die_mem;
482 }
483
484 /* die_find callback for inline function search */
485 static int __die_find_inline_cb(Dwarf_Die *die_mem, void *data)
486 {
487         Dwarf_Addr *addr = data;
488
489         if (dwarf_tag(die_mem) == DW_TAG_inlined_subroutine &&
490             dwarf_haspc(die_mem, *addr))
491                 return DIE_FIND_CB_FOUND;
492
493         return DIE_FIND_CB_CONTINUE;
494 }
495
496 /* Similar to dwarf_getfuncs, but returns inlined_subroutine if exists. */
497 static Dwarf_Die *die_find_inlinefunc(Dwarf_Die *sp_die, Dwarf_Addr addr,
498                                       Dwarf_Die *die_mem)
499 {
500         return die_find_child(sp_die, __die_find_inline_cb, &addr, die_mem);
501 }
502
503 /* Walker on lines (Note: line number will not be sorted) */
504 typedef int (* line_walk_handler_t) (const char *fname, int lineno,
505                                      Dwarf_Addr addr, void *data);
506
507 struct __line_walk_param {
508         const char *fname;
509         line_walk_handler_t handler;
510         void *data;
511         int retval;
512 };
513
514 static int __die_walk_funclines_cb(Dwarf_Die *in_die, void *data)
515 {
516         struct __line_walk_param *lw = data;
517         Dwarf_Addr addr;
518         int lineno;
519
520         if (dwarf_tag(in_die) == DW_TAG_inlined_subroutine) {
521                 lineno = die_get_call_lineno(in_die);
522                 if (lineno > 0 && dwarf_entrypc(in_die, &addr) == 0) {
523                         lw->retval = lw->handler(lw->fname, lineno, addr,
524                                                  lw->data);
525                         if (lw->retval != 0)
526                                 return DIE_FIND_CB_FOUND;
527                 }
528         }
529         return DIE_FIND_CB_SIBLING;
530 }
531
532 /* Walk on lines of blocks included in given DIE */
533 static int __die_walk_funclines(Dwarf_Die *sp_die,
534                                 line_walk_handler_t handler, void *data)
535 {
536         struct __line_walk_param lw = {
537                 .handler = handler,
538                 .data = data,
539                 .retval = 0,
540         };
541         Dwarf_Die die_mem;
542         Dwarf_Addr addr;
543         int lineno;
544
545         /* Handle function declaration line */
546         lw.fname = dwarf_decl_file(sp_die);
547         if (lw.fname && dwarf_decl_line(sp_die, &lineno) == 0 &&
548             dwarf_entrypc(sp_die, &addr) == 0) {
549                 lw.retval = handler(lw.fname, lineno, addr, data);
550                 if (lw.retval != 0)
551                         goto done;
552         }
553         die_find_child(sp_die, __die_walk_funclines_cb, &lw, &die_mem);
554 done:
555         return lw.retval;
556 }
557
558 static int __die_walk_culines_cb(Dwarf_Die *sp_die, void *data)
559 {
560         struct __line_walk_param *lw = data;
561
562         lw->retval = __die_walk_funclines(sp_die, lw->handler, lw->data);
563         if (lw->retval != 0)
564                 return DWARF_CB_ABORT;
565
566         return DWARF_CB_OK;
567 }
568
569 /*
570  * Walk on lines inside given PDIE. If the PDIE is subprogram, walk only on
571  * the lines inside the subprogram, otherwise PDIE must be a CU DIE.
572  */
573 static int die_walk_lines(Dwarf_Die *pdie, line_walk_handler_t handler,
574                           void *data)
575 {
576         Dwarf_Lines *lines;
577         Dwarf_Line *line;
578         Dwarf_Addr addr;
579         const char *fname;
580         int lineno, ret = 0;
581         Dwarf_Die die_mem, *cu_die;
582         size_t nlines, i;
583
584         /* Get the CU die */
585         if (dwarf_tag(pdie) == DW_TAG_subprogram)
586                 cu_die = dwarf_diecu(pdie, &die_mem, NULL, NULL);
587         else
588                 cu_die = pdie;
589         if (!cu_die) {
590                 pr_debug2("Failed to get CU from subprogram\n");
591                 return -EINVAL;
592         }
593
594         /* Get lines list in the CU */
595         if (dwarf_getsrclines(cu_die, &lines, &nlines) != 0) {
596                 pr_debug2("Failed to get source lines on this CU.\n");
597                 return -ENOENT;
598         }
599         pr_debug2("Get %zd lines from this CU\n", nlines);
600
601         /* Walk on the lines on lines list */
602         for (i = 0; i < nlines; i++) {
603                 line = dwarf_onesrcline(lines, i);
604                 if (line == NULL ||
605                     dwarf_lineno(line, &lineno) != 0 ||
606                     dwarf_lineaddr(line, &addr) != 0) {
607                         pr_debug2("Failed to get line info. "
608                                   "Possible error in debuginfo.\n");
609                         continue;
610                 }
611                 /* Filter lines based on address */
612                 if (pdie != cu_die)
613                         /*
614                          * Address filtering
615                          * The line is included in given function, and
616                          * no inline block includes it.
617                          */
618                         if (!dwarf_haspc(pdie, addr) ||
619                             die_find_inlinefunc(pdie, addr, &die_mem))
620                                 continue;
621                 /* Get source line */
622                 fname = dwarf_linesrc(line, NULL, NULL);
623
624                 ret = handler(fname, lineno, addr, data);
625                 if (ret != 0)
626                         return ret;
627         }
628
629         /*
630          * Dwarf lines doesn't include function declarations and inlined
631          * subroutines. We have to check functions list or given function.
632          */
633         if (pdie != cu_die)
634                 ret = __die_walk_funclines(pdie, handler, data);
635         else {
636                 struct __line_walk_param param = {
637                         .handler = handler,
638                         .data = data,
639                         .retval = 0,
640                 };
641                 dwarf_getfuncs(cu_die, __die_walk_culines_cb, &param, 0);
642                 ret = param.retval;
643         }
644
645         return ret;
646 }
647
648 struct __find_variable_param {
649         const char *name;
650         Dwarf_Addr addr;
651 };
652
653 static int __die_find_variable_cb(Dwarf_Die *die_mem, void *data)
654 {
655         struct __find_variable_param *fvp = data;
656         int tag;
657
658         tag = dwarf_tag(die_mem);
659         if ((tag == DW_TAG_formal_parameter ||
660              tag == DW_TAG_variable) &&
661             die_compare_name(die_mem, fvp->name))
662                 return DIE_FIND_CB_FOUND;
663
664         if (dwarf_haspc(die_mem, fvp->addr))
665                 return DIE_FIND_CB_CONTINUE;
666         else
667                 return DIE_FIND_CB_SIBLING;
668 }
669
670 /* Find a variable called 'name' at given address */
671 static Dwarf_Die *die_find_variable_at(Dwarf_Die *sp_die, const char *name,
672                                        Dwarf_Addr addr, Dwarf_Die *die_mem)
673 {
674         struct __find_variable_param fvp = { .name = name, .addr = addr};
675
676         return die_find_child(sp_die, __die_find_variable_cb, (void *)&fvp,
677                               die_mem);
678 }
679
680 static int __die_find_member_cb(Dwarf_Die *die_mem, void *data)
681 {
682         const char *name = data;
683
684         if ((dwarf_tag(die_mem) == DW_TAG_member) &&
685             die_compare_name(die_mem, name))
686                 return DIE_FIND_CB_FOUND;
687
688         return DIE_FIND_CB_SIBLING;
689 }
690
691 /* Find a member called 'name' */
692 static Dwarf_Die *die_find_member(Dwarf_Die *st_die, const char *name,
693                                   Dwarf_Die *die_mem)
694 {
695         return die_find_child(st_die, __die_find_member_cb, (void *)name,
696                               die_mem);
697 }
698
699 /* Get the name of given variable DIE */
700 static int die_get_typename(Dwarf_Die *vr_die, char *buf, int len)
701 {
702         Dwarf_Die type;
703         int tag, ret, ret2;
704         const char *tmp = "";
705
706         if (__die_get_real_type(vr_die, &type) == NULL)
707                 return -ENOENT;
708
709         tag = dwarf_tag(&type);
710         if (tag == DW_TAG_array_type || tag == DW_TAG_pointer_type)
711                 tmp = "*";
712         else if (tag == DW_TAG_subroutine_type) {
713                 /* Function pointer */
714                 ret = snprintf(buf, len, "(function_type)");
715                 return (ret >= len) ? -E2BIG : ret;
716         } else {
717                 if (!dwarf_diename(&type))
718                         return -ENOENT;
719                 if (tag == DW_TAG_union_type)
720                         tmp = "union ";
721                 else if (tag == DW_TAG_structure_type)
722                         tmp = "struct ";
723                 /* Write a base name */
724                 ret = snprintf(buf, len, "%s%s", tmp, dwarf_diename(&type));
725                 return (ret >= len) ? -E2BIG : ret;
726         }
727         ret = die_get_typename(&type, buf, len);
728         if (ret > 0) {
729                 ret2 = snprintf(buf + ret, len - ret, "%s", tmp);
730                 ret = (ret2 >= len - ret) ? -E2BIG : ret2 + ret;
731         }
732         return ret;
733 }
734
735 /* Get the name and type of given variable DIE, stored as "type\tname" */
736 static int die_get_varname(Dwarf_Die *vr_die, char *buf, int len)
737 {
738         int ret, ret2;
739
740         ret = die_get_typename(vr_die, buf, len);
741         if (ret < 0) {
742                 pr_debug("Failed to get type, make it unknown.\n");
743                 ret = snprintf(buf, len, "(unknown_type)");
744         }
745         if (ret > 0) {
746                 ret2 = snprintf(buf + ret, len - ret, "\t%s",
747                                 dwarf_diename(vr_die));
748                 ret = (ret2 >= len - ret) ? -E2BIG : ret2 + ret;
749         }
750         return ret;
751 }
752
753 /*
754  * Probe finder related functions
755  */
756
757 static struct probe_trace_arg_ref *alloc_trace_arg_ref(long offs)
758 {
759         struct probe_trace_arg_ref *ref;
760         ref = zalloc(sizeof(struct probe_trace_arg_ref));
761         if (ref != NULL)
762                 ref->offset = offs;
763         return ref;
764 }
765
766 /*
767  * Convert a location into trace_arg.
768  * If tvar == NULL, this just checks variable can be converted.
769  */
770 static int convert_variable_location(Dwarf_Die *vr_die, Dwarf_Addr addr,
771                                      Dwarf_Op *fb_ops,
772                                      struct probe_trace_arg *tvar)
773 {
774         Dwarf_Attribute attr;
775         Dwarf_Op *op;
776         size_t nops;
777         unsigned int regn;
778         Dwarf_Word offs = 0;
779         bool ref = false;
780         const char *regs;
781         int ret;
782
783         if (dwarf_attr(vr_die, DW_AT_external, &attr) != NULL)
784                 goto static_var;
785
786         /* TODO: handle more than 1 exprs */
787         if (dwarf_attr(vr_die, DW_AT_location, &attr) == NULL ||
788             dwarf_getlocation_addr(&attr, addr, &op, &nops, 1) <= 0 ||
789             nops == 0) {
790                 /* TODO: Support const_value */
791                 return -ENOENT;
792         }
793
794         if (op->atom == DW_OP_addr) {
795 static_var:
796                 if (!tvar)
797                         return 0;
798                 /* Static variables on memory (not stack), make @varname */
799                 ret = strlen(dwarf_diename(vr_die));
800                 tvar->value = zalloc(ret + 2);
801                 if (tvar->value == NULL)
802                         return -ENOMEM;
803                 snprintf(tvar->value, ret + 2, "@%s", dwarf_diename(vr_die));
804                 tvar->ref = alloc_trace_arg_ref((long)offs);
805                 if (tvar->ref == NULL)
806                         return -ENOMEM;
807                 return 0;
808         }
809
810         /* If this is based on frame buffer, set the offset */
811         if (op->atom == DW_OP_fbreg) {
812                 if (fb_ops == NULL)
813                         return -ENOTSUP;
814                 ref = true;
815                 offs = op->number;
816                 op = &fb_ops[0];
817         }
818
819         if (op->atom >= DW_OP_breg0 && op->atom <= DW_OP_breg31) {
820                 regn = op->atom - DW_OP_breg0;
821                 offs += op->number;
822                 ref = true;
823         } else if (op->atom >= DW_OP_reg0 && op->atom <= DW_OP_reg31) {
824                 regn = op->atom - DW_OP_reg0;
825         } else if (op->atom == DW_OP_bregx) {
826                 regn = op->number;
827                 offs += op->number2;
828                 ref = true;
829         } else if (op->atom == DW_OP_regx) {
830                 regn = op->number;
831         } else {
832                 pr_debug("DW_OP %x is not supported.\n", op->atom);
833                 return -ENOTSUP;
834         }
835
836         if (!tvar)
837                 return 0;
838
839         regs = get_arch_regstr(regn);
840         if (!regs) {
841                 /* This should be a bug in DWARF or this tool */
842                 pr_warning("Mapping for the register number %u "
843                            "missing on this architecture.\n", regn);
844                 return -ERANGE;
845         }
846
847         tvar->value = strdup(regs);
848         if (tvar->value == NULL)
849                 return -ENOMEM;
850
851         if (ref) {
852                 tvar->ref = alloc_trace_arg_ref((long)offs);
853                 if (tvar->ref == NULL)
854                         return -ENOMEM;
855         }
856         return 0;
857 }
858
859 #define BYTES_TO_BITS(nb)       ((nb) * BITS_PER_LONG / sizeof(long))
860
861 static int convert_variable_type(Dwarf_Die *vr_die,
862                                  struct probe_trace_arg *tvar,
863                                  const char *cast)
864 {
865         struct probe_trace_arg_ref **ref_ptr = &tvar->ref;
866         Dwarf_Die type;
867         char buf[16];
868         int ret;
869
870         /* TODO: check all types */
871         if (cast && strcmp(cast, "string") != 0) {
872                 /* Non string type is OK */
873                 tvar->type = strdup(cast);
874                 return (tvar->type == NULL) ? -ENOMEM : 0;
875         }
876
877         if (die_get_bit_size(vr_die) != 0) {
878                 /* This is a bitfield */
879                 ret = snprintf(buf, 16, "b%d@%d/%zd", die_get_bit_size(vr_die),
880                                 die_get_bit_offset(vr_die),
881                                 BYTES_TO_BITS(die_get_byte_size(vr_die)));
882                 goto formatted;
883         }
884
885         if (die_get_real_type(vr_die, &type) == NULL) {
886                 pr_warning("Failed to get a type information of %s.\n",
887                            dwarf_diename(vr_die));
888                 return -ENOENT;
889         }
890
891         pr_debug("%s type is %s.\n",
892                  dwarf_diename(vr_die), dwarf_diename(&type));
893
894         if (cast && strcmp(cast, "string") == 0) {      /* String type */
895                 ret = dwarf_tag(&type);
896                 if (ret != DW_TAG_pointer_type &&
897                     ret != DW_TAG_array_type) {
898                         pr_warning("Failed to cast into string: "
899                                    "%s(%s) is not a pointer nor array.\n",
900                                    dwarf_diename(vr_die), dwarf_diename(&type));
901                         return -EINVAL;
902                 }
903                 if (ret == DW_TAG_pointer_type) {
904                         if (die_get_real_type(&type, &type) == NULL) {
905                                 pr_warning("Failed to get a type"
906                                            " information.\n");
907                                 return -ENOENT;
908                         }
909                         while (*ref_ptr)
910                                 ref_ptr = &(*ref_ptr)->next;
911                         /* Add new reference with offset +0 */
912                         *ref_ptr = zalloc(sizeof(struct probe_trace_arg_ref));
913                         if (*ref_ptr == NULL) {
914                                 pr_warning("Out of memory error\n");
915                                 return -ENOMEM;
916                         }
917                 }
918                 if (!die_compare_name(&type, "char") &&
919                     !die_compare_name(&type, "unsigned char")) {
920                         pr_warning("Failed to cast into string: "
921                                    "%s is not (unsigned) char *.\n",
922                                    dwarf_diename(vr_die));
923                         return -EINVAL;
924                 }
925                 tvar->type = strdup(cast);
926                 return (tvar->type == NULL) ? -ENOMEM : 0;
927         }
928
929         ret = BYTES_TO_BITS(die_get_byte_size(&type));
930         if (!ret)
931                 /* No size ... try to use default type */
932                 return 0;
933
934         /* Check the bitwidth */
935         if (ret > MAX_BASIC_TYPE_BITS) {
936                 pr_info("%s exceeds max-bitwidth. Cut down to %d bits.\n",
937                         dwarf_diename(&type), MAX_BASIC_TYPE_BITS);
938                 ret = MAX_BASIC_TYPE_BITS;
939         }
940         ret = snprintf(buf, 16, "%c%d",
941                        die_is_signed_type(&type) ? 's' : 'u', ret);
942
943 formatted:
944         if (ret < 0 || ret >= 16) {
945                 if (ret >= 16)
946                         ret = -E2BIG;
947                 pr_warning("Failed to convert variable type: %s\n",
948                            strerror(-ret));
949                 return ret;
950         }
951         tvar->type = strdup(buf);
952         if (tvar->type == NULL)
953                 return -ENOMEM;
954         return 0;
955 }
956
957 static int convert_variable_fields(Dwarf_Die *vr_die, const char *varname,
958                                     struct perf_probe_arg_field *field,
959                                     struct probe_trace_arg_ref **ref_ptr,
960                                     Dwarf_Die *die_mem)
961 {
962         struct probe_trace_arg_ref *ref = *ref_ptr;
963         Dwarf_Die type;
964         Dwarf_Word offs;
965         int ret, tag;
966
967         pr_debug("converting %s in %s\n", field->name, varname);
968         if (die_get_real_type(vr_die, &type) == NULL) {
969                 pr_warning("Failed to get the type of %s.\n", varname);
970                 return -ENOENT;
971         }
972         pr_debug2("Var real type: (%x)\n", (unsigned)dwarf_dieoffset(&type));
973         tag = dwarf_tag(&type);
974
975         if (field->name[0] == '[' &&
976             (tag == DW_TAG_array_type || tag == DW_TAG_pointer_type)) {
977                 if (field->next)
978                         /* Save original type for next field */
979                         memcpy(die_mem, &type, sizeof(*die_mem));
980                 /* Get the type of this array */
981                 if (die_get_real_type(&type, &type) == NULL) {
982                         pr_warning("Failed to get the type of %s.\n", varname);
983                         return -ENOENT;
984                 }
985                 pr_debug2("Array real type: (%x)\n",
986                          (unsigned)dwarf_dieoffset(&type));
987                 if (tag == DW_TAG_pointer_type) {
988                         ref = zalloc(sizeof(struct probe_trace_arg_ref));
989                         if (ref == NULL)
990                                 return -ENOMEM;
991                         if (*ref_ptr)
992                                 (*ref_ptr)->next = ref;
993                         else
994                                 *ref_ptr = ref;
995                 }
996                 ref->offset += die_get_byte_size(&type) * field->index;
997                 if (!field->next)
998                         /* Save vr_die for converting types */
999                         memcpy(die_mem, vr_die, sizeof(*die_mem));
1000                 goto next;
1001         } else if (tag == DW_TAG_pointer_type) {
1002                 /* Check the pointer and dereference */
1003                 if (!field->ref) {
1004                         pr_err("Semantic error: %s must be referred by '->'\n",
1005                                field->name);
1006                         return -EINVAL;
1007                 }
1008                 /* Get the type pointed by this pointer */
1009                 if (die_get_real_type(&type, &type) == NULL) {
1010                         pr_warning("Failed to get the type of %s.\n", varname);
1011                         return -ENOENT;
1012                 }
1013                 /* Verify it is a data structure  */
1014                 if (dwarf_tag(&type) != DW_TAG_structure_type) {
1015                         pr_warning("%s is not a data structure.\n", varname);
1016                         return -EINVAL;
1017                 }
1018
1019                 ref = zalloc(sizeof(struct probe_trace_arg_ref));
1020                 if (ref == NULL)
1021                         return -ENOMEM;
1022                 if (*ref_ptr)
1023                         (*ref_ptr)->next = ref;
1024                 else
1025                         *ref_ptr = ref;
1026         } else {
1027                 /* Verify it is a data structure  */
1028                 if (tag != DW_TAG_structure_type) {
1029                         pr_warning("%s is not a data structure.\n", varname);
1030                         return -EINVAL;
1031                 }
1032                 if (field->name[0] == '[') {
1033                         pr_err("Semantic error: %s is not a pointor"
1034                                " nor array.\n", varname);
1035                         return -EINVAL;
1036                 }
1037                 if (field->ref) {
1038                         pr_err("Semantic error: %s must be referred by '.'\n",
1039                                field->name);
1040                         return -EINVAL;
1041                 }
1042                 if (!ref) {
1043                         pr_warning("Structure on a register is not "
1044                                    "supported yet.\n");
1045                         return -ENOTSUP;
1046                 }
1047         }
1048
1049         if (die_find_member(&type, field->name, die_mem) == NULL) {
1050                 pr_warning("%s(tyep:%s) has no member %s.\n", varname,
1051                            dwarf_diename(&type), field->name);
1052                 return -EINVAL;
1053         }
1054
1055         /* Get the offset of the field */
1056         ret = die_get_data_member_location(die_mem, &offs);
1057         if (ret < 0) {
1058                 pr_warning("Failed to get the offset of %s.\n", field->name);
1059                 return ret;
1060         }
1061         ref->offset += (long)offs;
1062
1063 next:
1064         /* Converting next field */
1065         if (field->next)
1066                 return convert_variable_fields(die_mem, field->name,
1067                                         field->next, &ref, die_mem);
1068         else
1069                 return 0;
1070 }
1071
1072 /* Show a variables in kprobe event format */
1073 static int convert_variable(Dwarf_Die *vr_die, struct probe_finder *pf)
1074 {
1075         Dwarf_Die die_mem;
1076         int ret;
1077
1078         pr_debug("Converting variable %s into trace event.\n",
1079                  dwarf_diename(vr_die));
1080
1081         ret = convert_variable_location(vr_die, pf->addr, pf->fb_ops,
1082                                         pf->tvar);
1083         if (ret == -ENOENT)
1084                 pr_err("Failed to find the location of %s at this address.\n"
1085                        " Perhaps, it has been optimized out.\n", pf->pvar->var);
1086         else if (ret == -ENOTSUP)
1087                 pr_err("Sorry, we don't support this variable location yet.\n");
1088         else if (pf->pvar->field) {
1089                 ret = convert_variable_fields(vr_die, pf->pvar->var,
1090                                               pf->pvar->field, &pf->tvar->ref,
1091                                               &die_mem);
1092                 vr_die = &die_mem;
1093         }
1094         if (ret == 0)
1095                 ret = convert_variable_type(vr_die, pf->tvar, pf->pvar->type);
1096         /* *expr will be cached in libdw. Don't free it. */
1097         return ret;
1098 }
1099
1100 /* Find a variable in a subprogram die */
1101 static int find_variable(Dwarf_Die *sp_die, struct probe_finder *pf)
1102 {
1103         Dwarf_Die vr_die, *scopes;
1104         char buf[32], *ptr;
1105         int ret, nscopes;
1106
1107         if (!is_c_varname(pf->pvar->var)) {
1108                 /* Copy raw parameters */
1109                 pf->tvar->value = strdup(pf->pvar->var);
1110                 if (pf->tvar->value == NULL)
1111                         return -ENOMEM;
1112                 if (pf->pvar->type) {
1113                         pf->tvar->type = strdup(pf->pvar->type);
1114                         if (pf->tvar->type == NULL)
1115                                 return -ENOMEM;
1116                 }
1117                 if (pf->pvar->name) {
1118                         pf->tvar->name = strdup(pf->pvar->name);
1119                         if (pf->tvar->name == NULL)
1120                                 return -ENOMEM;
1121                 } else
1122                         pf->tvar->name = NULL;
1123                 return 0;
1124         }
1125
1126         if (pf->pvar->name)
1127                 pf->tvar->name = strdup(pf->pvar->name);
1128         else {
1129                 ret = synthesize_perf_probe_arg(pf->pvar, buf, 32);
1130                 if (ret < 0)
1131                         return ret;
1132                 ptr = strchr(buf, ':'); /* Change type separator to _ */
1133                 if (ptr)
1134                         *ptr = '_';
1135                 pf->tvar->name = strdup(buf);
1136         }
1137         if (pf->tvar->name == NULL)
1138                 return -ENOMEM;
1139
1140         pr_debug("Searching '%s' variable in context.\n",
1141                  pf->pvar->var);
1142         /* Search child die for local variables and parameters. */
1143         if (die_find_variable_at(sp_die, pf->pvar->var, pf->addr, &vr_die))
1144                 ret = convert_variable(&vr_die, pf);
1145         else {
1146                 /* Search upper class */
1147                 nscopes = dwarf_getscopes_die(sp_die, &scopes);
1148                 while (nscopes-- > 1) {
1149                         pr_debug("Searching variables in %s\n",
1150                                  dwarf_diename(&scopes[nscopes]));
1151                         /* We should check this scope, so give dummy address */
1152                         if (die_find_variable_at(&scopes[nscopes],
1153                                                  pf->pvar->var, 0,
1154                                                  &vr_die)) {
1155                                 ret = convert_variable(&vr_die, pf);
1156                                 goto found;
1157                         }
1158                 }
1159                 if (scopes)
1160                         free(scopes);
1161                 ret = -ENOENT;
1162         }
1163 found:
1164         if (ret < 0)
1165                 pr_warning("Failed to find '%s' in this function.\n",
1166                            pf->pvar->var);
1167         return ret;
1168 }
1169
1170 /* Convert subprogram DIE to trace point */
1171 static int convert_to_trace_point(Dwarf_Die *sp_die, Dwarf_Addr paddr,
1172                                   bool retprobe, struct probe_trace_point *tp)
1173 {
1174         Dwarf_Addr eaddr;
1175         const char *name;
1176
1177         /* Copy the name of probe point */
1178         name = dwarf_diename(sp_die);
1179         if (name) {
1180                 if (dwarf_entrypc(sp_die, &eaddr) != 0) {
1181                         pr_warning("Failed to get entry address of %s\n",
1182                                    dwarf_diename(sp_die));
1183                         return -ENOENT;
1184                 }
1185                 tp->symbol = strdup(name);
1186                 if (tp->symbol == NULL)
1187                         return -ENOMEM;
1188                 tp->offset = (unsigned long)(paddr - eaddr);
1189         } else
1190                 /* This function has no name. */
1191                 tp->offset = (unsigned long)paddr;
1192
1193         /* Return probe must be on the head of a subprogram */
1194         if (retprobe) {
1195                 if (eaddr != paddr) {
1196                         pr_warning("Return probe must be on the head of"
1197                                    " a real function.\n");
1198                         return -EINVAL;
1199                 }
1200                 tp->retprobe = true;
1201         }
1202
1203         return 0;
1204 }
1205
1206 /* Call probe_finder callback with real subprogram DIE */
1207 static int call_probe_finder(Dwarf_Die *sp_die, struct probe_finder *pf)
1208 {
1209         Dwarf_Die die_mem;
1210         Dwarf_Attribute fb_attr;
1211         size_t nops;
1212         int ret;
1213
1214         /* If no real subprogram, find a real one */
1215         if (!sp_die || dwarf_tag(sp_die) != DW_TAG_subprogram) {
1216                 sp_die = die_find_real_subprogram(&pf->cu_die,
1217                                                   pf->addr, &die_mem);
1218                 if (!sp_die) {
1219                         pr_warning("Failed to find probe point in any "
1220                                    "functions.\n");
1221                         return -ENOENT;
1222                 }
1223         }
1224
1225         /* Get the frame base attribute/ops */
1226         dwarf_attr(sp_die, DW_AT_frame_base, &fb_attr);
1227         ret = dwarf_getlocation_addr(&fb_attr, pf->addr, &pf->fb_ops, &nops, 1);
1228         if (ret <= 0 || nops == 0) {
1229                 pf->fb_ops = NULL;
1230 #if _ELFUTILS_PREREQ(0, 142)
1231         } else if (nops == 1 && pf->fb_ops[0].atom == DW_OP_call_frame_cfa &&
1232                    pf->cfi != NULL) {
1233                 Dwarf_Frame *frame;
1234                 if (dwarf_cfi_addrframe(pf->cfi, pf->addr, &frame) != 0 ||
1235                     dwarf_frame_cfa(frame, &pf->fb_ops, &nops) != 0) {
1236                         pr_warning("Failed to get call frame on 0x%jx\n",
1237                                    (uintmax_t)pf->addr);
1238                         return -ENOENT;
1239                 }
1240 #endif
1241         }
1242
1243         /* Call finder's callback handler */
1244         ret = pf->callback(sp_die, pf);
1245
1246         /* *pf->fb_ops will be cached in libdw. Don't free it. */
1247         pf->fb_ops = NULL;
1248
1249         return ret;
1250 }
1251
1252 static int probe_point_line_walker(const char *fname, int lineno,
1253                                    Dwarf_Addr addr, void *data)
1254 {
1255         struct probe_finder *pf = data;
1256         int ret;
1257
1258         if (lineno != pf->lno || strtailcmp(fname, pf->fname) != 0)
1259                 return 0;
1260
1261         pf->addr = addr;
1262         ret = call_probe_finder(NULL, pf);
1263
1264         /* Continue if no error, because the line will be in inline function */
1265         return ret < 0 ? ret : 0;
1266 }
1267
1268 /* Find probe point from its line number */
1269 static int find_probe_point_by_line(struct probe_finder *pf)
1270 {
1271         return die_walk_lines(&pf->cu_die, probe_point_line_walker, pf);
1272 }
1273
1274 /* Find lines which match lazy pattern */
1275 static int find_lazy_match_lines(struct list_head *head,
1276                                  const char *fname, const char *pat)
1277 {
1278         FILE *fp;
1279         char *line = NULL;
1280         size_t line_len;
1281         ssize_t len;
1282         int count = 0, linenum = 1;
1283
1284         fp = fopen(fname, "r");
1285         if (!fp) {
1286                 pr_warning("Failed to open %s: %s\n", fname, strerror(errno));
1287                 return -errno;
1288         }
1289
1290         while ((len = getline(&line, &line_len, fp)) > 0) {
1291
1292                 if (line[len - 1] == '\n')
1293                         line[len - 1] = '\0';
1294
1295                 if (strlazymatch(line, pat)) {
1296                         line_list__add_line(head, linenum);
1297                         count++;
1298                 }
1299                 linenum++;
1300         }
1301
1302         if (ferror(fp))
1303                 count = -errno;
1304         free(line);
1305         fclose(fp);
1306
1307         if (count == 0)
1308                 pr_debug("No matched lines found in %s.\n", fname);
1309         return count;
1310 }
1311
1312 static int probe_point_lazy_walker(const char *fname, int lineno,
1313                                    Dwarf_Addr addr, void *data)
1314 {
1315         struct probe_finder *pf = data;
1316         int ret;
1317
1318         if (!line_list__has_line(&pf->lcache, lineno) ||
1319             strtailcmp(fname, pf->fname) != 0)
1320                 return 0;
1321
1322         pr_debug("Probe line found: line:%d addr:0x%llx\n",
1323                  lineno, (unsigned long long)addr);
1324         pf->addr = addr;
1325         ret = call_probe_finder(NULL, pf);
1326
1327         /*
1328          * Continue if no error, because the lazy pattern will match
1329          * to other lines
1330          */
1331         return ret < 0 ? ret : 0;
1332 }
1333
1334 /* Find probe points from lazy pattern  */
1335 static int find_probe_point_lazy(Dwarf_Die *sp_die, struct probe_finder *pf)
1336 {
1337         int ret = 0;
1338
1339         if (list_empty(&pf->lcache)) {
1340                 /* Matching lazy line pattern */
1341                 ret = find_lazy_match_lines(&pf->lcache, pf->fname,
1342                                             pf->pev->point.lazy_line);
1343                 if (ret <= 0)
1344                         return ret;
1345         }
1346
1347         return die_walk_lines(sp_die, probe_point_lazy_walker, pf);
1348 }
1349
1350 /* Callback parameter with return value */
1351 struct dwarf_callback_param {
1352         void *data;
1353         int retval;
1354 };
1355
1356 static int probe_point_inline_cb(Dwarf_Die *in_die, void *data)
1357 {
1358         struct dwarf_callback_param *param = data;
1359         struct probe_finder *pf = param->data;
1360         struct perf_probe_point *pp = &pf->pev->point;
1361         Dwarf_Addr addr;
1362
1363         if (pp->lazy_line)
1364                 param->retval = find_probe_point_lazy(in_die, pf);
1365         else {
1366                 /* Get probe address */
1367                 if (dwarf_entrypc(in_die, &addr) != 0) {
1368                         pr_warning("Failed to get entry address of %s.\n",
1369                                    dwarf_diename(in_die));
1370                         param->retval = -ENOENT;
1371                         return DWARF_CB_ABORT;
1372                 }
1373                 pf->addr = addr;
1374                 pf->addr += pp->offset;
1375                 pr_debug("found inline addr: 0x%jx\n",
1376                          (uintmax_t)pf->addr);
1377
1378                 param->retval = call_probe_finder(in_die, pf);
1379                 if (param->retval < 0)
1380                         return DWARF_CB_ABORT;
1381         }
1382
1383         return DWARF_CB_OK;
1384 }
1385
1386 /* Search function from function name */
1387 static int probe_point_search_cb(Dwarf_Die *sp_die, void *data)
1388 {
1389         struct dwarf_callback_param *param = data;
1390         struct probe_finder *pf = param->data;
1391         struct perf_probe_point *pp = &pf->pev->point;
1392
1393         /* Check tag and diename */
1394         if (dwarf_tag(sp_die) != DW_TAG_subprogram ||
1395             !die_compare_name(sp_die, pp->function))
1396                 return DWARF_CB_OK;
1397
1398         pf->fname = dwarf_decl_file(sp_die);
1399         if (pp->line) { /* Function relative line */
1400                 dwarf_decl_line(sp_die, &pf->lno);
1401                 pf->lno += pp->line;
1402                 param->retval = find_probe_point_by_line(pf);
1403         } else if (!dwarf_func_inline(sp_die)) {
1404                 /* Real function */
1405                 if (pp->lazy_line)
1406                         param->retval = find_probe_point_lazy(sp_die, pf);
1407                 else {
1408                         if (dwarf_entrypc(sp_die, &pf->addr) != 0) {
1409                                 pr_warning("Failed to get entry address of "
1410                                            "%s.\n", dwarf_diename(sp_die));
1411                                 param->retval = -ENOENT;
1412                                 return DWARF_CB_ABORT;
1413                         }
1414                         pf->addr += pp->offset;
1415                         /* TODO: Check the address in this function */
1416                         param->retval = call_probe_finder(sp_die, pf);
1417                 }
1418         } else {
1419                 struct dwarf_callback_param _param = {.data = (void *)pf,
1420                                                       .retval = 0};
1421                 /* Inlined function: search instances */
1422                 dwarf_func_inline_instances(sp_die, probe_point_inline_cb,
1423                                             &_param);
1424                 param->retval = _param.retval;
1425         }
1426
1427         return DWARF_CB_ABORT; /* Exit; no same symbol in this CU. */
1428 }
1429
1430 static int find_probe_point_by_func(struct probe_finder *pf)
1431 {
1432         struct dwarf_callback_param _param = {.data = (void *)pf,
1433                                               .retval = 0};
1434         dwarf_getfuncs(&pf->cu_die, probe_point_search_cb, &_param, 0);
1435         return _param.retval;
1436 }
1437
1438 /* Find probe points from debuginfo */
1439 static int find_probes(int fd, struct probe_finder *pf)
1440 {
1441         struct perf_probe_point *pp = &pf->pev->point;
1442         Dwarf_Off off, noff;
1443         size_t cuhl;
1444         Dwarf_Die *diep;
1445         Dwarf *dbg = NULL;
1446         Dwfl *dwfl;
1447         Dwarf_Addr bias;        /* Currently ignored */
1448         int ret = 0;
1449
1450         dbg = dwfl_init_offline_dwarf(fd, &dwfl, &bias);
1451         if (!dbg) {
1452                 pr_warning("No debug information found in the vmlinux - "
1453                         "please rebuild with CONFIG_DEBUG_INFO=y.\n");
1454                 return -EBADF;
1455         }
1456
1457 #if _ELFUTILS_PREREQ(0, 142)
1458         /* Get the call frame information from this dwarf */
1459         pf->cfi = dwarf_getcfi(dbg);
1460 #endif
1461
1462         off = 0;
1463         line_list__init(&pf->lcache);
1464         /* Loop on CUs (Compilation Unit) */
1465         while (!dwarf_nextcu(dbg, off, &noff, &cuhl, NULL, NULL, NULL)) {
1466                 /* Get the DIE(Debugging Information Entry) of this CU */
1467                 diep = dwarf_offdie(dbg, off + cuhl, &pf->cu_die);
1468                 if (!diep)
1469                         continue;
1470
1471                 /* Check if target file is included. */
1472                 if (pp->file)
1473                         pf->fname = cu_find_realpath(&pf->cu_die, pp->file);
1474                 else
1475                         pf->fname = NULL;
1476
1477                 if (!pp->file || pf->fname) {
1478                         if (pp->function)
1479                                 ret = find_probe_point_by_func(pf);
1480                         else if (pp->lazy_line)
1481                                 ret = find_probe_point_lazy(NULL, pf);
1482                         else {
1483                                 pf->lno = pp->line;
1484                                 ret = find_probe_point_by_line(pf);
1485                         }
1486                         if (ret < 0)
1487                                 break;
1488                 }
1489                 off = noff;
1490         }
1491         line_list__free(&pf->lcache);
1492         if (dwfl)
1493                 dwfl_end(dwfl);
1494
1495         return ret;
1496 }
1497
1498 /* Add a found probe point into trace event list */
1499 static int add_probe_trace_event(Dwarf_Die *sp_die, struct probe_finder *pf)
1500 {
1501         struct trace_event_finder *tf =
1502                         container_of(pf, struct trace_event_finder, pf);
1503         struct probe_trace_event *tev;
1504         int ret, i;
1505
1506         /* Check number of tevs */
1507         if (tf->ntevs == tf->max_tevs) {
1508                 pr_warning("Too many( > %d) probe point found.\n",
1509                            tf->max_tevs);
1510                 return -ERANGE;
1511         }
1512         tev = &tf->tevs[tf->ntevs++];
1513
1514         ret = convert_to_trace_point(sp_die, pf->addr, pf->pev->point.retprobe,
1515                                      &tev->point);
1516         if (ret < 0)
1517                 return ret;
1518
1519         pr_debug("Probe point found: %s+%lu\n", tev->point.symbol,
1520                  tev->point.offset);
1521
1522         /* Find each argument */
1523         tev->nargs = pf->pev->nargs;
1524         tev->args = zalloc(sizeof(struct probe_trace_arg) * tev->nargs);
1525         if (tev->args == NULL)
1526                 return -ENOMEM;
1527         for (i = 0; i < pf->pev->nargs; i++) {
1528                 pf->pvar = &pf->pev->args[i];
1529                 pf->tvar = &tev->args[i];
1530                 ret = find_variable(sp_die, pf);
1531                 if (ret != 0)
1532                         return ret;
1533         }
1534
1535         return 0;
1536 }
1537
1538 /* Find probe_trace_events specified by perf_probe_event from debuginfo */
1539 int find_probe_trace_events(int fd, struct perf_probe_event *pev,
1540                             struct probe_trace_event **tevs, int max_tevs)
1541 {
1542         struct trace_event_finder tf = {
1543                         .pf = {.pev = pev, .callback = add_probe_trace_event},
1544                         .max_tevs = max_tevs};
1545         int ret;
1546
1547         /* Allocate result tevs array */
1548         *tevs = zalloc(sizeof(struct probe_trace_event) * max_tevs);
1549         if (*tevs == NULL)
1550                 return -ENOMEM;
1551
1552         tf.tevs = *tevs;
1553         tf.ntevs = 0;
1554
1555         ret = find_probes(fd, &tf.pf);
1556         if (ret < 0) {
1557                 free(*tevs);
1558                 *tevs = NULL;
1559                 return ret;
1560         }
1561
1562         return (ret < 0) ? ret : tf.ntevs;
1563 }
1564
1565 #define MAX_VAR_LEN 64
1566
1567 /* Collect available variables in this scope */
1568 static int collect_variables_cb(Dwarf_Die *die_mem, void *data)
1569 {
1570         struct available_var_finder *af = data;
1571         struct variable_list *vl;
1572         char buf[MAX_VAR_LEN];
1573         int tag, ret;
1574
1575         vl = &af->vls[af->nvls - 1];
1576
1577         tag = dwarf_tag(die_mem);
1578         if (tag == DW_TAG_formal_parameter ||
1579             tag == DW_TAG_variable) {
1580                 ret = convert_variable_location(die_mem, af->pf.addr,
1581                                                 af->pf.fb_ops, NULL);
1582                 if (ret == 0) {
1583                         ret = die_get_varname(die_mem, buf, MAX_VAR_LEN);
1584                         pr_debug2("Add new var: %s\n", buf);
1585                         if (ret > 0)
1586                                 strlist__add(vl->vars, buf);
1587                 }
1588         }
1589
1590         if (af->child && dwarf_haspc(die_mem, af->pf.addr))
1591                 return DIE_FIND_CB_CONTINUE;
1592         else
1593                 return DIE_FIND_CB_SIBLING;
1594 }
1595
1596 /* Add a found vars into available variables list */
1597 static int add_available_vars(Dwarf_Die *sp_die, struct probe_finder *pf)
1598 {
1599         struct available_var_finder *af =
1600                         container_of(pf, struct available_var_finder, pf);
1601         struct variable_list *vl;
1602         Dwarf_Die die_mem, *scopes = NULL;
1603         int ret, nscopes;
1604
1605         /* Check number of tevs */
1606         if (af->nvls == af->max_vls) {
1607                 pr_warning("Too many( > %d) probe point found.\n", af->max_vls);
1608                 return -ERANGE;
1609         }
1610         vl = &af->vls[af->nvls++];
1611
1612         ret = convert_to_trace_point(sp_die, pf->addr, pf->pev->point.retprobe,
1613                                      &vl->point);
1614         if (ret < 0)
1615                 return ret;
1616
1617         pr_debug("Probe point found: %s+%lu\n", vl->point.symbol,
1618                  vl->point.offset);
1619
1620         /* Find local variables */
1621         vl->vars = strlist__new(true, NULL);
1622         if (vl->vars == NULL)
1623                 return -ENOMEM;
1624         af->child = true;
1625         die_find_child(sp_die, collect_variables_cb, (void *)af, &die_mem);
1626
1627         /* Find external variables */
1628         if (!af->externs)
1629                 goto out;
1630         /* Don't need to search child DIE for externs. */
1631         af->child = false;
1632         nscopes = dwarf_getscopes_die(sp_die, &scopes);
1633         while (nscopes-- > 1)
1634                 die_find_child(&scopes[nscopes], collect_variables_cb,
1635                                (void *)af, &die_mem);
1636         if (scopes)
1637                 free(scopes);
1638
1639 out:
1640         if (strlist__empty(vl->vars)) {
1641                 strlist__delete(vl->vars);
1642                 vl->vars = NULL;
1643         }
1644
1645         return ret;
1646 }
1647
1648 /* Find available variables at given probe point */
1649 int find_available_vars_at(int fd, struct perf_probe_event *pev,
1650                            struct variable_list **vls, int max_vls,
1651                            bool externs)
1652 {
1653         struct available_var_finder af = {
1654                         .pf = {.pev = pev, .callback = add_available_vars},
1655                         .max_vls = max_vls, .externs = externs};
1656         int ret;
1657
1658         /* Allocate result vls array */
1659         *vls = zalloc(sizeof(struct variable_list) * max_vls);
1660         if (*vls == NULL)
1661                 return -ENOMEM;
1662
1663         af.vls = *vls;
1664         af.nvls = 0;
1665
1666         ret = find_probes(fd, &af.pf);
1667         if (ret < 0) {
1668                 /* Free vlist for error */
1669                 while (af.nvls--) {
1670                         if (af.vls[af.nvls].point.symbol)
1671                                 free(af.vls[af.nvls].point.symbol);
1672                         if (af.vls[af.nvls].vars)
1673                                 strlist__delete(af.vls[af.nvls].vars);
1674                 }
1675                 free(af.vls);
1676                 *vls = NULL;
1677                 return ret;
1678         }
1679
1680         return (ret < 0) ? ret : af.nvls;
1681 }
1682
1683 /* Reverse search */
1684 int find_perf_probe_point(unsigned long addr, struct perf_probe_point *ppt)
1685 {
1686         Dwarf_Die cudie, spdie, indie;
1687         Dwarf *dbg = NULL;
1688         Dwfl *dwfl = NULL;
1689         Dwarf_Line *line;
1690         Dwarf_Addr laddr, eaddr, bias = 0;
1691         const char *tmp;
1692         int lineno, ret = 0;
1693         bool found = false;
1694
1695         /* Open the live linux kernel */
1696         dbg = dwfl_init_live_kernel_dwarf(addr, &dwfl, &bias);
1697         if (!dbg) {
1698                 pr_warning("No debug information found in the vmlinux - "
1699                         "please rebuild with CONFIG_DEBUG_INFO=y.\n");
1700                 ret = -EINVAL;
1701                 goto end;
1702         }
1703
1704         /* Adjust address with bias */
1705         addr += bias;
1706         /* Find cu die */
1707         if (!dwarf_addrdie(dbg, (Dwarf_Addr)addr - bias, &cudie)) {
1708                 pr_warning("Failed to find debug information for address %lx\n",
1709                            addr);
1710                 ret = -EINVAL;
1711                 goto end;
1712         }
1713
1714         /* Find a corresponding line */
1715         line = dwarf_getsrc_die(&cudie, (Dwarf_Addr)addr);
1716         if (line) {
1717                 if (dwarf_lineaddr(line, &laddr) == 0 &&
1718                     (Dwarf_Addr)addr == laddr &&
1719                     dwarf_lineno(line, &lineno) == 0) {
1720                         tmp = dwarf_linesrc(line, NULL, NULL);
1721                         if (tmp) {
1722                                 ppt->line = lineno;
1723                                 ppt->file = strdup(tmp);
1724                                 if (ppt->file == NULL) {
1725                                         ret = -ENOMEM;
1726                                         goto end;
1727                                 }
1728                                 found = true;
1729                         }
1730                 }
1731         }
1732
1733         /* Find a corresponding function */
1734         if (die_find_real_subprogram(&cudie, (Dwarf_Addr)addr, &spdie)) {
1735                 tmp = dwarf_diename(&spdie);
1736                 if (!tmp || dwarf_entrypc(&spdie, &eaddr) != 0)
1737                         goto end;
1738
1739                 if (ppt->line) {
1740                         if (die_find_inlinefunc(&spdie, (Dwarf_Addr)addr,
1741                                                 &indie)) {
1742                                 /* addr in an inline function */
1743                                 tmp = dwarf_diename(&indie);
1744                                 if (!tmp)
1745                                         goto end;
1746                                 ret = dwarf_decl_line(&indie, &lineno);
1747                         } else {
1748                                 if (eaddr == addr) {    /* Function entry */
1749                                         lineno = ppt->line;
1750                                         ret = 0;
1751                                 } else
1752                                         ret = dwarf_decl_line(&spdie, &lineno);
1753                         }
1754                         if (ret == 0) {
1755                                 /* Make a relative line number */
1756                                 ppt->line -= lineno;
1757                                 goto found;
1758                         }
1759                 }
1760                 /* We don't have a line number, let's use offset */
1761                 ppt->offset = addr - (unsigned long)eaddr;
1762 found:
1763                 ppt->function = strdup(tmp);
1764                 if (ppt->function == NULL) {
1765                         ret = -ENOMEM;
1766                         goto end;
1767                 }
1768                 found = true;
1769         }
1770
1771 end:
1772         if (dwfl)
1773                 dwfl_end(dwfl);
1774         if (ret >= 0)
1775                 ret = found ? 1 : 0;
1776         return ret;
1777 }
1778
1779 /* Add a line and store the src path */
1780 static int line_range_add_line(const char *src, unsigned int lineno,
1781                                struct line_range *lr)
1782 {
1783         /* Copy source path */
1784         if (!lr->path) {
1785                 lr->path = strdup(src);
1786                 if (lr->path == NULL)
1787                         return -ENOMEM;
1788         }
1789         return line_list__add_line(&lr->line_list, lineno);
1790 }
1791
1792 static int line_range_walk_cb(const char *fname, int lineno,
1793                               Dwarf_Addr addr __used,
1794                               void *data)
1795 {
1796         struct line_finder *lf = data;
1797
1798         if ((strtailcmp(fname, lf->fname) != 0) ||
1799             (lf->lno_s > lineno || lf->lno_e < lineno))
1800                 return 0;
1801
1802         if (line_range_add_line(fname, lineno, lf->lr) < 0)
1803                 return -EINVAL;
1804
1805         return 0;
1806 }
1807
1808 /* Find line range from its line number */
1809 static int find_line_range_by_line(Dwarf_Die *sp_die, struct line_finder *lf)
1810 {
1811         int ret;
1812
1813         ret = die_walk_lines(sp_die ?: &lf->cu_die, line_range_walk_cb, lf);
1814
1815         /* Update status */
1816         if (ret >= 0)
1817                 if (!list_empty(&lf->lr->line_list))
1818                         ret = lf->found = 1;
1819                 else
1820                         ret = 0;        /* Lines are not found */
1821         else {
1822                 free(lf->lr->path);
1823                 lf->lr->path = NULL;
1824         }
1825         return ret;
1826 }
1827
1828 static int line_range_inline_cb(Dwarf_Die *in_die, void *data)
1829 {
1830         struct dwarf_callback_param *param = data;
1831
1832         param->retval = find_line_range_by_line(in_die, param->data);
1833         return DWARF_CB_ABORT;  /* No need to find other instances */
1834 }
1835
1836 /* Search function from function name */
1837 static int line_range_search_cb(Dwarf_Die *sp_die, void *data)
1838 {
1839         struct dwarf_callback_param *param = data;
1840         struct line_finder *lf = param->data;
1841         struct line_range *lr = lf->lr;
1842
1843         if (dwarf_tag(sp_die) == DW_TAG_subprogram &&
1844             die_compare_name(sp_die, lr->function)) {
1845                 lf->fname = dwarf_decl_file(sp_die);
1846                 dwarf_decl_line(sp_die, &lr->offset);
1847                 pr_debug("fname: %s, lineno:%d\n", lf->fname, lr->offset);
1848                 lf->lno_s = lr->offset + lr->start;
1849                 if (lf->lno_s < 0)      /* Overflow */
1850                         lf->lno_s = INT_MAX;
1851                 lf->lno_e = lr->offset + lr->end;
1852                 if (lf->lno_e < 0)      /* Overflow */
1853                         lf->lno_e = INT_MAX;
1854                 pr_debug("New line range: %d to %d\n", lf->lno_s, lf->lno_e);
1855                 lr->start = lf->lno_s;
1856                 lr->end = lf->lno_e;
1857                 if (dwarf_func_inline(sp_die)) {
1858                         struct dwarf_callback_param _param;
1859                         _param.data = (void *)lf;
1860                         _param.retval = 0;
1861                         dwarf_func_inline_instances(sp_die,
1862                                                     line_range_inline_cb,
1863                                                     &_param);
1864                         param->retval = _param.retval;
1865                 } else
1866                         param->retval = find_line_range_by_line(sp_die, lf);
1867                 return DWARF_CB_ABORT;
1868         }
1869         return DWARF_CB_OK;
1870 }
1871
1872 static int find_line_range_by_func(struct line_finder *lf)
1873 {
1874         struct dwarf_callback_param param = {.data = (void *)lf, .retval = 0};
1875         dwarf_getfuncs(&lf->cu_die, line_range_search_cb, &param, 0);
1876         return param.retval;
1877 }
1878
1879 int find_line_range(int fd, struct line_range *lr)
1880 {
1881         struct line_finder lf = {.lr = lr, .found = 0};
1882         int ret = 0;
1883         Dwarf_Off off = 0, noff;
1884         size_t cuhl;
1885         Dwarf_Die *diep;
1886         Dwarf *dbg = NULL;
1887         Dwfl *dwfl;
1888         Dwarf_Addr bias;        /* Currently ignored */
1889         const char *comp_dir;
1890
1891         dbg = dwfl_init_offline_dwarf(fd, &dwfl, &bias);
1892         if (!dbg) {
1893                 pr_warning("No debug information found in the vmlinux - "
1894                         "please rebuild with CONFIG_DEBUG_INFO=y.\n");
1895                 return -EBADF;
1896         }
1897
1898         /* Loop on CUs (Compilation Unit) */
1899         while (!lf.found && ret >= 0) {
1900                 if (dwarf_nextcu(dbg, off, &noff, &cuhl, NULL, NULL, NULL) != 0)
1901                         break;
1902
1903                 /* Get the DIE(Debugging Information Entry) of this CU */
1904                 diep = dwarf_offdie(dbg, off + cuhl, &lf.cu_die);
1905                 if (!diep)
1906                         continue;
1907
1908                 /* Check if target file is included. */
1909                 if (lr->file)
1910                         lf.fname = cu_find_realpath(&lf.cu_die, lr->file);
1911                 else
1912                         lf.fname = 0;
1913
1914                 if (!lr->file || lf.fname) {
1915                         if (lr->function)
1916                                 ret = find_line_range_by_func(&lf);
1917                         else {
1918                                 lf.lno_s = lr->start;
1919                                 lf.lno_e = lr->end;
1920                                 ret = find_line_range_by_line(NULL, &lf);
1921                         }
1922                 }
1923                 off = noff;
1924         }
1925
1926         /* Store comp_dir */
1927         if (lf.found) {
1928                 comp_dir = cu_get_comp_dir(&lf.cu_die);
1929                 if (comp_dir) {
1930                         lr->comp_dir = strdup(comp_dir);
1931                         if (!lr->comp_dir)
1932                                 ret = -ENOMEM;
1933                 }
1934         }
1935
1936         pr_debug("path: %s\n", lr->path);
1937         dwfl_end(dwfl);
1938         return (ret < 0) ? ret : lf.found;
1939 }
1940