[SelectionDAG][RISCV] Teach ComputeNumSignBits to handle SREM.

This also removes a pattern from RISCV that is no longer needed
since the sexti32 on the LHS of the srem in the pattern implies
the result is sign extended so the sign_extend_inreg should be
removed in DAG combine now.

Reviewed By: luismarques, RKSimon

Differential Revision: https://reviews.llvm.org/D97133
This commit is contained in:
Craig Topper 2021-02-21 11:13:34 -08:00
parent bae04a3e2d
commit 1a6c1ac686
4 changed files with 55 additions and 105 deletions

View File

@ -3869,6 +3869,12 @@ unsigned SelectionDAG::ComputeNumSignBits(SDValue Op, const APInt &DemandedElts,
(VTBits - SignBitsOp0 + 1) + (VTBits - SignBitsOp1 + 1);
return OutValidBits > VTBits ? 1 : VTBits - OutValidBits + 1;
}
case ISD::SREM:
// The sign bit is the LHS's sign bit, except when the result of the
// remainder is zero. The magnitude of the result should be less than or
// equal to the magnitude of the LHS. Therefore, the result should have
// at least as many sign bits as the left hand side.
return ComputeNumSignBits(Op.getOperand(0), DemandedElts, Depth + 1);
case ISD::TRUNCATE: {
// Check if the sign bits of source go down as far as the truncated value.
unsigned NumSrcBits = Op.getOperand(0).getScalarValueSizeInBits();

View File

@ -93,7 +93,4 @@ def : Pat<(and (riscv_remuw (assertzexti32 GPR:$rs1),
// produce a result where res[63:32]=0 and res[31]=1.
def : Pat<(srem (sexti32 GPR:$rs1), (sexti32 GPR:$rs2)),
(REMW GPR:$rs1, GPR:$rs2)>;
def : Pat<(sext_inreg (srem (sexti32 GPR:$rs1),
(sexti32 GPR:$rs2)), i32),
(REMW GPR:$rs1, GPR:$rs2)>;
} // Predicates = [HasStdExtM, IsRV64]

View File

@ -1,29 +1,29 @@
; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
; RUN: llc < %s -mtriple=mips -mcpu=mips2 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP32,GP32R0R2
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP32
; RUN: llc < %s -mtriple=mips -mcpu=mips32 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP32,GP32R0R2
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP32
; RUN: llc < %s -mtriple=mips -mcpu=mips32r2 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP32,GP32R2R5
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP32
; RUN: llc < %s -mtriple=mips -mcpu=mips32r3 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP32,GP32R2R5
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP32
; RUN: llc < %s -mtriple=mips -mcpu=mips32r5 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP32,GP32R2R5
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP32
; RUN: llc < %s -mtriple=mips -mcpu=mips32r6 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefix=GP32R6
; RUN: llc < %s -mtriple=mips64 -mcpu=mips3 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP64,GP64R0R1
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP64
; RUN: llc < %s -mtriple=mips64 -mcpu=mips4 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP64,GP64R0R1
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP64
; RUN: llc < %s -mtriple=mips64 -mcpu=mips64 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP64,GP64R0R1
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP64
; RUN: llc < %s -mtriple=mips64 -mcpu=mips64r2 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP64,GP64R2R5
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP64
; RUN: llc < %s -mtriple=mips64 -mcpu=mips64r3 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP64,GP64R2R5
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP64
; RUN: llc < %s -mtriple=mips64 -mcpu=mips64r5 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP64,GP64R2R5
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefixes=GP64
; RUN: llc < %s -mtriple=mips64 -mcpu=mips64r6 -relocation-model=pic \
; RUN: -mips-jalr-reloc=false | FileCheck %s -check-prefix=GP64R6
@ -70,67 +70,43 @@ entry:
}
define signext i8 @srem_i8(i8 signext %a, i8 signext %b) {
; GP32R0R2-LABEL: srem_i8:
; GP32R0R2: # %bb.0: # %entry
; GP32R0R2-NEXT: div $zero, $4, $5
; GP32R0R2-NEXT: teq $5, $zero, 7
; GP32R0R2-NEXT: mfhi $1
; GP32R0R2-NEXT: sll $1, $1, 24
; GP32R0R2-NEXT: jr $ra
; GP32R0R2-NEXT: sra $2, $1, 24
;
; GP32R2R5-LABEL: srem_i8:
; GP32R2R5: # %bb.0: # %entry
; GP32R2R5-NEXT: div $zero, $4, $5
; GP32R2R5-NEXT: teq $5, $zero, 7
; GP32R2R5-NEXT: mfhi $1
; GP32R2R5-NEXT: jr $ra
; GP32R2R5-NEXT: seb $2, $1
; GP32-LABEL: srem_i8:
; GP32: # %bb.0: # %entry
; GP32-NEXT: div $zero, $4, $5
; GP32-NEXT: teq $5, $zero, 7
; GP32-NEXT: jr $ra
; GP32-NEXT: mfhi $2
;
; GP32R6-LABEL: srem_i8:
; GP32R6: # %bb.0: # %entry
; GP32R6-NEXT: mod $1, $4, $5
; GP32R6-NEXT: mod $2, $4, $5
; GP32R6-NEXT: teq $5, $zero, 7
; GP32R6-NEXT: jr $ra
; GP32R6-NEXT: seb $2, $1
; GP32R6-NEXT: jrc $ra
;
; GP64R0R1-LABEL: srem_i8:
; GP64R0R1: # %bb.0: # %entry
; GP64R0R1-NEXT: div $zero, $4, $5
; GP64R0R1-NEXT: teq $5, $zero, 7
; GP64R0R1-NEXT: mfhi $1
; GP64R0R1-NEXT: sll $1, $1, 24
; GP64R0R1-NEXT: jr $ra
; GP64R0R1-NEXT: sra $2, $1, 24
;
; GP64R2R5-LABEL: srem_i8:
; GP64R2R5: # %bb.0: # %entry
; GP64R2R5-NEXT: div $zero, $4, $5
; GP64R2R5-NEXT: teq $5, $zero, 7
; GP64R2R5-NEXT: mfhi $1
; GP64R2R5-NEXT: jr $ra
; GP64R2R5-NEXT: seb $2, $1
; GP64-LABEL: srem_i8:
; GP64: # %bb.0: # %entry
; GP64-NEXT: div $zero, $4, $5
; GP64-NEXT: teq $5, $zero, 7
; GP64-NEXT: jr $ra
; GP64-NEXT: mfhi $2
;
; GP64R6-LABEL: srem_i8:
; GP64R6: # %bb.0: # %entry
; GP64R6-NEXT: mod $1, $4, $5
; GP64R6-NEXT: mod $2, $4, $5
; GP64R6-NEXT: teq $5, $zero, 7
; GP64R6-NEXT: jr $ra
; GP64R6-NEXT: seb $2, $1
; GP64R6-NEXT: jrc $ra
;
; MMR3-LABEL: srem_i8:
; MMR3: # %bb.0: # %entry
; MMR3-NEXT: div $zero, $4, $5
; MMR3-NEXT: teq $5, $zero, 7
; MMR3-NEXT: mfhi16 $1
; MMR3-NEXT: jr $ra
; MMR3-NEXT: seb $2, $1
; MMR3-NEXT: mfhi16 $2
; MMR3-NEXT: jrc $ra
;
; MMR6-LABEL: srem_i8:
; MMR6: # %bb.0: # %entry
; MMR6-NEXT: mod $1, $4, $5
; MMR6-NEXT: mod $2, $4, $5
; MMR6-NEXT: teq $5, $zero, 7
; MMR6-NEXT: seb $2, $1
; MMR6-NEXT: jrc $ra
entry:
%r = srem i8 %a, %b
@ -138,67 +114,43 @@ entry:
}
define signext i16 @srem_i16(i16 signext %a, i16 signext %b) {
; GP32R0R2-LABEL: srem_i16:
; GP32R0R2: # %bb.0: # %entry
; GP32R0R2-NEXT: div $zero, $4, $5
; GP32R0R2-NEXT: teq $5, $zero, 7
; GP32R0R2-NEXT: mfhi $1
; GP32R0R2-NEXT: sll $1, $1, 16
; GP32R0R2-NEXT: jr $ra
; GP32R0R2-NEXT: sra $2, $1, 16
;
; GP32R2R5-LABEL: srem_i16:
; GP32R2R5: # %bb.0: # %entry
; GP32R2R5-NEXT: div $zero, $4, $5
; GP32R2R5-NEXT: teq $5, $zero, 7
; GP32R2R5-NEXT: mfhi $1
; GP32R2R5-NEXT: jr $ra
; GP32R2R5-NEXT: seh $2, $1
; GP32-LABEL: srem_i16:
; GP32: # %bb.0: # %entry
; GP32-NEXT: div $zero, $4, $5
; GP32-NEXT: teq $5, $zero, 7
; GP32-NEXT: jr $ra
; GP32-NEXT: mfhi $2
;
; GP32R6-LABEL: srem_i16:
; GP32R6: # %bb.0: # %entry
; GP32R6-NEXT: mod $1, $4, $5
; GP32R6-NEXT: mod $2, $4, $5
; GP32R6-NEXT: teq $5, $zero, 7
; GP32R6-NEXT: jr $ra
; GP32R6-NEXT: seh $2, $1
; GP32R6-NEXT: jrc $ra
;
; GP64R0R1-LABEL: srem_i16:
; GP64R0R1: # %bb.0: # %entry
; GP64R0R1-NEXT: div $zero, $4, $5
; GP64R0R1-NEXT: teq $5, $zero, 7
; GP64R0R1-NEXT: mfhi $1
; GP64R0R1-NEXT: sll $1, $1, 16
; GP64R0R1-NEXT: jr $ra
; GP64R0R1-NEXT: sra $2, $1, 16
;
; GP64R2R5-LABEL: srem_i16:
; GP64R2R5: # %bb.0: # %entry
; GP64R2R5-NEXT: div $zero, $4, $5
; GP64R2R5-NEXT: teq $5, $zero, 7
; GP64R2R5-NEXT: mfhi $1
; GP64R2R5-NEXT: jr $ra
; GP64R2R5-NEXT: seh $2, $1
; GP64-LABEL: srem_i16:
; GP64: # %bb.0: # %entry
; GP64-NEXT: div $zero, $4, $5
; GP64-NEXT: teq $5, $zero, 7
; GP64-NEXT: jr $ra
; GP64-NEXT: mfhi $2
;
; GP64R6-LABEL: srem_i16:
; GP64R6: # %bb.0: # %entry
; GP64R6-NEXT: mod $1, $4, $5
; GP64R6-NEXT: mod $2, $4, $5
; GP64R6-NEXT: teq $5, $zero, 7
; GP64R6-NEXT: jr $ra
; GP64R6-NEXT: seh $2, $1
; GP64R6-NEXT: jrc $ra
;
; MMR3-LABEL: srem_i16:
; MMR3: # %bb.0: # %entry
; MMR3-NEXT: div $zero, $4, $5
; MMR3-NEXT: teq $5, $zero, 7
; MMR3-NEXT: mfhi16 $1
; MMR3-NEXT: jr $ra
; MMR3-NEXT: seh $2, $1
; MMR3-NEXT: mfhi16 $2
; MMR3-NEXT: jrc $ra
;
; MMR6-LABEL: srem_i16:
; MMR6: # %bb.0: # %entry
; MMR6-NEXT: mod $1, $4, $5
; MMR6-NEXT: mod $2, $4, $5
; MMR6-NEXT: teq $5, $zero, 7
; MMR6-NEXT: seh $2, $1
; MMR6-NEXT: jrc $ra
entry:
%r = srem i16 %a, %b

View File

@ -1092,8 +1092,6 @@ define signext i8 @sext_remw_sext_sext_i8(i8 signext %a, i8 signext %b) nounwind
; RV64IM-LABEL: sext_remw_sext_sext_i8:
; RV64IM: # %bb.0:
; RV64IM-NEXT: remw a0, a0, a1
; RV64IM-NEXT: slli a0, a0, 56
; RV64IM-NEXT: srai a0, a0, 56
; RV64IM-NEXT: ret
%1 = srem i8 %a, %b
ret i8 %1
@ -1103,8 +1101,6 @@ define signext i16 @sext_remw_sext_sext_i16(i16 signext %a, i16 signext %b) noun
; RV64IM-LABEL: sext_remw_sext_sext_i16:
; RV64IM: # %bb.0:
; RV64IM-NEXT: remw a0, a0, a1
; RV64IM-NEXT: slli a0, a0, 48
; RV64IM-NEXT: srai a0, a0, 48
; RV64IM-NEXT: ret
%1 = srem i16 %a, %b
ret i16 %1
@ -1127,7 +1123,6 @@ define signext i32 @sext_i32_remw_sext_zext_i16(i16 signext %a, i16 zeroext %b)
; RV64IM-LABEL: sext_i32_remw_sext_zext_i16:
; RV64IM: # %bb.0:
; RV64IM-NEXT: rem a0, a0, a1
; RV64IM-NEXT: sext.w a0, a0
; RV64IM-NEXT: ret
%1 = sext i16 %a to i32
%2 = zext i16 %b to i32