[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