summaryrefslogtreecommitdiff
path: root/libdwfl
diff options
context:
space:
mode:
authorRoland McGrath <roland@redhat.com>2005-12-05 22:46:21 +0000
committerRoland McGrath <roland@redhat.com>2005-12-05 22:46:21 +0000
commit994b4899278199fc4d307780dac0ea50b238bc74 (patch)
tree319952538a8556fa7f4d1ffcb4ae258fc6c47a5b /libdwfl
parent038129b11ac71a13ccaf9029122be86d6c532990 (diff)
downloadelfutils-994b4899278199fc4d307780dac0ea50b238bc74.tar.gz
merge of 2cc527e6d8c8ff19dab478f7d12e58f1cfa6d6f5
and 7b542932f3e2947183b45bdbf39d448f457da9fd
Diffstat (limited to 'libdwfl')
-rw-r--r--libdwfl/ChangeLog15
-rw-r--r--libdwfl/Makefile.am3
-rw-r--r--libdwfl/dwfl_end.c1
-rw-r--r--libdwfl/dwfl_module_getdwarf.c27
-rw-r--r--libdwfl/dwfl_module_register_names.c60
-rw-r--r--libdwfl/libdwfl.h14
-rw-r--r--libdwfl/libdwflP.h5
7 files changed, 117 insertions, 8 deletions
diff --git a/libdwfl/ChangeLog b/libdwfl/ChangeLog
index e7b67e1e..f6f9565c 100644
--- a/libdwfl/ChangeLog
+++ b/libdwfl/ChangeLog
@@ -1,3 +1,18 @@
+2005-11-26 Roland McGrath <roland@redhat.com>
+
+ * dwfl_end.c (dwfl_end): Free the DWFL itself.
+
+2005-11-25 Roland McGrath <roland@redhat.com>
+
+ * dwfl_module_getdwarf.c (__libdwfl_module_getebl): New function.
+ (load_dw): Use it.
+ * dwfl_module_register_names.c (dwfl_module_register_names): Likewise.
+ * libdwflP.h: Declare it.
+
+ * dwfl_module_register_names.c: New file.
+ * Makefile.am (libdwfl_a_SOURCES): Add it.
+ * libdwfl.h: Declare dwfl_module_register_names.
+
2005-11-21 Roland McGrath <roland@redhat.com>
* linux-kernel-modules.c (dwfl_linux_kernel_module_section_address):
diff --git a/libdwfl/Makefile.am b/libdwfl/Makefile.am
index b2f4e9d2..787427ca 100644
--- a/libdwfl/Makefile.am
+++ b/libdwfl/Makefile.am
@@ -53,7 +53,8 @@ libdwfl_a_SOURCES = dwfl_begin.c dwfl_end.c dwfl_error.c \
dwfl_module_getsrc_file.c \
libdwfl_crc32.c libdwfl_crc32_file.c \
elf-from-memory.c \
- dwfl_module_return_value_location.c
+ dwfl_module_return_value_location.c \
+ dwfl_module_register_names.c
if MUDFLAP
diff --git a/libdwfl/dwfl_end.c b/libdwfl/dwfl_end.c
index b2836d30..01608df5 100644
--- a/libdwfl/dwfl_end.c
+++ b/libdwfl/dwfl_end.c
@@ -22,5 +22,6 @@ dwfl_end (Dwfl *dwfl)
if (dwfl->modules[i] != NULL)
__libdwfl_module_free (dwfl->modules[i]);
free (dwfl->modules);
+ free (dwfl);
}
}
diff --git a/libdwfl/dwfl_module_getdwarf.c b/libdwfl/dwfl_module_getdwarf.c
index 50245750..f8179869 100644
--- a/libdwfl/dwfl_module_getdwarf.c
+++ b/libdwfl/dwfl_module_getdwarf.c
@@ -281,6 +281,24 @@ find_symtab (Dwfl_Module *mod)
}
+/* Try to open a libebl backend for MOD. */
+Dwfl_Error
+internal_function_def
+__libdwfl_module_getebl (Dwfl_Module *mod)
+{
+ if (mod->ebl == NULL)
+ {
+ find_file (mod);
+ if (mod->elferr != DWFL_E_NOERROR)
+ return mod->elferr;
+
+ mod->ebl = ebl_openbackend (mod->main.elf);
+ if (mod->ebl == NULL)
+ return DWFL_E_LIBEBL;
+ }
+ return DWFL_E_NOERROR;
+}
+
/* Try to start up libdw on DEBUGFILE. */
static Dwfl_Error
load_dw (Dwfl_Module *mod, struct dwfl_file *debugfile)
@@ -293,12 +311,9 @@ load_dw (Dwfl_Module *mod, struct dwfl_file *debugfile)
if (cb->section_address == NULL)
return DWFL_E_NOREL;
- if (mod->ebl == NULL)
- {
- mod->ebl = ebl_openbackend (mod->main.elf);
- if (mod->ebl == NULL)
- return DWFL_E_LIBEBL;
- }
+ Dwfl_Error error = __libdwfl_module_getebl (mod);
+ if (error != DWFL_E_NOERROR)
+ return error;
find_symtab (mod);
Dwfl_Error result = mod->symerr;
diff --git a/libdwfl/dwfl_module_register_names.c b/libdwfl/dwfl_module_register_names.c
new file mode 100644
index 00000000..e9466902
--- /dev/null
+++ b/libdwfl/dwfl_module_register_names.c
@@ -0,0 +1,60 @@
+/* Enumerate DWARF register numbers and their names.
+ Copyright (C) 2005 Red Hat, Inc.
+
+ This program is Open Source software; you can redistribute it and/or
+ modify it under the terms of the Open Software License version 1.0 as
+ published by the Open Source Initiative.
+
+ You should have received a copy of the Open Software License along
+ with this program; if not, you may obtain a copy of the Open Software
+ License version 1.0 from http://www.opensource.org/licenses/osl.php or
+ by writing the Open Source Initiative c/o Lawrence Rosen, Esq.,
+ 3001 King Ranch Road, Ukiah, CA 95482. */
+
+#include "libdwflP.h"
+
+
+int
+dwfl_module_register_names (mod, func, arg)
+ Dwfl_Module *mod;
+ int (*func) (void *, int regno, const char *setname,
+ const char *prefix, const char *regname);
+ void *arg;
+{
+ if (unlikely (mod == NULL))
+ return -1;
+
+ if (unlikely (mod->ebl == NULL))
+ {
+ Dwfl_Error error = __libdwfl_module_getebl (mod);
+ if (error != DWFL_E_NOERROR)
+ {
+ __libdwfl_seterrno (error);
+ return -1;
+ }
+ }
+
+ int nregs = ebl_register_name (mod->ebl, -1, NULL, 0, NULL, NULL);
+ int result = 0;
+ for (int regno = 0; regno < nregs && likely (result == 0); ++regno)
+ {
+ char name[32];
+ const char *setname = NULL;
+ const char *prefix = NULL;
+ ssize_t len = ebl_register_name (mod->ebl, regno, name, sizeof name,
+ &prefix, &setname);
+ if (unlikely (len < 0))
+ {
+ __libdwfl_seterrno (DWFL_E_LIBEBL);
+ result = -1;
+ break;
+ }
+ if (likely (len > 0))
+ {
+ assert (len > 1); /* Backend should never yield "". */
+ result = (*func) (arg, regno, setname, prefix, name);
+ }
+ }
+
+ return result;
+}
diff --git a/libdwfl/libdwfl.h b/libdwfl/libdwfl.h
index 8b069e27..f4652809 100644
--- a/libdwfl/libdwfl.h
+++ b/libdwfl/libdwfl.h
@@ -344,5 +344,19 @@ extern int dwfl_module_return_value_location (Dwfl_Module *mod,
Dwarf_Die *functypedie,
const Dwarf_Op **locops);
+/* Enumerate the DWARF register numbers and their names.
+ For each register, CALLBACK gets its DWARF number, a string describing
+ the register set (such as "integer" or "FPU"), a prefix used in
+ assembler syntax (such as "%" or "$", may be ""), and the name for the
+ register (contains identifier characters only, possibly all digits).
+ The REGNAME string is valid only during the callback. */
+extern int dwfl_module_register_names (Dwfl_Module *mod,
+ int (*callback) (void *arg,
+ int regno,
+ const char *setname,
+ const char *prefix,
+ const char *regname),
+ void *arg);
+
#endif /* libdwfl.h */
diff --git a/libdwfl/libdwflP.h b/libdwfl/libdwflP.h
index 6c1bcd8e..a0d88d11 100644
--- a/libdwfl/libdwflP.h
+++ b/libdwfl/libdwflP.h
@@ -180,7 +180,6 @@ struct dwfl_arange
-
extern void __libdwfl_module_free (Dwfl_Module *mod) internal_function;
@@ -201,6 +200,10 @@ extern Dwfl_Error __libdwfl_relocate_value (Dwfl_Module *mod,
GElf_Addr *value)
internal_function;
+
+/* Ensure that MOD->ebl is set up. */
+extern Dwfl_Error __libdwfl_module_getebl (Dwfl_Module *mod) internal_function;
+
/* Iterate through all the CU's in the module. Start by passing a null
LASTCU, and then pass the last *CU returned. Success return with null
*CU no more CUs. */