Lines Matching refs:dso
100 struct dso *dso;
118 struct dso *target;
134 static struct dso ldso;
135 static struct dso *head, *tail, *fini_head, *syms_tail, *lazy_head;
152 static struct dso *builtin_deps[2];
153 static struct dso *const no_deps[1];
154 static struct dso *builtin_ctor_queue[4];
155 static struct dso **main_ctor_queue;
181 static int do_dlclose(struct dso *p);
190 static void preload_direct_deps(struct dso *p, ns_t *namespace, struct loadtasks *tasks);
192 static void preload_deps(struct dso *p, struct loadtasks *tasks);
194 UT_STATIC void assign_tls(struct dso *p);
203 static void handle_relro_sharing(struct dso *p, const dl_extinfo *extinfo, ssize_t *relro_fd_offset);
210 static void find_and_set_bss_name(struct dso *p);
214 static void notify_addition_to_debugger(struct dso *p);
215 static void notify_remove_to_debugger(struct dso *p);
216 static void add_dso_info_to_debug_map(struct dso *p);
217 static void remove_dso_info_from_debug_map(struct dso *p);
221 static void dlclose_ns(struct dso *p);
235 static void init_default_namespace(struct dso *app)
319 static void init_namespace(struct dso *app)
387 /* Compute load address for a virtual address in a given dso. */
389 void *laddr(const struct dso *p, size_t v)
396 static void *laddr_pg(const struct dso *p, size_t v)
556 static Sym *sysv_lookup(struct verinfo *verinfo, struct sym_info_pair s_info_p, struct dso *dso)
560 Sym *syms = dso->syms;
561 Elf_Symndx *hashtab = dso->hashtab;
562 char *strings = dso->strings;
564 if ((!dso->versym || (dso->versym[i] & 0x7fff) >= 0)
566 if (!check_verinfo(dso->verdef, dso->versym, i, verinfo, dso->strings)) {
576 dso->name, verinfo->s, verinfo->v, verinfo->use_vna_hash, verinfo->vna_hash);
580 static Sym *gnu_lookup(struct sym_info_pair s_info_p, uint32_t *hashtab, struct dso *dso, struct verinfo *verinfo)
588 LD_LOGD("gnu_lookup symbol not found (bloom filter), so:%{public}s s:%{public}s", dso->name, verinfo->s);
596 if ((h1 == (h2|1)) && (!dso->versym || (dso->versym[i] & 0x7fff) >= 0)
597 && !memcmp(verinfo->s, dso->strings + dso->syms[i].st_name, s_info_p.sym_l)) {
598 if (!check_verinfo(dso->verdef, dso->versym, i, verinfo, dso->strings)) {
602 return dso->syms+i;
610 dso->name, verinfo->s, verinfo->v, verinfo->use_vna_hash, verinfo->vna_hash);
614 static bool check_sym_accessible(struct dso *dso, ns_t *ns)
616 if (!dso || !dso->namespace || !ns) {
620 if (dso->namespace == ns) {
623 for (int i = 0; i < dso->parents_count; i++) {
624 if (dso->parents[i]->namespace == ns) {
629 "check_sym_accessible dso name [%{public}s] ns_name [%{public}s] not accessible!", dso->name, ns->ns_name);
633 static inline bool is_dso_accessible(struct dso *dso, ns_t *ns)
635 if (dso->namespace == ns) {
638 for (int i = 0; i < dso->parents_count; i++) {
639 if (dso->parents[i]->namespace == ns) {
644 "check_sym_accessible dso name [%{public}s] ns_name [%{public}s] not accessible!", dso->name, ns->ns_name);
648 static int find_dso_parent(struct dso *p, struct dso *target)
660 static void add_dso_parent(struct dso *p, struct dso *parent)
668 p->parents = (struct dso **)malloc(sizeof(struct dso *) * PARENTS_BASE_CAPACITY);
674 struct dso ** realloced = (struct dso **)realloc(
675 p->parents, sizeof(struct dso *) * (p->parents_capacity + PARENTS_BASE_CAPACITY));
687 static void remove_dso_parent(struct dso *p, struct dso *parent)
703 static void add_reloc_can_search_dso(struct dso *p, struct dso *can_search_so)
708 (struct dso **)malloc(sizeof(struct dso *) * RELOC_CAN_SEARCH_DSO_BASE_CAPACITY);
714 struct dso ** realloced = (struct dso **)realloc(
716 sizeof(struct dso *) * (p->reloc_can_search_dso_capacity + RELOC_CAN_SEARCH_DSO_BASE_CAPACITY));
728 static void free_reloc_can_search_dso(struct dso *p)
746 static void add_can_search_so_list_in_dso(struct dso *dso_relocating, struct dso *start_check_dso) {
747 struct dso *p = start_check_dso;
776 struct dso *dso, struct verinfo *verinfo, struct sym_info_pair s_info_g, int need_def, ns_t *ns)
785 if (ns && !check_sym_accessible(dso, ns))
788 if ((ght = dso->ghashtab)) {
798 sym = gnu_lookup(s_info_g, ght, dso, verinfo);
803 sym = sysv_lookup(verinfo, s_info_s, dso);
824 def.dso = dso;
828 static inline struct symdef find_sym2(struct dso *dso, struct verinfo *verinfo, int need_def, int use_deps, ns_t *ns)
835 struct dso **deps = use_deps ? dso->deps : 0;
836 for (; dso; dso=use_deps ? *deps++ : dso->syms_next) {
838 if (ns && !check_sym_accessible(dso, ns)) {
841 if ((ght = dso->ghashtab)) {
843 sym = gnu_lookup(s_info_g, ght, dso, verinfo);
846 sym = sysv_lookup(verinfo, s_info_s, dso);
860 def.dso = dso;
866 static inline struct symdef find_sym_by_deps(struct dso *dso, struct verinfo *verinfo, int need_def, ns_t *ns)
873 struct dso **deps = dso->deps;
874 for (; dso; dso=*deps++) {
876 if (!is_dso_accessible(dso, ns)) {
879 if ((ght = dso->ghashtab)) {
881 sym = gnu_lookup(s_info_g, ght, dso, verinfo);
884 sym = sysv_lookup(verinfo, s_info_s, dso);
898 def.dso = dso;
905 int sym_type, struct dso *dso, struct verinfo *verinfo, int need_def, struct dso *dso_relocating)
912 // skip head dso.
914 struct dso *dso_searching = 0;
936 def.dso = dso_searching;
942 static struct symdef find_sym(struct dso *dso, const char *s, int need_def)
945 return find_sym2(dso, &verinfo, need_def, 0, NULL);
948 static bool get_vna_hash(struct dso *dso, int sym_index, uint32_t *vna_hash)
950 if (!dso->versym || !dso->verneed) {
954 uint16_t vsym = dso->versym[sym_index];
960 Verneed *verneed = dso->verneed;
990 static void get_verinfo(struct dso *dso, int sym_index, struct verinfo *vinfo)
992 char *strings = dso->strings;
994 int16_t vsym = dso->versym[sym_index];
995 Verdef *verdef = dso->verdef;
1016 if (aux && aux->vda_name && strings && (dso->strings + aux->vda_name)) {
1017 vinfo->v = dso->strings + aux->vda_name;
1022 static void do_relocs(struct dso *dso, size_t *rel, size_t rel_size, size_t stride)
1024 unsigned char *base = dso->base;
1025 Sym *syms = dso->syms;
1026 char *strings = dso->strings;
1039 if (dso == &ldso) {
1047 if (skip_relative && IS_RELATIVE(rel[1], dso->syms)) continue;
1050 reloc_addr = laddr(dso, rel[0]);
1057 /* Save original addend in stage 2 where the dso
1074 vinfo.use_vna_hash = get_vna_hash(dso, sym_index, &vinfo.vna_hash);
1075 if (!vinfo.use_vna_hash && dso->versym && (dso->versym[sym_index] & 0x7fff) >= 0) {
1076 get_verinfo(dso, sym_index, &vinfo);
1078 if (dso->cache_sym_index == sym_index) {
1079 def = (struct symdef){ .dso = dso->cache_dso, .sym = dso->cache_sym };
1082 ? (struct symdef){ .dso = dso, .sym = sym }
1083 : dso != &ldso ? find_sym_by_saved_so_list(type, ctx, &vinfo, type==REL_PLT, dso)
1084 : find_sym2(ctx, &vinfo, type==REL_PLT, 0, dso->namespace);
1085 dso->cache_sym_index = sym_index;
1086 dso->cache_dso = def.dso;
1087 dso->cache_sym = def.sym;
1092 if (dso->lazy && (type==REL_PLT || type==REL_GOT)) {
1093 dso->lazy[3*dso->lazy_cnt+0] = rel[0];
1094 dso->lazy[3*dso->lazy_cnt+1] = rel[1];
1095 dso->lazy[3*dso->lazy_cnt+2] = addend;
1096 dso->lazy_cnt++;
1100 "dso=%{public}s s=%{public}s use_vna_hash=%{public}d van_hash=%{public}x",
1101 dso->name, name, vinfo.use_vna_hash, vinfo.vna_hash);
1103 dso->name, name);
1110 def.dso = dso;
1113 sym_val = def.sym ? (size_t)laddr(def.dso, def.sym->st_value) : 0;
1117 && def.dso->tls_id > static_tls_cnt) {
1120 dso->name, name, def.dso->name);
1150 *reloc_addr = def.sym ? (size_t)(def.dso->funcdescs
1151 + (def.sym - def.dso->syms)) : 0;
1156 reloc_addr[1] = def.sym ? (size_t)def.dso->got : 0;
1159 *reloc_addr = def.dso->tls_id;
1166 *reloc_addr = tls_val + def.dso->tls.offset + TPOFF_K + addend;
1170 *reloc_addr = tls_val - def.dso->tls.offset + addend;
1173 *reloc_addr = def.dso->tls.offset - tls_val + addend;
1178 if (def.dso->tls_id > static_tls_cnt) {
1183 dso->name, sym ? name : "(local)" );
1186 new->next = dso->td_index;
1187 dso->td_index = new;
1188 new->args[0] = def.dso->tls_id;
1195 reloc_addr[1] = tls_val + def.dso->tls.offset
1198 reloc_addr[1] = tls_val - def.dso->tls.offset
1212 dso->name, type);
1221 struct dso *p = lazy_head, *next;
1244 static void reclaim(struct dso *dso, size_t start, size_t end)
1246 if (start >= dso->relro_start && start < dso->relro_end) start = dso->relro_end;
1247 if (end >= dso->relro_start && end < dso->relro_end) end = dso->relro_start;
1249 char *base = laddr_pg(dso, start);
1253 static void reclaim_gaps(struct dso *dso)
1255 Phdr *ph = dso->phdr;
1256 size_t phcnt = dso->phnum;
1258 for (; phcnt--; ph=(void *)((char *)ph+dso->phentsize)) {
1261 reclaim(dso, ph->p_vaddr & -PAGE_SIZE, ph->p_vaddr);
1262 reclaim(dso, ph->p_vaddr+ph->p_memsz,
1310 UT_STATIC void unmap_library(struct dso *dso)
1312 if (dso->loadmap) {
1314 for (i=0; i<dso->loadmap->nsegs; i++) {
1315 if (!dso->loadmap->segs[i].p_memsz)
1318 munmap((void *)dso->loadmap->segs[i].addr,
1319 dso->loadmap->segs[i].p_memsz);
1321 (void)mprotect((void *)dso->loadmap->segs[i].addr,
1322 dso->loadmap->segs[i].p_memsz, PROT_NONE);
1325 free(dso->loadmap);
1326 } else if (dso->map && dso->map_len) {
1328 munmap(dso->map, dso->map_len);
1330 mprotect(dso->map, dso->map_len, PROT_NONE);
1420 UT_STATIC void *map_library(int fd, struct dso *dso, struct reserved_address_params *reserved_params)
1467 dso->tls.align = ph->p_align;
1468 dso->tls.len = ph->p_filesz;
1469 dso->tls.size = ph->p_memsz;
1471 dso->relro_start = ph->p_vaddr & -PAGE_SIZE;
1472 dso->relro_end = (ph->p_vaddr + ph->p_memsz) & -PAGE_SIZE;
1495 dso->loadmap = calloc(1, sizeof *dso->loadmap
1496 + nsegs * sizeof *dso->loadmap->segs);
1497 if (!dso->loadmap) goto error;
1498 dso->loadmap->nsegs = nsegs;
1508 unmap_library(dso);
1511 dso->loadmap->segs[i].addr = (size_t)map +
1513 dso->loadmap->segs[i].p_vaddr = ph->p_vaddr;
1514 dso->loadmap->segs[i].p_memsz = ph->p_memsz;
1530 map = (void *)dso->loadmap->segs[0].addr;
1559 /* we will find a mapping_align aligned address as the start of dso
1561 * we have enough space to shift the dso to the correct location. */
1579 /* use tmp_map_len to mmap enough space for the dso with anonymous mapping */
1593 /* use map_len to mmap correct space for the dso with file mapping */
1599 dso->map = map;
1600 dso->map_len = map_len;
1608 dso->phdr = 0;
1609 dso->phnum = 0;
1618 if (!dso->phdr && eh->e_phoff >= ph->p_offset
1620 dso->phdr = (void *)(base + ph->p_vaddr
1622 dso->phnum = eh->e_phnum;
1623 dso->phentsize = eh->e_phentsize;
1644 set_bss_vma_name(dso->name, (void *)pgbrk, zeromap_size);
1655 dso->base = base;
1656 dso->dynv = laddr(dso, dyn);
1657 if (dso->tls.size) dso->tls.image = laddr(dso, tls_image);
1663 if (map!=MAP_FAILED) unmap_library(dso);
1694 UT_STATIC int fixup_rpath(struct dso *p, char *buf, size_t buf_size)
1771 static void decode_dyn(struct dso *p)
1804 UT_STATIC size_t count_syms(struct dso *p)
1835 static void makefuncdescs(struct dso *p)
1890 static struct dso *search_dso_by_name(const char *name, const ns_t *ns) {
1893 struct dso *p = ns->ns_dsos->dsos[i];
1902 static struct dso *search_dso_by_fstat(const struct stat *st, const ns_t *ns, uint64_t file_offset) {
1905 struct dso *p = ns->ns_dsos->dsos[i];
1927 static struct dso *find_library_by_name(const char *name, const ns_t *ns, bool check_inherited)
1933 struct dso *p = search_dso_by_name(name, ns);
1950 UT_STATIC struct dso *find_library_by_fstat(const struct stat *st, const ns_t *ns, bool check_inherited, uint64_t file_offset) {
1954 struct dso *p = search_dso_by_fstat(st, ns, file_offset);
1968 struct dso *load_library(
1969 const char *name, struct dso *needed_by, ns_t *namespace, bool check_inherited, struct reserved_address_params *reserved_params)
1974 struct dso *p, temp_dso = {0};
2173 /* Add dso to namespace */
2186 static void load_direct_deps(struct dso *p, ns_t *namespace, struct reserved_address_params *reserved_params)
2193 if (p==head) for (struct dso *q=p->next; q; q=q->next)
2206 if (p==head) for (struct dso *q=p->next; q; q=q->next)
2210 struct dso *dep = load_library(p->strings + p->dynv[i+1], p, namespace, true, reserved_params);
2227 static void load_deps(struct dso *p, struct reserved_address_params *reserved_params)
2235 static void extend_bfs_deps(struct dso *p)
2238 struct dso **tmp;
2258 struct dso *dep = p->deps[i];
2302 static void add_syms(struct dso *p)
2310 static void revert_syms(struct dso *old_tail)
2312 struct dso *p, *next;
2322 static void do_mips_relocs(struct dso *p, size_t *got)
2369 static void do_android_relocs(struct dso *p, size_t dt_name, size_t dt_size)
2456 static void do_relr_relocs(struct dso *dso, size_t *relr, size_t relr_size)
2458 unsigned char *base = dso->base;
2462 reloc_addr = laddr(dso, relr[0]);
2473 static void reloc_all(struct dso *p, const dl_extinfo *extinfo)
2510 static void kernel_mapped_dso(struct dso *p)
2542 struct dso *p;
2581 static struct dso **queue_ctors(struct dso *dso)
2584 struct dso *p, **queue, **stack;
2592 if (dso->bfs_built) {
2593 for (cnt=0; dso->deps[cnt]; cnt++)
2594 dso->deps[cnt]->mark = 0;
2601 if (dso==head && cnt <= countof(builtin_ctor_queue))
2614 * dso and initial queue empty... */
2618 stack[--spos] = dso;
2619 dso->next_dep = 0;
2620 dso->mark = 1;
2643 static void do_init_fini(struct dso **queue)
2645 struct dso *p;
2723 struct dso *dtv_provider = container_of(tls_tail, struct dso, tls);
2725 struct dso *p;
2874 static struct dso app, vdso;
3029 /* Initial dso chain consists only of the app. */
3040 ldso.deps = (struct dso **)no_deps;
3060 for (struct dso *q=head; q; q=q->next) {
3071 for (struct dso *q=head; q; q=q->next) {
3078 for (struct dso *p=head; p; p=p->next) {
3099 vdso.deps = (struct dso **)no_deps;
3143 for (struct dso *q=head; q; q=q->next) {
3177 if (find_sym(head, "malloc", 1).dso != &ldso)
3179 if (find_sym(head, "aligned_alloc", 1).dso != &ldso)
3201 static void prepare_lazy(struct dso *p)
3223 static void *dlopen_post(struct dso* p, int mode) {
3286 struct dso *caller;
3288 caller = (struct dso *)addr2dso((size_t)caller_addr);
3311 struct dso *volatile p, *orig_tail, *orig_syms_tail, *orig_lazy_head, *next;
3317 struct dso **volatile ctor_queue = 0;
3319 struct dso *caller;
3359 caller = (struct dso *)addr2dso((size_t)caller_addr);
3514 struct dso *reloc_head_so = p;
3613 struct dso *caller;
3615 caller = (struct dso *)addr2dso((size_t)caller_addr);
3707 struct dso *caller;
3709 caller = (struct dso *)addr2dso((size_t)caller_addr);
3758 static void dlclose_ns(struct dso *p)
3776 struct dso *p;
3784 struct dso *p;
3803 static void *do_dlsym(struct dso *p, const char *s, const char *v, void *ra)
3808 struct dso *caller = NULL;
3826 caller = (struct dso *)addr2dso((size_t)ra);
3844 return __tls_get_addr((tls_mod_off_t []){def.dso->tls_id, def.sym->st_value-DTP_OFFSET});
3846 return def.dso->funcdescs + (def.sym - def.dso->syms);
3847 return laddr(def.dso, def.sym->st_value);
3850 extern int invalidate_exit_funcs(struct dso *p);
3852 static int so_can_unload(struct dso *p, int check_flag)
3866 /* dso is marked as RTLD_NODELETE library, do nothing here. */
3883 static int dlclose_post(struct dso *p)
3905 static int dlclose_impl(struct dso *p)
3907 struct dso *d;
3912 /* remove dso symbols from global list */
3924 /* remove dso from lazy list if needed */
3934 /* remove dso from fini list */
3949 /* remove dso from global dso list */
3958 /* remove dso from namespace */
3967 /* after destruct, invalidate atexit funcs which belong to this dso */
3986 static int do_dlclose(struct dso *p)
4025 start_entry->dso = p;
4030 struct dso *cur = ecur->dso;
4034 if (ef->dso == cur) {
4048 if (ef->dso == cur->deps[i]) {
4058 edeps->dso = cur->deps[i];
4066 LD_LOGE("[dlclose]: unload %{public}s succeed when dlclose %{public}s", ef->dso->name, p->name);
4071 if (ef->dso == p->deps[deps_num]) {
4086 dlclose_impl(ef->dso);
4092 int constructed = ef->dso->constructed;
4097 decode_vec(ef->dso->dynv, dyn, DYN_CNT);
4100 size_t *fn = (size_t *)laddr(ef->dso, dyn[DT_FINI_ARRAY]) + n;
4101 trace_marker_begin(HITRACE_TAG_MUSL, "calling destructors:", ef->dso->name);
4111 ef->dso->constructed = 0;
4117 dlclose_post(ef->dso);
4139 struct dso *dso = find_dso_by_handle(p);
4140 if (dso == NULL) {
4147 rc = do_dlclose(dso);
4162 static inline Sym* find_addr_by_elf(size_t addr_offset_so, struct dso *p) {
4174 static inline Sym* find_addr_by_gnu(size_t addr_offset_so, struct dso *p) {
4217 struct dso *p;
4256 struct dso *dso = find_dso_by_handle(p);
4257 if (dso == NULL) {
4261 res = do_dlsym(dso, s, "", ra);
4278 struct dso *dso = find_dso_by_handle(p);
4279 if (dso == NULL) {
4283 res = do_dlsym(dso, s, v, ra);
4323 struct dso *current;
4958 /* we will find a mapping_align aligned address as the start of dso
4960 * we have enough space to shift the dso to the correct location. */
4984 /* use tmp_map_len to mmap enough space for the dso with anonymous mapping */
5000 /* use map_len to mmap correct space for the dso with file mapping */
5133 struct dso *needed_by = task->needed_by;
5323 alloc_size = sizeof(struct dso) + strlen(task->pathname) + 1;
5335 LD_LOGE("Error loading header %{public}s: failed to allocate dso", task->name);
5372 /* Add dso to namespace */
5440 static void preload_direct_deps(struct dso *p, ns_t *namespace, struct loadtasks *tasks)
5449 for (struct dso *q = p->next; q; q = q->next) {
5471 for (struct dso *q = p->next; q; q = q->next) {
5546 static void preload_deps(struct dso *p, struct loadtasks *tasks)
5571 UT_STATIC void assign_tls(struct dso *p)
5631 static int serialize_gnu_relro(int fd, struct dso *dso, ssize_t *file_offset)
5633 ssize_t count = dso->relro_end - dso->relro_start;
5636 ssize_t write_size = TEMP_FAILURE_RETRY(write(fd, laddr(dso, dso->relro_start + offset), count));
5638 LD_LOGE("Error serializing relro %{public}s: failed to write GNU_RELRO", dso->name);
5645 ssize_t size = dso->relro_end - dso->relro_start;
5647 laddr(dso, dso->relro_start),
5654 LD_LOGE("Error serializing relro %{public}s: failed to map GNU_RELRO", dso->name);
5661 static int map_gnu_relro(int fd, struct dso *dso, ssize_t *file_offset)
5666 LD_LOGE("Error mapping relro %{public}s: failed to get file state", dso->name);
5674 LD_LOGE("Error mapping relro %{public}s: failed to map fd", dso->name);
5679 char *mem_base = (char *)(laddr(dso, dso->relro_start));
5681 ssize_t size = dso->relro_end - dso->relro_start;
5684 LD_LOGE("Error mapping relro %{public}s: invalid file size", dso->name);
5712 LD_LOGE("Error mapping relro %{public}s: failed to map GNU_RELRO", dso->name);
5725 static void handle_relro_sharing(struct dso *p, const dl_extinfo *extinfo, ssize_t *relro_fd_offset)
5764 static void find_and_set_bss_name(struct dso *p)
5793 static void notify_addition_to_debugger(struct dso *p)
5804 static void notify_remove_to_debugger(struct dso *p)
5815 static void add_dso_info_to_debug_map(struct dso *p)
5817 for (struct dso *so = p; so != NULL; so = so->next) {
5820 LD_LOGE("malloc error! dso name: %{public}s.", so->name);
5844 static void remove_dso_info_from_debug_map(struct dso *p)