- Add field at to RAnalRef
  - Set ref->at to the addrees of the opcode which does the
    jump/call
  - Set correctly the xrefs "from" address
* r_core
  - Modify afl to accept an optional argument [fcn name] to
    filter output by function
  - Change afl output to group xrefs by type (code and data)
This commit is contained in:
Nibble 2010-08-02 12:42:59 +02:00
parent cfc552e156
commit a7750b3204
7 changed files with 49 additions and 38 deletions

View File

@ -138,7 +138,7 @@ int main(int argc, char **argv) {
r_core_gdiff (core, file, file2, va);
if (rad) {
r_core_anal_bb_list (core, R_TRUE);
r_core_anal_fcn_list (core, R_TRUE);
r_core_anal_fcn_list (core, NULL, R_TRUE);
} else
r_core_anal_graph (core, 0, R_CORE_ANAL_GRAPHBODY|R_CORE_ANAL_GRAPHDIFF);
r_core_free (core);

View File

@ -92,20 +92,17 @@ R_API int r_anal_fcn(RAnal *anal, RAnalFcn *fcn, ut64 addr, ut8 *buf, ut64 len)
}
switch (aop.type) {
case R_ANAL_OP_TYPE_JMP:
case R_ANAL_OP_TYPE_CJMP:
case R_ANAL_OP_TYPE_CALL:
r_list_foreach (fcn->refs, iter, refi) {
if (aop.jump == refi->addr)
goto _dup_ref;
}
if (!(ref = r_anal_ref_new ())) {
eprintf ("Error: new (ref)\n");
return R_ANAL_RET_ERROR;
}
ref = R_NEW (RAnalRef);
ref->type = R_ANAL_REF_TYPE_CODE;
ref->at = aop.addr;
ref->addr = aop.jump;
r_list_append (fcn->refs, ref);
_dup_ref:
break;
case R_ANAL_OP_TYPE_RET:
return R_ANAL_RET_END;

View File

@ -10,6 +10,7 @@ R_API RAnalRef *r_anal_ref_new() { // TODO: deprecate?
RAnalRef *ref = R_NEW (RAnalRef);
if (ref) {
ref->addr = -1;
ref->at = -1;
ref->type = R_ANAL_REF_TYPE_CODE; // HUH?
}
return ref;

View File

@ -259,6 +259,7 @@ R_API int r_core_anal_fcn(RCore *core, ut64 at, ut64 from, int depth) {
return R_ANAL_RET_ERROR;
}
ref->addr = from;
ref->at = at;
r_list_append (fcni->xrefs, ref);
}
return R_FALSE;
@ -280,18 +281,24 @@ R_API int r_core_anal_fcn(RCore *core, ut64 at, ut64 from, int depth) {
if (f) { /* Check if it's already flagged */
fcn->name = strdup (f->name);
} else {
char *flagname;
fcn->name = r_str_dup_printf ("fcn_%08"PFMT64x"", at);
fcn->name = r_str_dup_printf ("fcn.%08"PFMT64x"", at);
/* Add flag */
flagname = r_str_dup_printf ("fcn.%s", fcn->name);
r_flag_space_set (core->flags, "functions");
r_flag_set (core->flags, flagname, at, fcn->size, 0);
free (flagname);
r_flag_set (core->flags, fcn->name, at, fcn->size, 0);
}
if (from != -1) {
if (!(ref = r_anal_ref_new ())) {
eprintf ("Error: new (xref)\n");
return R_ANAL_RET_ERROR;
}
ref->addr = from;
ref->at = at;
r_list_append (fcn->xrefs, ref);
}
r_list_append (core->anal->fcns, fcn);
r_list_foreach (fcn->refs, iter, refi) {
if (refi->addr != -1)
r_core_anal_fcn (core, refi->addr, at, depth-1);
if (refi->addr != -1 && (refi->addr < fcn->addr || refi->addr > fcn->addr+fcn->size))
r_core_anal_fcn (core, refi->addr, refi->at, depth-1);
}
}
} while (fcnlen != R_ANAL_RET_END);
@ -339,33 +346,38 @@ R_API void r_core_anal_refs(RCore *core, ut64 addr, int gv) {
r_cons_printf ("}\n");
}
R_API int r_core_anal_fcn_list(RCore *core, int rad) {
R_API int r_core_anal_fcn_list(RCore *core, const char *input, int rad) {
RAnalFcn *fcni;
struct r_anal_ref_t *refi;
struct r_anal_var_t *vari;
RListIter *iter, *iter2;
r_list_foreach (core->anal->fcns, iter, fcni)
if (!rad) {
r_cons_printf ("[0x%08"PFMT64x"] size=%"PFMT64d" name=%s",
fcni->addr, fcni->size, fcni->name);
r_cons_printf (" diff=%s", fcni->diff=='m'?"match": fcni->diff=='u'?"unmatch": "new");
r_cons_printf ("\n refs: ");
r_list_foreach (fcni->refs, iter2, refi) {
r_cons_printf ("0x%08"PFMT64x"(%c) ", refi->addr, refi->type);
}
r_cons_printf ("\n xrefs: ");
r_list_foreach (fcni->xrefs, iter2, refi) {
r_cons_printf ("0x%08"PFMT64x"(%c) ", refi->addr, refi->type);
}
r_cons_printf ("\n vars:\n");
r_list_foreach (fcni->vars, iter2, vari) {
r_cons_printf (" %-10s delta=0x%02x type=%s\n", vari->name, vari->delta,
r_anal_var_type_to_str (core->anal, vari->type));
}
r_cons_newline ();
} else r_cons_printf ("af+ 0x%08"PFMT64x" %"PFMT64d" %s (%c)\n",
fcni->addr, fcni->size, fcni->name, fcni->diff?fcni->diff:'n');
if (input == NULL || input[0] == '\0' || !strcmp (fcni->name, input+1)) {
if (!rad) {
r_cons_printf ("[0x%08"PFMT64x"] size=%"PFMT64d" name=%s",
fcni->addr, fcni->size, fcni->name);
r_cons_printf (" diff=%s",
fcni->diff=='m'?"match":fcni->diff=='u'?"unmatch":"new");
r_cons_printf ("\n refs: ");
r_list_foreach (fcni->refs, iter2, refi)
r_cons_printf ("0x%08"PFMT64x"(%c) ", refi->addr, refi->type);
r_cons_printf ("\n CODE xrefs: ");
r_list_foreach (fcni->xrefs, iter2, refi)
if (refi->type == R_ANAL_REF_TYPE_CODE)
r_cons_printf ("0x%08"PFMT64x" ", refi->addr, refi->type);
r_cons_printf ("\n DATA xrefs: ");
r_list_foreach (fcni->xrefs, iter2, refi)
if (refi->type == R_ANAL_REF_TYPE_DATA)
r_cons_printf ("0x%08"PFMT64x" ", refi->addr, refi->type);
r_cons_printf ("\n vars:\n");
r_list_foreach (fcni->vars, iter2, vari)
r_cons_printf (" %-10s delta=0x%02x type=%s\n", vari->name,
vari->delta, r_anal_var_type_to_str (core->anal, vari->type));
r_cons_newline ();
} else r_cons_printf ("af+ 0x%08"PFMT64x" %"PFMT64d" %s (%c)\n",
fcni->addr, fcni->size, fcni->name, fcni->diff?fcni->diff:'n');
}
r_cons_flush ();
return R_TRUE;
}

View File

@ -1680,10 +1680,10 @@ static int cmd_anal(void *data, const char *input) {
}
break;
case 'l':
r_core_anal_fcn_list (core, 0);
r_core_anal_fcn_list (core, input+2, 0);
break;
case '*':
r_core_anal_fcn_list (core, 1);
r_core_anal_fcn_list (core, input+2, 1);
break;
case '?':
r_cons_printf (
@ -1691,7 +1691,7 @@ static int cmd_anal(void *data, const char *input) {
" af @ [addr] ; Analyze functions (start at addr)\n"
" af+ addr size name [diff] ; Add function\n"
" af- [addr] ; Clean all function analysis data (or function at addr)\n"
" afl ; List functions\n"
" afl [fcn name] ; List functions\n"
" af* ; Output radare commands\n");
break;
default:

View File

@ -246,6 +246,7 @@ enum {
typedef struct r_anal_ref_t {
int type;
ut64 at;
ut64 addr;
} RAnalRef;

View File

@ -128,7 +128,7 @@ R_API int r_core_anal_bb(RCore *core, ut64 at, int depth, int head);
R_API int r_core_anal_bb_list(struct r_core_t *core, int rad);
R_API int r_core_anal_bb_seek(struct r_core_t *core, ut64 addr);
R_API int r_core_anal_fcn(struct r_core_t *core, ut64 at, ut64 from, int depth);
R_API int r_core_anal_fcn_list(struct r_core_t *core, int rad);
R_API int r_core_anal_fcn_list(RCore *core, const char *input, int rad);
R_API int r_core_anal_graph(struct r_core_t *core, ut64 addr, int opts);
R_API int r_core_anal_graph_fcn(struct r_core_t *core, char *input, int opts);