summaryrefslogtreecommitdiffstats
path: root/libexec/rtld-elf/i386/reloc.c
diff options
context:
space:
mode:
Diffstat (limited to 'libexec/rtld-elf/i386/reloc.c')
-rw-r--r--libexec/rtld-elf/i386/reloc.c42
1 files changed, 24 insertions, 18 deletions
diff --git a/libexec/rtld-elf/i386/reloc.c b/libexec/rtld-elf/i386/reloc.c
index 818d2eb..9efebb3 100644
--- a/libexec/rtld-elf/i386/reloc.c
+++ b/libexec/rtld-elf/i386/reloc.c
@@ -70,23 +70,28 @@ do_copy_relocations(Obj_Entry *dstobj)
void *dstaddr;
const Elf_Sym *dstsym;
const char *name;
- unsigned long hash;
size_t size;
const void *srcaddr;
const Elf_Sym *srcsym;
- const Ver_Entry *ve;
- Obj_Entry *srcobj;
+ const Obj_Entry *srcobj, *defobj;
+ SymLook req;
+ int res;
dstaddr = (void *) (dstobj->relocbase + rel->r_offset);
dstsym = dstobj->symtab + ELF_R_SYM(rel->r_info);
name = dstobj->strtab + dstsym->st_name;
- hash = elf_hash(name);
size = dstsym->st_size;
- ve = fetch_ventry(dstobj, ELF_R_SYM(rel->r_info));
-
- for (srcobj = dstobj->next; srcobj != NULL; srcobj = srcobj->next)
- if ((srcsym = symlook_obj(name, hash, srcobj, ve, 0)) != NULL)
+ symlook_init(&req, name);
+ req.ventry = fetch_ventry(dstobj, ELF_R_SYM(rel->r_info));
+
+ for (srcobj = dstobj->next; srcobj != NULL; srcobj = srcobj->next) {
+ res = symlook_obj(&req, srcobj);
+ if (res == 0) {
+ srcsym = req.sym_out;
+ defobj = req.defobj_out;
break;
+ }
+ }
if (srcobj == NULL) {
_rtld_error("Undefined symbol \"%s\" referenced from COPY"
@@ -94,7 +99,7 @@ do_copy_relocations(Obj_Entry *dstobj)
return -1;
}
- srcaddr = (const void *) (srcobj->relocbase + srcsym->st_value);
+ srcaddr = (const void *) (defobj->relocbase + srcsym->st_value);
memcpy(dstaddr, srcaddr, size);
}
}
@@ -114,7 +119,7 @@ init_pltgot(Obj_Entry *obj)
/* Process the non-PLT relocations. */
int
-reloc_non_plt(Obj_Entry *obj, Obj_Entry *obj_rtld)
+reloc_non_plt(Obj_Entry *obj, Obj_Entry *obj_rtld, RtldLockState *lockstate)
{
const Elf_Rel *rellim;
const Elf_Rel *rel;
@@ -146,7 +151,7 @@ reloc_non_plt(Obj_Entry *obj, Obj_Entry *obj_rtld)
const Obj_Entry *defobj;
def = find_symdef(ELF_R_SYM(rel->r_info), obj, &defobj,
- false, cache);
+ false, cache, lockstate);
if (def == NULL)
goto done;
@@ -165,7 +170,7 @@ reloc_non_plt(Obj_Entry *obj, Obj_Entry *obj_rtld)
const Obj_Entry *defobj;
def = find_symdef(ELF_R_SYM(rel->r_info), obj, &defobj,
- false, cache);
+ false, cache, lockstate);
if (def == NULL)
goto done;
@@ -195,7 +200,7 @@ reloc_non_plt(Obj_Entry *obj, Obj_Entry *obj_rtld)
const Obj_Entry *defobj;
def = find_symdef(ELF_R_SYM(rel->r_info), obj, &defobj,
- false, cache);
+ false, cache, lockstate);
if (def == NULL)
goto done;
@@ -213,7 +218,7 @@ reloc_non_plt(Obj_Entry *obj, Obj_Entry *obj_rtld)
const Obj_Entry *defobj;
def = find_symdef(ELF_R_SYM(rel->r_info), obj, &defobj,
- false, cache);
+ false, cache, lockstate);
if (def == NULL)
goto done;
@@ -243,7 +248,7 @@ reloc_non_plt(Obj_Entry *obj, Obj_Entry *obj_rtld)
const Obj_Entry *defobj;
def = find_symdef(ELF_R_SYM(rel->r_info), obj, &defobj,
- false, cache);
+ false, cache, lockstate);
if (def == NULL)
goto done;
@@ -257,7 +262,7 @@ reloc_non_plt(Obj_Entry *obj, Obj_Entry *obj_rtld)
const Obj_Entry *defobj;
def = find_symdef(ELF_R_SYM(rel->r_info), obj, &defobj,
- false, cache);
+ false, cache, lockstate);
if (def == NULL)
goto done;
@@ -301,7 +306,7 @@ reloc_plt(Obj_Entry *obj)
/* Relocate the jump slots in an object. */
int
-reloc_jmpslots(Obj_Entry *obj)
+reloc_jmpslots(Obj_Entry *obj, RtldLockState *lockstate)
{
const Elf_Rel *rellim;
const Elf_Rel *rel;
@@ -316,7 +321,8 @@ reloc_jmpslots(Obj_Entry *obj)
assert(ELF_R_TYPE(rel->r_info) == R_386_JMP_SLOT);
where = (Elf_Addr *)(obj->relocbase + rel->r_offset);
- def = find_symdef(ELF_R_SYM(rel->r_info), obj, &defobj, true, NULL);
+ def = find_symdef(ELF_R_SYM(rel->r_info), obj, &defobj, true, NULL,
+ lockstate);
if (def == NULL)
return -1;
target = (Elf_Addr)(defobj->relocbase + def->st_value);
OpenPOWER on IntegriCloud