misc: Delete the now unnecessary create methods.
[gem5.git] / src / mem / comm_monitor.cc
index 4255d58ad705fca035ea3d8dea066bb7e6a3ed61..297837ab1fe216f6b8dfdc0b56e68692f0aea10d 100644 (file)
@@ -1,6 +1,8 @@
 /*
- * Copyright (c) 2012 ARM Limited
- * All rights reserved
+ * Copyright (c) 2012-2013, 2015, 2018-2019 ARM Limited
+ * Copyright (c) 2016 Google Inc.
+ * Copyright (c) 2017, Centre National de la Recherche Scientifique
+ * All rights reserved.
  *
  * The license below extends only to copyright in the software and shall
  * not be construed as granting a license to any other intellectual
  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- * Authors: Thomas Grass
- *          Andreas Hansson
  */
 
-#include "debug/CommMonitor.hh"
 #include "mem/comm_monitor.hh"
+
+#include "base/trace.hh"
+#include "debug/CommMonitor.hh"
 #include "sim/stats.hh"
 
-CommMonitor::CommMonitor(Params* params)
-    : MemObject(params),
-      masterPort(name() + "-master", *this),
-      slavePort(name() + "-slave", *this),
-      samplePeriodicEvent(this),
-      samplePeriodTicks(params->sample_period),
-      readAddrMask(params->read_addr_mask),
-      writeAddrMask(params->write_addr_mask),
-      stats(params)
+CommMonitor::CommMonitor(const Params &params)
+    : SimObject(params),
+      memSidePort(name() + "-mem_side_port", *this),
+      cpuSidePort(name() + "-cpu_side_port", *this),
+      samplePeriodicEvent([this]{ samplePeriodic(); }, name()),
+      samplePeriodTicks(params.sample_period),
+      samplePeriod(params.sample_period / SimClock::Float::s),
+      stats(this, params)
 {
-    // keep track of the sample period both in ticks and absolute time
-    samplePeriod.setTick(params->sample_period);
-
     DPRINTF(CommMonitor,
-            "Created monitor %s with sample period %d ticks (%f s)\n",
-            name(), samplePeriodTicks, samplePeriod);
-}
-
-CommMonitor*
-CommMonitorParams::create()
-{
-    return new CommMonitor(this);
+            "Created monitor %s with sample period %d ticks (%f ms)\n",
+            name(), samplePeriodTicks, samplePeriod * 1E3);
 }
 
 void
 CommMonitor::init()
 {
     // make sure both sides of the monitor are connected
-    if (!slavePort.isConnected() || !masterPort.isConnected())
+    if (!cpuSidePort.isConnected() || !memSidePort.isConnected())
         fatal("Communication monitor is not connected on both sides.\n");
 }
 
-MasterPort&
-CommMonitor::getMasterPort(const std::string& if_name, int idx)
+void
+CommMonitor::regProbePoints()
 {
-    if (if_name == "master") {
-        return masterPort;
-    } else {
-        return MemObject::getMasterPort(if_name, idx);
-    }
+    ppPktReq.reset(new ProbePoints::Packet(getProbeManager(), "PktRequest"));
+    ppPktResp.reset(new ProbePoints::Packet(getProbeManager(), "PktResponse"));
 }
 
-SlavePort&
-CommMonitor::getSlavePort(const std::string& if_name, int idx)
+Port &
+CommMonitor::getPort(const std::string &if_name, PortID idx)
 {
-    if (if_name == "slave") {
-        return slavePort;
+    if (if_name == "mem_side_port") {
+        return memSidePort;
+    } else if (if_name == "cpu_side_port") {
+        return cpuSidePort;
     } else {
-        return MemObject::getSlavePort(if_name, idx);
+        return SimObject::getPort(if_name, idx);
     }
 }
 
 void
 CommMonitor::recvFunctional(PacketPtr pkt)
 {
-    masterPort.sendFunctional(pkt);
+    memSidePort.sendFunctional(pkt);
 }
 
 void
 CommMonitor::recvFunctionalSnoop(PacketPtr pkt)
 {
-    slavePort.sendFunctionalSnoop(pkt);
+    cpuSidePort.sendFunctionalSnoop(pkt);
 }
 
-Tick
-CommMonitor::recvAtomic(PacketPtr pkt)
+CommMonitor::MonitorStats::MonitorStats(Stats::Group *parent,
+                                        const CommMonitorParams &params)
+    : Stats::Group(parent),
+
+      disableBurstLengthHists(params.disable_burst_length_hists),
+      ADD_STAT(readBurstLengthHist,
+               "Histogram of burst lengths of transmitted packets"),
+      ADD_STAT(writeBurstLengthHist,
+               "Histogram of burst lengths of transmitted packets"),
+
+      disableBandwidthHists(params.disable_bandwidth_hists),
+      readBytes(0),
+      ADD_STAT(readBandwidthHist,
+               "Histogram of read bandwidth per sample period (bytes/s)"),
+      ADD_STAT(totalReadBytes, "Number of bytes read"),
+      ADD_STAT(averageReadBandwidth, "Average read bandwidth (bytes/s)",
+               totalReadBytes / simSeconds),
+
+      writtenBytes(0),
+      ADD_STAT(writeBandwidthHist, "Histogram of write bandwidth (bytes/s)"),
+      ADD_STAT(totalWrittenBytes, "Number of bytes written"),
+      ADD_STAT(averageWriteBandwidth, "Average write bandwidth (bytes/s)",
+               totalWrittenBytes / simSeconds),
+
+      disableLatencyHists(params.disable_latency_hists),
+      ADD_STAT(readLatencyHist, "Read request-response latency"),
+      ADD_STAT(writeLatencyHist, "Write request-response latency"),
+
+      disableITTDists(params.disable_itt_dists),
+      ADD_STAT(ittReadRead, "Read-to-read inter transaction time"),
+      ADD_STAT(ittWriteWrite , "Write-to-write inter transaction time"),
+      ADD_STAT(ittReqReq, "Request-to-request inter transaction time"),
+      timeOfLastRead(0), timeOfLastWrite(0), timeOfLastReq(0),
+
+      disableOutstandingHists(params.disable_outstanding_hists),
+      ADD_STAT(outstandingReadsHist, "Outstanding read transactions"),
+      outstandingReadReqs(0),
+      ADD_STAT(outstandingWritesHist, "Outstanding write transactions"),
+      outstandingWriteReqs(0),
+
+      disableTransactionHists(params.disable_transaction_hists),
+      ADD_STAT(readTransHist,
+               "Histogram of read transactions per sample period"),
+      readTrans(0),
+      ADD_STAT(writeTransHist,
+               "Histogram of write transactions per sample period"),
+      writeTrans(0),
+
+      disableAddrDists(params.disable_addr_dists),
+      readAddrMask(params.read_addr_mask),
+      writeAddrMask(params.write_addr_mask),
+      ADD_STAT(readAddrDist, "Read address distribution"),
+      ADD_STAT(writeAddrDist, "Write address distribution")
 {
-    return masterPort.sendAtomic(pkt);
-}
+    using namespace Stats;
 
-Tick
-CommMonitor::recvAtomicSnoop(PacketPtr pkt)
-{
-    return slavePort.sendAtomicSnoop(pkt);
-}
+    readBurstLengthHist
+        .init(params.burst_length_bins)
+        .flags(disableBurstLengthHists ? nozero : pdf);
 
-bool
-CommMonitor::recvTimingReq(PacketPtr pkt)
-{
-    // should always see a request
-    assert(pkt->isRequest());
+    writeBurstLengthHist
+        .init(params.burst_length_bins)
+        .flags(disableBurstLengthHists ? nozero : pdf);
 
-    // Store relevant fields of packet, because packet may be modified
-    // or even deleted when sendTiming() is called.
-    bool isRead = pkt->isRead();
-    bool isWrite = pkt->isWrite();
-    unsigned size = pkt->getSize();
-    Addr addr = pkt->getAddr();
-    bool needsResponse = pkt->needsResponse();
-    bool memInhibitAsserted = pkt->memInhibitAsserted();
-    Packet::SenderState* senderState = pkt->senderState;
+    // Stats based on received responses
+    readBandwidthHist
+        .init(params.bandwidth_bins)
+        .flags(disableBandwidthHists ? nozero : pdf);
 
-    // If a cache miss is served by a cache, a monitor near the memory
-    // would see a request which needs a response, but this response
-    // would be inhibited and not come back from the memory. Therefore
-    // we additionally have to check the inhibit flag.
-    if (needsResponse && !memInhibitAsserted && !stats.disableLatencyHists) {
-        pkt->senderState = new CommMonitorSenderState(senderState,
-                                                      curTick());
-    }
+    averageReadBandwidth
+        .flags(disableBandwidthHists ? nozero : pdf);
 
-    // Attempt to send the packet (always succeeds for inhibited
-    // packets)
-    bool successful = masterPort.sendTimingReq(pkt);
+    totalReadBytes
+        .flags(disableBandwidthHists ? nozero : pdf);
 
-    // If not successful, restore the sender state
-    if (!successful && needsResponse && !stats.disableLatencyHists) {
-        delete pkt->senderState;
-        pkt->senderState = senderState;
-    }
+    // Stats based on successfully sent requests
+    writeBandwidthHist
+        .init(params.bandwidth_bins)
+        .flags(disableBandwidthHists ? (pdf | nozero) : pdf);
+
+    averageWriteBandwidth
+        .flags(disableBandwidthHists ? nozero : pdf);
+
+    totalWrittenBytes
+        .flags(disableBandwidthHists ? nozero : pdf);
+
+
+    readLatencyHist
+        .init(params.latency_bins)
+        .flags(disableLatencyHists ? nozero : pdf);
+
+    writeLatencyHist
+        .init(params.latency_bins)
+        .flags(disableLatencyHists ? nozero : pdf);
 
-    if (successful && isRead) {
-        DPRINTF(CommMonitor, "Forwarded read request\n");
+    ittReadRead
+        .init(1, params.itt_max_bin, params.itt_max_bin /
+              params.itt_bins)
+        .flags(disableITTDists ? nozero : pdf);
 
+    ittWriteWrite
+        .init(1, params.itt_max_bin, params.itt_max_bin /
+              params.itt_bins)
+        .flags(disableITTDists ? nozero : pdf);
+
+    ittReqReq
+        .init(1, params.itt_max_bin, params.itt_max_bin /
+              params.itt_bins)
+        .flags(disableITTDists ? nozero : pdf);
+
+    outstandingReadsHist
+        .init(params.outstanding_bins)
+        .flags(disableOutstandingHists ? nozero : pdf);
+
+    outstandingWritesHist
+        .init(params.outstanding_bins)
+        .flags(disableOutstandingHists ? nozero : pdf);
+
+    readTransHist
+        .init(params.transaction_bins)
+        .flags(disableTransactionHists ? nozero : pdf);
+
+    writeTransHist
+        .init(params.transaction_bins)
+        .flags(disableTransactionHists ? nozero : pdf);
+
+    readAddrDist
+        .init(0)
+        .flags(disableAddrDists ? nozero : pdf);
+
+    writeAddrDist
+        .init(0)
+        .flags(disableAddrDists ? nozero : pdf);
+}
+
+void
+CommMonitor::MonitorStats::updateReqStats(
+    const ProbePoints::PacketInfo& pkt_info, bool is_atomic,
+    bool expects_response)
+{
+    if (pkt_info.cmd.isRead()) {
         // Increment number of observed read transactions
-        if (!stats.disableTransactionHists) {
-            ++stats.readTrans;
-        }
+        if (!disableTransactionHists)
+            ++readTrans;
 
         // Get sample of burst length
-        if (!stats.disableBurstLengthHists) {
-            stats.readBurstLengthHist.sample(size);
-        }
+        if (!disableBurstLengthHists)
+            readBurstLengthHist.sample(pkt_info.size);
 
         // Sample the masked address
-        if (!stats.disableAddrDists) {
-            stats.readAddrDist.sample(addr & readAddrMask);
-        }
-
-        // If it needs a response increment number of outstanding read
-        // requests
-        if (!stats.disableOutstandingHists && needsResponse) {
-            ++stats.outstandingReadReqs;
-        }
+        if (!disableAddrDists)
+            readAddrDist.sample(pkt_info.addr & readAddrMask);
 
-        if (!stats.disableITTDists) {
+        if (!disableITTDists) {
             // Sample value of read-read inter transaction time
-            if (stats.timeOfLastRead != 0) {
-                stats.ittReadRead.sample(curTick() - stats.timeOfLastRead);
-            }
-            stats.timeOfLastRead = curTick();
+            if (timeOfLastRead != 0)
+                ittReadRead.sample(curTick() - timeOfLastRead);
+            timeOfLastRead = curTick();
 
             // Sample value of req-req inter transaction time
-            if (stats.timeOfLastReq != 0) {
-                stats.ittReqReq.sample(curTick() - stats.timeOfLastReq);
-            }
-            stats.timeOfLastReq = curTick();
+            if (timeOfLastReq != 0)
+                ittReqReq.sample(curTick() - timeOfLastReq);
+            timeOfLastReq = curTick();
         }
-    } else if (successful && isWrite) {
-        DPRINTF(CommMonitor, "Forwarded write request\n");
+        if (!is_atomic && !disableOutstandingHists && expects_response)
+            ++outstandingReadReqs;
 
+    } else if (pkt_info.cmd.isWrite()) {
         // Same as for reads
-        if (!stats.disableTransactionHists) {
-            ++stats.writeTrans;
-        }
+        if (!disableTransactionHists)
+            ++writeTrans;
 
-        if (!stats.disableBurstLengthHists) {
-            stats.writeBurstLengthHist.sample(size);
-        }
+        if (!disableBurstLengthHists)
+            writeBurstLengthHist.sample(pkt_info.size);
 
         // Update the bandwidth stats on the request
-        if (!stats.disableBandwidthHists) {
-            stats.writtenBytes += size;
-            stats.totalWrittenBytes += size;
+        if (!disableBandwidthHists) {
+            writtenBytes += pkt_info.size;
+            totalWrittenBytes += pkt_info.size;
         }
 
         // Sample the masked write address
-        if (!stats.disableAddrDists) {
-            stats.writeAddrDist.sample(addr & writeAddrMask);
+        if (!disableAddrDists)
+            writeAddrDist.sample(pkt_info.addr & writeAddrMask);
+
+        if (!disableITTDists) {
+            // Sample value of write-to-write inter transaction time
+            if (timeOfLastWrite != 0)
+                ittWriteWrite.sample(curTick() - timeOfLastWrite);
+            timeOfLastWrite = curTick();
+
+            // Sample value of req-to-req inter transaction time
+            if (timeOfLastReq != 0)
+                ittReqReq.sample(curTick() - timeOfLastReq);
+            timeOfLastReq = curTick();
         }
 
-        if (!stats.disableOutstandingHists && needsResponse) {
-            ++stats.outstandingWriteReqs;
+        if (!is_atomic && !disableOutstandingHists && expects_response)
+            ++outstandingWriteReqs;
+    }
+}
+
+void
+CommMonitor::MonitorStats::updateRespStats(
+    const ProbePoints::PacketInfo& pkt_info, Tick latency, bool is_atomic)
+{
+    if (pkt_info.cmd.isRead()) {
+        // Decrement number of outstanding read requests
+        if (!is_atomic && !disableOutstandingHists) {
+            assert(outstandingReadReqs != 0);
+            --outstandingReadReqs;
         }
 
-        if (!stats.disableITTDists) {
-            // Sample value of write-to-write inter transaction time
-            if (stats.timeOfLastWrite != 0) {
-                stats.ittWriteWrite.sample(curTick() - stats.timeOfLastWrite);
-            }
-            stats.timeOfLastWrite = curTick();
+        if (!disableLatencyHists)
+            readLatencyHist.sample(latency);
 
-            // Sample value of req-to-req inter transaction time
-            if (stats.timeOfLastReq != 0) {
-                stats.ittReqReq.sample(curTick() - stats.timeOfLastReq);
-            }
-            stats.timeOfLastReq = curTick();
+        // Update the bandwidth stats based on responses for reads
+        if (!disableBandwidthHists) {
+            readBytes += pkt_info.size;
+            totalReadBytes += pkt_info.size;
+        }
+
+    } else if (pkt_info.cmd.isWrite()) {
+        // Decrement number of outstanding write requests
+        if (!is_atomic && !disableOutstandingHists) {
+            assert(outstandingWriteReqs != 0);
+            --outstandingWriteReqs;
         }
-    } else if (successful) {
-        DPRINTF(CommMonitor, "Forwarded non read/write request\n");
+
+        if (!disableLatencyHists)
+            writeLatencyHist.sample(latency);
+    }
+}
+
+Tick
+CommMonitor::recvAtomic(PacketPtr pkt)
+{
+    const bool expects_response(pkt->needsResponse() &&
+                                !pkt->cacheResponding());
+    ProbePoints::PacketInfo req_pkt_info(pkt);
+    ppPktReq->notify(req_pkt_info);
+
+    const Tick delay(memSidePort.sendAtomic(pkt));
+
+    stats.updateReqStats(req_pkt_info, true, expects_response);
+    if (expects_response)
+        stats.updateRespStats(req_pkt_info, delay, true);
+
+    // Some packets, such as WritebackDirty, don't need response.
+    assert(pkt->isResponse() || !expects_response);
+    ProbePoints::PacketInfo resp_pkt_info(pkt);
+    ppPktResp->notify(resp_pkt_info);
+    return delay;
+}
+
+Tick
+CommMonitor::recvAtomicSnoop(PacketPtr pkt)
+{
+    return cpuSidePort.sendAtomicSnoop(pkt);
+}
+
+bool
+CommMonitor::recvTimingReq(PacketPtr pkt)
+{
+    // should always see a request
+    assert(pkt->isRequest());
+
+    // Store relevant fields of packet, because packet may be modified
+    // or even deleted when sendTiming() is called.
+    const ProbePoints::PacketInfo pkt_info(pkt);
+
+    const bool expects_response(pkt->needsResponse() &&
+                                !pkt->cacheResponding());
+
+    // If a cache miss is served by a cache, a monitor near the memory
+    // would see a request which needs a response, but this response
+    // would not come back from the memory. Therefore we additionally
+    // have to check the cacheResponding flag
+    if (expects_response && !stats.disableLatencyHists) {
+        pkt->pushSenderState(new CommMonitorSenderState(curTick()));
     }
 
+    // Attempt to send the packet
+    bool successful = memSidePort.sendTimingReq(pkt);
+
+    // If not successful, restore the sender state
+    if (!successful && expects_response && !stats.disableLatencyHists) {
+        delete pkt->popSenderState();
+    }
+
+    if (successful) {
+        ppPktReq->notify(pkt_info);
+    }
+
+    if (successful) {
+        DPRINTF(CommMonitor, "Forwarded %s request\n", pkt->isRead() ? "read" :
+                pkt->isWrite() ? "write" : "non read/write");
+        stats.updateReqStats(pkt_info, false, expects_response);
+    }
     return successful;
 }
 
@@ -245,70 +406,43 @@ CommMonitor::recvTimingResp(PacketPtr pkt)
 
     // Store relevant fields of packet, because packet may be modified
     // or even deleted when sendTiming() is called.
-    bool isRead = pkt->isRead();
-    bool isWrite = pkt->isWrite();
-    unsigned size = pkt->getSize();
+    const ProbePoints::PacketInfo pkt_info(pkt);
+
     Tick latency = 0;
-    CommMonitorSenderState* commReceivedState =
+    CommMonitorSenderState* received_state =
         dynamic_cast<CommMonitorSenderState*>(pkt->senderState);
 
     if (!stats.disableLatencyHists) {
         // Restore initial sender state
-        if (commReceivedState == NULL)
+        if (received_state == NULL)
             panic("Monitor got a response without monitor sender state\n");
 
         // Restore the sate
-        pkt->senderState = commReceivedState->origSenderState;
+        pkt->senderState = received_state->predecessor;
     }
 
     // Attempt to send the packet
-    bool successful = slavePort.sendTimingResp(pkt);
+    bool successful = cpuSidePort.sendTimingResp(pkt);
 
     if (!stats.disableLatencyHists) {
         // If packet successfully send, sample value of latency,
         // afterwards delete sender state, otherwise restore state
         if (successful) {
-            latency = curTick() - commReceivedState->transmitTime;
+            latency = curTick() - received_state->transmitTime;
             DPRINTF(CommMonitor, "Latency: %d\n", latency);
-            delete commReceivedState;
+            delete received_state;
         } else {
             // Don't delete anything and let the packet look like we
             // did not touch it
-            pkt->senderState = commReceivedState;
+            pkt->senderState = received_state;
         }
     }
 
-    if (successful && isRead) {
-        // Decrement number of outstanding read requests
-        DPRINTF(CommMonitor, "Received read response\n");
-        if (!stats.disableOutstandingHists) {
-            assert(stats.outstandingReadReqs != 0);
-            --stats.outstandingReadReqs;
-        }
-
-        if (!stats.disableLatencyHists) {
-            stats.readLatencyHist.sample(latency);
-        }
-
-        // Update the bandwidth stats based on responses for reads
-        if (!stats.disableBandwidthHists) {
-            stats.readBytes += size;
-            stats.totalReadBytes += size;
-        }
-
-    } else if (successful && isWrite) {
-        // Decrement number of outstanding write requests
-        DPRINTF(CommMonitor, "Received write response\n");
-        if (!stats.disableOutstandingHists) {
-            assert(stats.outstandingWriteReqs != 0);
-            --stats.outstandingWriteReqs;
-        }
-
-        if (!stats.disableLatencyHists) {
-            stats.writeLatencyHist.sample(latency);
-        }
-    } else if (successful) {
-        DPRINTF(CommMonitor, "Received non read/write response\n");
+    if (successful) {
+        ppPktResp->notify(pkt_info);
+        DPRINTF(CommMonitor, "Received %s response\n", pkt->isRead() ? "read" :
+                pkt->isWrite() ?  "write" : "non read/write");
+        stats.updateRespStats(pkt_info, latency, false);
     }
     return successful;
 }
@@ -316,181 +450,57 @@ CommMonitor::recvTimingResp(PacketPtr pkt)
 void
 CommMonitor::recvTimingSnoopReq(PacketPtr pkt)
 {
-    slavePort.sendTimingSnoopReq(pkt);
+    cpuSidePort.sendTimingSnoopReq(pkt);
 }
 
 bool
 CommMonitor::recvTimingSnoopResp(PacketPtr pkt)
 {
-    return masterPort.sendTimingSnoopResp(pkt);
+    return memSidePort.sendTimingSnoopResp(pkt);
 }
 
-bool
-CommMonitor::isSnooping() const
-{
-    return slavePort.getMasterPort().isSnooping();
-}
-
-unsigned
-CommMonitor::deviceBlockSizeMaster()
+void
+CommMonitor::recvRetrySnoopResp()
 {
-    return slavePort.peerBlockSize();
+    cpuSidePort.sendRetrySnoopResp();
 }
 
-unsigned
-CommMonitor::deviceBlockSizeSlave()
+bool
+CommMonitor::isSnooping() const
 {
-    return masterPort.peerBlockSize();
+    // check if the connected request port is snooping
+    return cpuSidePort.isSnooping();
 }
 
 AddrRangeList
-CommMonitor::getAddrRanges()
+CommMonitor::getAddrRanges() const
 {
-    return masterPort.getSlavePort().getAddrRanges();
+    // get the address ranges of the connected CPU-side port
+    return memSidePort.getAddrRanges();
 }
 
 void
-CommMonitor::recvRetryMaster()
+CommMonitor::recvReqRetry()
 {
-    slavePort.sendRetry();
+    cpuSidePort.sendRetryReq();
 }
 
 void
-CommMonitor::recvRetrySlave()
+CommMonitor::recvRespRetry()
 {
-    masterPort.sendRetry();
+    memSidePort.sendRetryResp();
 }
 
-void
-CommMonitor::recvRangeChange()
+bool
+CommMonitor::tryTiming(PacketPtr pkt)
 {
-    slavePort.sendRangeChange();
+    return memSidePort.tryTiming(pkt);
 }
 
 void
-CommMonitor::regStats()
+CommMonitor::recvRangeChange()
 {
-    // Initialise all the monitor stats
-    using namespace Stats;
-
-    stats.readBurstLengthHist
-        .init(params()->burst_length_bins)
-        .name(name() + ".readBurstLengthHist")
-        .desc("Histogram of burst lengths of transmitted packets")
-        .flags(stats.disableBurstLengthHists ? nozero : pdf);
-
-    stats.writeBurstLengthHist
-        .init(params()->burst_length_bins)
-        .name(name() + ".writeBurstLengthHist")
-        .desc("Histogram of burst lengths of transmitted packets")
-        .flags(stats.disableBurstLengthHists ? nozero : pdf);
-
-    // Stats based on received responses
-    stats.readBandwidthHist
-        .init(params()->bandwidth_bins)
-        .name(name() + ".readBandwidthHist")
-        .desc("Histogram of read bandwidth per sample period (bytes/s)")
-        .flags(stats.disableBandwidthHists ? nozero : pdf);
-
-    stats.averageReadBW
-        .name(name() + ".averageReadBandwidth")
-        .desc("Average read bandwidth (bytes/s)")
-        .flags(stats.disableBandwidthHists ? nozero : pdf);
-
-    stats.totalReadBytes
-        .name(name() + ".totalReadBytes")
-        .desc("Number of bytes read")
-        .flags(stats.disableBandwidthHists ? nozero : pdf);
-
-    stats.averageReadBW = stats.totalReadBytes / simSeconds;
-
-    // Stats based on successfully sent requests
-    stats.writeBandwidthHist
-        .init(params()->bandwidth_bins)
-        .name(name() + ".writeBandwidthHist")
-        .desc("Histogram of write bandwidth (bytes/s)")
-        .flags(stats.disableBandwidthHists ? (pdf | nozero) : pdf);
-
-    stats.averageWriteBW
-        .name(name() + ".averageWriteBandwidth")
-        .desc("Average write bandwidth (bytes/s)")
-        .flags(stats.disableBandwidthHists ? nozero : pdf);
-
-    stats.totalWrittenBytes
-        .name(name() + ".totalWrittenBytes")
-        .desc("Number of bytes written")
-        .flags(stats.disableBandwidthHists ? nozero : pdf);
-
-    stats.averageWriteBW = stats.totalWrittenBytes / simSeconds;
-
-    stats.readLatencyHist
-        .init(params()->latency_bins)
-        .name(name() + ".readLatencyHist")
-        .desc("Read request-response latency")
-        .flags(stats.disableLatencyHists ? nozero : pdf);
-
-    stats.writeLatencyHist
-        .init(params()->latency_bins)
-        .name(name() + ".writeLatencyHist")
-        .desc("Write request-response latency")
-        .flags(stats.disableLatencyHists ? nozero : pdf);
-
-    stats.ittReadRead
-        .init(1, params()->itt_max_bin, params()->itt_max_bin /
-              params()->itt_bins)
-        .name(name() + ".ittReadRead")
-        .desc("Read-to-read inter transaction time")
-        .flags(stats.disableITTDists ? nozero : pdf);
-
-    stats.ittWriteWrite
-        .init(1, params()->itt_max_bin, params()->itt_max_bin /
-              params()->itt_bins)
-        .name(name() + ".ittWriteWrite")
-        .desc("Write-to-write inter transaction time")
-        .flags(stats.disableITTDists ? nozero : pdf);
-
-    stats.ittReqReq
-        .init(1, params()->itt_max_bin, params()->itt_max_bin /
-              params()->itt_bins)
-        .name(name() + ".ittReqReq")
-        .desc("Request-to-request inter transaction time")
-        .flags(stats.disableITTDists ? nozero : pdf);
-
-    stats.outstandingReadsHist
-        .init(params()->outstanding_bins)
-        .name(name() + ".outstandingReadsHist")
-        .desc("Outstanding read transactions")
-        .flags(stats.disableOutstandingHists ? nozero : pdf);
-
-    stats.outstandingWritesHist
-        .init(params()->outstanding_bins)
-        .name(name() + ".outstandingWritesHist")
-        .desc("Outstanding write transactions")
-        .flags(stats.disableOutstandingHists ? nozero : pdf);
-
-    stats.readTransHist
-        .init(params()->transaction_bins)
-        .name(name() + ".readTransHist")
-        .desc("Histogram of read transactions per sample period")
-        .flags(stats.disableTransactionHists ? nozero : pdf);
-
-    stats.writeTransHist
-        .init(params()->transaction_bins)
-        .name(name() + ".writeTransHist")
-        .desc("Histogram of read transactions per sample period")
-        .flags(stats.disableTransactionHists ? nozero : pdf);
-
-    stats.readAddrDist
-        .init(0)
-        .name(name() + ".readAddrDist")
-        .desc("Read address distribution")
-        .flags(stats.disableAddrDists ? nozero : pdf);
-
-    stats.writeAddrDist
-        .init(0)
-        .name(name() + ".writeAddrDist")
-        .desc("Write address distribution")
-        .flags(stats.disableAddrDists ? nozero : pdf);
+    cpuSidePort.sendRangeChange();
 }
 
 void