From 680ec0ec26436d6a716bed94933ad2c9caa32d80 Mon Sep 17 00:00:00 2001 From: Faith Ekstrand Date: Thu, 25 Jul 2024 13:01:43 -0500 Subject: [PATCH] nak/sm50: OpIAdd2 only supports one negate modifier Part-of: --- src/nouveau/compiler/nak/sm50.rs | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/src/nouveau/compiler/nak/sm50.rs b/src/nouveau/compiler/nak/sm50.rs index 58c6967f5c3..867e7b3425e 100644 --- a/src/nouveau/compiler/nak/sm50.rs +++ b/src/nouveau/compiler/nak/sm50.rs @@ -1122,10 +1122,25 @@ impl SM50Op for OpIAdd2 { use RegFile::GPR; let [src0, src1] = &mut self.srcs; swap_srcs_if_not_reg(src0, src1, GPR); + if src0.src_mod.is_ineg() && src1.src_mod.is_ineg() { + let val = b.alloc_ssa(GPR, 1); + b.push_op(OpIAdd2 { + dst: val.into(), + carry_out: Dst::None, + srcs: [Src::new_zero(), *src0], + }); + *src0 = val.into(); + } b.copy_alu_src_if_not_reg(src0, GPR, SrcType::I32); } fn encode(&self, e: &mut SM50Encoder<'_>) { + // Hardware requires at least one of these be unmodified. Otherwise, it + // encodes as iadd.po which isn't what we want. + assert!( + self.srcs[0].src_mod.is_none() || self.srcs[1].src_mod.is_none() + ); + let carry_out = match self.carry_out { Dst::Reg(reg) if reg.file() == RegFile::Carry => true, Dst::None => false,