Enable register windows.
[gem5.git] / arch / mips / isa_traits.hh
index 4850010d48da8687744112666f1af858d2586cfb..35c207828d3df16911dc9ab52779e049eddf2b86 100644 (file)
@@ -40,9 +40,9 @@
 class FastCPU;
 class FullCPU;
 class Checkpoint;
+class ExecContext;
 
 namespace LittleEndianGuest {};
-using namespace LittleEndianGuest;
 
 #define TARGET_MIPS
 
@@ -91,51 +91,65 @@ class SyscallReturn {
 
 namespace MipsISA
 {
+    using namespace LittleEndianGuest;
+
     typedef uint32_t MachInst;
     typedef uint32_t MachInst;
     typedef uint64_t ExtMachInst;
     typedef uint8_t  RegIndex;
 //  typedef uint64_t Addr;
-    enum {
-        MemoryEnd = 0xffffffffffffffffULL,
-
-        NumIntRegs = 32,
-        NumFloatRegs = 32,
-        NumMiscRegs = 258, //account for hi,lo regs
-
-        MaxRegsOfAnyType = 32,
-        // Static instruction parameters
-        MaxInstSrcRegs = 3,
-        MaxInstDestRegs = 2,
-
-        // semantically meaningful register indices
-        ZeroReg = 0,   // architecturally meaningful
-        // the rest of these depend on the ABI
-        StackPointerReg = 30,
-        GlobalPointerReg = 29,
-        ProcedureValueReg = 27,
-        ReturnAddressReg = 26,
-        ReturnValueReg = 0,
-        FramePointerReg = 15,
-        ArgumentReg0 = 16,
-        ArgumentReg1 = 17,
-        ArgumentReg2 = 18,
-        ArgumentReg3 = 19,
-        ArgumentReg4 = 20,
-        ArgumentReg5 = 21,
-        SyscallNumReg = ReturnValueReg,
-        SyscallPseudoReturnReg = ArgumentReg4,
-        SyscallSuccessReg = 19,
-        LogVMPageSize = 13,    // 8K bytes
-        VMPageSize = (1 << LogVMPageSize),
-
-        BranchPredAddrShiftAmt = 2, // instructions are 4-byte aligned
-
-        WordBytes = 4,
-        HalfwordBytes = 2,
-        ByteBytes = 1,
-        DepNA = 0,
-    };
+
+       // Constants Related to the number of registers
+
+    const int NumIntArchRegs = 32;
+    const int NumPALShadowRegs = 8;
+    const int NumFloatArchRegs = 32;
+    // @todo: Figure out what this number really should be.
+    const int NumMiscArchRegs = 32;
+
+    const int NumIntRegs = NumIntArchRegs + NumPALShadowRegs;
+    const int NumFloatRegs = NumFloatArchRegs;
+    const int NumMiscRegs = NumMiscArchRegs;
+
+    const int TotalNumRegs = NumIntRegs + NumFloatRegs +
+    NumMiscRegs + 0/*NumInternalProcRegs*/;
+
+    const int TotalDataRegs = NumIntRegs + NumFloatRegs;
+
+    // Static instruction parameters
+    const int MaxInstSrcRegs = 3;
+    const int MaxInstDestRegs = 2;
+
+    // semantically meaningful register indices
+    const int ZeroReg = 0;
+    const int AssemblerReg = 1;
+    const int ReturnValueReg1 = 2;
+    const int ReturnValueReg2 = 3;
+    const int ArgumentReg0 = 4;
+    const int ArgumentReg1 = 5;
+    const int ArgumentReg2 = 6;
+    const int ArgumentReg3 = 7;
+    const int KernelReg0 = 26;
+    const int KernelReg1 = 27;
+    const int GlobalPointerReg = 28;
+    const int StackPointerReg = 29;
+    const int FramePointerReg = 30;
+    const int ReturnAddressReg = 31;
+
+    const int SyscallNumReg = ReturnValueReg1;
+    const int SyscallPseudoReturnReg = ReturnValueReg1;
+    const int SyscallSuccessReg = ReturnValueReg1;
+
+    const int LogVMPageSize = 13;      // 8K bytes
+    const int VMPageSize = (1 << LogVMPageSize);
+
+    const int BranchPredAddrShiftAmt = 2; // instructions are 4-byte aligned
+
+    const int MachineBytes = 4;
+    const int WordBytes = 4;
+    const int HalfwordBytes = 2;
+    const int ByteBytes = 1;
+
 
     // These enumerate all the registers for dependence tracking.
     enum DependenceTags {
@@ -150,18 +164,102 @@ namespace MipsISA
     };
 
     typedef uint64_t IntReg;
-    typedef IntReg IntRegFile[NumIntRegs];
 
-    // floating point register file entry type
+    class IntRegFile
+    {
+      protected:
+        IntReg regs[NumIntRegs];
+
+      public:
+        IntReg readReg(int intReg)
+        {
+            return regs[intReg];
+        }
+
+        Fault setReg(int intReg, const IntReg &val)
+        {
+            regs[intReg] = val;
+            return NoFault;
+        }
+
+        void serialize(std::ostream &os);
+
+        void unserialize(Checkpoint *cp, const std::string &section);
+
+    };
+
+/* floating point register file entry type
     typedef union {
         uint64_t q;
         double d;
-    } FloatReg;
+    } FloatReg;*/
 
-    typedef union {
+    typedef double FloatReg;
+    typedef uint64_t FloatRegBits;
+
+/*typedef union {
         uint64_t q[NumFloatRegs];      // integer qword view
         double d[NumFloatRegs];                // double-precision floating point view
-    } FloatRegFile;
+    } FloatRegFile;*/
+
+   class FloatRegFile
+    {
+      protected:
+
+        FloatRegBits q[NumFloatRegs];  // integer qword view
+        double d[NumFloatRegs];        // double-precision floating point view
+
+      public:
+
+        FloatReg readReg(int floatReg)
+        {
+            return d[floatReg];
+        }
+
+        FloatReg readReg(int floatReg, int width)
+        {
+            return readReg(floatReg);
+        }
+
+        FloatRegBits readRegBits(int floatReg)
+        {
+            return q[floatReg];
+        }
+
+        FloatRegBits readRegBits(int floatReg, int width)
+        {
+            return readRegBits(floatReg);
+        }
+
+        Fault setReg(int floatReg, const FloatReg &val)
+        {
+            d[floatReg] = val;
+            return NoFault;
+        }
+
+        Fault setReg(int floatReg, const FloatReg &val, int width)
+        {
+            return setReg(floatReg, val);
+        }
+
+        Fault setRegBits(int floatReg, const FloatRegBits &val)
+        {
+            q[floatReg] = val;
+            return NoFault;
+        }
+
+        Fault setRegBits(int floatReg, const FloatRegBits &val, int width)
+        {
+            return setRegBits(floatReg, val);
+        }
+
+        void serialize(std::ostream &os);
+
+        void unserialize(Checkpoint *cp, const std::string &section);
+
+    };
+
+        void copyRegs(ExecContext *src, ExecContext *dest);
 
     // cop-0/cop-1 system control register file
     typedef uint64_t MiscReg;
@@ -402,32 +500,136 @@ extern const Addr PageOffset;
     };
 #endif
 
-    enum {
-        TotalNumRegs =
-        NumIntRegs + NumFloatRegs + NumMiscRegs + NumInternalProcRegs
-    };
-
-    enum {
-        TotalDataRegs = NumIntRegs + NumFloatRegs
-    };
-
     typedef union {
         IntReg  intreg;
         FloatReg   fpreg;
         MiscReg ctrlreg;
     } AnyReg;
 
-    struct RegFile {
+    class RegFile {
+      protected:
         IntRegFile intRegFile;         // (signed) integer register file
         FloatRegFile floatRegFile;     // floating point register file
-        MiscRegFile miscRegs;          // control register file
+        MiscRegFile miscRegFile;       // control register file
+
+      public:
 
+        void clear()
+        {
+            bzero(&intRegFile, sizeof(intRegFile));
+            bzero(&floatRegFile, sizeof(floatRegFile));
+            bzero(&miscRegFile, sizeof(miscRegFile));
+        }
+
+        MiscReg readMiscReg(int miscReg)
+        {
+            return miscRegFile.readReg(miscReg);
+        }
+
+        MiscReg readMiscRegWithEffect(int miscReg,
+                Fault &fault, ExecContext *xc)
+        {
+            fault = NoFault;
+            return miscRegFile.readRegWithEffect(miscReg, fault, xc);
+        }
+
+        Fault setMiscReg(int miscReg, const MiscReg &val)
+        {
+            return miscRegFile.setReg(miscReg, val);
+        }
+
+        Fault setMiscRegWithEffect(int miscReg, const MiscReg &val,
+                ExecContext * xc)
+        {
+            return miscRegFile.setRegWithEffect(miscReg, val, xc);
+        }
+
+        FloatReg readFloatReg(int floatReg)
+        {
+            return floatRegFile.readReg(floatReg);
+        }
+
+        FloatReg readFloatReg(int floatReg, int width)
+        {
+            return readFloatReg(floatReg);
+        }
+
+        FloatRegBits readFloatRegBits(int floatReg)
+        {
+            return floatRegFile.readRegBits(floatReg);
+        }
+
+        FloatRegBits readFloatRegBits(int floatReg, int width)
+        {
+            return readFloatRegBits(floatReg);
+        }
+
+        Fault setFloatReg(int floatReg, const FloatReg &val)
+        {
+            return floatRegFile.setReg(floatReg, val);
+        }
+
+        Fault setFloatReg(int floatReg, const FloatReg &val, int width)
+        {
+            return setFloatReg(floatReg, val);
+        }
+
+        Fault setFloatRegBits(int floatReg, const FloatRegBits &val)
+        {
+            return floatRegFile.setRegBits(floatReg, val);
+        }
+
+        Fault setFloatRegBits(int floatReg, const FloatRegBits &val, int width)
+        {
+            return setFloatRegBits(floatReg, val);
+        }
+
+        IntReg readIntReg(int intReg)
+        {
+            return intRegFile.readReg(intReg);
+        }
+
+        Fault setIntReg(int intReg, const IntReg &val)
+        {
+            return intRegFile.setReg(intReg, val);
+        }
+      protected:
 
         Addr pc;                       // program counter
         Addr npc;                      // next-cycle program counter
         Addr nnpc;                     // next-next-cycle program counter
                                         // used to implement branch delay slot
                                         // not real register
+      public:
+        Addr readPC()
+        {
+            return pc;
+        }
+
+        void setPC(Addr val)
+        {
+            pc = val;
+        }
+
+        Addr readNextPC()
+        {
+            return npc;
+        }
+
+        void setNextPC(Addr val)
+        {
+            npc = val;
+        }
+
+        Addr readNextNPC()
+        {
+            return nnpc;
+        }
+
+        void setNextNPC(Addr val)
+        {
+            nnpc = val;
+        }
 
         MiscReg hi;                     // MIPS HI Register
         MiscReg lo;                     // MIPS LO Register
@@ -448,6 +650,13 @@ extern const Addr PageOffset;
 
         void createCP0Regs();
         void coldReset();
+
+        typedef int ContextParam;
+        typedef int ContextVal;
+
+        void changeContext(ContextParam param, ContextVal val)
+        {
+        }
     };
 
     StaticInstPtr decodeInst(ExtMachInst);
@@ -523,18 +732,21 @@ extern const Addr PageOffset;
 
     static inline void setSyscallReturn(SyscallReturn return_value, RegFile *regs)
     {
-        // check for error condition.  SPARC syscall convention is to
-        // indicate success/failure in reg the carry bit of the ccr
-        // and put the return value itself in the standard return value reg ().
+        // check for error condition.  Alpha syscall convention is to
+        // indicate success/failure in reg a3 (r19) and put the
+        // return value itself in the standard return value reg (v0).
         if (return_value.successful()) {
             // no error
-            //regs->miscRegFile.ccrFields.iccFields.c = 0;
-            regs->intRegFile[ReturnValueReg] = return_value.value();
+            regs->setIntReg(ReturnValueReg1, 0);
+            regs->setIntReg(ReturnValueReg2, return_value.value());
         } else {
             // got an error, return details
-            //regs->miscRegFile.ccrFields.iccFields.c = 1;
-            regs->intRegFile[ReturnValueReg] = -return_value.value();
+            regs->setIntReg(ReturnValueReg1, (IntReg) -1);
+            regs->setIntReg(ReturnValueReg2, -return_value.value());
         }
+
+        //regs->intRegFile[ReturnValueReg1] = (IntReg)return_value;
+        //panic("Returning from syscall\n");
     }
 
     // Machine operations