diff options
Diffstat (limited to 'src/long_mode')
| -rw-r--r-- | src/long_mode/display.rs | 8 | ||||
| -rw-r--r-- | src/long_mode/mod.rs | 36 | 
2 files changed, 44 insertions, 0 deletions
| diff --git a/src/long_mode/display.rs b/src/long_mode/display.rs index e653399..c3f4413 100644 --- a/src/long_mode/display.rs +++ b/src/long_mode/display.rs @@ -513,6 +513,8 @@ const MNEMONICS: &[&'static str] = &[      "vmxoff",      "monitor",      "mwait", +    "monitorx", +    "mwaitx",      "clac",      "stac",      "encls", @@ -527,6 +529,8 @@ const MNEMONICS: &[&'static str] = &[      "enclu",      "rdpkru",      "wrpkru", +    "rdpru", +    "clzero",      "rdseed",      "rdrand",      "addps", @@ -2152,6 +2156,8 @@ impl <T: fmt::Write, Color: fmt::Display, Y: YaxColors<Color>> Colorize<T, Color              Opcode::VMXOFF |              Opcode::MONITOR |              Opcode::MWAIT | +            Opcode::MONITORX | +            Opcode::MWAITX |              Opcode::SKINIT |              Opcode::CLGI |              Opcode::STGI | @@ -2169,6 +2175,8 @@ impl <T: fmt::Write, Color: fmt::Display, Y: YaxColors<Color>> Colorize<T, Color              Opcode::ENCLU |              Opcode::RDPKRU |              Opcode::WRPKRU | +            Opcode::RDPRU | +            Opcode::CLZERO |              Opcode::LAR => { write!(out, "{}", colors.platform_op(self)) }              Opcode::CRC32 | diff --git a/src/long_mode/mod.rs b/src/long_mode/mod.rs index d165e38..f15e2a1 100644 --- a/src/long_mode/mod.rs +++ b/src/long_mode/mod.rs @@ -1131,6 +1131,8 @@ pub enum Opcode {      VMXOFF,      MONITOR,      MWAIT, +    MONITORX, +    MWAITX,      CLAC,      STAC,      ENCLS, @@ -1146,6 +1148,9 @@ pub enum Opcode {      RDPKRU,      WRPKRU, +    RDPRU, +    CLZERO, +      RDSEED,      RDRAND, @@ -3278,6 +3283,12 @@ impl InstDecoder {                      return Err(DecodeError::InvalidOpcode);                  }              } +            Opcode::MONITORX | Opcode::MWAITX | // these are gated on the `monitorx` and `mwaitx` cpuid bits, but are AMD-only. +            Opcode::CLZERO | Opcode::RDPRU => { // again, gated on specific cpuid bits, but AMD-only. +                if !self.amd_quirks() { +                    return Err(DecodeError::InvalidOpcode); +                } +            }              other => {                  if !self.bmi1() {                      if BMI1.contains(&other) { @@ -8049,6 +8060,14 @@ fn unlikely_operands<T: Iterator<Item=u8>>(decoder: &InstDecoder, mut bytes_iter                  instruction.operand_count = 1;                  instruction.operands[0] = read_E(&mut bytes_iter, instruction, modrm, 2, length)?;              } else if r == 5 { +                let mod_bits = modrm >> 6; +                if mod_bits != 0b11 { +                    instruction.opcode = Opcode::Invalid; +                    instruction.operands[0] = OperandSpec::Nothing; +                    instruction.operand_count = 0; +                    return Err(DecodeError::InvalidOpcode); +                } +                  let m = modrm & 7;                  match m {                      0b110 => { @@ -8084,6 +8103,23 @@ fn unlikely_operands<T: Iterator<Item=u8>>(decoder: &InstDecoder, mut bytes_iter                          instruction.opcode = Opcode::RDTSCP;                          instruction.operands[0] = OperandSpec::Nothing;                          instruction.operand_count = 0; +                    } else if m == 2 { +                        instruction.opcode = Opcode::MONITORX; +                        instruction.operands[0] = OperandSpec::Nothing; +                        instruction.operand_count = 0; +                    } else if m == 3 { +                        instruction.opcode = Opcode::MWAITX; +                        instruction.operands[0] = OperandSpec::Nothing; +                        instruction.operand_count = 0; +                    } else if m == 4 { +                        instruction.opcode = Opcode::CLZERO; +                        instruction.operands[0] = OperandSpec::Nothing; +                        instruction.operand_count = 0; +                    } else if m == 5 { +                        instruction.opcode = Opcode::RDPRU; +                        instruction.operands[0] = OperandSpec::RegRRR; +                        instruction.modrm_rrr = RegSpec::ecx(); +                        instruction.operand_count = 1;                      } else {                          instruction.opcode = Opcode::Invalid;                          return Err(DecodeError::InvalidOpcode); | 
