Skip to content

Commit

Permalink
Initial regload support for linux-x32/64 coredumps
Browse files Browse the repository at this point in the history
  • Loading branch information
radare committed Jun 2, 2016
1 parent 24c0dfc commit 2702c3f
Show file tree
Hide file tree
Showing 3 changed files with 49 additions and 9 deletions.
41 changes: 36 additions & 5 deletions libr/bin/format/elf/elf.c
Original file line number Diff line number Diff line change
Expand Up @@ -23,13 +23,14 @@ static RBinElfSection *g_sections = NULL;

static inline int __strnlen(const char *str, int len) {
int l = 0;
while (IS_PRINTABLE(*str) && --len) {
if (((ut8)*str)==0xff)
while (IS_PRINTABLE (*str) && --len) {
if (((ut8)*str) == 0xff) {
break;
}
str++;
l++;
}
return l+1;
return l + 1;
}

static int handle_e_ident(struct Elf_(r_bin_elf_obj_t) *bin) {
Expand Down Expand Up @@ -159,10 +160,12 @@ static int init_shdr(struct Elf_(r_bin_elf_obj_t) *bin) {
int len;

if (!bin || bin->shdr) return true;
if (!UT32_MUL(&shdr_size, bin->ehdr.e_shnum, sizeof (Elf_(Shdr))))
if (!UT32_MUL(&shdr_size, bin->ehdr.e_shnum, sizeof (Elf_(Shdr)))) {
return false;
if (shdr_size < 1)
}
if (shdr_size < 1) {
return false;
}
if (shdr_size > bin->size)
return false;
if (bin->ehdr.e_shoff > bin->size)
Expand Down Expand Up @@ -1589,6 +1592,34 @@ char* Elf_(r_bin_elf_get_osabi_name)(struct Elf_(r_bin_elf_obj_t) *bin) {
return strdup ("linux");
}

ut8 *Elf_(r_bin_elf_grab_regstate)(struct Elf_(r_bin_elf_obj_t) *bin, int *len) {
RListIter *iter;
if (bin->phdr) {
int i;
int num = bin->ehdr.e_phnum;
for (i = 0; i < num; i++) {
if (bin->phdr[i].p_type != PT_NOTE) {
continue;
}
int bits = Elf_(r_bin_elf_get_bits)(bin);
int regdelta = (bits == 64)? 0x84: 0x40; // x64 vs x32
int regsize = 160; // for x86-64
ut8 *buf = malloc (regsize);
if (r_buf_read_at (bin->b, bin->phdr[i].p_offset + regdelta, buf, regsize) != regsize) {
free (buf);
eprintf ("Cannot read register state from CORE file\n");
return NULL;
}
if (len) {
*len = regsize;
}
return buf;
}
}
eprintf ("Cannot find NOTE section\n");
return NULL;
}

int Elf_(r_bin_elf_is_big_endian)(struct Elf_(r_bin_elf_obj_t) *bin) {
return (bin->ehdr.e_ident[EI_DATA] == ELFDATA2MSB);
}
Expand Down
1 change: 1 addition & 0 deletions libr/bin/format/elf/elf.h
Original file line number Diff line number Diff line change
Expand Up @@ -143,6 +143,7 @@ bool Elf_(r_bin_elf_entry_write)(struct Elf_(r_bin_elf_obj_t) *bin, ut64 addr);
int Elf_(r_bin_elf_del_rpath)(struct Elf_(r_bin_elf_obj_t) *bin);
int Elf_(r_bin_elf_has_relro)(struct Elf_(r_bin_elf_obj_t) *bin);
int Elf_(r_bin_elf_has_nx)(struct Elf_(r_bin_elf_obj_t) *bin);
ut8 *Elf_(r_bin_elf_grab_regstate)(struct Elf_(r_bin_elf_obj_t) *bin, int *len);

#endif

16 changes: 12 additions & 4 deletions libr/bin/p/bin_elf.c
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,16 @@ static void * load_bytes(RBinFile *arch, const ut8 *buf, ut64 sz, ut64 loadaddr,
if (res) {
sdb_ns_set (sdb, "info", res->kv);
}
const char *elf_type = Elf_(r_bin_elf_get_file_type (res));
if (elf_type && !strncmp (elf_type, "CORE", 4)) {
int len;
ut8 *regs = Elf_(r_bin_elf_grab_regstate)(res, &len);
eprintf ("LEN = %d\n", len);
char *hexregs = r_hex_bin2strdup (regs, len);
eprintf ("arw %s\n", hexregs);
free (hexregs);
free (regs);
}
r_buf_free (tbuf);
return res;
}
Expand All @@ -55,15 +65,14 @@ static int load(RBinFile *arch) {
const ut8 *bytes = arch ? r_buf_buffer (arch->buf) : NULL;
ut64 sz = arch ? r_buf_size (arch->buf): 0;
if (!arch || !arch->o) return false;
arch->o->bin_obj = load_bytes (arch, bytes, sz,
arch->o->loadaddr, arch->sdb);
arch->o->bin_obj = load_bytes (arch, bytes, sz, arch->o->loadaddr, arch->sdb);
return arch->o->bin_obj != NULL;
}

static int destroy(RBinFile *arch) {
int i;
ELFOBJ* eobj = arch->o->bin_obj;
for (i=0; i< eobj->imports_by_ord_size; i++) {
for (i = 0; i < eobj->imports_by_ord_size; i++) {
RBinImport *imp = eobj->imports_by_ord[i];
if (imp) {
free (imp->name);
Expand Down Expand Up @@ -138,7 +147,6 @@ static RList* sections(RBinFile *arch) {
struct Elf_(r_bin_elf_obj_t)* obj = arch && arch->o ? arch->o->bin_obj : NULL;
Elf_(Phdr)* phdr = NULL;


if (!obj || !(ret = r_list_new ()))
return NULL;
ret->free = free;
Expand Down

0 comments on commit 2702c3f

Please sign in to comment.