From 52da64becceaa8b7f2bdefd3359f86545bd36662 Mon Sep 17 00:00:00 2001 From: Ahmed Mohamed Abd El-MAwgood Date: Sun, 14 Aug 2016 03:07:43 +0300 Subject: [PATCH] Fix for function name decorators (oridinal, sym.blablabla) (#5488) implemented function guess matched name which finds longest function name in sdb_types that is substring of the current function name --- libr/anal/types.c | 23 +++++++++++++++++++++-- libr/core/cmd_anal.c | 4 ++-- libr/core/tp.c | 8 ++++++-- libr/include/r_anal.h | 3 ++- 4 files changed, 31 insertions(+), 7 deletions(-) diff --git a/libr/anal/types.c b/libr/anal/types.c index 524a118918..8a27c56d86 100644 --- a/libr/anal/types.c +++ b/libr/anal/types.c @@ -247,7 +247,7 @@ R_API char *r_anal_type_format(RAnal *anal, const char *t) { } // Function prototypes api R_API int r_anal_type_func_exist(RAnal *anal, const char *func_name) { - char *fcn = sdb_const_get (anal->sdb_types, func_name, 0); + const char *fcn = sdb_const_get (anal->sdb_types, func_name, 0); return fcn && !strcmp (fcn, "func"); } @@ -277,5 +277,24 @@ R_API char *r_anal_type_func_args_name(RAnal *anal, const char *func_name, int i char *query = sdb_fmt (-1, "func.%s.arg.%d", func_name, i); const char *get = sdb_const_get (anal->sdb_types, query, 0); char *ret = strchr (get, ','); - return ret ==0 ? ret : ret + 1; + return ret == 0 ? ret : ret + 1; +} +static int capture_sub_string (void *p, const char *k, const char *v) { + char **ret = (char **)p; + if (strcmp (v, "func")) { + return 1; + } + if (strstr (ret[1], k) && (!ret[0] || strlen(k) > strlen (ret[0]))) { + free (ret[0]); + ret[0] = strdup (k); + } + return 1; +} +R_API char *r_anal_type_func_guess(RAnal *anal, char *func_name) { + char *ret[] = { + NULL, + func_name + }; + sdb_foreach (anal->sdb_types, capture_sub_string, ret); + return ret[0]; } diff --git a/libr/core/cmd_anal.c b/libr/core/cmd_anal.c index bdf39667d6..c4e01be584 100644 --- a/libr/core/cmd_anal.c +++ b/libr/core/cmd_anal.c @@ -5,14 +5,14 @@ static void type_cmd_help (RCore *core) { const char *help_msg[] = { "Usage:", "aftm", "", - "aftm", "", "type matching ana", + "aftm", "", "type matching analysis", NULL }; r_core_cmd_help (core, help_msg); } static void type_cmd(RCore *core, const char *input) { RAnalFunction *fcn = r_anal_get_fcn_in (core->anal, core->offset, -1); - if (!fcn) { + if (!fcn && *input != '?') { eprintf ("cant find function here\n"); } switch (*input) { diff --git a/libr/core/tp.c b/libr/core/tp.c index 5863f00aea..bb467876f4 100644 --- a/libr/core/tp.c +++ b/libr/core/tp.c @@ -15,11 +15,14 @@ static bool r_anal_emul_init (RCore *core) { } return true; } -static void type_match (RCore *core, ut64 addr, const char *fcn_name) { +static void type_match (RCore *core, ut64 addr, char *name) { Sdb *trace = core->anal->esil->db_trace; RAnal *anal = core->anal; RAnalVar *v; - if (!r_anal_type_func_exist (anal, fcn_name)) { + char *fcn_name; + if (r_anal_type_func_exist (anal, name)) { + fcn_name = strdup (name); + } else if (!(fcn_name = r_anal_type_func_guess (anal, name))) { eprintf ("can't find function prototype for %s\n",fcn_name); return; } @@ -134,6 +137,7 @@ static void type_match (RCore *core, ut64 addr, const char *fcn_name) { } free (type); } + free (fcn_name); } static int stack_clean (RCore *core, ut64 addr, RAnalFunction *fcn) { diff --git a/libr/include/r_anal.h b/libr/include/r_anal.h index 30e8a4d297..7b213741ba 100644 --- a/libr/include/r_anal.h +++ b/libr/include/r_anal.h @@ -1124,7 +1124,8 @@ R_API int r_anal_type_func_exist(RAnal *anal, const char *func_name); R_API const char *r_anal_type_func_cc(RAnal *anal, const char *func_name); R_API int r_anal_type_func_args_count(RAnal *anal, const char *func_name); R_API char *r_anal_type_func_args_type(RAnal *anal, const char *func_name, int i); - R_API char *r_anal_type_func_args_name(RAnal *anal, const char *func_name, int i); +R_API char *r_anal_type_func_args_name(RAnal *anal, const char *func_name, int i); +R_API char *r_anal_type_func_guess(RAnal *anal, char *func_name); /* anal.c */ R_API RAnal *r_anal_new(void); R_API int r_anal_purge (RAnal *anal);