cpu: Move MaxWidth and MaxThreads from O3CPUImpl to cpu/o3/limits.hh.

Change-Id: I2534661bbdbd8537129403f97c8fb767a2eb85d6
Reviewed-on: https://gem5-review.googlesource.com/c/public/gem5/+/42097
Reviewed-by: Giacomo Travaglini <giacomo.travaglini@arm.com>
Reviewed-by: Matthew Poremba <matthew.poremba@amd.com>
Maintainer: Gabe Black <gabe.black@gmail.com>
Tested-by: kokoro <noreply+kokoro@google.com>
This commit is contained in:
Gabe Black
2021-03-01 16:45:30 -08:00
parent 306ed368c5
commit 729ab6d4d8
23 changed files with 195 additions and 147 deletions

View File

@@ -47,6 +47,7 @@
#include "arch/types.hh"
#include "base/types.hh"
#include "cpu/inst_seq.hh"
#include "cpu/o3/limits.hh"
#include "sim/faults.hh"
/** Struct that defines the information passed from fetch to decode. */
@@ -57,7 +58,7 @@ struct DefaultFetchDefaultDecode
int size;
DynInstPtr insts[Impl::MaxWidth];
DynInstPtr insts[O3MaxWidth];
Fault fetchFault;
InstSeqNum fetchFaultSN;
bool clearFetchFault;
@@ -71,7 +72,7 @@ struct DefaultDecodeDefaultRename
int size;
DynInstPtr insts[Impl::MaxWidth];
DynInstPtr insts[O3MaxWidth];
};
/** Struct that defines the information passed from rename to IEW. */
@@ -82,7 +83,7 @@ struct DefaultRenameDefaultIEW
int size;
DynInstPtr insts[Impl::MaxWidth];
DynInstPtr insts[O3MaxWidth];
};
/** Struct that defines the information passed from IEW to commit. */
@@ -93,16 +94,16 @@ struct DefaultIEWDefaultCommit
int size;
DynInstPtr insts[Impl::MaxWidth];
DynInstPtr mispredictInst[Impl::MaxThreads];
Addr mispredPC[Impl::MaxThreads];
InstSeqNum squashedSeqNum[Impl::MaxThreads];
TheISA::PCState pc[Impl::MaxThreads];
DynInstPtr insts[O3MaxWidth];
DynInstPtr mispredictInst[O3MaxThreads];
Addr mispredPC[O3MaxThreads];
InstSeqNum squashedSeqNum[O3MaxThreads];
TheISA::PCState pc[O3MaxThreads];
bool squash[Impl::MaxThreads];
bool branchMispredict[Impl::MaxThreads];
bool branchTaken[Impl::MaxThreads];
bool includeSquashInst[Impl::MaxThreads];
bool squash[O3MaxThreads];
bool branchMispredict[O3MaxThreads];
bool branchTaken[O3MaxThreads];
bool includeSquashInst[O3MaxThreads];
};
template<class Impl>
@@ -112,7 +113,7 @@ struct IssueStruct
int size;
DynInstPtr insts[Impl::MaxWidth];
DynInstPtr insts[O3MaxWidth];
};
/** Struct that defines all backwards communication. */
@@ -135,13 +136,13 @@ struct TimeBufStruct
bool branchTaken;
};
decodeComm decodeInfo[Impl::MaxThreads];
decodeComm decodeInfo[O3MaxThreads];
struct renameComm
{
};
renameComm renameInfo[Impl::MaxThreads];
renameComm renameInfo[O3MaxThreads];
struct iewComm
{
@@ -160,7 +161,7 @@ struct TimeBufStruct
bool usedLSQ;
};
iewComm iewInfo[Impl::MaxThreads];
iewComm iewInfo[O3MaxThreads];
struct commitComm
{
@@ -226,14 +227,14 @@ struct TimeBufStruct
};
commitComm commitInfo[Impl::MaxThreads];
commitComm commitInfo[O3MaxThreads];
bool decodeBlock[Impl::MaxThreads];
bool decodeUnblock[Impl::MaxThreads];
bool renameBlock[Impl::MaxThreads];
bool renameUnblock[Impl::MaxThreads];
bool iewBlock[Impl::MaxThreads];
bool iewUnblock[Impl::MaxThreads];
bool decodeBlock[O3MaxThreads];
bool decodeUnblock[O3MaxThreads];
bool renameBlock[O3MaxThreads];
bool renameUnblock[O3MaxThreads];
bool iewBlock[O3MaxThreads];
bool iewUnblock[O3MaxThreads];
};
#endif //__CPU_O3_COMM_HH__

View File

@@ -46,6 +46,7 @@
#include "base/statistics.hh"
#include "cpu/exetrace.hh"
#include "cpu/inst_seq.hh"
#include "cpu/o3/limits.hh"
#include "cpu/timebuf.hh"
#include "enums/CommitPolicy.hh"
#include "sim/probe/probe.hh"
@@ -125,7 +126,7 @@ class DefaultCommit
/** Next commit status, to be set at the end of the cycle. */
CommitStatus _nextStatus;
/** Per-thread status. */
ThreadStatus commitStatus[Impl::MaxThreads];
ThreadStatus commitStatus[O3MaxThreads];
/** Commit policy used in SMT mode. */
CommitPolicy commitPolicy;
@@ -175,7 +176,7 @@ class DefaultCommit
void setActiveThreads(std::list<ThreadID> *at_ptr);
/** Sets pointer to the commited state rename map. */
void setRenameMap(RenameMap rm_ptr[Impl::MaxThreads]);
void setRenameMap(RenameMap rm_ptr[O3MaxThreads]);
/** Sets pointer to the ROB. */
void setROB(ROB *rob_ptr);
@@ -374,13 +375,13 @@ class DefaultCommit
/** Records if the number of ROB entries has changed this cycle. If it has,
* then the number of free entries must be re-broadcast.
*/
bool changedROBNumEntries[Impl::MaxThreads];
bool changedROBNumEntries[O3MaxThreads];
/** Records if a thread has to squash this cycle due to a trap. */
bool trapSquash[Impl::MaxThreads];
bool trapSquash[O3MaxThreads];
/** Records if a thread has to squash this cycle due to an XC write. */
bool tcSquash[Impl::MaxThreads];
bool tcSquash[O3MaxThreads];
/**
* Instruction passed to squashAfter().
@@ -389,7 +390,7 @@ class DefaultCommit
* that caused a squash since this needs to be passed to the fetch
* stage once squashing starts.
*/
DynInstPtr squashAfterInst[Impl::MaxThreads];
DynInstPtr squashAfterInst[O3MaxThreads];
/** Priority List used for Commit Policy */
std::list<ThreadID> priority_list;
@@ -442,29 +443,29 @@ class DefaultCommit
/** The commit PC state of each thread. Refers to the instruction that
* is currently being processed/committed.
*/
TheISA::PCState pc[Impl::MaxThreads];
TheISA::PCState pc[O3MaxThreads];
/** The sequence number of the youngest valid instruction in the ROB. */
InstSeqNum youngestSeqNum[Impl::MaxThreads];
InstSeqNum youngestSeqNum[O3MaxThreads];
/** The sequence number of the last commited instruction. */
InstSeqNum lastCommitedSeqNum[Impl::MaxThreads];
InstSeqNum lastCommitedSeqNum[O3MaxThreads];
/** Records if there is a trap currently in flight. */
bool trapInFlight[Impl::MaxThreads];
bool trapInFlight[O3MaxThreads];
/** Records if there were any stores committed this cycle. */
bool committedStores[Impl::MaxThreads];
bool committedStores[O3MaxThreads];
/** Records if commit should check if the ROB is truly empty (see
commit_impl.hh). */
bool checkEmptyROB[Impl::MaxThreads];
bool checkEmptyROB[O3MaxThreads];
/** Pointer to the list of active threads. */
std::list<ThreadID> *activeThreads;
/** Rename map interface. */
RenameMap *renameMap[Impl::MaxThreads];
RenameMap *renameMap[O3MaxThreads];
/** True if last committed microop can be followed by an interrupt */
bool canHandleInterrupts;
@@ -479,8 +480,8 @@ class DefaultCommit
void updateComInstStats(const DynInstPtr &inst);
// HTM
int htmStarts[Impl::MaxThreads];
int htmStops[Impl::MaxThreads];
int htmStarts[O3MaxThreads];
int htmStops[O3MaxThreads];
struct CommitStats : public Stats::Group
{

View File

@@ -53,6 +53,7 @@
#include "cpu/exetrace.hh"
#include "cpu/null_static_inst.hh"
#include "cpu/o3/commit.hh"
#include "cpu/o3/limits.hh"
#include "cpu/o3/thread_state.hh"
#include "cpu/timebuf.hh"
#include "debug/Activity.hh"
@@ -93,10 +94,10 @@ DefaultCommit<Impl>::DefaultCommit(O3CPU *_cpu, const DerivO3CPUParams &params)
avoidQuiesceLiveLock(false),
stats(_cpu, this)
{
if (commitWidth > Impl::MaxWidth)
if (commitWidth > O3MaxWidth)
fatal("commitWidth (%d) is larger than compiled limit (%d),\n"
"\tincrease MaxWidth in src/cpu/o3/impl.hh\n",
commitWidth, static_cast<int>(Impl::MaxWidth));
"\tincrease O3MaxWidth in src/cpu/o3/limits.hh\n",
commitWidth, static_cast<int>(O3MaxWidth));
_status = Active;
_nextStatus = Inactive;
@@ -108,7 +109,7 @@ DefaultCommit<Impl>::DefaultCommit(O3CPU *_cpu, const DerivO3CPUParams &params)
}
}
for (ThreadID tid = 0; tid < Impl::MaxThreads; tid++) {
for (ThreadID tid = 0; tid < O3MaxThreads; tid++) {
commitStatus[tid] = Idle;
changedROBNumEntries[tid] = false;
trapSquash[tid] = false;

View File

@@ -47,6 +47,7 @@
#include "cpu/checker/cpu.hh"
#include "cpu/checker/thread_context.hh"
#include "cpu/o3/isa_specific.hh"
#include "cpu/o3/limits.hh"
#include "cpu/o3/thread_context.hh"
#include "cpu/simple_thread.hh"
#include "cpu/thread_context.hh"
@@ -187,10 +188,9 @@ FullO3CPU<Impl>::FullO3CPU(const DerivO3CPUParams &params)
} else {
active_threads = params.workload.size();
if (active_threads > Impl::MaxThreads) {
panic("Workload Size too large. Increase the 'MaxThreads' "
"constant in your O3CPU impl. file (e.g. o3/alpha/impl.hh) "
"or edit your workload size.");
if (active_threads > O3MaxThreads) {
panic("Workload Size too large. Increase the 'O3MaxThreads' "
"constant in cpu/o3/limits.hh or edit your workload size.");
}
}
@@ -450,7 +450,7 @@ FullO3CPUStats::FullO3CPUStats(FullO3CPU *cpu)
// Number of Instructions simulated
// --------------------------------
// Should probably be in Base CPU but need templated
// MaxThreads so put in here instead
// O3MaxThreads so put in here instead
committedInsts
.init(cpu->numThreads)
.flags(Stats::total);

View File

@@ -55,6 +55,7 @@
#include "config/the_isa.hh"
#include "cpu/o3/comm.hh"
#include "cpu/o3/cpu_policy.hh"
#include "cpu/o3/limits.hh"
#include "cpu/o3/scoreboard.hh"
#include "cpu/o3/thread_state.hh"
#include "cpu/activity.hh"
@@ -510,10 +511,10 @@ class FullO3CPU : public BaseO3CPU
typename CPUPolicy::FreeList freeList;
/** The rename map. */
typename CPUPolicy::RenameMap renameMap[Impl::MaxThreads];
typename CPUPolicy::RenameMap renameMap[O3MaxThreads];
/** The commit rename map. */
typename CPUPolicy::RenameMap commitRenameMap[Impl::MaxThreads];
typename CPUPolicy::RenameMap commitRenameMap[O3MaxThreads];
/** The re-order buffer. */
typename CPUPolicy::ROB rob;
@@ -611,7 +612,7 @@ class FullO3CPU : public BaseO3CPU
}
/** The global sequence number counter. */
InstSeqNum globalSeqNum;//[Impl::MaxThreads];
InstSeqNum globalSeqNum;//[O3MaxThreads];
/** Pointer to the checker, which can dynamically verify
* instruction results at run time. This can be set to NULL if it

View File

@@ -44,6 +44,7 @@
#include <queue>
#include "base/statistics.hh"
#include "cpu/o3/limits.hh"
#include "cpu/timebuf.hh"
struct DerivO3CPUParams;
@@ -95,7 +96,7 @@ class DefaultDecode
DecodeStatus _status;
/** Per-thread status. */
ThreadStatus decodeStatus[Impl::MaxThreads];
ThreadStatus decodeStatus[O3MaxThreads];
public:
/** DefaultDecode constructor. */
@@ -237,10 +238,10 @@ class DefaultDecode
typename TimeBuffer<FetchStruct>::wire fromFetch;
/** Queue of all instructions coming from fetch this cycle. */
std::queue<DynInstPtr> insts[Impl::MaxThreads];
std::queue<DynInstPtr> insts[O3MaxThreads];
/** Skid buffer between fetch and decode. */
std::queue<DynInstPtr> skidBuffer[Impl::MaxThreads];
std::queue<DynInstPtr> skidBuffer[O3MaxThreads];
/** Variable that tracks if decode has written to the time buffer this
* cycle. Used to tell CPU if there is activity this cycle.
@@ -254,7 +255,7 @@ class DefaultDecode
};
/** Tracks which stages are telling decode to stall. */
Stalls stalls[Impl::MaxThreads];
Stalls stalls[O3MaxThreads];
/** Rename to decode delay. */
Cycles renameToDecodeDelay;
@@ -284,16 +285,16 @@ class DefaultDecode
unsigned skidBufferMax;
/** SeqNum of Squashing Branch Delay Instruction (used for MIPS)*/
Addr bdelayDoneSeqNum[Impl::MaxThreads];
Addr bdelayDoneSeqNum[O3MaxThreads];
/** Instruction used for squashing branch (used for MIPS)*/
DynInstPtr squashInst[Impl::MaxThreads];
DynInstPtr squashInst[O3MaxThreads];
/** Tells when their is a pending delay slot inst. to send
* to rename. If there is, then wait squash after the next
* instruction (used for MIPS).
*/
bool squashAfterDelaySlot[Impl::MaxThreads];
bool squashAfterDelaySlot[O3MaxThreads];
struct DecodeStats : public Stats::Group
{

View File

@@ -44,8 +44,9 @@
#include "arch/types.hh"
#include "base/trace.hh"
#include "config/the_isa.hh"
#include "cpu/o3/decode.hh"
#include "cpu/inst_seq.hh"
#include "cpu/o3/decode.hh"
#include "cpu/o3/limits.hh"
#include "debug/Activity.hh"
#include "debug/Decode.hh"
#include "debug/O3PipeView.hh"
@@ -67,14 +68,14 @@ DefaultDecode<Impl>::DefaultDecode(O3CPU *_cpu, const DerivO3CPUParams &params)
numThreads(params.numThreads),
stats(_cpu)
{
if (decodeWidth > Impl::MaxWidth)
if (decodeWidth > O3MaxWidth)
fatal("decodeWidth (%d) is larger than compiled limit (%d),\n"
"\tincrease MaxWidth in src/cpu/o3/impl.hh\n",
decodeWidth, static_cast<int>(Impl::MaxWidth));
"\tincrease O3MaxWidth in src/cpu/o3/limits.hh\n",
decodeWidth, static_cast<int>(O3MaxWidth));
// @todo: Make into a parameter
skidBufferMax = (fetchToDecodeDelay + 1) * params.fetchWidth;
for (int tid = 0; tid < Impl::MaxThreads; tid++) {
for (int tid = 0; tid < O3MaxThreads; tid++) {
stalls[tid] = {false};
decodeStatus[tid] = Idle;
bdelayDoneSeqNum[tid] = 0;

View File

@@ -44,6 +44,7 @@
#include "arch/decoder.hh"
#include "base/statistics.hh"
#include "config/the_isa.hh"
#include "cpu/o3/limits.hh"
#include "cpu/pc_event.hh"
#include "cpu/pred/bpred_unit.hh"
#include "cpu/timebuf.hh"
@@ -200,7 +201,7 @@ class DefaultFetch
FetchStatus _status;
/** Per-thread status. */
ThreadStatus fetchStatus[Impl::MaxThreads];
ThreadStatus fetchStatus[O3MaxThreads];
/** Fetch policy. */
SMTFetchPolicy fetchPolicy;
@@ -372,7 +373,7 @@ class DefaultFetch
}
/** The decoder. */
TheISA::Decoder *decoder[Impl::MaxThreads];
TheISA::Decoder *decoder[O3MaxThreads];
RequestPort &getInstPort() { return icachePort; }
@@ -429,17 +430,17 @@ class DefaultFetch
/** BPredUnit. */
BPredUnit *branchPred;
TheISA::PCState pc[Impl::MaxThreads];
TheISA::PCState pc[O3MaxThreads];
Addr fetchOffset[Impl::MaxThreads];
Addr fetchOffset[O3MaxThreads];
StaticInstPtr macroop[Impl::MaxThreads];
StaticInstPtr macroop[O3MaxThreads];
/** Can the fetch stage redirect from an interrupt on this instruction? */
bool delayedCommit[Impl::MaxThreads];
bool delayedCommit[O3MaxThreads];
/** Memory request used to access cache. */
RequestPtr memReq[Impl::MaxThreads];
RequestPtr memReq[O3MaxThreads];
/** Variable that tracks if fetch has written to the time buffer this
* cycle. Used to tell CPU if there is activity this cycle.
@@ -457,7 +458,7 @@ class DefaultFetch
};
/** Tracks which stages are telling fetch to stall. */
Stalls stalls[Impl::MaxThreads];
Stalls stalls[O3MaxThreads];
/** Decode to fetch delay. */
Cycles decodeToFetchDelay;
@@ -498,25 +499,25 @@ class DefaultFetch
Addr fetchBufferMask;
/** The fetch data that is being fetched and buffered. */
uint8_t *fetchBuffer[Impl::MaxThreads];
uint8_t *fetchBuffer[O3MaxThreads];
/** The PC of the first instruction loaded into the fetch buffer. */
Addr fetchBufferPC[Impl::MaxThreads];
Addr fetchBufferPC[O3MaxThreads];
/** The size of the fetch queue in micro-ops */
unsigned fetchQueueSize;
/** Queue of fetched instructions. Per-thread to prevent HoL blocking. */
std::deque<DynInstPtr> fetchQueue[Impl::MaxThreads];
std::deque<DynInstPtr> fetchQueue[O3MaxThreads];
/** Whether or not the fetch buffer data is valid. */
bool fetchBufferValid[Impl::MaxThreads];
bool fetchBufferValid[O3MaxThreads];
/** Size of instructions. */
int instSize;
/** Icache stall statistics. */
Counter lastIcacheStall[Impl::MaxThreads];
Counter lastIcacheStall[O3MaxThreads];
/** List of Active Threads */
std::list<ThreadID> *activeThreads;
@@ -539,7 +540,7 @@ class DefaultFetch
IcachePort icachePort;
/** Set to true if a pipelined I-cache request should be issued. */
bool issuePipelinedIfetch[Impl::MaxThreads];
bool issuePipelinedIfetch[O3MaxThreads];
/** Event used to delay fault generation of translation faults */
FinishTranslationEvent finishTranslationEvent;

View File

@@ -58,6 +58,7 @@
#include "cpu/o3/cpu.hh"
#include "cpu/o3/fetch.hh"
#include "cpu/o3/isa_specific.hh"
#include "cpu/o3/limits.hh"
#include "debug/Activity.hh"
#include "debug/Drain.hh"
#include "debug/Fetch.hh"
@@ -93,14 +94,14 @@ DefaultFetch<Impl>::DefaultFetch(O3CPU *_cpu, const DerivO3CPUParams &params)
icachePort(this, _cpu),
finishTranslationEvent(this), fetchStats(_cpu, this)
{
if (numThreads > Impl::MaxThreads)
if (numThreads > O3MaxThreads)
fatal("numThreads (%d) is larger than compiled limit (%d),\n"
"\tincrease MaxThreads in src/cpu/o3/impl.hh\n",
numThreads, static_cast<int>(Impl::MaxThreads));
if (fetchWidth > Impl::MaxWidth)
"\tincrease O3MaxThreads in src/cpu/o3/limits.hh\n",
numThreads, static_cast<int>(O3MaxThreads));
if (fetchWidth > O3MaxWidth)
fatal("fetchWidth (%d) is larger than compiled limit (%d),\n"
"\tincrease MaxWidth in src/cpu/o3/impl.hh\n",
fetchWidth, static_cast<int>(Impl::MaxWidth));
"\tincrease O3MaxWidth in src/cpu/o3/limits.hh\n",
fetchWidth, static_cast<int>(O3MaxWidth));
if (fetchBufferSize > cacheBlkSize)
fatal("fetch buffer size (%u bytes) is greater than the cache "
"block size (%u bytes)\n", fetchBufferSize, cacheBlkSize);
@@ -111,7 +112,7 @@ DefaultFetch<Impl>::DefaultFetch(O3CPU *_cpu, const DerivO3CPUParams &params)
// Get the size of an instruction.
instSize = sizeof(TheISA::MachInst);
for (int i = 0; i < Impl::MaxThreads; i++) {
for (int i = 0; i < O3MaxThreads; i++) {
fetchStatus[i] = Idle;
decoder[i] = nullptr;
pc[i] = 0;

View File

@@ -46,6 +46,7 @@
#include "base/statistics.hh"
#include "cpu/o3/comm.hh"
#include "cpu/o3/limits.hh"
#include "cpu/o3/lsq.hh"
#include "cpu/o3/scoreboard.hh"
#include "cpu/timebuf.hh"
@@ -117,7 +118,7 @@ class DefaultIEW
/** Overall stage status. */
Status _status;
/** Dispatch status. */
StageStatus dispatchStatus[Impl::MaxThreads];
StageStatus dispatchStatus[O3MaxThreads];
/** Execute status. */
StageStatus exeStatus;
/** Writeback status. */
@@ -341,10 +342,10 @@ class DefaultIEW
typename TimeBuffer<IEWStruct>::wire toCommit;
/** Queue of all instructions coming from rename this cycle. */
std::queue<DynInstPtr> insts[Impl::MaxThreads];
std::queue<DynInstPtr> insts[O3MaxThreads];
/** Skid buffer between rename and IEW. */
std::queue<DynInstPtr> skidBuffer[Impl::MaxThreads];
std::queue<DynInstPtr> skidBuffer[O3MaxThreads];
/** Scoreboard pointer. */
Scoreboard* scoreboard;
@@ -377,7 +378,7 @@ class DefaultIEW
private:
/** Records if there is a fetch redirect on this cycle for each thread. */
bool fetchRedirect[Impl::MaxThreads];
bool fetchRedirect[O3MaxThreads];
/** Records if the queues have been changed (inserted or issued insts),
* so that IEW knows to broadcast the updated amount of free entries.

View File

@@ -52,6 +52,7 @@
#include "cpu/checker/cpu.hh"
#include "cpu/o3/fu_pool.hh"
#include "cpu/o3/iew.hh"
#include "cpu/o3/limits.hh"
#include "cpu/timebuf.hh"
#include "debug/Activity.hh"
#include "debug/Drain.hh"
@@ -77,18 +78,18 @@ DefaultIEW<Impl>::DefaultIEW(O3CPU *_cpu, const DerivO3CPUParams &params)
numThreads(params.numThreads),
iewStats(cpu)
{
if (dispatchWidth > Impl::MaxWidth)
if (dispatchWidth > O3MaxWidth)
fatal("dispatchWidth (%d) is larger than compiled limit (%d),\n"
"\tincrease MaxWidth in src/cpu/o3/impl.hh\n",
dispatchWidth, static_cast<int>(Impl::MaxWidth));
if (issueWidth > Impl::MaxWidth)
"\tincrease O3MaxWidth in src/cpu/o3/limits.hh\n",
dispatchWidth, static_cast<int>(O3MaxWidth));
if (issueWidth > O3MaxWidth)
fatal("issueWidth (%d) is larger than compiled limit (%d),\n"
"\tincrease MaxWidth in src/cpu/o3/impl.hh\n",
issueWidth, static_cast<int>(Impl::MaxWidth));
if (wbWidth > Impl::MaxWidth)
"\tincrease O3MaxWidth in src/cpu/o3/limits.hh\n",
issueWidth, static_cast<int>(O3MaxWidth));
if (wbWidth > O3MaxWidth)
fatal("wbWidth (%d) is larger than compiled limit (%d),\n"
"\tincrease MaxWidth in src/cpu/o3/impl.hh\n",
wbWidth, static_cast<int>(Impl::MaxWidth));
"\tincrease O3MaxWidth in src/cpu/o3/limits.hh\n",
wbWidth, static_cast<int>(O3MaxWidth));
_status = Active;
exeStatus = Running;
@@ -100,7 +101,7 @@ DefaultIEW<Impl>::DefaultIEW(O3CPU *_cpu, const DerivO3CPUParams &params)
// Instruction queue needs the queue between issue and execute.
instQueue.setIssueToExecuteQueue(&issueToExecQueue);
for (ThreadID tid = 0; tid < Impl::MaxThreads; tid++) {
for (ThreadID tid = 0; tid < O3MaxThreads; tid++) {
dispatchStatus[tid] = Running;
fetchRedirect[tid] = false;
}

View File

@@ -68,12 +68,6 @@ struct O3CPUImpl
* case.
*/
typedef O3CPU CPUType;
enum
{
MaxWidth = 12,
MaxThreads = 4
};
};
#endif // __CPU_O3_SPARC_IMPL_HH__

View File

@@ -49,8 +49,9 @@
#include "base/statistics.hh"
#include "base/types.hh"
#include "cpu/o3/dep_graph.hh"
#include "cpu/inst_seq.hh"
#include "cpu/o3/dep_graph.hh"
#include "cpu/o3/limits.hh"
#include "cpu/op_class.hh"
#include "cpu/timebuf.hh"
#include "enums/SMTQueuePolicy.hh"
@@ -286,7 +287,7 @@ class InstructionQueue
/** The memory dependence unit, which tracks/predicts memory dependences
* between instructions.
*/
MemDepUnit memDepUnit[Impl::MaxThreads];
MemDepUnit memDepUnit[O3MaxThreads];
/** The queue to the execute stage. Issued instructions will be written
* into it.
@@ -307,7 +308,7 @@ class InstructionQueue
//////////////////////////////////////
/** List of all the instructions in the IQ (some of which may be issued). */
std::list<DynInstPtr> instList[Impl::MaxThreads];
std::list<DynInstPtr> instList[O3MaxThreads];
/** List of instructions that are ready to be executed. */
std::list<DynInstPtr> instsToExecute;
@@ -410,10 +411,10 @@ class InstructionQueue
std::list<ThreadID> *activeThreads;
/** Per Thread IQ count */
unsigned count[Impl::MaxThreads];
unsigned count[O3MaxThreads];
/** Max IQ Entries Per Thread */
unsigned maxEntries[Impl::MaxThreads];
unsigned maxEntries[O3MaxThreads];
/** Number of free IQ entries left. */
unsigned freeEntries;
@@ -436,7 +437,7 @@ class InstructionQueue
Cycles commitToIEWDelay;
/** The sequence number of the squashed instruction. */
InstSeqNum squashedSeqNum[Impl::MaxThreads];
InstSeqNum squashedSeqNum[O3MaxThreads];
/** A cache of the recently woken registers. It is 1 if the register
* has been woken up recently, and 0 if the register has been added

View File

@@ -48,6 +48,7 @@
#include "base/logging.hh"
#include "cpu/o3/fu_pool.hh"
#include "cpu/o3/inst_queue.hh"
#include "cpu/o3/limits.hh"
#include "debug/IQ.hh"
#include "enums/OpClass.hh"
#include "params/DerivO3CPU.hh"
@@ -113,7 +114,7 @@ InstructionQueue<Impl>::InstructionQueue(O3CPU *cpu_ptr, IEW *iew_ptr,
regScoreboard.resize(numPhysRegs);
//Initialize Mem Dependence Units
for (ThreadID tid = 0; tid < Impl::MaxThreads; tid++) {
for (ThreadID tid = 0; tid < O3MaxThreads; tid++) {
memDepUnit[tid].init(params, tid, cpu_ptr);
memDepUnit[tid].setIQ(this);
}
@@ -151,7 +152,7 @@ InstructionQueue<Impl>::InstructionQueue(O3CPU *cpu_ptr, IEW *iew_ptr,
DPRINTF(IQ, "IQ sharing policy set to Threshold:"
"%i entries per thread.\n",thresholdIQ);
}
for (ThreadID tid = numThreads; tid < Impl::MaxThreads; tid++) {
for (ThreadID tid = numThreads; tid < O3MaxThreads; tid++) {
maxEntries[tid] = 0;
}
}
@@ -389,7 +390,7 @@ void
InstructionQueue<Impl>::resetState()
{
//Initialize thread IQ counts
for (ThreadID tid = 0; tid < Impl::MaxThreads; tid++) {
for (ThreadID tid = 0; tid < O3MaxThreads; tid++) {
count[tid] = 0;
instList[tid].clear();
}
@@ -406,7 +407,7 @@ InstructionQueue<Impl>::resetState()
regScoreboard[i] = false;
}
for (ThreadID tid = 0; tid < Impl::MaxThreads; ++tid) {
for (ThreadID tid = 0; tid < O3MaxThreads; ++tid) {
squashedSeqNum[tid] = 0;
}

34
src/cpu/o3/limits.hh Normal file
View File

@@ -0,0 +1,34 @@
/*
* Copyright 2021 Google Inc.
*
* 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.
*/
#ifndef __CPU_O3_LIMITS_HH__
#define __CPU_O3_LIMITS_HH__
static constexpr int O3MaxWidth = 12;
static constexpr int O3MaxThreads = 4;
#endif // __CPU_O3_LIMITS_HH__

View File

@@ -48,6 +48,7 @@
#include "base/logging.hh"
#include "cpu/o3/cpu.hh"
#include "cpu/o3/limits.hh"
#include "cpu/o3/lsq.hh"
#include "debug/Drain.hh"
#include "debug/Fetch.hh"
@@ -72,7 +73,7 @@ LSQ<Impl>::LSQ(O3CPU *cpu_ptr, IEW *iew_ptr, const DerivO3CPUParams &params)
dcachePort(this, cpu_ptr),
numThreads(params.numThreads)
{
assert(numThreads > 0 && numThreads <= Impl::MaxThreads);
assert(numThreads > 0 && numThreads <= O3MaxThreads);
//**********************************************
//************ Handle SMT Parameters ***********

View File

@@ -48,6 +48,7 @@
#include "base/str.hh"
#include "config/the_isa.hh"
#include "cpu/checker/cpu.hh"
#include "cpu/o3/limits.hh"
#include "cpu/o3/lsq.hh"
#include "cpu/o3/lsq_unit.hh"
#include "debug/Activity.hh"
@@ -260,7 +261,7 @@ template<class Impl>
std::string
LSQUnit<Impl>::name() const
{
if (Impl::MaxThreads == 1) {
if (O3MaxThreads == 1) {
return iewStage->name() + ".lsq";
} else {
return iewStage->name() + ".lsq.thread" + std::to_string(lsqID);

View File

@@ -49,6 +49,7 @@
#include "base/statistics.hh"
#include "cpu/inst_seq.hh"
#include "cpu/o3/limits.hh"
#include "debug/MemDepUnit.hh"
struct SNHash
@@ -247,7 +248,7 @@ class MemDepUnit
MemDepHash memDepHash;
/** A list of all instructions in the memory dependence unit. */
std::list<DynInstPtr> instList[Impl::MaxThreads];
std::list<DynInstPtr> instList[O3MaxThreads];
/** A list of all instructions that are going to be replayed. */
std::list<DynInstPtr> instsToReplay;

View File

@@ -47,6 +47,7 @@
#include "base/debug.hh"
#include "cpu/o3/inst_queue.hh"
#include "cpu/o3/limits.hh"
#include "cpu/o3/mem_dep_unit.hh"
#include "debug/MemDepUnit.hh"
#include "params/DerivO3CPU.hh"
@@ -72,7 +73,7 @@ MemDepUnit<MemDepPred, Impl>::MemDepUnit(const DerivO3CPUParams &params)
template <class MemDepPred, class Impl>
MemDepUnit<MemDepPred, Impl>::~MemDepUnit()
{
for (ThreadID tid = 0; tid < Impl::MaxThreads; tid++) {
for (ThreadID tid = 0; tid < O3MaxThreads; tid++) {
ListIt inst_list_it = instList[tid].begin();
@@ -131,7 +132,7 @@ MemDepUnit<MemDepPred, Impl>::isDrained() const
bool drained = instsToReplay.empty()
&& memDepHash.empty()
&& instsToReplay.empty();
for (int i = 0; i < Impl::MaxThreads; ++i)
for (int i = 0; i < O3MaxThreads; ++i)
drained = drained && instList[i].empty();
return drained;
@@ -143,7 +144,7 @@ MemDepUnit<MemDepPred, Impl>::drainSanityCheck() const
{
assert(instsToReplay.empty());
assert(memDepHash.empty());
for (int i = 0; i < Impl::MaxThreads; ++i)
for (int i = 0; i < O3MaxThreads; ++i)
assert(instList[i].empty());
assert(instsToReplay.empty());
assert(memDepHash.empty());
@@ -614,7 +615,7 @@ template <class MemDepPred, class Impl>
void
MemDepUnit<MemDepPred, Impl>::dumpLists()
{
for (ThreadID tid = 0; tid < Impl::MaxThreads; tid++) {
for (ThreadID tid = 0; tid < O3MaxThreads; tid++) {
cprintf("Instruction list %i size: %i\n",
tid, instList[tid].size());

View File

@@ -47,6 +47,7 @@
#include "base/statistics.hh"
#include "config/the_isa.hh"
#include "cpu/o3/limits.hh"
#include "cpu/timebuf.hh"
#include "sim/probe/probe.hh"
@@ -116,7 +117,7 @@ class DefaultRename
RenameStatus _status;
/** Per-thread status. */
ThreadStatus renameStatus[Impl::MaxThreads];
ThreadStatus renameStatus[O3MaxThreads];
/** Probe points. */
typedef typename std::pair<InstSeqNum, PhysRegIdPtr> SeqNumRegPair;
@@ -173,7 +174,7 @@ class DefaultRename
void setActiveThreads(std::list<ThreadID> *at_ptr);
/** Sets pointer to rename maps (per-thread structures). */
void setRenameMap(RenameMap rm_ptr[Impl::MaxThreads]);
void setRenameMap(RenameMap rm_ptr[O3MaxThreads]);
/** Sets pointer to the free list. */
void setFreeList(FreeList *fl_ptr);
@@ -321,7 +322,7 @@ class DefaultRename
/** A per-thread list of all destination register renames, used to either
* undo rename mappings or free old physical registers.
*/
std::list<RenameHistory> historyBuffer[Impl::MaxThreads];
std::list<RenameHistory> historyBuffer[O3MaxThreads];
/** Pointer to CPU. */
O3CPU *cpu;
@@ -351,13 +352,13 @@ class DefaultRename
typename TimeBuffer<DecodeStruct>::wire fromDecode;
/** Queue of all instructions coming from decode this cycle. */
InstQueue insts[Impl::MaxThreads];
InstQueue insts[O3MaxThreads];
/** Skid buffer between rename and decode. */
InstQueue skidBuffer[Impl::MaxThreads];
InstQueue skidBuffer[O3MaxThreads];
/** Rename map interface. */
RenameMap *renameMap[Impl::MaxThreads];
RenameMap *renameMap[O3MaxThreads];
/** Free list interface. */
FreeList *freeList;
@@ -371,17 +372,17 @@ class DefaultRename
/** Count of instructions in progress that have been sent off to the IQ
* and ROB, but are not yet included in their occupancy counts.
*/
int instsInProgress[Impl::MaxThreads];
int instsInProgress[O3MaxThreads];
/** Count of Load instructions in progress that have been sent off to the IQ
* and ROB, but are not yet included in their occupancy counts.
*/
int loadsInProgress[Impl::MaxThreads];
int loadsInProgress[O3MaxThreads];
/** Count of Store instructions in progress that have been sent off to the IQ
* and ROB, but are not yet included in their occupancy counts.
*/
int storesInProgress[Impl::MaxThreads];
int storesInProgress[O3MaxThreads];
/** Variable that tracks if decode has written to the time buffer this
* cycle. Used to tell CPU if there is activity this cycle.
@@ -402,13 +403,13 @@ class DefaultRename
/** Per-thread tracking of the number of free entries of back-end
* structures.
*/
FreeEntries freeEntries[Impl::MaxThreads];
FreeEntries freeEntries[O3MaxThreads];
/** Records if the ROB is empty. In SMT mode the ROB may be dynamically
* partitioned between threads, so the ROB must tell rename when it is
* empty.
*/
bool emptyROB[Impl::MaxThreads];
bool emptyROB[O3MaxThreads];
/** Source of possible stalls. */
struct Stalls
@@ -418,15 +419,15 @@ class DefaultRename
};
/** Tracks which stages are telling decode to stall. */
Stalls stalls[Impl::MaxThreads];
Stalls stalls[O3MaxThreads];
/** The serialize instruction that rename has stalled on. */
DynInstPtr serializeInst[Impl::MaxThreads];
DynInstPtr serializeInst[O3MaxThreads];
/** Records if rename needs to serialize on the next instruction for any
* thread.
*/
bool serializeOnNextInst[Impl::MaxThreads];
bool serializeOnNextInst[O3MaxThreads];
/** Delay between iew and rename, in ticks. */
int iewToRenameDelay;

View File

@@ -44,6 +44,7 @@
#include <list>
#include "cpu/o3/limits.hh"
#include "cpu/o3/rename.hh"
#include "cpu/reg_class.hh"
#include "debug/Activity.hh"
@@ -62,14 +63,14 @@ DefaultRename<Impl>::DefaultRename(O3CPU *_cpu, const DerivO3CPUParams &params)
numThreads(params.numThreads),
stats(_cpu)
{
if (renameWidth > Impl::MaxWidth)
if (renameWidth > O3MaxWidth)
fatal("renameWidth (%d) is larger than compiled limit (%d),\n"
"\tincrease MaxWidth in src/cpu/o3/impl.hh\n",
renameWidth, static_cast<int>(Impl::MaxWidth));
"\tincrease O3MaxWidth in src/cpu/o3/limits.hh\n",
renameWidth, static_cast<int>(O3MaxWidth));
// @todo: Make into a parameter.
skidBufferMax = (decodeToRenameDelay + 1) * params.decodeWidth;
for (uint32_t tid = 0; tid < Impl::MaxThreads; tid++) {
for (uint32_t tid = 0; tid < O3MaxThreads; tid++) {
renameStatus[tid] = Idle;
renameMap[tid] = nullptr;
instsInProgress[tid] = 0;

View File

@@ -48,6 +48,7 @@
#include "arch/registers.hh"
#include "base/types.hh"
#include "config/the_isa.hh"
#include "cpu/o3/limits.hh"
#include "enums/SMTQueuePolicy.hh"
struct DerivO3CPUParams;
@@ -76,7 +77,7 @@ class ROB
private:
/** Per-thread ROB status. */
Status robStatus[Impl::MaxThreads];
Status robStatus[O3MaxThreads];
/** ROB resource sharing policy for SMT mode. */
SMTQueuePolicy robPolicy;
@@ -272,13 +273,13 @@ class ROB
unsigned numEntries;
/** Entries Per Thread */
unsigned threadEntries[Impl::MaxThreads];
unsigned threadEntries[O3MaxThreads];
/** Max Insts a Thread Can Have in the ROB */
unsigned maxEntries[Impl::MaxThreads];
unsigned maxEntries[O3MaxThreads];
/** ROB List of Instructions */
std::list<DynInstPtr> instList[Impl::MaxThreads];
std::list<DynInstPtr> instList[O3MaxThreads];
/** Number of instructions that can be squashed in a single cycle. */
unsigned squashWidth;
@@ -302,7 +303,7 @@ class ROB
* and after a squash.
* This will always be set to cpu->instList.end() if it is invalid.
*/
InstIt squashIt[Impl::MaxThreads];
InstIt squashIt[O3MaxThreads];
public:
/** Number of instructions in the ROB. */
@@ -313,10 +314,10 @@ class ROB
private:
/** The sequence number of the squashed instruction. */
InstSeqNum squashedSeqNum[Impl::MaxThreads];
InstSeqNum squashedSeqNum[O3MaxThreads];
/** Is the ROB done squashing. */
bool doneSquashing[Impl::MaxThreads];
bool doneSquashing[O3MaxThreads];
/** Number of active threads. */
ThreadID numThreads;

View File

@@ -44,6 +44,7 @@
#include <list>
#include "base/logging.hh"
#include "cpu/o3/limits.hh"
#include "cpu/o3/rob.hh"
#include "debug/Fetch.hh"
#include "debug/ROB.hh"
@@ -88,7 +89,7 @@ ROB<Impl>::ROB(O3CPU *_cpu, const DerivO3CPUParams &params)
}
}
for (ThreadID tid = numThreads; tid < Impl::MaxThreads; tid++) {
for (ThreadID tid = numThreads; tid < O3MaxThreads; tid++) {
maxEntries[tid] = 0;
}
@@ -99,7 +100,7 @@ template <class Impl>
void
ROB<Impl>::resetState()
{
for (ThreadID tid = 0; tid < Impl::MaxThreads; tid++) {
for (ThreadID tid = 0; tid < O3MaxThreads; tid++) {
threadEntries[tid] = 0;
squashIt[tid] = instList[tid].end();
squashedSeqNum[tid] = 0;