summaryrefslogtreecommitdiff
path: root/src/cpu/simple/base.cc
diff options
context:
space:
mode:
Diffstat (limited to 'src/cpu/simple/base.cc')
-rw-r--r--src/cpu/simple/base.cc62
1 files changed, 35 insertions, 27 deletions
diff --git a/src/cpu/simple/base.cc b/src/cpu/simple/base.cc
index b8d1f3bed..877dc5bd4 100644
--- a/src/cpu/simple/base.cc
+++ b/src/cpu/simple/base.cc
@@ -70,7 +70,7 @@ using namespace std;
using namespace TheISA;
BaseSimpleCPU::BaseSimpleCPU(Params *p)
- : BaseCPU(p), thread(NULL)
+ : BaseCPU(p), thread(NULL), predecoder(NULL)
{
#if FULL_SYSTEM
thread = new SimpleThread(this, 0, p->system, p->itb, p->dtb);
@@ -301,7 +301,7 @@ BaseSimpleCPU::post_interrupt(int int_num, int index)
BaseCPU::post_interrupt(int_num, index);
if (thread->status() == ThreadContext::Suspended) {
- DPRINTF(IPI,"Suspended Processor awoke\n");
+ DPRINTF(Quiesce,"Suspended Processor awoke\n");
thread->activate();
}
}
@@ -367,16 +367,23 @@ BaseSimpleCPU::preExecute()
inst = gtoh(inst);
//If we're not in the middle of a macro instruction
if (!curMacroStaticInst) {
-#if THE_ISA == ALPHA_ISA
- StaticInstPtr instPtr = StaticInst::decode(makeExtMI(inst, thread->readPC()));
-#elif THE_ISA == SPARC_ISA
- StaticInstPtr instPtr = StaticInst::decode(makeExtMI(inst, thread->getTC()));
-#elif THE_ISA == MIPS_ISA
- //Mips doesn't do anything in it's MakeExtMI function right now,
- //so it won't be called.
- StaticInstPtr instPtr = StaticInst::decode(inst);
-#endif
- if (instPtr->isMacroOp()) {
+ StaticInstPtr instPtr = NULL;
+
+ //Predecode, ie bundle up an ExtMachInst
+ //This should go away once the constructor can be set up properly
+ predecoder.setTC(thread->getTC());
+ //If more fetch data is needed, pass it in.
+ if(predecoder.needMoreBytes())
+ predecoder.moreBytes(thread->readPC(), 0, inst);
+ else
+ predecoder.process();
+ //If an instruction is ready, decode it
+ if (predecoder.extMachInstReady())
+ instPtr = StaticInst::decode(predecoder.getExtMachInst());
+
+ //If we decoded an instruction and it's microcoded, start pulling
+ //out micro ops
+ if (instPtr && instPtr->isMacroOp()) {
curMacroStaticInst = instPtr;
curStaticInst = curMacroStaticInst->
fetchMicroOp(thread->readMicroPC());
@@ -389,17 +396,19 @@ BaseSimpleCPU::preExecute()
fetchMicroOp(thread->readMicroPC());
}
+ //If we decoded an instruction this "tick", record information about it.
+ if(curStaticInst)
+ {
+ traceData = Trace::getInstRecord(curTick, tc, curStaticInst,
+ thread->readPC());
- traceData = Trace::getInstRecord(curTick, tc, curStaticInst,
- thread->readPC());
-
- DPRINTF(Decode,"Decode: Decoded %s instruction (opcode: 0x%x): 0x%x\n",
- curStaticInst->getName(), curStaticInst->getOpcode(),
- curStaticInst->machInst);
+ DPRINTF(Decode,"Decode: Decoded %s instruction: 0x%x\n",
+ curStaticInst->getName(), curStaticInst->machInst);
#if FULL_SYSTEM
- thread->setInst(inst);
+ thread->setInst(inst);
#endif // FULL_SYSTEM
+ }
}
void
@@ -409,7 +418,8 @@ BaseSimpleCPU::postExecute()
if (thread->profile) {
bool usermode = TheISA::inUserMode(tc);
thread->profilePC = usermode ? 1 : thread->readPC();
- ProfileNode *node = thread->profile->consume(tc, inst);
+ StaticInstPtr si(inst);
+ ProfileNode *node = thread->profile->consume(tc, si);
if (node)
thread->profileNode = node;
}
@@ -427,7 +437,9 @@ BaseSimpleCPU::postExecute()
traceFunctions(thread->readPC());
if (traceData) {
- traceData->finalize();
+ traceData->dump();
+ delete traceData;
+ traceData = NULL;
}
}
@@ -440,9 +452,9 @@ BaseSimpleCPU::advancePC(Fault fault)
fault->invoke(tc);
thread->setMicroPC(0);
thread->setNextMicroPC(1);
- } else {
+ } else if (predecoder.needMoreBytes()) {
//If we're at the last micro op for this instruction
- if (curStaticInst->isLastMicroOp()) {
+ if (curStaticInst && curStaticInst->isLastMicroOp()) {
//We should be working with a macro op
assert(curMacroStaticInst);
//Close out this macro op, and clean up the
@@ -461,13 +473,9 @@ BaseSimpleCPU::advancePC(Fault fault)
} else {
// go to the next instruction
thread->setPC(thread->readNextPC());
-#if ISA_HAS_DELAY_SLOT
thread->setNextPC(thread->readNextNPC());
thread->setNextNPC(thread->readNextNPC() + sizeof(MachInst));
assert(thread->readNextPC() != thread->readNextNPC());
-#else
- thread->setNextPC(thread->readNextPC() + sizeof(MachInst));
-#endif
}
}