summaryrefslogtreecommitdiff
path: root/src/arch/x86/types.hh
diff options
context:
space:
mode:
Diffstat (limited to 'src/arch/x86/types.hh')
-rw-r--r--src/arch/x86/types.hh62
1 files changed, 36 insertions, 26 deletions
diff --git a/src/arch/x86/types.hh b/src/arch/x86/types.hh
index a604c3efc..dd60c0aec 100644
--- a/src/arch/x86/types.hh
+++ b/src/arch/x86/types.hh
@@ -104,6 +104,33 @@ namespace X86ISA
Bitfield<0> b;
EndBitUnion(Rex)
+ enum OpcodeType {
+ BadOpcode,
+ OneByteOpcode,
+ TwoByteOpcode,
+ ThreeByte0F38Opcode,
+ ThreeByte0F3AOpcode
+ };
+
+ static inline const char *
+ opcodeTypeToStr(OpcodeType type)
+ {
+ switch (type) {
+ case BadOpcode:
+ return "bad";
+ case OneByteOpcode:
+ return "one byte";
+ case TwoByteOpcode:
+ return "two byte";
+ case ThreeByte0F38Opcode:
+ return "three byte 0f38";
+ case ThreeByte0F3AOpcode:
+ return "three byte 0f3a";
+ default:
+ return "unrecognized!";
+ }
+ }
+
BitUnion8(Opcode)
Bitfield<7,3> top5;
Bitfield<2,0> bottom3;
@@ -136,16 +163,7 @@ namespace X86ISA
//This holds all of the bytes of the opcode
struct
{
- //The number of bytes in this opcode. Right now, we ignore that
- //this can be 3 in some cases
- uint8_t num;
- //The first byte detected in a 2+ byte opcode. Should be 0xF0.
- uint8_t prefixA;
- //The second byte detected in a 3+ byte opcode. Could be 0x38-0x3F
- //for some SSE instructions. 3dNow! instructions are handled as
- //two byte opcodes and then split out further by the immediate
- //byte.
- uint8_t prefixB;
+ OpcodeType type;
//The main opcode byte. The highest addressed byte in the opcode.
Opcode op;
} opcode;
@@ -173,14 +191,12 @@ namespace X86ISA
operator << (std::ostream & os, const ExtMachInst & emi)
{
ccprintf(os, "\n{\n\tleg = %#x,\n\trex = %#x,\n\t"
- "op = {\n\t\tnum = %d,\n\t\top = %#x,\n\t\t"
- "prefixA = %#x,\n\t\tprefixB = %#x\n\t},\n\t"
+ "op = {\n\t\ttype = %s,\n\t\top = %#x,\n\t\t},\n\t"
"modRM = %#x,\n\tsib = %#x,\n\t"
"immediate = %#x,\n\tdisplacement = %#x\n\t"
"dispSize = %d}\n",
(uint8_t)emi.legacy, (uint8_t)emi.rex,
- emi.opcode.num, (uint8_t)emi.opcode.op,
- emi.opcode.prefixA, emi.opcode.prefixB,
+ opcodeTypeToStr(emi.opcode.type), (uint8_t)emi.opcode.op,
(uint8_t)emi.modRM, (uint8_t)emi.sib,
emi.immediate, emi.displacement, emi.dispSize);
return os;
@@ -193,14 +209,10 @@ namespace X86ISA
return false;
if(emi1.rex != emi2.rex)
return false;
- if(emi1.opcode.num != emi2.opcode.num)
+ if(emi1.opcode.type != emi2.opcode.type)
return false;
if(emi1.opcode.op != emi2.opcode.op)
return false;
- if(emi1.opcode.prefixA != emi2.opcode.prefixA)
- return false;
- if(emi1.opcode.prefixB != emi2.opcode.prefixB)
- return false;
if(emi1.modRM != emi2.modRM)
return false;
if(emi1.sib != emi2.sib)
@@ -284,13 +296,11 @@ __hash_namespace_begin
template<>
struct hash<X86ISA::ExtMachInst> {
size_t operator()(const X86ISA::ExtMachInst &emi) const {
- return (((uint64_t)emi.legacy << 56) |
- ((uint64_t)emi.rex << 48) |
- ((uint64_t)emi.modRM << 40) |
- ((uint64_t)emi.sib << 32) |
- ((uint64_t)emi.opcode.num << 24) |
- ((uint64_t)emi.opcode.prefixA << 16) |
- ((uint64_t)emi.opcode.prefixB << 8) |
+ return (((uint64_t)emi.legacy << 40) |
+ ((uint64_t)emi.rex << 32) |
+ ((uint64_t)emi.modRM << 24) |
+ ((uint64_t)emi.sib << 16) |
+ ((uint64_t)emi.opcode.type << 8) |
((uint64_t)emi.opcode.op)) ^
emi.immediate ^ emi.displacement ^
emi.mode ^