summaryrefslogtreecommitdiff
path: root/src/cpu/o3
diff options
context:
space:
mode:
Diffstat (limited to 'src/cpu/o3')
-rw-r--r--src/cpu/o3/free_list.hh9
-rw-r--r--src/cpu/o3/iew_impl.hh13
-rw-r--r--src/cpu/o3/inst_queue_impl.hh13
-rw-r--r--src/cpu/o3/regfile.cc6
-rw-r--r--src/cpu/o3/regfile.hh6
-rw-r--r--src/cpu/o3/rename_impl.hh8
-rw-r--r--src/cpu/o3/rename_map.cc25
7 files changed, 51 insertions, 29 deletions
diff --git a/src/cpu/o3/free_list.hh b/src/cpu/o3/free_list.hh
index 46bebf30d..82ff25d3b 100644
--- a/src/cpu/o3/free_list.hh
+++ b/src/cpu/o3/free_list.hh
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2016-2017 ARM Limited
+ * Copyright (c) 2016-2018 ARM Limited
* All rights reserved
*
* The license below extends only to copyright in the software and shall
@@ -79,10 +79,9 @@ class SimpleFreeList
template<class InputIt>
void
addRegs(InputIt first, InputIt last) {
- std::for_each(first, last,
- [this](const typename InputIt::value_type& reg) {
- this->freeRegs.push(&reg);
- });
+ std::for_each(first, last, [this](typename InputIt::value_type& reg) {
+ this->freeRegs.push(&reg);
+ });
}
/** Get the next available register from the free list */
diff --git a/src/cpu/o3/iew_impl.hh b/src/cpu/o3/iew_impl.hh
index 56c182564..5872f90d2 100644
--- a/src/cpu/o3/iew_impl.hh
+++ b/src/cpu/o3/iew_impl.hh
@@ -1480,11 +1480,14 @@ DefaultIEW<Impl>::writebackInsts()
int dependents = instQueue.wakeDependents(inst);
for (int i = 0; i < inst->numDestRegs(); i++) {
- //mark as Ready
- DPRINTF(IEW,"Setting Destination Register %i (%s)\n",
- inst->renamedDestRegIdx(i)->index(),
- inst->renamedDestRegIdx(i)->className());
- scoreboard->setReg(inst->renamedDestRegIdx(i));
+ // Mark register as ready if not pinned
+ if (inst->renamedDestRegIdx(i)->
+ getNumPinnedWritesToComplete() == 0) {
+ DPRINTF(IEW,"Setting Destination Register %i (%s)\n",
+ inst->renamedDestRegIdx(i)->index(),
+ inst->renamedDestRegIdx(i)->className());
+ scoreboard->setReg(inst->renamedDestRegIdx(i));
+ }
}
if (dependents) {
diff --git a/src/cpu/o3/inst_queue_impl.hh b/src/cpu/o3/inst_queue_impl.hh
index 20b41e51d..c3e3fdf32 100644
--- a/src/cpu/o3/inst_queue_impl.hh
+++ b/src/cpu/o3/inst_queue_impl.hh
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2011-2014, 2017-2018 ARM Limited
+ * Copyright (c) 2011-2014, 2017-2019 ARM Limited
* Copyright (c) 2013 Advanced Micro Devices, Inc.
* All rights reserved.
*
@@ -1033,6 +1033,17 @@ InstructionQueue<Impl>::wakeDependents(const DynInstPtr &completed_inst)
continue;
}
+ // Avoid waking up dependents if the register is pinned
+ dest_reg->decrNumPinnedWritesToComplete();
+ if (dest_reg->isPinned())
+ completed_inst->setPinnedRegsWritten();
+
+ if (dest_reg->getNumPinnedWritesToComplete() != 0) {
+ DPRINTF(IQ, "Reg %d [%s] is pinned, skipping\n",
+ dest_reg->index(), dest_reg->className());
+ continue;
+ }
+
DPRINTF(IQ, "Waking any dependents on register %i (%s).\n",
dest_reg->index(),
dest_reg->className());
diff --git a/src/cpu/o3/regfile.cc b/src/cpu/o3/regfile.cc
index cc4bba6b0..afed8f9fa 100644
--- a/src/cpu/o3/regfile.cc
+++ b/src/cpu/o3/regfile.cc
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2016-2017 ARM Limited
+ * Copyright (c) 2016-2018 ARM Limited
* All rights reserved
*
* The license below extends only to copyright in the software and shall
@@ -216,8 +216,8 @@ PhysRegFile::getRegIds(RegClass cls) -> IdRange
return std::make_pair(miscRegIds.begin(), miscRegIds.end());
}
/* There is no way to make an empty iterator */
- return std::make_pair(PhysIds::const_iterator(),
- PhysIds::const_iterator());
+ return std::make_pair(PhysIds::iterator(),
+ PhysIds::iterator());
}
PhysRegIdPtr
diff --git a/src/cpu/o3/regfile.hh b/src/cpu/o3/regfile.hh
index d4b6602ad..352e6ac93 100644
--- a/src/cpu/o3/regfile.hh
+++ b/src/cpu/o3/regfile.hh
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2016-2017 ARM Limited
+ * Copyright (c) 2016-2018 ARM Limited
* All rights reserved
*
* The license below extends only to copyright in the software and shall
@@ -70,8 +70,8 @@ class PhysRegFile
using VecMode = Enums::VecRegRenameMode;
using VecPredRegContainer = TheISA::VecPredRegContainer;
public:
- using IdRange = std::pair<PhysIds::const_iterator,
- PhysIds::const_iterator>;
+ using IdRange = std::pair<PhysIds::iterator,
+ PhysIds::iterator>;
private:
static constexpr auto NumVecElemPerVecReg = TheISA::NumVecElemPerVecReg;
diff --git a/src/cpu/o3/rename_impl.hh b/src/cpu/o3/rename_impl.hh
index 43f0b2746..d55bed655 100644
--- a/src/cpu/o3/rename_impl.hh
+++ b/src/cpu/o3/rename_impl.hh
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2010-2012, 2014-2016 ARM Limited
+ * Copyright (c) 2010-2012, 2014-2019 ARM Limited
* Copyright (c) 2013 Advanced Micro Devices, Inc.
* All rights reserved.
*
@@ -976,7 +976,9 @@ DefaultRename<Impl>::doSquash(const InstSeqNum &squashed_seq_num, ThreadID tid)
assert(hb_it != historyBuffer[tid].end());
DPRINTF(Rename, "[tid:%i] Removing history entry with sequence "
- "number %i.\n", tid, hb_it->instSeqNum);
+ "number %i (archReg: %d, newPhysReg: %d, prevPhysReg: %d).\n",
+ tid, hb_it->instSeqNum, hb_it->archReg.index(),
+ hb_it->newPhysReg->index(), hb_it->prevPhysReg->index());
// Undo the rename mapping only if it was really a change.
// Special regs that are not really renamed (like misc regs
@@ -1140,12 +1142,12 @@ DefaultRename<Impl>::renameDestRegs(const DynInstPtr &inst, ThreadID tid)
typename RenameMap::RenameInfo rename_result;
RegId flat_dest_regid = tc->flattenRegId(dest_reg);
+ flat_dest_regid.setNumPinnedWrites(dest_reg.getNumPinnedWrites());
rename_result = map->rename(flat_dest_regid);
inst->flattenDestReg(dest_idx, flat_dest_regid);
- // Mark Scoreboard entry as not ready
scoreboard->unsetReg(rename_result.first);
DPRINTF(Rename,
diff --git a/src/cpu/o3/rename_map.cc b/src/cpu/o3/rename_map.cc
index 9d912e582..64f3dbf8c 100644
--- a/src/cpu/o3/rename_map.cc
+++ b/src/cpu/o3/rename_map.cc
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2016-2017,2019 ARM Limited
+ * Copyright (c) 2016-2018,2019 ARM Limited
* All rights reserved
*
* The license below extends only to copyright in the software and shall
@@ -78,16 +78,23 @@ SimpleRenameMap::rename(const RegId& arch_reg)
// requested architected register.
PhysRegIdPtr prev_reg = map[arch_reg.flatIndex()];
- // If it's not referencing the zero register, then rename the
- // register.
- if (arch_reg != zeroReg) {
- renamed_reg = freeList->getReg();
-
- map[arch_reg.flatIndex()] = renamed_reg;
- } else {
- // Otherwise return the zero register so nothing bad happens.
+ if (arch_reg == zeroReg) {
assert(prev_reg->isZeroReg());
renamed_reg = prev_reg;
+ } else if (prev_reg->getNumPinnedWrites() > 0) {
+ // Do not rename if the register is pinned
+ assert(arch_reg.getNumPinnedWrites() == 0); // Prevent pinning the
+ // same register twice
+ DPRINTF(Rename, "Renaming pinned reg, numPinnedWrites %d\n",
+ prev_reg->getNumPinnedWrites());
+ renamed_reg = prev_reg;
+ renamed_reg->decrNumPinnedWrites();
+ } else {
+ renamed_reg = freeList->getReg();
+ map[arch_reg.flatIndex()] = renamed_reg;
+ renamed_reg->setNumPinnedWrites(arch_reg.getNumPinnedWrites());
+ renamed_reg->setNumPinnedWritesToComplete(
+ arch_reg.getNumPinnedWrites() + 1);
}
DPRINTF(Rename, "Renamed reg %d to physical reg %d (%d) old mapping was"