Skip to content

[DAGCombiner] Add hasOneUse checks for folding (not (add X, -1)) to (neg X) #126667

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Feb 12, 2025

Conversation

tclin914
Copy link
Contributor

To get more better codegen for AArch with bic, x86 with andn and riscv with andn.

…neg X)

To get more better codegen for AArch with bic, x86 with andn and riscv with andn.
@llvmbot
Copy link
Member

llvmbot commented Feb 11, 2025

@llvm/pr-subscribers-backend-x86

@llvm/pr-subscribers-backend-aarch64

Author: Jim Lin (tclin914)

Changes

To get more better codegen for AArch with bic, x86 with andn and riscv with andn.


Full diff: https://github.com/llvm/llvm-project/pull/126667.diff

4 Files Affected:

  • (modified) llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp (+1-1)
  • (modified) llvm/test/CodeGen/AArch64/align-down.ll (+3-4)
  • (modified) llvm/test/CodeGen/X86/align-down.ll (+33-18)
  • (modified) llvm/test/CodeGen/X86/not-of-dec.ll (+7-8)
diff --git a/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp b/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
index f4caaf426de6a07..6c663d19675b842 100644
--- a/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
+++ b/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
@@ -9702,7 +9702,7 @@ SDValue DAGCombiner::visitXOR(SDNode *N) {
   }
 
   // fold (not (add X, -1)) -> (neg X)
-  if (isAllOnesConstant(N1) && N0.getOpcode() == ISD::ADD &&
+  if (isAllOnesConstant(N1) && N0.getOpcode() == ISD::ADD && N0.hasOneUse() &&
       isAllOnesOrAllOnesSplat(N0.getOperand(1))) {
     return DAG.getNegative(N0.getOperand(0), DL, VT);
   }
diff --git a/llvm/test/CodeGen/AArch64/align-down.ll b/llvm/test/CodeGen/AArch64/align-down.ll
index 4b1cdfd2770f676..96e2a5d7d33f781 100644
--- a/llvm/test/CodeGen/AArch64/align-down.ll
+++ b/llvm/test/CodeGen/AArch64/align-down.ll
@@ -54,10 +54,9 @@ define i32 @t2_commutative(i32 %ptr, i32 %alignment) nounwind {
 define i32 @t3_extrause0(i32 %ptr, i32 %alignment, ptr %mask_storage) nounwind {
 ; CHECK-LABEL: t3_extrause0:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    neg w8, w1
-; CHECK-NEXT:    sub w9, w1, #1
-; CHECK-NEXT:    and w0, w0, w8
-; CHECK-NEXT:    str w9, [x2]
+; CHECK-NEXT:    sub w8, w1, #1
+; CHECK-NEXT:    bic w0, w0, w8
+; CHECK-NEXT:    str w8, [x2]
 ; CHECK-NEXT:    ret
   %mask = add i32 %alignment, -1
   store i32 %mask, ptr %mask_storage
diff --git a/llvm/test/CodeGen/X86/align-down.ll b/llvm/test/CodeGen/X86/align-down.ll
index 3c64e108e06ddb0..c359c04f527a31f 100644
--- a/llvm/test/CodeGen/X86/align-down.ll
+++ b/llvm/test/CodeGen/X86/align-down.ll
@@ -82,25 +82,40 @@ define i32 @t2_commutative(i32 %ptr, i32 %alignment) nounwind {
 ; Extra use tests
 
 define i32 @t3_extrause0(i32 %ptr, i32 %alignment, ptr %mask_storage) nounwind {
-; X86-LABEL: t3_extrause0:
-; X86:       # %bb.0:
-; X86-NEXT:    movl {{[0-9]+}}(%esp), %ecx
-; X86-NEXT:    movl {{[0-9]+}}(%esp), %eax
-; X86-NEXT:    leal -1(%eax), %edx
-; X86-NEXT:    movl %edx, (%ecx)
-; X86-NEXT:    negl %eax
-; X86-NEXT:    andl {{[0-9]+}}(%esp), %eax
-; X86-NEXT:    retl
+; NOBMI-X86-LABEL: t3_extrause0:
+; NOBMI-X86:       # %bb.0:
+; NOBMI-X86-NEXT:    movl {{[0-9]+}}(%esp), %ecx
+; NOBMI-X86-NEXT:    movl {{[0-9]+}}(%esp), %eax
+; NOBMI-X86-NEXT:    decl %eax
+; NOBMI-X86-NEXT:    movl %eax, (%ecx)
+; NOBMI-X86-NEXT:    notl %eax
+; NOBMI-X86-NEXT:    andl {{[0-9]+}}(%esp), %eax
+; NOBMI-X86-NEXT:    retl
 ;
-; X64-LABEL: t3_extrause0:
-; X64:       # %bb.0:
-; X64-NEXT:    movl %esi, %eax
-; X64-NEXT:    leal -1(%rax), %ecx
-; X64-NEXT:    movl %ecx, (%rdx)
-; X64-NEXT:    negl %eax
-; X64-NEXT:    andl %edi, %eax
-; X64-NEXT:    # kill: def $eax killed $eax killed $rax
-; X64-NEXT:    retq
+; BMI-X86-LABEL: t3_extrause0:
+; BMI-X86:       # %bb.0:
+; BMI-X86-NEXT:    movl {{[0-9]+}}(%esp), %eax
+; BMI-X86-NEXT:    movl {{[0-9]+}}(%esp), %ecx
+; BMI-X86-NEXT:    decl %ecx
+; BMI-X86-NEXT:    movl %ecx, (%eax)
+; BMI-X86-NEXT:    andnl {{[0-9]+}}(%esp), %ecx, %eax
+; BMI-X86-NEXT:    retl
+;
+; NOBMI-X64-LABEL: t3_extrause0:
+; NOBMI-X64:       # %bb.0:
+; NOBMI-X64-NEXT:    # kill: def $esi killed $esi def $rsi
+; NOBMI-X64-NEXT:    leal -1(%rsi), %eax
+; NOBMI-X64-NEXT:    movl %eax, (%rdx)
+; NOBMI-X64-NEXT:    notl %eax
+; NOBMI-X64-NEXT:    andl %edi, %eax
+; NOBMI-X64-NEXT:    retq
+;
+; BMI-X64-LABEL: t3_extrause0:
+; BMI-X64:       # %bb.0:
+; BMI-X64-NEXT:    decl %esi
+; BMI-X64-NEXT:    movl %esi, (%rdx)
+; BMI-X64-NEXT:    andnl %edi, %esi, %eax
+; BMI-X64-NEXT:    retq
   %mask = add i32 %alignment, -1
   store i32 %mask, ptr %mask_storage
   %bias = and i32 %ptr, %mask
diff --git a/llvm/test/CodeGen/X86/not-of-dec.ll b/llvm/test/CodeGen/X86/not-of-dec.ll
index 97906495031234f..29461619ac80557 100644
--- a/llvm/test/CodeGen/X86/not-of-dec.ll
+++ b/llvm/test/CodeGen/X86/not-of-dec.ll
@@ -57,18 +57,17 @@ define i32 @t2_extrause(i32 %alignment, ptr %mask_storage) nounwind {
 ; X86:       # %bb.0:
 ; X86-NEXT:    movl {{[0-9]+}}(%esp), %ecx
 ; X86-NEXT:    movl {{[0-9]+}}(%esp), %eax
-; X86-NEXT:    leal -1(%eax), %edx
-; X86-NEXT:    movl %edx, (%ecx)
-; X86-NEXT:    negl %eax
+; X86-NEXT:    decl %eax
+; X86-NEXT:    movl %eax, (%ecx)
+; X86-NEXT:    notl %eax
 ; X86-NEXT:    retl
 ;
 ; X64-LABEL: t2_extrause:
 ; X64:       # %bb.0:
-; X64-NEXT:    movl %edi, %eax
-; X64-NEXT:    leal -1(%rax), %ecx
-; X64-NEXT:    movl %ecx, (%rsi)
-; X64-NEXT:    negl %eax
-; X64-NEXT:    # kill: def $eax killed $eax killed $rax
+; X64-NEXT:    # kill: def $edi killed $edi def $rdi
+; X64-NEXT:    leal -1(%rdi), %eax
+; X64-NEXT:    movl %eax, (%rsi)
+; X64-NEXT:    notl %eax
 ; X64-NEXT:    retq
   %mask = add i32 %alignment, -1
   store i32 %mask, ptr %mask_storage

@llvmbot
Copy link
Member

llvmbot commented Feb 11, 2025

@llvm/pr-subscribers-llvm-selectiondag

Author: Jim Lin (tclin914)

Changes

To get more better codegen for AArch with bic, x86 with andn and riscv with andn.


Full diff: https://github.com/llvm/llvm-project/pull/126667.diff

4 Files Affected:

  • (modified) llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp (+1-1)
  • (modified) llvm/test/CodeGen/AArch64/align-down.ll (+3-4)
  • (modified) llvm/test/CodeGen/X86/align-down.ll (+33-18)
  • (modified) llvm/test/CodeGen/X86/not-of-dec.ll (+7-8)
diff --git a/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp b/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
index f4caaf426de6a07..6c663d19675b842 100644
--- a/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
+++ b/llvm/lib/CodeGen/SelectionDAG/DAGCombiner.cpp
@@ -9702,7 +9702,7 @@ SDValue DAGCombiner::visitXOR(SDNode *N) {
   }
 
   // fold (not (add X, -1)) -> (neg X)
-  if (isAllOnesConstant(N1) && N0.getOpcode() == ISD::ADD &&
+  if (isAllOnesConstant(N1) && N0.getOpcode() == ISD::ADD && N0.hasOneUse() &&
       isAllOnesOrAllOnesSplat(N0.getOperand(1))) {
     return DAG.getNegative(N0.getOperand(0), DL, VT);
   }
diff --git a/llvm/test/CodeGen/AArch64/align-down.ll b/llvm/test/CodeGen/AArch64/align-down.ll
index 4b1cdfd2770f676..96e2a5d7d33f781 100644
--- a/llvm/test/CodeGen/AArch64/align-down.ll
+++ b/llvm/test/CodeGen/AArch64/align-down.ll
@@ -54,10 +54,9 @@ define i32 @t2_commutative(i32 %ptr, i32 %alignment) nounwind {
 define i32 @t3_extrause0(i32 %ptr, i32 %alignment, ptr %mask_storage) nounwind {
 ; CHECK-LABEL: t3_extrause0:
 ; CHECK:       // %bb.0:
-; CHECK-NEXT:    neg w8, w1
-; CHECK-NEXT:    sub w9, w1, #1
-; CHECK-NEXT:    and w0, w0, w8
-; CHECK-NEXT:    str w9, [x2]
+; CHECK-NEXT:    sub w8, w1, #1
+; CHECK-NEXT:    bic w0, w0, w8
+; CHECK-NEXT:    str w8, [x2]
 ; CHECK-NEXT:    ret
   %mask = add i32 %alignment, -1
   store i32 %mask, ptr %mask_storage
diff --git a/llvm/test/CodeGen/X86/align-down.ll b/llvm/test/CodeGen/X86/align-down.ll
index 3c64e108e06ddb0..c359c04f527a31f 100644
--- a/llvm/test/CodeGen/X86/align-down.ll
+++ b/llvm/test/CodeGen/X86/align-down.ll
@@ -82,25 +82,40 @@ define i32 @t2_commutative(i32 %ptr, i32 %alignment) nounwind {
 ; Extra use tests
 
 define i32 @t3_extrause0(i32 %ptr, i32 %alignment, ptr %mask_storage) nounwind {
-; X86-LABEL: t3_extrause0:
-; X86:       # %bb.0:
-; X86-NEXT:    movl {{[0-9]+}}(%esp), %ecx
-; X86-NEXT:    movl {{[0-9]+}}(%esp), %eax
-; X86-NEXT:    leal -1(%eax), %edx
-; X86-NEXT:    movl %edx, (%ecx)
-; X86-NEXT:    negl %eax
-; X86-NEXT:    andl {{[0-9]+}}(%esp), %eax
-; X86-NEXT:    retl
+; NOBMI-X86-LABEL: t3_extrause0:
+; NOBMI-X86:       # %bb.0:
+; NOBMI-X86-NEXT:    movl {{[0-9]+}}(%esp), %ecx
+; NOBMI-X86-NEXT:    movl {{[0-9]+}}(%esp), %eax
+; NOBMI-X86-NEXT:    decl %eax
+; NOBMI-X86-NEXT:    movl %eax, (%ecx)
+; NOBMI-X86-NEXT:    notl %eax
+; NOBMI-X86-NEXT:    andl {{[0-9]+}}(%esp), %eax
+; NOBMI-X86-NEXT:    retl
 ;
-; X64-LABEL: t3_extrause0:
-; X64:       # %bb.0:
-; X64-NEXT:    movl %esi, %eax
-; X64-NEXT:    leal -1(%rax), %ecx
-; X64-NEXT:    movl %ecx, (%rdx)
-; X64-NEXT:    negl %eax
-; X64-NEXT:    andl %edi, %eax
-; X64-NEXT:    # kill: def $eax killed $eax killed $rax
-; X64-NEXT:    retq
+; BMI-X86-LABEL: t3_extrause0:
+; BMI-X86:       # %bb.0:
+; BMI-X86-NEXT:    movl {{[0-9]+}}(%esp), %eax
+; BMI-X86-NEXT:    movl {{[0-9]+}}(%esp), %ecx
+; BMI-X86-NEXT:    decl %ecx
+; BMI-X86-NEXT:    movl %ecx, (%eax)
+; BMI-X86-NEXT:    andnl {{[0-9]+}}(%esp), %ecx, %eax
+; BMI-X86-NEXT:    retl
+;
+; NOBMI-X64-LABEL: t3_extrause0:
+; NOBMI-X64:       # %bb.0:
+; NOBMI-X64-NEXT:    # kill: def $esi killed $esi def $rsi
+; NOBMI-X64-NEXT:    leal -1(%rsi), %eax
+; NOBMI-X64-NEXT:    movl %eax, (%rdx)
+; NOBMI-X64-NEXT:    notl %eax
+; NOBMI-X64-NEXT:    andl %edi, %eax
+; NOBMI-X64-NEXT:    retq
+;
+; BMI-X64-LABEL: t3_extrause0:
+; BMI-X64:       # %bb.0:
+; BMI-X64-NEXT:    decl %esi
+; BMI-X64-NEXT:    movl %esi, (%rdx)
+; BMI-X64-NEXT:    andnl %edi, %esi, %eax
+; BMI-X64-NEXT:    retq
   %mask = add i32 %alignment, -1
   store i32 %mask, ptr %mask_storage
   %bias = and i32 %ptr, %mask
diff --git a/llvm/test/CodeGen/X86/not-of-dec.ll b/llvm/test/CodeGen/X86/not-of-dec.ll
index 97906495031234f..29461619ac80557 100644
--- a/llvm/test/CodeGen/X86/not-of-dec.ll
+++ b/llvm/test/CodeGen/X86/not-of-dec.ll
@@ -57,18 +57,17 @@ define i32 @t2_extrause(i32 %alignment, ptr %mask_storage) nounwind {
 ; X86:       # %bb.0:
 ; X86-NEXT:    movl {{[0-9]+}}(%esp), %ecx
 ; X86-NEXT:    movl {{[0-9]+}}(%esp), %eax
-; X86-NEXT:    leal -1(%eax), %edx
-; X86-NEXT:    movl %edx, (%ecx)
-; X86-NEXT:    negl %eax
+; X86-NEXT:    decl %eax
+; X86-NEXT:    movl %eax, (%ecx)
+; X86-NEXT:    notl %eax
 ; X86-NEXT:    retl
 ;
 ; X64-LABEL: t2_extrause:
 ; X64:       # %bb.0:
-; X64-NEXT:    movl %edi, %eax
-; X64-NEXT:    leal -1(%rax), %ecx
-; X64-NEXT:    movl %ecx, (%rsi)
-; X64-NEXT:    negl %eax
-; X64-NEXT:    # kill: def $eax killed $eax killed $rax
+; X64-NEXT:    # kill: def $edi killed $edi def $rdi
+; X64-NEXT:    leal -1(%rdi), %eax
+; X64-NEXT:    movl %eax, (%rsi)
+; X64-NEXT:    notl %eax
 ; X64-NEXT:    retq
   %mask = add i32 %alignment, -1
   store i32 %mask, ptr %mask_storage

Copy link
Collaborator

@momchil-velikov momchil-velikov left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM.

@tclin914 tclin914 merged commit 31bfae3 into llvm:main Feb 12, 2025
5 of 8 checks passed
@tclin914 tclin914 deleted the foldnottonegwithhasoneusecheck branch February 12, 2025 04:24
flovent pushed a commit to flovent/llvm-project that referenced this pull request Feb 13, 2025
…neg X) (llvm#126667)

To get more better codegen for AArch with bic, x86 with andn and riscv
with andn.
joaosaffran pushed a commit to joaosaffran/llvm-project that referenced this pull request Feb 14, 2025
…neg X) (llvm#126667)

To get more better codegen for AArch with bic, x86 with andn and riscv
with andn.
sivan-shani pushed a commit to sivan-shani/llvm-project that referenced this pull request Feb 24, 2025
…neg X) (llvm#126667)

To get more better codegen for AArch with bic, x86 with andn and riscv
with andn.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants