summaryrefslogtreecommitdiffstats
path: root/src/findtextrel.c
diff options
context:
space:
mode:
authorRoland McGrath <[email protected]>2010-11-22 17:48:55 -0800
committerRoland McGrath <[email protected]>2010-11-22 17:48:55 -0800
commitc8b4d919f8e86a099c25843917e7739b7d82ff53 (patch)
tree0ecfb2af91cfd910cbf60404bc16271a78973267 /src/findtextrel.c
parenta4b8ab4f181452bc6e5517f7a0c032a1049c18c6 (diff)
parent65d8e4e86abf37779b1a734ab29ad4bb4f532020 (diff)
Merge branch 'master' into portable
Diffstat (limited to 'src/findtextrel.c')
-rw-r--r--src/findtextrel.c62
1 files changed, 38 insertions, 24 deletions
diff --git a/src/findtextrel.c b/src/findtextrel.c
index 35ab3c4b..8b7925db 100644
--- a/src/findtextrel.c
+++ b/src/findtextrel.c
@@ -1,5 +1,5 @@
/* Locate source files or functions which caused text relocations.
- Copyright (C) 2005, 2006, 2007, 2009 Red Hat, Inc.
+ Copyright (C) 2005-2010 Red Hat, Inc.
This file is part of Red Hat elfutils.
Written by Ulrich Drepper <[email protected]>, 2005.
@@ -262,7 +262,10 @@ process_file (const char *fname, bool more_than_one)
the symbol table. */
Elf_Scn *symscn = NULL;
Elf_Scn *scn = NULL;
- while ((scn = elf_nextscn (elf, scn)) != NULL)
+ bool seen_dynamic = false;
+ bool have_textrel = false;
+ while ((scn = elf_nextscn (elf, scn)) != NULL
+ && (!seen_dynamic || symscn == NULL))
{
/* Handle the section if it is a symbol table. */
GElf_Shdr shdr_mem;
@@ -276,38 +279,49 @@ process_file (const char *fname, bool more_than_one)
goto err_elf_close;
}
- if (shdr->sh_type == SHT_DYNAMIC)
+ switch (shdr->sh_type)
{
- Elf_Data *data = elf_getdata (scn, NULL);
-
- for (size_t cnt = 0; cnt < shdr->sh_size / shdr->sh_entsize;
- ++cnt)
+ case SHT_DYNAMIC:
+ if (!seen_dynamic)
{
- GElf_Dyn dynmem;
- GElf_Dyn *dyn;
+ seen_dynamic = true;
+
+ Elf_Data *data = elf_getdata (scn, NULL);
- dyn = gelf_getdyn (data, cnt, &dynmem);
- if (dyn == NULL)
+ for (size_t cnt = 0; cnt < shdr->sh_size / shdr->sh_entsize;
+ ++cnt)
{
- error (0, 0, gettext ("cannot read dynamic section: %s"),
- elf_errmsg (-1));
- goto err_elf_close;
- }
+ GElf_Dyn dynmem;
+ GElf_Dyn *dyn;
- if (dyn->d_tag == DT_TEXTREL
- || (dyn->d_tag == DT_FLAGS
- && (dyn->d_un.d_val & DF_TEXTREL) != 0))
- goto have_textrel;
+ dyn = gelf_getdyn (data, cnt, &dynmem);
+ if (dyn == NULL)
+ {
+ error (0, 0, gettext ("cannot read dynamic section: %s"),
+ elf_errmsg (-1));
+ goto err_elf_close;
+ }
+
+ if (dyn->d_tag == DT_TEXTREL
+ || (dyn->d_tag == DT_FLAGS
+ && (dyn->d_un.d_val & DF_TEXTREL) != 0))
+ have_textrel = true;
+ }
}
+ break;
+
+ case SHT_SYMTAB:
+ symscn = scn;
+ break;
}
- else if (shdr->sh_type == SHT_SYMTAB)
- symscn = scn;
}
- error (0, 0, gettext ("no text relocations reported in '%s'"), fname);
- return 1;
+ if (!have_textrel)
+ {
+ error (0, 0, gettext ("no text relocations reported in '%s'"), fname);
+ return 1;
+ }
- have_textrel:;
int fd2 = -1;
Elf *elf2 = NULL;
/* Get the address ranges for the loaded segments. */