More faithfulness to what instructions should work in what modes, and added the MOVSX...
authorGabe Black <gblack@eecs.umich.edu>
Tue, 19 Jun 2007 22:40:10 +0000 (22:40 +0000)
committerGabe Black <gblack@eecs.umich.edu>
Tue, 19 Jun 2007 22:40:10 +0000 (22:40 +0000)
--HG--
extra : convert_revision : 38b9bf6cd4bdec6355b1158967c7d3562715cacd

src/arch/x86/isa/decoder/one_byte_opcodes.isa
src/arch/x86/isa/insts/data_transfer/move.py
src/arch/x86/isa/microops/regop.isa

index 78270e782e90ed93ae2b24050c390927f848391a..c3f95137a4cc079143b8663e8b215088bf5a5209 100644 (file)
                 default: aas();
             }
         }
-        0x08: decode OPCODE_OP_BOTTOM3 {
-            0x0: inc_eAX();
-            0x1: inc_eCX();
-            0x2: inc_eDX();
-            0x3: inc_eBX();
-            0x4: inc_eSP();
-            0x5: inc_eBP();
-            0x6: inc_eSI();
-            0x7: inc_eDI();
+        0x08: decode MODE_SUBMODE {
+            0x0: M5InternalError::error (
+                {{"Tried to execute an REX prefix!"}});
+            default: decode OPCODE_OP_BOTTOM3 {
+                0x0: inc_eAX();
+                0x1: inc_eCX();
+                0x2: inc_eDX();
+                0x3: inc_eBX();
+                0x4: inc_eSP();
+                0x5: inc_eBP();
+                0x6: inc_eSI();
+                0x7: inc_eDI();
+            }
         }
-        0x09: decode OPCODE_OP_BOTTOM3 {
-            0x0: dec_eAX();
-            0x1: dec_eCX();
-            0x2: dec_eDX();
-            0x3: dec_eBX();
-            0x4: dec_eSP();
-            0x5: dec_eBP();
-            0x6: dec_eSI();
-            0x7: dec_eDI();
+        0x09: decode MODE_SUBMODE {
+            0x0: M5InternalError::error (
+                {{"Tried to execute an REX prefix!"}});
+            default: decode OPCODE_OP_BOTTOM3 {
+                0x0: dec_eAX();
+                0x1: dec_eCX();
+                0x2: dec_eDX();
+                0x3: dec_eBX();
+                0x4: dec_eSP();
+                0x5: dec_eBP();
+                0x6: dec_eSI();
+                0x7: dec_eDI();
+            }
         }
         format Inst {
             0x0A: decode OPCODE_OP_BOTTOM3 {
                 0x0: This_should_be_an_illegal_instruction();
                 default: bound_Gv_Ma();
             }
-            0x3: arpl_Ew_Gw();
+            0x3: decode MODE_SUBMODE {
+                0x0: Inst::MOVSXD(Gv,Ed);
+                default: arpl_Ew_Gw();
+            }
             0x4: M5InternalError::error(
                 {{"Tried to execute the FS segment override prefix!"}});
             0x5: M5InternalError::error(
             0x7: group10_Ev(); //Make sure this is Ev
         }
         0x12: decode OPCODE_OP_BOTTOM3 {
-            0x0: nop_or_pause(); //Check for repe prefix
+            default: nop_or_pause(); //Check for repe prefix
             0x1: xchg_rCX_rAX();
             0x2: xchg_rDX_rAX();
             0x3: xchg_rVX_rAX();
index ff4af0af47f5a6de4b58601c3c72cb8fb9a0a19a..1464e63791b1b02ab80671182945ef61057f4e99 100644 (file)
@@ -74,6 +74,15 @@ def macroop MOV_M_I {
     limm "env.reg", "IMMEDIATE"
     #Do a store to put the register operand into memory
 };
+
+def macroop MOVSXD_R_R {
+    sext "env.reg", "env.regm", "env.dataSize"
+};
+
+def macroop MOVSXD_R_M {
+    #Do a load to fill the register operand from memory
+    sext "env.reg", "env.regm", "env.dataSize"
+};
 '''
 #let {{
 #    class MOV(Inst):
index 6f86892c3b758df849ceb50c698714a58f47c777..7c5b6df014e321c98fb73e399f4abd26ea873c3d 100644 (file)
@@ -356,11 +356,20 @@ let {{
     decoder_output = ""
     exec_output = ""
 
-    def defineMicroRegOp(mnemonic, code):
+    def setUpMicroRegOp(name, Name, base, code, child):
         global header_output
         global decoder_output
         global exec_output
         global microopClasses
+
+        iop = InstObjParams(name, Name, base, {"code" : code})
+        header_output += MicroRegOpDeclare.subst(iop)
+        decoder_output += MicroRegOpConstructor.subst(iop)
+        exec_output += MicroRegOpExecute.subst(iop)
+
+        microopClasses[name] = child
+
+    def defineMicroRegOp(mnemonic, code):
         Name = mnemonic
         name = mnemonic.lower()
 
@@ -371,34 +380,23 @@ let {{
         regCode = matcher.sub("SrcReg2", code)
         immCode = matcher.sub("imm8", code)
 
-        # Build up the all register version of this micro op
-        iop = InstObjParams(name, Name, 'RegOp', {"code" : regCode})
-        header_output += MicroRegOpDeclare.subst(iop)
-        decoder_output += MicroRegOpConstructor.subst(iop)
-        exec_output += MicroRegOpExecute.subst(iop)
-
+        # Build the all register version of this micro op
         class RegOpChild(RegOp):
             def __init__(self, dest, src1, src2):
                 super(RegOpChild, self).__init__(dest, src1, src2)
                 self.className = Name
                 self.mnemonic = name
 
-        microopClasses[name] = RegOpChild
-
-        # Build up the immediate version of this micro op
-        iop = InstObjParams(name + "i", Name,
-                'RegOpImm', {"code" : immCode})
-        header_output += MicroRegOpImmDeclare.subst(iop)
-        decoder_output += MicroRegOpImmConstructor.subst(iop)
-        exec_output += MicroRegOpImmExecute.subst(iop)
+        setUpMicroRegOp(name, Name, "RegOp", regCode, RegOpChild);
 
-        class RegOpImmChild(RegOpImm):
-            def __init__(self, dest, src1, imm):
-                super(RegOpImmChild, self).__init__(dest, src1, imm)
+        # Build the immediate version of this micro op
+        class RegOpChildImm(RegOpImm):
+            def __init__(self, dest, src1, src2):
+                super(RegOpChildImm, self).__init__(dest, src1, src2)
                 self.className = Name + "Imm"
                 self.mnemonic = name + "i"
 
-        microopClasses[name + "i"] = RegOpImmChild
+        setUpMicroRegOp(name + "i", Name + "Imm", "RegOpImm", immCode, RegOpChildImm);
 
     defineMicroRegOp('Add', 'DestReg = merge(DestReg, SrcReg1 + op2, dataSize)') #Needs to set OF,CF,SF
     defineMicroRegOp('Or', 'DestReg = merge(DestReg, SrcReg1 | op2, dataSize)')
@@ -412,10 +410,6 @@ let {{
 
     # This has it's own function because Wr ops have implicit destinations
     def defineMicroRegOpWr(mnemonic, code):
-        global header_output
-        global decoder_output
-        global exec_output
-        global microopClasses
         Name = mnemonic
         name = mnemonic.lower()
 
@@ -426,58 +420,56 @@ let {{
         regCode = matcher.sub("SrcReg2", code)
         immCode = matcher.sub("imm8", code)
 
-        # Build up the all register version of this micro op
-        iop = InstObjParams(name, Name, 'RegOp', {"code" : regCode})
-        header_output += MicroRegOpDeclare.subst(iop)
-        decoder_output += MicroRegOpConstructor.subst(iop)
-        exec_output += MicroRegOpExecute.subst(iop)
-
+        # Build the all register version of this micro op
         class RegOpChild(RegOp):
             def __init__(self, src1, src2):
                 super(RegOpChild, self).__init__("NUM_INTREGS", src1, src2)
                 self.className = Name
                 self.mnemonic = name
 
-        microopClasses[name] = RegOpChild
-
-        # Build up the immediate version of this micro op
-        iop = InstObjParams(name + "i", Name,
-                'RegOpImm', {"code" : immCode})
-        header_output += MicroRegOpImmDeclare.subst(iop)
-        decoder_output += MicroRegOpImmConstructor.subst(iop)
-        exec_output += MicroRegOpImmExecute.subst(iop)
+        setUpMicroRegOp(name, Name, "RegOp", regCode, RegOpChild);
 
-        class RegOpImmChild(RegOpImm):
-            def __init__(self, src1, imm):
-                super(RegOpImmChild, self).__init__("NUM_INTREGS", src1, imm)
+        # Build the immediate version of this micro op
+        class RegOpChildImm(RegOpImm):
+            def __init__(self, src1, src2):
+                super(RegOpChildImm, self).__init__("NUM_INTREGS", src1, src2)
                 self.className = Name + "Imm"
                 self.mnemonic = name + "i"
 
-        microopClasses[name + "i"] = RegOpImmChild
+        setUpMicroRegOp(name + "i", Name + "Imm", "RegOpImm", immCode, RegOpChildImm);
 
     defineMicroRegOpWr('Wrip', 'RIP = SrcReg1 + op2')
 
     # This has it's own function because Rd ops don't always have two parameters
     def defineMicroRegOpRd(mnemonic, code):
-        global header_output
-        global decoder_output
-        global exec_output
-        global microopClasses
         Name = mnemonic
         name = mnemonic.lower()
 
-        iop = InstObjParams(name, Name, 'RegOp', {"code" : code})
-        header_output += MicroRegOpDeclare.subst(iop)
-        decoder_output += MicroRegOpConstructor.subst(iop)
-        exec_output += MicroRegOpExecute.subst(iop)
-
         class RegOpChild(RegOp):
             def __init__(self, dest, src1 = "NUM_INTREGS"):
                 super(RegOpChild, self).__init__(dest, src1, "NUM_INTREGS")
                 self.className = Name
                 self.mnemonic = name
 
-        microopClasses[name] = RegOpChild
+        setUpMicroRegOp(name, Name, "RegOp", code, RegOpChild);
 
     defineMicroRegOpRd('Rdip', 'DestReg = RIP')
+
+    def defineMicroRegOpImm(mnemonic, code):
+        Name = mnemonic
+        name = mnemonic.lower()
+
+        class RegOpChild(RegOpImm):
+            def __init__(self, dest, src1, src2):
+                super(RegOpChild, self).__init__(dest, src1, src2)
+                self.className = Name
+                self.mnemonic = name
+
+        setUpMicroRegOp(name, Name, "RegOpImm", code, RegOpChild);
+
+    defineMicroRegOpImm('Sext', '''
+            IntReg val = SrcReg1;
+            int sign_bit = bits(val, imm8-1, imm8-1);
+            val = sign_bit ? (val | ~mask(imm8)) : val;
+            DestReg = merge(DestReg, val, dataSize);''')
 }};