mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
Bug 1058095 - IonMonkey: Move fields from InstructionData into LInstruction r=bhackett
This commit is contained in:
parent
cf2b0c46a6
commit
e29bfc0ecb
@ -249,7 +249,7 @@ BacktrackingAllocator::tryGroupReusedRegister(uint32_t def, uint32_t use)
|
||||
return true;
|
||||
}
|
||||
LiveInterval *interval = usedReg.getInterval(0);
|
||||
LBlock *block = insData[reg.ins()].block();
|
||||
LBlock *block = reg.ins()->block();
|
||||
|
||||
// The input's lifetime must end within the same block as the definition,
|
||||
// otherwise it could live on in phis elsewhere.
|
||||
@ -263,7 +263,7 @@ BacktrackingAllocator::tryGroupReusedRegister(uint32_t def, uint32_t use)
|
||||
continue;
|
||||
|
||||
LUse *use = iter->use;
|
||||
if (FindReusingDefinition(insData[iter->pos].ins(), use)) {
|
||||
if (FindReusingDefinition(insData[iter->pos], use)) {
|
||||
reg.setMustCopyInput();
|
||||
return true;
|
||||
}
|
||||
@ -958,16 +958,16 @@ BacktrackingAllocator::resolveControlFlow()
|
||||
continue;
|
||||
|
||||
CodePosition start = interval->start();
|
||||
InstructionData *data = &insData[start];
|
||||
if (interval->start() > entryOf(data->block())) {
|
||||
MOZ_ASSERT(start == inputOf(data->ins()) || start == outputOf(data->ins()));
|
||||
LInstruction *ins = insData[start];
|
||||
if (interval->start() > entryOf(ins->block())) {
|
||||
MOZ_ASSERT(start == inputOf(ins) || start == outputOf(ins));
|
||||
|
||||
LiveInterval *prevInterval = reg->intervalFor(start.previous());
|
||||
if (start.subpos() == CodePosition::INPUT) {
|
||||
if (!moveInput(inputOf(data->ins()), prevInterval, interval, reg->type()))
|
||||
if (!moveInput(inputOf(ins), prevInterval, interval, reg->type()))
|
||||
return false;
|
||||
} else {
|
||||
if (!moveAfter(outputOf(data->ins()), prevInterval, interval, reg->type()))
|
||||
if (!moveAfter(outputOf(ins), prevInterval, interval, reg->type()))
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@ -1119,7 +1119,7 @@ BacktrackingAllocator::reifyAllocations()
|
||||
|
||||
// For any uses which feed into MUST_REUSE_INPUT definitions,
|
||||
// add copies if the use and def have different allocations.
|
||||
LInstruction *ins = insData[iter->pos].ins();
|
||||
LInstruction *ins = insData[iter->pos];
|
||||
if (LDefinition *def = FindReusingDefinition(ins, alloc)) {
|
||||
LiveInterval *outputInterval =
|
||||
vregs[def->virtualRegister()].intervalFor(outputOf(ins));
|
||||
@ -1403,12 +1403,12 @@ BacktrackingAllocator::minimalInterval(const LiveInterval *interval, bool *pfixe
|
||||
if (fixed)
|
||||
return false;
|
||||
fixed = true;
|
||||
if (minimalUse(interval, insData[iter->pos].ins()))
|
||||
if (minimalUse(interval, insData[iter->pos]))
|
||||
minimal = true;
|
||||
break;
|
||||
|
||||
case LUse::REGISTER:
|
||||
if (minimalUse(interval, insData[iter->pos].ins()))
|
||||
if (minimalUse(interval, insData[iter->pos]))
|
||||
minimal = true;
|
||||
break;
|
||||
|
||||
@ -1540,7 +1540,7 @@ BacktrackingAllocator::trySplitAfterLastRegisterUse(LiveInterval *interval, Live
|
||||
// If the definition of the interval is in a register, consider that a
|
||||
// register use too for our purposes here.
|
||||
if (isRegisterDefinition(interval)) {
|
||||
CodePosition spillStart = minimalDefEnd(insData[interval->start()].ins()).next();
|
||||
CodePosition spillStart = minimalDefEnd(insData[interval->start()]).next();
|
||||
if (!conflict || spillStart < conflict->start()) {
|
||||
lastUse = lastRegisterFrom = interval->start();
|
||||
lastRegisterTo = spillStart;
|
||||
@ -1552,7 +1552,7 @@ BacktrackingAllocator::trySplitAfterLastRegisterUse(LiveInterval *interval, Live
|
||||
iter++)
|
||||
{
|
||||
LUse *use = iter->use;
|
||||
LInstruction *ins = insData[iter->pos].ins();
|
||||
LInstruction *ins = insData[iter->pos];
|
||||
|
||||
// Uses in the interval should be sorted.
|
||||
MOZ_ASSERT(iter->pos >= lastUse);
|
||||
@ -1609,7 +1609,7 @@ BacktrackingAllocator::trySplitBeforeFirstRegisterUse(LiveInterval *interval, Li
|
||||
iter++)
|
||||
{
|
||||
LUse *use = iter->use;
|
||||
LInstruction *ins = insData[iter->pos].ins();
|
||||
LInstruction *ins = insData[iter->pos];
|
||||
|
||||
if (!conflict || outputOf(ins) >= conflict->end()) {
|
||||
if (isRegisterUse(use, ins, /* considerCopy = */ true)) {
|
||||
@ -1661,7 +1661,7 @@ BacktrackingAllocator::splitAtAllRegisterUses(LiveInterval *interval)
|
||||
// Treat the definition of the interval as a register use so that it
|
||||
// can be split and spilled ASAP.
|
||||
CodePosition from = interval->start();
|
||||
CodePosition to = minimalDefEnd(insData[from].ins()).next();
|
||||
CodePosition to = minimalDefEnd(insData[from]).next();
|
||||
if (!addLiveInterval(newIntervals, vreg, spillInterval, from, to))
|
||||
return false;
|
||||
spillStart = to;
|
||||
@ -1680,7 +1680,7 @@ BacktrackingAllocator::splitAtAllRegisterUses(LiveInterval *interval)
|
||||
iter != interval->usesEnd();
|
||||
iter++)
|
||||
{
|
||||
LInstruction *ins = insData[iter->pos].ins();
|
||||
LInstruction *ins = insData[iter->pos];
|
||||
if (iter->pos < spillStart) {
|
||||
newIntervals.back()->addUseAtEnd(new(alloc()) UsePosition(iter->use, iter->pos));
|
||||
} else if (isRegisterUse(iter->use, ins)) {
|
||||
@ -1748,7 +1748,7 @@ BacktrackingAllocator::splitAt(LiveInterval *interval,
|
||||
// Don't spill the interval until after the end of its definition.
|
||||
CodePosition spillStart = interval->start();
|
||||
if (isRegisterDefinition(interval))
|
||||
spillStart = minimalDefEnd(insData[interval->start()].ins()).next();
|
||||
spillStart = minimalDefEnd(insData[interval->start()]).next();
|
||||
|
||||
uint32_t vreg = interval->vreg();
|
||||
|
||||
@ -1782,7 +1782,7 @@ BacktrackingAllocator::splitAt(LiveInterval *interval,
|
||||
|
||||
size_t activeSplitPosition = NextSplitPosition(0, splitPositions, interval->start());
|
||||
for (UsePositionIterator iter(interval->usesBegin()); iter != interval->usesEnd(); iter++) {
|
||||
LInstruction *ins = insData[iter->pos].ins();
|
||||
LInstruction *ins = insData[iter->pos];
|
||||
if (iter->pos < spillStart) {
|
||||
newIntervals.back()->addUseAtEnd(new(alloc()) UsePosition(iter->use, iter->pos));
|
||||
activeSplitPosition = NextSplitPosition(activeSplitPosition, splitPositions, iter->pos);
|
||||
@ -1820,7 +1820,7 @@ BacktrackingAllocator::splitAt(LiveInterval *interval,
|
||||
else
|
||||
end = newInterval->usesBack()->pos.next();
|
||||
} else {
|
||||
start = inputOf(insData[newInterval->usesBegin()->pos].ins());
|
||||
start = inputOf(insData[newInterval->usesBegin()->pos]);
|
||||
end = newInterval->usesBack()->pos.next();
|
||||
}
|
||||
for (; activeRange > 0; --activeRange) {
|
||||
|
@ -110,7 +110,8 @@ LBlock::init(TempAllocator &alloc)
|
||||
if (!inputs)
|
||||
return false;
|
||||
|
||||
new (&phis_[phiIndex++]) LPhi(phi, inputs);
|
||||
LPhi *lphi = new (&phis_[phiIndex++]) LPhi(phi, inputs);
|
||||
lphi->setBlock(this);
|
||||
}
|
||||
}
|
||||
return true;
|
||||
|
@ -611,6 +611,10 @@ class LInstruction
|
||||
// to hold either gcthings or Values.
|
||||
LSafepoint *safepoint_;
|
||||
|
||||
LBlock *block_;
|
||||
LMoveGroup *inputMoves_;
|
||||
LMoveGroup *movesAfter_;
|
||||
|
||||
protected:
|
||||
MDefinition *mir_;
|
||||
|
||||
@ -618,6 +622,9 @@ class LInstruction
|
||||
: id_(0),
|
||||
snapshot_(nullptr),
|
||||
safepoint_(nullptr),
|
||||
block_(nullptr),
|
||||
inputMoves_(nullptr),
|
||||
movesAfter_(nullptr),
|
||||
mir_(nullptr)
|
||||
{ }
|
||||
|
||||
@ -697,6 +704,24 @@ class LInstruction
|
||||
/* Untyped MIR for this op. Prefer mir() methods in subclasses. */
|
||||
return mir_;
|
||||
}
|
||||
LBlock *block() const {
|
||||
return block_;
|
||||
}
|
||||
void setBlock(LBlock *block) {
|
||||
block_ = block;
|
||||
}
|
||||
LMoveGroup *inputMoves() const {
|
||||
return inputMoves_;
|
||||
}
|
||||
void setInputMoves(LMoveGroup *moves) {
|
||||
inputMoves_ = moves;
|
||||
}
|
||||
LMoveGroup *movesAfter() const {
|
||||
return movesAfter_;
|
||||
}
|
||||
void setMovesAfter(LMoveGroup *moves) {
|
||||
movesAfter_ = moves;
|
||||
}
|
||||
void assignSnapshot(LSnapshot *snapshot);
|
||||
void initSafepoint(TempAllocator &alloc);
|
||||
|
||||
@ -778,6 +803,7 @@ class LBlock
|
||||
bool init(TempAllocator &alloc);
|
||||
|
||||
void add(LInstruction *ins) {
|
||||
ins->setBlock(this);
|
||||
instructions_.pushBack(ins);
|
||||
}
|
||||
size_t numPhis() const {
|
||||
|
@ -420,7 +420,7 @@ LinearScanAllocator::reifyAllocations()
|
||||
return false;
|
||||
}
|
||||
}
|
||||
else if (interval->start() > entryOf(insData[interval->start()].block()) &&
|
||||
else if (interval->start() > entryOf(insData[interval->start()]->block()) &&
|
||||
(!reg->canonicalSpill() ||
|
||||
(reg->canonicalSpill() == interval->getAllocation() &&
|
||||
!reg->mustSpillAtDefinition()) ||
|
||||
@ -437,15 +437,15 @@ LinearScanAllocator::reifyAllocations()
|
||||
// register.
|
||||
LiveInterval *prevInterval = reg->getInterval(interval->index() - 1);
|
||||
CodePosition start = interval->start();
|
||||
InstructionData *data = &insData[start];
|
||||
LInstruction *ins = insData[start];
|
||||
|
||||
MOZ_ASSERT(start == inputOf(data->ins()) || start == outputOf(data->ins()));
|
||||
MOZ_ASSERT(start == inputOf(ins) || start == outputOf(ins));
|
||||
|
||||
if (start.subpos() == CodePosition::INPUT) {
|
||||
if (!moveInput(inputOf(data->ins()), prevInterval, interval, reg->type()))
|
||||
if (!moveInput(inputOf(ins), prevInterval, interval, reg->type()))
|
||||
return false;
|
||||
} else {
|
||||
if (!moveAfter(outputOf(data->ins()), prevInterval, interval, reg->type()))
|
||||
if (!moveAfter(outputOf(ins), prevInterval, interval, reg->type()))
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -789,7 +789,7 @@ LinearScanAllocator::assign(LAllocation allocation)
|
||||
|
||||
// If this spill is inside a loop, and the definition is outside
|
||||
// the loop, instead move the spill to outside the loop.
|
||||
InstructionData *other = &insData[current->start()];
|
||||
LInstruction *other = insData[current->start()];
|
||||
uint32_t loopDepthAtDef = reg->block()->mir()->loopDepth();
|
||||
uint32_t loopDepthAtSpill = other->block()->mir()->loopDepth();
|
||||
if (loopDepthAtSpill > loopDepthAtDef)
|
||||
|
@ -474,10 +474,10 @@ RegisterAllocator::init()
|
||||
for (size_t i = 0; i < graph.numBlocks(); i++) {
|
||||
LBlock *block = graph.getBlock(i);
|
||||
for (LInstructionIterator ins = block->begin(); ins != block->end(); ins++)
|
||||
insData[*ins].init(*ins, block);
|
||||
insData[ins->id()] = *ins;
|
||||
for (size_t j = 0; j < block->numPhis(); j++) {
|
||||
LPhi *phi = block->getPhi(j);
|
||||
insData[phi].init(phi, block);
|
||||
insData[phi->id()] = phi;
|
||||
}
|
||||
}
|
||||
|
||||
@ -485,38 +485,38 @@ RegisterAllocator::init()
|
||||
}
|
||||
|
||||
LMoveGroup *
|
||||
RegisterAllocator::getInputMoveGroup(uint32_t ins)
|
||||
RegisterAllocator::getInputMoveGroup(uint32_t id)
|
||||
{
|
||||
InstructionData *data = &insData[ins];
|
||||
MOZ_ASSERT(!data->ins()->isPhi());
|
||||
MOZ_ASSERT(!data->ins()->isLabel());
|
||||
LInstruction *ins = insData[id];
|
||||
MOZ_ASSERT(!ins->isPhi());
|
||||
MOZ_ASSERT(!ins->isLabel());
|
||||
|
||||
if (data->inputMoves())
|
||||
return data->inputMoves();
|
||||
if (ins->inputMoves())
|
||||
return ins->inputMoves();
|
||||
|
||||
LMoveGroup *moves = LMoveGroup::New(alloc());
|
||||
data->setInputMoves(moves);
|
||||
data->block()->insertBefore(data->ins(), moves);
|
||||
ins->setInputMoves(moves);
|
||||
ins->block()->insertBefore(ins, moves);
|
||||
|
||||
return moves;
|
||||
}
|
||||
|
||||
LMoveGroup *
|
||||
RegisterAllocator::getMoveGroupAfter(uint32_t ins)
|
||||
RegisterAllocator::getMoveGroupAfter(uint32_t id)
|
||||
{
|
||||
InstructionData *data = &insData[ins];
|
||||
MOZ_ASSERT(!data->ins()->isPhi());
|
||||
LInstruction *ins = insData[id];
|
||||
MOZ_ASSERT(!ins->isPhi());
|
||||
|
||||
if (data->movesAfter())
|
||||
return data->movesAfter();
|
||||
if (ins->movesAfter())
|
||||
return ins->movesAfter();
|
||||
|
||||
LMoveGroup *moves = LMoveGroup::New(alloc());
|
||||
data->setMovesAfter(moves);
|
||||
ins->setMovesAfter(moves);
|
||||
|
||||
if (data->ins()->isLabel())
|
||||
data->block()->insertAfter(data->block()->getEntryMoveGroup(alloc()), moves);
|
||||
if (ins->isLabel())
|
||||
ins->block()->insertAfter(ins->block()->getEntryMoveGroup(alloc()), moves);
|
||||
else
|
||||
data->block()->insertAfter(data->ins(), moves);
|
||||
ins->block()->insertAfter(ins, moves);
|
||||
return moves;
|
||||
}
|
||||
|
||||
|
@ -217,45 +217,10 @@ class CodePosition
|
||||
}
|
||||
};
|
||||
|
||||
// Structure to track moves inserted before or after an instruction.
|
||||
class InstructionData
|
||||
{
|
||||
LInstruction *ins_;
|
||||
LBlock *block_;
|
||||
LMoveGroup *inputMoves_;
|
||||
LMoveGroup *movesAfter_;
|
||||
|
||||
public:
|
||||
void init(LInstruction *ins, LBlock *block) {
|
||||
MOZ_ASSERT(!ins_);
|
||||
MOZ_ASSERT(!block_);
|
||||
ins_ = ins;
|
||||
block_ = block;
|
||||
}
|
||||
LInstruction *ins() const {
|
||||
return ins_;
|
||||
}
|
||||
LBlock *block() const {
|
||||
return block_;
|
||||
}
|
||||
void setInputMoves(LMoveGroup *moves) {
|
||||
inputMoves_ = moves;
|
||||
}
|
||||
LMoveGroup *inputMoves() const {
|
||||
return inputMoves_;
|
||||
}
|
||||
void setMovesAfter(LMoveGroup *moves) {
|
||||
movesAfter_ = moves;
|
||||
}
|
||||
LMoveGroup *movesAfter() const {
|
||||
return movesAfter_;
|
||||
}
|
||||
};
|
||||
|
||||
// Structure to track all moves inserted next to instructions in a graph.
|
||||
class InstructionDataMap
|
||||
{
|
||||
FixedList<InstructionData> insData_;
|
||||
FixedList<LInstruction *> insData_;
|
||||
|
||||
public:
|
||||
InstructionDataMap()
|
||||
@ -265,26 +230,20 @@ class InstructionDataMap
|
||||
bool init(MIRGenerator *gen, uint32_t numInstructions) {
|
||||
if (!insData_.init(gen->alloc(), numInstructions))
|
||||
return false;
|
||||
memset(&insData_[0], 0, sizeof(InstructionData) * numInstructions);
|
||||
memset(&insData_[0], 0, sizeof(LInstruction *) * numInstructions);
|
||||
return true;
|
||||
}
|
||||
|
||||
InstructionData &operator[](CodePosition pos) {
|
||||
LInstruction *&operator[](CodePosition pos) {
|
||||
return operator[](pos.ins());
|
||||
}
|
||||
const InstructionData &operator[](CodePosition pos) const {
|
||||
LInstruction *const &operator[](CodePosition pos) const {
|
||||
return operator[](pos.ins());
|
||||
}
|
||||
InstructionData &operator[](LInstruction *ins) {
|
||||
return operator[](ins->id());
|
||||
}
|
||||
const InstructionData &operator[](LInstruction *ins) const {
|
||||
return operator[](ins->id());
|
||||
}
|
||||
InstructionData &operator[](uint32_t ins) {
|
||||
LInstruction *&operator[](uint32_t ins) {
|
||||
return insData_[ins];
|
||||
}
|
||||
const InstructionData &operator[](uint32_t ins) const {
|
||||
LInstruction *const &operator[](uint32_t ins) const {
|
||||
return insData_[ins];
|
||||
}
|
||||
};
|
||||
@ -336,8 +295,8 @@ class RegisterAllocator
|
||||
// All phis in a block write their outputs after all of them have
|
||||
// read their inputs. Consequently, it doesn't make sense to talk
|
||||
// about code positions in the middle of a series of phis.
|
||||
if (insData[pos].ins()->isPhi()) {
|
||||
while (insData[pos + 1].ins()->isPhi())
|
||||
if (insData[pos]->isPhi()) {
|
||||
while (insData[pos + 1]->isPhi())
|
||||
++pos;
|
||||
}
|
||||
return CodePosition(pos, CodePosition::OUTPUT);
|
||||
@ -349,8 +308,8 @@ class RegisterAllocator
|
||||
// All phis in a block read their inputs before any of them write their
|
||||
// outputs. Consequently, it doesn't make sense to talk about code
|
||||
// positions in the middle of a series of phis.
|
||||
if (insData[pos].ins()->isPhi()) {
|
||||
while (pos > 0 && insData[pos - 1].ins()->isPhi())
|
||||
if (insData[pos]->isPhi()) {
|
||||
while (pos > 0 && insData[pos - 1]->isPhi())
|
||||
--pos;
|
||||
}
|
||||
return CodePosition(pos, CodePosition::INPUT);
|
||||
@ -365,8 +324,8 @@ class RegisterAllocator
|
||||
return outputOf(block->lastId());
|
||||
}
|
||||
|
||||
LMoveGroup *getInputMoveGroup(uint32_t ins);
|
||||
LMoveGroup *getMoveGroupAfter(uint32_t ins);
|
||||
LMoveGroup *getInputMoveGroup(uint32_t id);
|
||||
LMoveGroup *getMoveGroupAfter(uint32_t id);
|
||||
|
||||
LMoveGroup *getInputMoveGroup(CodePosition pos) {
|
||||
return getInputMoveGroup(pos.ins());
|
||||
@ -381,7 +340,7 @@ class RegisterAllocator
|
||||
// If moves are introduced between the instruction and the OSI point then
|
||||
// safepoint information for the instruction may be incorrect.
|
||||
while (true) {
|
||||
LInstruction *next = insData[outputOf(ins).next()].ins();
|
||||
LInstruction *next = insData[ins->id() + 1];
|
||||
if (!next->isNop() && !next->isOsiPoint())
|
||||
break;
|
||||
ins = next;
|
||||
|
Loading…
Reference in New Issue
Block a user