changeset 76dd3a85e4ae in /z/repo/gem5
details: http://repo.gem5.org/gem5?cmd=changeset;node=76dd3a85e4ae
description:
        inorder: treat SE mode syscalls as a trapping instruction
        define a syscallContext to schedule the syscall and then use syscall() 
to actually perform the action

diffstat:

 src/cpu/inorder/cpu.cc                      |  21 ++++++++++++---------
 src/cpu/inorder/cpu.hh                      |  14 ++++++++++----
 src/cpu/inorder/inorder_dyn_inst.cc         |   3 ++-
 src/cpu/inorder/inorder_dyn_inst.hh         |   5 +++++
 src/cpu/inorder/resources/execution_unit.cc |  14 +++++++++++---
 5 files changed, 40 insertions(+), 17 deletions(-)

diffs (188 lines):

diff -r 8d523e8d4165 -r 76dd3a85e4ae src/cpu/inorder/cpu.cc
--- a/src/cpu/inorder/cpu.cc    Sun Jun 19 21:43:38 2011 -0400
+++ b/src/cpu/inorder/cpu.cc    Sun Jun 19 21:43:38 2011 -0400
@@ -105,7 +105,7 @@
     "HaltThread",
     "SuspendThread",
     "Trap",
-    "InstGraduated",
+    "Syscall",
     "SquashFromMemStall",
     "UpdatePCs"
 };
@@ -151,6 +151,11 @@
         cpu->resPool->trap(fault, tid, inst);
         break;
 
+      case Syscall:
+        cpu->syscall(inst->syscallNum, tid);
+        cpu->resPool->trap(fault, tid, inst);
+        break;
+
       default:
         fatal("Unrecognized Event Type %s", eventNames[cpuEventType]);    
     }
@@ -1068,9 +1073,6 @@
 {
     DPRINTF(InOrderCPU,"Activating next ready thread\n");
 
-    // NOTE: Add 5 to the event priority so that we always activate
-    // threads after we've finished deactivating, squashing,etc.
-    // other threads
     scheduleCpuEvent(ActivateNextReadyThread, NoFault, 0/*tid*/, dummyInst[0], 
                      delay, ActivateNextReadyThread_Pri);
 
@@ -1382,11 +1384,6 @@
     // Check for instruction-count-based events.
     comInstEventQueue[tid]->serviceEvents(thread[tid]->numInst);
 
-    // Broadcast to other resources an instruction
-    // has been completed
-    resPool->scheduleEvent((CPUEventType)ResourcePool::InstGraduated, inst, 
-                           0, 0, tid);
-
     // Finally, remove instruction from CPU
     removeInst(inst);
 }
@@ -1601,6 +1598,12 @@
 
 #if !FULL_SYSTEM
 void
+InOrderCPU::syscallContext(Fault fault, ThreadID tid, DynInstPtr inst, int 
delay)
+{
+    scheduleCpuEvent(Syscall, fault, tid, inst, delay, Syscall_Pri);
+}
+
+void
 InOrderCPU::syscall(int64_t callnum, ThreadID tid)
 {
     DPRINTF(InOrderCPU, "[tid:%i] Executing syscall().\n\n", tid);
diff -r 8d523e8d4165 -r 76dd3a85e4ae src/cpu/inorder/cpu.hh
--- a/src/cpu/inorder/cpu.hh    Sun Jun 19 21:43:38 2011 -0400
+++ b/src/cpu/inorder/cpu.hh    Sun Jun 19 21:43:38 2011 -0400
@@ -182,7 +182,7 @@
         HaltThread,
         SuspendThread,
         Trap,
-        InstGraduated,
+        Syscall,
         SquashFromMemStall,
         UpdatePCs,
         NumCPUEvents
@@ -192,6 +192,7 @@
 
     enum CPUEventPri {
         InOrderCPU_Pri                 = Event::CPU_Tick_Pri,
+        Syscall_Pri                    = Event::CPU_Tick_Pri + 9,
         ActivateNextReadyThread_Pri    = Event::CPU_Tick_Pri + 10
     };
 
@@ -207,6 +208,7 @@
         DynInstPtr inst;
         Fault fault;
         unsigned vpe;
+        short syscall_num;
         
       public:
         /** Constructs a CPU event. */
@@ -436,6 +438,13 @@
 
     /** Check if this address is a valid data address. */
     bool validDataAddr(Addr addr) { return true; }
+#else
+    /** Schedule a syscall on the CPU */
+    void syscallContext(Fault fault, ThreadID tid, DynInstPtr inst,
+                        int delay = 0);
+
+    /** Executes a syscall.*/
+    void syscall(int64_t callnum, ThreadID tid);
 #endif
 
     /** Schedule a trap on the CPU */
@@ -650,9 +659,6 @@
     Fault write(DynInstPtr inst, uint8_t *data, unsigned size,
                 Addr addr, unsigned flags, uint64_t *write_res = NULL);
 
-    /** Executes a syscall.*/
-    void syscall(int64_t callnum, ThreadID tid);
-
   public:
     /** Per-Thread List of all the instructions in flight. */
     std::list<DynInstPtr> instList[ThePipeline::MaxThreads];
diff -r 8d523e8d4165 -r 76dd3a85e4ae src/cpu/inorder/inorder_dyn_inst.cc
--- a/src/cpu/inorder/inorder_dyn_inst.cc       Sun Jun 19 21:43:38 2011 -0400
+++ b/src/cpu/inorder/inorder_dyn_inst.cc       Sun Jun 19 21:43:38 2011 -0400
@@ -296,7 +296,8 @@
 void
 InOrderDynInst::syscall(int64_t callnum)
 {
-    cpu->syscall(callnum, this->threadNumber);
+    syscallNum = callnum;
+    cpu->syscallContext(NoFault, this->threadNumber, this);
 }
 #endif
 
diff -r 8d523e8d4165 -r 76dd3a85e4ae src/cpu/inorder/inorder_dyn_inst.hh
--- a/src/cpu/inorder/inorder_dyn_inst.hh       Sun Jun 19 21:43:38 2011 -0400
+++ b/src/cpu/inorder/inorder_dyn_inst.hh       Sun Jun 19 21:43:38 2011 -0400
@@ -385,6 +385,9 @@
     bool isQuiesce() const { return staticInst->isQuiesce(); }
     bool isIprAccess() const { return staticInst->isIprAccess(); }
     bool isUnverifiable() const { return staticInst->isUnverifiable(); }
+    bool isSyscall() const
+    { return staticInst->isSyscall(); }
+
 
     /////////////////////////////////////////////
     //
@@ -509,6 +512,8 @@
     void trap(Fault fault);
     bool simPalCheck(int palFunc);
 #else
+    short syscallNum;
+
     /** Calls a syscall. */
     void syscall(int64_t callnum);
 #endif
diff -r 8d523e8d4165 -r 76dd3a85e4ae src/cpu/inorder/resources/execution_unit.cc
--- a/src/cpu/inorder/resources/execution_unit.cc       Sun Jun 19 21:43:38 
2011 -0400
+++ b/src/cpu/inorder/resources/execution_unit.cc       Sun Jun 19 21:43:38 
2011 -0400
@@ -89,6 +89,8 @@
     DynInstPtr inst = reqs[slot_num]->inst;
     Fault fault = NoFault;
     Tick cur_tick = curTick();
+    unsigned stage_num = exec_req->getStageNum();
+    ThreadID tid = inst->readTid();
 #if TRACING_ON
     InstSeqNum seq_num = inst->seqNum;
 #endif
@@ -149,13 +151,10 @@
                         assert(inst->isControl());
 
                         // Set up Squash Generated By this Misprediction
-                        unsigned stage_num = exec_req->getStageNum();
-                        ThreadID tid = inst->readTid();
                         TheISA::PCState pc = inst->pcState();
                         TheISA::advancePC(pc, inst->staticInst);
                         inst->setPredTarg(pc);
                         inst->setSquashInfo(stage_num);
-
                         setupSquash(inst, stage_num, tid);
 
                         DPRINTF(InOrderExecute, "[tid:%i]: [sn:%i] Squashing 
from "
@@ -210,6 +209,15 @@
                             seq_num,
                             (inst->resultType(0) == InOrderDynInst::Float) ?
                             inst->readFloatResult(0) : inst->readIntResult(0));
+
+#if !FULL_SYSTEM
+                    // The Syscall might change the PC, so conservatively
+                    // squash everything behing it
+                    if (inst->isSyscall()) {
+                        inst->setSquashInfo(stage_num);
+                        setupSquash(inst, stage_num, tid);
+                    }
+#endif
                 } else {
                     DPRINTF(InOrderExecute, "[tid:%i]: [sn:%i]: had a %s "
                             "fault.\n", inst->readTid(), seq_num, 
fault->name());
_______________________________________________
gem5-dev mailing list
[email protected]
http://m5sim.org/mailman/listinfo/gem5-dev

Reply via email to