mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2026-05-05 00:58:05 +02:00
aco: use std::vector and IDSet in RA validator
Signed-off-by: Rhys Perry <pendingchaos02@gmail.com> Reviewed-by: Daniel Schürmann <daniel@schuermann.dev> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/13541>
This commit is contained in:
parent
b42f4b8809
commit
11602d2d36
1 changed files with 30 additions and 26 deletions
|
|
@ -670,6 +670,7 @@ struct Assignment {
|
|||
Location defloc;
|
||||
Location firstloc;
|
||||
PhysReg reg;
|
||||
bool valid;
|
||||
};
|
||||
|
||||
bool
|
||||
|
|
@ -849,7 +850,7 @@ validate_ra(Program* program)
|
|||
std::vector<std::vector<Temp>> phi_sgpr_ops(program->blocks.size());
|
||||
uint16_t sgpr_limit = get_addr_sgpr_from_waves(program, program->num_waves);
|
||||
|
||||
std::map<unsigned, Assignment> assignments;
|
||||
std::vector<Assignment> assignments(program->peekAllocationId());
|
||||
for (Block& block : program->blocks) {
|
||||
Location loc;
|
||||
loc.block = █
|
||||
|
|
@ -870,16 +871,16 @@ validate_ra(Program* program)
|
|||
continue;
|
||||
if (!op.isFixed())
|
||||
err |= ra_fail(program, loc, Location(), "Operand %d is not assigned a register", i);
|
||||
if (assignments.count(op.tempId()) && assignments[op.tempId()].reg != op.physReg())
|
||||
if (assignments[op.tempId()].valid && assignments[op.tempId()].reg != op.physReg())
|
||||
err |=
|
||||
ra_fail(program, loc, assignments.at(op.tempId()).firstloc,
|
||||
ra_fail(program, loc, assignments[op.tempId()].firstloc,
|
||||
"Operand %d has an inconsistent register assignment with instruction", i);
|
||||
if ((op.getTemp().type() == RegType::vgpr &&
|
||||
op.physReg().reg_b + op.bytes() > (256 + program->config->num_vgprs) * 4) ||
|
||||
(op.getTemp().type() == RegType::sgpr &&
|
||||
op.physReg() + op.size() > program->config->num_sgprs &&
|
||||
op.physReg() < sgpr_limit))
|
||||
err |= ra_fail(program, loc, assignments.at(op.tempId()).firstloc,
|
||||
err |= ra_fail(program, loc, assignments[op.tempId()].firstloc,
|
||||
"Operand %d has an out-of-bounds register assignment", i);
|
||||
if (op.physReg() == vcc && !program->needs_vcc)
|
||||
err |= ra_fail(program, loc, Location(),
|
||||
|
|
@ -889,8 +890,10 @@ validate_ra(Program* program)
|
|||
err |= ra_fail(program, loc, Location(), "Operand %d not aligned correctly", i);
|
||||
if (!assignments[op.tempId()].firstloc.block)
|
||||
assignments[op.tempId()].firstloc = loc;
|
||||
if (!assignments[op.tempId()].defloc.block)
|
||||
if (!assignments[op.tempId()].defloc.block) {
|
||||
assignments[op.tempId()].reg = op.physReg();
|
||||
assignments[op.tempId()].valid = true;
|
||||
}
|
||||
}
|
||||
|
||||
for (unsigned i = 0; i < instr->definitions.size(); i++) {
|
||||
|
|
@ -901,14 +904,14 @@ validate_ra(Program* program)
|
|||
err |=
|
||||
ra_fail(program, loc, Location(), "Definition %d is not assigned a register", i);
|
||||
if (assignments[def.tempId()].defloc.block)
|
||||
err |= ra_fail(program, loc, assignments.at(def.tempId()).defloc,
|
||||
err |= ra_fail(program, loc, assignments[def.tempId()].defloc,
|
||||
"Temporary %%%d also defined by instruction", def.tempId());
|
||||
if ((def.getTemp().type() == RegType::vgpr &&
|
||||
def.physReg().reg_b + def.bytes() > (256 + program->config->num_vgprs) * 4) ||
|
||||
(def.getTemp().type() == RegType::sgpr &&
|
||||
def.physReg() + def.size() > program->config->num_sgprs &&
|
||||
def.physReg() < sgpr_limit))
|
||||
err |= ra_fail(program, loc, assignments.at(def.tempId()).firstloc,
|
||||
err |= ra_fail(program, loc, assignments[def.tempId()].firstloc,
|
||||
"Definition %d has an out-of-bounds register assignment", i);
|
||||
if (def.physReg() == vcc && !program->needs_vcc)
|
||||
err |= ra_fail(program, loc, Location(),
|
||||
|
|
@ -920,6 +923,7 @@ validate_ra(Program* program)
|
|||
assignments[def.tempId()].firstloc = loc;
|
||||
assignments[def.tempId()].defloc = loc;
|
||||
assignments[def.tempId()].reg = def.physReg();
|
||||
assignments[def.tempId()].valid = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -931,23 +935,22 @@ validate_ra(Program* program)
|
|||
std::array<unsigned, 2048> regs; /* register file in bytes */
|
||||
regs.fill(0);
|
||||
|
||||
std::set<Temp> live;
|
||||
for (unsigned id : live_vars.live_out[block.index])
|
||||
live.insert(Temp(id, program->temp_rc[id]));
|
||||
IDSet live = live_vars.live_out[block.index];
|
||||
/* remove killed p_phi sgpr operands */
|
||||
for (Temp tmp : phi_sgpr_ops[block.index])
|
||||
live.erase(tmp);
|
||||
live.erase(tmp.id());
|
||||
|
||||
/* check live out */
|
||||
for (Temp tmp : live) {
|
||||
PhysReg reg = assignments.at(tmp.id()).reg;
|
||||
for (unsigned id : live) {
|
||||
Temp tmp(id, program->temp_rc[id]);
|
||||
PhysReg reg = assignments[id].reg;
|
||||
for (unsigned i = 0; i < tmp.bytes(); i++) {
|
||||
if (regs[reg.reg_b + i]) {
|
||||
err |= ra_fail(program, loc, Location(),
|
||||
"Assignment of element %d of %%%d already taken by %%%d in live-out",
|
||||
i, tmp.id(), regs[reg.reg_b + i]);
|
||||
i, id, regs[reg.reg_b + i]);
|
||||
}
|
||||
regs[reg.reg_b + i] = tmp.id();
|
||||
regs[reg.reg_b + i] = id;
|
||||
}
|
||||
}
|
||||
regs.fill(0);
|
||||
|
|
@ -958,7 +961,7 @@ validate_ra(Program* program)
|
|||
/* check killed p_phi sgpr operands */
|
||||
if (instr->opcode == aco_opcode::p_logical_end) {
|
||||
for (Temp tmp : phi_sgpr_ops[block.index]) {
|
||||
PhysReg reg = assignments.at(tmp.id()).reg;
|
||||
PhysReg reg = assignments[tmp.id()].reg;
|
||||
for (unsigned i = 0; i < tmp.bytes(); i++) {
|
||||
if (regs[reg.reg_b + i])
|
||||
err |= ra_fail(
|
||||
|
|
@ -966,14 +969,14 @@ validate_ra(Program* program)
|
|||
"Assignment of element %d of %%%d already taken by %%%d in live-out", i,
|
||||
tmp.id(), regs[reg.reg_b + i]);
|
||||
}
|
||||
live.emplace(tmp);
|
||||
live.insert(tmp.id());
|
||||
}
|
||||
}
|
||||
|
||||
for (const Definition& def : instr->definitions) {
|
||||
if (!def.isTemp())
|
||||
continue;
|
||||
live.erase(def.getTemp());
|
||||
live.erase(def.tempId());
|
||||
}
|
||||
|
||||
/* don't count phi operands as live-in, since they are actually
|
||||
|
|
@ -982,15 +985,16 @@ validate_ra(Program* program)
|
|||
for (const Operand& op : instr->operands) {
|
||||
if (!op.isTemp())
|
||||
continue;
|
||||
live.insert(op.getTemp());
|
||||
live.insert(op.tempId());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (Temp tmp : live) {
|
||||
PhysReg reg = assignments.at(tmp.id()).reg;
|
||||
for (unsigned id : live) {
|
||||
Temp tmp(id, program->temp_rc[id]);
|
||||
PhysReg reg = assignments[id].reg;
|
||||
for (unsigned i = 0; i < tmp.bytes(); i++)
|
||||
regs[reg.reg_b + i] = tmp.id();
|
||||
regs[reg.reg_b + i] = id;
|
||||
}
|
||||
|
||||
for (aco_ptr<Instruction>& instr : block.instructions) {
|
||||
|
|
@ -999,7 +1003,7 @@ validate_ra(Program* program)
|
|||
/* remove killed p_phi operands from regs */
|
||||
if (instr->opcode == aco_opcode::p_logical_end) {
|
||||
for (Temp tmp : phi_sgpr_ops[block.index]) {
|
||||
PhysReg reg = assignments.at(tmp.id()).reg;
|
||||
PhysReg reg = assignments[tmp.id()].reg;
|
||||
for (unsigned i = 0; i < tmp.bytes(); i++)
|
||||
regs[reg.reg_b + i] = 0;
|
||||
}
|
||||
|
|
@ -1021,11 +1025,11 @@ validate_ra(Program* program)
|
|||
if (!def.isTemp())
|
||||
continue;
|
||||
Temp tmp = def.getTemp();
|
||||
PhysReg reg = assignments.at(tmp.id()).reg;
|
||||
PhysReg reg = assignments[tmp.id()].reg;
|
||||
for (unsigned j = 0; j < tmp.bytes(); j++) {
|
||||
if (regs[reg.reg_b + j])
|
||||
err |= ra_fail(
|
||||
program, loc, assignments.at(regs[reg.reg_b + j]).defloc,
|
||||
program, loc, assignments[regs[reg.reg_b + j]].defloc,
|
||||
"Assignment of element %d of %%%d already taken by %%%d from instruction", i,
|
||||
tmp.id(), regs[reg.reg_b + j]);
|
||||
regs[reg.reg_b + j] = tmp.id();
|
||||
|
|
@ -1037,7 +1041,7 @@ validate_ra(Program* program)
|
|||
for (unsigned j = reg.byte() & ~(written - 1); j < written; j++) {
|
||||
unsigned written_reg = reg.reg() * 4u + j;
|
||||
if (regs[written_reg] && regs[written_reg] != def.tempId())
|
||||
err |= ra_fail(program, loc, assignments.at(regs[written_reg]).defloc,
|
||||
err |= ra_fail(program, loc, assignments[regs[written_reg]].defloc,
|
||||
"Assignment of element %d of %%%d overwrites the full register "
|
||||
"taken by %%%d from instruction",
|
||||
i, tmp.id(), regs[written_reg]);
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue