mirror of
https://github.com/radareorg/radare2.git
synced 2024-11-24 13:49:50 +00:00
Improve array indexing in disassembly ##anal
This commit is contained in:
parent
b4e2ebd031
commit
bc4b5933d2
@ -911,6 +911,17 @@ static void ds_highlight_word(RDisasmState * ds, char *word, char *color) {
|
||||
ds->opstr = asm_str? asm_str: source;
|
||||
}
|
||||
|
||||
static char *get_op_ireg (void *user, ut64 addr) {
|
||||
RCore *core = (RCore *)user;
|
||||
char *res = NULL;
|
||||
RAnalOp *op = r_core_anal_op (core, addr, R_ANAL_OP_MASK_ESIL);
|
||||
if (op && op->ireg) {
|
||||
res = strdup (op->ireg);
|
||||
}
|
||||
r_anal_op_free (op);
|
||||
return res;
|
||||
}
|
||||
|
||||
static void ds_build_op_str(RDisasmState *ds, bool print_color) {
|
||||
RCore *core = ds->core;
|
||||
if (!ds->opstr) {
|
||||
@ -925,6 +936,7 @@ static void ds_build_op_str(RDisasmState *ds, bool print_color) {
|
||||
ut64 at = ds->vat;
|
||||
RAnalFunction *f = fcnIn (ds, at, R_ANAL_FCN_TYPE_NULL);
|
||||
core->parser->varlist = r_anal_var_list_dynamic;
|
||||
core->parser->get_op_ireg = get_op_ireg;
|
||||
r_parse_varsub (core->parser, f, at, ds->analop.size,
|
||||
ds->opstr, ds->strsub, sizeof (ds->strsub));
|
||||
if (*ds->strsub) {
|
||||
|
@ -34,6 +34,7 @@ typedef struct r_parse_t {
|
||||
RAnalHint *hint; // weak anal ref
|
||||
RList *parsers;
|
||||
RAnalVarList varlist;
|
||||
char* (*get_op_ireg)(void *user, ut64 addr);
|
||||
RAnalBind analb;
|
||||
} RParse;
|
||||
|
||||
|
@ -300,36 +300,55 @@ static inline int issegoff (const char *w) {
|
||||
}
|
||||
#endif
|
||||
|
||||
static void parse_localvar (RParse *p, char *newstr, size_t newstr_len, const char *var, const char *reg, char sign, bool att) {
|
||||
static void parse_localvar (RParse *p, char *newstr, size_t newstr_len, const char *var, const char *reg, char sign, char *ireg, bool att) {
|
||||
RStrBuf *sb = r_strbuf_new ("");
|
||||
if (att) {
|
||||
if (p->localvar_only) {
|
||||
snprintf (newstr, newstr_len - 1, "%s", var);
|
||||
if (ireg) {
|
||||
r_strbuf_setf (sb, "(%%%s)", ireg);
|
||||
}
|
||||
snprintf (newstr, newstr_len - 1, "%s%s", var, r_strbuf_get (sb));
|
||||
} else {
|
||||
snprintf (newstr, newstr_len - 1, "%s(%%%s)", var, reg);
|
||||
if (ireg) {
|
||||
r_strbuf_setf (sb, ", %%%s", ireg);
|
||||
}
|
||||
snprintf (newstr, newstr_len - 1, "%s(%%%s%s)", var, reg, r_strbuf_get (sb));
|
||||
}
|
||||
} else {
|
||||
if (ireg) {
|
||||
r_strbuf_setf (sb, " + %s", ireg);
|
||||
}
|
||||
if (p->localvar_only) {
|
||||
snprintf (newstr, newstr_len - 1, "[%s]", var);
|
||||
snprintf (newstr, newstr_len - 1, "[%s%s]", var, r_strbuf_get (sb));
|
||||
} else {
|
||||
snprintf (newstr, newstr_len - 1, "[%s %c %s]", reg, sign, var);
|
||||
snprintf (newstr, newstr_len - 1, "[%s%s %c %s]", reg, r_strbuf_get (sb), sign, var);
|
||||
}
|
||||
}
|
||||
r_strbuf_free (sb);
|
||||
}
|
||||
|
||||
static inline void mk_reg_str(const char *regname, int delta, bool sign, bool att, char *dest, int len) {
|
||||
static inline void mk_reg_str(const char *regname, int delta, bool sign, bool att, char *ireg, char *dest, int len) {
|
||||
RStrBuf *sb = r_strbuf_new ("");
|
||||
if (att) {
|
||||
if (ireg) {
|
||||
r_strbuf_setf (sb, ", %%%s", ireg);
|
||||
}
|
||||
if (delta < 10) {
|
||||
snprintf (dest, len - 1, "%s%d(%%%s)", sign ? "" : "-", delta, regname);
|
||||
snprintf (dest, len - 1, "%s%d(%%%s%s)", sign ? "" : "-", delta, regname, r_strbuf_get (sb));
|
||||
} else {
|
||||
snprintf (dest, len - 1, "%s0x%x(%%%s)", sign ? "" : "-", delta, regname);
|
||||
snprintf (dest, len - 1, "%s0x%x(%%%s%s)", sign ? "" : "-", delta, regname, r_strbuf_get (sb));
|
||||
}
|
||||
} else {
|
||||
if (ireg) {
|
||||
r_strbuf_setf (sb, " + %s", ireg);
|
||||
}
|
||||
if (delta < 10) {
|
||||
snprintf (dest, len - 1, "[%s %c %d]", regname, sign ? '+':'-', delta);
|
||||
snprintf (dest, len - 1, "[%s%s %c %d]", regname, r_strbuf_get (sb), sign ? '+':'-', delta);
|
||||
} else {
|
||||
snprintf (dest, len - 1, "[%s %c 0x%x]", regname, sign ? '+':'-', delta);
|
||||
snprintf (dest, len - 1, "[%s%s %c 0x%x]", regname, r_strbuf_get (sb), sign ? '+':'-', delta);
|
||||
}
|
||||
}
|
||||
r_strbuf_free (sb);
|
||||
}
|
||||
|
||||
static bool varsub (RParse *p, RAnalFunction *f, ut64 addr, int oplen, char *data, char *str, int len) {
|
||||
@ -405,14 +424,18 @@ static bool varsub (RParse *p, RAnalFunction *f, ut64 addr, int oplen, char *dat
|
||||
if (ucase && tstr[1]) {
|
||||
ucase = tstr[1] >= 'A' && tstr[1] <= 'Z';
|
||||
}
|
||||
char *ireg = NULL;
|
||||
if (p->get_op_ireg) {
|
||||
ireg = p->get_op_ireg(p->user, addr);
|
||||
}
|
||||
r_list_foreach (spargs, spiter, sparg) {
|
||||
// assuming delta always positive?
|
||||
mk_reg_str (p->anal->reg->name[R_REG_NAME_SP], sparg->delta, true, att, oldstr, sizeof (oldstr));
|
||||
mk_reg_str (p->anal->reg->name[R_REG_NAME_SP], sparg->delta, true, att, ireg, oldstr, sizeof (oldstr));
|
||||
|
||||
if (ucase) {
|
||||
r_str_case (oldstr, true);
|
||||
}
|
||||
parse_localvar (p, newstr, sizeof (newstr), sparg->name, p->anal->reg->name[R_REG_NAME_SP], '+', att);
|
||||
parse_localvar (p, newstr, sizeof (newstr), sparg->name, p->anal->reg->name[R_REG_NAME_SP], '+', ireg, att);
|
||||
if (ucase) {
|
||||
char *plus = strchr (newstr, '+');
|
||||
if (plus) {
|
||||
@ -443,11 +466,11 @@ static bool varsub (RParse *p, RAnalFunction *f, ut64 addr, int oplen, char *dat
|
||||
sign = '-';
|
||||
bparg->delta = -bparg->delta;
|
||||
}
|
||||
mk_reg_str (p->anal->reg->name[R_REG_NAME_BP], bparg->delta, sign=='+', att, oldstr, sizeof (oldstr));
|
||||
mk_reg_str (p->anal->reg->name[R_REG_NAME_BP], bparg->delta, sign=='+', att, ireg, oldstr, sizeof (oldstr));
|
||||
if (ucase) {
|
||||
r_str_case (oldstr, true);
|
||||
}
|
||||
parse_localvar (p, newstr, sizeof (newstr), bparg->name, p->anal->reg->name[R_REG_NAME_BP], sign, att);
|
||||
parse_localvar (p, newstr, sizeof (newstr), bparg->name, p->anal->reg->name[R_REG_NAME_BP], sign, ireg, att);
|
||||
if (ucase) {
|
||||
char *plus = strchr (newstr, sign);
|
||||
if (plus) {
|
||||
@ -498,6 +521,7 @@ static bool varsub (RParse *p, RAnalFunction *f, ut64 addr, int oplen, char *dat
|
||||
ret = false;
|
||||
}
|
||||
free (tstr);
|
||||
free (ireg);
|
||||
r_list_free (spargs);
|
||||
r_list_free (bpargs);
|
||||
return ret;
|
||||
|
Loading…
Reference in New Issue
Block a user