diff options
Diffstat (limited to 'src/cpu/inorder/resource_pool.cc')
-rw-r--r-- | src/cpu/inorder/resource_pool.cc | 475 |
1 files changed, 0 insertions, 475 deletions
diff --git a/src/cpu/inorder/resource_pool.cc b/src/cpu/inorder/resource_pool.cc deleted file mode 100644 index e0f23235e..000000000 --- a/src/cpu/inorder/resource_pool.cc +++ /dev/null @@ -1,475 +0,0 @@ -/* - * Copyright (c) 2012 ARM Limited - * 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 - * property including but not limited to intellectual property relating - * to a hardware implementation of the functionality of the software - * licensed hereunder. You may use the software subject to the license - * terms below provided that you ensure that this notice is replicated - * unmodified and in its entirety in all distributions of the software, - * modified or unmodified, in source code or in binary form. - * - * Copyright (c) 2007 MIPS Technologies, Inc. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are - * met: redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer; - * redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution; - * neither the name of the copyright holders nor the names of its - * contributors may be used to endorse or promote products derived from - * this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT - * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR - * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT - * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, - * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT - * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, - * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY - * 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: Korey Sewell - * - */ - -#include <list> -#include <vector> - -#include "cpu/inorder/resources/resource_list.hh" -#include "cpu/inorder/resource_pool.hh" -#include "debug/Resource.hh" - -using namespace std; -using namespace ThePipeline; - -ResourcePool::ResourcePool(InOrderCPU *_cpu, ThePipeline::Params *params) - : cpu(_cpu), instUnit(NULL), dataUnit(NULL) -{ - //@todo: use this function to instantiate the resources in resource pool. - //This will help in the auto-generation of this pipeline model. - //ThePipeline::addResources(resources, memObjects); - - int stage_width = cpu->stageWidth; - - // Declare Resource Objects - // name - id - bandwidth - latency - CPU - Parameters - // -------------------------------------------------- - resources.push_back(new FetchSeqUnit("fetch_seq_unit", FetchSeq, - stage_width * 2, Cycles(0), - _cpu, params)); - - // Keep track of the instruction fetch unit so we can easily - // provide a pointer to it in the CPU. - instUnit = new FetchUnit("icache_port", ICache, - stage_width * 2 + MaxThreads, Cycles(0), _cpu, - params); - resources.push_back(instUnit); - - resources.push_back(new DecodeUnit("decode_unit", Decode, - stage_width, Cycles(0), _cpu, - params)); - - resources.push_back(new BranchPredictor("branch_predictor", BPred, - stage_width, Cycles(0), - _cpu, params)); - - resources.push_back(new InstBuffer("fetch_buffer_t0", FetchBuff, 4, - Cycles(0), _cpu, params)); - - resources.push_back(new UseDefUnit("regfile_manager", RegManager, - stage_width * 3, Cycles(0), _cpu, - params)); - - resources.push_back(new AGENUnit("agen_unit", AGEN, - stage_width, Cycles(0), _cpu, - params)); - - resources.push_back(new ExecutionUnit("execution_unit", ExecUnit, - stage_width, Cycles(0), _cpu, - params)); - - resources.push_back(new MultDivUnit("mult_div_unit", MDU, - stage_width * 2, Cycles(0), - _cpu, params)); - - // Keep track of the data load/store unit so we can easily provide - // a pointer to it in the CPU. - dataUnit = new CacheUnit("dcache_port", DCache, - stage_width * 2 + MaxThreads, Cycles(0), _cpu, - params); - resources.push_back(dataUnit); - - gradObjects.push_back(BPred); - resources.push_back(new GraduationUnit("graduation_unit", Grad, - stage_width, Cycles(0), _cpu, - params)); - - resources.push_back(new InstBuffer("fetch_buffer_t1", FetchBuff2, 4, - Cycles(0), _cpu, params)); - -} - -ResourcePool::~ResourcePool() -{ - cout << "Deleting resources ..." << endl; - - for (int i=0; i < resources.size(); i++) { - DPRINTF(Resource, "Deleting resource: %s.\n", resources[i]->name()); - - delete resources[i]; - } -} - - -void -ResourcePool::init() -{ - for (int i=0; i < resources.size(); i++) { - DPRINTF(Resource, "Initializing resource: %s.\n", - resources[i]->name()); - - resources[i]->init(); - } -} - -string -ResourcePool::name() -{ - return cpu->name() + ".ResourcePool"; -} - -void -ResourcePool::print() -{ - for (int i=0; i < resources.size(); i++) { - DPRINTF(InOrderDynInst, "Res:%i %s\n", - i, resources[i]->name()); - } - -} - - -void -ResourcePool::regStats() -{ - DPRINTF(Resource, "Registering Stats Throughout Resource Pool.\n"); - - int num_resources = resources.size(); - - for (int idx = 0; idx < num_resources; idx++) { - resources[idx]->regStats(); - } -} - -unsigned -ResourcePool::getResIdx(const ThePipeline::ResourceId &res_id) -{ - int num_resources = resources.size(); - - for (int idx = 0; idx < num_resources; idx++) { - if (resources[idx]->getId() == res_id) - return idx; - } - - // todo: change return value to int and return a -1 here - // maybe even have enumerated type - // panic for now... - panic("Can't find resource idx for: %i\n", res_id); - - return 0; -} - -ResReqPtr -ResourcePool::request(int res_idx, DynInstPtr inst) -{ - //Make Sure This is a valid resource ID - assert(res_idx >= 0 && res_idx < resources.size()); - - return resources[res_idx]->request(inst); -} - -void -ResourcePool::squash(DynInstPtr inst, int res_idx, InstSeqNum done_seq_num, - ThreadID tid) -{ - resources[res_idx]->squash(inst, ThePipeline::NumStages-1, done_seq_num, - tid); -} - -void -ResourcePool::trap(const Fault &fault, ThreadID tid, DynInstPtr inst) -{ - DPRINTF(Resource, "[tid:%i] Broadcasting Trap to all " - "resources.\n", tid); - - int num_resources = resources.size(); - - for (int idx = 0; idx < num_resources; idx++) - resources[idx]->trap(fault, tid, inst); -} - -int -ResourcePool::slotsAvail(int res_idx) -{ - return resources[res_idx]->slotsAvail(); -} - -int -ResourcePool::slotsInUse(int res_idx) -{ - return resources[res_idx]->slotsInUse(); -} - -//@todo: split this function and call this version schedulePoolEvent -// and use this scheduleEvent for scheduling a specific event on -// a resource -//@todo: For arguments that arent being used in a ResPoolEvent, a dummyParam -// or some typedef can be used to signify what's important info -// to the event construction -void -ResourcePool::scheduleEvent(InOrderCPU::CPUEventType e_type, DynInstPtr inst, - Cycles delay, int res_idx, ThreadID tid) -{ - assert(delay >= 0); - - Tick when = cpu->clockEdge(delay); - - switch ((int)e_type) - { - case ResourcePool::InstGraduated: - { - DPRINTF(Resource, "Scheduling Inst-Graduated Resource Pool " - "Event for tick %i.\n", curTick() + delay); - ResPoolEventPri grad_pri = ResGrad_Pri; - ResPoolEvent *res_pool_event = - new ResPoolEvent(this, - e_type, - inst, - inst->squashingStage, - inst->seqNum, - inst->readTid(), - grad_pri); - cpu->schedule(res_pool_event, when); - } - break; - - case ResourcePool::SquashAll: - { - DPRINTF(Resource, "Scheduling Squash Resource Pool Event for " - "tick %i.\n", curTick() + delay); - ResPoolEventPri squash_pri = ResSquash_Pri; - ResPoolEvent *res_pool_event = - new ResPoolEvent(this, - e_type, - inst, - inst->squashingStage, - inst->squashSeqNum, - inst->readTid(), - squash_pri); - cpu->schedule(res_pool_event, when); - } - break; - - case ResourcePool::UpdateAfterContextSwitch: - { - DPRINTF(Resource, "Scheduling UpdatePC Resource Pool Event " - "for tick %i.\n", - curTick() + delay); - ResPoolEvent *res_pool_event = new ResPoolEvent(this, - e_type, - inst, - inst->squashingStage, - inst->seqNum, - inst->readTid()); - cpu->schedule(res_pool_event, when); - } - break; - - default: - DPRINTF(Resource, "Ignoring Unrecognized CPU Event (%s).\n", - InOrderCPU::eventNames[e_type]); - } -} - -void -ResourcePool::unscheduleEvent(int res_idx, DynInstPtr inst) -{ - resources[res_idx]->unscheduleEvent(inst); -} - -void -ResourcePool::squashAll(DynInstPtr inst, int stage_num, - InstSeqNum done_seq_num, ThreadID tid) -{ - DPRINTF(Resource, "[tid:%i] Broadcasting Squash All Event " - " starting w/stage %i for all instructions above [sn:%i].\n", - tid, stage_num, done_seq_num); - - int num_resources = resources.size(); - - for (int idx = 0; idx < num_resources; idx++) { - resources[idx]->squash(inst, stage_num, done_seq_num, tid); - } -} - -void -ResourcePool::squashDueToMemStall(DynInstPtr inst, int stage_num, - InstSeqNum done_seq_num, ThreadID tid) -{ - DPRINTF(Resource, "[tid:%i] Broadcasting SquashDueToMemStall Event" - " starting w/stage %i for all instructions above [sn:%i].\n", - tid, stage_num, done_seq_num); - - int num_resources = resources.size(); - - for (int idx = 0; idx < num_resources; idx++) { - resources[idx]->squashDueToMemStall(inst, stage_num, done_seq_num, - tid); - } -} - -void -ResourcePool::activateThread(ThreadID tid) -{ - bool do_activate = cpu->threadModel != InOrderCPU::SwitchOnCacheMiss || - cpu->numActiveThreads() < 1 || - cpu->activeThreadId() == tid; - - - if (do_activate) { - DPRINTF(Resource, "[tid:%i] Broadcasting Thread Activation to all " - "resources.\n", tid); - - int num_resources = resources.size(); - - for (int idx = 0; idx < num_resources; idx++) { - resources[idx]->activateThread(tid); - } - } else { - DPRINTF(Resource, "[tid:%i] Ignoring Thread Activation to all " - "resources.\n", tid); - } -} - -void -ResourcePool::deactivateThread(ThreadID tid) -{ - DPRINTF(Resource, "[tid:%i] Broadcasting Thread Deactivation to all " - "resources.\n", tid); - - int num_resources = resources.size(); - - for (int idx = 0; idx < num_resources; idx++) { - resources[idx]->deactivateThread(tid); - } -} - -void -ResourcePool::suspendThread(ThreadID tid) -{ - DPRINTF(Resource, "[tid:%i] Broadcasting Thread Suspension to all " - "resources.\n", tid); - - int num_resources = resources.size(); - - for (int idx = 0; idx < num_resources; idx++) { - resources[idx]->suspendThread(tid); - } -} - -void -ResourcePool::instGraduated(InstSeqNum seq_num, ThreadID tid) -{ - DPRINTF(Resource, "[tid:%i] Broadcasting [sn:%i] graduation to " - "appropriate resources.\n", tid, seq_num); - - int num_resources = gradObjects.size(); - - for (int idx = 0; idx < num_resources; idx++) { - resources[gradObjects[idx]]->instGraduated(seq_num, tid); - } -} - -void -ResourcePool::updateAfterContextSwitch(DynInstPtr inst, ThreadID tid) -{ - DPRINTF(Resource, "[tid:%i] Broadcasting Update PC to all resources.\n", - tid); - - int num_resources = resources.size(); - - for (int idx = 0; idx < num_resources; idx++) { - resources[idx]->updateAfterContextSwitch(inst, tid); - } -} - -ResourcePool::ResPoolEvent::ResPoolEvent(ResourcePool *_resPool, - InOrderCPU::CPUEventType e_type, - DynInstPtr _inst, - int stage_num, - InstSeqNum seq_num, - ThreadID _tid, - ResPoolEventPri res_pri) - : Event(res_pri), resPool(_resPool), - eventType(e_type), inst(_inst), seqNum(seq_num), - stageNum(stage_num), tid(_tid) -{ } - - -void -ResourcePool::ResPoolEvent::process() -{ - switch ((int)eventType) - { - - case ResourcePool::InstGraduated: - resPool->instGraduated(seqNum, tid); - break; - - case ResourcePool::SquashAll: - resPool->squashAll(inst, stageNum, seqNum, tid); - break; - - case ResourcePool::UpdateAfterContextSwitch: - resPool->updateAfterContextSwitch(inst, tid); - break; - - default: - fatal("Unrecognized Event Type"); - } - - resPool->cpu->cpuEventRemoveList.push(this); -} - - -const char * -ResourcePool::ResPoolEvent::description() const -{ - return "Resource Pool event"; -} - -/** Schedule resource event, regardless of its current state. */ -void -ResourcePool::ResPoolEvent::scheduleEvent(Cycles delay) -{ - InOrderCPU *cpu = resPool->cpu; - assert(!scheduled() || squashed()); - cpu->reschedule(this, cpu->clockEdge(delay), true); -} - -/** Unschedule resource event, regardless of its current state. */ -void -ResourcePool::ResPoolEvent::unscheduleEvent() -{ - if (scheduled()) - squash(); -} |