depgraph for r2 ascii graphs, agn doesnt requires body now

This commit is contained in:
pancake 2015-12-10 22:45:00 +01:00
parent c07c288f19
commit 6dc0bd41c1
3 changed files with 80 additions and 78 deletions

View File

@ -2662,12 +2662,13 @@ static void cmd_agraph_node(RCore *core, const char *input) {
input++; input++;
args = r_str_argv (input, &n_args); args = r_str_argv (input, &n_args);
if (n_args != 2) { if (n_args < 1 || n_args>2) {
r_cons_printf ("Wrong arguments\n"); r_cons_printf ("Wrong arguments\n");
r_str_argv_free (args); r_str_argv_free (args);
break; break;
} }
//strdup cause there is double free in r_str_argv_free due to a realloc call //strdup cause there is double free in r_str_argv_free due to a realloc call
if (n_args>1) {
body = strdup (args[1]); body = strdup (args[1]);
if (strncmp (body, "base64:", B_LEN) == 0) { if (strncmp (body, "base64:", B_LEN) == 0) {
body = r_str_replace (body, "\\n", "", true); body = r_str_replace (body, "\\n", "", true);
@ -2681,6 +2682,9 @@ static void cmd_agraph_node(RCore *core, const char *input) {
body = newbody; body = newbody;
} }
body = r_str_concat (body, "\n"); body = r_str_concat (body, "\n");
} else {
body = strdup ("");
}
r_agraph_add_node (core->graph, args[0], body); r_agraph_add_node (core->graph, args[0], body);
r_str_argv_free (args); r_str_argv_free (args);
free (body); free (body);
@ -2809,13 +2813,13 @@ static void cmd_anal_graph(RCore *core, const char *input) {
case '-': case '-':
r_agraph_reset (core->graph); r_agraph_reset (core->graph);
break; break;
case 'n': case 'n': // "agn"
cmd_agraph_node (core, input + 1); cmd_agraph_node (core, input + 1);
break; break;
case 'e': case 'e': // "age"
cmd_agraph_edge (core, input + 1); cmd_agraph_edge (core, input + 1);
break; break;
case 'g': case 'g': // "agg"
cmd_agraph_print (core, input + 1); cmd_agraph_print (core, input + 1);
break; break;
case 't': case 't':

View File

@ -1,4 +1,4 @@
/* Copyright radare2 2014-2015 - Author: pancake, ret2libc */ /* Copyright radare2 - 2014-2015 - pancake, ret2libc */
#include <r_core.h> #include <r_core.h>
#include <r_cons.h> #include <r_cons.h>
@ -777,18 +777,14 @@ static RGraphNode *get_sibling (const RAGraph *g, const RANode *n, int is_left,
return res; return res;
} }
static int adjust_class_val (const RAGraph *g, const RGraphNode *gn, static int adjust_class_val (const RAGraph *g, const RGraphNode *gn, const RGraphNode *sibl, Sdb *res, int is_left) {
const RGraphNode *sibl, Sdb *res, int is_left) { if (is_left) return hash_get_int (res, sibl) - hash_get_int (res, gn) - dist_nodes (g, gn, sibl);
if (is_left)
return hash_get_int (res, sibl) - hash_get_int (res, gn) - dist_nodes (g, gn, sibl);
else
return hash_get_int (res, gn) - hash_get_int (res, sibl) - dist_nodes (g, sibl, gn); return hash_get_int (res, gn) - hash_get_int (res, sibl) - dist_nodes (g, sibl, gn);
} }
/* adjusts the position of previously placed left/right classes */ /* adjusts the position of previously placed left/right classes */
/* tries to place classes as close as possible */ /* tries to place classes as close as possible */
static void adjust_class (const RAGraph *g, int is_left, static void adjust_class (const RAGraph *g, int is_left, RList **classes, Sdb *res, int c) {
RList **classes, Sdb *res, int c) {
const RGraphNode *gn; const RGraphNode *gn;
const RListIter *it; const RListIter *it;
const RANode *an; const RANode *an;
@ -841,26 +837,19 @@ static void adjust_class (const RAGraph *g, int is_left,
} }
} }
static int place_nodes_val (const RAGraph *g, const RGraphNode *gn, static int place_nodes_val (const RAGraph *g, const RGraphNode *gn, const RGraphNode *sibl, Sdb *res, int is_left) {
const RGraphNode *sibl, Sdb *res, int is_left) { if (is_left) return hash_get_int (res, sibl) + dist_nodes (g, sibl, gn);
if (is_left)
return hash_get_int (res, sibl) + dist_nodes (g, sibl, gn);
return hash_get_int (res, sibl) - dist_nodes (g, gn, sibl); return hash_get_int (res, sibl) - dist_nodes (g, gn, sibl);
} }
static int place_nodes_sel_p (int newval, int oldval, int is_first, int is_left) { static int place_nodes_sel_p (int newval, int oldval, int is_first, int is_left) {
if (is_first) if (is_first) return newval;
return newval; if (is_left) return R_MAX (oldval, newval);
if (is_left)
return R_MAX (oldval, newval);
else
return R_MIN (oldval, newval); return R_MIN (oldval, newval);
} }
/* places left/right the nodes of a class */ /* places left/right the nodes of a class */
static void place_nodes (const RAGraph *g, const RGraphNode *gn, int is_left, static void place_nodes (const RAGraph *g, const RGraphNode *gn, int is_left, Sdb *v_nodes, RList **classes, Sdb *res, Sdb *placed) {
Sdb *v_nodes, RList **classes, Sdb *res, Sdb *placed) {
const RList *lv = hash_get_rlist (v_nodes, gn); const RList *lv = hash_get_rlist (v_nodes, gn);
int p = 0, v, is_first = true; int p = 0, v, is_first = true;
const RGraphNode *gk; const RGraphNode *gk;
@ -1068,8 +1057,7 @@ static int RP_listcmp (const struct len_pos_t *a, const struct len_pos_t *b) {
return a->pos >= b->pos; return a->pos >= b->pos;
} }
static void collect_changes (const RAGraph *g, int l, const RGraphNode *b, static void collect_changes (const RAGraph *g, int l, const RGraphNode *b, int from_up, int s, int e, RList *list, int is_left) {
int from_up, int s, int e, RList *list, int is_left) {
const RGraphNode *vt = g->layers[l].nodes[e - 1]; const RGraphNode *vt = g->layers[l].nodes[e - 1];
const RGraphNode *vtp = g->layers[l].nodes[s]; const RGraphNode *vtp = g->layers[l].nodes[s];
RListComparator lcmp; RListComparator lcmp;
@ -1112,10 +1100,8 @@ static void collect_changes (const RAGraph *g, int l, const RGraphNode *b,
cx = R_NEW0 (struct len_pos_t); cx = R_NEW0 (struct len_pos_t);
cx->len = c; cx->len = c;
cx->pos = avi->x; cx->pos = avi->x;
if (is_left) if (is_left) cx->pos += dist_nodes (g, vi, vt);
cx->pos += dist_nodes (g, vi, vt); else cx->pos -= dist_nodes (g, vtp, vi);
else
cx->pos -= dist_nodes (g, vtp, vi);
r_list_add_sorted (list, cx, lcmp); r_list_add_sorted (list, cx, lcmp);
} }
@ -1125,17 +1111,13 @@ static void collect_changes (const RAGraph *g, int l, const RGraphNode *b,
cx = R_NEW (struct len_pos_t); cx = R_NEW (struct len_pos_t);
cx->len = is_left ? INT_MAX : INT_MIN; cx->len = is_left ? INT_MAX : INT_MIN;
cx->pos = ab->x; cx->pos = ab->x;
if (is_left) if (is_left) cx->pos += dist_nodes (g, b, vt);
cx->pos += dist_nodes (g, b, vt); else cx->pos -= dist_nodes (g, vtp, b);
else
cx->pos -= dist_nodes (g, vtp, b);
r_list_add_sorted (list, cx, lcmp); r_list_add_sorted (list, cx, lcmp);
} }
} }
static void combine_sequences (const RAGraph *g, int l, static void combine_sequences (const RAGraph *g, int l, const RGraphNode *bm, const RGraphNode *bp, int from_up, int a, int r) {
const RGraphNode *bm, const RGraphNode *bp,
int from_up, int a, int r) {
RList *Rm = r_list_new (), *Rp = r_list_new (); RList *Rm = r_list_new (), *Rp = r_list_new ();
const RGraphNode *vt, *vtp; const RGraphNode *vt, *vtp;
RANode *at, *atp; RANode *at, *atp;
@ -1186,14 +1168,12 @@ static void combine_sequences (const RAGraph *g, int l,
for (i = t - 2; i >= a; --i) { for (i = t - 2; i >= a; --i) {
const RGraphNode *gv = g->layers[l].nodes[i]; const RGraphNode *gv = g->layers[l].nodes[i];
RANode *av = get_anode (gv); RANode *av = get_anode (gv);
av->x = R_MIN (av->x, at->x - dist_nodes (g, gv, vt)); av->x = R_MIN (av->x, at->x - dist_nodes (g, gv, vt));
} }
for (i = t + 1; i < r; ++i) { for (i = t + 1; i < r; ++i) {
const RGraphNode *gv = g->layers[l].nodes[i]; const RGraphNode *gv = g->layers[l].nodes[i];
RANode *av = get_anode (gv); RANode *av = get_anode (gv);
av->x = R_MAX (av->x, atp->x + dist_nodes (g, vtp, gv)); av->x = R_MAX (av->x, atp->x + dist_nodes (g, vtp, gv));
} }
} }
@ -1203,9 +1183,7 @@ static void combine_sequences (const RAGraph *g, int l,
* neighbours in the "previous" layer. Those neighbours are considered as * neighbours in the "previous" layer. Those neighbours are considered as
* "fixed". The previous layer depends on the direction used during the layers * "fixed". The previous layer depends on the direction used during the layers
* traversal */ * traversal */
static void place_sequence (const RAGraph *g, int l, static void place_sequence (const RAGraph *g, int l, const RGraphNode *bm, const RGraphNode *bp, int from_up, int va, int vr) {
const RGraphNode *bm, const RGraphNode *bp,
int from_up, int va, int vr) {
int vt; int vt;
if (vr == va + 1) { if (vr == va + 1) {
@ -1563,7 +1541,6 @@ static char *get_body (RCore *core, ut64 addr, int size, bool with_offset,
static void get_bbupdate(RAGraph *g, RCore *core, RAnalFunction *fcn) { static void get_bbupdate(RAGraph *g, RCore *core, RAnalFunction *fcn) {
RAnalBlock *bb; RAnalBlock *bb;
RListIter *iter; RListIter *iter;
core->keep_asmqjmps = false; core->keep_asmqjmps = false;
r_list_foreach (fcn->bbs, iter, bb) { r_list_foreach (fcn->bbs, iter, bb) {
RANode *node; RANode *node;
@ -1858,7 +1835,7 @@ static void agraph_set_layout(RAGraph *g, bool is_interactive) {
RGraphNode *n; RGraphNode *n;
RANode *a; RANode *a;
set_layout(g); set_layout (g);
update_graph_sizes (g); update_graph_sizes (g);
graph_foreach_anode (r_graph_get_nodes (g->graph), it, n, a) { graph_foreach_anode (r_graph_get_nodes (g->graph), it, n, a) {
@ -1884,9 +1861,9 @@ static void agraph_print_node(const RAGraph *g, RANode *n) {
const int cur = g->curnode && get_anode (g->curnode) == n; const int cur = g->curnode && get_anode (g->curnode) == n;
if (is_mini (g)) { if (is_mini (g)) {
small_RANode_print(g, n, cur); small_RANode_print (g, n, cur);
} else { } else {
normal_RANode_print(g, n, cur); normal_RANode_print (g, n, cur);
} }
} }
@ -2024,13 +2001,13 @@ static void follow_nth(RAGraph *g, int nth) {
} }
static void agraph_follow_true(RAGraph *g) { static void agraph_follow_true(RAGraph *g) {
follow_nth(g, 0); follow_nth (g, 0);
agraph_update_seek(g, get_anode (g->curnode), false); agraph_update_seek (g, get_anode (g->curnode), false);
} }
static void agraph_follow_false(RAGraph *g) { static void agraph_follow_false(RAGraph *g) {
follow_nth(g, 1); follow_nth (g, 1);
agraph_update_seek(g, get_anode (g->curnode), false); agraph_update_seek (g, get_anode (g->curnode), false);
} }
/* seek the next node in visual order */ /* seek the next node in visual order */
@ -2046,8 +2023,7 @@ static void agraph_prev_node(RAGraph *g) {
} }
static void agraph_update_title (RAGraph *g, RAnalFunction *fcn) { static void agraph_update_title (RAGraph *g, RAnalFunction *fcn) {
const char *mode_str = g->is_callgraph ? mode2str(g, "CG") : const char *mode_str = g->is_callgraph ? mode2str(g, "CG") : mode2str (g, "BB");
mode2str (g, "BB");
char *new_title = r_str_newf( char *new_title = r_str_newf(
"[0x%08"PFMT64x"]> VV @ %s (nodes %d edges %d zoom %d%%) %s mouse:%s movements-speed:%d", "[0x%08"PFMT64x"]> VV @ %s (nodes %d edges %d zoom %d%%) %s mouse:%s movements-speed:%d",
fcn->addr, fcn->name, g->graph->n_nodes, g->graph->n_edges, fcn->addr, fcn->name, g->graph->n_nodes, g->graph->n_edges,
@ -2271,8 +2247,8 @@ R_API RANode *r_agraph_add_node(const RAGraph *g, const char *title, const char
if (res) return res; if (res) return res;
res = R_NEW0 (RANode); res = R_NEW0 (RANode);
if (!res) return NULL; if (!res) return NULL;
res->title = title ? strdup(title) : strdup(""); res->title = title ? strdup(title) : strdup ("");
res->body = body ? strdup(body) : strdup(""); res->body = body ? strdup(body) : strdup ("");
res->layer = -1; res->layer = -1;
res->pos_in_layer = -1; res->pos_in_layer = -1;
res->is_dummy = false; res->is_dummy = false;
@ -2318,9 +2294,8 @@ R_API bool r_agraph_del_node(const RAGraph *g, const char *title) {
innodes = r_graph_innodes (g->graph, res->gnode); innodes = r_graph_innodes (g->graph, res->gnode);
graph_foreach_anode (innodes, it, gn, an) { graph_foreach_anode (innodes, it, gn, an) {
sdb_array_remove (g->db, const char *key = sdb_fmt (2, "agraph.nodes.%s.neighbours", an->title);
sdb_fmt (2, "agraph.nodes.%s.neighbours", an->title), sdb_array_remove (g->db, key, res->title, 0);
res->title, 0);
} }
r_graph_del_node (g->graph, res->gnode); r_graph_del_node (g->graph, res->gnode);
@ -2330,8 +2305,7 @@ R_API bool r_agraph_del_node(const RAGraph *g, const char *title) {
return true; return true;
} }
static int user_node_cb(struct g_cb *user, const char *k UNUSED, static int user_node_cb(struct g_cb *user, const char *k UNUSED, const char *v) {
const char *v) {
RANodeCallback cb = user->node_cb; RANodeCallback cb = user->node_cb;
void *user_data = user->data; void *user_data = user->data;
RANode *n = (RANode *)(size_t)sdb_atoi (v); RANode *n = (RANode *)(size_t)sdb_atoi (v);
@ -2339,8 +2313,7 @@ static int user_node_cb(struct g_cb *user, const char *k UNUSED,
return 1; return 1;
} }
static int user_edge_cb(struct g_cb *user, const char *k UNUSED, static int user_edge_cb(struct g_cb *user, const char *k UNUSED, const char *v) {
const char *v) {
RAEdgeCallback cb = user->edge_cb; RAEdgeCallback cb = user->edge_cb;
RAGraph *g = user->graph; RAGraph *g = user->graph;
void *user_data = user->data; void *user_data = user->data;

View File

@ -4,12 +4,37 @@
# #
grep -e DEPS */Makefile | sed -e 's,/Makefile,,' > /tmp/rdeps.txt grep -e DEPS */Makefile | sed -e 's,/Makefile,,' > /tmp/rdeps.txt
MODE=dot if [ -z "$1" ]; then
#MODE=gml MODE=dot
#MODE=gml
MODE=r2
else
MODE="$1"
fi
if [ $MODE = "dot" ]; then if [ "$MODE" = "-h" ]; then
echo "digraph G {"; echo "Usage: depgraph [r2|dot|gml]"
exit 0
elif [ $MODE = "r2" ]; then
cat /tmp/rdeps.txt | perl -ne '
use List::MoreUtils qw(uniq);
/(.*):(.*)=(.*)$/;
my $lib=$1;
@deps=split(/ /, $3);
foreach $dep (uniq @deps) {
print "agn $dep\n";
}
foreach $dep (@deps) {
print "age $dep r_$lib\n";
}'
echo "agg"
elif [ $MODE = "dot" ]; then
echo "digraph G {"
cat /tmp/rdeps.txt | perl -ne ' cat /tmp/rdeps.txt | perl -ne '
/(.*):(.*)=(.*)$/; /(.*):(.*)=(.*)$/;
my $lib=$1; my $lib=$1;