[llvm] [AMDGPU] Add v2i32 V_BFI combines for andn2 and orn2 (PR #196325)
via llvm-commits
llvm-commits at lists.llvm.org
Thu May 7 07:28:59 PDT 2026
llvmorg-github-actions[bot] wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-backend-amdgpu
Author: Harrison Hao (harrisonGPU)
<details>
<summary>Changes</summary>
Add vector v2i32 pattern matches that lower to two lane wise V_BFI_B32 operations.
TODO: Support v2i16, v4i16 pattern.
---
Full diff: https://github.com/llvm/llvm-project/pull/196325.diff
3 Files Affected:
- (modified) llvm/lib/Target/AMDGPU/AMDGPUInstructions.td (+1)
- (modified) llvm/lib/Target/AMDGPU/SIInstructions.td (+32)
- (modified) llvm/test/CodeGen/AMDGPU/andorn2.ll (+31)
``````````diff
diff --git a/llvm/lib/Target/AMDGPU/AMDGPUInstructions.td b/llvm/lib/Target/AMDGPU/AMDGPUInstructions.td
index 529b2990f9b3a..cc7e4816caeec 100644
--- a/llvm/lib/Target/AMDGPU/AMDGPUInstructions.td
+++ b/llvm/lib/Target/AMDGPU/AMDGPUInstructions.td
@@ -262,6 +262,7 @@ def xor_oneuse : HasOneUseBinOp<xor>;
} // Properties = [SDNPCommutative, SDNPAssociative]
def not_oneuse : HasOneUseUnaryOp<not>;
+def vnot_oneuse : HasOneUseUnaryOp<vnot>;
def add_oneuse : HasOneUseBinOp<add>;
def sub_oneuse : HasOneUseBinOp<sub>;
diff --git a/llvm/lib/Target/AMDGPU/SIInstructions.td b/llvm/lib/Target/AMDGPU/SIInstructions.td
index d1033c81a9361..408835e9e73b8 100644
--- a/llvm/lib/Target/AMDGPU/SIInstructions.td
+++ b/llvm/lib/Target/AMDGPU/SIInstructions.td
@@ -2735,6 +2735,18 @@ def : AMDGPUPatIgnoreCopies <
(i32 (EXTRACT_SUBREG VReg_64:$z, sub1))), sub1)
>;
+// v2i32 version
+def : AMDGPUPatIgnoreCopies <
+ (DivergentBinFrag<or> (and v2i32:$y, v2i32:$x), (and v2i32:$z, (vnot v2i32:$x))),
+ (REG_SEQUENCE VReg_64,
+ (V_BFI_B32_e64 (i32 (EXTRACT_SUBREG VReg_64:$x, sub0)),
+ (i32 (EXTRACT_SUBREG VReg_64:$y, sub0)),
+ (i32 (EXTRACT_SUBREG VReg_64:$z, sub0))), sub0,
+ (V_BFI_B32_e64 (i32 (EXTRACT_SUBREG VReg_64:$x, sub1)),
+ (i32 (EXTRACT_SUBREG VReg_64:$y, sub1)),
+ (i32 (EXTRACT_SUBREG VReg_64:$z, sub1))), sub1)
+>;
+
// (z & ~x)
def : AMDGPUPatIgnoreCopies <
(DivergentBinFrag<and> i32:$z, (not_oneuse i32:$x)),
@@ -2751,6 +2763,16 @@ def : AMDGPUPatIgnoreCopies <
(i32 (EXTRACT_SUBREG VReg_64:$z, sub1))), sub1)
>;
+// v2i32 version
+def : AMDGPUPatIgnoreCopies <
+ (DivergentBinFrag<and> v2i32:$z, (vnot_oneuse v2i32:$x)),
+ (REG_SEQUENCE VReg_64,
+ (V_BFI_B32_e64 (i32 (EXTRACT_SUBREG VReg_64:$x, sub0)), (i32 0),
+ (i32 (EXTRACT_SUBREG VReg_64:$z, sub0))), sub0,
+ (V_BFI_B32_e64 (i32 (EXTRACT_SUBREG VReg_64:$x, sub1)), (i32 0),
+ (i32 (EXTRACT_SUBREG VReg_64:$z, sub1))), sub1)
+>;
+
// (y | ~x)
def : AMDGPUPatIgnoreCopies <
(DivergentBinFrag<or> i32:$y, (not_oneuse i32:$x)),
@@ -2767,6 +2789,16 @@ def : AMDGPUPatIgnoreCopies <
(i32 (EXTRACT_SUBREG VReg_64:$y, sub1)), (i32 -1)), sub1)
>;
+// v2i32 version
+def : AMDGPUPatIgnoreCopies <
+ (DivergentBinFrag<or> v2i32:$y, (vnot_oneuse v2i32:$x)),
+ (REG_SEQUENCE VReg_64,
+ (V_BFI_B32_e64 (i32 (EXTRACT_SUBREG VReg_64:$x, sub0)),
+ (i32 (EXTRACT_SUBREG VReg_64:$y, sub0)), (i32 -1)), sub0,
+ (V_BFI_B32_e64 (i32 (EXTRACT_SUBREG VReg_64:$x, sub1)),
+ (i32 (EXTRACT_SUBREG VReg_64:$y, sub1)), (i32 -1)), sub1)
+>;
+
// SHA-256 Ch function
// z ^ (x & (y ^ z))
def : AMDGPUPatIgnoreCopies <
diff --git a/llvm/test/CodeGen/AMDGPU/andorn2.ll b/llvm/test/CodeGen/AMDGPU/andorn2.ll
index 1527d50e28b35..ac91102f9daeb 100644
--- a/llvm/test/CodeGen/AMDGPU/andorn2.ll
+++ b/llvm/test/CodeGen/AMDGPU/andorn2.ll
@@ -95,5 +95,36 @@ entry:
ret void
}
+; GCN-LABEL: {{^}}vector_bfi_v2i32
+; GCN: v_bfi_b32
+; GCN: v_bfi_b32
+define <2 x i32> @vector_bfi_v2i32(<2 x i32> %x, <2 x i32> %y, <2 x i32> %z) {
+ %ny = and <2 x i32> %y, %x
+ %nx = xor <2 x i32> %x, <i32 -1, i32 -1>
+ %nz = and <2 x i32> %z, %nx
+ %r = or <2 x i32> %ny, %nz
+ ret <2 x i32> %r
+}
+
+; GCN-LABEL: {{^}}vector_andn2_v2i32_one_use
+; GCN: v_bfi_b32
+; GCN: v_bfi_b32
+define <2 x i32> @vector_andn2_v2i32_one_use(<2 x i32> %v, <2 x i32> %s) {
+entry:
+ %not = xor <2 x i32> %v, <i32 -1, i32 -1>
+ %r = and <2 x i32> %s, %not
+ ret <2 x i32> %r
+}
+
+; GCN-LABEL: {{^}}vector_orn2_v2i32_one_use
+; GCN: v_bfi_b32
+; GCN: v_bfi_b32
+define <2 x i32> @vector_orn2_v2i32_one_use(<2 x i32> %v, <2 x i32> %s) {
+entry:
+ %not = xor <2 x i32> %v, <i32 -1, i32 -1>
+ %r = or <2 x i32> %s, %not
+ ret <2 x i32> %r
+}
+
; Function Attrs: nounwind readnone
declare i32 @llvm.amdgcn.workitem.id.x() #0
``````````
</details>
https://github.com/llvm/llvm-project/pull/196325
More information about the llvm-commits
mailing list