From 5af52fe4fc36c1a355f4bfad58f80f52f822f768 Mon Sep 17 00:00:00 2001 From: norly Date: Sat, 15 Jun 2013 11:53:17 +0100 Subject: [PATCH] Make symtab and reltab resident in ElfuScn --- include/libelfu/types.h | 88 ++++++++++++++++++++--------------------- src/modelops/clone.c | 4 +- src/modelops/fromFile.c | 57 ++++---------------------- src/modelops/relocate.c | 13 +++--- 4 files changed, 59 insertions(+), 103 deletions(-) diff --git a/include/libelfu/types.h b/include/libelfu/types.h index b216e53..46fbc69 100644 --- a/include/libelfu/types.h +++ b/include/libelfu/types.h @@ -7,49 +7,6 @@ #include -typedef struct ElfuScn { - GElf_Shdr shdr; - - Elf_Data data; - - struct ElfuScn *linkptr; - struct ElfuScn *infoptr; - - struct ElfuScn *oldptr; - - struct ElfuSymtab *symtab; - struct ElfuReltab *reltab; - - CIRCLEQ_ENTRY(ElfuScn) elemChildScn; - CIRCLEQ_ENTRY(ElfuScn) elem; -} ElfuScn; - - -typedef struct ElfuPhdr { - GElf_Phdr phdr; - - CIRCLEQ_HEAD(ChildScnList, ElfuScn) childScnList; - CIRCLEQ_HEAD(ChildPhdrList, ElfuPhdr) childPhdrList; - - CIRCLEQ_ENTRY(ElfuPhdr) elemChildPhdr; - CIRCLEQ_ENTRY(ElfuPhdr) elem; -} ElfuPhdr; - - -typedef struct { - int elfclass; - GElf_Ehdr ehdr; - - CIRCLEQ_HEAD(PhdrList, ElfuPhdr) phdrList; - CIRCLEQ_HEAD(OrphanScnList, ElfuScn) orphanScnList; - - ElfuScn *shstrtab; -} ElfuElf; - - - - - typedef struct ElfuSym { char *name; @@ -60,7 +17,7 @@ typedef struct ElfuSym { unsigned char type; unsigned char other; - ElfuScn *scnptr; + struct ElfuScn *scnptr; int shndx; CIRCLEQ_ENTRY(ElfuSym) elem; @@ -94,4 +51,47 @@ typedef struct ElfuReltab { } ElfuReltab; + + + + +typedef struct ElfuScn { + GElf_Shdr shdr; + + Elf_Data data; + + struct ElfuScn *linkptr; + struct ElfuScn *infoptr; + + struct ElfuScn *oldptr; + + struct ElfuSymtab symtab; + struct ElfuReltab reltab; + + CIRCLEQ_ENTRY(ElfuScn) elemChildScn; + CIRCLEQ_ENTRY(ElfuScn) elem; +} ElfuScn; + + +typedef struct ElfuPhdr { + GElf_Phdr phdr; + + CIRCLEQ_HEAD(ChildScnList, ElfuScn) childScnList; + CIRCLEQ_HEAD(ChildPhdrList, ElfuPhdr) childPhdrList; + + CIRCLEQ_ENTRY(ElfuPhdr) elemChildPhdr; + CIRCLEQ_ENTRY(ElfuPhdr) elem; +} ElfuPhdr; + + +typedef struct { + int elfclass; + GElf_Ehdr ehdr; + + CIRCLEQ_HEAD(PhdrList, ElfuPhdr) phdrList; + CIRCLEQ_HEAD(OrphanScnList, ElfuScn) orphanScnList; + + ElfuScn *shstrtab; +} ElfuElf; + #endif diff --git a/src/modelops/clone.c b/src/modelops/clone.c index ca4b38f..8f92919 100644 --- a/src/modelops/clone.c +++ b/src/modelops/clone.c @@ -34,8 +34,8 @@ ElfuScn* elfu_mCloneScn(ElfuScn *ms) newscn->oldptr = ms; - ms->symtab = NULL; - ms->reltab = NULL; + CIRCLEQ_INIT(&ms->symtab.syms); + CIRCLEQ_INIT(&ms->reltab.rels); return newscn; } diff --git a/src/modelops/fromFile.c b/src/modelops/fromFile.c index 23105e6..85afe20 100644 --- a/src/modelops/fromFile.c +++ b/src/modelops/fromFile.c @@ -16,9 +16,8 @@ static char* symstr(ElfuScn *symtab, size_t off) } -static ElfuSymtab* symtabFromScn32(ElfuScn *ms, ElfuScn**origScnArr) +static void parseSymtab32(ElfuScn *ms, ElfuScn**origScnArr) { - ElfuSymtab *st; size_t i; assert(ms); @@ -26,15 +25,6 @@ static ElfuSymtab* symtabFromScn32(ElfuScn *ms, ElfuScn**origScnArr) assert(origScnArr); - st = malloc(sizeof(*st)); - if (!st) { - ELFU_WARN("elfu_mSymtabFromScn32: malloc() failed for st.\n"); - goto ERROR; - } - - CIRCLEQ_INIT(&st->syms); - - for (i = 1; (i + 1) * sizeof(Elf32_Sym) <= ms->shdr.sh_size; i++) { Elf32_Sym *cursym = &(((Elf32_Sym*)ms->data.d_buf)[i]); ElfuSym *sym = malloc(sizeof(*sym)); @@ -60,38 +50,19 @@ static ElfuSymtab* symtabFromScn32(ElfuScn *ms, ElfuScn**origScnArr) } - CIRCLEQ_INSERT_TAIL(&st->syms, sym, elem); + CIRCLEQ_INSERT_TAIL(&ms->symtab.syms, sym, elem); } - - - return st; - - ERROR: - if (st) { - free(st); - } - return NULL; } -static ElfuReltab* reltabFromScn32(ElfuScn *ms) +static void parseReltab32(ElfuScn *ms) { - ElfuReltab *rt; size_t i; assert(ms); assert(ms->data.d_buf); - rt = malloc(sizeof(*rt)); - if (!rt) { - ELFU_WARN("elfu_mReltabFromScn32: malloc() failed for rt.\n"); - goto ERROR; - } - - CIRCLEQ_INIT(&rt->rels); - - for (i = 0; (i + 1) * sizeof(Elf32_Rel) <= ms->shdr.sh_size; i++) { Elf32_Rel *currel = &(((Elf32_Rel*)ms->data.d_buf)[i]); ElfuRel *rel; @@ -107,17 +78,8 @@ static ElfuReltab* reltabFromScn32(ElfuScn *ms) rel->addendUsed = 0; rel->addend = 0; - CIRCLEQ_INSERT_TAIL(&rt->rels, rel, elem); + CIRCLEQ_INSERT_TAIL(&ms->reltab.rels, rel, elem); } - - - return rt; - - ERROR: - if (rt) { - free(rt); - } - return NULL; } @@ -255,8 +217,8 @@ static ElfuScn* modelFromSection(Elf_Scn *scn) ms->oldptr = NULL; - ms->symtab = NULL; - ms->reltab = NULL; + CIRCLEQ_INIT(&ms->symtab.syms); + CIRCLEQ_INIT(&ms->reltab.rels); return ms; @@ -408,11 +370,10 @@ ElfuElf* elfu_mFromElf(Elf *e) case SHT_SYMTAB: case SHT_DYNSYM: if (me->elfclass == ELFCLASS32) { - ms->symtab = symtabFromScn32(ms, secArray); + parseSymtab32(ms, secArray); } else if (me->elfclass == ELFCLASS64) { // TODO } - assert(ms->symtab); break; } } @@ -425,11 +386,10 @@ ElfuElf* elfu_mFromElf(Elf *e) switch (ms->shdr.sh_type) { case SHT_REL: if (me->elfclass == ELFCLASS32) { - ms->reltab = reltabFromScn32(ms); + parseReltab32(ms); } else if (me->elfclass == ELFCLASS64) { // TODO } - assert(ms->reltab); break; case SHT_RELA: if (me->elfclass == ELFCLASS32) { @@ -437,7 +397,6 @@ ElfuElf* elfu_mFromElf(Elf *e) } else if (me->elfclass == ELFCLASS64) { // TODO } - assert(ms->reltab); break; } } diff --git a/src/modelops/relocate.c b/src/modelops/relocate.c index 972bda3..679f57f 100644 --- a/src/modelops/relocate.c +++ b/src/modelops/relocate.c @@ -41,11 +41,9 @@ static GElf_Word pltLookupVal(ElfuElf *metarget, char *name) /* Look up name */ - assert(relplt->reltab); assert(relplt->linkptr); - assert(relplt->linkptr->symtab); j = 0; - CIRCLEQ_FOREACH(rel, &relplt->reltab->rels, elem) { + CIRCLEQ_FOREACH(rel, &relplt->reltab.rels, elem) { GElf_Word i; ElfuSym *sym; @@ -55,7 +53,7 @@ static GElf_Word pltLookupVal(ElfuElf *metarget, char *name) continue; } - sym = CIRCLEQ_FIRST(&relplt->linkptr->symtab->syms); + sym = CIRCLEQ_FIRST(&relplt->linkptr->symtab.syms); for (i = 1; i < rel->sym; i++) { sym = CIRCLEQ_NEXT(sym, elem); } @@ -88,11 +86,10 @@ static GElf_Word symtabLookupVal(ElfuElf *metarget, ElfuScn *msst, GElf_Word ent assert(metarget); assert(msst); - assert(msst->symtab); assert(entry > 0); - assert(!CIRCLEQ_EMPTY(&msst->symtab->syms)); + assert(!CIRCLEQ_EMPTY(&msst->symtab.syms)); - sym = CIRCLEQ_FIRST(&msst->symtab->syms); + sym = CIRCLEQ_FIRST(&msst->symtab.syms); for (i = 1; i < entry; i++) { sym = CIRCLEQ_NEXT(sym, elem); } @@ -140,7 +137,7 @@ void elfu_mRelocate32(ElfuElf *metarget, ElfuScn *mstarget, ElfuScn *msrt) mstarget->shdr.sh_type, mstarget->shdr.sh_size); - CIRCLEQ_FOREACH(rel, &msrt->reltab->rels, elem) { + CIRCLEQ_FOREACH(rel, &msrt->reltab.rels, elem) { Elf32_Word *dest = (Elf32_Word*)(((char*)(mstarget->data.d_buf)) + rel->offset); Elf32_Word a = rel->addendUsed ? rel->addend : *dest; Elf32_Addr p = mstarget->shdr.sh_addr + rel->offset; -- 2.30.2