inorder: add flatDestReg member to dyninst
use it in reg. dep. tracking
This commit is contained in:
@@ -324,9 +324,10 @@ InOrderDynInst::setSquashInfo(unsigned stage_num)
|
||||
// the faulting instruction too. Squash
|
||||
// functions squash above a seqNum, so we
|
||||
// decrement here for that case
|
||||
if (fault != NoFault)
|
||||
if (fault != NoFault) {
|
||||
squashSeqNum = seqNum - 1;
|
||||
else
|
||||
return;
|
||||
} else
|
||||
squashSeqNum = seqNum;
|
||||
|
||||
#if ISA_HAS_DELAY_SLOT
|
||||
|
||||
@@ -261,6 +261,16 @@ class InOrderDynInst : public FastAlloc, public RefCounted
|
||||
*/
|
||||
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.
|
||||
*/
|
||||
@@ -706,6 +716,35 @@ class InOrderDynInst : public FastAlloc, public RefCounted
|
||||
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.
|
||||
*/
|
||||
@@ -770,7 +809,7 @@ class InOrderDynInst : public FastAlloc, public RefCounted
|
||||
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;
|
||||
}
|
||||
|
||||
|
||||
@@ -92,23 +92,26 @@ RegDepMap::insert(DynInstPtr inst)
|
||||
inst->staticInst->getName(),
|
||||
dest_regs);
|
||||
|
||||
for (int i = 0; i < dest_regs; i++)
|
||||
insert(inst->destRegIdx(i), inst);
|
||||
for (int i = 0; i < dest_regs; i++) {
|
||||
InOrderCPU::RegType reg_type;
|
||||
TheISA::RegIndex raw_idx = inst->destRegIdx(i);
|
||||
TheISA::RegIndex flat_idx = cpu->flattenRegIdx(raw_idx,
|
||||
reg_type,
|
||||
inst->threadNumber);
|
||||
inst->flattenDestReg(i, flat_idx);
|
||||
insert(reg_type, flat_idx, inst);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
RegDepMap::insert(RegIndex idx, DynInstPtr inst)
|
||||
RegDepMap::insert(uint8_t reg_type, RegIndex idx, DynInstPtr inst)
|
||||
{
|
||||
InOrderCPU::RegType reg_type;
|
||||
TheISA::RegIndex flat_idx = cpu->flattenRegIdx(idx, reg_type,
|
||||
inst->threadNumber);
|
||||
|
||||
DPRINTF(RegDepMap, "Inserting [sn:%i] onto %s dep. list for "
|
||||
"reg. idx %i (%i).\n", inst->seqNum, mapNames[reg_type],
|
||||
idx, flat_idx);
|
||||
"reg. idx %i.\n", inst->seqNum, mapNames[reg_type],
|
||||
idx);
|
||||
|
||||
regMap[reg_type][flat_idx].push_back(inst);
|
||||
regMap[reg_type][idx].push_back(inst);
|
||||
|
||||
inst->setRegDepEntry();
|
||||
}
|
||||
@@ -179,36 +182,37 @@ RegDepMap::canRead(uint8_t reg_type, RegIndex idx, DynInstPtr inst)
|
||||
}
|
||||
|
||||
ThePipeline::DynInstPtr
|
||||
RegDepMap::canForward(uint8_t reg_type, unsigned reg_idx, DynInstPtr inst,
|
||||
unsigned clean_idx)
|
||||
RegDepMap::canForward(uint8_t reg_type, unsigned reg_idx, DynInstPtr inst)
|
||||
{
|
||||
std::list<DynInstPtr>::iterator list_it = regMap[reg_type][reg_idx].begin();
|
||||
std::list<DynInstPtr>::iterator list_end = regMap[reg_type][reg_idx].end();
|
||||
|
||||
DynInstPtr forward_inst = NULL;
|
||||
|
||||
// Look for first/oldest instruction
|
||||
// Look for instruction immediately in front of requestor to supply
|
||||
// data
|
||||
while (list_it != list_end &&
|
||||
(*list_it)->seqNum < inst->seqNum) {
|
||||
forward_inst = (*list_it);
|
||||
list_it++;
|
||||
}
|
||||
DPRINTF(RegDepMap, "[sn:%i] Found potential forwarding value for reg %i (%i)"
|
||||
" w/ [sn:%i]\n",
|
||||
inst->seqNum, reg_idx, clean_idx, inst->seqNum);
|
||||
|
||||
if (forward_inst) {
|
||||
int dest_reg_idx = forward_inst->getDestIdxNum(clean_idx);
|
||||
int dest_reg_idx = forward_inst->getDestIdxNum(reg_idx);
|
||||
assert(dest_reg_idx != -1);
|
||||
|
||||
DPRINTF(RegDepMap, "[sn:%i] Found potential forwarding value for reg %i "
|
||||
" w/ [sn:%i] dest. reg. #%i\n",
|
||||
inst->seqNum, reg_idx, forward_inst->seqNum, dest_reg_idx);
|
||||
|
||||
if (forward_inst->isExecuted() &&
|
||||
forward_inst->readResultTime(dest_reg_idx) < curTick()) {
|
||||
return forward_inst;
|
||||
} else {
|
||||
if (!forward_inst->isExecuted()) {
|
||||
DPRINTF(RegDepMap, "[sn:%i] Can't get value through "
|
||||
"forwarding, [sn:%i] has not been executed yet.\n",
|
||||
inst->seqNum, forward_inst->seqNum);
|
||||
"forwarding, [sn:%i] %s has not been executed yet.\n",
|
||||
inst->seqNum, forward_inst->seqNum, forward_inst->instName());
|
||||
} else if (forward_inst->readResultTime(dest_reg_idx) >= curTick()) {
|
||||
DPRINTF(RegDepMap, "[sn:%i] Can't get value through "
|
||||
"forwarding, [sn:%i] executed on tick:%i.\n",
|
||||
|
||||
@@ -77,7 +77,7 @@ class RegDepMap
|
||||
* another instruction for this destination register?
|
||||
*/
|
||||
DynInstPtr canForward(uint8_t reg_type, unsigned reg_idx,
|
||||
DynInstPtr inst, unsigned clean_idx);
|
||||
DynInstPtr inst);
|
||||
|
||||
/** find an instruction to forward/bypass a value from */
|
||||
DynInstPtr findBypassInst(RegIndex idx);
|
||||
@@ -94,9 +94,9 @@ class RegDepMap
|
||||
|
||||
private:
|
||||
/** Insert an instruction into a specific destination register index
|
||||
* onto map. This must be called w/the unflattened registered index
|
||||
* onto map.
|
||||
*/
|
||||
void insert(RegIndex idx, DynInstPtr inst);
|
||||
void insert(uint8_t reg_type, RegIndex idx, DynInstPtr inst);
|
||||
|
||||
/** Remove a specific instruction and dest. register index from map
|
||||
* This must be called w/the unflattened registered index
|
||||
|
||||
@@ -1075,7 +1075,7 @@ CacheUnitEvent::process()
|
||||
|
||||
//@todo: eventually, we should do a timing translation w/
|
||||
// hw page table walk on tlb miss
|
||||
DPRINTF(Fault, "Handling Fault %s\n", inst->fault->name());
|
||||
DPRINTF(Fault, "Handling Fault %s : [sn:%i] %x\n", inst->fault->name(), inst->seqNum, inst->getMemAddr());
|
||||
inst->fault->invoke(tlb_res->cpu->tcBase(tid), inst->staticInst);
|
||||
|
||||
tlb_res->tlbBlocked[tid] = false;
|
||||
|
||||
@@ -179,6 +179,7 @@ UseDefUnit::execute(int slot_idx)
|
||||
InOrderCPU::RegType reg_type;
|
||||
RegIndex reg_idx = inst->_srcRegIdx[ud_idx];
|
||||
RegIndex flat_idx = cpu->flattenRegIdx(reg_idx, reg_type, tid);
|
||||
inst->flattenSrcReg(ud_idx, flat_idx);
|
||||
|
||||
DPRINTF(InOrderUseDef, "[tid:%i]: [sn:%i]: Attempting to read source "
|
||||
"register idx %i (reg #%i, flat#%i).\n",
|
||||
@@ -246,12 +247,11 @@ UseDefUnit::execute(int slot_idx)
|
||||
// Look for forwarding opportunities
|
||||
DynInstPtr forward_inst = regDepMap[tid]->canForward(reg_type,
|
||||
flat_idx,
|
||||
inst,
|
||||
reg_idx);
|
||||
inst);
|
||||
|
||||
if (forward_inst) {
|
||||
int dest_reg_idx =
|
||||
forward_inst->getDestIdxNum(reg_idx);
|
||||
forward_inst->getDestIdxNum(flat_idx);
|
||||
|
||||
switch (reg_type)
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user