[llvm] c623584 - [RISCV] Add isel patterns for fshl with immediate to select FSRI/FSRIW

Craig Topper via llvm-commits llvm-commits at lists.llvm.org
Thu Nov 5 09:38:19 PST 2020


Author: Craig Topper
Date: 2020-11-05T09:37:43-08:00
New Revision: c623584b6ffacbac6aa012515dab57423cb9f851

URL: https://github.com/llvm/llvm-project/commit/c623584b6ffacbac6aa012515dab57423cb9f851
DIFF: https://github.com/llvm/llvm-project/commit/c623584b6ffacbac6aa012515dab57423cb9f851.diff

LOG: [RISCV] Add isel patterns for fshl with immediate to select FSRI/FSRIW

There is no FSLI instruction, but we can emulate it using FSRI by swapping operands and subtracting the immediate from the bitwidth.

Differential Revision: https://reviews.llvm.org/D90826

Added: 
    

Modified: 
    llvm/lib/Target/RISCV/RISCVInstrInfoB.td
    llvm/test/CodeGen/RISCV/rv32Zbb.ll
    llvm/test/CodeGen/RISCV/rv32Zbbp.ll
    llvm/test/CodeGen/RISCV/rv32Zbt.ll
    llvm/test/CodeGen/RISCV/rv64Zbt.ll

Removed: 
    


################################################################################
diff  --git a/llvm/lib/Target/RISCV/RISCVInstrInfoB.td b/llvm/lib/Target/RISCV/RISCVInstrInfoB.td
index 18abd3bdb6571..382aaa1aec684 100644
--- a/llvm/lib/Target/RISCV/RISCVInstrInfoB.td
+++ b/llvm/lib/Target/RISCV/RISCVInstrInfoB.td
@@ -41,13 +41,19 @@ def shfl_uimm : Operand<XLenVT>, ImmLeaf<XLenVT, [{
 }
 
 
-// Convert rotl immediate to a rotr immediate.
+// Convert rotl immediate to a rotr immediate for XLen instructions.
 def ImmROTL2R : SDNodeXForm<imm, [{
   uint64_t XLen = Subtarget->getXLen();
   return CurDAG->getTargetConstant(XLen - N->getZExtValue(), SDLoc(N),
                                    N->getValueType(0));
 }]>;
 
+// Convert rotl immediate to a rotr immediate for W instructions.
+def ImmROTL2RW : SDNodeXForm<imm, [{
+  return CurDAG->getTargetConstant(32 - N->getZExtValue(), SDLoc(N),
+                                   N->getValueType(0));
+}]>;
+
 //===----------------------------------------------------------------------===//
 // Instruction class templates
 //===----------------------------------------------------------------------===//
@@ -827,6 +833,10 @@ def : Pat<(fshr GPR:$rs3, GPR:$rs1, GPR:$rs2),
           (FSR GPR:$rs1, GPR:$rs2, GPR:$rs3)>;
 def : Pat<(fshr GPR:$rs3, GPR:$rs1, uimmlog2xlen:$shamt),
           (FSRI GPR:$rs1, GPR:$rs3, uimmlog2xlen:$shamt)>;
+// We can use FSRI for fshl by immediate if we subtract the immediate from
+// XLen and swap the operands.
+def : Pat<(fshl GPR:$rs3, GPR:$rs1, uimmlog2xlen:$shamt),
+          (FSRI GPR:$rs1, GPR:$rs3, (ImmROTL2R uimmlog2xlen:$shamt))>;
 } // Predicates = [HasStdExtZbt]
 
 let Predicates = [HasStdExtZbb] in {
@@ -1036,6 +1046,10 @@ def : Pat<(sext_inreg (fshr GPR:$rs3, (shl GPR:$rs1, (i64 32)),
                             uimm6gt32:$shamt),
                       i32),
           (FSRIW GPR:$rs1, GPR:$rs3, (ImmSub32 uimm6gt32:$shamt))>;
+def : Pat<(sext_inreg (fshl GPR:$rs3, (shl GPR:$rs1, (i64 32)),
+                            uimm5:$shamt),
+                      i32),
+          (FSRIW GPR:$rs1, GPR:$rs3, (ImmROTL2RW uimm5:$shamt))>;
 } // Predicates = [HasStdExtZbt, IsRV64]
 
 let Predicates = [HasStdExtZbb, IsRV64] in {

diff  --git a/llvm/test/CodeGen/RISCV/rv32Zbb.ll b/llvm/test/CodeGen/RISCV/rv32Zbb.ll
index d5585f89ec89d..c0776265601a5 100644
--- a/llvm/test/CodeGen/RISCV/rv32Zbb.ll
+++ b/llvm/test/CodeGen/RISCV/rv32Zbb.ll
@@ -245,8 +245,7 @@ define i64 @sloi_i64(i64 %a) nounwind {
 ;
 ; RV32IB-LABEL: sloi_i64:
 ; RV32IB:       # %bb.0:
-; RV32IB-NEXT:    addi a2, zero, 1
-; RV32IB-NEXT:    fsl a1, a1, a0, a2
+; RV32IB-NEXT:    fsri a1, a0, a1, 31
 ; RV32IB-NEXT:    sloi a0, a0, 1
 ; RV32IB-NEXT:    ret
 ;
@@ -297,8 +296,7 @@ define i64 @sroi_i64(i64 %a) nounwind {
 ;
 ; RV32IB-LABEL: sroi_i64:
 ; RV32IB:       # %bb.0:
-; RV32IB-NEXT:    addi a2, zero, 31
-; RV32IB-NEXT:    fsl a0, a1, a0, a2
+; RV32IB-NEXT:    fsri a0, a0, a1, 1
 ; RV32IB-NEXT:    sroi a1, a1, 1
 ; RV32IB-NEXT:    ret
 ;

diff  --git a/llvm/test/CodeGen/RISCV/rv32Zbbp.ll b/llvm/test/CodeGen/RISCV/rv32Zbbp.ll
index 3ab76197151eb..ab75431e151e5 100644
--- a/llvm/test/CodeGen/RISCV/rv32Zbbp.ll
+++ b/llvm/test/CodeGen/RISCV/rv32Zbbp.ll
@@ -693,9 +693,8 @@ define i64 @rori_i64(i64 %a) nounwind {
 ;
 ; RV32IB-LABEL: rori_i64:
 ; RV32IB:       # %bb.0:
-; RV32IB-NEXT:    addi a3, zero, 31
-; RV32IB-NEXT:    fsl a2, a1, a0, a3
-; RV32IB-NEXT:    fsl a1, a0, a1, a3
+; RV32IB-NEXT:    fsri a2, a0, a1, 1
+; RV32IB-NEXT:    fsri a1, a1, a0, 1
 ; RV32IB-NEXT:    mv a0, a2
 ; RV32IB-NEXT:    ret
 ;
@@ -738,9 +737,8 @@ define i64 @rori_i64_fshr(i64 %a) nounwind {
 ;
 ; RV32IB-LABEL: rori_i64_fshr:
 ; RV32IB:       # %bb.0:
-; RV32IB-NEXT:    addi a3, zero, 1
-; RV32IB-NEXT:    fsl a2, a0, a1, a3
-; RV32IB-NEXT:    fsl a1, a1, a0, a3
+; RV32IB-NEXT:    fsri a2, a1, a0, 31
+; RV32IB-NEXT:    fsri a1, a0, a1, 31
 ; RV32IB-NEXT:    mv a0, a2
 ; RV32IB-NEXT:    ret
 ;

diff  --git a/llvm/test/CodeGen/RISCV/rv32Zbt.ll b/llvm/test/CodeGen/RISCV/rv32Zbt.ll
index 52a1c164529e1..2f8d9c6c06783 100644
--- a/llvm/test/CodeGen/RISCV/rv32Zbt.ll
+++ b/llvm/test/CodeGen/RISCV/rv32Zbt.ll
@@ -227,7 +227,7 @@ define i64 @fshl_i64(i64 %a, i64 %b, i64 %c) nounwind {
 ; RV32IB-NEXT:    mv t0, zero
 ; RV32IB-NEXT:    bgez a1, .LBB5_8
 ; RV32IB-NEXT:  .LBB5_5:
-; RV32IB-NEXT:    fsl a1, a3, a2, a6
+; RV32IB-NEXT:    fsri a1, a2, a3, 1
 ; RV32IB-NEXT:    srl a1, a1, t1
 ; RV32IB-NEXT:    sub a2, a6, a5
 ; RV32IB-NEXT:    slli a3, t3, 1
@@ -275,7 +275,7 @@ define i64 @fshl_i64(i64 %a, i64 %b, i64 %c) nounwind {
 ; RV32IBT-NEXT:    mv t0, zero
 ; RV32IBT-NEXT:    bgez a5, .LBB5_8
 ; RV32IBT-NEXT:  .LBB5_5:
-; RV32IBT-NEXT:    fsl a2, a3, a2, a6
+; RV32IBT-NEXT:    fsri a2, a2, a3, 1
 ; RV32IBT-NEXT:    srl a1, a2, a1
 ; RV32IBT-NEXT:    sub a2, a6, t3
 ; RV32IBT-NEXT:    slli a3, t2, 1
@@ -413,15 +413,14 @@ define i64 @fshr_i64(i64 %a, i64 %b, i64 %c) nounwind {
 ; RV32IB-NEXT:    mv t0, zero
 ; RV32IB-NEXT:    bgez a5, .LBB7_8
 ; RV32IB-NEXT:  .LBB7_5:
-; RV32IB-NEXT:    addi a5, zero, 1
-; RV32IB-NEXT:    fsl a1, a1, a0, a5
-; RV32IB-NEXT:    sll a1, a1, t1
 ; RV32IB-NEXT:    sub a2, a6, a2
 ; RV32IB-NEXT:    lui a5, 524288
 ; RV32IB-NEXT:    addi a5, a5, -1
-; RV32IB-NEXT:    and a0, a0, a5
-; RV32IB-NEXT:    srl a0, a0, a2
-; RV32IB-NEXT:    or a1, a1, a0
+; RV32IB-NEXT:    and a5, a0, a5
+; RV32IB-NEXT:    srl a2, a5, a2
+; RV32IB-NEXT:    fsri a0, a0, a1, 31
+; RV32IB-NEXT:    sll a0, a0, t1
+; RV32IB-NEXT:    or a1, a0, a2
 ; RV32IB-NEXT:    or a0, t0, a7
 ; RV32IB-NEXT:    bgez t2, .LBB7_9
 ; RV32IB-NEXT:  .LBB7_6:
@@ -441,53 +440,52 @@ define i64 @fshr_i64(i64 %a, i64 %b, i64 %c) nounwind {
 ;
 ; RV32IBT-LABEL: fshr_i64:
 ; RV32IBT:       # %bb.0:
-; RV32IBT-NEXT:    not a7, a4
-; RV32IBT-NEXT:    andi t1, a7, 63
-; RV32IBT-NEXT:    addi t0, zero, 31
-; RV32IBT-NEXT:    addi t2, t1, -32
-; RV32IBT-NEXT:    slli a6, a0, 1
-; RV32IBT-NEXT:    bltz t2, .LBB7_2
+; RV32IBT-NEXT:    andi a5, a4, 63
+; RV32IBT-NEXT:    addi t1, a5, -32
+; RV32IBT-NEXT:    addi a6, zero, 31
+; RV32IBT-NEXT:    bltz t1, .LBB7_2
 ; RV32IBT-NEXT:  # %bb.1:
-; RV32IBT-NEXT:    sll t1, a6, t2
+; RV32IBT-NEXT:    srl a7, a3, t1
 ; RV32IBT-NEXT:    j .LBB7_3
 ; RV32IBT-NEXT:  .LBB7_2:
-; RV32IBT-NEXT:    addi a5, zero, 1
-; RV32IBT-NEXT:    fsl a1, a1, a0, a5
-; RV32IBT-NEXT:    sll a1, a1, a7
-; RV32IBT-NEXT:    lui a5, 524288
-; RV32IBT-NEXT:    addi a5, a5, -1
-; RV32IBT-NEXT:    and a0, a0, a5
-; RV32IBT-NEXT:    sub a5, t0, t1
-; RV32IBT-NEXT:    srl a0, a0, a5
-; RV32IBT-NEXT:    or t1, a1, a0
+; RV32IBT-NEXT:    srl a7, a2, a4
+; RV32IBT-NEXT:    sub a5, a6, a5
+; RV32IBT-NEXT:    slli a2, a3, 1
+; RV32IBT-NEXT:    sll a2, a2, a5
+; RV32IBT-NEXT:    or a7, a7, a2
 ; RV32IBT-NEXT:  .LBB7_3:
-; RV32IBT-NEXT:    andi a0, a4, 63
-; RV32IBT-NEXT:    addi a5, a0, -32
+; RV32IBT-NEXT:    not a2, a4
+; RV32IBT-NEXT:    andi t2, a2, 63
+; RV32IBT-NEXT:    addi a5, t2, -32
+; RV32IBT-NEXT:    slli t3, a0, 1
 ; RV32IBT-NEXT:    bltz a5, .LBB7_7
 ; RV32IBT-NEXT:  # %bb.4:
-; RV32IBT-NEXT:    mv a1, zero
+; RV32IBT-NEXT:    mv t0, zero
 ; RV32IBT-NEXT:    bgez a5, .LBB7_8
 ; RV32IBT-NEXT:  .LBB7_5:
-; RV32IBT-NEXT:    srl a2, a2, a4
-; RV32IBT-NEXT:    sub a0, t0, a0
-; RV32IBT-NEXT:    slli a3, a3, 1
-; RV32IBT-NEXT:    sll a0, a3, a0
-; RV32IBT-NEXT:    or a2, a2, a0
-; RV32IBT-NEXT:    or a1, t1, a1
-; RV32IBT-NEXT:    bgez t2, .LBB7_9
+; RV32IBT-NEXT:    lui a5, 524288
+; RV32IBT-NEXT:    addi a5, a5, -1
+; RV32IBT-NEXT:    and t3, a0, a5
+; RV32IBT-NEXT:    sub a5, a6, t2
+; RV32IBT-NEXT:    srl a5, t3, a5
+; RV32IBT-NEXT:    fsri a0, a0, a1, 31
+; RV32IBT-NEXT:    sll a0, a0, a2
+; RV32IBT-NEXT:    or a1, a0, a5
+; RV32IBT-NEXT:    or a0, t0, a7
+; RV32IBT-NEXT:    bgez t1, .LBB7_9
 ; RV32IBT-NEXT:  .LBB7_6:
-; RV32IBT-NEXT:    sll a0, a6, a7
-; RV32IBT-NEXT:    or a0, a0, a2
+; RV32IBT-NEXT:    srl a2, a3, a4
+; RV32IBT-NEXT:    or a1, a1, a2
 ; RV32IBT-NEXT:    ret
 ; RV32IBT-NEXT:  .LBB7_7:
-; RV32IBT-NEXT:    srl a1, a3, a4
+; RV32IBT-NEXT:    sll t0, t3, a2
 ; RV32IBT-NEXT:    bltz a5, .LBB7_5
 ; RV32IBT-NEXT:  .LBB7_8:
-; RV32IBT-NEXT:    srl a2, a3, a5
-; RV32IBT-NEXT:    or a1, t1, a1
-; RV32IBT-NEXT:    bltz t2, .LBB7_6
+; RV32IBT-NEXT:    sll a1, t3, a5
+; RV32IBT-NEXT:    or a0, t0, a7
+; RV32IBT-NEXT:    bltz t1, .LBB7_6
 ; RV32IBT-NEXT:  .LBB7_9:
-; RV32IBT-NEXT:    or a0, zero, a2
+; RV32IBT-NEXT:    or a1, a1, zero
 ; RV32IBT-NEXT:    ret
   %1 = tail call i64 @llvm.fshr.i64(i64 %a, i64 %b, i64 %c)
   ret i64 %1
@@ -528,17 +526,15 @@ define i64 @fshri_i64(i64 %a, i64 %b) nounwind {
 ;
 ; RV32IB-LABEL: fshri_i64:
 ; RV32IB:       # %bb.0:
-; RV32IB-NEXT:    addi a1, zero, 27
-; RV32IB-NEXT:    fsl a2, a3, a2, a1
-; RV32IB-NEXT:    fsl a1, a0, a3, a1
+; RV32IB-NEXT:    fsri a2, a2, a3, 5
+; RV32IB-NEXT:    fsri a1, a3, a0, 5
 ; RV32IB-NEXT:    mv a0, a2
 ; RV32IB-NEXT:    ret
 ;
 ; RV32IBT-LABEL: fshri_i64:
 ; RV32IBT:       # %bb.0:
-; RV32IBT-NEXT:    addi a1, zero, 27
-; RV32IBT-NEXT:    fsl a2, a3, a2, a1
-; RV32IBT-NEXT:    fsl a1, a0, a3, a1
+; RV32IBT-NEXT:    fsri a2, a2, a3, 5
+; RV32IBT-NEXT:    fsri a1, a3, a0, 5
 ; RV32IBT-NEXT:    mv a0, a2
 ; RV32IBT-NEXT:    ret
   %1 = tail call i64 @llvm.fshr.i64(i64 %a, i64 %b, i64 5)
@@ -555,14 +551,12 @@ define i32 @fshli_i32(i32 %a, i32 %b) nounwind {
 ;
 ; RV32IB-LABEL: fshli_i32:
 ; RV32IB:       # %bb.0:
-; RV32IB-NEXT:    addi a2, zero, 5
-; RV32IB-NEXT:    fsl a0, a0, a1, a2
+; RV32IB-NEXT:    fsri a0, a1, a0, 27
 ; RV32IB-NEXT:    ret
 ;
 ; RV32IBT-LABEL: fshli_i32:
 ; RV32IBT:       # %bb.0:
-; RV32IBT-NEXT:    addi a2, zero, 5
-; RV32IBT-NEXT:    fsl a0, a0, a1, a2
+; RV32IBT-NEXT:    fsri a0, a1, a0, 27
 ; RV32IBT-NEXT:    ret
   %1 = tail call i32 @llvm.fshl.i32(i32 %a, i32 %b, i32 5)
   ret i32 %1
@@ -582,17 +576,15 @@ define i64 @fshli_i64(i64 %a, i64 %b) nounwind {
 ;
 ; RV32IB-LABEL: fshli_i64:
 ; RV32IB:       # %bb.0:
-; RV32IB-NEXT:    addi a4, zero, 5
-; RV32IB-NEXT:    fsl a2, a0, a3, a4
-; RV32IB-NEXT:    fsl a1, a1, a0, a4
+; RV32IB-NEXT:    fsri a2, a3, a0, 27
+; RV32IB-NEXT:    fsri a1, a0, a1, 27
 ; RV32IB-NEXT:    mv a0, a2
 ; RV32IB-NEXT:    ret
 ;
 ; RV32IBT-LABEL: fshli_i64:
 ; RV32IBT:       # %bb.0:
-; RV32IBT-NEXT:    addi a4, zero, 5
-; RV32IBT-NEXT:    fsl a2, a0, a3, a4
-; RV32IBT-NEXT:    fsl a1, a1, a0, a4
+; RV32IBT-NEXT:    fsri a2, a3, a0, 27
+; RV32IBT-NEXT:    fsri a1, a0, a1, 27
 ; RV32IBT-NEXT:    mv a0, a2
 ; RV32IBT-NEXT:    ret
   %1 = tail call i64 @llvm.fshl.i64(i64 %a, i64 %b, i64 5)

diff  --git a/llvm/test/CodeGen/RISCV/rv64Zbt.ll b/llvm/test/CodeGen/RISCV/rv64Zbt.ll
index 0bc752638cefa..71b6fa25becbb 100644
--- a/llvm/test/CodeGen/RISCV/rv64Zbt.ll
+++ b/llvm/test/CodeGen/RISCV/rv64Zbt.ll
@@ -262,18 +262,12 @@ define signext i32 @fshli_i32(i32 signext %a, i32 signext %b) nounwind {
 ;
 ; RV64IB-LABEL: fshli_i32:
 ; RV64IB:       # %bb.0:
-; RV64IB-NEXT:    slli a1, a1, 32
-; RV64IB-NEXT:    addi a2, zero, 5
-; RV64IB-NEXT:    fsl a0, a0, a1, a2
-; RV64IB-NEXT:    sext.w a0, a0
+; RV64IB-NEXT:    fsriw a0, a1, a0, 27
 ; RV64IB-NEXT:    ret
 ;
 ; RV64IBT-LABEL: fshli_i32:
 ; RV64IBT:       # %bb.0:
-; RV64IBT-NEXT:    slli a1, a1, 32
-; RV64IBT-NEXT:    addi a2, zero, 5
-; RV64IBT-NEXT:    fsl a0, a0, a1, a2
-; RV64IBT-NEXT:    sext.w a0, a0
+; RV64IBT-NEXT:    fsriw a0, a1, a0, 27
 ; RV64IBT-NEXT:    ret
   %1 = tail call i32 @llvm.fshl.i32(i32 %a, i32 %b, i32 5)
   ret i32 %1
@@ -289,14 +283,12 @@ define i64 @fshli_i64(i64 %a, i64 %b) nounwind {
 ;
 ; RV64IB-LABEL: fshli_i64:
 ; RV64IB:       # %bb.0:
-; RV64IB-NEXT:    addi a2, zero, 5
-; RV64IB-NEXT:    fsl a0, a0, a1, a2
+; RV64IB-NEXT:    fsri a0, a1, a0, 59
 ; RV64IB-NEXT:    ret
 ;
 ; RV64IBT-LABEL: fshli_i64:
 ; RV64IBT:       # %bb.0:
-; RV64IBT-NEXT:    addi a2, zero, 5
-; RV64IBT-NEXT:    fsl a0, a0, a1, a2
+; RV64IBT-NEXT:    fsri a0, a1, a0, 59
 ; RV64IBT-NEXT:    ret
   %1 = tail call i64 @llvm.fshl.i64(i64 %a, i64 %b, i64 5)
   ret i64 %1


        


More information about the llvm-commits mailing list