aco: support DPP8

Reviewed-by: Rhys Perry <pendingchaos02@gmail.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/13971>
This commit is contained in:
Tatsuyuki Ishi
2021-11-29 00:12:04 +09:00
committed by Marge Bot
parent 5c3dfb4ef5
commit da0412e55b
12 changed files with 201 additions and 96 deletions

View File

@@ -292,12 +292,12 @@ convert_to_SDWA(chip_class chip, aco_ptr<Instruction>& instr)
}
bool
can_use_DPP(const aco_ptr<Instruction>& instr, bool pre_ra)
can_use_DPP(const aco_ptr<Instruction>& instr, bool pre_ra, bool dpp8)
{
assert(instr->isVALU() && !instr->operands.empty());
if (instr->isDPP())
return true;
return instr->isDPP8() == dpp8;
if (instr->operands.size() && instr->operands[0].isLiteral())
return false;
@@ -316,6 +316,8 @@ can_use_DPP(const aco_ptr<Instruction>& instr, bool pre_ra)
const VOP3_instruction* vop3 = &instr->vop3();
if (vop3->clamp || vop3->omod || vop3->opsel)
return false;
if (dpp8)
return false;
if (instr->format == Format::VOP3)
return false;
if (instr->operands.size() > 1 && !instr->operands[1].isOfType(RegType::vgpr))
@@ -331,29 +333,39 @@ can_use_DPP(const aco_ptr<Instruction>& instr, bool pre_ra)
}
aco_ptr<Instruction>
convert_to_DPP(aco_ptr<Instruction>& instr)
convert_to_DPP(aco_ptr<Instruction>& instr, bool dpp8)
{
if (instr->isDPP())
return NULL;
aco_ptr<Instruction> tmp = std::move(instr);
Format format =
(Format)(((uint32_t)tmp->format & ~(uint32_t)Format::VOP3) | (uint32_t)Format::DPP);
instr.reset(create_instruction<DPP_instruction>(tmp->opcode, format, tmp->operands.size(),
tmp->definitions.size()));
Format format = (Format)(((uint32_t)tmp->format & ~(uint32_t)Format::VOP3) |
(dpp8 ? (uint32_t)Format::DPP8 : (uint32_t)Format::DPP16));
if (dpp8)
instr.reset(create_instruction<DPP8_instruction>(tmp->opcode, format, tmp->operands.size(),
tmp->definitions.size()));
else
instr.reset(create_instruction<DPP16_instruction>(tmp->opcode, format, tmp->operands.size(),
tmp->definitions.size()));
std::copy(tmp->operands.cbegin(), tmp->operands.cend(), instr->operands.begin());
for (unsigned i = 0; i < instr->definitions.size(); i++)
instr->definitions[i] = tmp->definitions[i];
DPP_instruction* dpp = &instr->dpp();
dpp->dpp_ctrl = dpp_quad_perm(0, 1, 2, 3);
dpp->row_mask = 0xf;
dpp->bank_mask = 0xf;
if (dpp8) {
DPP8_instruction* dpp = &instr->dpp8();
for (unsigned i = 0; i < 8; i++)
dpp->lane_sel[i] = i;
} else {
DPP16_instruction* dpp = &instr->dpp16();
dpp->dpp_ctrl = dpp_quad_perm(0, 1, 2, 3);
dpp->row_mask = 0xf;
dpp->bank_mask = 0xf;
if (tmp->isVOP3()) {
const VOP3_instruction* vop3 = &tmp->vop3();
memcpy(dpp->neg, vop3->neg, sizeof(dpp->neg));
memcpy(dpp->abs, vop3->abs, sizeof(dpp->abs));
if (tmp->isVOP3()) {
const VOP3_instruction* vop3 = &tmp->vop3();
memcpy(dpp->neg, vop3->neg, sizeof(dpp->neg));
memcpy(dpp->abs, vop3->abs, sizeof(dpp->abs));
}
}
if (instr->isVOPC() || instr->definitions.size() > 1)