[llvm] [RISCV] Remove artificial restriction on ShAmt from (shl (and X, C2), C) -> (slli (srliw X, C3), C3+C) isel. (PR #143010)

Craig Topper via llvm-commits llvm-commits at lists.llvm.org
Thu Jun 5 10:29:14 PDT 2025


https://github.com/topperc created https://github.com/llvm/llvm-project/pull/143010

This code incorrectly inherited a `ShAmt <= 32` check from an earlier pattern.

>From ab271274190f752d977d89a00997d86c048f8f0b Mon Sep 17 00:00:00 2001
From: Craig Topper <craig.topper at sifive.com>
Date: Thu, 5 Jun 2025 10:01:03 -0700
Subject: [PATCH 1/2] Pre-commit test

---
 llvm/test/CodeGen/RISCV/and-shl.ll | 19 +++++++++++++++++++
 1 file changed, 19 insertions(+)

diff --git a/llvm/test/CodeGen/RISCV/and-shl.ll b/llvm/test/CodeGen/RISCV/and-shl.ll
index c3cb5d8e2e37d..778cfc2a42c21 100644
--- a/llvm/test/CodeGen/RISCV/and-shl.ll
+++ b/llvm/test/CodeGen/RISCV/and-shl.ll
@@ -77,3 +77,22 @@ define i32 @and_0xfff_shl_2_multi_use(i32 %x) {
   %r = add i32 %a, %s
   ret i32 %r
 }
+
+define i64 @and_0xfff_shl_33(i64 %x) {
+; RV32I-LABEL: and_0xfff_shl_33:
+; RV32I:       # %bb.0:
+; RV32I-NEXT:    slli a0, a0, 20
+; RV32I-NEXT:    srli a1, a0, 19
+; RV32I-NEXT:    li a0, 0
+; RV32I-NEXT:    ret
+;
+; RV64I-LABEL: and_0xfff_shl_33:
+; RV64I:       # %bb.0:
+; RV64I-NEXT:    slli a0, a0, 52
+; RV64I-NEXT:    srli a0, a0, 52
+; RV64I-NEXT:    slli a0, a0, 33
+; RV64I-NEXT:    ret
+  %a = and i64 %x, 4095
+  %s = shl i64 %a, 33
+  ret i64 %s
+}

>From 1304d34d886d5291562fbdcc45152734c2e78257 Mon Sep 17 00:00:00 2001
From: Craig Topper <craig.topper at sifive.com>
Date: Thu, 5 Jun 2025 10:25:41 -0700
Subject: [PATCH 2/2] [RISCV] Remove artificial restriction on ShAmt from (shl
 (and X, C2), C) -> (slli (srliw X, C3), C3+C) fold.

---
 llvm/lib/Target/RISCV/RISCVISelDAGToDAG.cpp | 4 ++--
 llvm/test/CodeGen/RISCV/and-shl.ll          | 3 +--
 2 files changed, 3 insertions(+), 4 deletions(-)

diff --git a/llvm/lib/Target/RISCV/RISCVISelDAGToDAG.cpp b/llvm/lib/Target/RISCV/RISCVISelDAGToDAG.cpp
index 4dd53fdd0213d..a5cdf9f79f57a 100644
--- a/llvm/lib/Target/RISCV/RISCVISelDAGToDAG.cpp
+++ b/llvm/lib/Target/RISCV/RISCVISelDAGToDAG.cpp
@@ -1051,11 +1051,11 @@ void RISCVDAGToDAGISel::Select(SDNode *Node) {
     unsigned ShAmt = N1C->getZExtValue();
     uint64_t Mask = N0.getConstantOperandVal(1);
 
-    if (ShAmt <= 32 && isShiftedMask_64(Mask)) {
+    if (isShiftedMask_64(Mask)) {
       unsigned XLen = Subtarget->getXLen();
       unsigned LeadingZeros = XLen - llvm::bit_width(Mask);
       unsigned TrailingZeros = llvm::countr_zero(Mask);
-      if (TrailingZeros > 0 && LeadingZeros == 32) {
+      if (ShAmt <= 32 && TrailingZeros > 0 && LeadingZeros == 32) {
         // Optimize (shl (and X, C2), C) -> (slli (srliw X, C3), C3+C)
         // where C2 has 32 leading zeros and C3 trailing zeros.
         SDNode *SRLIW = CurDAG->getMachineNode(
diff --git a/llvm/test/CodeGen/RISCV/and-shl.ll b/llvm/test/CodeGen/RISCV/and-shl.ll
index 778cfc2a42c21..26b4a90d88fba 100644
--- a/llvm/test/CodeGen/RISCV/and-shl.ll
+++ b/llvm/test/CodeGen/RISCV/and-shl.ll
@@ -89,8 +89,7 @@ define i64 @and_0xfff_shl_33(i64 %x) {
 ; RV64I-LABEL: and_0xfff_shl_33:
 ; RV64I:       # %bb.0:
 ; RV64I-NEXT:    slli a0, a0, 52
-; RV64I-NEXT:    srli a0, a0, 52
-; RV64I-NEXT:    slli a0, a0, 33
+; RV64I-NEXT:    srli a0, a0, 19
 ; RV64I-NEXT:    ret
   %a = and i64 %x, 4095
   %s = shl i64 %a, 33



More information about the llvm-commits mailing list