bfd_entry_t *entry;
/** backtrace address */
bfd_vma vma;
- /** stream to log to */
- FILE *file;
- /** TRUE if complete */
+ /** TRUE if address found */
bool found;
+ /** optional stream to log to */
+ FILE *file;
+ /** optional list of function names to match */
+ char **list;
+ /** optional number of names in list */
+ int count;
+ /** TRUE if found function name is in list */
+ bool in_list;
} bfd_find_data_t;
/**
const char *function;
char fbuf[512] = "", sbuf[512] = "";
u_int line;
+ int i;
+
+ if (data->found || (get_section_flags(abfd, section) & SEC_ALLOC) == 0)
+ {
+ return;
+ }
+ vma = get_section_vma(abfd, section);
+ if (data->vma < vma)
+ {
+ return;
+ }
+ size = get_section_size(section);
+ if (data->vma >= vma + size)
+ {
+ return;
+ }
- if (!data->found || (get_section_flags(abfd, section) & SEC_ALLOC) != 0)
+ data->found = bfd_find_nearest_line(abfd, section, data->entry->syms,
+ data->vma - vma, &source, &function,
+ &line);
+ if (!data->found)
+ {
+ return;
+ }
+ if (data->count && function)
{
- vma = get_section_vma(abfd, section);
- if (data->vma >= vma)
+ for (i = 0; i < data->count; i++)
{
- size = get_section_size(section);
- if (data->vma < vma + size)
+ if (streq(function, data->list[i]))
{
- data->found = bfd_find_nearest_line(abfd, section,
- data->entry->syms, data->vma - vma,
- &source, &function, &line);
- if (data->found)
- {
- if (source || function)
- {
- if (function)
- {
- snprintf(fbuf, sizeof(fbuf), "%s%s() ",
- esc(data->file, TTY_FG_BLUE), function);
- }
- if (source)
- {
- snprintf(sbuf, sizeof(sbuf), "%s@ %s:%d",
- esc(data->file, TTY_FG_GREEN), source, line);
- }
- println(data->file, " -> %s%s%s", fbuf, sbuf,
- esc(data->file, TTY_FG_DEF));
- }
- }
+ data->in_list = TRUE;
+ break;
}
}
}
+ else if (data->file && (source || function))
+ {
+ if (function)
+ {
+ snprintf(fbuf, sizeof(fbuf), "%s%s() ",
+ esc(data->file, TTY_FG_BLUE), function);
+ }
+ if (source)
+ {
+ snprintf(sbuf, sizeof(sbuf), "%s@ %s:%d",
+ esc(data->file, TTY_FG_GREEN), source, line);
+ }
+ println(data->file, " -> %s%s%s", fbuf, sbuf,
+ esc(data->file, TTY_FG_DEF));
+ }
}
/**
}
/**
- * Print the source file with line number to file, libbfd variant
+ * Lookup the given address
*/
-static void print_sourceline(FILE *file, char *filename, void *ptr, void *base)
+static void lookup_addr(char *filename, bfd_find_data_t *data)
{
bfd_entry_t *entry;
- bfd_find_data_t data = {
- .file = file,
- .vma = (uintptr_t)ptr,
- };
bool old = FALSE;
bfd_mutex->lock(bfd_mutex);
entry = get_bfd_entry(filename);
if (entry)
{
- data.entry = entry;
- bfd_map_over_sections(entry->abfd, (void*)find_addr, &data);
+ data->entry = entry;
+ bfd_map_over_sections(entry->abfd, (void*)find_addr, data);
}
if (lib && lib->leak_detective)
{
bfd_mutex->unlock(bfd_mutex);
}
+/**
+ * Print the source file with line number to file, libbfd variant
+ */
+static void print_sourceline(FILE *file, char *filename, void *ptr, void *base)
+{
+ bfd_find_data_t data = {
+ .file = file,
+ .vma = (uintptr_t)ptr,
+ };
+
+ lookup_addr(filename, &data);
+}
+
+/**
+ * Check if the function name of the source line is in the given list
+ */
+static bool contains_function_bfd(char *filename, void *ptr, char *list[],
+ int count)
+{
+ bfd_find_data_t data = {
+ .vma = (uintptr_t)ptr,
+ .list = list,
+ .count = count,
+ };
+
+ lookup_addr(filename, &data);
+ return data.in_list;
+}
+
#else /* !HAVE_BFD_H */
void backtrace_init() {}
{
Dl_info info;
- if (dladdr(this->frames[i], &info) && info.dli_sname)
+ if (dladdr(this->frames[i], &info))
{
- for (j = 0; j < count; j++)
+ if (info.dli_sname)
+ {
+ for (j = 0; j < count; j++)
+ {
+ if (streq(info.dli_sname, function[j]))
+ {
+ return TRUE;
+ }
+ }
+ }
+#ifdef HAVE_BFD_H
+ else if (info.dli_fname[0])
{
- if (streq(info.dli_sname, function[j]))
+ void *ptr = this->frames[i];
+
+ if (strstr(info.dli_fname, ".so"))
+ {
+ ptr = (void*)(this->frames[i] - info.dli_fbase);
+ }
+ if (contains_function_bfd((char*)info.dli_fname, ptr,
+ function, count))
{
return TRUE;
}
}
+#endif /* HAVE_BFD_H */
}
}
#elif defined(HAVE_DBGHELP)