#include <string>
#include "arch/faults.hh"
+#include "arch/isa_traits.hh"
+#include "arch/mt.hh"
+#include "arch/types.hh"
+#include "arch/utility.hh"
#include "base/fast_alloc.hh"
#include "base/trace.hh"
-#include "cpu/inorder/inorder_trace.hh"
+#include "base/types.hh"
#include "config/full_system.hh"
-#include "cpu/thread_context.hh"
+#include "config/the_isa.hh"
+#include "cpu/inorder/inorder_trace.hh"
+#include "cpu/inorder/pipeline_traits.hh"
+#include "cpu/inorder/resource.hh"
+#include "cpu/inorder/resource_sked.hh"
+#include "cpu/inorder/thread_state.hh"
#include "cpu/exetrace.hh"
#include "cpu/inst_seq.hh"
#include "cpu/op_class.hh"
#include "cpu/static_inst.hh"
-#include "cpu/inorder/thread_state.hh"
-#include "cpu/inorder/resource.hh"
-#include "cpu/inorder/pipeline_traits.hh"
+#include "cpu/thread_context.hh"
+#include "debug/InOrderDynInst.hh"
#include "mem/packet.hh"
#include "sim/system.hh"
+#if THE_ISA == ALPHA_ISA
+#include "arch/alpha/ev5.hh"
+#endif
+
/**
* @file
* Defines a dynamic instruction context for a inorder CPU model.
*/
// Forward declaration.
-class StaticInstPtr;
class ResourceRequest;
+class Packet;
class InOrderDynInst : public FastAlloc, public RefCounted
{
// Floating point register type.
typedef TheISA::FloatReg FloatReg;
// Floating point register type.
+ typedef TheISA::FloatRegBits FloatRegBits;
+ // Floating point register type.
typedef TheISA::MiscReg MiscReg;
typedef short int PhysRegIndex;
typedef std::list<DynInstPtr>::iterator ListIt;
enum {
- MaxInstSrcRegs = TheISA::MaxInstSrcRegs, /// Max source regs
- MaxInstDestRegs = TheISA::MaxInstDestRegs, /// Max dest regs
+ MaxInstSrcRegs = TheISA::MaxInstSrcRegs, /// Max source regs
+ MaxInstDestRegs = TheISA::MaxInstDestRegs, /// Max dest regs
};
public:
- /** BaseDynInst constructor given a binary instruction.
- * @param inst The binary instruction.
- * @param PC The PC of the instruction.
- * @param pred_PC The predicted next PC.
- * @param seq_num The sequence number of the instruction.
- * @param cpu Pointer to the instruction's CPU.
- */
- InOrderDynInst(ExtMachInst inst, Addr PC, Addr pred_PC, InstSeqNum seq_num,
- InOrderCPU *cpu);
-
/** BaseDynInst constructor given a binary instruction.
* @param seq_num The sequence number of the instruction.
* @param cpu Pointer to the instruction's CPU.
* NOTE: Must set Binary Instrution through Member Function
*/
- InOrderDynInst(InOrderCPU *cpu, InOrderThreadState *state, InstSeqNum seq_num,
- unsigned tid);
-
- /** BaseDynInst constructor given a StaticInst pointer.
- * @param _staticInst The StaticInst for this BaseDynInst.
- */
- InOrderDynInst(StaticInstPtr &_staticInst);
-
- /** Skeleton Constructor. */
- InOrderDynInst();
+ InOrderDynInst(InOrderCPU *cpu, InOrderThreadState *state,
+ InstSeqNum seq_num, ThreadID tid, unsigned asid = 0);
/** InOrderDynInst destructor. */
~InOrderDynInst();
/** The sequence number of the instruction. */
InstSeqNum seqNum;
- /** The sequence number of the instruction. */
- InstSeqNum bdelaySeqNum;
+ /** If this instruction is squashing, the number should we squash behind. */
+ InstSeqNum squashSeqNum;
enum Status {
- RegDepMapEntry, /// Instruction has been entered onto the RegDepMap
+ RegDepMapEntry, /// Instruction is entered onto the RegDepMap
IqEntry, /// Instruction is in the IQ
RobEntry, /// Instruction is in the ROB
LsqEntry, /// Instruction is in the LSQ
/// instructions ahead of it
SerializeAfter, /// Needs to serialize instructions behind it
SerializeHandled, /// Serialization has been handled
+ RemoveList, /// Is Instruction on Remove List?
NumStatus
};
/** Data used for a store for operation. */
uint64_t storeData;
- /** The resource schedule for this inst */
- ThePipeline::ResSchedule resSched;
-
/** List of active resource requests for this instruction */
std::list<ResourceRequest*> reqList;
/** The effective physical address. */
Addr physEffAddr;
- /** Effective virtual address for a copy source. */
- Addr copySrcEffAddr;
-
- /** Effective physical address for a copy source. */
- Addr copySrcPhysEffAddr;
-
/** The memory request flags (from translation). */
unsigned memReqFlags;
/** How many source registers are ready. */
unsigned readyRegs;
+ enum ResultType {
+ None,
+ Integer,
+ Float,
+ FloatBits,
+ Double
+ };
+
/** An instruction src/dest has to be one of these types */
- union InstValue {
- uint64_t integer;
- float fp;
- double dbl;
+ struct InstValue {
+ IntReg intVal;
+ union {
+ FloatReg f;
+ FloatRegBits i;
+ } fpVal;
+
+ InstValue()
+ {
+ intVal = 0;
+ fpVal.i = 0;
+ }
};
/** Result of an instruction execution */
struct InstResult {
- InstValue val;
+ ResultType type;
+ InstValue res;
Tick tick;
+
+ InstResult()
+ : type(None), tick(0)
+ { }
};
/** The source of the instruction; assumes for now that there's only one
InstResult instResult[MaxInstDestRegs];
/** PC of this instruction. */
- Addr PC;
-
- /** Next non-speculative PC. It is not filled in at fetch, but rather
- * once the target of the branch is truly known (either decode or
- * execute).
- */
- Addr nextPC;
-
- /** Next next non-speculative PC. It is not filled in at fetch, but rather
- * once the target of the branch is truly known (either decode or
- * execute).
- */
- Addr nextNPC;
+ TheISA::PCState pc;
/** Predicted next PC. */
- Addr predPC;
-
- /** Address to fetch from */
- Addr fetchAddr;
+ TheISA::PCState predPC;
/** Address to get/write data from/to */
+ /* Fetching address when inst. starts, Data address for load/store after fetch*/
Addr memAddr;
/** Whether or not the source register is ready.
*/
bool _readySrcRegIdx[MaxInstSrcRegs];
+ /** Flattened register index of the destination registers of this
+ * instruction.
+ */
+ TheISA::RegIndex _flatDestRegIdx[TheISA::MaxInstDestRegs];
+
+ /** Flattened register index of the source registers of this
+ * instruction.
+ */
+ TheISA::RegIndex _flatSrcRegIdx[TheISA::MaxInstSrcRegs];
+
/** Physical register index of the destination registers of this
* instruction.
*/
int nextStage;
- /* vars to keep track of InstStage's - used for resource sched defn */
- int nextInstStageNum;
- ThePipeline::InstStage *currentInstStage;
- std::list<ThePipeline::InstStage*> instStageList;
-
private:
/** Function to initialize variables in the constructors. */
void initVars();
public:
Tick memTime;
+ PacketDataPtr splitMemData;
+ RequestPtr splitMemReq;
+ int totalSize;
+ int split2ndSize;
+ Addr split2ndAddr;
+ bool split2ndAccess;
+ uint8_t split2ndData;
+ PacketDataPtr split2ndDataPtr;
+ unsigned split2ndFlags;
+ bool splitInst;
+ int splitFinishCnt;
+ uint64_t *split2ndStoreDataPtr;
+ bool splitInstSked;
+
////////////////////////////////////////////////////////////
//
// BASE INSTRUCTION INFORMATION.
//
////////////////////////////////////////////////////////////
- void setMachInst(ExtMachInst inst);
+ std::string instName()
+ { return (staticInst) ? staticInst->getName() : "undecoded-inst"; }
+
+ void setStaticInst(StaticInstPtr si);
+
+ ExtMachInst getMachInst() { return staticInst->machInst; }
/** Sets the StaticInst. */
void setStaticInst(StaticInstPtr &static_inst);
short readTid() { return threadNumber; }
/** Sets the thread id. */
- void setTid(unsigned tid) { threadNumber = tid; }
+ void setTid(ThreadID tid) { threadNumber = tid; }
void setVpn(int id) { virtProcNumber = id; }
/** Returns the fault type. */
Fault getFault() { return fault; }
+ /** Read this CPU's ID. */
+ int cpuId();
+
+ /** Read this context's system-wide ID **/
+ int contextId() { return thread->contextId(); }
+
////////////////////////////////////////////////////////////
//
// INSTRUCTION TYPES - Forward checks to StaticInst object.
//
////////////////////////////////////////////////////////////
- bool isNop() const { return staticInst->isNop(); }
- bool isMemRef() const { return staticInst->isMemRef(); }
- bool isLoad() const { return staticInst->isLoad(); }
- bool isStore() const { return staticInst->isStore(); }
+ bool isNop() const { return staticInst->isNop(); }
+ bool isMemRef() const { return staticInst->isMemRef(); }
+ bool isLoad() const { return staticInst->isLoad(); }
+ bool isStore() const { return staticInst->isStore(); }
bool isStoreConditional() const
{ return staticInst->isStoreConditional(); }
bool isInstPrefetch() const { return staticInst->isInstPrefetch(); }
bool isDataPrefetch() const { return staticInst->isDataPrefetch(); }
- bool isCopy() const { return staticInst->isCopy(); }
- bool isInteger() const { return staticInst->isInteger(); }
- bool isFloating() const { return staticInst->isFloating(); }
- bool isControl() const { return staticInst->isControl(); }
- bool isCall() const { return staticInst->isCall(); }
- bool isReturn() const { return staticInst->isReturn(); }
- bool isDirectCtrl() const { return staticInst->isDirectCtrl(); }
+ bool isInteger() const { return staticInst->isInteger(); }
+ bool isFloating() const { return staticInst->isFloating(); }
+ bool isControl() const { return staticInst->isControl(); }
+ bool isCall() const { return staticInst->isCall(); }
+ bool isReturn() const { return staticInst->isReturn(); }
+ bool isDirectCtrl() const { return staticInst->isDirectCtrl(); }
bool isIndirectCtrl() const { return staticInst->isIndirectCtrl(); }
- bool isCondCtrl() const { return staticInst->isCondCtrl(); }
- bool isUncondCtrl() const { return staticInst->isUncondCtrl(); }
+ bool isCondCtrl() const { return staticInst->isCondCtrl(); }
+ bool isUncondCtrl() const { return staticInst->isUncondCtrl(); }
bool isCondDelaySlot() const { return staticInst->isCondDelaySlot(); }
bool isThreadSync() const { return staticInst->isThreadSync(); }
bool isQuiesce() const { return staticInst->isQuiesce(); }
bool isIprAccess() const { return staticInst->isIprAccess(); }
bool isUnverifiable() const { return staticInst->isUnverifiable(); }
+ bool isSyscall() const
+ { return staticInst->isSyscall(); }
+
/////////////////////////////////////////////
//
// RESOURCE SCHEDULING
//
/////////////////////////////////////////////
+ typedef ThePipeline::RSkedPtr RSkedPtr;
+ bool inFrontEnd;
- void setNextStage(int stage_num) { nextStage = stage_num; }
- int getNextStage() { return nextStage; }
+ RSkedPtr frontSked;
+ RSkedIt frontSked_end;
- ThePipeline::InstStage *addStage();
- ThePipeline::InstStage *addStage(int stage);
- ThePipeline::InstStage *currentStage() { return currentInstStage; }
- void deleteStages();
+ RSkedPtr backSked;
+ RSkedIt backSked_end;
- /** Add A Entry To Reource Schedule */
- void addToSched(ThePipeline::ScheduleEntry* sched_entry)
- { resSched.push(sched_entry); }
+ RSkedIt curSkedEntry;
+ void setFrontSked(RSkedPtr front_sked)
+ {
+ frontSked = front_sked;
+ frontSked_end.init(frontSked);
+ frontSked_end = frontSked->end();
+ //DPRINTF(InOrderDynInst, "Set FrontSked End to : %x \n" ,
+ // frontSked_end.getIt()/*, frontSked->end()*/);
+ //assert(frontSked_end == frontSked->end());
+
+ // This initializes instruction to be able
+ // to walk the resource schedule
+ curSkedEntry.init(frontSked);
+ curSkedEntry = frontSked->begin();
+ }
- /** Print Resource Schedule */
- void printSched()
+ void setBackSked(RSkedPtr back_sked)
{
- using namespace ThePipeline;
+ backSked = back_sked;
+ backSked_end.init(backSked);
+ backSked_end = backSked->end();
+ }
- ResSchedule tempSched;
- std::cerr << "\tInst. Res. Schedule: ";
- while (!resSched.empty()) {
- std::cerr << '\t' << resSched.top()->stageNum << "-"
- << resSched.top()->resNum << ", ";
+ void setNextStage(int stage_num) { nextStage = stage_num; }
+ int getNextStage() { return nextStage; }
- tempSched.push(resSched.top());
- resSched.pop();
+ /** Print Resource Schedule */
+ void printSked()
+ {
+ if (frontSked != NULL) {
+ frontSked->print();
}
- std::cerr << std::endl;
- resSched = tempSched;
+ if (backSked != NULL) {
+ backSked->print();
+ }
}
/** Return Next Resource Stage To Be Used */
int nextResStage()
{
- if (resSched.empty())
- return -1;
- else
- return resSched.top()->stageNum;
+ assert((inFrontEnd && curSkedEntry != frontSked_end) ||
+ (!inFrontEnd && curSkedEntry != backSked_end));
+
+ return curSkedEntry->stageNum;
}
/** Return Next Resource To Be Used */
int nextResource()
{
- if (resSched.empty())
- return -1;
- else
- return resSched.top()->resNum;
+ assert((inFrontEnd && curSkedEntry != frontSked_end) ||
+ (!inFrontEnd && curSkedEntry != backSked_end));
+
+ return curSkedEntry->resNum;
}
- /** Remove & Deallocate a schedule entry */
- void popSchedEntry()
+ /** Finish using a schedule entry, increment to next entry */
+ bool finishSkedEntry()
{
- if (!resSched.empty()) {
- ThePipeline::ScheduleEntry* sked = resSched.top();
- resSched.pop();
- delete sked;
+ curSkedEntry++;
+
+ if (inFrontEnd && curSkedEntry == frontSked_end) {
+ DPRINTF(InOrderDynInst, "[sn:%i] Switching to "
+ "back end schedule.\n", seqNum);
+ assert(backSked != NULL);
+ curSkedEntry.init(backSked);
+ curSkedEntry = backSked->begin();
+ inFrontEnd = false;
+ } else if (!inFrontEnd && curSkedEntry == backSked_end) {
+ return true;
}
+
+ DPRINTF(InOrderDynInst, "[sn:%i] Next Stage: %i "
+ "Next Resource: %i.\n", seqNum, curSkedEntry->stageNum,
+ curSkedEntry->resNum);
+
+ return false;
}
/** Release a Resource Request (Currently Unused) */
void setCurResSlot(unsigned slot_num) { curResSlot = slot_num; }
/** Calls a syscall. */
+#if FULL_SYSTEM
+ /** Calls hardware return from error interrupt. */
+ Fault hwrei();
+ /** Traps to handle specified fault. */
+ void trap(Fault fault);
+ bool simPalCheck(int palFunc);
+#else
+ short syscallNum;
+#endif
+
+ /** Emulates a syscall. */
void syscall(int64_t callnum);
- void prefetch(Addr addr, unsigned flags);
- void writeHint(Addr addr, int size, unsigned flags);
- Fault copySrcTranslate(Addr src);
- Fault copy(Addr dest);
////////////////////////////////////////////////////////////
//
////////////////////////////////////////////////////////////
virtual void deallocateContext(int thread_num);
- virtual void enableVirtProcElement(unsigned vpe);
- virtual void disableVirtProcElement(unsigned vpe);
-
- virtual void enableMultiThreading(unsigned vpe);
- virtual void disableMultiThreading(unsigned vpe);
-
- virtual void setThreadRescheduleCondition(uint32_t cond);
-
////////////////////////////////////////////////////////////
//
// PROGRAM COUNTERS - PC/NPC/NPC
//
////////////////////////////////////////////////////////////
/** Read the PC of this instruction. */
- const Addr readPC() const { return PC; }
+ const TheISA::PCState &pcState() const { return pc; }
/** Sets the PC of this instruction. */
- void setPC(Addr pc) { PC = pc; }
-
- /** Returns the next PC. This could be the speculative next PC if it is
- * called prior to the actual branch target being calculated.
- */
- Addr readNextPC() { return nextPC; }
-
- /** Set the next PC of this instruction (its actual target). */
- void setNextPC(uint64_t val) { nextPC = val; }
-
- /** Returns the next NPC. This could be the speculative next NPC if it is
- * called prior to the actual branch target being calculated.
- */
- Addr readNextNPC() { return nextNPC; }
+ void pcState(const TheISA::PCState &_pc) { pc = _pc; }
- /** Set the next PC of this instruction (its actual target). */
- void setNextNPC(uint64_t val) { nextNPC = val; }
+ const Addr instAddr() { return pc.instAddr(); }
+ const Addr nextInstAddr() { return pc.nextInstAddr(); }
+ const MicroPC microPC() { return pc.microPC(); }
////////////////////////////////////////////////////////////
//
//
////////////////////////////////////////////////////////////
/** Set the predicted target of this current instruction. */
- void setPredTarg(Addr predicted_PC) { predPC = predicted_PC; }
+ void setPredTarg(const TheISA::PCState &predictedPC)
+ { predPC = predictedPC; }
/** Returns the predicted target of the branch. */
- Addr readPredTarg() { return predPC; }
+ TheISA::PCState readPredTarg() { return predPC; }
+
+ /** Returns the predicted PC immediately after the branch. */
+ Addr predInstAddr() { return predPC.instAddr(); }
+
+ /** Returns the predicted PC two instructions after the branch */
+ Addr predNextInstAddr() { return predPC.nextInstAddr(); }
+
+ /** Returns the predicted micro PC after the branch */
+ Addr readPredMicroPC() { return predPC.microPC(); }
/** Returns whether the instruction was predicted taken or not. */
bool predTaken() { return predictTaken; }
/** Returns whether the instruction mispredicted. */
- bool mispredicted()
+ bool
+ mispredicted()
{
- // Special case since a not-taken, cond. delay slot, effectively
- // nullifies the delay slot instruction
- if (isCondDelaySlot() && !predictTaken) {
- return predPC != nextPC;
- } else {
- return predPC != nextNPC;
- }
+ TheISA::PCState nextPC = pc;
+ TheISA::advancePC(nextPC, staticInst);
+ return !(nextPC == predPC);
}
- /** Returns whether the instruction mispredicted. */
- bool mistargeted() { return predPC != nextNPC; }
-
/** Returns the branch target address. */
- Addr branchTarget() const { return staticInst->branchTarget(PC); }
+ TheISA::PCState branchTarget() const
+ { return staticInst->branchTarget(pc); }
/** Checks whether or not this instruction has had its branch target
* calculated yet. For now it is not utilized and is hacked to be
bool procDelaySlotOnMispred;
+ void setSquashInfo(unsigned stage_num);
+
////////////////////////////////////////////
//
// MEMORY ACCESS
//
////////////////////////////////////////////
- /**
- * Does a read to a given address.
- * @param addr The address to read.
- * @param data The read's data is written into this parameter.
- * @param flags The request's flags.
- * @return Returns any fault due to the read.
- */
- template <class T>
- Fault read(Addr addr, T &data, unsigned flags);
-
- /**
- * Does a write to a given address.
- * @param data The data to be written.
- * @param addr The address to write to.
- * @param flags The request's flags.
- * @param res The result of the write (for load locked/store conditionals).
- * @return Returns any fault due to the write.
- */
- template <class T>
- Fault write(T data, Addr addr, unsigned flags,
- uint64_t *res);
- /** Initiates a memory access - Calculate Eff. Addr & Initiate Memory Access
- * Only valid for memory operations.
+ Fault readMem(Addr addr, uint8_t *data, unsigned size, unsigned flags);
+
+ Fault writeMem(uint8_t *data, unsigned size,
+ Addr addr, unsigned flags, uint64_t *res);
+
+ /** Initiates a memory access - Calculate Eff. Addr & Initiate Memory
+ * Access Only valid for memory operations.
*/
Fault initiateAcc();
/** Read Effective Address from instruction & do memory access */
Fault memAccess();
- RequestPtr memReq;
+ RequestPtr fetchMemReq;
+ RequestPtr dataMemReq;
bool memAddrReady;
Addr getMemAddr()
{ return memAddr; }
- int getMemAccSize() { return staticInst->memAccSize(this); }
-
- int getMemFlags() { return staticInst->memAccFlags(); }
-
/** Sets the effective address. */
void setEA(Addr &ea) { instEffAddr = ea; eaCalcDone = true; }
/** Returns the effective address. */
const Addr &getEA() const { return instEffAddr; }
- /** Returns whether or not the eff. addr. calculation has been completed. */
+ /** Returns whether or not the eff. addr. calculation has been completed.*/
bool doneEACalc() { return eaCalcDone; }
/** Returns whether or not the eff. addr. source registers are ready.
//
//////////////////////////////////////////////////
/** Returns the number of source registers. */
- int8_t numSrcRegs() const { return staticInst->numSrcRegs(); }
+ int8_t numSrcRegs() const { return staticInst->numSrcRegs(); }
/** Returns the number of destination registers. */
int8_t numDestRegs() const { return staticInst->numDestRegs(); }
return _srcRegIdx[idx];
}
+ /** Flattens a source architectural register index into a logical index.
+ */
+ void flattenSrcReg(int idx, TheISA::RegIndex flattened_src)
+ {
+ _flatSrcRegIdx[idx] = flattened_src;
+ }
+
+ /** Flattens a destination architectural register index into a logical
+ * index.
+ */
+ void flattenDestReg(int idx, TheISA::RegIndex flattened_dest)
+ {
+ _flatDestRegIdx[idx] = flattened_dest;
+ }
+
+ /** Returns the flattened register index of the i'th destination
+ * register.
+ */
+ TheISA::RegIndex flattenedDestRegIdx(int idx) const
+ {
+ return _flatDestRegIdx[idx];
+ }
+
+ /** Returns the flattened register index of the i'th source register */
+ TheISA::RegIndex flattenedSrcRegIdx(int idx) const
+ {
+ return _flatSrcRegIdx[idx];
+ }
+
/** Returns the physical register index of the previous physical register
* that remapped to the same logical register index.
*/
int getDestIdxNum(PhysRegIndex dest_idx)
{
for (int i=0; i < staticInst->numDestRegs(); i++) {
- if (_destRegIdx[i] == dest_idx)
+ if (_flatDestRegIdx[i] == dest_idx)
return i;
}
/** Functions that sets an integer or floating point
* source register to a value. */
void setIntSrc(int idx, uint64_t val);
- void setFloatSrc(int idx, FloatReg val, int width = 32);
- void setFloatRegBitsSrc(int idx, uint64_t val);
+ void setFloatSrc(int idx, FloatReg val);
+ void setFloatRegBitsSrc(int idx, TheISA::FloatRegBits val);
- uint64_t* getIntSrcPtr(int idx) { return &instSrc[idx].integer; }
- uint64_t readIntSrc(int idx) { return instSrc[idx].integer; }
+ TheISA::IntReg* getIntSrcPtr(int idx) { return &instSrc[idx].intVal; }
+ uint64_t readIntSrc(int idx) { return instSrc[idx].intVal; }
/** These Instructions read a integer/float/misc. source register
* value in the instruction. The instruction's execute function will
* language (which is why the name isnt readIntSrc(...)) Note: That
* the source reg. value is set using the setSrcReg() function.
*/
- IntReg readIntRegOperand(const StaticInst *si, int idx, unsigned tid=0);
- FloatReg readFloatRegOperand(const StaticInst *si, int idx,
- int width = TheISA::SingleWidth);
- FloatRegBits readFloatRegOperandBits(const StaticInst *si, int idx,
- int width = TheISA::SingleWidth);
+ IntReg readIntRegOperand(const StaticInst *si, int idx, ThreadID tid = 0);
+ FloatReg readFloatRegOperand(const StaticInst *si, int idx);
+ TheISA::FloatRegBits readFloatRegOperandBits(const StaticInst *si, int idx);
MiscReg readMiscReg(int misc_reg);
MiscReg readMiscRegNoEffect(int misc_reg);
MiscReg readMiscRegOperand(const StaticInst *si, int idx);
MiscReg readMiscRegOperandNoEffect(const StaticInst *si, int idx);
/** Returns the result value instruction. */
- uint64_t readIntResult(int idx) { return instResult[idx].val.integer; }
- float readFloatResult(int idx) { return instResult[idx].val.fp; }
- double readDoubleResult(int idx) { return instResult[idx].val.dbl; }
+ ResultType resultType(int idx)
+ {
+ return instResult[idx].type;
+ }
+
+ IntReg readIntResult(int idx)
+ {
+ return instResult[idx].res.intVal;
+ }
+
+ FloatReg readFloatResult(int idx)
+ {
+ return instResult[idx].res.fpVal.f;
+ }
+
+ FloatRegBits readFloatBitsResult(int idx)
+ {
+ return instResult[idx].res.fpVal.i;
+ }
+
Tick readResultTime(int idx) { return instResult[idx].tick; }
- uint64_t* getIntResultPtr(int idx) { return &instResult[idx].val.integer; }
+ IntReg* getIntResultPtr(int idx) { return &instResult[idx].res.intVal; }
/** This is the interface that an instruction will use to write
* it's destination register.
*/
void setIntRegOperand(const StaticInst *si, int idx, IntReg val);
- void setFloatRegOperand(const StaticInst *si, int idx, FloatReg val,
- int width = TheISA::SingleWidth);
- void setFloatRegOperandBits(const StaticInst *si, int idx, FloatRegBits val,
- int width = TheISA::SingleWidth);
+ void setFloatRegOperand(const StaticInst *si, int idx, FloatReg val);
+ void setFloatRegOperandBits(const StaticInst *si, int idx,
+ TheISA::FloatRegBits val);
void setMiscReg(int misc_reg, const MiscReg &val);
void setMiscRegNoEffect(int misc_reg, const MiscReg &val);
void setMiscRegOperand(const StaticInst *si, int idx, const MiscReg &val);
- void setMiscRegOperandNoEffect(const StaticInst *si, int idx, const MiscReg &val);
+ void setMiscRegOperandNoEffect(const StaticInst *si, int idx,
+ const MiscReg &val);
+
+ virtual uint64_t readRegOtherThread(unsigned idx,
+ ThreadID tid = InvalidThreadID);
+ virtual void setRegOtherThread(unsigned idx, const uint64_t &val,
+ ThreadID tid = InvalidThreadID);
+
+ /** Returns the number of consecutive store conditional failures. */
+ unsigned readStCondFailures()
+ { return thread->storeCondFailures; }
- virtual uint64_t readRegOtherThread(unsigned idx, int tid = -1);
- virtual void setRegOtherThread(unsigned idx, const uint64_t &val, int tid = -1);
+ /** Sets the number of consecutive store conditional failures. */
+ void setStCondFailures(unsigned sc_failures)
+ { thread->storeCondFailures = sc_failures; }
//////////////////////////////////////////////////////////////
//
/** Sets this instruction as entered on the CPU Reg Dep Map */
void setRegDepEntry() { status.set(RegDepMapEntry); }
+ /** Unsets this instruction as entered on the CPU Reg Dep Map */
+ void clearRegDepEntry() { status.reset(RegDepMapEntry); }
+
/** Returns whether or not the entry is on the CPU Reg Dep Map */
bool isRegDepEntry() const { return status[RegDepMapEntry]; }
+ /** Sets this instruction as entered on the CPU Reg Dep Map */
+ void setRemoveList() { status.set(RemoveList); }
+
+ /** Returns whether or not the entry is on the CPU Reg Dep Map */
+ bool isRemoveList() const { return status[RemoveList]; }
+
/** Sets this instruction as completed. */
void setCompleted() { status.set(Completed); }
*/
bool eaCalcDone;
- public:
- /** Whether or not the memory operation is done. */
- bool memOpDone;
-
public:
/** Load queue index. */
int16_t lqIdx;
/** Iterator pointing to this BaseDynInst in the list of all insts. */
ListIt instListIt;
+ bool onInstList;
+
/** Returns iterator to this instruction in the list of all insts. */
- ListIt &getInstListIt() { return instListIt; }
+ ListIt getInstListIt() { return instListIt; }
/** Sets iterator for this instruction in the list of all insts. */
- void setInstListIt(ListIt _instListIt) { instListIt = _instListIt; }
+ void setInstListIt(ListIt _instListIt) { onInstList = true; instListIt = _instListIt; }
/** Count of total number of dynamic instructions. */
static int instcount;
-#ifdef DEBUG
- void dumpSNList();
-#endif
-
+ void resetInstCount();
+
/** Dumps out contents of this BaseDynInst. */
void dump();
/** Dumps out contents of this BaseDynInst into given string. */
void dump(std::string &outstring);
-
- //inline int curCount() { return curCount(); }
+ //inline int curCount() { return curCount(); }
};