summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorFrancisco Jerez <[email protected]>2012-04-06 19:16:04 +0200
committerChristoph Bumiller <[email protected]>2012-04-14 21:54:02 +0200
commit530ff61ba77f940f6f4093956b99221ab62ab430 (patch)
treea08809afd47b2881d1a19cf3e8dd5b590d5889b8
parented255dbae2ada50cbdb71f6b03f4e42d3ed7ebc6 (diff)
nv50/ir: Take into account function args in the live range calculation code.
-rw-r--r--src/gallium/drivers/nv50/codegen/nv50_ir_ra.cpp22
-rw-r--r--src/gallium/drivers/nv50/codegen/nv50_ir_ssa.cpp9
2 files changed, 28 insertions, 3 deletions
diff --git a/src/gallium/drivers/nv50/codegen/nv50_ir_ra.cpp b/src/gallium/drivers/nv50/codegen/nv50_ir_ra.cpp
index a08ca31ff84..3f825461956 100644
--- a/src/gallium/drivers/nv50/codegen/nv50_ir_ra.cpp
+++ b/src/gallium/drivers/nv50/codegen/nv50_ir_ra.cpp
@@ -268,7 +268,8 @@ RegAlloc::BuildIntervalsPass::addLiveRange(Value *val,
Instruction *insn = val->getUniqueInsn();
if (!insn)
- return;
+ insn = bb->getFirst();
+
assert(bb->getFirst()->serial <= bb->getExit()->serial);
assert(bb->getExit()->serial + 1 >= end);
@@ -420,6 +421,7 @@ RegAlloc::ArgumentMovesPass::visit(BasicBlock *bb)
bool
RegAlloc::buildLiveSets(BasicBlock *bb)
{
+ Function *f = bb->getFunction();
BasicBlock *bn;
Instruction *i;
unsigned int s, d;
@@ -453,6 +455,14 @@ RegAlloc::buildLiveSets(BasicBlock *bb)
// if (!bb->getEntry())
// return true;
+ if (bb == BasicBlock::get(f->cfgExit)) {
+ for (std::deque<ValueRef>::iterator it = f->outs.begin();
+ it != f->outs.end(); ++it) {
+ assert(it->get()->asLValue());
+ bb->liveSet.set(it->get()->id);
+ }
+ }
+
for (i = bb->getExit(); i && i != bb->getEntry()->prev; i = i->prev) {
for (d = 0; i->defExists(d); ++d)
bb->liveSet.clr(i->getDef(d)->id);
@@ -476,8 +486,6 @@ RegAlloc::BuildIntervalsPass::collectLiveValues(BasicBlock *bb)
{
BasicBlock *bbA = NULL, *bbB = NULL;
- assert(bb->cfg.incidentCount() || bb->liveSet.popCount() == 0);
-
if (bb->cfg.outgoingCount()) {
// trickery to save a loop of OR'ing liveSets
// aliasing works fine with BitSet::setOr
@@ -548,6 +556,14 @@ RegAlloc::BuildIntervalsPass::visit(BasicBlock *bb)
}
}
+ if (bb == BasicBlock::get(func->cfg.getRoot())) {
+ for (std::deque<ValueDef>::iterator it = func->ins.begin();
+ it != func->ins.end(); ++it) {
+ if (it->get()->reg.data.id >= 0) // add hazard for fixed regs
+ it->get()->livei.extend(0, 1);
+ }
+ }
+
return true;
}
diff --git a/src/gallium/drivers/nv50/codegen/nv50_ir_ssa.cpp b/src/gallium/drivers/nv50/codegen/nv50_ir_ssa.cpp
index 88a9911816a..38a37efdd4f 100644
--- a/src/gallium/drivers/nv50/codegen/nv50_ir_ssa.cpp
+++ b/src/gallium/drivers/nv50/codegen/nv50_ir_ssa.cpp
@@ -219,6 +219,7 @@ void DominatorTree::findDominanceFrontiers()
void
Function::buildLiveSetsPreSSA(BasicBlock *bb, const int seq)
{
+ Function *f = bb->getFunction();
BitSet usedBeforeAssigned(allLValues.getSize(), true);
BitSet assigned(allLValues.getSize(), true);
@@ -248,6 +249,14 @@ Function::buildLiveSetsPreSSA(BasicBlock *bb, const int seq)
assigned.set(i->getDef(d)->id);
}
+ if (bb == BasicBlock::get(f->cfgExit)) {
+ for (std::deque<ValueRef>::iterator it = f->outs.begin();
+ it != f->outs.end(); ++it) {
+ if (!assigned.test(it->get()->id))
+ usedBeforeAssigned.set(it->get()->id);
+ }
+ }
+
bb->liveSet.andNot(assigned);
bb->liveSet |= usedBeforeAssigned;
}