Fix #14530 - Implementation of i.~{} aka RCoreItem ##anal

This commit is contained in:
radare 2019-07-10 18:31:16 +02:00 committed by GitHub
parent 4892bdb3ab
commit c8bda90d59
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
8 changed files with 216 additions and 18 deletions

View File

@ -1,6 +1,5 @@
/* radare - LGPL - Copyright 2008-2018 - nibble, pancake */
// TODO: rename to r_anal_meta_get() ??
#if 0
TODO
====

View File

@ -9,7 +9,7 @@ DEPS+=r_reg r_search r_syscall r_socket r_fs r_magic r_crypto
OBJS=core.o cmd.o cfile.o cconfig.o visual.o cio.o yank.o libs.o agraph.o
OBJS+=fortune.o hack.o vasm.o patch.o cbin.o corelog.o rtr.o cmd_api.o
OBJS+=carg.o canal.o project.o gdiff.o casm.o disasm.o plugin.o
OBJS+=vmenus.o vmenus_graph.o vmenus_zigns.o zdiff.o
OBJS+=vmenus.o vmenus_graph.o vmenus_zigns.o zdiff.o citem.o
OBJS+=task.o panels.o pseudo.o vmarks.o anal_tp.o anal_objc.o blaze.o cundo.o
OBJS+=esil_data_flow.o

View File

@ -468,14 +468,13 @@ static int is_hit_inrange(RCoreAsmHit *hit, ut64 start_range, ut64 end_range){
R_API RList *r_core_asm_bwdisassemble(RCore *core, ut64 addr, int n, int len) {
RAsmOp op;
// len = n * 32;
// if (n > core->blocksize) n = core->blocksize;
ut64 at;
ut32 idx = 0, hit_count;
int numinstr, asmlen, ii;
const int addrbytes = core->io->addrbytes;
RAsmCode *c;
RList *hits = r_core_asm_hit_list_new();
RList *hits = r_core_asm_hit_list_new ();
if (!hits) {
return NULL;
}
@ -504,14 +503,14 @@ R_API RList *r_core_asm_bwdisassemble(RCore *core, ut64 addr, int n, int len) {
if (r_cons_is_breaked ()) {
break;
}
c = r_asm_mdisassemble (core->assembler, buf+(len-idx), idx);
c = r_asm_mdisassemble (core->assembler, buf + len - idx, idx);
if (strstr (c->assembly, "invalid") || strstr (c->assembly, ".byte")) {
r_asm_code_free(c);
continue;
}
numinstr = 0;
asmlen = strlen (c->assembly);
for(ii = 0; ii < asmlen; ++ii) {
for (ii = 0; ii < asmlen; ++ii) {
if (c->assembly[ii] == '\n') {
++numinstr;
}

87
libr/core/citem.c Normal file
View File

@ -0,0 +1,87 @@
/* radare - LGPL - Copyright 2019 - pancake */
#include <r_core.h>
R_API RCoreItem *r_core_item_at (RCore *core, ut64 addr) {
RCoreItem *ci = R_NEW0 (RCoreItem);
ci->addr = addr;
RIOMap *map = r_io_map_get (core->io, addr);
if (map) {
ci->perm = map->perm;
// TODO: honor section perms too?
if (map->perm & R_PERM_X) {
// if theres a meta consider it data
RAnalMetaItem *item = r_meta_find (core->anal, addr, R_META_TYPE_ANY, 0);
if (item) {
switch (item->type) {
case R_META_TYPE_DATA:
ci->type = "data";
ci->size = item->size;
ci->data = r_core_cmd_strf (core, "pdi 1 @e:asm.flags=0@e:asm.lines=0@e:scr.color=0@0x%08"PFMT64x, addr);
r_str_trim (ci->data);
break;
case R_META_TYPE_FORMAT:
ci->type = "format"; // struct :?
ci->size = item->size;
break;
case R_META_TYPE_STRING:
ci->type = "string";
ci->size = item->size;
break;
}
if (item->str) {
if (!ci->data) {
ci->data = strdup (item->str);
}
}
}
}
}
RAnalFunction *fcn = r_anal_get_fcn_in (core->anal, addr, 1);
if (fcn) {
ci->fcnname = strdup (fcn->name);
}
RBinObject *o = r_bin_cur_object (core->bin);
RBinSection *sec = r_bin_get_section_at (o, addr, core->io->va);
if (sec) {
ci->sectname = strdup (sec->name);
}
if (!ci->data) {
RAnalOp* op = r_core_anal_op (core, addr, R_ANAL_OP_MASK_ESIL | R_ANAL_OP_MASK_HINT);
if (op) {
if (!ci->data) {
if (op->mnemonic) {
ci->data = strdup (op->mnemonic);
} else {
ci->data = r_core_cmd_strf (core, "pi 1 @e:scr.color=0@0x%08"PFMT64x, addr);
r_str_trim (ci->data);
}
}
ci->size = op->size;
r_anal_op_free (op);
}
}
char *cmt = r_core_cmd_strf (core, "CC.@0x%08"PFMT64x, addr);
if (cmt) {
if (*cmt) {
ci->comment = strdup (cmt);
r_str_trim (ci->comment);
}
free (cmt);
}
if (!ci->type) {
ci->type = "code";
}
ci->next = ci->addr + ci->size;
char *prev = r_core_cmd_strf (core, "pd -1@e:asm.lines=0~[0]");
r_str_trim (prev);
ci->prev = r_num_get (NULL, prev);
free (prev);
return ci;
}
R_API void r_core_item_free (RCoreItem *ci) {
free (ci->data);
free (ci);
}

View File

@ -117,23 +117,85 @@ static bool demangle_internal(RCore *core, const char *lang, const char *s) {
return true;
}
static int demangle(RCore *core, const char *s) {
char *p, *q;
static bool demangle(RCore *core, const char *s) {
r_return_val_if_fail (core && s, false);
const char *ss = strchr (s, ' ');
if (!*s) {
return 0;
return false;
}
if (!ss) {
const char *lang = r_config_get (core->config, "bin.lang");
demangle_internal (core, lang, s);
return 1;
return true;
}
p = strdup (s);
q = p + (ss - s);
char *p = strdup (s);
char *q = p + (ss - s);
*q = 0;
demangle_internal (core, p, q + 1);
free (p);
return 1;
return true;
}
static void cmd_info_here(RCore *core, int mode) {
RCoreItem *item = r_core_item_at (core, core->offset);
if (item) {
PJ *pj = pj_new ();
pj_o (pj);
pj_ks (pj, "type", item->type);
pj_ks (pj, "perm", r_str_rwx_i (item->perm));
pj_kn (pj, "size", item->size);
pj_kn (pj, "addr", item->addr);
pj_kn (pj, "next", item->next);
pj_kn (pj, "prev", item->prev);
if (item->fcnname) {
pj_ks (pj, "fcnname", item->fcnname);
}
if (item->sectname) {
pj_ks (pj, "sectname", item->sectname);
}
if (item->comment) {
pj_ks (pj, "comment", item->comment);
}
RListIter *iter;
RAnalRef *ref;
if (item->data) {
pj_ks (pj, "data", item->data);
}
{
RList *refs = r_anal_refs_get (core->anal, core->offset);
if (refs && r_list_length (refs) > 0) {
pj_k (pj, "refs");
pj_a (pj);
r_list_foreach (refs, iter, ref) {
pj_o (pj);
pj_ks (pj, "type", r_anal_ref_type_tostring (ref->type));
pj_kn (pj, "addr", ref->addr);
pj_end (pj);
}
pj_end (pj);
}
}
{
RList *refs = r_anal_xrefs_get (core->anal, core->offset);
if (refs && r_list_length (refs) > 0) {
pj_k (pj, "xrefs");
pj_a (pj);
r_list_foreach (refs, iter, ref) {
pj_o (pj);
pj_ks (pj, "type", r_anal_ref_type_tostring (ref->type));
pj_kn (pj, "addr", ref->addr);
pj_end (pj);
}
pj_end (pj);
}
}
pj_end (pj);
char *s = pj_drain (pj);
r_cons_printf ("%s\n", s);
free (s);
r_core_item_free (item);
}
}
#define STR(x) (x)? (x): ""
@ -1074,6 +1136,9 @@ static int cmd_info(void *data, const char *input) {
}
cmd_info_bin (core, va, mode);
goto done;
case '.': // "i."
cmd_info_here (core, input[1]);
goto done;
default:
cmd_info_bin (core, va, mode);
break;

View File

@ -903,10 +903,10 @@ static void ds_free(RDisasmState *ds) {
/* XXX move to r_print */
static char *colorize_asm_string(RCore *core, RDisasmState *ds, bool print_color) {
char *spacer = NULL;
char *source = ds->opstr? ds->opstr: r_asm_op_get_asm (&ds->asmop);
char *hlstr = r_meta_get_string (ds->core->anal, R_META_TYPE_HIGHLIGHT, ds->at);
bool partial_reset = line_highlighted (ds) ? true : ((hlstr && *hlstr) ? true : false);
free (hlstr);
RAnalFunction *f = ds->show_color_args ? fcnIn (ds, ds->vat, R_ANAL_FCN_TYPE_NULL) : NULL;
if (!ds->show_color || !ds->colorop) {
@ -917,7 +917,7 @@ static char *colorize_asm_string(RCore *core, RDisasmState *ds, bool print_color
r_cons_strcat (r_print_color_op_type (core->print, ds->analop.type));
}
// workaround dummy colorizer in case of paired commands (tms320 & friends)
spacer = strstr (source, "||");
char *spacer = strstr (source, "||");
if (spacer) {
char *scol1, *s1 = r_str_ndup (source, spacer - source);
char *scol2, *s2 = strdup (spacer + 2);
@ -1545,14 +1545,13 @@ R_API int r_core_bb_starts_in_middle(RCore *core, ut64 at, int oplen) {
static void ds_print_show_cursor(RDisasmState *ds) {
RCore *core = ds->core;
char res[] = " ";
void *p;
if (!ds->show_marks) {
return;
}
int q = core->print->cur_enabled &&
ds->cursor >= ds->index &&
ds->cursor < (ds->index + ds->asmop.size);
p = r_bp_get_at (core->dbg->bp, ds->at);
RBreakpointItem *p = r_bp_get_at (core->dbg->bp, ds->at);
if (ds->midflags) {
(void)handleMidFlags (core, ds, false);
}
@ -2701,6 +2700,7 @@ static void ds_adistrick_comments(RDisasmState *ds) {
}
}
// TODO move into RAnal.meta
static bool ds_print_data_type(RDisasmState *ds, const ut8 *buf, int ib, int size) {
RCore *core = ds->core;
const char *type = NULL;
@ -2717,7 +2717,7 @@ static bool ds_print_data_type(RDisasmState *ds, const ut8 *buf, int ib, int siz
// adjust alignment
r_cons_printf (" ");
ut64 n = r_read_ble (buf, core->print->big_endian, size * 8);
{
if (r_config_get_i (core->config, "asm.marks")) {
int q = core->print->cur_enabled &&
ds->cursor >= ds->index &&
ds->cursor < (ds->index + size);
@ -6090,6 +6090,34 @@ toro:
case R_META_TYPE_DATA:
//r_cons_printf (".data: %s\n", meta->str);
i += meta->size;
{
int idx = i;
ut64 at = core->offset + i;
int hexlen = len - idx;
int delta = at - meta->from;
if (meta->size < hexlen) {
hexlen = meta->size;
}
// int oplen = meta->size - delta;
core->print->flags &= ~R_PRINT_FLAGS_HEADER;
// TODO do not pass a copy in parameter buf that is possibly to small for this
// print operation
int size = R_MIN (meta->size, len - idx);
ut8 *buf = calloc (size, 1);
if (buf) {
r_io_read_at (core->io, at, buf, size);
RDisasmState ds = {0};
ds.core = core;
if (!ds_print_data_type (&ds, buf, 0, size)) {
r_cons_printf ("hex length=%" PFMT64d " delta=%d\n", size , delta);
r_print_hexdump (core->print, at, buf+idx, hexlen-delta, 16, 1, 1);
} else {
r_cons_newline ();
}
free (buf);
}
ret = true;
}
continue;
case R_META_TYPE_STRING:
//r_cons_printf (".string: %s\n", meta->str);

View File

@ -4,6 +4,7 @@ r_core_sources = [
'esil_data_flow.c',
'casm.c',
'blaze.c',
'citem.c',
'canal.c',
'carg.c',
'cbin.c',

View File

@ -141,6 +141,7 @@ typedef struct r_core_file_t {
ut8 alive;
} RCoreFile;
typedef struct r_core_times_t {
ut64 loadlibs_init_time;
ut64 loadlibs_time;
@ -333,6 +334,24 @@ typedef struct r_core_t {
RList *ropchain;
} RCore;
// maybe move into RAnal
typedef struct r_core_item_t {
const char *type;
ut64 addr;
ut64 next;
ut64 prev;
int size;
int perm;
char *data;
char *comment;
char *sectname;
char *fcnname;
} RCoreItem;
R_API RCoreItem *r_core_item_at (RCore *core, ut64 addr);
R_API void r_core_item_free (RCoreItem *ci);
R_API int r_core_bind(RCore *core, RCoreBind *bnd);
typedef struct r_core_cmpwatch_t {