X-Git-Url: http://nsz.repo.hu/git/?p=musl;a=blobdiff_plain;f=src%2Fldso%2Fdynlink.c;h=0cb025928617dffeb5ae1d52381457e3b14519e8;hp=0a64ef8ae2decafba3cf592da87ed34319cf615f;hb=05eff01e89ee345e70acdbebc9c3778766b76ee2;hpb=0420b874465db7544a9e1f320969b4920c9405d8 diff --git a/src/ldso/dynlink.c b/src/ldso/dynlink.c index 0a64ef8a..0cb02592 100644 --- a/src/ldso/dynlink.c +++ b/src/ldso/dynlink.c @@ -20,7 +20,7 @@ static int errflag; static char errbuf[128]; -#ifdef __PIC__ +#ifdef SHARED #include "reloc.h" @@ -105,9 +105,12 @@ static uint32_t hash(const char *s0) return h & 0xfffffff; } -static Sym *lookup(const char *s, uint32_t h, Sym *syms, uint32_t *hashtab, char *strings) +static Sym *lookup(const char *s, uint32_t h, struct dso *dso) { size_t i; + Sym *syms = dso->syms; + uint32_t *hashtab = dso->hashtab; + char *strings = dso->strings; for (i=hashtab[2+h%hashtab[0]]; i; i=hashtab[2+hashtab[0]+i]) { if (!strcmp(s, strings+syms[i].st_name)) return syms+i; @@ -128,7 +131,7 @@ static void *find_sym(struct dso *dso, const char *s, int need_def) for (; dso; dso=dso->next) { Sym *sym; if (!dso->global) continue; - sym = lookup(s, h, dso->syms, dso->hashtab, dso->strings); + sym = lookup(s, h, dso); if (sym && (!need_def || sym->st_shndx) && sym->st_value && (1<<(sym->st_info&0xf) & OK_TYPES) && (1<<(sym->st_info>>4) & OK_BINDS)) { @@ -577,12 +580,16 @@ void *__dynlink(int argc, char **argv) decode_dyn(lib); if (aux[AT_PHDR]) { + size_t interp_off = 0; /* Find load address of the main program, via AT_PHDR vs PT_PHDR. */ phdr = (void *)aux[AT_PHDR]; for (i=aux[AT_PHNUM]; i; i--, phdr=(void *)((char *)phdr + aux[AT_PHENT])) { if (phdr->p_type == PT_PHDR) app->base = (void *)(aux[AT_PHDR] - phdr->p_vaddr); + else if (phdr->p_type == PT_INTERP) + interp_off = (size_t)phdr->p_vaddr; } + if (interp_off) lib->name = (char *)app->base + interp_off; app->name = argv[0]; app->dynv = (void *)(app->base + find_dyn( (void *)aux[AT_PHDR], aux[AT_PHNUM], aux[AT_PHENT])); @@ -612,6 +619,7 @@ void *__dynlink(int argc, char **argv) } runtime = 0; close(fd); + lib->name = ldname; app->name = argv[0]; app->dynv = (void *)(app->base + dyno); aux[AT_ENTRY] = ehdr->e_entry; @@ -783,12 +791,11 @@ static void *do_dlsym(struct dso *p, const char *s, void *ra) return res; } h = hash(s); - sym = lookup(s, h, p->syms, p->hashtab, p->strings); + sym = lookup(s, h, p); if (sym && sym->st_value && (1<<(sym->st_info&0xf) & OK_TYPES)) return p->base + sym->st_value; if (p->deps) for (i=0; p->deps[i]; i++) { - sym = lookup(s, h, p->deps[i]->syms, - p->deps[i]->hashtab, p->deps[i]->strings); + sym = lookup(s, h, p); if (sym && sym->st_value && (1<<(sym->st_info&0xf) & OK_TYPES)) return p->deps[i]->base + sym->st_value; }