Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(292)

Unified Diff: syzygy/core/disassembler_util.cc

Issue 2841863003: Improve the decoding of the VEX encoded instructions. (Closed)
Patch Set: Use a constant. Created 3 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « no previous file | syzygy/core/disassembler_util_unittest.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: syzygy/core/disassembler_util.cc
diff --git a/syzygy/core/disassembler_util.cc b/syzygy/core/disassembler_util.cc
index 7be5c8781853644f4d74abb1c39bed05a1411cca..a0cd5d19e35d33ae4cba11325b3057656536889f 100644
--- a/syzygy/core/disassembler_util.cc
+++ b/syzygy/core/disassembler_util.cc
@@ -47,21 +47,47 @@ namespace {
//
// See http://wiki.osdev.org/X86-64_Instruction_Encoding#Three_byte_VEX_escape_prefix
// for more details.
+//
+// NOTE: Most of these instructions can have a variable length because they use
+// ModRM:r/m, we only support the variants that have been observed in Chrome.
size_t Get3ByteVexEncodedInstructionSize(_CodeInfo* ci) {
chrisha 2017/04/26 15:09:10 This is no longer just 3byte VEX instructions? Or
+ const uint8_t kModRMMask = 0xC0;
+
DCHECK_EQ(0xC4, ci->code[0]);
// Switch case based on the opcode map used by this instruction.
switch (ci->code[1] & 0x1F) {
case 0x02: {
switch (ci->code[3]) {
- case 0x13: return 5; // vcvtps2ps
- case 0x18: return 5; // vbroadcastss
- case 0x36: return 5; // vpermd
- case 0x58: return 6; // vpbroadcastd
+ case 0x13: return 5; // vcvtph2ps
+ case 0x18: { // vbroadcastss
+ CHECK((ci->code[4] & kModRMMask) != 0) <<
huangs 2017/04/25 22:14:20 Perhaps this should be CHECK((ci->code[4] & kMod
+ "Unsupported variant of the vbroadcastss instruction";
+ return 5;
+ }
+ case 0x36: { // vpermd
+ CHECK((ci->code[4] & kModRMMask) != 0) <<
+ "Unsupported variant of the vpermd instruction";
+ return 5;
+ }
+ case 0x58: // vpbroadcastb
+ case 0x78: { // vpbroadcastd
+ if ((ci->code[4] & kModRMMask) != kModRMMask) {
+ return 6;
huangs 2017/04/25 22:14:20 Cannot guarantee 6, due to possibility of SIB. For
+ } else {
+ return 5;
+ }
+ }
case 0x5A: return 6; // vbroadcasti128
- case 0x78: return 5; // vpbroadcastb
- case 0x8C: return 5; // vpmaskmovd
- case 0x8E: return 5; // vpmaskmovd
- case 0x90: return 6; // vpgatherdd
+ case 0x8C: { // vpmaskmovd
+ CHECK((ci->code[4] & kModRMMask) == 0) <<
+ "Unsupported variant of the vpmaskmovd instruction";
+ return 5;
+ }
+ case 0x90: { // vpgatherdd
+ CHECK((ci->code[4] & kModRMMask) == 0) <<
+ "Unsupported variant of the vpgatherdd instruction";
+ return 6;
+ }
default:
break;
}
@@ -71,8 +97,16 @@ size_t Get3ByteVexEncodedInstructionSize(_CodeInfo* ci) {
switch (ci->code[3]) {
case 0x00: return 6; // vpermq
case 0x1D: return 6; // vcvtps2ph
- case 0x38: return 7; // vinserti128
- case 0x39: return 6; // vextracti128
+ case 0x38: { // vinserti128
+ CHECK((ci->code[4] & kModRMMask) == 0) <<
+ "Unsupported variant of the vinserti128 instruction";
+ return 7;
+ }
+ case 0x39: { // vextracti128
+ CHECK((ci->code[4] & kModRMMask) != 0) <<
+ "Unsupported variant of the vextracti128 instruction";
+ return 6;
+ }
default: break;
}
break;
@@ -150,10 +184,9 @@ bool HandleBadDecode(_CodeInfo* ci,
return true;
}
- }
-
- if (ci->code[0] == 0xC4)
+ } else if (ci->code[0] == 0xC4) {
size = Get3ByteVexEncodedInstructionSize(ci);
+ }
if (size == 0)
return false;
« no previous file with comments | « no previous file | syzygy/core/disassembler_util_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698