aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authoriximeow <me@iximeow.net>2020-08-03 01:15:42 -0700
committeriximeow <me@iximeow.net>2020-08-09 01:38:57 -0700
commit967230df2e6e57996d92996ae350dbabc0946f87 (patch)
tree000039a577a7396dec5faea2a20ac35945579fc6
parent200447fed7f7fffa6c13360375b99b8d675b81ac (diff)
handle bad lea
-rw-r--r--src/long_mode/mod.rs8
-rw-r--r--test/long_mode/mod.rs1
2 files changed, 8 insertions, 1 deletions
diff --git a/src/long_mode/mod.rs b/src/long_mode/mod.rs
index 4ef7a04..17c0521 100644
--- a/src/long_mode/mod.rs
+++ b/src/long_mode/mod.rs
@@ -3756,7 +3756,7 @@ pub enum OperandCode {
Ev_Gv = OperandCodeBuilder::new().op0_is_rrr_and_embedded_instructions().read_E().only_modrm_operands().mem_reg().bits(),
Gb_Eb = OperandCodeBuilder::new().op0_is_rrr_and_embedded_instructions().read_E().byte_operands().only_modrm_operands().reg_mem().bits(),
Gv_Ev = OperandCodeBuilder::new().op0_is_rrr_and_embedded_instructions().read_E().only_modrm_operands().reg_mem().bits(),
- Gv_M = OperandCodeBuilder::new().op0_is_rrr_and_embedded_instructions().read_E().only_modrm_operands().reg_mem().operand_case(2).bits(),
+ Gv_M = OperandCodeBuilder::new().op0_is_rrr_and_embedded_instructions().read_E().reg_mem().operand_case(25).bits(),
Gb_Eb_Ib = OperandCodeBuilder::new().op0_is_rrr_and_embedded_instructions().read_E().byte_operands().reg_mem().operand_case(1).bits(),
Gv_Ev_Iv = OperandCodeBuilder::new().op0_is_rrr_and_embedded_instructions().read_E().reg_mem().operand_case(1).bits(),
Rv_Gmm_Ib = OperandCodeBuilder::new().op0_is_rrr_and_embedded_instructions().read_modrm().read_E().reg_mem().operand_case(25).bits(),
@@ -5785,6 +5785,12 @@ fn read_operands<T: Iterator<Item=u8>>(decoder: &InstDecoder, mut bytes_iter: T,
} else {
let operand_code: OperandCode = unsafe { core::mem::transmute(operand_code.bits()) };
match operand_code {
+ OperandCode::Gv_M => {
+ if mem_oper == OperandSpec::RegMMM {
+ return Err(DecodeError::InvalidOperand);
+ }
+ instruction.operands[1] = mem_oper;
+ }
OperandCode::Eb_R0 => {
// turns out xed cand capstone both permit nonzero rrr bits here.
// if (modrm & 0b00111000) != 0 {
diff --git a/test/long_mode/mod.rs b/test/long_mode/mod.rs
index 291efd4..4b77eb0 100644
--- a/test/long_mode/mod.rs
+++ b/test/long_mode/mod.rs
@@ -1246,6 +1246,7 @@ fn test_misc() {
test_display(&[0x48, 0x8d, 0xa4, 0xc7, 0x20, 0x00, 0x00, 0x12], "lea rsp, [rdi + rax * 8 + 0x12000020]");
test_display(&[0x33, 0xc0], "xor eax, eax");
test_display(&[0x48, 0x8d, 0x53, 0x08], "lea rdx, [rbx + 0x8]");
+ test_invalid(&[0x8d, 0xdd]);
test_display(&[0x31, 0xc9], "xor ecx, ecx");
test_display(&[0x48, 0x29, 0xc8], "sub rax, rcx");
test_display(&[0x48, 0x03, 0x0b], "add rcx, [rbx]");