changeset ae411fcf4935 in /z/repo/gem5
details: http://repo.gem5.org/gem5?cmd=changeset;node=ae411fcf4935
description:
        O3 CPU: Strengthen condition for handling interrupts
        The condition for handling interrupts is to check whether or not the 
cpu's
        instruction list is empty. As observed, this can lead to cases in which 
even
        though the instruction list is empty, interrupts are handled when they 
should
        not be. The condition is being strengthened so that interrupts get 
handled only
        when the last committed microop did not had IsDelayedCommit set.

diffstat:

 src/cpu/o3/commit.hh      |   3 +++
 src/cpu/o3/commit_impl.hh |  26 ++++++++++++++++++--------
 src/cpu/o3/fetch_impl.hh  |   1 +
 3 files changed, 22 insertions(+), 8 deletions(-)

diffs (95 lines):

diff -r e7ae13867098 -r ae411fcf4935 src/cpu/o3/commit.hh
--- a/src/cpu/o3/commit.hh      Fri Feb 10 08:37:28 2012 -0600
+++ b/src/cpu/o3/commit.hh      Fri Feb 10 08:37:30 2012 -0600
@@ -441,6 +441,9 @@
     /** Rename map interface. */
     RenameMap *renameMap[Impl::MaxThreads];
 
+    /** True if last committed microop can be followed by an interrupt */
+    bool canHandleInterrupts;
+
     /** Updates commit stats based on this instruction. */
     void updateComInstStats(DynInstPtr &inst);
 
diff -r e7ae13867098 -r ae411fcf4935 src/cpu/o3/commit_impl.hh
--- a/src/cpu/o3/commit_impl.hh Fri Feb 10 08:37:28 2012 -0600
+++ b/src/cpu/o3/commit_impl.hh Fri Feb 10 08:37:30 2012 -0600
@@ -105,7 +105,8 @@
       numThreads(params->numThreads),
       drainPending(false),
       switchedOut(false),
-      trapLatency(params->trapLatency)
+      trapLatency(params->trapLatency),
+      canHandleInterrupts(true)
 {
     _status = Active;
     _nextStatus = Inactive;
@@ -714,7 +715,7 @@
 
     // Wait until all in flight instructions are finished before enterring
     // the interrupt.
-    if (cpu->instList.empty()) {
+    if (canHandleInterrupts && cpu->instList.empty()) {
         // Squash or record that I need to squash this cycle if
         // an interrupt needed to be handled.
         DPRINTF(Commit, "Interrupt detected.\n");
@@ -743,7 +744,10 @@
 
         interrupt = NoFault;
     } else {
-        DPRINTF(Commit, "Interrupt pending, waiting for ROB to empty.\n");
+        DPRINTF(Commit, "Interrupt pending: instruction is %sin "
+                "flight, ROB is %sempty\n",
+                canHandleInterrupts ? "not " : "",
+                cpu->instList.empty() ? "" : "not " );
     }
 }
 
@@ -775,11 +779,6 @@
 DefaultCommit<Impl>::commit()
 {
     if (FullSystem) {
-        // Check for any interrupt that we've already squashed for and
-        // start processing it.
-        if (interrupt != NoFault)
-            handleInterrupt();
-
         // Check if we have a interrupt and get read to handle it
         if (cpu->checkInterrupts(cpu->tcBase(0)))
             propagateInterrupt();
@@ -936,6 +935,11 @@
     // Commit as many instructions as possible until the commit bandwidth
     // limit is reached, or it becomes impossible to commit any more.
     while (num_committed < commitWidth) {
+        // Check for any interrupt that we've already squashed for
+        // and start processing it.
+        if (interrupt != NoFault)
+            handleInterrupt();
+
         int commit_thread = getCommittingThread();
 
         if (commit_thread == -1 || !rob->isHeadReady(commit_thread))
@@ -992,6 +996,12 @@
                     cpu->instDone(tid);
                 }
 
+                if (tid == 0) {
+                    canHandleInterrupts =  (!head_inst->isDelayedCommit()) &&
+                                           ((THE_ISA != ALPHA_ISA) ||
+                                             (!(pc[0].instAddr() & 0x3)));
+                }
+
                 // Updates misc. registers.
                 head_inst->updateMiscRegs();
 
diff -r e7ae13867098 -r ae411fcf4935 src/cpu/o3/fetch_impl.hh
--- a/src/cpu/o3/fetch_impl.hh  Fri Feb 10 08:37:28 2012 -0600
+++ b/src/cpu/o3/fetch_impl.hh  Fri Feb 10 08:37:30 2012 -0600
@@ -1144,6 +1144,7 @@
             // an delayed commit micro-op currently (delayed commit 
instructions
             // are not interruptable by interrupts, only faults)
             ++fetchMiscStallCycles;
+            DPRINTF(Fetch, "[tid:%i]: Fetch is stalled!\n", tid);
             return;
         }
     } else {
_______________________________________________
gem5-dev mailing list
[email protected]
http://m5sim.org/mailman/listinfo/gem5-dev

Reply via email to