Hoa Nguyen has submitted this change. ( https://gem5-review.googlesource.com/c/public/gem5/+/36095 )

Change subject: cpu-o3,stats: Update stats style for iew and iew_impl
......................................................................

cpu-o3,stats: Update stats style for iew and iew_impl

Change-Id: Ie213aeb402fee5f015f10c9c03e5b9c02ba1f3fe
Signed-off-by: Hoa Nguyen <hoangu...@ucdavis.edu>
Reviewed-on: https://gem5-review.googlesource.com/c/public/gem5/+/36095
Reviewed-by: Daniel Carvalho <oda...@yahoo.com.br>
Maintainer: Bobby R. Bruce <bbr...@ucdavis.edu>
Tested-by: kokoro <noreply+kok...@google.com>
---
M src/cpu/o3/iew.hh
M src/cpu/o3/iew_impl.hh
2 files changed, 197 insertions(+), 234 deletions(-)

Approvals:
  Daniel Carvalho: Looks good to me, approved
  Bobby R. Bruce: Looks good to me, approved
  kokoro: Regressions pass



diff --git a/src/cpu/o3/iew.hh b/src/cpu/o3/iew.hh
index 07f986d..683902a 100644
--- a/src/cpu/o3/iew.hh
+++ b/src/cpu/o3/iew.hh
@@ -426,70 +426,81 @@
     /** Maximum size of the skid buffer. */
     unsigned skidBufferMax;

-    /** Stat for total number of idle cycles. */
-    Stats::Scalar iewIdleCycles;
-    /** Stat for total number of squashing cycles. */
-    Stats::Scalar iewSquashCycles;
-    /** Stat for total number of blocking cycles. */
-    Stats::Scalar iewBlockCycles;
-    /** Stat for total number of unblocking cycles. */
-    Stats::Scalar iewUnblockCycles;
-    /** Stat for total number of instructions dispatched. */
-    Stats::Scalar iewDispatchedInsts;
-    /** Stat for total number of squashed instructions dispatch skips. */
-    Stats::Scalar iewDispSquashedInsts;
-    /** Stat for total number of dispatched load instructions. */
-    Stats::Scalar iewDispLoadInsts;
-    /** Stat for total number of dispatched store instructions. */
-    Stats::Scalar iewDispStoreInsts;
- /** Stat for total number of dispatched non speculative instructions. */
-    Stats::Scalar iewDispNonSpecInsts;
-    /** Stat for number of times the IQ becomes full. */
-    Stats::Scalar iewIQFullEvents;
-    /** Stat for number of times the LSQ becomes full. */
-    Stats::Scalar iewLSQFullEvents;
-    /** Stat for total number of memory ordering violation events. */
-    Stats::Scalar memOrderViolationEvents;
-    /** Stat for total number of incorrect predicted taken branches. */
-    Stats::Scalar predictedTakenIncorrect;
-    /** Stat for total number of incorrect predicted not taken branches. */
-    Stats::Scalar predictedNotTakenIncorrect;
- /** Stat for total number of mispredicted branches detected at execute. */
-    Stats::Formula branchMispredicts;

-    /** Stat for total number of executed instructions. */
-    Stats::Scalar iewExecutedInsts;
-    /** Stat for total number of executed load instructions. */
-    Stats::Vector iewExecLoadInsts;
-    /** Stat for total number of executed store instructions. */
-//    Stats::Scalar iewExecStoreInsts;
- /** Stat for total number of squashed instructions skipped at execute. */
-    Stats::Scalar iewExecSquashedInsts;
-    /** Number of executed software prefetches. */
-    Stats::Vector iewExecutedSwp;
-    /** Number of executed nops. */
-    Stats::Vector iewExecutedNop;
-    /** Number of executed meomory references. */
-    Stats::Vector iewExecutedRefs;
-    /** Number of executed branches. */
-    Stats::Vector iewExecutedBranches;
-    /** Number of executed store instructions. */
-    Stats::Formula iewExecStoreInsts;
-    /** Number of instructions executed per cycle. */
-    Stats::Formula iewExecRate;
+    struct IEWStats : public Stats::Group
+    {
+        IEWStats(O3CPU *cpu);

-    /** Number of instructions sent to commit. */
-    Stats::Vector iewInstsToCommit;
-    /** Number of instructions that writeback. */
-    Stats::Vector writebackCount;
-    /** Number of instructions that wake consumers. */
-    Stats::Vector producerInst;
-    /** Number of instructions that wake up from producers. */
-    Stats::Vector consumerInst;
-    /** Number of instructions per cycle written back. */
-    Stats::Formula wbRate;
-    /** Average number of woken instructions per writeback. */
-    Stats::Formula wbFanout;
+        /** Stat for total number of idle cycles. */
+        Stats::Scalar idleCycles;
+        /** Stat for total number of squashing cycles. */
+        Stats::Scalar squashCycles;
+        /** Stat for total number of blocking cycles. */
+        Stats::Scalar blockCycles;
+        /** Stat for total number of unblocking cycles. */
+        Stats::Scalar unblockCycles;
+        /** Stat for total number of instructions dispatched. */
+        Stats::Scalar dispatchedInsts;
+ /** Stat for total number of squashed instructions dispatch skips. */
+        Stats::Scalar dispSquashedInsts;
+        /** Stat for total number of dispatched load instructions. */
+        Stats::Scalar dispLoadInsts;
+        /** Stat for total number of dispatched store instructions. */
+        Stats::Scalar dispStoreInsts;
+ /** Stat for total number of dispatched non speculative instructions. */
+        Stats::Scalar dispNonSpecInsts;
+        /** Stat for number of times the IQ becomes full. */
+        Stats::Scalar iqFullEvents;
+        /** Stat for number of times the LSQ becomes full. */
+        Stats::Scalar lsqFullEvents;
+        /** Stat for total number of memory ordering violation events. */
+        Stats::Scalar memOrderViolationEvents;
+        /** Stat for total number of incorrect predicted taken branches. */
+        Stats::Scalar predictedTakenIncorrect;
+ /** Stat for total number of incorrect predicted not taken branches. */
+        Stats::Scalar predictedNotTakenIncorrect;
+        /** Stat for total number of mispredicted branches detected at
+         *  execute. */
+        Stats::Formula branchMispredicts;
+
+        struct ExecutedInstStats : public Stats::Group
+        {
+            ExecutedInstStats(O3CPU* cpu);
+
+            /** Stat for total number of executed instructions. */
+            Stats::Scalar numInsts;
+            /** Stat for total number of executed load instructions. */
+            Stats::Vector numLoadInsts;
+            /** Stat for total number of squashed instructions skipped at
+             *  execute. */
+            Stats::Scalar numSquashedInsts;
+            /** Number of executed software prefetches. */
+            Stats::Vector numSwp;
+            /** Number of executed nops. */
+            Stats::Vector numNop;
+            /** Number of executed meomory references. */
+            Stats::Vector numRefs;
+            /** Number of executed branches. */
+            Stats::Vector numBranches;
+            /** Number of executed store instructions. */
+            Stats::Formula numStoreInsts;
+            /** Number of instructions executed per cycle. */
+            Stats::Formula numRate;
+        } executedInstStats;
+
+        /** Number of instructions sent to commit. */
+        Stats::Vector instsToCommit;
+        /** Number of instructions that writeback. */
+        Stats::Vector writebackCount;
+        /** Number of instructions that wake consumers. */
+        Stats::Vector producerInst;
+        /** Number of instructions that wake up from producers. */
+        Stats::Vector consumerInst;
+        /** Number of instructions per cycle written back. */
+        Stats::Formula wbRate;
+        /** Average number of woken instructions per writeback. */
+        Stats::Formula wbFanout;
+    } iewStats;
 };

 #endif // __CPU_O3_IEW_HH__
diff --git a/src/cpu/o3/iew_impl.hh b/src/cpu/o3/iew_impl.hh
index 0eec644..fc89a89 100644
--- a/src/cpu/o3/iew_impl.hh
+++ b/src/cpu/o3/iew_impl.hh
@@ -77,7 +77,8 @@
       wbNumInst(0),
       wbCycle(0),
       wbWidth(params.wbWidth),
-      numThreads(params.numThreads)
+      numThreads(params.numThreads),
+      iewStats(cpu)
 {
     if (dispatchWidth > Impl::MaxWidth)
         fatal("dispatchWidth (%d) is larger than compiled limit (%d),\n"
@@ -140,162 +141,113 @@
 }

 template <class Impl>
-void
-DefaultIEW<Impl>::regStats()
+DefaultIEW<Impl>::
+IEWStats::IEWStats(O3CPU *cpu)
+    : Stats::Group(cpu),
+    ADD_STAT(idleCycles, "Number of cycles IEW is idle"),
+    ADD_STAT(squashCycles, "Number of cycles IEW is squashing"),
+    ADD_STAT(blockCycles, "Number of cycles IEW is blocking"),
+    ADD_STAT(unblockCycles, "Number of cycles IEW is unblocking"),
+    ADD_STAT(dispatchedInsts, "Number of instructions dispatched to IQ"),
+    ADD_STAT(dispSquashedInsts,
+             "Number of squashed instructions skipped by dispatch"),
+    ADD_STAT(dispLoadInsts, "Number of dispatched load instructions"),
+    ADD_STAT(dispStoreInsts, "Number of dispatched store instructions"),
+    ADD_STAT(dispNonSpecInsts,
+             "Number of dispatched non-speculative instructions"),
+    ADD_STAT(iqFullEvents,
+             "Number of times the IQ has become full, causing a stall"),
+    ADD_STAT(lsqFullEvents,
+             "Number of times the LSQ has become full, causing a stall"),
+    ADD_STAT(memOrderViolationEvents, "Number of memory order violations"),
+    ADD_STAT(predictedTakenIncorrect,
+             "Number of branches that were predicted taken incorrectly"),
+    ADD_STAT(predictedNotTakenIncorrect,
+ "Number of branches that were predicted not taken incorrectly"),
+    ADD_STAT(branchMispredicts,
+             "Number of branch mispredicts detected at execute",
+             predictedTakenIncorrect + predictedNotTakenIncorrect),
+    executedInstStats(cpu),
+    ADD_STAT(instsToCommit, "Cumulative count of insts sent to commit"),
+    ADD_STAT(writebackCount, "Cumulative count of insts written-back"),
+    ADD_STAT(producerInst, "Number of instructions producing a value"),
+    ADD_STAT(consumerInst, "Number of instructions consuming a value"),
+    ADD_STAT(wbRate, "Insts written-back per cycle"),
+    ADD_STAT(wbFanout, "Average fanout of values written-back")
 {
-    using namespace Stats;
-
-    instQueue.regStats();
-
-    iewIdleCycles
-        .name(name() + ".iewIdleCycles")
-        .desc("Number of cycles IEW is idle");
-
-    iewSquashCycles
-        .name(name() + ".iewSquashCycles")
-        .desc("Number of cycles IEW is squashing");
-
-    iewBlockCycles
-        .name(name() + ".iewBlockCycles")
-        .desc("Number of cycles IEW is blocking");
-
-    iewUnblockCycles
-        .name(name() + ".iewUnblockCycles")
-        .desc("Number of cycles IEW is unblocking");
-
-    iewDispatchedInsts
-        .name(name() + ".iewDispatchedInsts")
-        .desc("Number of instructions dispatched to IQ");
-
-    iewDispSquashedInsts
-        .name(name() + ".iewDispSquashedInsts")
-        .desc("Number of squashed instructions skipped by dispatch");
-
-    iewDispLoadInsts
-        .name(name() + ".iewDispLoadInsts")
-        .desc("Number of dispatched load instructions");
-
-    iewDispStoreInsts
-        .name(name() + ".iewDispStoreInsts")
-        .desc("Number of dispatched store instructions");
-
-    iewDispNonSpecInsts
-        .name(name() + ".iewDispNonSpecInsts")
-        .desc("Number of dispatched non-speculative instructions");
-
-    iewIQFullEvents
-        .name(name() + ".iewIQFullEvents")
-        .desc("Number of times the IQ has become full, causing a stall");
-
-    iewLSQFullEvents
-        .name(name() + ".iewLSQFullEvents")
-        .desc("Number of times the LSQ has become full, causing a stall");
-
-    memOrderViolationEvents
-        .name(name() + ".memOrderViolationEvents")
-        .desc("Number of memory order violations");
-
-    predictedTakenIncorrect
-        .name(name() + ".predictedTakenIncorrect")
-        .desc("Number of branches that were predicted taken incorrectly");
-
-    predictedNotTakenIncorrect
-        .name(name() + ".predictedNotTakenIncorrect")
- .desc("Number of branches that were predicted not taken incorrectly");
-
-    branchMispredicts
-        .name(name() + ".branchMispredicts")
-        .desc("Number of branch mispredicts detected at execute");
-
- branchMispredicts = predictedTakenIncorrect + predictedNotTakenIncorrect;
-
-    iewExecutedInsts
-        .name(name() + ".iewExecutedInsts")
-        .desc("Number of executed instructions");
-
-    iewExecLoadInsts
+    instsToCommit
         .init(cpu->numThreads)
-        .name(name() + ".iewExecLoadInsts")
-        .desc("Number of load instructions executed")
-        .flags(total);
-
-    iewExecSquashedInsts
-        .name(name() + ".iewExecSquashedInsts")
-        .desc("Number of squashed instructions skipped in execute");
-
-    iewExecutedSwp
-        .init(cpu->numThreads)
-        .name(name() + ".exec_swp")
-        .desc("number of swp insts executed")
-        .flags(total);
-
-    iewExecutedNop
-        .init(cpu->numThreads)
-        .name(name() + ".exec_nop")
-        .desc("number of nop insts executed")
-        .flags(total);
-
-    iewExecutedRefs
-        .init(cpu->numThreads)
-        .name(name() + ".exec_refs")
-        .desc("number of memory reference insts executed")
-        .flags(total);
-
-    iewExecutedBranches
-        .init(cpu->numThreads)
-        .name(name() + ".exec_branches")
-        .desc("Number of branches executed")
-        .flags(total);
-
-    iewExecStoreInsts
-        .name(name() + ".exec_stores")
-        .desc("Number of stores executed")
-        .flags(total);
-    iewExecStoreInsts = iewExecutedRefs - iewExecLoadInsts;
-
-    iewExecRate
-        .name(name() + ".exec_rate")
-        .desc("Inst execution rate")
-        .flags(total);
-
-    iewExecRate = iewExecutedInsts / cpu->numCycles;
-
-    iewInstsToCommit
-        .init(cpu->numThreads)
-        .name(name() + ".wb_sent")
-        .desc("cumulative count of insts sent to commit")
-        .flags(total);
+        .flags(Stats::total);

     writebackCount
         .init(cpu->numThreads)
-        .name(name() + ".wb_count")
-        .desc("cumulative count of insts written-back")
-        .flags(total);
+        .flags(Stats::total);

     producerInst
         .init(cpu->numThreads)
-        .name(name() + ".wb_producers")
-        .desc("num instructions producing a value")
-        .flags(total);
+        .flags(Stats::total);

     consumerInst
         .init(cpu->numThreads)
-        .name(name() + ".wb_consumers")
-        .desc("num instructions consuming a value")
-        .flags(total);
-
-    wbFanout
-        .name(name() + ".wb_fanout")
-        .desc("average fanout of values written-back")
-        .flags(total);
-
-    wbFanout = producerInst / consumerInst;
+        .flags(Stats::total);

     wbRate
-        .name(name() + ".wb_rate")
-        .desc("insts written-back per cycle")
-        .flags(total);
+        .flags(Stats::total);
     wbRate = writebackCount / cpu->numCycles;
+
+    wbFanout
+        .flags(Stats::total);
+    wbFanout = producerInst / consumerInst;
+}
+
+template <class Impl>
+DefaultIEW<Impl>::IEWStats::
+ExecutedInstStats::ExecutedInstStats(O3CPU *cpu)
+    : Stats::Group(cpu),
+    ADD_STAT(numInsts, "Number of executed instructions"),
+    ADD_STAT(numLoadInsts, "Number of load instructions executed"),
+    ADD_STAT(numSquashedInsts,
+             "Number of squashed instructions skipped in execute"),
+    ADD_STAT(numSwp, "Number of swp insts executed"),
+    ADD_STAT(numNop, "Number of nop insts executed"),
+    ADD_STAT(numRefs, "Number of memory reference insts executed"),
+    ADD_STAT(numBranches, "Number of branches executed"),
+    ADD_STAT(numStoreInsts, "Number of stores executed"),
+    ADD_STAT(numRate, "Inst execution rate", numInsts / cpu->numCycles)
+{
+    numLoadInsts
+        .init(cpu->numThreads)
+        .flags(Stats::total);
+
+    numSwp
+        .init(cpu->numThreads)
+        .flags(Stats::total);
+
+    numNop
+        .init(cpu->numThreads)
+        .flags(Stats::total);
+
+    numRefs
+        .init(cpu->numThreads)
+        .flags(Stats::total);
+
+    numBranches
+        .init(cpu->numThreads)
+        .flags(Stats::total);
+
+    numStoreInsts
+        .flags(Stats::total);
+    numStoreInsts = numRefs - numLoadInsts;
+
+    numRate
+        .flags(Stats::total);
+}
+
+template <class Impl>
+void
+DefaultIEW<Impl>::regStats()
+{
+    instQueue.regStats();
 }

 template<class Impl>
@@ -917,10 +869,10 @@
     //     check if stall conditions have passed

     if (dispatchStatus[tid] == Blocked) {
-        ++iewBlockCycles;
+        ++iewStats.blockCycles;

     } else if (dispatchStatus[tid] == Squashing) {
-        ++iewSquashCycles;
+        ++iewStats.squashCycles;
     }

// Dispatch should try to dispatch as many instructions as its bandwidth
@@ -941,7 +893,7 @@
         // the rest of unblocking.
         dispatchInsts(tid);

-        ++iewUnblockCycles;
+        ++iewStats.unblockCycles;

         if (validInstsFromRename()) {
             // Add the current inputs to the skid buffer so they can be
@@ -998,7 +950,7 @@
DPRINTF(IEW, "[tid:%i] Issue: Squashed instruction encountered, "
                     "not adding to IQ.\n", tid);

-            ++iewDispSquashedInsts;
+            ++iewStats.dispSquashedInsts;

             insts_to_dispatch.pop();

@@ -1027,7 +979,7 @@
             // get full in the IQ.
             toRename->iewUnblock[tid] = false;

-            ++iewIQFullEvents;
+            ++iewStats.iqFullEvents;
             break;
         }

@@ -1046,7 +998,7 @@
             // get full in the IQ.
             toRename->iewUnblock[tid] = false;

-            ++iewLSQFullEvents;
+            ++iewStats.lsqFullEvents;
             break;
         }

@@ -1071,7 +1023,7 @@

             ldstQueue.insertStore(inst);

-            ++iewDispStoreInsts;
+            ++iewStats.dispStoreInsts;

             // AMOs need to be set as "canCommit()"
             // so that commit can process them when they reach the
@@ -1080,7 +1032,7 @@
             instQueue.insertNonSpec(inst);
             add_to_iq = false;

-            ++iewDispNonSpecInsts;
+            ++iewStats.dispNonSpecInsts;

             toRename->iewInfo[tid].dispatchedToSQ++;
         } else if (inst->isLoad()) {
@@ -1091,7 +1043,7 @@
             // memory access.
             ldstQueue.insertLoad(inst);

-            ++iewDispLoadInsts;
+            ++iewStats.dispLoadInsts;

             add_to_iq = true;

@@ -1102,7 +1054,7 @@

             ldstQueue.insertStore(inst);

-            ++iewDispStoreInsts;
+            ++iewStats.dispStoreInsts;

             if (inst->isStoreConditional()) {
                 // Store conditionals need to be set as "canCommit()"
@@ -1113,7 +1065,7 @@
                 instQueue.insertNonSpec(inst);
                 add_to_iq = false;

-                ++iewDispNonSpecInsts;
+                ++iewStats.dispNonSpecInsts;
             } else {
                 add_to_iq = true;
             }
@@ -1134,7 +1086,7 @@

             instQueue.recordProducer(inst);

-            iewExecutedNop[tid]++;
+            iewStats.executedInstStats.numNop[tid]++;

             add_to_iq = false;
         } else {
@@ -1152,7 +1104,7 @@
             // Specifically insert it as nonspeculative.
             instQueue.insertNonSpec(inst);

-            ++iewDispNonSpecInsts;
+            ++iewStats.dispNonSpecInsts;

             add_to_iq = false;
         }
@@ -1167,7 +1119,7 @@

         toRename->iewInfo[tid].dispatched++;

-        ++iewDispatchedInsts;
+        ++iewStats.dispatchedInsts;

 #if TRACING_ON
         inst->dispatchTick = curTick() - inst->fetchTick;
@@ -1263,7 +1215,7 @@
// commit any squashed instructions. I like the latter a bit more.
             inst->setCanCommit();

-            ++iewExecSquashedInsts;
+            ++iewStats.executedInstStats.numSquashedInsts;

             continue;
         }
@@ -1395,9 +1347,9 @@
                 ppMispredict->notify(inst);

                 if (inst->readPredTaken()) {
-                    predictedTakenIncorrect++;
+                    iewStats.predictedTakenIncorrect++;
                 } else {
-                    predictedNotTakenIncorrect++;
+                    iewStats.predictedNotTakenIncorrect++;
                 }
             } else if (ldstQueue.violation(tid)) {
                 assert(inst->isMemRef());
@@ -1420,7 +1372,7 @@
                 // Squash.
                 squashDueToMemOrder(violator, tid);

-                ++memOrderViolationEvents;
+                ++iewStats.memOrderViolationEvents;
             }
         } else {
             // Reset any state associated with redirects that will not
@@ -1437,7 +1389,7 @@
                 DPRINTF(IEW, "Violation will not be handled because "
                         "already squashing\n");

-                ++memOrderViolationEvents;
+                ++iewStats.memOrderViolationEvents;
             }
         }
     }
@@ -1477,7 +1429,7 @@
         DPRINTF(IEW, "Sending instructions to commit, [sn:%lli] PC %s.\n",
                 inst->seqNum, inst->pcState());

-        iewInstsToCommit[tid]++;
+        iewStats.instsToCommit[tid]++;
         // Notify potential listeners that execution is complete for this
         // instruction.
         ppToCommit->notify(inst);
@@ -1502,10 +1454,10 @@
             }

             if (dependents) {
-                producerInst[tid]++;
-                consumerInst[tid]+= dependents;
+                iewStats.producerInst[tid]++;
+                iewStats.consumerInst[tid]+= dependents;
             }
-            writebackCount[tid]++;
+            iewStats.writebackCount[tid]++;
         }
     }
 }
@@ -1646,7 +1598,7 @@
 {
     ThreadID tid = inst->threadNumber;

-    iewExecutedInsts++;
+    iewStats.executedInstStats.numInsts++;

 #if TRACING_ON
     if (DTRACE(O3PipeView)) {
@@ -1658,16 +1610,16 @@
     //  Control operations
     //
     if (inst->isControl())
-        iewExecutedBranches[tid]++;
+        iewStats.executedInstStats.numBranches[tid]++;

     //
     //  Memory operations
     //
     if (inst->isMemRef()) {
-        iewExecutedRefs[tid]++;
+        iewStats.executedInstStats.numRefs[tid]++;

         if (inst->isLoad()) {
-            iewExecLoadInsts[tid]++;
+            iewStats.executedInstStats.numLoadInsts[tid]++;
         }
     }
 }
@@ -1702,9 +1654,9 @@
             squashDueToBranch(inst, tid);

             if (inst->readPredTaken()) {
-                predictedTakenIncorrect++;
+                iewStats.predictedTakenIncorrect++;
             } else {
-                predictedNotTakenIncorrect++;
+                iewStats.predictedNotTakenIncorrect++;
             }
         }
     }

--
To view, visit https://gem5-review.googlesource.com/c/public/gem5/+/36095
To unsubscribe, or for help writing mail filters, visit https://gem5-review.googlesource.com/settings

Gerrit-Project: public/gem5
Gerrit-Branch: develop
Gerrit-Change-Id: Ie213aeb402fee5f015f10c9c03e5b9c02ba1f3fe
Gerrit-Change-Number: 36095
Gerrit-PatchSet: 16
Gerrit-Owner: Hoa Nguyen <hoangu...@ucdavis.edu>
Gerrit-Reviewer: Bobby R. Bruce <bbr...@ucdavis.edu>
Gerrit-Reviewer: Daniel Carvalho <oda...@yahoo.com.br>
Gerrit-Reviewer: Hoa Nguyen <hoangu...@ucdavis.edu>
Gerrit-Reviewer: Jason Lowe-Power <power...@gmail.com>
Gerrit-Reviewer: kokoro <noreply+kok...@google.com>
Gerrit-CC: Giacomo Travaglini <giacomo.travagl...@arm.com>
Gerrit-MessageType: merged
_______________________________________________
gem5-dev mailing list -- gem5-dev@gem5.org
To unsubscribe send an email to gem5-dev-le...@gem5.org
%(web_page_url)slistinfo%(cgiext)s/%(_internal_name)s

Reply via email to