1
0
mirror of https://github.com/RPCS3/llvm-mirror.git synced 2024-11-22 18:54:02 +01:00

[RISCV] Have sexti32 also recognize AssertZExt from types smaller than i32.

An i64 AssertZExt from a type smaller than i32 has at least 33
leading zeros which mean it has at least 33 sign bits.

Since we have a couple patterns that use two sexti32, I've
switched to a ComplexPattern so tablegen didn't have to generate
9 different permutations.

As noted in the FIXME, maybe we should just call computeNumSignBits,
but we don't have tests that benefit from that yet.

Reviewed By: luismarques

Differential Revision: https://reviews.llvm.org/D97130
This commit is contained in:
Craig Topper 2021-02-22 14:36:44 -08:00
parent 782b2539f9
commit 44d510a3c6
8 changed files with 30 additions and 9 deletions

View File

@ -1123,6 +1123,27 @@ bool RISCVDAGToDAGISel::selectShiftMask(SDValue N, unsigned ShiftWidth,
return true;
}
bool RISCVDAGToDAGISel::selectSExti32(SDValue N, SDValue &Val) {
if (N.getOpcode() == ISD::SIGN_EXTEND_INREG &&
cast<VTSDNode>(N.getOperand(1))->getVT() == MVT::i32) {
Val = N.getOperand(0);
return true;
}
// FIXME: Should we just call computeNumSignBits here?
if (N.getOpcode() == ISD::AssertSext &&
cast<VTSDNode>(N->getOperand(1))->getVT().bitsLE(MVT::i32)) {
Val = N;
return true;
}
if (N.getOpcode() == ISD::AssertZext &&
cast<VTSDNode>(N->getOperand(1))->getVT().bitsLT(MVT::i32)) {
Val = N;
return true;
}
return false;
}
// Match (srl (and val, mask), imm) where the result would be a
// zero-extended 32-bit integer. i.e. the mask is 0xffffffff or the result
// is equivalent to this (SimplifyDemandedBits may have removed lower bits

View File

@ -54,6 +54,8 @@ public:
return selectShiftMask(N, 32, ShAmt);
}
bool selectSExti32(SDValue N, SDValue &Val);
bool MatchSRLIW(SDNode *N) const;
bool MatchSLLIUW(SDNode *N) const;

View File

@ -848,9 +848,7 @@ def IsOrAdd: PatFrag<(ops node:$A, node:$B), (or node:$A, node:$B), [{
def assertsexti32 : PatFrag<(ops node:$src), (assertsext node:$src), [{
return cast<VTSDNode>(N->getOperand(1))->getVT().bitsLE(MVT::i32);
}]>;
def sexti32 : PatFrags<(ops node:$src),
[(sext_inreg node:$src, i32),
(assertsexti32 node:$src)]>;
def sexti32 : ComplexPattern<i64, 1, "selectSExti32">;
def assertzexti32 : PatFrag<(ops node:$src), (assertzext node:$src), [{
return cast<VTSDNode>(N->getOperand(1))->getVT().bitsLE(MVT::i32);
}]>;

View File

@ -356,7 +356,7 @@ def : Pat<(sext_inreg (assertzexti32 (fp_to_uint FPR64:$rs1)), i32),
(FCVT_WU_D $rs1, 0b001)>;
// [u]int32->fp
def : Pat<(sint_to_fp (i64 (sexti32 GPR:$rs1))), (FCVT_D_W $rs1)>;
def : Pat<(sint_to_fp (i64 (sexti32 (i64 GPR:$rs1)))), (FCVT_D_W $rs1)>;
def : Pat<(uint_to_fp (i64 (zexti32 GPR:$rs1))), (FCVT_D_WU $rs1)>;
def : Pat<(i64 (fp_to_sint FPR64:$rs1)), (FCVT_L_D FPR64:$rs1, 0b001)>;

View File

@ -400,7 +400,7 @@ def : Pat<(i64 (fp_to_sint FPR32:$rs1)), (FCVT_L_S $rs1, 0b001)>;
def : Pat<(i64 (fp_to_uint FPR32:$rs1)), (FCVT_LU_S $rs1, 0b001)>;
// [u]int->fp. Match GCC and default to using dynamic rounding mode.
def : Pat<(sint_to_fp (i64 (sexti32 GPR:$rs1))), (FCVT_S_W $rs1, 0b111)>;
def : Pat<(sint_to_fp (i64 (sexti32 (i64 GPR:$rs1)))), (FCVT_S_W $rs1, 0b111)>;
def : Pat<(uint_to_fp (i64 (zexti32 GPR:$rs1))), (FCVT_S_WU $rs1, 0b111)>;
def : Pat<(sint_to_fp (i64 GPR:$rs1)), (FCVT_S_L $rs1, 0b111)>;
def : Pat<(uint_to_fp (i64 GPR:$rs1)), (FCVT_S_LU $rs1, 0b111)>;

View File

@ -91,6 +91,6 @@ def : Pat<(and (riscv_remuw (assertzexti32 GPR:$rs1),
// Although the sexti32 operands may not have originated from an i32 srem,
// this pattern is safe as it is impossible for two sign extended inputs to
// produce a result where res[63:32]=0 and res[31]=1.
def : Pat<(srem (sexti32 GPR:$rs1), (sexti32 GPR:$rs2)),
def : Pat<(srem (sexti32 (i64 GPR:$rs1)), (sexti32 (i64 GPR:$rs2))),
(REMW GPR:$rs1, GPR:$rs2)>;
} // Predicates = [HasStdExtM, IsRV64]

View File

@ -357,7 +357,7 @@ def : Pat<(i64 (fp_to_sint FPR16:$rs1)), (FCVT_L_H $rs1, 0b001)>;
def : Pat<(i64 (fp_to_uint FPR16:$rs1)), (FCVT_LU_H $rs1, 0b001)>;
// [u]int->fp. Match GCC and default to using dynamic rounding mode.
def : Pat<(sint_to_fp (i64 (sexti32 GPR:$rs1))), (FCVT_H_W $rs1, 0b111)>;
def : Pat<(sint_to_fp (i64 (sexti32 (i64 GPR:$rs1)))), (FCVT_H_W $rs1, 0b111)>;
def : Pat<(uint_to_fp (i64 (zexti32 GPR:$rs1))), (FCVT_H_WU $rs1, 0b111)>;
def : Pat<(sint_to_fp (i64 GPR:$rs1)), (FCVT_H_L $rs1, 0b111)>;
def : Pat<(uint_to_fp (i64 GPR:$rs1)), (FCVT_H_LU $rs1, 0b111)>;

View File

@ -1109,7 +1109,7 @@ define signext i16 @sext_remw_sext_sext_i16(i16 signext %a, i16 signext %b) noun
define signext i32 @sext_i32_remw_zext_sext_i16(i16 zeroext %0, i16 signext %1) nounwind {
; RV64IM-LABEL: sext_i32_remw_zext_sext_i16:
; RV64IM: # %bb.0:
; RV64IM-NEXT: rem a0, a0, a1
; RV64IM-NEXT: remw a0, a0, a1
; RV64IM-NEXT: ret
%3 = sext i16 %1 to i32
%4 = zext i16 %0 to i32
@ -1120,7 +1120,7 @@ define signext i32 @sext_i32_remw_zext_sext_i16(i16 zeroext %0, i16 signext %1)
define signext i32 @sext_i32_remw_sext_zext_i16(i16 signext %a, i16 zeroext %b) nounwind {
; RV64IM-LABEL: sext_i32_remw_sext_zext_i16:
; RV64IM: # %bb.0:
; RV64IM-NEXT: rem a0, a0, a1
; RV64IM-NEXT: remw a0, a0, a1
; RV64IM-NEXT: ret
%1 = sext i16 %a to i32
%2 = zext i16 %b to i32