[Hexagon] Use legal types when lowering CONCAT_VECTORS via BUILD_VECTOR

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@330344 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Krzysztof Parzyszek 2018-04-19 17:11:58 +00:00
parent b7f081acd6
commit 980f5afda1
2 changed files with 60 additions and 0 deletions

View File

@ -971,6 +971,32 @@ HexagonTargetLowering::LowerHvxConcatVectors(SDValue Op, SelectionDAG &DAG)
SmallVector<SDValue,8> Elems;
for (SDValue V : Op.getNode()->ops())
DAG.ExtractVectorElements(V, Elems);
// A vector of i16 will be broken up into a build_vector of i16's.
// This is a problem, since at the time of operation legalization,
// all operations are expected to be type-legalized, and i16 is not
// a legal type. If any of the extracted elements is not of a valid
// type, sign-extend it to a valid one.
for (unsigned i = 0, e = Elems.size(); i != e; ++i) {
SDValue V = Elems[i];
MVT Ty = ty(V);
if (!isTypeLegal(Ty)) {
EVT NTy = getTypeToTransformTo(*DAG.getContext(), Ty);
if (V.getOpcode() == ISD::EXTRACT_VECTOR_ELT) {
Elems[i] = DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, NTy,
DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, NTy,
V.getOperand(0), V.getOperand(1)),
DAG.getValueType(Ty));
continue;
}
// A few less complicated cases.
if (V.getOpcode() == ISD::Constant)
Elems[i] = DAG.getSExtOrTrunc(V, dl, NTy);
else if (V.isUndef())
Elems[i] = DAG.getUNDEF(NTy);
else
llvm_unreachable("Unexpected vector element");
}
}
return DAG.getBuildVector(VecTy, dl, Elems);
}

View File

@ -0,0 +1,34 @@
; RUN: llc -march=hexagon < %s | FileCheck %s
; Make sure this doesn't crash.
; CHECK: = mem
target triple = "hexagon"
; Function Attrs: nounwind readnone
declare i32 @llvm.hexagon.A2.subh.l16.sat.ll(i32, i32) #0
; Function Attrs: nounwind readonly
define dso_local signext i16 @f0(i16* nocapture readonly %a0) local_unnamed_addr #1 {
b0:
%v0 = load <8 x i16>, <8 x i16>* undef, align 2, !tbaa !0
%v1 = shufflevector <8 x i16> %v0, <8 x i16> undef, <8 x i32> <i32 7, i32 6, i32 5, i32 4, i32 3, i32 2, i32 1, i32 0>
%v2 = shufflevector <8 x i16> %v1, <8 x i16> undef, <16 x i32> <i32 0, i32 1, i32 2, i32 3, i32 4, i32 5, i32 6, i32 7, i32 7, i32 6, i32 5, i32 4, i32 3, i32 2, i32 1, i32 0>
%v3 = lshr <16 x i16> %v2, <i16 2, i16 2, i16 2, i16 2, i16 2, i16 2, i16 2, i16 2, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1>
%v4 = and <16 x i16> %v3, <i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1, i16 1>
%v5 = extractelement <16 x i16> %v4, i32 0
%v6 = sext i16 %v5 to i32
%v7 = tail call i32 @llvm.hexagon.A2.subh.l16.sat.ll(i32 %v6, i32 16)
%v8 = trunc i32 %v7 to i16
%v9 = icmp sgt i16 %v8, -1
%v10 = select i1 %v9, i16 0, i16 undef
ret i16 %v10
}
attributes #0 = { nounwind readnone }
attributes #1 = { nounwind readonly "target-cpu"="hexagonv60" "target-features"="+hvx-length64b,+hvxv60" }
!0 = !{!1, !1, i64 0}
!1 = !{!"short", !2, i64 0}
!2 = !{!"omnipotent char", !3, i64 0}
!3 = !{!"Simple C/C++ TBAA"}