aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTakoroka <137927095+Takoroka@users.noreply.github.com>2026-10-30 12:25:13 -0400
committerTakoroka <137927095+Takoroka@users.noreply.github.com>2026-11-01 11:08:23 -0500
commite71bb09e2da08fe7f19846e0010cf8e9e5ddb53e (patch)
tree7a6b7df01b59fb7205361724d3d979b58113a1c7
parent6a96ec2cdcd83436b714664b628d9420d6bd9cf1 (diff)
nx2: lower UPRMT
Nintendo Switch Sports Resort's pixel shaders take bytes of a uniform register with UPRMT (immediate selector, URZ third source). Rewrite it to PRMT on the registers its uniform registers live in, as the other uniform arithmetic is.
-rw-r--r--src/shader_recompiler/frontend/ampere/lower_to_maxwell.h7
1 files changed, 4 insertions, 3 deletions
diff --git a/src/shader_recompiler/frontend/ampere/lower_to_maxwell.h b/src/shader_recompiler/frontend/ampere/lower_to_maxwell.h
index 272707b1c1..d7204fed44 100644
--- a/src/shader_recompiler/frontend/ampere/lower_to_maxwell.h
+++ b/src/shader_recompiler/frontend/ampere/lower_to_maxwell.h
@@ -55,7 +55,7 @@ inline LoweredProgram LowerToMaxwell(std::span<const Instruction> code) {
bool uses_uniform_bank = false;
for (const auto& instruction : code) {
const u32 op = instruction.Bits(0, 12);
- uses_uniform_bank |= op == 0x3c4 || op == 0x2bd || op == 0xf60 || op == 0xc11 || op == 0xd08 || op == 0xc0c || op == 0x986 || op == 0x9a8 || op == 0xc12 || op == 0xc17 || op == 0xe24 || op == 0xc24 || op == 0xd00 || op == 0xd09 || op == 0x9c3 || op == 0xc45 || op == 0x2a4 || op == 0x891 || op == 0x890 || op == 0x290 || op == 0x28c || op == 0x88c || op == 0x287 || op == 0x887 || op == 0x958 || op == 0xab9 || op == 0xabb || op == 0x899 || op == 0xc20 || op == 0xe21 || op == 0xe23 || op == 0xc02 ||
+ uses_uniform_bank |= op == 0x3c4 || op == 0x2bd || op == 0x896 || op == 0xf60 || op == 0xc11 || op == 0xd08 || op == 0xc0c || op == 0x986 || op == 0x9a8 || op == 0xc12 || op == 0xc17 || op == 0xe24 || op == 0xc24 || op == 0xd00 || op == 0xd09 || op == 0x9c3 || op == 0xc45 || op == 0x2a4 || op == 0x891 || op == 0x890 || op == 0x290 || op == 0x28c || op == 0x88c || op == 0x287 || op == 0x887 || op == 0x958 || op == 0xab9 || op == 0xabb || op == 0x899 || op == 0xc20 || op == 0xe21 || op == 0xe23 || op == 0xc02 ||
op == 0x886 || op == 0x3c2 || op == 0xc82 || op == 0x882 || op == 0x292 || op == 0x892 || op == 0x291 || op == 0x981 || op == 0xc13 || op == 0xc10 || op == 0xc23 || op == 0x526 || op == 0x2be || op == 0x8a4 || op == 0xd05 || (op == 0x984 && instruction.Bits(91, 1)) || op == 0x89c || op == 0x883 || op == 0x2a5 || op == 0xd06 || op == 0x299 || op == 0xc09 || (op == 0x81c && instruction.Bits(67, 1));
}
const auto address_of = [](u32 index) { return 0x50U + index * 8 + ((index + 1) / 3) * 8; };
@@ -116,7 +116,7 @@ inline LoweredProgram LowerToMaxwell(std::span<const Instruction> code) {
bool uniform_guard = false;
u32 uniform_output = 7; // ULOP3's UPn output: computed in P(6-n), then merged into R239
if (opcode == 0x2a4 || opcode == 0x8a4 || opcode == 0x891 || opcode == 0x890 || opcode == 0x290 ||
- opcode == 0x292 || opcode == 0x892 || opcode == 0x291) {
+ opcode == 0x292 || opcode == 0x892 || opcode == 0x291 || opcode == 0x896) {
if (insn.Bits(12, 4) != 7 && opcode != 0x292 && opcode != 0x892)
return fail(index, "native uniform arithmetic predication");
uniform_guard = insn.Bits(12, 4) != 7;
@@ -138,7 +138,8 @@ inline LoweredProgram LowerToMaxwell(std::span<const Instruction> code) {
insn.words[2] = (insn.words[2] & ~(7U << 17)) | ((6 - uniform_output) << 17);
}
opcode = opcode == 0x2a4 ? 0x224 : opcode == 0x8a4 ? 0x824 : opcode == 0x891 ? 0x811 : opcode == 0x890 ? 0x810
- : opcode == 0x292 ? 0x212 : opcode == 0x892 ? 0x812 : opcode == 0x291 ? 0x211 : 0x210;
+ : opcode == 0x292 ? 0x212 : opcode == 0x892 ? 0x812 : opcode == 0x291 ? 0x211
+ : opcode == 0x896 ? 0x816 : 0x210;
}
const bool uniform_predication = opcode == 0xabb || opcode == 0xab9 || opcode == 0xc82 || opcode == 0x882;
const u32 native_predicate = insn.Bits(12, 4);