[llvm] [AMDGPU] Add regbankselect rules for G_ADD/SUB and variants (PR #159860)

Anshil Gandhi via llvm-commits llvm-commits at lists.llvm.org
Tue Oct 28 11:16:54 PDT 2025


================
@@ -345,6 +346,25 @@ void AMDGPURegBankLegalizeCombiner::tryCombineS1AnyExt(MachineInstr &MI) {
   llvm_unreachable("missing anyext + trunc combine");
 }
 
+void AMDGPURegBankLegalizeCombiner::tryCombineTrunc(MachineInstr &MI) {
+  if (MI.getOpcode() != AMDGPU::G_TRUNC)
+    return;
+
+  Register Dst = MI.getOperand(0).getReg();
+  Register Src = MI.getOperand(1).getReg();
+  auto *SrcDefMI = MRI.getVRegDef(Src);
+  if (MRI.getType(Dst) != LLT::scalar(1) || !MRI.use_empty(Dst))
+    return;
+
+  if (SrcDefMI && (SrcDefMI->getOpcode() == AMDGPU::G_UADDO ||
+                   SrcDefMI->getOpcode() == AMDGPU::G_USUBO ||
+                   SrcDefMI->getOpcode() == AMDGPU::G_UADDE ||
+                   SrcDefMI->getOpcode() == AMDGPU::G_USUBE)) {
+    MI.eraseFromParent();
+    return;
+  }
+}
+
----------------
gandhi56 wrote:

Consider the following legalized function:

```
bb.0:
  %0:sgpr(s32) = COPY $sgpr0
  %1:sgpr(s32) = COPY $sgpr1
  %2:sgpr(s32) = COPY $sgpr2
  %8:sgpr(s32) = G_CONSTANT i32 1
  %9:sgpr(s32) = G_AND %2:sgpr, %8:sgpr
  %4:sgpr(s32), %6:sgpr(s32) = G_UADDE %0:sgpr, %1:sgpr, %9:sgpr
  %5:sgpr(s1) = G_TRUNC %6:sgpr(s32)
  S_ENDPGM 0, implicit %4:sgpr(s32), implicit %5:sgpr(s1)
```
%5 was emitted above because has an implicit use. However, an assertion fails because %5 is an s1 mapped to the SGPR register bank.

To resolve this issue, I think we need to introduce an `Scc` register bank (similar to `Vcc`) for s1 values. Another option is to emit a `G_ANYEXT` if the `Scc` has uses following it's definition.

https://github.com/llvm/llvm-project/pull/159860


More information about the llvm-commits mailing list