diff options
author | Vladimir Kostyukov <vladimir.kostyukov@intel.com> | 2014-07-01 18:28:43 +0700 |
---|---|---|
committer | Vladimir Kostyukov <vladimir.kostyukov@intel.com> | 2014-07-09 10:59:33 +0000 |
commit | 79bb184ec0a661bf1276eef555dd5e20828bc528 (patch) | |
tree | ccac7bc93ddca873940467ce8be7472a8b8915f5 /disassembler | |
parent | 62f28f943e2da2873c7a09096c292f01a21c6478 (diff) | |
download | art-79bb184ec0a661bf1276eef555dd5e20828bc528.zip art-79bb184ec0a661bf1276eef555dd5e20828bc528.tar.gz art-79bb184ec0a661bf1276eef555dd5e20828bc528.tar.bz2 |
ART: Correct disassembling of regs from opcodes
Registers, which are part of opcode might have 1-byte size
or 2-byte size depending on the instruction and 66h prefix.
This patch makes the decoding of such instruction correct.
Examples:
- '664155' should be decoded as 'push r13w'
(66h + REX.B)
- '41B320' should be decoded as 'mov r11l, 0x20'
(byte-operand + REX.B)
Change-Id: I83913e3a5f2ef03c4019c0f5eea6b11fc51ee4cc
Signed-off-by: Vladimir Kostyukov <vladimir.kostyukov@intel.com>
Diffstat (limited to 'disassembler')
-rw-r--r-- | disassembler/disassembler_x86.cc | 8 |
1 files changed, 5 insertions, 3 deletions
diff --git a/disassembler/disassembler_x86.cc b/disassembler/disassembler_x86.cc index a6f9a8a..101a55d 100644 --- a/disassembler/disassembler_x86.cc +++ b/disassembler/disassembler_x86.cc @@ -125,10 +125,11 @@ static void DumpIndexReg(std::ostream& os, uint8_t rex, uint8_t reg) { DumpAddrReg(os, rex, reg_num); } -static void DumpOpcodeReg(std::ostream& os, uint8_t rex, uint8_t reg) { +static void DumpOpcodeReg(std::ostream& os, uint8_t rex, uint8_t reg, + bool byte_operand, uint8_t size_override) { bool rex_b = (rex & REX_B) != 0; size_t reg_num = rex_b ? (reg + 8) : reg; - DumpReg0(os, rex, reg_num, false, 0); + DumpReg0(os, rex, reg_num, byte_operand, size_override); } enum SegmentPrefix { @@ -955,6 +956,7 @@ DISASSEMBLER_ENTRY(cmp, immediate_bytes = 1; byte_operand = true; reg_in_opcode = true; + byte_operand = true; break; case 0xB8: case 0xB9: case 0xBA: case 0xBB: case 0xBC: case 0xBD: case 0xBE: case 0xBF: if (rex == 0x48) { @@ -1079,7 +1081,7 @@ DISASSEMBLER_ENTRY(cmp, uint8_t rex_w = (supports_rex_ && target_specific) ? (rex | 0x48) : rex; if (reg_in_opcode) { DCHECK(!has_modrm); - DumpOpcodeReg(args, rex_w, *instr & 0x7); + DumpOpcodeReg(args, rex_w, *instr & 0x7, byte_operand, prefix[2]); } instr++; uint32_t address_bits = 0; |