shader: keep fragment layer values under lane masks

Co-authored-by: shadowbeat070 <70843316+shadowbeat070@users.noreply.github.com>
This commit is contained in:
nmzik
2026-09-05 11:43:49 +04:00
parent 2ec0e9e8f3
commit b96a30ed88
16 changed files with 458 additions and 25 deletions
@@ -259,13 +259,20 @@ void Translator::S_MOV_B64(const Decoder::Instruction& inst) {
}
void Translator::S_WQM_B64(const Decoder::Instruction& inst) {
const auto mask_valid = ReadMaskValid(inst.src0);
const auto source_mask = ReadMask(inst.src0);
const auto mask_valid = ReadMaskValid(inst.src0);
const auto result =
IR::U64(ir.Emit(IR::ValueOpcode::WqmU64, {ReadOperand(inst.src0, IR::Type::U64)}));
// WQM activates whole quads and cannot clear an already active lane.
const auto widened_mask = ir.LogicalOr(source_mask, ThreadBit(ExtractU64(result)));
WriteOperand(DestinationOperand(inst), result);
if (inst.dst.kind == Decoder::OperandKind::Sgpr) {
if (inst.dst.kind == Decoder::OperandKind::ExecLo) {
ir.SetExec(widened_mask);
} else if (inst.dst.kind == Decoder::OperandKind::VccLo) {
ir.SetVcc(widened_mask);
} else if (inst.dst.kind == Decoder::OperandKind::Sgpr) {
const auto dst = static_cast<IR::ScalarReg>(inst.dst.reg);
ir.SetThreadBitScalarReg(dst, ThreadBit(ExtractU64(result)));
ir.SetThreadBitScalarReg(dst, widened_mask);
ir.SetScalarMaskTag(dst, mask_valid);
}
ir.SetScc(IR::U1(ir.Emit(IR::ValueOpcode::INotEqual64, {result, IR::Value(uint64_t {0})})));
@@ -1137,9 +1137,13 @@ IR::Program TranslateProgram(const Decoder::Program& decoded, const CFG::Graph&
builtin(IR::StageInputKind::FragCoord, 3));
}
if (ps->ps_front_face) {
entry_ir.SetVectorReg(static_cast<IR::VectorReg>(reg),
entry_ir.SetVectorReg(static_cast<IR::VectorReg>(reg++),
builtin(IR::StageInputKind::FrontFacing));
}
if (ps->ps_ancillary) {
entry_ir.SetVectorReg(static_cast<IR::VectorReg>(reg),
builtin(IR::StageInputKind::PackedAncillary));
}
} else if (options.stage == ShaderType::Vertex) {
entry_ir.SetVectorReg(static_cast<IR::VectorReg>(5),
builtin(IR::StageInputKind::VertexIndex));