summaryrefslogtreecommitdiff
path: root/cpu/beta_cpu/commit_impl.hh
diff options
context:
space:
mode:
authorNathan Binkert <binkertn@umich.edu>2005-06-04 20:50:10 -0400
committerNathan Binkert <binkertn@umich.edu>2005-06-04 20:50:10 -0400
commit13c005a8af79a8481879ce099b45a1f98faae165 (patch)
tree3125dfe10539270433981b39119dd727295c255c /cpu/beta_cpu/commit_impl.hh
parent5a94e6f2cc6ed8480063da68d20274ced2930925 (diff)
downloadgem5-13c005a8af79a8481879ce099b45a1f98faae165.tar.xz
shuffle files around for new directory structure
--HG-- rename : cpu/base_cpu.cc => cpu/base.cc rename : cpu/base_cpu.hh => cpu/base.hh rename : cpu/beta_cpu/2bit_local_pred.cc => cpu/o3/2bit_local_pred.cc rename : cpu/beta_cpu/2bit_local_pred.hh => cpu/o3/2bit_local_pred.hh rename : cpu/beta_cpu/alpha_full_cpu.cc => cpu/o3/alpha_cpu.cc rename : cpu/beta_cpu/alpha_full_cpu.hh => cpu/o3/alpha_cpu.hh rename : cpu/beta_cpu/alpha_full_cpu_builder.cc => cpu/o3/alpha_cpu_builder.cc rename : cpu/beta_cpu/alpha_full_cpu_impl.hh => cpu/o3/alpha_cpu_impl.hh rename : cpu/beta_cpu/alpha_dyn_inst.cc => cpu/o3/alpha_dyn_inst.cc rename : cpu/beta_cpu/alpha_dyn_inst.hh => cpu/o3/alpha_dyn_inst.hh rename : cpu/beta_cpu/alpha_dyn_inst_impl.hh => cpu/o3/alpha_dyn_inst_impl.hh rename : cpu/beta_cpu/alpha_impl.hh => cpu/o3/alpha_impl.hh rename : cpu/beta_cpu/alpha_params.hh => cpu/o3/alpha_params.hh rename : cpu/beta_cpu/bpred_unit.cc => cpu/o3/bpred_unit.cc rename : cpu/beta_cpu/bpred_unit.hh => cpu/o3/bpred_unit.hh rename : cpu/beta_cpu/bpred_unit_impl.hh => cpu/o3/bpred_unit_impl.hh rename : cpu/beta_cpu/btb.cc => cpu/o3/btb.cc rename : cpu/beta_cpu/btb.hh => cpu/o3/btb.hh rename : cpu/beta_cpu/comm.hh => cpu/o3/comm.hh rename : cpu/beta_cpu/commit.cc => cpu/o3/commit.cc rename : cpu/beta_cpu/commit.hh => cpu/o3/commit.hh rename : cpu/beta_cpu/commit_impl.hh => cpu/o3/commit_impl.hh rename : cpu/beta_cpu/full_cpu.cc => cpu/o3/cpu.cc rename : cpu/beta_cpu/full_cpu.hh => cpu/o3/cpu.hh rename : cpu/beta_cpu/cpu_policy.hh => cpu/o3/cpu_policy.hh rename : cpu/beta_cpu/decode.cc => cpu/o3/decode.cc rename : cpu/beta_cpu/decode.hh => cpu/o3/decode.hh rename : cpu/beta_cpu/decode_impl.hh => cpu/o3/decode_impl.hh rename : cpu/beta_cpu/fetch.cc => cpu/o3/fetch.cc rename : cpu/beta_cpu/fetch.hh => cpu/o3/fetch.hh rename : cpu/beta_cpu/fetch_impl.hh => cpu/o3/fetch_impl.hh rename : cpu/beta_cpu/free_list.cc => cpu/o3/free_list.cc rename : cpu/beta_cpu/free_list.hh => cpu/o3/free_list.hh rename : cpu/beta_cpu/iew.cc => cpu/o3/iew.cc rename : cpu/beta_cpu/iew.hh => cpu/o3/iew.hh rename : cpu/beta_cpu/iew_impl.hh => cpu/o3/iew_impl.hh rename : cpu/beta_cpu/inst_queue.cc => cpu/o3/inst_queue.cc rename : cpu/beta_cpu/inst_queue.hh => cpu/o3/inst_queue.hh rename : cpu/beta_cpu/inst_queue_impl.hh => cpu/o3/inst_queue_impl.hh rename : cpu/beta_cpu/mem_dep_unit.cc => cpu/o3/mem_dep_unit.cc rename : cpu/beta_cpu/mem_dep_unit.hh => cpu/o3/mem_dep_unit.hh rename : cpu/beta_cpu/mem_dep_unit_impl.hh => cpu/o3/mem_dep_unit_impl.hh rename : cpu/beta_cpu/ras.cc => cpu/o3/ras.cc rename : cpu/beta_cpu/ras.hh => cpu/o3/ras.hh rename : cpu/beta_cpu/regfile.hh => cpu/o3/regfile.hh rename : cpu/beta_cpu/rename.cc => cpu/o3/rename.cc rename : cpu/beta_cpu/rename.hh => cpu/o3/rename.hh rename : cpu/beta_cpu/rename_impl.hh => cpu/o3/rename_impl.hh rename : cpu/beta_cpu/rename_map.cc => cpu/o3/rename_map.cc rename : cpu/beta_cpu/rename_map.hh => cpu/o3/rename_map.hh rename : cpu/beta_cpu/rob.cc => cpu/o3/rob.cc rename : cpu/beta_cpu/rob.hh => cpu/o3/rob.hh rename : cpu/beta_cpu/rob_impl.hh => cpu/o3/rob_impl.hh rename : cpu/beta_cpu/sat_counter.cc => cpu/o3/sat_counter.cc rename : cpu/beta_cpu/sat_counter.hh => cpu/o3/sat_counter.hh rename : cpu/beta_cpu/store_set.cc => cpu/o3/store_set.cc rename : cpu/beta_cpu/store_set.hh => cpu/o3/store_set.hh rename : cpu/beta_cpu/tournament_pred.cc => cpu/o3/tournament_pred.cc rename : cpu/beta_cpu/tournament_pred.hh => cpu/o3/tournament_pred.hh rename : cpu/ooo_cpu/ooo_cpu.cc => cpu/ozone/cpu.cc rename : cpu/ooo_cpu/ooo_cpu.hh => cpu/ozone/cpu.hh rename : cpu/ooo_cpu/ooo_impl.hh => cpu/ozone/cpu_impl.hh rename : cpu/ooo_cpu/ea_list.cc => cpu/ozone/ea_list.cc rename : cpu/ooo_cpu/ea_list.hh => cpu/ozone/ea_list.hh rename : cpu/simple_cpu/simple_cpu.cc => cpu/simple/cpu.cc rename : cpu/simple_cpu/simple_cpu.hh => cpu/simple/cpu.hh rename : cpu/full_cpu/smt.hh => cpu/smt.hh rename : cpu/full_cpu/op_class.hh => encumbered/cpu/full/op_class.hh extra : convert_revision : c4a891d8d6d3e0e9e5ea56be47d851da44d8c032
Diffstat (limited to 'cpu/beta_cpu/commit_impl.hh')
-rw-r--r--cpu/beta_cpu/commit_impl.hh502
1 files changed, 0 insertions, 502 deletions
diff --git a/cpu/beta_cpu/commit_impl.hh b/cpu/beta_cpu/commit_impl.hh
deleted file mode 100644
index 22ec22c70..000000000
--- a/cpu/beta_cpu/commit_impl.hh
+++ /dev/null
@@ -1,502 +0,0 @@
-/*
- * Copyright (c) 2004-2005 The Regents of The University of Michigan
- * 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.
- */
-
-#include "base/timebuf.hh"
-#include "cpu/beta_cpu/commit.hh"
-#include "cpu/exetrace.hh"
-
-template <class Impl>
-SimpleCommit<Impl>::SimpleCommit(Params &params)
- : dcacheInterface(params.dcacheInterface),
- iewToCommitDelay(params.iewToCommitDelay),
- renameToROBDelay(params.renameToROBDelay),
- renameWidth(params.renameWidth),
- iewWidth(params.executeWidth),
- commitWidth(params.commitWidth)
-{
- _status = Idle;
-}
-
-template <class Impl>
-void
-SimpleCommit<Impl>::regStats()
-{
- commitCommittedInsts
- .name(name() + ".commitCommittedInsts")
- .desc("The number of committed instructions")
- .prereq(commitCommittedInsts);
- commitSquashedInsts
- .name(name() + ".commitSquashedInsts")
- .desc("The number of squashed insts skipped by commit")
- .prereq(commitSquashedInsts);
- commitSquashEvents
- .name(name() + ".commitSquashEvents")
- .desc("The number of times commit is told to squash")
- .prereq(commitSquashEvents);
- commitNonSpecStalls
- .name(name() + ".commitNonSpecStalls")
- .desc("The number of times commit has been forced to stall to "
- "communicate backwards")
- .prereq(commitNonSpecStalls);
- commitCommittedBranches
- .name(name() + ".commitCommittedBranches")
- .desc("The number of committed branches")
- .prereq(commitCommittedBranches);
- commitCommittedLoads
- .name(name() + ".commitCommittedLoads")
- .desc("The number of committed loads")
- .prereq(commitCommittedLoads);
- commitCommittedMemRefs
- .name(name() + ".commitCommittedMemRefs")
- .desc("The number of committed memory references")
- .prereq(commitCommittedMemRefs);
- branchMispredicts
- .name(name() + ".branchMispredicts")
- .desc("The number of times a branch was mispredicted")
- .prereq(branchMispredicts);
- n_committed_dist
- .init(0,commitWidth,1)
- .name(name() + ".COM:committed_per_cycle")
- .desc("Number of insts commited each cycle")
- .flags(Stats::pdf)
- ;
-}
-
-template <class Impl>
-void
-SimpleCommit<Impl>::setCPU(FullCPU *cpu_ptr)
-{
- DPRINTF(Commit, "Commit: Setting CPU pointer.\n");
- cpu = cpu_ptr;
-}
-
-template <class Impl>
-void
-SimpleCommit<Impl>::setTimeBuffer(TimeBuffer<TimeStruct> *tb_ptr)
-{
- DPRINTF(Commit, "Commit: Setting time buffer pointer.\n");
- timeBuffer = tb_ptr;
-
- // Setup wire to send information back to IEW.
- toIEW = timeBuffer->getWire(0);
-
- // Setup wire to read data from IEW (for the ROB).
- robInfoFromIEW = timeBuffer->getWire(-iewToCommitDelay);
-}
-
-template <class Impl>
-void
-SimpleCommit<Impl>::setRenameQueue(TimeBuffer<RenameStruct> *rq_ptr)
-{
- DPRINTF(Commit, "Commit: Setting rename queue pointer.\n");
- renameQueue = rq_ptr;
-
- // Setup wire to get instructions from rename (for the ROB).
- fromRename = renameQueue->getWire(-renameToROBDelay);
-}
-
-template <class Impl>
-void
-SimpleCommit<Impl>::setIEWQueue(TimeBuffer<IEWStruct> *iq_ptr)
-{
- DPRINTF(Commit, "Commit: Setting IEW queue pointer.\n");
- iewQueue = iq_ptr;
-
- // Setup wire to get instructions from IEW.
- fromIEW = iewQueue->getWire(-iewToCommitDelay);
-}
-
-template <class Impl>
-void
-SimpleCommit<Impl>::setROB(ROB *rob_ptr)
-{
- DPRINTF(Commit, "Commit: Setting ROB pointer.\n");
- rob = rob_ptr;
-}
-
-template <class Impl>
-void
-SimpleCommit<Impl>::tick()
-{
- // If the ROB is currently in its squash sequence, then continue
- // to squash. In this case, commit does not do anything. Otherwise
- // run commit.
- if (_status == ROBSquashing) {
- if (rob->isDoneSquashing()) {
- _status = Running;
- } else {
- rob->doSquash();
-
- // Send back sequence number of tail of ROB, so other stages
- // can squash younger instructions. Note that really the only
- // stage that this is important for is the IEW stage; other
- // stages can just clear all their state as long as selective
- // replay isn't used.
- toIEW->commitInfo.doneSeqNum = rob->readTailSeqNum();
- toIEW->commitInfo.robSquashing = true;
- }
- } else {
- commit();
- }
-
- markCompletedInsts();
-
- // Writeback number of free ROB entries here.
- DPRINTF(Commit, "Commit: ROB has %d free entries.\n",
- rob->numFreeEntries());
- toIEW->commitInfo.freeROBEntries = rob->numFreeEntries();
-}
-
-template <class Impl>
-void
-SimpleCommit<Impl>::commit()
-{
- //////////////////////////////////////
- // Check for interrupts
- //////////////////////////////////////
-
- // Process interrupts if interrupts are enabled and not in PAL mode.
- // Take the PC from commit and write it to the IPR, then squash. The
- // interrupt completing will take care of restoring the PC from that value
- // in the IPR. Look at IPR[EXC_ADDR];
- // hwrei() is what resets the PC to the place where instruction execution
- // beings again.
-#ifdef FULL_SYSTEM
- if (//checkInterrupts &&
- cpu->check_interrupts() &&
- !cpu->inPalMode(readCommitPC())) {
- // Will need to squash all instructions currently in flight and have
- // the interrupt handler restart at the last non-committed inst.
- // Most of that can be handled through the trap() function. The
- // processInterrupts() function really just checks for interrupts
- // and then calls trap() if there is an interrupt present.
-
- // CPU will handle implementation of the interrupt.
- cpu->processInterrupts();
- }
-#endif // FULL_SYSTEM
-
- ////////////////////////////////////
- // Check for squash signal, handle that first
- ////////////////////////////////////
-
- // Want to mainly check if the IEW stage is telling the ROB to squash.
- // Should I also check if the commit stage is telling the ROB to squah?
- // This might be necessary to keep the same timing between the IQ and
- // the ROB...
- if (fromIEW->squash) {
- DPRINTF(Commit, "Commit: Squashing instructions in the ROB.\n");
-
- _status = ROBSquashing;
-
- InstSeqNum squashed_inst = fromIEW->squashedSeqNum;
-
- rob->squash(squashed_inst);
-
- // Send back the sequence number of the squashed instruction.
- toIEW->commitInfo.doneSeqNum = squashed_inst;
-
- // Send back the squash signal to tell stages that they should squash.
- toIEW->commitInfo.squash = true;
-
- // Send back the rob squashing signal so other stages know that the
- // ROB is in the process of squashing.
- toIEW->commitInfo.robSquashing = true;
-
- toIEW->commitInfo.branchMispredict = fromIEW->branchMispredict;
-
- toIEW->commitInfo.branchTaken = fromIEW->branchTaken;
-
- toIEW->commitInfo.nextPC = fromIEW->nextPC;
-
- toIEW->commitInfo.mispredPC = fromIEW->mispredPC;
-
- if (toIEW->commitInfo.branchMispredict) {
- ++branchMispredicts;
- }
- }
-
- if (_status != ROBSquashing) {
- // If we're not currently squashing, then get instructions.
- getInsts();
-
- // Try to commit any instructions.
- commitInsts();
- }
-
- // If the ROB is empty, we can set this stage to idle. Use this
- // in the future when the Idle status will actually be utilized.
-#if 0
- if (rob->isEmpty()) {
- DPRINTF(Commit, "Commit: ROB is empty. Status changed to idle.\n");
- _status = Idle;
- // Schedule an event so that commit will actually wake up
- // once something gets put in the ROB.
- }
-#endif
-}
-
-// Loop that goes through as many instructions in the ROB as possible and
-// tries to commit them. The actual work for committing is done by the
-// commitHead() function.
-template <class Impl>
-void
-SimpleCommit<Impl>::commitInsts()
-{
- ////////////////////////////////////
- // Handle commit
- // Note that commit will be handled prior to the ROB so that the ROB
- // only tries to commit instructions it has in this current cycle, and
- // not instructions it is writing in during this cycle.
- // Can't commit and squash things at the same time...
- ////////////////////////////////////
-
- if (rob->isEmpty())
- return;
-
- DynInstPtr head_inst = rob->readHeadInst();
-
- unsigned num_committed = 0;
-
- // Commit as many instructions as possible until the commit bandwidth
- // limit is reached, or it becomes impossible to commit any more.
- while (!rob->isEmpty() &&
- head_inst->readyToCommit() &&
- num_committed < commitWidth)
- {
- DPRINTF(Commit, "Commit: Trying to commit head instruction.\n");
-
- // If the head instruction is squashed, it is ready to retire at any
- // time. However, we need to avoid updating any other state
- // incorrectly if it's already been squashed.
- if (head_inst->isSquashed()) {
-
- DPRINTF(Commit, "Commit: Retiring squashed instruction from "
- "ROB.\n");
-
- // Tell ROB to retire head instruction. This retires the head
- // inst in the ROB without affecting any other stages.
- rob->retireHead();
-
- ++commitSquashedInsts;
-
- } else {
- // Increment the total number of non-speculative instructions
- // executed.
- // Hack for now: it really shouldn't happen until after the
- // commit is deemed to be successful, but this count is needed
- // for syscalls.
- cpu->funcExeInst++;
-
- // Try to commit the head instruction.
- bool commit_success = commitHead(head_inst, num_committed);
-
- // Update what instruction we are looking at if the commit worked.
- if (commit_success) {
- ++num_committed;
-
- // Send back which instruction has been committed.
- // @todo: Update this later when a wider pipeline is used.
- // Hmm, can't really give a pointer here...perhaps the
- // sequence number instead (copy).
- toIEW->commitInfo.doneSeqNum = head_inst->seqNum;
-
- ++commitCommittedInsts;
-
- if (!head_inst->isNop()) {
- cpu->instDone();
- }
- } else {
- break;
- }
- }
-
- // Update the pointer to read the next instruction in the ROB.
- head_inst = rob->readHeadInst();
- }
-
- DPRINTF(CommitRate, "%i\n", num_committed);
- n_committed_dist.sample(num_committed);
-}
-
-template <class Impl>
-bool
-SimpleCommit<Impl>::commitHead(DynInstPtr &head_inst, unsigned inst_num)
-{
- // Make sure instruction is valid
- assert(head_inst);
-
- // If the instruction is not executed yet, then it is a non-speculative
- // or store inst. Signal backwards that it should be executed.
- if (!head_inst->isExecuted()) {
- // Keep this number correct. We have not yet actually executed
- // and committed this instruction.
- cpu->funcExeInst--;
-
- if (head_inst->isNonSpeculative()) {
- DPRINTF(Commit, "Commit: Encountered a store or non-speculative "
- "instruction at the head of the ROB, PC %#x.\n",
- head_inst->readPC());
-
- toIEW->commitInfo.nonSpecSeqNum = head_inst->seqNum;
-
- // Change the instruction so it won't try to commit again until
- // it is executed.
- head_inst->clearCanCommit();
-
- ++commitNonSpecStalls;
-
- return false;
- } else {
- panic("Commit: Trying to commit un-executed instruction "
- "of unknown type!\n");
- }
- }
-
- // Now check if it's one of the special trap or barrier or
- // serializing instructions.
- if (head_inst->isThreadSync() ||
- head_inst->isSerializing() ||
- head_inst->isMemBarrier() ||
- head_inst->isWriteBarrier() )
- {
- // Not handled for now. Mem barriers and write barriers are safe
- // to simply let commit as memory accesses only happen once they
- // reach the head of commit. Not sure about the other two.
- panic("Serializing or barrier instructions"
- " are not handled yet.\n");
- }
-
- // Check if the instruction caused a fault. If so, trap.
- Fault inst_fault = head_inst->getFault();
-
- if (inst_fault != No_Fault && inst_fault != Fake_Mem_Fault) {
- if (!head_inst->isNop()) {
-#ifdef FULL_SYSTEM
- cpu->trap(inst_fault);
-#else // !FULL_SYSTEM
- panic("fault (%d) detected @ PC %08p", inst_fault,
- head_inst->PC);
-#endif // FULL_SYSTEM
- }
- }
-
- // Check if we're really ready to commit. If not then return false.
- // I'm pretty sure all instructions should be able to commit if they've
- // reached this far. For now leave this in as a check.
- if (!rob->isHeadReady()) {
- panic("Commit: Unable to commit head instruction!\n");
- return false;
- }
-
- // If it's a branch, then send back branch prediction update info
- // to the fetch stage.
- // This should be handled in the iew stage if a mispredict happens...
-
- if (head_inst->isControl()) {
-
-#if 0
- toIEW->nextPC = head_inst->readPC();
- //Maybe switch over to BTB incorrect.
- toIEW->btbMissed = head_inst->btbMiss();
- toIEW->target = head_inst->nextPC;
- //Maybe also include global history information.
- //This simple version will have no branch prediction however.
-#endif
-
- ++commitCommittedBranches;
- }
-
- // Now that the instruction is going to be committed, finalize its
- // trace data.
- if (head_inst->traceData) {
- head_inst->traceData->finalize();
- }
-
- //Finally clear the head ROB entry.
- rob->retireHead();
-
- // Return true to indicate that we have committed an instruction.
- return true;
-}
-
-template <class Impl>
-void
-SimpleCommit<Impl>::getInsts()
-{
- //////////////////////////////////////
- // Handle ROB functions
- //////////////////////////////////////
-
- // Read any issued instructions and place them into the ROB. Do this
- // prior to squashing to avoid having instructions in the ROB that
- // don't get squashed properly.
- int insts_to_process = min((int)renameWidth, fromRename->size);
-
- for (int inst_num = 0;
- inst_num < insts_to_process;
- ++inst_num)
- {
- if (!fromRename->insts[inst_num]->isSquashed()) {
- DPRINTF(Commit, "Commit: Inserting PC %#x into ROB.\n",
- fromRename->insts[inst_num]->readPC());
- rob->insertInst(fromRename->insts[inst_num]);
- } else {
- DPRINTF(Commit, "Commit: Instruction %i PC %#x was "
- "squashed, skipping.\n",
- fromRename->insts[inst_num]->seqNum,
- fromRename->insts[inst_num]->readPC());
- }
- }
-}
-
-template <class Impl>
-void
-SimpleCommit<Impl>::markCompletedInsts()
-{
- // Grab completed insts out of the IEW instruction queue, and mark
- // instructions completed within the ROB.
- for (int inst_num = 0;
- inst_num < fromIEW->size && fromIEW->insts[inst_num];
- ++inst_num)
- {
- DPRINTF(Commit, "Commit: Marking PC %#x, SN %i ready within ROB.\n",
- fromIEW->insts[inst_num]->readPC(),
- fromIEW->insts[inst_num]->seqNum);
-
- // Mark the instruction as ready to commit.
- fromIEW->insts[inst_num]->setCanCommit();
- }
-}
-
-template <class Impl>
-uint64_t
-SimpleCommit<Impl>::readCommitPC()
-{
- return rob->readHeadPC();
-}