42 ret = dwarf_getsrcfiles(cu_die, &files, &nfiles);
46 for (i = 0; i < nfiles; i++) {
47 src = dwarf_filesrc(files, i,
NULL,
NULL);
67 if (dwarf_attr(cu_die, DW_AT_comp_dir, &attr) ==
NULL)
69 return dwarf_formstring(&attr);
87 line = dwarf_getsrc_die(cu_die, (Dwarf_Addr)addr);
88 if (line && dwarf_lineaddr(line, &laddr) == 0 &&
89 addr == (
unsigned long)laddr && dwarf_lineno(line, lineno) == 0) {
90 *fname = dwarf_linesrc(line,
NULL,
NULL);
99 static int __die_find_inline_cb(Dwarf_Die *die_mem,
void *
data);
142 name = dwarf_diename(dw_die);
143 return name ? (
strcmp(tname, name) == 0) :
false;
155 Dwarf_Attribute
attr;
158 if (!dwarf_attr(in_die, DW_AT_call_line, &attr))
161 dwarf_formudata(&attr, &ret);
175 Dwarf_Attribute
attr;
177 if (dwarf_attr_integrate(vr_die, DW_AT_type, &attr) &&
178 dwarf_formref_die(&attr, die_mem))
185 static Dwarf_Die *__die_get_real_type(Dwarf_Die *vr_die, Dwarf_Die *die_mem)
193 tag = dwarf_tag(vr_die);
194 }
while (tag == DW_TAG_const_type ||
195 tag == DW_TAG_restrict_type ||
196 tag == DW_TAG_volatile_type ||
197 tag == DW_TAG_shared_type);
215 vr_die = __die_get_real_type(vr_die, die_mem);
216 }
while (vr_die && dwarf_tag(vr_die) == DW_TAG_typedef);
222 static int die_get_attr_udata(Dwarf_Die *tp_die,
unsigned int attr_name,
225 Dwarf_Attribute
attr;
227 if (dwarf_attr(tp_die, attr_name, &attr) ==
NULL ||
228 dwarf_formudata(&attr, result) != 0)
235 static int die_get_attr_sdata(Dwarf_Die *tp_die,
unsigned int attr_name,
238 Dwarf_Attribute
attr;
240 if (dwarf_attr(tp_die, attr_name, &attr) ==
NULL ||
241 dwarf_formsdata(&attr, result) != 0)
258 if (die_get_attr_udata(tp_die, DW_AT_encoding, &ret))
261 return (ret == DW_ATE_signed_char || ret == DW_ATE_signed ||
262 ret == DW_ATE_signed_fixed);
275 Dwarf_Attribute
attr;
280 if (dwarf_attr(mb_die, DW_AT_data_member_location, &attr) ==
NULL)
283 if (dwarf_formudata(&attr, offs) != 0) {
285 ret = dwarf_getlocation(&attr, &expr, &nexpr);
286 if (ret < 0 || nexpr == 0)
289 if (expr[0].atom != DW_OP_plus_uconst || nexpr != 1) {
290 pr_debug(
"Unable to get offset:Unexpected OP %x (%zd)\n",
291 expr[0].atom, nexpr);
294 *offs = (Dwarf_Word)expr[0].
number;
300 static int die_get_call_fileno(Dwarf_Die *in_die)
304 if (die_get_attr_sdata(in_die, DW_AT_call_file, &idx) == 0)
311 static int die_get_decl_fileno(Dwarf_Die *pdie)
315 if (die_get_attr_sdata(pdie, DW_AT_decl_file, &idx) == 0)
334 idx = die_get_call_fileno(in_die);
335 if (idx < 0 || !dwarf_diecu(in_die, &cu_die,
NULL,
NULL) ||
336 dwarf_getsrcfiles(&cu_die, &files,
NULL) != 0)
339 return dwarf_filesrc(files, idx,
NULL,
NULL);
359 int (*
callback)(Dwarf_Die *,
void *),
360 void *
data, Dwarf_Die *die_mem)
365 ret = dwarf_child(rt_die, die_mem);
376 memcpy(die_mem, &child_die,
sizeof(Dwarf_Die));
380 dwarf_siblingof(die_mem, die_mem) == 0);
391 static int __die_search_func_cb(Dwarf_Die *fn_die,
void *
data)
395 if (dwarf_tag(fn_die) == DW_TAG_subprogram &&
396 dwarf_haspc(fn_die, ad->
addr)) {
398 return DWARF_CB_ABORT;
419 if (!dwarf_getfuncs(cu_die, __die_search_func_cb, &ad, 0))
426 static int __die_find_inline_cb(Dwarf_Die *die_mem,
void *
data)
428 Dwarf_Addr *addr =
data;
430 if (dwarf_tag(die_mem) == DW_TAG_inlined_subroutine &&
431 dwarf_haspc(die_mem, *addr))
453 sp_die =
die_find_child(sp_die, __die_find_inline_cb, &addr, &tmp_die);
459 memcpy(die_mem, sp_die,
sizeof(Dwarf_Die));
474 static int __die_walk_instances_cb(Dwarf_Die *inst,
void *data)
477 Dwarf_Attribute attr_mem;
478 Dwarf_Die origin_mem;
479 Dwarf_Attribute *
attr;
483 attr = dwarf_attr(inst, DW_AT_abstract_origin, &attr_mem);
487 origin = dwarf_formref_die(attr, &origin_mem);
488 if (origin ==
NULL || origin->addr != iwp->
addr)
492 if (dwarf_tag(inst) == DW_TAG_inlined_subroutine) {
493 dwarf_decl_line(origin, &tmp);
495 tmp = die_get_decl_fileno(origin);
496 if (die_get_call_fileno(inst) == tmp)
522 .
addr = or_die->addr,
544 static int __die_walk_funclines_cb(Dwarf_Die *in_die,
void *data)
551 if (dwarf_tag(in_die) == DW_TAG_inlined_subroutine) {
554 if (fname && lineno > 0 && dwarf_entrypc(in_die, &addr) == 0) {
565 fname = dwarf_decl_file(in_die);
566 if (fname && dwarf_decl_line(in_die, &lineno) == 0) {
578 static int __die_walk_funclines(Dwarf_Die *sp_die,
bool recursive,
593 fname = dwarf_decl_file(sp_die);
594 if (fname && dwarf_decl_line(sp_die, &lineno) == 0 &&
595 dwarf_entrypc(sp_die, &addr) == 0) {
605 static int __die_walk_culines_cb(Dwarf_Die *sp_die,
void *data)
611 return DWARF_CB_ABORT;
635 Dwarf_Die die_mem, *cu_die;
639 if (dwarf_tag(rt_die) != DW_TAG_compile_unit)
640 cu_die = dwarf_diecu(rt_die, &die_mem,
NULL,
NULL);
644 pr_debug2(
"Failed to get CU from given DIE.\n");
649 if (dwarf_getsrclines(cu_die, &lines, &nlines) != 0) {
650 pr_debug2(
"Failed to get source lines on this CU.\n");
653 pr_debug2(
"Get %zd lines from this CU\n", nlines);
656 for (i = 0; i < nlines; i++) {
657 line = dwarf_onesrcline(lines, i);
659 dwarf_lineno(line, &lineno) != 0 ||
660 dwarf_lineaddr(line, &addr) != 0) {
662 "Possible error in debuginfo.\n");
666 if (rt_die != cu_die)
672 if (!dwarf_haspc(rt_die, addr) ||
676 fname = dwarf_linesrc(line,
NULL,
NULL);
678 ret =
callback(fname, lineno, addr, data);
687 if (rt_die != cu_die)
692 ret = __die_walk_funclines(rt_die,
false, callback, data);
699 dwarf_getfuncs(cu_die, __die_walk_culines_cb, ¶m, 0);
711 static int __die_find_variable_cb(Dwarf_Die *die_mem,
void *data)
716 tag = dwarf_tag(die_mem);
717 if ((tag == DW_TAG_formal_parameter ||
718 tag == DW_TAG_variable) &&
722 if (dwarf_haspc(die_mem, fvp->
addr))
738 Dwarf_Addr addr, Dwarf_Die *die_mem)
742 return die_find_child(sp_die, __die_find_variable_cb, (
void *)&fvp,
746 static int __die_find_member_cb(Dwarf_Die *die_mem,
void *data)
750 if ((dwarf_tag(die_mem) == DW_TAG_member) &&
788 const char *tmp =
"";
790 if (__die_get_real_type(vr_die, &type) ==
NULL)
793 tag = dwarf_tag(&type);
794 if (tag == DW_TAG_array_type || tag == DW_TAG_pointer_type)
796 else if (tag == DW_TAG_subroutine_type) {
798 ret =
snprintf(buf, len,
"(function_type)");
801 if (!dwarf_diename(&type))
803 if (tag == DW_TAG_union_type)
805 else if (tag == DW_TAG_structure_type)
807 else if (tag == DW_TAG_enumeration_type)
810 ret =
snprintf(buf, len,
"%s%s", tmp, dwarf_diename(&type));
815 ret2 =
snprintf(buf + ret, len - ret,
"%s", tmp);
816 ret = (ret2 >= len -
ret) ? -
E2BIG : ret2 + ret;
835 pr_debug(
"Failed to get type, make it unknown.\n");
836 ret =
snprintf(buf, len,
"(unknown_type)");
839 ret2 =
snprintf(buf + ret, len - ret,
"\t%s",
840 dwarf_diename(vr_die));
841 ret = (ret2 >= len -
ret) ? -
E2BIG : ret2 + ret;