Home | History | Annotate | Download | only in libdwfl

Lines Matching refs:mod

69 /* Open libelf FILE->fd and compute the load base of ELF as loaded in MOD.
72 open_elf (Dwfl_Module *mod, struct dwfl_file *file)
151 if (file == &mod->main)
153 mod->e_type = ehdr->e_type;
156 if (mod->e_type == ET_EXEC && file->vaddr != mod->low_addr)
157 mod->e_type = ET_DYN;
160 assert (mod->main.elf != NULL);
165 /* We have an authoritative build ID for this module MOD, so don't use
168 mod_verify_build_id (Dwfl_Module *mod)
170 assert (mod->build_id_len > 0);
172 switch (__builtin_expect (__libdwfl_find_build_id (mod, false,
173 mod->main.elf), 2))
180 mod->elferr = INTUSE(dwfl_errno) ();
185 mod->elferr = DWFL_E_WRONG_ID_ELF;
193 elf_end (mod->main.elf);
194 mod->main.elf = NULL;
195 if (mod->main.fd >= 0)
197 close (mod->main.fd);
198 mod->main.fd = -1;
203 When we return success, MOD->main.elf and MOD->main.bias are set up. */
206 __libdwfl_getelf (Dwfl_Module *mod)
208 if (mod->main.elf != NULL /* Already done. */
209 || mod->elferr != DWFL_E_NOERROR) /* Cached failure. */
212 mod->main.fd = (*mod->dwfl->callbacks->find_elf) (MODCB_ARGS (mod),
213 &mod->main.name,
214 &mod->main.elf);
215 const bool fallback = mod->main.elf == NULL && mod->main.fd < 0;
216 mod->elferr = open_elf (mod, &mod->main);
217 if (mod->elferr != DWFL_E_NOERROR)
220 if (!mod->main.valid)
224 free (mod->build_id_bits);
225 mod->build_id_bits = NULL;
226 mod->build_id_len = 0;
229 mod_verify_build_id (mod);
231 mod->main_bias = mod->e_type == ET_REL ? 0 : mod->low_addr - mod->main.vaddr;
251 find_prelink_address_sync (Dwfl_Module *mod, struct dwfl_file *file)
255 if (elf_getshdrstrndx (mod->main.elf, &shstrndx) < 0)
259 while ((scn = elf_nextscn (mod->main.elf, scn)) != NULL)
269 const char *secname = elf_strptr (mod->main.elf, shstrndx,
302 src.d_size = gelf_fsize (mod->main.elf, ELF_T_EHDR, 1, EV_CURRENT);
304 if (unlikely (gelf_xlatetom (mod->main.elf, &dst, &src,
305 elf_getident (mod->main.elf, NULL)[EI_DATA])
309 size_t shentsize = gelf_fsize (mod->main.elf, ELF_T_SHDR, 1, EV_CURRENT);
310 size_t phentsize = gelf_fsize (mod->main.elf, ELF_T_PHDR, 1, EV_CURRENT);
350 if (unlikely (elf_getphdrnum (mod->main.elf, &main_phnum)))
355 if (unlikely (gelf_getphdr (mod->main.elf, i, &phdr) == NULL))
378 if (unlikely (gelf_xlatetom (mod->main.elf, &dst, &src,
406 src.d_size = gelf_fsize (mod->main.elf, ELF_T_SHDR, shnum - 1, EV_CURRENT);
415 if (unlikely (gelf_xlatetom (mod->main.elf, &dst, &src,
455 while ((scn = elf_nextscn (mod->main.elf, scn)) != NULL)
464 if (highest > mod->main.vaddr)
466 mod->main.address_sync = highest;
488 When we return success, MOD->debug is set up. */
490 find_debuginfo (Dwfl_Module *mod)
492 if (mod->debug.elf != NULL)
497 debuglink_file = INTUSE(dwelf_elf_gnu_debuglink) (mod->main.elf,
500 mod->debug.fd = (*mod->dwfl->callbacks->find_debuginfo) (MODCB_ARGS (mod),
501 mod->main.name,
504 &mod->debug.name);
505 Dwfl_Error result = open_elf (mod, &mod->debug);
506 if (result == DWFL_E_NOERROR && mod->debug.address_sync != 0)
507 result = find_prelink_address_sync (mod, &mod
512 it if found. Only called when mod->dw is already setup but still
516 find_debug_altlink (Dwfl_Module *mod, const char *filename)
518 assert (mod->dw != NULL);
522 ssize_t build_id_len = INTUSE(dwelf_dwarf_gnu_debugaltlink) (mod->dw,
530 mod->alt_fd = (*mod->dwfl->callbacks->find_debuginfo) (MODCB_ARGS (mod),
536 /* The (internal) callbacks might just set mod->alt_elf directly
540 Dwfl_Error error = open_elf_file (&mod->alt_elf, &mod->alt_fd,
544 mod->alt = INTUSE(dwarf_begin_elf) (mod->alt_elf,
546 if (mod->alt == NULL)
548 elf_end (mod->alt_elf);
549 mod->alt_elf = NULL;
550 close (mod->alt_fd);
551 mod->alt_fd = -1;
554 dwarf_setalt (mod->dw, mod->alt);
651 find_dynsym (Dwfl_Module *mod)
654 GElf_Ehdr *ehdr = gelf_getehdr (mod->main.elf, &ehdr_mem);
657 if (unlikely (elf_getphdrnum (mod->main.elf, &phnum) != 0))
663 GElf_Phdr *phdr = gelf_getphdr (mod->main.elf, i, &phdr_mem);
671 Elf_Data *data = elf_getdata_rawchunk (mod->main.elf,
687 size_t n = data->d_size / gelf_fsize (mod->main.elf,
726 in case the dynamic segment wasn't adjusted or mod->main_bias. */
730 find_offsets (mod->main.elf, adjust, phnum, i_max, addrs, offs);
738 data = elf_getdata_rawchunk (mod->main.elf,
743 mod->syments = (entsz == 4
747 if (offs[i_gnu_hash] != 0 && mod->syments == 0)
759 data = elf_getdata_rawchunk (mod->main.elf, offs[i_gnu_hash],
767 + (gelf_getclass (mod->main.elf)
779 = elf_getdata_rawchunk (mod->main.elf, buckets_at,
795 data = elf_getdata_rawchunk (mod->main.elf,
802 mod->syments = maxndx + 1;
811 if (offs[i_strtab] > offs[i_symtab] && mod->syments == 0)
812 mod->syments = ((offs[i_strtab] - offs[i_symtab])
813 / gelf_fsize (mod->main.elf,
816 if (mod->syments > 0)
818 mod->symdata = elf_getdata_rawchunk (mod->main.elf,
820 gelf_fsize (mod->main.elf,
822 mod->syments,
825 if (mod->symdata != NULL)
827 mod->symstrdata = elf_getdata_rawchunk (mod->main.elf,
831 if (mod->symstrdata == NULL)
832 mod->symdata = NULL;
834 if (mod->symdata == NULL)
835 mod->symerr = DWFL_E (LIBELF, elf_errno ());
838 mod->symfile = &mod->main;
839 mod->symerr = DWFL_E_NOERROR;
848 if (mod->symfile == NULL)
849 translate_offs (mod->main_bias);
860 find_aux_address_sync (Dwfl_Module *mod)
864 mod->aux_sym.address_sync = mod->main.address_sync;
869 if (unlikely (gelf_getehdr (mod->main.elf, &ehdr_main) == NULL)
870 || unlikely (gelf_getehdr (mod->aux_sym.elf, &ehdr_aux) == NULL))
872 mod->aux_sym.address_sync += ehdr_aux.e_entry - ehdr_main.e_entry;
876 if (mod->aux_sym.address_sync != 0)
877 return find_prelink_address_sync (mod, &mod->aux_sym) == DWFL_E_NOERROR;
887 find_aux_sym (Dwfl_Module *mod __attribute__ ((unused)),
895 Elf *elf = mod->main.elf;
937 mod->aux_sym.elf = elf_memory (buffer, size);
938 if (mod->aux_sym.elf == NULL)
942 mod->aux_sym.fd = -1;
943 mod->aux_sym.elf->flags |= ELF_F_MALLOCED;
944 if (open_elf (mod, &mod->aux_sym) != DWFL_E_NOERROR)
946 if (! find_aux_address_sync (mod))
948 elf_end (mod->aux_sym.elf);
949 mod->aux_sym.elf = NULL;
956 while ((scn = elf_nextscn (mod->aux_sym.elf, scn)) != NULL)
966 mod->aux_syments = shdr->sh_size / shdr->sh_entsize;
967 mod->aux_first_global = shdr->sh_info;
990 mod->aux_syments = 0;
991 elf_end (mod->aux_sym.elf);
992 mod->aux_sym.elf = NULL;
1002 /* Try to find a symbol table in either MOD->main.elf or MOD->debug.elf. */
1004 find_symtab (Dwfl_Module *mod)
1006 if (mod->symdata != NULL || mod->aux_symdata != NULL /* Already done. */
1007 || mod->symerr != DWFL_E_NOERROR) /* Cached previous failure. */
1010 __libdwfl_getelf (mod);
1011 mod->symerr = mod->elferr;
1012 if (mod->symerr != DWFL_E_NOERROR)
1019 mod->symerr = load_symtab (&mod->main, &mod->symfile, &symscn,
1020 &xndxscn, &mod->syments, &mod->first_global,
1022 switch (mod->symerr)
1032 mod->symerr = find_debuginfo (mod);
1033 switch (mod->symerr)
1039 mod->symerr = load_symtab (&mod->debug, &mod->symfile, &symscn,
1040 &xndxscn, &mod->syments,
1041 &mod->first_global, &strshndx);
1045 mod->symerr = DWFL_E_NO_SYMTAB;
1049 switch (mod->symerr)
1059 find_aux_sym (mod, &aux_symscn, &aux_xndxscn, &aux_strshndx);
1064 mod->symerr = DWFL_E_NOERROR;
1071 mod->symerr = DWFL_E_NOERROR;
1076 find_dynsym (mod);
1083 if (elf_strptr (mod->symfile->elf, strshndx, 0) == NULL)
1086 mod->symerr = DWFL_E (LIBELF, elf_errno ());
1090 /* Cache the data; MOD->syments and MOD->first_global were set above. */
1092 mod->symstrdata = elf_getdata (elf_getscn (mod->symfile->elf, strshndx),
1094 if (mod->symstrdata == NULL || mod->symstrdata->d_buf == NULL)
1098 mod->symxndxdata = NULL;
1101 mod->symxndxdata = elf_getdata (xndxscn, NULL);
1102 if (mod->symxndxdata == NULL || mod->symxndxdata->d_buf == NULL)
1106 mod->symdata = elf_getdata (symscn, NULL);
1107 if (mod->symdata == NULL || mod->symdata->d_buf == NULL)
1112 if (mod->syments > mod->symdata->d_size / shdr->sh_entsize
1113 || (size_t) mod->first_global > mod->syments)
1121 if (elf_strptr (mod->aux_sym.elf, aux_strshndx, 0) == NULL)
1124 mod->aux_syments = 0;
1125 elf_end (mod->aux_sym.elf);
1126 mod->aux_sym.elf = NULL;
1129 find_dynsym (mod);
1133 mod->aux_symstrdata = elf_getdata (elf_getscn (mod->aux_sym.elf,
1136 if (mod->aux_symstrdata == NULL || mod->aux_symstrdata->d_buf == NULL)
1140 mod->aux_symxndxdata = NULL;
1143 mod->aux_symxndxdata = elf_getdata (aux_xndxscn, NULL);
1144 if (mod->aux_symxndxdata == NULL
1145 || mod->aux_symxndxdata->d_buf == NULL)
1149 mod->aux_symdata = elf_getdata (aux_symscn, NULL);
1150 if (mod->aux_symdata == NULL || mod->aux_symdata->d_buf == NULL)
1155 if (mod->aux_syments > mod->aux_symdata->d_size / shdr->sh_entsize
1156 || (size_t) mod->aux_first_global > mod->aux_syments)
1162 /* Try to open a libebl backend for MOD. */
1165 __libdwfl_module_getebl (Dwfl_Module *mod)
1167 if (mod->ebl == NULL)
1169 __libdwfl_getelf (mod);
1170 if (mod->elferr != DWFL_E_NOERROR)
1171 return mod->elferr;
1173 mod->ebl = ebl_openbackend (mod->main.elf);
1174 if (mod->ebl == NULL)
1182 load_dw (Dwfl_Module *mod, struct dwfl_file *debugfile)
1184 if (mod->e_type == ET_REL && !debugfile->relocated)
1186 const Dwfl_Callbacks *const cb = mod->dwfl->callbacks;
1192 Dwfl_Error error = __libdwfl_module_getebl (mod);
1196 find_symtab (mod);
1197 Dwfl_Error result = mod->symerr;
1199 result = __libdwfl_relocate (mod, debugfile->elf, true);
1204 if (mod->main.fd != -1 && elf_cntl (mod->main.elf, ELF_C_FDREAD) == 0)
1206 close (mod->main.fd);
1207 mod->main.fd = -1;
1216 mod->dw = INTUSE(dwarf_begin_elf) (debugfile->elf, DWARF_C_READ, NULL);
1217 if (mod->dw == NULL)
1224 mod->lazycu = 1;
1231 find_dw (Dwfl_Module *mod)
1233 if (mod->dw != NULL /* Already done. */
1234 || mod->dwerr != DWFL_E_NOERROR) /* Cached previous failure. */
1237 __libdwfl_getelf (mod);
1238 mod->dwerr = mod->elferr;
1239 if (mod->dwerr != DWFL_E_NOERROR)
1243 mod->dwerr = load_dw (mod, &mod->main);
1244 switch (mod->dwerr)
1247 mod->debug.elf = mod->main.elf;
1248 mod->debug.address_sync = mod->main.address_sync;
1253 find_debug_altlink (mod, mod->main.name);
1264 mod->dwerr = find_debuginfo (mod);
1265 switch (mod->dwerr)
1268 mod->dwerr = load_dw (mod, &mod->debug);
1269 if (mod->dwerr == DWFL_E_NOERROR)
1274 find_debug_altlink (mod, mod->debug.name);
1281 mod->dwerr = DWFL_E_NO_DWARF;
1289 mod->dwerr = __libdwfl_canon_error (mod->dwerr);
1293 dwfl_module_getdwarf (Dwfl_Module *mod, Dwarf_Addr *bias)
1295 if (mod == NULL)
1298 find_dw (mod);
1299 if (mod->dwerr == DWFL_E_NOERROR)
1303 if (mod->e_type == ET_REL
1304 && mod->main.relocated && ! mod->debug.relocated)
1306 mod->debug.relocated = true;
1307 if (mod->debug.elf != mod->main.elf)
1308 (void) __libdwfl_relocate (mod, mod->debug.elf, false);
1311 *bias = dwfl_adjusted_dwarf_addr (mod, 0);
1312 return mod->dw;
1315 __libdwfl_seterrno (mod->dwerr);
1321 dwfl_module_getsymtab (Dwfl_Module *mod)
1323 if (mod == NULL)
1326 find_symtab (mod);
1327 if (mod->symerr == DWFL_E_NOERROR)
1329 return (mod->syments + mod->aux_syments
1330 - (mod->syments > 0 && mod->aux_syments > 0 ? 1 : 0));
1332 __libdwfl_seterrno (mod->symerr);
1338 dwfl_module_getsymtab_first_global (Dwfl_Module *mod)
1340 if (mod == NULL)
1343 find_symtab (mod);
1344 if (mod->symerr == DWFL_E_NOERROR)
1351 int skip_aux_zero = (mod->syments > 0 && mod->aux_syments > 0) ? 1 : 0;
1352 return mod->first_global + mod->aux_first_global - skip_aux_zero;
1355 __libdwfl_seterrno (mod->symerr);