summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/link.h20
-rw-r--r--ldso/ldso/dl-elf.c24
2 files changed, 43 insertions, 1 deletions
diff --git a/include/link.h b/include/link.h
index c3ef6a6b0..f8e7f629d 100644
--- a/include/link.h
+++ b/include/link.h
@@ -92,4 +92,24 @@ struct link_map
struct link_map *l_next, *l_prev; /* Chain of loaded objects. */
};
+#ifdef __USE_GNU
+
+struct dl_phdr_info
+ {
+ ElfW(Addr) dlpi_addr;
+ const char *dlpi_name;
+ const ElfW(Phdr) *dlpi_phdr;
+ ElfW(Half) dlpi_phnum;
+ };
+
+__BEGIN_DECLS
+
+extern int dl_iterate_phdr (int (*callback) (struct dl_phdr_info *info,
+ size_t size, void *data),
+ void *data) __THROW;
+
+__END_DECLS
+
+#endif
+
#endif /* link.h */
diff --git a/ldso/ldso/dl-elf.c b/ldso/ldso/dl-elf.c
index e11cb0d92..c58ca5dfb 100644
--- a/ldso/ldso/dl-elf.c
+++ b/ldso/ldso/dl-elf.c
@@ -894,4 +894,26 @@ char *_dl_strdup(const char *string)
_dl_strcpy(retval, string);
return retval;
}
-
+#ifdef __USE_GNU
+#if ! defined LIBDL || (! defined PIC && ! defined __PIC__)
+int
+__dl_iterate_phdr (int (*callback) (struct dl_phdr_info *info, size_t size, void *data), void *data)
+{
+ struct elf_resolve *l;
+ struct dl_phdr_info info;
+ int ret = 0;
+
+ for (l = _dl_loaded_modules; l != NULL; l = l->next) {
+ info.dlpi_addr = l->loadaddr;
+ info.dlpi_name = l->libname;
+ info.dlpi_phdr = l->ppnt;
+ info.dlpi_phnum = l->n_phent;
+ ret = callback (&info, sizeof (struct dl_phdr_info), data);
+ if (ret)
+ break;
+ }
+ return ret;
+}
+strong_alias(__dl_iterate_phdr, dl_iterate_phdr);
+#endif
+#endif