[llvm] 6d5697f - [SystemZ] Fix ICE with i128->i64 uaddo carry chain

Ulrich Weigand via llvm-commits llvm-commits at lists.llvm.org
Thu Jan 23 10:15:44 PST 2025


Author: Ulrich Weigand
Date: 2025-01-23T19:15:11+01:00
New Revision: 6d5697f7cb4e933d2f176c46b7ac05a9cbaeb8b6

URL: https://github.com/llvm/llvm-project/commit/6d5697f7cb4e933d2f176c46b7ac05a9cbaeb8b6
DIFF: https://github.com/llvm/llvm-project/commit/6d5697f7cb4e933d2f176c46b7ac05a9cbaeb8b6.diff

LOG: [SystemZ] Fix ICE with i128->i64 uaddo carry chain

We can only optimize a uaddo_carry via specialized instruction
if the carry was produced by another uaddo(_carry) instruction;
there is already a check for that.

However, i128 uaddo(_carry) use a completely different mechanism;
they indicate carry in a vector register instead of the CC flag.
Thus, we must also check that we don't mix those two - that check
has been missing.

Fixes: https://github.com/llvm/llvm-project/issues/124001

Added: 
    llvm/test/CodeGen/SystemZ/pr124001.ll

Modified: 
    llvm/lib/Target/SystemZ/SystemZISelLowering.cpp

Removed: 
    


################################################################################
diff  --git a/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp b/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp
index 4040ab6d45103a..1fb31c26e20d3c 100644
--- a/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp
+++ b/llvm/lib/Target/SystemZ/SystemZISelLowering.cpp
@@ -4708,15 +4708,19 @@ SDValue SystemZTargetLowering::lowerXALUO(SDValue Op,
 }
 
 static bool isAddCarryChain(SDValue Carry) {
-  while (Carry.getOpcode() == ISD::UADDO_CARRY)
+  while (Carry.getOpcode() == ISD::UADDO_CARRY &&
+         Carry->getValueType(0) != MVT::i128)
     Carry = Carry.getOperand(2);
-  return Carry.getOpcode() == ISD::UADDO;
+  return Carry.getOpcode() == ISD::UADDO &&
+         Carry->getValueType(0) != MVT::i128;
 }
 
 static bool isSubBorrowChain(SDValue Carry) {
-  while (Carry.getOpcode() == ISD::USUBO_CARRY)
+  while (Carry.getOpcode() == ISD::USUBO_CARRY &&
+         Carry->getValueType(0) != MVT::i128)
     Carry = Carry.getOperand(2);
-  return Carry.getOpcode() == ISD::USUBO;
+  return Carry.getOpcode() == ISD::USUBO &&
+         Carry->getValueType(0) != MVT::i128;
 }
 
 // Lower UADDO_CARRY/USUBO_CARRY nodes.

diff  --git a/llvm/test/CodeGen/SystemZ/pr124001.ll b/llvm/test/CodeGen/SystemZ/pr124001.ll
new file mode 100644
index 00000000000000..9cf630a55dd650
--- /dev/null
+++ b/llvm/test/CodeGen/SystemZ/pr124001.ll
@@ -0,0 +1,23 @@
+; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py UTC_ARGS: --version 5
+; RUN: llc < %s -mtriple=s390x-linux-gnu -mcpu=z13 | FileCheck %s
+
+define i64 @test(i128 %in) {
+; CHECK-LABEL: test:
+; CHECK:       # %bb.0:
+; CHECK-NEXT:    larl %r1, .LCPI0_0
+; CHECK-NEXT:    vl %v0, 0(%r2), 3
+; CHECK-NEXT:    vl %v1, 0(%r1), 3
+; CHECK-NEXT:    vaccq %v0, %v0, %v1
+; CHECK-NEXT:    vlgvg %r1, %v0, 1
+; CHECK-NEXT:    la %r2, 1(%r1)
+; CHECK-NEXT:    br %r14
+  %1 = tail call { i128, i1 } @llvm.uadd.with.overflow.i128(i128 %in, i128 1)
+  %2 = extractvalue { i128, i1 } %1, 1
+  %3 = zext i1 %2 to i64
+  %4 = add i64 %3, 1
+  ret i64 %4
+}
+
+declare { i128, i1 } @llvm.uadd.with.overflow.i128(i128, i128) #0
+
+attributes #0 = { nocallback nofree nosync nounwind speculatable willreturn memory(none) }


        


More information about the llvm-commits mailing list