aco/spill: Reduce allocations in next_uses_per_block
Reviewed-by: Daniel Schürmann <daniel@schuermann.dev> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/11925>
This commit is contained in:
parent
a6bcda6a01
commit
a3ac3b231f
|
@ -171,13 +171,14 @@ void
|
|||
next_uses_per_block(spill_ctx& ctx, unsigned block_idx, uint32_t& worklist)
|
||||
{
|
||||
Block* block = &ctx.program->blocks[block_idx];
|
||||
std::unordered_map<Temp, std::pair<uint32_t, uint32_t>> next_uses =
|
||||
ctx.next_use_distances_end[block_idx];
|
||||
ctx.next_use_distances_start[block_idx] = ctx.next_use_distances_end[block_idx];
|
||||
auto& next_use_distances_start = ctx.next_use_distances_start[block_idx];
|
||||
|
||||
/* to compute the next use distance at the beginning of the block, we have to add the block's
|
||||
* size */
|
||||
for (std::unordered_map<Temp, std::pair<uint32_t, uint32_t>>::iterator it = next_uses.begin();
|
||||
it != next_uses.end(); ++it)
|
||||
for (std::unordered_map<Temp, std::pair<uint32_t, uint32_t>>::iterator it =
|
||||
next_use_distances_start.begin();
|
||||
it != next_use_distances_start.end(); ++it)
|
||||
it->second.second = it->second.second + block->instructions.size();
|
||||
|
||||
int idx = block->instructions.size() - 1;
|
||||
|
@ -189,7 +190,7 @@ next_uses_per_block(spill_ctx& ctx, unsigned block_idx, uint32_t& worklist)
|
|||
|
||||
for (const Definition& def : instr->definitions) {
|
||||
if (def.isTemp())
|
||||
next_uses.erase(def.getTemp());
|
||||
next_use_distances_start.erase(def.getTemp());
|
||||
}
|
||||
|
||||
for (const Operand& op : instr->operands) {
|
||||
|
@ -199,24 +200,24 @@ next_uses_per_block(spill_ctx& ctx, unsigned block_idx, uint32_t& worklist)
|
|||
if (op.regClass().type() == RegType::vgpr && op.regClass().is_linear())
|
||||
continue;
|
||||
if (op.isTemp())
|
||||
next_uses[op.getTemp()] = {block_idx, idx};
|
||||
next_use_distances_start[op.getTemp()] = {block_idx, idx};
|
||||
}
|
||||
idx--;
|
||||
}
|
||||
|
||||
assert(block_idx != 0 || next_uses.empty());
|
||||
ctx.next_use_distances_start[block_idx] = next_uses;
|
||||
assert(block_idx != 0 || next_use_distances_start.empty());
|
||||
std::unordered_set<Temp> phi_defs;
|
||||
while (idx >= 0) {
|
||||
aco_ptr<Instruction>& instr = block->instructions[idx];
|
||||
assert(instr->opcode == aco_opcode::p_linear_phi || instr->opcode == aco_opcode::p_phi);
|
||||
|
||||
std::pair<uint32_t, uint32_t> distance{block_idx, 0};
|
||||
|
||||
auto it = instr->definitions[0].isTemp() ? next_uses.find(instr->definitions[0].getTemp())
|
||||
: next_uses.end();
|
||||
if (it != next_uses.end()) {
|
||||
auto it = instr->definitions[0].isTemp() ? next_use_distances_start.find(instr->definitions[0].getTemp())
|
||||
: next_use_distances_start.end();
|
||||
if (it != next_use_distances_start.end() &&
|
||||
phi_defs.insert(instr->definitions[0].getTemp()).second) {
|
||||
distance = it->second;
|
||||
next_uses.erase(it);
|
||||
}
|
||||
|
||||
for (unsigned i = 0; i < instr->operands.size(); i++) {
|
||||
|
@ -236,8 +237,11 @@ next_uses_per_block(spill_ctx& ctx, unsigned block_idx, uint32_t& worklist)
|
|||
}
|
||||
|
||||
/* all remaining live vars must be live-out at the predecessors */
|
||||
for (std::pair<const Temp, std::pair<uint32_t, uint32_t>>& pair : next_uses) {
|
||||
for (std::pair<const Temp, std::pair<uint32_t, uint32_t>>& pair : next_use_distances_start) {
|
||||
Temp temp = pair.first;
|
||||
if (phi_defs.count(temp)) {
|
||||
continue;
|
||||
}
|
||||
uint32_t distance = pair.second.second;
|
||||
uint32_t dom = pair.second.first;
|
||||
std::vector<unsigned>& preds = temp.is_linear() ? block->linear_preds : block->logical_preds;
|
||||
|
|
Loading…
Reference in New Issue