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
This commit is contained in:
parent
2971b8401a
commit
991d0185c6
|
@ -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();
|
||||
}
|
||||
|
||||
|
|
|
@ -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.
|
||||
*/
|
||||
|
|
|
@ -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];
|
||||
|
|
|
@ -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)
|
||||
|
|
|
@ -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);
|
||||
|
|
Loading…
Reference in a new issue