mirror of
https://github.com/radareorg/radare2.git
synced 2025-03-01 18:57:20 +00:00
fix disassembling 'backwards'
(e.g. pd -5) producing wrong output fixes #5105
This commit is contained in:
parent
20bd6003ae
commit
7c3fb53a5e
@ -1017,11 +1017,19 @@ static int pdi(RCore *core, int nb_opcodes, int nb_bytes, int fmt) {
|
|||||||
}
|
}
|
||||||
} else if (!nb_bytes) {
|
} else if (!nb_bytes) {
|
||||||
if (nb_opcodes < 0) {
|
if (nb_opcodes < 0) {
|
||||||
|
ut64 start;
|
||||||
/* Backward disassembly of `ilen` opcodes
|
/* Backward disassembly of `ilen` opcodes
|
||||||
* - We compute the new starting offset
|
* - We compute the new starting offset
|
||||||
* - Read at the new offset */
|
* - Read at the new offset */
|
||||||
nb_opcodes = -nb_opcodes;
|
nb_opcodes = -nb_opcodes;
|
||||||
r_core_asm_bwdis_len (core, &nb_bytes, &core->offset, nb_opcodes);
|
if (r_core_prevop_addr (core, core->offset, nb_opcodes, &start)) {
|
||||||
|
// We have some anal_info.
|
||||||
|
nb_bytes = core->offset - start;
|
||||||
|
} else {
|
||||||
|
// anal ignorance.
|
||||||
|
r_core_asm_bwdis_len (core, &nb_bytes, &core->offset,
|
||||||
|
nb_opcodes);
|
||||||
|
}
|
||||||
r_core_read_at (core, core->offset, core->block, nb_bytes);
|
r_core_read_at (core, core->offset, core->block, nb_bytes);
|
||||||
} else {
|
} else {
|
||||||
// workaround for the `for` loop below
|
// workaround for the `for` loop below
|
||||||
@ -2755,6 +2763,7 @@ static int cmd_print(void *data, const char *input) {
|
|||||||
if (!processed_cmd) {
|
if (!processed_cmd) {
|
||||||
ut64 addr = core->offset;
|
ut64 addr = core->offset;
|
||||||
ut8 *block = NULL;
|
ut8 *block = NULL;
|
||||||
|
ut64 start;
|
||||||
|
|
||||||
if (bw_disassemble) {
|
if (bw_disassemble) {
|
||||||
block = malloc (core->blocksize);
|
block = malloc (core->blocksize);
|
||||||
@ -2769,7 +2778,13 @@ static int cmd_print(void *data, const char *input) {
|
|||||||
} else { //pd
|
} else { //pd
|
||||||
const int bs = core->blocksize;
|
const int bs = core->blocksize;
|
||||||
int instr_len;
|
int instr_len;
|
||||||
r_core_asm_bwdis_len (core, &instr_len, &addr, l);
|
if (r_core_prevop_addr (core, core->offset, l, &start)) {
|
||||||
|
// We have some anal_info.
|
||||||
|
instr_len = core->offset - start;
|
||||||
|
} else {
|
||||||
|
// anal ignorance.
|
||||||
|
r_core_asm_bwdis_len (core, &instr_len, &addr, l);
|
||||||
|
}
|
||||||
ut64 prevaddr = core->offset;
|
ut64 prevaddr = core->offset;
|
||||||
r_core_seek(core, prevaddr - instr_len, true);
|
r_core_seek(core, prevaddr - instr_len, true);
|
||||||
block = realloc (block, R_MAX(instr_len, bs));
|
block = realloc (block, R_MAX(instr_len, bs));
|
||||||
|
@ -631,6 +631,30 @@ static ut64 prevop_addr (RCore *core, ut64 addr) {
|
|||||||
return target - 4;
|
return target - 4;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Returns true if we can use analysis to find the previous operation address,
|
||||||
|
// sets prev_addr to the value of the instruction numinstrs back.
|
||||||
|
// If we can't use the anal, then set prev_addr to UT64_MAX and return false;
|
||||||
|
R_API bool r_core_prevop_addr (RCore* core, ut64 start_addr, int numinstrs,
|
||||||
|
ut64* prev_addr) {
|
||||||
|
RAnalBlock* bb;
|
||||||
|
int i;
|
||||||
|
// Check that we're in a bb, otherwise this prevop stuff won't work.
|
||||||
|
bb = r_anal_bb_from_offset (core->anal, start_addr);
|
||||||
|
if (bb) {
|
||||||
|
if (r_anal_bb_opaddr_at (bb, start_addr) != UT64_MAX) {
|
||||||
|
// Do some anal looping.
|
||||||
|
for (i = 0; i < numinstrs; ++i) {
|
||||||
|
*prev_addr = prevop_addr (core, start_addr);
|
||||||
|
start_addr = *prev_addr;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// Dang! not in a bb, return false and fallback to other methods.
|
||||||
|
*prev_addr = UT64_MAX;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
static void reset_print_cur(RPrint *p) {
|
static void reset_print_cur(RPrint *p) {
|
||||||
p->cur = 0;
|
p->cur = 0;
|
||||||
p->ocur = -1;
|
p->ocur = -1;
|
||||||
|
@ -227,6 +227,7 @@ R_API int r_core_read_at(RCore *core, ut64 addr, ut8 *buf, int size);
|
|||||||
R_API int r_core_is_valid_offset (RCore *core, ut64 offset);
|
R_API int r_core_is_valid_offset (RCore *core, ut64 offset);
|
||||||
R_API int r_core_shift_block(RCore *core, ut64 addr, ut64 b_size, st64 dist);
|
R_API int r_core_shift_block(RCore *core, ut64 addr, ut64 b_size, st64 dist);
|
||||||
R_API void r_core_visual_prompt_input (RCore *core);
|
R_API void r_core_visual_prompt_input (RCore *core);
|
||||||
|
R_API bool r_core_prevop_addr (RCore* core, ut64 start_addr, int numinstrs, ut64* prev_addr);
|
||||||
R_API bool r_core_visual_hudstuff(RCore *core);
|
R_API bool r_core_visual_hudstuff(RCore *core);
|
||||||
R_API int r_core_visual_classes(RCore *core);
|
R_API int r_core_visual_classes(RCore *core);
|
||||||
R_API int r_core_visual_types(RCore *core);
|
R_API int r_core_visual_types(RCore *core);
|
||||||
|
Loading…
x
Reference in New Issue
Block a user