diff options
Diffstat (limited to 'llvm/lib/Target/X86/X86ISelLowering.cpp')
-rw-r--r-- | llvm/lib/Target/X86/X86ISelLowering.cpp | 16 |
1 files changed, 13 insertions, 3 deletions
diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp b/llvm/lib/Target/X86/X86ISelLowering.cpp index 3e1806bc4ff..6a0fb38af95 100644 --- a/llvm/lib/Target/X86/X86ISelLowering.cpp +++ b/llvm/lib/Target/X86/X86ISelLowering.cpp @@ -33984,9 +33984,10 @@ static SDValue detectUSatPattern(SDValue In, EVT VT) { /// or: /// (truncate (smax ((smin (x, signed_max_of_dest_type)), /// signed_min_of_dest_type)) to dest_type). +/// With MatchPackUS, the smax/smin range is [0, unsigned_max_of_dest_type]. /// Return the source value to be truncated or SDValue() if the pattern was not /// matched. -static SDValue detectSSatPattern(SDValue In, EVT VT) { +static SDValue detectSSatPattern(SDValue In, EVT VT, bool MatchPackUS = false) { unsigned NumDstBits = VT.getScalarSizeInBits(); unsigned NumSrcBits = In.getScalarValueSizeInBits(); assert(NumSrcBits > NumDstBits && "Unexpected types for truncate operation"); @@ -34000,8 +34001,14 @@ static SDValue detectSSatPattern(SDValue In, EVT VT) { return SDValue(); }; - APInt SignedMax = APInt::getSignedMaxValue(NumDstBits).sext(NumSrcBits); - APInt SignedMin = APInt::getSignedMinValue(NumDstBits).sext(NumSrcBits); + APInt SignedMax, SignedMin; + if (MatchPackUS) { + SignedMax = APInt::getAllOnesValue(NumDstBits).zext(NumSrcBits); + SignedMin = APInt(NumSrcBits, 0); + } else { + SignedMax = APInt::getSignedMaxValue(NumDstBits).sext(NumSrcBits); + SignedMin = APInt::getSignedMinValue(NumDstBits).sext(NumSrcBits); + } if (SDValue SMin = MatchMinMax(In, ISD::SMIN, SignedMax)) if (SDValue SMax = MatchMinMax(SMin, ISD::SMAX, SignedMin)) @@ -34046,6 +34053,9 @@ static SDValue combineTruncateWithSat(SDValue In, EVT VT, const SDLoc &DL, if (auto SSatVal = detectSSatPattern(In, VT)) return truncateVectorWithPACK(X86ISD::PACKSS, VT, SSatVal, DL, DAG, Subtarget); + if (auto USatVal = detectSSatPattern(In, VT, true)) + return truncateVectorWithPACK(X86ISD::PACKUS, VT, USatVal, DL, DAG, + Subtarget); } return SDValue(); } |