From f057c712f91b215034fe84fa0f22694aaa8dffb3 Mon Sep 17 00:00:00 2001 From: iximeow Date: Fri, 15 Jan 2021 14:52:11 -0800 Subject: fix several missing or invalid decodings among 0f01 opcodes * `mwaitx`, `monitorx`, `rdpru`, and `clzero` are now supported * swapgs is no longer decoded in protected mode * rdpkru and wrpkru are no longer decoded if mod bits != 11 --- test/long_mode/mod.rs | 42 +++++++++++++++++++++++++++++++++++++++++- test/protected_mode/mod.rs | 39 +++++++++++++++++++++++++++++++++++++-- 2 files changed, 78 insertions(+), 3 deletions(-) (limited to 'test') diff --git a/test/long_mode/mod.rs b/test/long_mode/mod.rs index 8489822..0830c2d 100644 --- a/test/long_mode/mod.rs +++ b/test/long_mode/mod.rs @@ -831,6 +831,9 @@ fn test_ssse3() { fn test_0f01() { // drawn heavily from "Table A-6. Opcode Extensions for One- and Two-byte Opcodes by Group // Number" + for x in &[0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f] { + test_invalid(&[0x0f, 0x01, *x]); + } test_display(&[0x0f, 0x01, 0x38], "invlpg [rax]"); test_display(&[0x0f, 0x01, 0x3f], "invlpg [rdi]"); test_display(&[0x0f, 0x01, 0x40, 0xff], "sgdt [rax - 0x1]"); @@ -839,18 +842,24 @@ fn test_0f01() { test_display(&[0x0f, 0x01, 0x51, 0xff], "lgdt [rcx - 0x1]"); test_display(&[0x0f, 0x01, 0x59, 0xff], "lidt [rcx - 0x1]"); test_display(&[0x0f, 0x01, 0x61, 0xff], "smsw [rcx - 0x1]"); + test_invalid(&[0x0f, 0x01, 0x69, 0xff]); + test_display(&[0x0f, 0x01, 0x71, 0xff], "lmsw [rcx - 0x1]"); + test_display(&[0x0f, 0x01, 0x79, 0xff], "invlpg [rcx - 0x1]"); test_display(&[0x0f, 0x01, 0xc0], "enclv"); test_display(&[0x0f, 0x01, 0xc1], "vmcall"); test_display(&[0x0f, 0x01, 0xc2], "vmlaunch"); test_display(&[0x0f, 0x01, 0xc3], "vmresume"); test_display(&[0x0f, 0x01, 0xc4], "vmxoff"); - test_invalid(&[0x0f, 0x01, 0xc5]); + test_invalid(&[0x0f, 0x01, 0xc5]); // TODO: TME would make this `pconfig` test_invalid(&[0x0f, 0x01, 0xc6]); test_invalid(&[0x0f, 0x01, 0xc7]); test_display(&[0x0f, 0x01, 0xc8], "monitor"); test_display(&[0x0f, 0x01, 0xc9], "mwait"); test_display(&[0x0f, 0x01, 0xca], "clac"); test_display(&[0x0f, 0x01, 0xcb], "stac"); + test_invalid(&[0x0f, 0x01, 0xcc]); + test_invalid(&[0x0f, 0x01, 0xcd]); + test_invalid(&[0x0f, 0x01, 0xce]); test_display(&[0x0f, 0x01, 0xcf], "encls"); test_display(&[0x0f, 0x01, 0xd0], "xgetbv"); test_display(&[0x0f, 0x01, 0xd1], "xsetbv"); @@ -868,10 +877,41 @@ fn test_0f01() { test_display(&[0x0f, 0x01, 0xdd], "clgi"); test_display(&[0x0f, 0x01, 0xde], "skinit eax"); test_display(&[0x0f, 0x01, 0xdf], "invlpga rax, ecx"); + test_display(&[0x4f, 0x0f, 0x01, 0xe0], "smsw r8w"); + test_display(&[0x0f, 0x01, 0xe0], "smsw ax"); + test_display(&[0x0f, 0x01, 0xe1], "smsw cx"); + test_display(&[0x0f, 0x01, 0xe2], "smsw dx"); + test_display(&[0x0f, 0x01, 0xe3], "smsw bx"); + test_display(&[0x0f, 0x01, 0xe4], "smsw sp"); + test_display(&[0x0f, 0x01, 0xe5], "smsw bp"); + test_display(&[0x0f, 0x01, 0xe6], "smsw si"); + test_display(&[0x0f, 0x01, 0xe7], "smsw di"); + test_invalid(&[0x0f, 0x01, 0xe8]); + test_invalid(&[0x0f, 0x01, 0xe8]); + test_invalid(&[0x0f, 0x01, 0xe9]); + test_invalid(&[0x0f, 0x01, 0xea]); + test_invalid(&[0x0f, 0x01, 0xeb]); + test_invalid(&[0x0f, 0x01, 0xec]); + test_invalid(&[0x0f, 0x01, 0xed]); test_display(&[0x0f, 0x01, 0xee], "rdpkru"); test_display(&[0x0f, 0x01, 0xef], "wrpkru"); + test_display(&[0x4f, 0x0f, 0x01, 0xf0], "lmsw r8w"); + test_display(&[0x0f, 0x01, 0xf0], "lmsw ax"); + test_display(&[0x0f, 0x01, 0xf1], "lmsw cx"); + test_display(&[0x0f, 0x01, 0xf2], "lmsw dx"); + test_display(&[0x0f, 0x01, 0xf3], "lmsw bx"); + test_display(&[0x0f, 0x01, 0xf4], "lmsw sp"); + test_display(&[0x0f, 0x01, 0xf5], "lmsw bp"); + test_display(&[0x0f, 0x01, 0xf6], "lmsw si"); + test_display(&[0x0f, 0x01, 0xf7], "lmsw di"); test_display(&[0x0f, 0x01, 0xf8], "swapgs"); test_display(&[0x0f, 0x01, 0xf9], "rdtscp"); + test_display(&[0x0f, 0x01, 0xfa], "monitorx"); + test_display(&[0x0f, 0x01, 0xfb], "mwaitx"); + test_display(&[0x0f, 0x01, 0xfc], "clzero"); + test_display(&[0x0f, 0x01, 0xfd], "rdpru ecx"); + test_invalid(&[0x0f, 0x01, 0xfe]); + test_invalid(&[0x0f, 0x01, 0xff]); } #[test] diff --git a/test/protected_mode/mod.rs b/test/protected_mode/mod.rs index dd0a51f..e3c7975 100644 --- a/test/protected_mode/mod.rs +++ b/test/protected_mode/mod.rs @@ -766,18 +766,24 @@ fn test_0f01() { test_display(&[0x0f, 0x01, 0x51, 0xff], "lgdt [ecx - 0x1]"); test_display(&[0x0f, 0x01, 0x59, 0xff], "lidt [ecx - 0x1]"); test_display(&[0x0f, 0x01, 0x61, 0xff], "smsw [ecx - 0x1]"); + test_invalid(&[0x0f, 0x01, 0x69, 0xff]); + test_display(&[0x0f, 0x01, 0x71, 0xff], "lmsw [ecx - 0x1]"); + test_display(&[0x0f, 0x01, 0x79, 0xff], "invlpg [ecx - 0x1]"); test_display(&[0x0f, 0x01, 0xc0], "enclv"); test_display(&[0x0f, 0x01, 0xc1], "vmcall"); test_display(&[0x0f, 0x01, 0xc2], "vmlaunch"); test_display(&[0x0f, 0x01, 0xc3], "vmresume"); test_display(&[0x0f, 0x01, 0xc4], "vmxoff"); - test_invalid(&[0x0f, 0x01, 0xc5]); + test_invalid(&[0x0f, 0x01, 0xc5]); // TODO: TME would make this `pconfig` test_invalid(&[0x0f, 0x01, 0xc6]); test_invalid(&[0x0f, 0x01, 0xc7]); test_display(&[0x0f, 0x01, 0xc8], "monitor"); test_display(&[0x0f, 0x01, 0xc9], "mwait"); test_display(&[0x0f, 0x01, 0xca], "clac"); test_display(&[0x0f, 0x01, 0xcb], "stac"); + test_invalid(&[0x0f, 0x01, 0xcc]); + test_invalid(&[0x0f, 0x01, 0xcd]); + test_invalid(&[0x0f, 0x01, 0xce]); test_display(&[0x0f, 0x01, 0xcf], "encls"); test_display(&[0x0f, 0x01, 0xd0], "xgetbv"); test_display(&[0x0f, 0x01, 0xd1], "xsetbv"); @@ -795,10 +801,39 @@ fn test_0f01() { test_display(&[0x0f, 0x01, 0xdd], "clgi"); test_display(&[0x0f, 0x01, 0xde], "skinit eax"); test_display(&[0x0f, 0x01, 0xdf], "invlpga eax, ecx"); + test_display(&[0x0f, 0x01, 0xe0], "smsw ax"); + test_display(&[0x0f, 0x01, 0xe1], "smsw cx"); + test_display(&[0x0f, 0x01, 0xe2], "smsw dx"); + test_display(&[0x0f, 0x01, 0xe3], "smsw bx"); + test_display(&[0x0f, 0x01, 0xe4], "smsw sp"); + test_display(&[0x0f, 0x01, 0xe5], "smsw bp"); + test_display(&[0x0f, 0x01, 0xe6], "smsw si"); + test_display(&[0x0f, 0x01, 0xe7], "smsw di"); + test_invalid(&[0x0f, 0x01, 0xe8]); + test_invalid(&[0x0f, 0x01, 0xe8]); + test_invalid(&[0x0f, 0x01, 0xe9]); + test_invalid(&[0x0f, 0x01, 0xea]); + test_invalid(&[0x0f, 0x01, 0xeb]); + test_invalid(&[0x0f, 0x01, 0xec]); + test_invalid(&[0x0f, 0x01, 0xed]); test_display(&[0x0f, 0x01, 0xee], "rdpkru"); test_display(&[0x0f, 0x01, 0xef], "wrpkru"); - test_display(&[0x0f, 0x01, 0xf8], "swapgs"); + test_display(&[0x0f, 0x01, 0xf0], "lmsw ax"); + test_display(&[0x0f, 0x01, 0xf1], "lmsw cx"); + test_display(&[0x0f, 0x01, 0xf2], "lmsw dx"); + test_display(&[0x0f, 0x01, 0xf3], "lmsw bx"); + test_display(&[0x0f, 0x01, 0xf4], "lmsw sp"); + test_display(&[0x0f, 0x01, 0xf5], "lmsw bp"); + test_display(&[0x0f, 0x01, 0xf6], "lmsw si"); + test_display(&[0x0f, 0x01, 0xf7], "lmsw di"); + test_invalid(&[0x0f, 0x01, 0xf8]); test_display(&[0x0f, 0x01, 0xf9], "rdtscp"); + test_display(&[0x0f, 0x01, 0xfa], "monitorx"); + test_display(&[0x0f, 0x01, 0xfb], "mwaitx"); + test_display(&[0x0f, 0x01, 0xfc], "clzero"); + test_display(&[0x0f, 0x01, 0xfd], "rdpru ecx"); + test_invalid(&[0x0f, 0x01, 0xfe]); + test_invalid(&[0x0f, 0x01, 0xff]); } #[test] -- cgit v1.1