This is the mail archive of the
mailing list for the elfutils project.
Re: [PATCH] Don't assert on mod->e_type in __libdwfl_relocate_value.
- From: Mark Wielaard <mjw at redhat dot com>
- To: elfutils-devel at lists dot fedorahosted dot org
- Date: Sat, 13 Jul 2013 23:59:17 +0200
- Subject: Re: [PATCH] Don't assert on mod->e_type in __libdwfl_relocate_value.
On Fri, 2013-07-12 at 22:50 -0700, Roland McGrath wrote:
> Hmm. Unless something else depends on e_type being ET_NONE or something,
> it seems like it would be wiser just to set it earlier. The assert is
> pretty sensible in that something is very wrong if we get there for a
> non-ET_REL file.
The reason I didn't do this was because when this happens we get here
from the dwfl_build_id_find_elf callback. That will open a file it
thinks is correct, but then has to verify it through
__libdwfl_find_elf_build_id. And that could fail to match. So if we set
it earlier then it would be speculative on that Elf file being the main
Elf file of the Module, it might later change.
Since nothing seems to depend on mod->e_type being ET_NONE we could set
it speculatively. But it is a question where exactly. I would be
inclined to do it just before the __libdwfl_relocate_value call in
__libdwfl_find_elf_build_id which has access to the Elf ehdr->e_type and
expects mod to be non-null when called for ET_REL files itself.
The following seems to work for me, but might need some more testing:
diff --git a/libdwfl/dwfl_module_build_id.c b/libdwfl/dwfl_module_build_id.c
index cae007b..fdd3165 100644
@@ -128,9 +128,17 @@ __libdwfl_find_elf_build_id (Dwfl_Module *mod, Elf *elf,
vaddr = NO_VADDR;
else if (mod == NULL || ehdr->e_type != ET_REL)
vaddr = shdr->sh_addr;
- else if (__libdwfl_relocate_value (mod, elf, &shstrndx,
- elf_ndxscn (scn), &vaddr))
- vaddr = NO_VADDR;
+ // mod must be non-null for ET_REL (see check above)
+ // for the main file MOD->E_TYPE will not have been
+ // setup yet, but __libdwfl_relocate_value needs it.
+ if (mod->e_type == ET_NONE)
+ mod->e_type = ET_REL;
+ if (__libdwfl_relocate_value (mod, elf, &shstrndx,
+ elf_ndxscn (scn), &vaddr))
+ vaddr = NO_VADDR;
result = check_notes (elf_getdata (scn, NULL), vaddr);
diff --git a/libdwfl/relocate.c b/libdwfl/relocate.c
index bd51ad6..e06819d 100644
@@ -38,6 +38,8 @@ internal_function
__libdwfl_relocate_value (Dwfl_Module *mod, Elf *elf, size_t *shstrndx,
Elf32_Word shndx, GElf_Addr *value)
+ assert (mod->e_type == ET_REL);
Elf_Scn *refscn = elf_getscn (elf, shndx);
GElf_Shdr refshdr_mem, *refshdr = gelf_getshdr (refscn, &refshdr_mem);
if (refshdr == NULL)
What do you think?