Skip to content

Conversation

zhaoqi5
Copy link
Contributor

@zhaoqi5 zhaoqi5 commented Sep 16, 2025

After this commit, DAGCombiner will have more opportunities to optimize vector types and+...+not to andn.

Many combines in DAGCombiner will be enabled, but only shows changes after combining and(add(not)) to and(not(sub)) in the tests of this commit.

…bines

After this commit, DAGCombiner will have more opportunities to
optimize vector types `and+...+not` to `andn`.

Many combines in DAGCombiner will be enabled, but only shows
changes after combining `and(add(not))` to `and(not(sub))` in
the tests of this commit.
@llvmbot
Copy link
Member

llvmbot commented Sep 16, 2025

@llvm/pr-subscribers-backend-loongarch

Author: ZhaoQi (zhaoqi5)

Changes

After this commit, DAGCombiner will have more opportunities to optimize vector types and+...+not to andn.

Many combines in DAGCombiner will be enabled, but only shows changes after combining and(add(not)) to and(not(sub)) in the tests of this commit.


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

3 Files Affected:

  • (modified) llvm/lib/Target/LoongArch/LoongArchISelLowering.cpp (+6-2)
  • (modified) llvm/test/CodeGen/LoongArch/lasx/and-not-combine.ll (+8-15)
  • (modified) llvm/test/CodeGen/LoongArch/lsx/and-not-combine.ll (+8-15)
diff --git a/llvm/lib/Target/LoongArch/LoongArchISelLowering.cpp b/llvm/lib/Target/LoongArch/LoongArchISelLowering.cpp
index 634914d3b3fd0..7a4e5b5597f7c 100644
--- a/llvm/lib/Target/LoongArch/LoongArchISelLowering.cpp
+++ b/llvm/lib/Target/LoongArch/LoongArchISelLowering.cpp
@@ -8249,8 +8249,12 @@ EVT LoongArchTargetLowering::getSetCCResultType(const DataLayout &DL,
 }
 
 bool LoongArchTargetLowering::hasAndNot(SDValue Y) const {
-  // TODO: Support vectors.
-  return Y.getValueType().isScalarInteger() && !isa<ConstantSDNode>(Y);
+  EVT VT = Y.getValueType();
+
+  if (VT.isVector())
+    return Subtarget.hasExtLSX() && VT.isInteger();
+
+  return VT.isScalarInteger() && !isa<ConstantSDNode>(Y);
 }
 
 bool LoongArchTargetLowering::getTgtMemIntrinsic(IntrinsicInfo &Info,
diff --git a/llvm/test/CodeGen/LoongArch/lasx/and-not-combine.ll b/llvm/test/CodeGen/LoongArch/lasx/and-not-combine.ll
index 75ac4c99ef7c1..67549599db2f3 100644
--- a/llvm/test/CodeGen/LoongArch/lasx/and-not-combine.ll
+++ b/llvm/test/CodeGen/LoongArch/lasx/and-not-combine.ll
@@ -8,9 +8,8 @@ define void @and_not_combine_v32i8(ptr %res, ptr %a0, ptr %a1, ptr %a2) nounwind
 ; CHECK-NEXT:    xvld $xr0, $a2, 0
 ; CHECK-NEXT:    xvld $xr1, $a3, 0
 ; CHECK-NEXT:    xvld $xr2, $a1, 0
-; CHECK-NEXT:    xvxori.b $xr0, $xr0, 255
-; CHECK-NEXT:    xvadd.b $xr0, $xr0, $xr1
-; CHECK-NEXT:    xvand.v $xr0, $xr2, $xr0
+; CHECK-NEXT:    xvsub.b $xr0, $xr0, $xr1
+; CHECK-NEXT:    xvandn.v $xr0, $xr0, $xr2
 ; CHECK-NEXT:    xvst $xr0, $a0, 0
 ; CHECK-NEXT:    ret
 entry:
@@ -30,10 +29,8 @@ define void @and_not_combine_v16i16(ptr %res, ptr %a0, ptr %a1, ptr %a2) nounwin
 ; CHECK-NEXT:    xvld $xr0, $a2, 0
 ; CHECK-NEXT:    xvld $xr1, $a3, 0
 ; CHECK-NEXT:    xvld $xr2, $a1, 0
-; CHECK-NEXT:    xvrepli.b $xr3, -1
-; CHECK-NEXT:    xvxor.v $xr0, $xr0, $xr3
-; CHECK-NEXT:    xvadd.h $xr0, $xr0, $xr1
-; CHECK-NEXT:    xvand.v $xr0, $xr2, $xr0
+; CHECK-NEXT:    xvsub.h $xr0, $xr0, $xr1
+; CHECK-NEXT:    xvandn.v $xr0, $xr0, $xr2
 ; CHECK-NEXT:    xvst $xr0, $a0, 0
 ; CHECK-NEXT:    ret
 entry:
@@ -53,10 +50,8 @@ define void @and_not_combine_v8i32(ptr %res, ptr %a0, ptr %a1, ptr %a2) nounwind
 ; CHECK-NEXT:    xvld $xr0, $a2, 0
 ; CHECK-NEXT:    xvld $xr1, $a3, 0
 ; CHECK-NEXT:    xvld $xr2, $a1, 0
-; CHECK-NEXT:    xvrepli.b $xr3, -1
-; CHECK-NEXT:    xvxor.v $xr0, $xr0, $xr3
-; CHECK-NEXT:    xvadd.w $xr0, $xr0, $xr1
-; CHECK-NEXT:    xvand.v $xr0, $xr2, $xr0
+; CHECK-NEXT:    xvsub.w $xr0, $xr0, $xr1
+; CHECK-NEXT:    xvandn.v $xr0, $xr0, $xr2
 ; CHECK-NEXT:    xvst $xr0, $a0, 0
 ; CHECK-NEXT:    ret
 entry:
@@ -76,10 +71,8 @@ define void @and_not_combine_v4i64(ptr %res, ptr %a0, ptr %a1, ptr %a2) nounwind
 ; CHECK-NEXT:    xvld $xr0, $a2, 0
 ; CHECK-NEXT:    xvld $xr1, $a3, 0
 ; CHECK-NEXT:    xvld $xr2, $a1, 0
-; CHECK-NEXT:    xvrepli.b $xr3, -1
-; CHECK-NEXT:    xvxor.v $xr0, $xr0, $xr3
-; CHECK-NEXT:    xvadd.d $xr0, $xr0, $xr1
-; CHECK-NEXT:    xvand.v $xr0, $xr2, $xr0
+; CHECK-NEXT:    xvsub.d $xr0, $xr0, $xr1
+; CHECK-NEXT:    xvandn.v $xr0, $xr0, $xr2
 ; CHECK-NEXT:    xvst $xr0, $a0, 0
 ; CHECK-NEXT:    ret
 entry:
diff --git a/llvm/test/CodeGen/LoongArch/lsx/and-not-combine.ll b/llvm/test/CodeGen/LoongArch/lsx/and-not-combine.ll
index 39060bfa92c0d..3c6d34505e114 100644
--- a/llvm/test/CodeGen/LoongArch/lsx/and-not-combine.ll
+++ b/llvm/test/CodeGen/LoongArch/lsx/and-not-combine.ll
@@ -8,9 +8,8 @@ define void @and_not_combine_v16i8(ptr %res, ptr %a0, ptr %a1, ptr %a2) nounwind
 ; CHECK-NEXT:    vld $vr0, $a2, 0
 ; CHECK-NEXT:    vld $vr1, $a3, 0
 ; CHECK-NEXT:    vld $vr2, $a1, 0
-; CHECK-NEXT:    vxori.b $vr0, $vr0, 255
-; CHECK-NEXT:    vadd.b $vr0, $vr0, $vr1
-; CHECK-NEXT:    vand.v $vr0, $vr2, $vr0
+; CHECK-NEXT:    vsub.b $vr0, $vr0, $vr1
+; CHECK-NEXT:    vandn.v $vr0, $vr0, $vr2
 ; CHECK-NEXT:    vst $vr0, $a0, 0
 ; CHECK-NEXT:    ret
 entry:
@@ -30,10 +29,8 @@ define void @and_not_combine_v8i16(ptr %res, ptr %a0, ptr %a1, ptr %a2) nounwind
 ; CHECK-NEXT:    vld $vr0, $a2, 0
 ; CHECK-NEXT:    vld $vr1, $a3, 0
 ; CHECK-NEXT:    vld $vr2, $a1, 0
-; CHECK-NEXT:    vrepli.b $vr3, -1
-; CHECK-NEXT:    vxor.v $vr0, $vr0, $vr3
-; CHECK-NEXT:    vadd.h $vr0, $vr0, $vr1
-; CHECK-NEXT:    vand.v $vr0, $vr2, $vr0
+; CHECK-NEXT:    vsub.h $vr0, $vr0, $vr1
+; CHECK-NEXT:    vandn.v $vr0, $vr0, $vr2
 ; CHECK-NEXT:    vst $vr0, $a0, 0
 ; CHECK-NEXT:    ret
 entry:
@@ -53,10 +50,8 @@ define void @and_not_combine_v4i32(ptr %res, ptr %a0, ptr %a1, ptr %a2) nounwind
 ; CHECK-NEXT:    vld $vr0, $a2, 0
 ; CHECK-NEXT:    vld $vr1, $a3, 0
 ; CHECK-NEXT:    vld $vr2, $a1, 0
-; CHECK-NEXT:    vrepli.b $vr3, -1
-; CHECK-NEXT:    vxor.v $vr0, $vr0, $vr3
-; CHECK-NEXT:    vadd.w $vr0, $vr0, $vr1
-; CHECK-NEXT:    vand.v $vr0, $vr2, $vr0
+; CHECK-NEXT:    vsub.w $vr0, $vr0, $vr1
+; CHECK-NEXT:    vandn.v $vr0, $vr0, $vr2
 ; CHECK-NEXT:    vst $vr0, $a0, 0
 ; CHECK-NEXT:    ret
 entry:
@@ -76,10 +71,8 @@ define void @and_not_combine_v2i64(ptr %res, ptr %a0, ptr %a1, ptr %a2) nounwind
 ; CHECK-NEXT:    vld $vr0, $a2, 0
 ; CHECK-NEXT:    vld $vr1, $a3, 0
 ; CHECK-NEXT:    vld $vr2, $a1, 0
-; CHECK-NEXT:    vrepli.b $vr3, -1
-; CHECK-NEXT:    vxor.v $vr0, $vr0, $vr3
-; CHECK-NEXT:    vadd.d $vr0, $vr0, $vr1
-; CHECK-NEXT:    vand.v $vr0, $vr2, $vr0
+; CHECK-NEXT:    vsub.d $vr0, $vr0, $vr1
+; CHECK-NEXT:    vandn.v $vr0, $vr0, $vr2
 ; CHECK-NEXT:    vst $vr0, $a0, 0
 ; CHECK-NEXT:    ret
 entry:

Copy link
Member

@heiher heiher left a comment

Choose a reason for hiding this comment

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

LGTM.

Base automatically changed from users/zhaoqi5/test-and-not to main September 25, 2025 08:45
@zhaoqi5 zhaoqi5 merged commit 9440f40 into main Sep 26, 2025
9 checks passed
@zhaoqi5 zhaoqi5 deleted the users/zhaoqi5/vector-hasandnot branch September 26, 2025 01:21
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.

3 participants