summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKorey Sewell <ksewell@umich.edu>2011-02-18 14:27:52 -0500
committerKorey Sewell <ksewell@umich.edu>2011-02-18 14:27:52 -0500
commit991d0185c68b53a04ae5d1f1a05749bbfddced89 (patch)
tree70a97d5b52ff695810b00513a9b3e0907e2a5d4b
parent2971b8401a4a76a774962900d9aed6e9eb4b2950 (diff)
downloadgem5-991d0185c68b53a04ae5d1f1a05749bbfddced89.tar.xz
inorder: initialize res. req. vectors based on resource bandwidth
first change in an optimization that will stop InOrder from allocating new memory for every instruction's request to a resource. This gets expensive since every instruction needs to access ~10 requests before graduation. Instead, the plan is to allocate just enough resource request objects to satisfy each resource's bandwidth (e.g. the execution unit would need to allocate 3 resource request objects for a 1-issue pipeline since on any given cycle it could have 2 read requests and 1 write request) and then let the instructions contend and reuse those allocated requests. The end result is a smaller memory footprint for the InOrder model and increased simulation performance
-rw-r--r--src/cpu/inorder/resource.cc6
-rw-r--r--src/cpu/inorder/resource.hh2
-rw-r--r--src/cpu/inorder/resources/cache_unit.cc5
-rw-r--r--src/cpu/inorder/resources/use_def.cc13
-rw-r--r--src/cpu/inorder/resources/use_def.hh2
5 files changed, 28 insertions, 0 deletions
diff --git a/src/cpu/inorder/resource.cc b/src/cpu/inorder/resource.cc
index 72b45dda8..5a31125c6 100644
--- a/src/cpu/inorder/resource.cc
+++ b/src/cpu/inorder/resource.cc
@@ -40,6 +40,8 @@ Resource::Resource(string res_name, int res_id, int res_width,
: resName(res_name), id(res_id),
width(res_width), latency(res_latency), cpu(_cpu)
{
+ reqs.resize(width);
+
// Use to deny a instruction a resource.
deniedReq = new ResourceRequest(this, NULL, 0, 0, 0, 0);
}
@@ -57,6 +59,10 @@ Resource::init()
// Set Up Resource Events to Appropriate Resource BandWidth
resourceEvent = new ResourceEvent[width];
+ for (int i = 0; i < width; i++) {
+ reqs[i] = new ResourceRequest(this, NULL, 0, 0, 0, 0);
+ }
+
initSlots();
}
diff --git a/src/cpu/inorder/resource.hh b/src/cpu/inorder/resource.hh
index bd9ec48ca..7f6cb6642 100644
--- a/src/cpu/inorder/resource.hh
+++ b/src/cpu/inorder/resource.hh
@@ -224,6 +224,8 @@ class Resource {
/** Mapping of slot-numbers to the resource-request pointers */
std::map<int, ResReqPtr> reqMap;
+ std::vector<ResReqPtr> reqs;
+
/** A list of all the available execution slots for this resource.
* This correlates with the actual resource event idx.
*/
diff --git a/src/cpu/inorder/resources/cache_unit.cc b/src/cpu/inorder/resources/cache_unit.cc
index 8cd105493..47fafe45a 100644
--- a/src/cpu/inorder/resources/cache_unit.cc
+++ b/src/cpu/inorder/resources/cache_unit.cc
@@ -133,6 +133,11 @@ CacheUnit::getPort(const string &if_name, int idx)
void
CacheUnit::init()
{
+ for (int i = 0; i < width; i++) {
+ reqs[i] = new CacheRequest(this, NULL, 0, 0, 0, 0, 0,
+ MemCmd::Command(0), 0, 0, 0);
+ }
+
// Currently Used to Model TLB Latency. Eventually
// Switch to Timing TLB translations.
resourceEvent = new CacheUnitEvent[width];
diff --git a/src/cpu/inorder/resources/use_def.cc b/src/cpu/inorder/resources/use_def.cc
index 538b20246..dd178403b 100644
--- a/src/cpu/inorder/resources/use_def.cc
+++ b/src/cpu/inorder/resources/use_def.cc
@@ -88,6 +88,19 @@ UseDefUnit::regStats()
Resource::regStats();
}
+void
+UseDefUnit::init()
+{
+ // Set Up Resource Events to Appropriate Resource BandWidth
+ resourceEvent = new ResourceEvent[width];
+
+ for (int i = 0; i < width; i++) {
+ reqs[i] = new UseDefRequest(this, NULL, 0, 0, 0, 0, 0);
+ }
+
+ initSlots();
+}
+
ResReqPtr
UseDefUnit::getRequest(DynInstPtr inst, int stage_num, int res_idx,
int slot_num, unsigned cmd)
diff --git a/src/cpu/inorder/resources/use_def.hh b/src/cpu/inorder/resources/use_def.hh
index d2cc55315..6db8ed987 100644
--- a/src/cpu/inorder/resources/use_def.hh
+++ b/src/cpu/inorder/resources/use_def.hh
@@ -56,6 +56,8 @@ class UseDefUnit : public Resource {
UseDefUnit(std::string res_name, int res_id, int res_width,
int res_latency, InOrderCPU *_cpu, ThePipeline::Params *params);
+ void init();
+
ResourceRequest* getRequest(DynInstPtr _inst, int stage_num,
int res_idx, int slot_num,
unsigned cmd);