char * elf_strptr(Elf * elf, size_t ndx, size_t off) { Elf_Scn * s; Elf_Data * d; char * rc; if (elf == 0) return (0); extern const char *elf_macho_str_off(size_t off); if (elf->ed_kind == ELF_K_MACHO && (ndx == SHN_MACHO || ndx == SHN_MACHO_64)) return (char *)elf_macho_str_off(off); if ((s = elf_getscn(elf, ndx)) == 0) { _elf_seterr(EREQ_STRSCN, 0); return (0); } READLOCKS(elf, s) if (elf->ed_class == ELFCLASS32) { Elf32_Shdr* sh = (Elf32_Shdr*)s->s_shdr; if ((sh == 0) || (sh->sh_type != SHT_STRTAB)) { _elf_seterr(EREQ_STRSCN, 0); READUNLOCKS(elf, s) return (0); }
static Dwarf * scngrp_read (Dwarf *result, Elf *elf, GElf_Ehdr *ehdr, Dwarf_Cmd cmd, Elf_Scn *scngrp) { /* SCNGRP is the section descriptor for a section group which might contain debug sections. */ Elf_Data *data = elf_getdata (scngrp, NULL); if (data == NULL) { /* We cannot read the section content. Fail! */ free (result); return NULL; } /* The content of the section is a number of 32-bit words which represent section indices. The first word is a flag word. */ Elf32_Word *scnidx = (Elf32_Word *) data->d_buf; size_t cnt; for (cnt = 1; cnt * sizeof (Elf32_Word) <= data->d_size; ++cnt) { Elf_Scn *scn = elf_getscn (elf, scnidx[cnt]); if (scn == NULL) { /* A section group refers to a non-existing section. Should never happen. */ __libdw_seterrno (DWARF_E_INVALID_ELF); free (result); return NULL; } check_section (result, ehdr, scn, true); } return valid_p (result); }
static Elf_Scn *elf_section_by_name(Elf *elf, GElf_Ehdr *ep, GElf_Shdr *shp, const char *name, size_t *idx) { Elf_Scn *sec = NULL; size_t cnt = 1; /* Elf is corrupted/truncated, avoid calling elf_strptr. */ if (!elf_rawdata(elf_getscn(elf, ep->e_shstrndx), NULL)) return NULL; while ((sec = elf_nextscn(elf, sec)) != NULL) { char *str; gelf_getshdr(sec, shp); str = elf_strptr(elf, ep->e_shstrndx, shp->sh_name); if (!strcmp(name, str)) { if (idx) *idx = cnt; break; } ++cnt; } return sec; }
int find_symbol(char *fn, struct lsym *lsym, unsigned long baseaddr) { struct lsym *ls; int num = 0; for (ls = lsym; ls->name; ls++) num++; elf_version(EV_CURRENT); int fd = open(fn, O_RDONLY); if (fd < 0) return -1; long ret = -1; Elf *elf = elf_begin(fd, ELF_C_READ, NULL); if (elf == NULL) goto out; GElf_Ehdr header; if (!gelf_getehdr(elf, &header)) goto out_elf; Elf_Scn *section = NULL; int found = 0; while (found < num && (section = elf_nextscn(elf, section)) != 0) { GElf_Shdr shdr, *sh; sh = gelf_getshdr(section, &shdr); if (sh->sh_type == SHT_SYMTAB || sh->sh_type == SHT_DYNSYM) { Elf_Data *data = elf_getdata(section, NULL); GElf_Sym *sym, symbol; int j; unsigned numsym = sh->sh_size / sh->sh_entsize; for (j = 0; j < numsym; j++) { sym = gelf_getsymshndx(data, NULL, j, &symbol, NULL); char *symname = elf_strptr(elf, shdr.sh_link, sym->st_name); for (ls = lsym; ls->name; ls++) { if (!strcmp(symname, ls->name)) { Elf_Scn *oscn = elf_getscn(elf, sym->st_shndx); GElf_Shdr oshdr, *osh; osh = gelf_getshdr(oscn, &oshdr); ls->addr = (sym->st_value - osh->sh_addr) + osh->sh_offset + baseaddr; found++; if (found == num) break; } } } } } if (found == num) ret = 0; out_elf: elf_end(elf); out: close(fd); return ret; }
int elf_getphnum(Elf *elf, size_t *phnum) { GElf_Ehdr ehdr; Elf_Scn *scn; GElf_Shdr shdr0; if (gelf_getehdr(elf, &ehdr) == NULL) return (0); if (ehdr.e_phnum != PN_XNUM) { *phnum = ehdr.e_phnum; return (1); } if ((scn = elf_getscn(elf, 0)) == NULL || gelf_getshdr(scn, &shdr0) == NULL) return (0); if (shdr0.sh_info == 0) *phnum = ehdr.e_phnum; else *phnum = shdr0.sh_info; return (1); }
static void handle_dynamic_section(elf_info_s *elf, Elf_Scn *scn, GElf_Shdr shdr) { Elf_Data *data; GElf_Addr replt_addr; size_t replt_count; /* get data of .dynamic */ data = elf_getdata(scn, NULL); /* iterate through .dynamic */ for (size_t i = 0; i < shdr.sh_size / shdr.sh_entsize; ++i) { GElf_Dyn dyn; // get entries i gelf_getdyn(data, i, &dyn); // if replt if (dyn.d_tag == DT_JMPREL) replt_addr = dyn.d_un.d_ptr; // if replt_size if (dyn.d_tag == DT_PLTRELSZ) replt_count = dyn.d_un.d_val; } LOG(INFO, "Section relplt at 0x%lx (%zu)", replt_addr, replt_count); for (size_t i = 1; i < elf->hdr.e_shnum; ++i) { Elf_Scn *scn; GElf_Shdr shdr; scn = elf_getscn(elf->elf, i); gelf_getshdr(scn, &shdr); if (shdr.sh_addr == replt_addr && shdr.sh_size == replt_count) { elf->replt = elf_getdata(scn, NULL); elf->replt_count = shdr.sh_size / shdr.sh_entsize; break; } } }
Elf_Scn * get_scnbyname(Elf *elf, char *name, int *num) { Elf32_Ehdr * ehdr; Elf_Scn * scn; Elf32_Shdr * shdr; Elf_Data * data; int cnt, tmp; if (!num) num = &tmp; *num = 0; if ((ehdr = elf32_getehdr(elf))==NULL) return NULL; if (((scn = elf_getscn(elf, ehdr->e_shstrndx)) == NULL) || ((data = elf_getdata(scn, NULL)) == NULL)) return NULL; for (cnt = 1, scn = NULL; (scn = elf_nextscn(elf, scn)); cnt++) { if ((shdr = elf32_getshdr(scn)) == NULL) return NULL; if (! strcmp(name, (char *)data->d_buf + shdr->sh_name)) { *num = cnt; return scn; } } return NULL; }
char* elf_strptr(Elf *elf, size_t section, size_t offset) { Elf_Scn *scn; Elf_Data *sd; if (!elf) { return NULL; } elf_assert(elf->e_magic == ELF_MAGIC); if (!(scn = elf_getscn(elf, section))) { return NULL; } if (scn->s_type != SHT_STRTAB) { seterr(ERROR_NOSTRTAB); return NULL; } if (offset >= 0 && offset < scn->s_size) { sd = NULL; while ((sd = elf_getdata(scn, sd))) { if (sd->d_buf && offset >= (size_t)sd->d_off && offset < (size_t)sd->d_off + sd->d_size) { return (char*)sd->d_buf + (offset - sd->d_off); } } } seterr(ERROR_BADSTROFF); return NULL; }
Elf_Scn *elf_utils_new_scn_with_name(Elf *e, const char *scn_name) { Elf_Scn *scn; GElf_Shdr shdr; size_t shstrndx, index, namelen; Elf_Data *shstrdata; void *ptr; ELF_ASSERT(elf_getshdrstrndx(e, &shstrndx) == 0); ELF_ASSERT(scn = elf_getscn(e, shstrndx)); ELF_ASSERT(shstrdata = elf_getdata(scn, NULL)); namelen = strlen(scn_name) + 1; ELF_ASSERT(gelf_getshdr(scn, &shdr)); if (!elf_utils_shift_contents(e, shdr.sh_offset + shdr.sh_size, namelen)) goto failure; ASSERT(ptr = realloc(shstrdata->d_buf, shstrdata->d_size + namelen)); index = shstrdata->d_size; strcpy(ptr+index, scn_name); shstrdata->d_buf = ptr; shstrdata->d_size += namelen; shdr.sh_size += namelen; ELF_ASSERT(gelf_update_shdr(scn, &shdr)); ELF_ASSERT(scn = elf_newscn(e)); ELF_ASSERT(gelf_getshdr(scn, &shdr)); shdr.sh_name = index; ELF_ASSERT(gelf_update_shdr(scn, &shdr)); return scn; failure: return NULL; }
bool addr_in_section (Elf *elf, GElf_Word shndx, GElf_Addr addr) { GElf_Shdr shdr; Elf_Scn *scn = elf_getscn (elf, shndx); gelf_getshdr (scn, &shdr); return addr >= shdr.sh_addr && addr < shdr.sh_addr + shdr.sh_size; }
static void set_flag(char *ifile, ulong_t flval) { Elf *elf; Elf_Scn *scn; Elf_Data *data; GElf_Shdr shdr; GElf_Dyn dyn; int fd, secidx, nent, i; (void) elf_version(EV_CURRENT); if ((fd = open(ifile, O_RDWR)) < 0) die("Can't open %s", ifile); if ((elf = elf_begin(fd, ELF_C_RDWR, NULL)) == NULL) elfdie("Can't start ELF for %s", ifile); if ((secidx = findelfsecidx(elf, ".dynamic")) == -1) die("Can't find .dynamic section in %s\n", ifile); if ((scn = elf_getscn(elf, secidx)) == NULL) elfdie("elf_getscn (%d)", secidx); if (gelf_getshdr(scn, &shdr) == NULL) elfdie("gelf_shdr"); if ((data = elf_getdata(scn, NULL)) == NULL) elfdie("elf_getdata"); nent = shdr.sh_size / shdr.sh_entsize; for (i = 0; i < nent; i++) { if (gelf_getdyn(data, i, &dyn) == NULL) elfdie("gelf_getdyn"); if (dyn.d_tag == DT_FLAGS_1) { dyn.d_un.d_val |= (Elf64_Xword)flval; if (gelf_update_dyn(data, i, &dyn) == 0) elfdie("gelf_update_dyn"); break; } } if (i == nent) { die("%s's .dynamic section doesn't have a DT_FLAGS_1 " "field\n", ifile); } if (elf_update(elf, ELF_C_WRITE) == -1) elfdie("Couldn't update %s with changes", ifile); (void) elf_end(elf); (void) close(fd); }
Elf_Scn *xelf_getscn(Elf *e, size_t idx) { Elf_Scn *scn = elf_getscn(e, idx); if (scn == NULL) { eprintf("elf_getscn() failed: %s", elf_errmsg(-1)); exit(EXIT_FAILURE); } return scn; }
static const char * elf_section_name (Elf *elf, GElf_Word shndx) { GElf_Ehdr ehdr; GElf_Shdr shdr; Elf_Scn *scn = elf_getscn (elf, shndx); gelf_getshdr (scn, &shdr); gelf_getehdr (elf, &ehdr); return elf_strptr (elf, ehdr.e_shstrndx, shdr.sh_name); }
/* Load the ELF section with the specified index and set the pointer pointed to by section_data to the memory where it was loaded. */ int _dwarf_load_section(Dwarf_Debug dbg, Dwarf_Half section_index, Dwarf_Small ** section_data, Dwarf_Error * error) { if (section_index == 0) { return DW_DLV_NO_ENTRY; } /* check to see if the section is already loaded */ if (*section_data != NULL) { return DW_DLV_OK; } { #ifdef __SGI_FAST_LIBELF enum elf_sgi_error_type sres; sres = elf_sgi_section(dbg->de_elf, section_index, (void**) section_data); if (sres != ELF_SGI_ERROR_OK) { DWARF_DBG_ERROR(dbg, _dwarf_error_code_from_elf_sgi_error_code(sres), DW_DLV_ERROR); } #else Elf_Scn* scn; Elf_Data* data; scn = elf_getscn(dbg->de_elf, section_index); if (scn == NULL) { _dwarf_error(dbg, error, DW_DLE_MDE); return DW_DLV_ERROR; } /* When using libelf as a producer, section data may be stored in multiple buffers. In libdwarf however, we only use libelf as a consumer (there is a dwarf producer API, but it doesn't use libelf). Because of this, this single call to elf_getdata will retrieve the entire section in a single contiguous buffer. */ data = elf_getdata(scn, NULL); if (data == NULL) { _dwarf_error(dbg, error, DW_DLE_MDE); return DW_DLV_ERROR; } *section_data = data->d_buf; #endif /* !defined(__SGI_FAST_LIBELF) */ } return DW_DLV_OK; }
unsigned long _libelf_checksum(Elf *e, int elfclass) { size_t shn; Elf_Scn *scn; Elf_Data *d; unsigned long checksum; GElf_Ehdr eh; GElf_Shdr shdr; if (e == NULL) { LIBELF_SET_ERROR(ARGUMENT, 0); return (0L); } if (e->e_class != elfclass) { LIBELF_SET_ERROR(CLASS, 0); return (0L); } if (gelf_getehdr(e, &eh) == NULL) return (0); /* * Iterate over all sections in the ELF file, computing the * checksum along the way. * * The first section is always SHN_UNDEF and can be skipped. * Non-allocatable sections are skipped, as are sections that * could be affected by utilities such as strip(1). */ checksum = 0; for (shn = 1; shn < e->e_u.e_elf.e_nscn; shn++) { if ((scn = elf_getscn(e, shn)) == NULL) return (0); if (gelf_getshdr(scn, &shdr) == NULL) return (0); if ((shdr.sh_flags & SHF_ALLOC) == 0 || shdr.sh_type == SHT_DYNAMIC || shdr.sh_type == SHT_DYNSYM) continue; d = NULL; while ((d = elf_rawdata(scn, d)) != NULL) checksum = _libelf_sum(checksum, (unsigned char *) d->d_buf, d->d_size); } /* * Return a 16-bit checksum compatible with Solaris. */ return (((checksum >> 16) & 0xFFFFUL) + (checksum & 0xFFFFUL)); }
/* * Load template of the function described by the given symbol. */ static struct code_template* function_template_load32(Elf* e, Elf32_Sym* func32) { Elf_Scn* scn = elf_getscn(e, func32->st_shndx); assert(scn); Elf32_Shdr* shdr32 = elf32_getshdr(scn); assert(shdr32); return ct_load(e, scn, func32->st_value, func32->st_size, shdr32->sh_addralign); }
static struct code_template* function_template_load64(Elf* e, Elf64_Sym* func64) { Elf_Scn* scn = elf_getscn(e, func64->st_shndx); assert(scn); Elf64_Shdr* shdr64 = elf64_getshdr(scn); assert(shdr64); return ct_load(e, scn, func64->st_value, func64->st_size, shdr64->sh_addralign); }
Elf_Scn * elf_nextscn(Elf *e, Elf_Scn *s) { if (e == NULL || (e->e_kind != ELF_K_ELF) || (s && s->s_elf != e)) { LIBELF_SET_ERROR(ARGUMENT, 0); return (NULL); } return (s == NULL ? elf_getscn(e, (size_t) 1) : STAILQ_NEXT(s, s_next)); }
static int init_scns() { Elf* e = g.e; size_t shstrndx = g.shstrndx; size_t shdrnum = g.shdrnum; int i = 0; GElf_Shdr shdr; Elf_Scn** buf = (Elf_Scn**)malloc(shdrnum * sizeof(Elf_Scn*)); GElf_Shdr* buf2 = (GElf_Shdr*)malloc(shdrnum * sizeof(GElf_Shdr)); if (buf == NULL) { errx (EXIT_FAILURE , "malloc failed"); return -1; } Elf_Scn *scn = NULL; while ((scn = elf_nextscn(e, scn)) != NULL && i < shdrnum) { if (gelf_getshdr (scn , & shdr ) != & shdr) { errx ( EXIT_FAILURE , " getshdr () failed : %s.", elf_errmsg ( -1)); free(buf); return -1; } buf[i] = scn; buf2[i] = shdr; i++; } if (i < shdrnum) { /* the .shstrtab section*/ /* size_t shstrndx; */ /* if (elf_getshdrstrndx (e, &shstrndx) != 0) */ /* errx (EXIT_FAILURE, " getshdrstrndx () failed : %s.", */ /* elf_errmsg (-1)); */ if ((scn = elf_getscn (e, shstrndx)) == NULL ) errx ( EXIT_FAILURE , " getscn () failed : %s.", elf_errmsg ( -1)); if (gelf_getshdr(scn , &shdr) != & shdr ) errx ( EXIT_FAILURE , " getshdr ( shstrndx ) failed : %s.", elf_errmsg ( -1)); buf[i] = scn; buf2[i] = shdr; } // printf("[D] No. of sections:%d\n", i-1); g.scns = buf; g.shdrs = buf2; return 0; }
static int is_function(Elf *elf, GElf_Sym *sym) { Elf_Scn *scn; GElf_Shdr shdr; /* * With dynamic linking, it is possible that certain undefined * symbols exist in the objects. The actual definition will be * found elsewhere, so we'll just skip it for this object. */ if (sym->st_shndx == SHN_UNDEF) return (0); if (GELF_ST_TYPE(sym->st_info) == STT_FUNC) { if (GELF_ST_BIND(sym->st_info) == STB_GLOBAL) return (1); if (GELF_ST_BIND(sym->st_info) == STB_WEAK) return (1); if (gflag && GELF_ST_BIND(sym->st_info) == STB_LOCAL) return (1); } /* * It's not a function; determine if it's in an executable section. */ if (GELF_ST_TYPE(sym->st_info) != STT_NOTYPE) return (0); /* * If it isn't global, and it isn't weak, and it isn't * a 'local with the gflag set', then get out. */ if (GELF_ST_BIND(sym->st_info) != STB_GLOBAL && GELF_ST_BIND(sym->st_info) != STB_WEAK && !(gflag && GELF_ST_BIND(sym->st_info) == STB_LOCAL)) return (0); if (sym->st_shndx >= SHN_LORESERVE) return (0); scn = elf_getscn(elf, sym->st_shndx); (void) gelf_getshdr(scn, &shdr); if (!(shdr.sh_flags & SHF_EXECINSTR)) return (0); return (1); }
static void handle_dynsym_section(elf_info_s *elf, Elf_Scn *scn, GElf_Shdr shdr) { Elf_Data *data; /* get .dynsym data and size */ elf->dynsym = elf_getdata(scn, NULL); elf->dynsym_count = shdr.sh_size / shdr.sh_entsize; /* retrieve the header table index link which point to .dynstr */ scn = elf_getscn(elf->elf, shdr.sh_link); gelf_getshdr(scn, &shdr); /* get the data of .dynstr */ data = elf_getdata(scn, NULL); elf->dynstr = data->d_buf; }
Elf_Scn* getSection(Elf *elf,const char *name) { Elf64_Ehdr *ehdr = elf64_getehdr(elf); if(!ehdr) return NULL; Elf_Data *data = elf_getdata(elf_getscn(elf,ehdr->e_shstrndx),NULL); if(!data) return NULL; for(Elf_Scn *scn = NULL;(scn = elf_nextscn(elf,scn));) { Elf64_Shdr *shdr = elf64_getshdr(scn); if(shdr && !strcmp(name,(const char*)data->d_buf + shdr->sh_name)) return scn; } return NULL; }
/* if this function encounters an error it never returns */ static void exec_getsection( Elf *elf, size_t index, Elf32_Shdr **shdr, Elf_Data **data, int line ) #define exec_getsection(a,b,c,d) \ exec_getsection(a,b,c,d,__LINE__) { Elf_Scn *section; char *location; location = NULL; section = elf_getscn( elf, index ); if ( section ) { if ( shdr ) { *shdr = elf32_getshdr(section); if ( *shdr == NULL ) { location = "elf32_getshdr"; } } if ( location == NULL && data ) { *data = elf_getdata(section, NULL); if ( *data == NULL ) { location = "elf_getdata"; } else if ( (*data)->d_buf == NULL ) { location = "d_buf"; } } if ( location == NULL ) { return; } } else { location = "elf_getscn"; } fprintf( stderr, "exec_getsection: %s@%d - %s\n", location, line, elf_errmsg( -1 ) ); exit( 1 ); }
Dwfl_Error internal_function __libdwfl_relocate_value (Dwfl_Module *mod, Elf *elf, size_t *shstrndx, Elf32_Word shndx, GElf_Addr *value) { assert (mod->e_type == ET_REL); Elf_Scn *refscn = elf_getscn (elf, shndx); GElf_Shdr refshdr_mem, *refshdr = gelf_getshdr (refscn, &refshdr_mem); if (refshdr == NULL) return DWFL_E_LIBELF; if (refshdr->sh_addr == 0 && (refshdr->sh_flags & SHF_ALLOC)) { /* This is a loaded section. Find its actual address and update the section header. */ if (*shstrndx == SHN_UNDEF && unlikely (elf_getshdrstrndx (elf, shstrndx) < 0)) return DWFL_E_LIBELF; const char *name = elf_strptr (elf, *shstrndx, refshdr->sh_name); if (unlikely (name == NULL)) return DWFL_E_LIBELF; if ((*mod->dwfl->callbacks->section_address) (MODCB_ARGS (mod), name, shndx, refshdr, &refshdr->sh_addr)) return CBFAIL; if (refshdr->sh_addr == (Dwarf_Addr) -1l) /* The callback indicated this section wasn't really loaded but we don't really care. */ refshdr->sh_addr = 0; /* Make no adjustment below. */ /* Update the in-core file's section header to show the final load address (or unloadedness). This serves as a cache, so we won't get here again for the same section. */ if (likely (refshdr->sh_addr != 0) && unlikely (! gelf_update_shdr (refscn, refshdr))) return DWFL_E_LIBELF; } if (refshdr->sh_flags & SHF_ALLOC) /* Apply the adjustment. */ *value += dwfl_adjusted_address (mod, refshdr->sh_addr); return DWFL_E_NOERROR; }
/* * Return TRUE(1) if the given section is ".bss" for "-p" option. * Return FALSE(0) if not ".bss" section. */ static int is_bss_section(unsigned int shndx, Elf * elf_file, unsigned int shstrndx) { Elf_Scn *scn = elf_getscn(elf_file, shndx); char *sym_name; if (scn != NULL) { GElf_Shdr shdr; (void) gelf_getshdr(scn, &shdr); sym_name = elf_strptr(elf_file, shstrndx, shdr.sh_name); if (strcmp(BSS_SECN, sym_name) == 0) return (1); } return (0); }
/* * Get section descriptor for the associated string table * and verify that the type of the section pointed to is * indeed of type STRTAB. Returns a valid section descriptor * or NULL on error. */ static Elf_Scn * get_scnfd(Elf * e_file, int shstrtab, int SCN_TYPE) { Elf_Scn *fd_scn; GElf_Shdr shdr; if ((fd_scn = elf_getscn(e_file, shstrtab)) == NULL) { return (NULL); } (void) gelf_getshdr(fd_scn, &shdr); if (shdr.sh_type != SCN_TYPE) { return (NULL); } return (fd_scn); }
void elf_utils_free_scn_contents(Elf *e, int scndx) { Elf_Scn *scn; Elf_Data *data; ELF_ASSERT(scn = elf_getscn(e, scndx)); data = NULL; while ((data = elf_getdata(scn, data)) != NULL) { free(data->d_buf); data->d_buf = NULL; } failure: return; }
Dwfl_Error internal_function __libdwfl_relocate (Dwfl_Module *mod, Elf *debugfile, bool debug) { assert (mod->e_type == ET_REL); GElf_Ehdr ehdr_mem; const GElf_Ehdr *ehdr = gelf_getehdr (debugfile, &ehdr_mem); if (ehdr == NULL) return DWFL_E_LIBELF; size_t d_shstrndx; if (elf_getshdrstrndx (debugfile, &d_shstrndx) < 0) return DWFL_E_LIBELF; RELOC_SYMTAB_CACHE (reloc_symtab); /* Look at each section in the debuginfo file, and process the relocation sections for debugging sections. */ Dwfl_Error result = DWFL_E_NOERROR; Elf_Scn *scn = NULL; while (result == DWFL_E_NOERROR && (scn = elf_nextscn (debugfile, scn)) != NULL) { GElf_Shdr shdr_mem; GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem); if ((shdr->sh_type == SHT_REL || shdr->sh_type == SHT_RELA) && shdr->sh_size != 0) { /* It's a relocation section. */ Elf_Scn *tscn = elf_getscn (debugfile, shdr->sh_info); if (unlikely (tscn == NULL)) result = DWFL_E_LIBELF; else result = relocate_section (mod, debugfile, ehdr, d_shstrndx, &reloc_symtab, scn, shdr, tscn, debug, !debug); } } return result; }
int elf_utils_duplicate_scn_contents(Elf *e, int scndx) { Elf_Scn *scn; Elf_Data *data; void *new_data; ELF_ASSERT(scn = elf_getscn(e, scndx)); data = NULL; while ((data = elf_getdata(scn, data)) != NULL) { ASSERT(new_data = malloc(data->d_size)); memcpy(new_data, data->d_buf, data->d_size); data->d_buf = new_data; } return 1; failure: return 0; }
bool ElfWriter::addSectionData(int section_index, void *data, uint64_t size) { Elf_Scn *scn = elf_getscn(m_elf, section_index); if (!scn) { logError("Unable to retrieve section number"); return false; } Elf_Data *elfData = elf_newdata(scn); if (!elfData) { logError("Unable to add section data"); return false; } elfData->d_buf = data; elfData->d_type = ELF_T_BYTE; elfData->d_size = size; elfData->d_off = 0; elfData->d_align = 1; elfData->d_version = EV_CURRENT; return true; }