diff options
Diffstat (limited to 'ldso/ldso/c6x/elfinterp.c')
-rw-r--r-- | ldso/ldso/c6x/elfinterp.c | 32 |
1 files changed, 18 insertions, 14 deletions
diff --git a/ldso/ldso/c6x/elfinterp.c b/ldso/ldso/c6x/elfinterp.c index 3772f90b3..f0e05b9d0 100644 --- a/ldso/ldso/c6x/elfinterp.c +++ b/ldso/ldso/c6x/elfinterp.c @@ -69,14 +69,12 @@ _dl_linux_resolver (struct elf_resolve *tpnt, int reloc_entry) got_addr = (char **) DL_RELOC_ADDR(tpnt->loadaddr, this_reloc->r_offset); /* Get the address to be used to fill in the GOT entry. */ - new_addr = _dl_find_hash(symname, tpnt->symbol_scope, tpnt, - ELF_RTYPE_CLASS_PLT, NULL); + new_addr = _dl_find_hash(symname, &_dl_loaded_modules->symbol_scope, tpnt, ELF_RTYPE_CLASS_PLT, NULL); if (unlikely(!new_addr)) { _dl_dprintf(2, "%s: can't resolve symbol '%s' in lib '%s'.\n", _dl_progname, symname, tpnt->libname); _dl_exit(1); } - #if defined (__SUPPORT_LD_DEBUG__) if (_dl_debug_bindings) { _dl_dprintf(_dl_debug_file, "\nresolve function: %s", symname); @@ -96,9 +94,9 @@ _dl_linux_resolver (struct elf_resolve *tpnt, int reloc_entry) } static int -_dl_parse(struct elf_resolve *tpnt, struct dyn_elf *scope, +_dl_parse(struct elf_resolve *tpnt, struct r_scope_elem *scope, unsigned long rel_addr, unsigned long rel_size, - int (*reloc_fnc) (struct elf_resolve *tpnt, struct dyn_elf *scope, + int (*reloc_fnc) (struct elf_resolve *tpnt, struct r_scope_elem *scope, ELF_RELOC *rpnt, ElfW(Sym) *symtab, char *strtab)) { unsigned int i; @@ -148,7 +146,7 @@ _dl_parse(struct elf_resolve *tpnt, struct dyn_elf *scope, } static int -_dl_do_reloc (struct elf_resolve *tpnt,struct dyn_elf *scope, +_dl_do_reloc (struct elf_resolve *tpnt,struct r_scope_elem *scope, ELF_RELOC *rpnt, ElfW(Sym) *symtab, char *strtab) { int reloc_type; @@ -157,7 +155,9 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct dyn_elf *scope, unsigned long *reloc_addr; unsigned long symbol_addr, sym_val; long reloc_addend; - unsigned long old_val, new_val; + unsigned long old_val, new_val = 0; + struct symbol_ref sym_ref; + struct elf_resolve *symbol_tpnt; reloc_addr = (unsigned long *)(intptr_t) DL_RELOC_ADDR (tpnt->loadaddr, rpnt->r_offset); @@ -167,14 +167,17 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct dyn_elf *scope, symtab_index = ELF_R_SYM(rpnt->r_info); symbol_addr = 0; symname = strtab + symtab[symtab_index].st_name; + sym_ref.sym = &symtab[symtab_index]; + sym_ref.tpnt = NULL; if (ELF_ST_BIND (symtab[symtab_index].st_info) == STB_LOCAL) { symbol_addr = (unsigned long) DL_RELOC_ADDR (tpnt->loadaddr, symtab[symtab_index].st_value); + symbol_tpnt = tpnt; } else { - symbol_addr = (unsigned long) _dl_find_hash(strtab + symtab[symtab_index].st_name, - scope, tpnt, elf_machine_type_class(reloc_type), - NULL); + symbol_addr = (unsigned long) _dl_find_hash(symname, + scope, NULL, elf_machine_type_class(reloc_type), + &sym_ref); /* * We want to allow undefined references to weak symbols - this might * have been intentional. We should not be linking local symbols @@ -186,6 +189,7 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct dyn_elf *scope, _dl_progname, strtab + symtab[symtab_index].st_name); _dl_exit (1); } + symbol_tpnt = sym_ref.tpnt; } old_val = *reloc_addr; sym_val = symbol_addr + reloc_addend; @@ -199,7 +203,7 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct dyn_elf *scope, *reloc_addr = sym_val; break; case R_C6000_DSBT_INDEX: - new_val = (old_val & ~0x007fff00) | ((tpnt->loadaddr.map->dsbt_index & 0x7fff) << 8); + new_val = (old_val & ~0x007fff00) | ((symbol_tpnt->dsbt_index & 0x7fff) << 8); *reloc_addr = new_val; break; case R_C6000_ABS_L16: @@ -242,7 +246,7 @@ _dl_do_reloc (struct elf_resolve *tpnt,struct dyn_elf *scope, static int _dl_do_lazy_reloc (struct elf_resolve *tpnt, - struct dyn_elf *scope attribute_unused, + struct r_scope_elem *scope attribute_unused, ELF_RELOC *rpnt, ElfW(Sym) *symtab attribute_unused, char *strtab attribute_unused) { @@ -283,9 +287,9 @@ _dl_parse_lazy_relocation_information int _dl_parse_relocation_information -(struct dyn_elf *rpnt, unsigned long rel_addr, unsigned long rel_size) +(struct dyn_elf *rpnt, struct r_scope_elem *scope, unsigned long rel_addr, unsigned long rel_size) { - return _dl_parse(rpnt->dyn, rpnt->dyn->symbol_scope, rel_addr, rel_size, _dl_do_reloc); + return _dl_parse(rpnt->dyn, scope, rel_addr, rel_size, _dl_do_reloc); } /* We don't have copy relocs. */ |