cfg: Add one more divergence case

* Seen in RDR shaders
This commit is contained in:
IndecisiveTurtle 2024-08-18 00:07:24 +03:00
parent 63938ba8dd
commit 68c465813c
2 changed files with 6 additions and 3 deletions

View File

@ -37,6 +37,7 @@ static IR::Condition MakeCondition(Opcode opcode) {
return IR::Condition::Execnz;
case Opcode::S_AND_SAVEEXEC_B64:
case Opcode::S_ANDN2_B64:
case Opcode::V_CMPX_NE_U32:
return IR::Condition::Execnz;
default:
return IR::Condition::True;
@ -93,7 +94,8 @@ void CFG::EmitDivergenceLabels() {
// While this instruction does not save EXEC it is often used paired
// with SAVEEXEC to mask the threads that didn't pass the condition
// of initial branch.
inst.opcode == Opcode::S_ANDN2_B64;
inst.opcode == Opcode::S_ANDN2_B64 ||
inst.opcode == Opcode::V_CMPX_NE_U32;
};
const auto is_close_scope = [](const GcnInst& inst) {
// Closing an EXEC scope can be either a branch instruction
@ -187,7 +189,8 @@ void CFG::LinkBlocks() {
const auto end_inst{block.end_inst};
// Handle divergence block inserted here.
if (end_inst.opcode == Opcode::S_AND_SAVEEXEC_B64 ||
end_inst.opcode == Opcode::S_ANDN2_B64) {
end_inst.opcode == Opcode::S_ANDN2_B64 ||
end_inst.opcode == Opcode::V_CMPX_NE_U32) {
// Blocks are stored ordered by address in the set
auto next_it = std::next(it);
auto* target_block = &(*next_it);

View File

@ -166,7 +166,7 @@ struct Liverpool {
static constexpr auto* GetBinaryInfo(const Shader& sh) {
const auto* code = sh.template Address<u32*>();
const auto* bininfo = std::bit_cast<const BinaryInfo*>(code + (code[1] + 1) * 2);
ASSERT_MSG(bininfo->Valid(), "Invalid shader binary header");
//ASSERT_MSG(bininfo->Valid(), "Invalid shader binary header");
return bininfo;
}