forked from OSchip/llvm-project
[InstCombine] Add constant vector support to getMinimumFPType for visitFPTrunc.
This patch teaches getMinimumFPType to support shrinking a vector of ConstantFPs. This should improve our ability to combine vector fptrunc with fp binops. Differential Revision: https://reviews.llvm.org/D43774 llvm-svn: 326729
This commit is contained in:
parent
75bc70fb56
commit
8452faceae
|
@ -1435,6 +1435,36 @@ static Type *shrinkFPConstant(ConstantFP *CFP) {
|
|||
return nullptr;
|
||||
}
|
||||
|
||||
// Determine if this is a vector of ConstantFPs and if so, return the minimal
|
||||
// type we can safely truncate all elements to.
|
||||
// TODO: Make these support undef elements.
|
||||
static Type *shrinkFPConstantVector(Value *V) {
|
||||
auto *CV = dyn_cast<Constant>(V);
|
||||
if (!CV || !CV->getType()->isVectorTy())
|
||||
return nullptr;
|
||||
|
||||
Type *MinType = nullptr;
|
||||
|
||||
unsigned NumElts = CV->getType()->getVectorNumElements();
|
||||
for (unsigned i = 0; i != NumElts; ++i) {
|
||||
auto *CFP = dyn_cast_or_null<ConstantFP>(CV->getAggregateElement(i));
|
||||
if (!CFP)
|
||||
return nullptr;
|
||||
|
||||
Type *T = shrinkFPConstant(CFP);
|
||||
if (!T)
|
||||
return nullptr;
|
||||
|
||||
// If we haven't found a type yet or this type has a larger mantissa than
|
||||
// our previous type, this is our new minimal type.
|
||||
if (!MinType || T->getFPMantissaWidth() > MinType->getFPMantissaWidth())
|
||||
MinType = T;
|
||||
}
|
||||
|
||||
// Make a vector type from the minimal type.
|
||||
return VectorType::get(MinType, NumElts);
|
||||
}
|
||||
|
||||
/// Find the minimum FP type we can safely truncate to.
|
||||
static Type *getMinimumFPType(Value *V) {
|
||||
if (auto *FPExt = dyn_cast<FPExtInst>(V))
|
||||
|
@ -1447,6 +1477,10 @@ static Type *getMinimumFPType(Value *V) {
|
|||
if (Type *T = shrinkFPConstant(CFP))
|
||||
return T;
|
||||
|
||||
// Try to shrink a vector of FP constants.
|
||||
if (Type *T = shrinkFPConstantVector(V))
|
||||
return T;
|
||||
|
||||
return V->getType();
|
||||
}
|
||||
|
||||
|
|
|
@ -59,9 +59,7 @@ entry:
|
|||
define <2 x float> @test5(<2 x float> %x) nounwind {
|
||||
; CHECK-LABEL: @test5(
|
||||
; CHECK-NEXT: entry:
|
||||
; CHECK-NEXT: [[TMP1:%.*]] = fpext <2 x float> [[X:%.*]] to <2 x double>
|
||||
; CHECK-NEXT: [[TMP3:%.*]] = fadd <2 x double> [[TMP1]], zeroinitializer
|
||||
; CHECK-NEXT: [[TMP34:%.*]] = fptrunc <2 x double> [[TMP3]] to <2 x float>
|
||||
; CHECK-NEXT: [[TMP34:%.*]] = fadd <2 x float> [[X:%.*]], zeroinitializer
|
||||
; CHECK-NEXT: ret <2 x float> [[TMP34]]
|
||||
;
|
||||
entry:
|
||||
|
@ -75,9 +73,7 @@ entry:
|
|||
define <2 x float> @test6(<2 x float> %x) nounwind {
|
||||
; CHECK-LABEL: @test6(
|
||||
; CHECK-NEXT: entry:
|
||||
; CHECK-NEXT: [[TMP1:%.*]] = fpext <2 x float> [[X:%.*]] to <2 x double>
|
||||
; CHECK-NEXT: [[TMP3:%.*]] = fadd <2 x double> [[TMP1]], <double 0.000000e+00, double -0.000000e+00>
|
||||
; CHECK-NEXT: [[TMP34:%.*]] = fptrunc <2 x double> [[TMP3]] to <2 x float>
|
||||
; CHECK-NEXT: [[TMP34:%.*]] = fadd <2 x float> [[X:%.*]], <float 0.000000e+00, float -0.000000e+00>
|
||||
; CHECK-NEXT: ret <2 x float> [[TMP34]]
|
||||
;
|
||||
entry:
|
||||
|
@ -87,11 +83,26 @@ entry:
|
|||
ret <2 x float> %tmp34
|
||||
}
|
||||
|
||||
; Test with an undef element
|
||||
; TODO: Support undef elements.
|
||||
define <2 x float> @test6_undef(<2 x float> %x) nounwind {
|
||||
; CHECK-LABEL: @test6_undef(
|
||||
; CHECK-NEXT: entry:
|
||||
; CHECK-NEXT: [[TMP1:%.*]] = fpext <2 x float> [[X:%.*]] to <2 x double>
|
||||
; CHECK-NEXT: [[TMP3:%.*]] = fadd <2 x double> [[TMP1]], <double 0.000000e+00, double undef>
|
||||
; CHECK-NEXT: [[TMP34:%.*]] = fptrunc <2 x double> [[TMP3]] to <2 x float>
|
||||
; CHECK-NEXT: ret <2 x float> [[TMP34]]
|
||||
;
|
||||
entry:
|
||||
%tmp1 = fpext <2 x float> %x to <2 x double>
|
||||
%tmp3 = fadd <2 x double> %tmp1, <double 0.000000e+00, double undef>
|
||||
%tmp34 = fptrunc <2 x double> %tmp3 to <2 x float>
|
||||
ret <2 x float> %tmp34
|
||||
}
|
||||
|
||||
define <2 x float> @not_half_shrinkable(<2 x float> %x) {
|
||||
; CHECK-LABEL: @not_half_shrinkable(
|
||||
; CHECK-NEXT: [[EXT:%.*]] = fpext <2 x float> [[X:%.*]] to <2 x double>
|
||||
; CHECK-NEXT: [[ADD:%.*]] = fadd <2 x double> [[EXT]], <double 0.000000e+00, double 2.049000e+03>
|
||||
; CHECK-NEXT: [[R:%.*]] = fptrunc <2 x double> [[ADD]] to <2 x float>
|
||||
; CHECK-NEXT: [[R:%.*]] = fadd <2 x float> [[X:%.*]], <float 0.000000e+00, float 2.049000e+03>
|
||||
; CHECK-NEXT: ret <2 x float> [[R]]
|
||||
;
|
||||
%ext = fpext <2 x float> %x to <2 x double>
|
||||
|
|
Loading…
Reference in New Issue