Debugger: disassemble register shifts

This commit is contained in:
Jeffrey Pfau 2014-11-15 16:32:38 -08:00
parent cade03e10d
commit 264f6f1df2
2 changed files with 69 additions and 1 deletions

View File

@ -22,7 +22,7 @@
#define ADDR_MODE_1_LSL \
ADDR_MODE_1_SHIFT(LSL) \
if (!info->op3.shifterImm) { \
info->operandFormat &= ~ARM_OPERAND_SHIFT_REGISTER_3; \
info->operandFormat &= ~ARM_OPERAND_SHIFT_IMMEDIATE_3; \
info->op3.shifterOp = ARM_SHIFT_NONE; \
}

View File

@ -15,6 +15,7 @@ static int _decodeRegister(int reg, char* buffer, int blen);
static int _decodeRegisterList(int list, char* buffer, int blen);
static int _decodePCRelative(uint32_t address, uint32_t pc, char* buffer, int blen);
static int _decodeMemory(struct ARMMemoryAccess memory, int pc, char* buffer, int blen);
static int _decodeShift(union ARMOperand operand, bool reg, char* buffer, int blen);
static const char* _armConditions[] = {
"eq",
@ -165,6 +166,45 @@ static int _decodeMemory(struct ARMMemoryAccess memory, int pc, char* buffer, in
return total;
}
static int _decodeShift(union ARMOperand op, bool reg, char* buffer, int blen) {
if (blen <= 1) {
return 0;
}
int total = 0;
strncpy(buffer, ", ", blen - 1);
ADVANCE(2);
int written;
switch (op.shifterOp) {
case ARM_SHIFT_LSL:
strncpy(buffer, "lsl ", blen - 1);
ADVANCE(4);
break;
case ARM_SHIFT_LSR:
strncpy(buffer, "lsr ", blen - 1);
ADVANCE(4);
break;
case ARM_SHIFT_ASR:
strncpy(buffer, "asr ", blen - 1);
ADVANCE(4);
break;
case ARM_SHIFT_ROR:
strncpy(buffer, "ror ", blen - 1);
ADVANCE(4);
break;
case ARM_SHIFT_RRX:
strncpy(buffer, "rrx", blen - 1);
ADVANCE(3);
return total;
}
if (!reg) {
written = snprintf(buffer, blen - 1, "#%i", op.shifterImm);
} else {
written = _decodeRegister(op.shifterReg, buffer, blen);
}
ADVANCE(written);
return total;
}
static const char* _armMnemonicStrings[] = {
"ill",
"adc",
@ -317,6 +357,13 @@ int ARMDisassemble(struct ARMInstructionInfo* info, uint32_t pc, char* buffer, i
written = _decodeRegister(info->op1.reg, buffer, blen);
ADVANCE(written);
}
if (info->operandFormat & ARM_OPERAND_SHIFT_REGISTER_1) {
written = _decodeShift(info->op1, true, buffer, blen);
ADVANCE(written);
} else if (info->operandFormat & ARM_OPERAND_SHIFT_IMMEDIATE_1) {
written = _decodeShift(info->op1, false, buffer, blen);
ADVANCE(written);
}
if (info->operandFormat & ARM_OPERAND_2) {
strncpy(buffer, ", ", blen);
ADVANCE(2);
@ -331,6 +378,13 @@ int ARMDisassemble(struct ARMInstructionInfo* info, uint32_t pc, char* buffer, i
written = _decodeRegister(info->op2.reg, buffer, blen);
ADVANCE(written);
}
if (info->operandFormat & ARM_OPERAND_SHIFT_REGISTER_2) {
written = _decodeShift(info->op2, true, buffer, blen);
ADVANCE(written);
} else if (info->operandFormat & ARM_OPERAND_SHIFT_IMMEDIATE_2) {
written = _decodeShift(info->op2, false, buffer, blen);
ADVANCE(written);
}
if (info->operandFormat & ARM_OPERAND_3) {
strncpy(buffer, ", ", blen - 1);
ADVANCE(2);
@ -345,6 +399,13 @@ int ARMDisassemble(struct ARMInstructionInfo* info, uint32_t pc, char* buffer, i
written = _decodeRegister(info->op3.reg, buffer, blen);
ADVANCE(written);
}
if (info->operandFormat & ARM_OPERAND_SHIFT_REGISTER_3) {
written = _decodeShift(info->op3, true, buffer, blen);
ADVANCE(written);
} else if (info->operandFormat & ARM_OPERAND_SHIFT_IMMEDIATE_3) {
written = _decodeShift(info->op3, false, buffer, blen);
ADVANCE(written);
}
if (info->operandFormat & ARM_OPERAND_4) {
strncpy(buffer, ", ", blen - 1);
ADVANCE(2);
@ -359,6 +420,13 @@ int ARMDisassemble(struct ARMInstructionInfo* info, uint32_t pc, char* buffer, i
written = _decodeRegister(info->op4.reg, buffer, blen);
ADVANCE(written);
}
if (info->operandFormat & ARM_OPERAND_SHIFT_REGISTER_4) {
written = _decodeShift(info->op4, true, buffer, blen);
ADVANCE(written);
} else if (info->operandFormat & ARM_OPERAND_SHIFT_IMMEDIATE_4) {
written = _decodeShift(info->op4, false, buffer, blen);
ADVANCE(written);
}
break;
}
buffer[blen - 1] = '\0';