[llvm] [RISCV] Add TH_EXT(U) to hasAllNBitUsers in RISCVOptWInstrs. (PR #157544)

Craig Topper via llvm-commits llvm-commits at lists.llvm.org
Mon Sep 8 18:50:18 PDT 2025


https://github.com/topperc updated https://github.com/llvm/llvm-project/pull/157544

>From 82fe5d0e5e42878b53708a32e4ba72d26971e2a4 Mon Sep 17 00:00:00 2001
From: Craig Topper <craig.topper at sifive.com>
Date: Mon, 8 Sep 2025 14:03:28 -0700
Subject: [PATCH 1/2] Pre-commit test

---
 llvm/test/CodeGen/RISCV/rv64xtheadbb.ll | 92 +++++++++++++++++++++++++
 1 file changed, 92 insertions(+)

diff --git a/llvm/test/CodeGen/RISCV/rv64xtheadbb.ll b/llvm/test/CodeGen/RISCV/rv64xtheadbb.ll
index 4c7bd8828812f..6cae6b9f5c8a6 100644
--- a/llvm/test/CodeGen/RISCV/rv64xtheadbb.ll
+++ b/llvm/test/CodeGen/RISCV/rv64xtheadbb.ll
@@ -1220,3 +1220,95 @@ bb2:                                              ; preds = %bb2, %bb
 bb7:                                              ; preds = %bb2
   ret void
 }
+
+define signext i32 @hasAllNBitUsers_extu(i64 %arg1, i64 %arg2, i64 %arg3)  {
+; RV64I-LABEL: hasAllNBitUsers_extu:
+; RV64I:       # %bb.0: # %entry
+; RV64I-NEXT:    addi a2, a2, -1
+; RV64I-NEXT:    li a3, 256
+; RV64I-NEXT:  .LBB38_1: # %bb2
+; RV64I-NEXT:    # =>This Inner Loop Header: Depth=1
+; RV64I-NEXT:    slli a0, a0, 47
+; RV64I-NEXT:    srli a0, a0, 62
+; RV64I-NEXT:    addi a2, a2, 1
+; RV64I-NEXT:    addw a0, a0, a1
+; RV64I-NEXT:    bltu a2, a3, .LBB38_1
+; RV64I-NEXT:  # %bb.2: # %bb7
+; RV64I-NEXT:    ret
+;
+; RV64XTHEADBB-LABEL: hasAllNBitUsers_extu:
+; RV64XTHEADBB:       # %bb.0: # %entry
+; RV64XTHEADBB-NEXT:    addi a2, a2, -1
+; RV64XTHEADBB-NEXT:    li a3, 256
+; RV64XTHEADBB-NEXT:  .LBB38_1: # %bb2
+; RV64XTHEADBB-NEXT:    # =>This Inner Loop Header: Depth=1
+; RV64XTHEADBB-NEXT:    th.extu a0, a0, 16, 15
+; RV64XTHEADBB-NEXT:    addi a2, a2, 1
+; RV64XTHEADBB-NEXT:    add a0, a0, a1
+; RV64XTHEADBB-NEXT:    bltu a2, a3, .LBB38_1
+; RV64XTHEADBB-NEXT:  # %bb.2: # %bb7
+; RV64XTHEADBB-NEXT:    sext.w a0, a0
+; RV64XTHEADBB-NEXT:    ret
+entry:
+  br label %bb2
+
+bb2:                                              ; preds = %bb2, %entry
+  %i1 = phi i64 [ %arg1, %entry ], [ %i5, %bb2 ]
+  %i2 = phi i64 [ %arg3, %entry ], [ %i3, %bb2 ]
+  %i3 = add i64 %i2, 1
+  %i4 = lshr i64 %i1, 15
+  %i4b = and i64 %i4, 3
+  %i5 = add i64 %i4b, %arg2
+  %i6 = icmp ugt i64 %i2, 255
+  br i1 %i6, label %bb7, label %bb2
+
+bb7:                                              ; preds = %bb2
+  %i7 = trunc i64 %i5 to i32
+  ret i32 %i7
+}
+
+define signext i32 @hasAllNBitUsers_ext(i64 %arg1, i64 %arg2, i64 %arg3)  {
+; RV64I-LABEL: hasAllNBitUsers_ext:
+; RV64I:       # %bb.0: # %entry
+; RV64I-NEXT:    addi a2, a2, -1
+; RV64I-NEXT:    li a3, 256
+; RV64I-NEXT:  .LBB39_1: # %bb2
+; RV64I-NEXT:    # =>This Inner Loop Header: Depth=1
+; RV64I-NEXT:    slli a0, a0, 47
+; RV64I-NEXT:    srli a0, a0, 62
+; RV64I-NEXT:    addi a2, a2, 1
+; RV64I-NEXT:    addw a0, a0, a1
+; RV64I-NEXT:    bltu a2, a3, .LBB39_1
+; RV64I-NEXT:  # %bb.2: # %bb7
+; RV64I-NEXT:    ret
+;
+; RV64XTHEADBB-LABEL: hasAllNBitUsers_ext:
+; RV64XTHEADBB:       # %bb.0: # %entry
+; RV64XTHEADBB-NEXT:    addi a2, a2, -1
+; RV64XTHEADBB-NEXT:    li a3, 256
+; RV64XTHEADBB-NEXT:  .LBB39_1: # %bb2
+; RV64XTHEADBB-NEXT:    # =>This Inner Loop Header: Depth=1
+; RV64XTHEADBB-NEXT:    th.extu a0, a0, 16, 15
+; RV64XTHEADBB-NEXT:    addi a2, a2, 1
+; RV64XTHEADBB-NEXT:    add a0, a0, a1
+; RV64XTHEADBB-NEXT:    bltu a2, a3, .LBB39_1
+; RV64XTHEADBB-NEXT:  # %bb.2: # %bb7
+; RV64XTHEADBB-NEXT:    sext.w a0, a0
+; RV64XTHEADBB-NEXT:    ret
+entry:
+  br label %bb2
+
+bb2:                                              ; preds = %bb2, %entry
+  %i1 = phi i64 [ %arg1, %entry ], [ %i5, %bb2 ]
+  %i2 = phi i64 [ %arg3, %entry ], [ %i3, %bb2 ]
+  %i3 = add i64 %i2, 1
+  %i4 = ashr i64 %i1, 15
+  %i4b = and i64 %i4, 3
+  %i5 = add i64 %i4b, %arg2
+  %i6 = icmp ugt i64 %i2, 255
+  br i1 %i6, label %bb7, label %bb2
+
+bb7:                                              ; preds = %bb2
+  %i7 = trunc i64 %i5 to i32
+  ret i32 %i7
+}

>From 3b8ffb93be444099172ef4859f30dcd9e313d79d Mon Sep 17 00:00:00 2001
From: Craig Topper <craig.topper at sifive.com>
Date: Mon, 8 Sep 2025 13:14:07 -0700
Subject: [PATCH 2/2] [RISCV] Add TH_EXT(U) to hasAllNBitUsers in
 RISCVOptWInstrs.

---
 llvm/lib/Target/RISCV/RISCVOptWInstrs.cpp  | 8 ++++++++
 llvm/test/CodeGen/RISCV/bitextract-mac.ll  | 4 ++--
 llvm/test/CodeGen/RISCV/ctlz-cttz-ctpop.ll | 2 +-
 llvm/test/CodeGen/RISCV/rv64xtheadbb.ll    | 6 ++----
 4 files changed, 13 insertions(+), 7 deletions(-)

diff --git a/llvm/lib/Target/RISCV/RISCVOptWInstrs.cpp b/llvm/lib/Target/RISCV/RISCVOptWInstrs.cpp
index badc111118727..d08115b72977f 100644
--- a/llvm/lib/Target/RISCV/RISCVOptWInstrs.cpp
+++ b/llvm/lib/Target/RISCV/RISCVOptWInstrs.cpp
@@ -356,6 +356,14 @@ static bool hasAllNBitUsers(const MachineInstr &OrigMI,
           return false;
         Worklist.emplace_back(UserMI, Bits);
         break;
+      case RISCV::TH_EXT:
+      case RISCV::TH_EXTU:
+        unsigned Msb = UserMI->getOperand(2).getImm();
+        unsigned Lsb = UserMI->getOperand(3).getImm();
+        // Behavior of Msb < Lsb is not well documented.
+        if (Msb >= Lsb && Bits > Msb)
+          break;
+        return false;
       }
     }
   }
diff --git a/llvm/test/CodeGen/RISCV/bitextract-mac.ll b/llvm/test/CodeGen/RISCV/bitextract-mac.ll
index 71066b2619cfa..41a32656e3257 100644
--- a/llvm/test/CodeGen/RISCV/bitextract-mac.ll
+++ b/llvm/test/CodeGen/RISCV/bitextract-mac.ll
@@ -107,7 +107,7 @@ define i32 @f(i32 %A, i32 %B, i32 %C) {
 ;
 ; RV64XTHEADBB-LABEL: f:
 ; RV64XTHEADBB:       # %bb.0: # %entry
-; RV64XTHEADBB-NEXT:    mulw a0, a1, a0
+; RV64XTHEADBB-NEXT:    mul a0, a1, a0
 ; RV64XTHEADBB-NEXT:    th.extu a1, a0, 5, 2
 ; RV64XTHEADBB-NEXT:    th.extu a0, a0, 11, 5
 ; RV64XTHEADBB-NEXT:    mul a0, a1, a0
@@ -116,7 +116,7 @@ define i32 @f(i32 %A, i32 %B, i32 %C) {
 ;
 ; RV64XTHEAD-LABEL: f:
 ; RV64XTHEAD:       # %bb.0: # %entry
-; RV64XTHEAD-NEXT:    mulw a0, a1, a0
+; RV64XTHEAD-NEXT:    mul a0, a1, a0
 ; RV64XTHEAD-NEXT:    th.extu a1, a0, 5, 2
 ; RV64XTHEAD-NEXT:    th.extu a0, a0, 11, 5
 ; RV64XTHEAD-NEXT:    th.mulah a2, a1, a0
diff --git a/llvm/test/CodeGen/RISCV/ctlz-cttz-ctpop.ll b/llvm/test/CodeGen/RISCV/ctlz-cttz-ctpop.ll
index c253382d3aac9..908a12331d1bb 100644
--- a/llvm/test/CodeGen/RISCV/ctlz-cttz-ctpop.ll
+++ b/llvm/test/CodeGen/RISCV/ctlz-cttz-ctpop.ll
@@ -2438,7 +2438,7 @@ define i16 @test_ctpop_i16(i16 %a) nounwind {
 ; RV64XTHEADBB-NEXT:    and a0, a0, a2
 ; RV64XTHEADBB-NEXT:    add a0, a1, a0
 ; RV64XTHEADBB-NEXT:    srli a1, a0, 4
-; RV64XTHEADBB-NEXT:    addw a0, a0, a1
+; RV64XTHEADBB-NEXT:    add a0, a0, a1
 ; RV64XTHEADBB-NEXT:    th.extu a1, a0, 11, 8
 ; RV64XTHEADBB-NEXT:    andi a0, a0, 15
 ; RV64XTHEADBB-NEXT:    add a0, a0, a1
diff --git a/llvm/test/CodeGen/RISCV/rv64xtheadbb.ll b/llvm/test/CodeGen/RISCV/rv64xtheadbb.ll
index 6cae6b9f5c8a6..d504d418c150b 100644
--- a/llvm/test/CodeGen/RISCV/rv64xtheadbb.ll
+++ b/llvm/test/CodeGen/RISCV/rv64xtheadbb.ll
@@ -1244,10 +1244,9 @@ define signext i32 @hasAllNBitUsers_extu(i64 %arg1, i64 %arg2, i64 %arg3)  {
 ; RV64XTHEADBB-NEXT:    # =>This Inner Loop Header: Depth=1
 ; RV64XTHEADBB-NEXT:    th.extu a0, a0, 16, 15
 ; RV64XTHEADBB-NEXT:    addi a2, a2, 1
-; RV64XTHEADBB-NEXT:    add a0, a0, a1
+; RV64XTHEADBB-NEXT:    addw a0, a0, a1
 ; RV64XTHEADBB-NEXT:    bltu a2, a3, .LBB38_1
 ; RV64XTHEADBB-NEXT:  # %bb.2: # %bb7
-; RV64XTHEADBB-NEXT:    sext.w a0, a0
 ; RV64XTHEADBB-NEXT:    ret
 entry:
   br label %bb2
@@ -1290,10 +1289,9 @@ define signext i32 @hasAllNBitUsers_ext(i64 %arg1, i64 %arg2, i64 %arg3)  {
 ; RV64XTHEADBB-NEXT:    # =>This Inner Loop Header: Depth=1
 ; RV64XTHEADBB-NEXT:    th.extu a0, a0, 16, 15
 ; RV64XTHEADBB-NEXT:    addi a2, a2, 1
-; RV64XTHEADBB-NEXT:    add a0, a0, a1
+; RV64XTHEADBB-NEXT:    addw a0, a0, a1
 ; RV64XTHEADBB-NEXT:    bltu a2, a3, .LBB39_1
 ; RV64XTHEADBB-NEXT:  # %bb.2: # %bb7
-; RV64XTHEADBB-NEXT:    sext.w a0, a0
 ; RV64XTHEADBB-NEXT:    ret
 entry:
   br label %bb2



More information about the llvm-commits mailing list