[PATCH] D72019: [X86] Use carry flag from add for (seteq (add X, -1), -1).

Craig Topper via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Mon Dec 30 15:53:49 PST 2019


craig.topper updated this revision to Diff 235656.
craig.topper added a comment.

Invert the condition. Despite what the PR said, it should be jb to the top of the loop not jae. The original code condition was jne on a compare with -1. If the add produce a value != -1, then the carry flag is set since -1 plus anything but 0 will have unsigned overflow and produce a value other than -1. Only 0+-1 produces -1 and it does it without overflowing.


CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D72019/new/

https://reviews.llvm.org/D72019

Files:
  llvm/lib/Target/X86/X86ISelLowering.cpp
  llvm/test/CodeGen/X86/pr44412.ll


Index: llvm/test/CodeGen/X86/pr44412.ll
===================================================================
--- llvm/test/CodeGen/X86/pr44412.ll
+++ llvm/test/CodeGen/X86/pr44412.ll
@@ -14,9 +14,8 @@
 ; CHECK-NEXT:  .LBB0_2: # =>This Inner Loop Header: Depth=1
 ; CHECK-NEXT:    movl %ebx, %edi
 ; CHECK-NEXT:    callq foo
-; CHECK-NEXT:    decl %ebx
-; CHECK-NEXT:    cmpl $-1, %ebx
-; CHECK-NEXT:    jne .LBB0_2
+; CHECK-NEXT:    addl $-1, %ebx
+; CHECK-NEXT:    jb .LBB0_2
 ; CHECK-NEXT:  .LBB0_3:
 ; CHECK-NEXT:    popq %rbx
 ; CHECK-NEXT:    retq
Index: llvm/lib/Target/X86/X86ISelLowering.cpp
===================================================================
--- llvm/lib/Target/X86/X86ISelLowering.cpp
+++ llvm/lib/Target/X86/X86ISelLowering.cpp
@@ -21682,6 +21682,36 @@
     }
   }
 
+  // Try to use the carry flag from the add in place of an separate CMP for:
+  // (seteq (add X, -1), -1). Similar for setne.
+  if (isAllOnesConstant(Op1) && Op0.getOpcode() == ISD::ADD &&
+      Op0.getOperand(1) == Op1 && (CC == ISD::SETEQ || CC == ISD::SETNE)) {
+    // Transform to an x86-specific ALU node with flags if there is a chance of
+    // using an RMW op or only the flags are used. Otherwise, leave
+    // the node alone and emit a 'cmp' instruction.
+    auto CheckAddUsers = [](SDValue Op) {
+      for (SDNode::use_iterator UI = Op.getNode()->use_begin(),
+             UE = Op.getNode()->use_end(); UI != UE; ++UI)
+        if (UI->getOpcode() != ISD::CopyToReg &&
+            UI->getOpcode() != ISD::SETCC &&
+            UI->getOpcode() != ISD::STORE)
+          return false;
+
+      return true;
+    };
+
+    if (CheckAddUsers(Op0)) {
+      SDVTList VTs = DAG.getVTList(Op0.getValueType(), MVT::i32);
+
+      SDValue New = DAG.getNode(X86ISD::ADD, dl, VTs, Op0.getOperand(0),
+                                Op0.getOperand(1));
+      DAG.ReplaceAllUsesOfValueWith(SDValue(Op0.getNode(), 0), New);
+      X86::CondCode CCode = CC == ISD::SETEQ ? X86::COND_AE : X86::COND_B;
+      X86CC = DAG.getTargetConstant(CCode, dl, MVT::i8);
+      return SDValue(New.getNode(), 1);
+    }
+  }
+
   bool IsFP = Op1.getSimpleValueType().isFloatingPoint();
   X86::CondCode CondCode = TranslateX86CC(CC, dl, IsFP, Op0, Op1, DAG);
   if (CondCode == X86::COND_INVALID)


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D72019.235656.patch
Type: text/x-patch
Size: 2287 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20191230/d5a1b4ca/attachment.bin>


More information about the llvm-commits mailing list