diff options
| -rw-r--r-- | llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp | 13 | ||||
| -rw-r--r-- | llvm/test/CodeGen/AArch64/fold-constants.ll | 16 | 
2 files changed, 24 insertions, 5 deletions
diff --git a/llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp b/llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp index 771bb00d86a..4596b8eba1a 100644 --- a/llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp +++ b/llvm/lib/CodeGen/SelectionDAG/SelectionDAG.cpp @@ -3338,12 +3338,15 @@ SDValue SelectionDAG::FoldConstantVectorArithmetic(unsigned Opcode, SDLoc DL,        !std::all_of(Ops.begin(), Ops.end(), IsScalarOrSameVectorSize))      return SDValue(); +  // If we are comparing vectors, then the result needs to be a i1 boolean +  // that is then sign-extended back to the legal result type. +  EVT SVT = (Opcode == ISD::SETCC ? MVT::i1 : VT.getScalarType()); +    // Find legal integer scalar type for constant promotion and    // ensure that its scalar size is at least as large as source. -  EVT SVT = VT.getScalarType(); -  EVT LegalSVT = SVT; -  if (SVT.isInteger()) { -    LegalSVT = TLI->getTypeToTransformTo(*getContext(), SVT); +  EVT LegalSVT = VT.getScalarType(); +  if (LegalSVT.isInteger()) { +    LegalSVT = TLI->getTypeToTransformTo(*getContext(), LegalSVT);      if (LegalSVT.bitsLT(SVT))        return SDValue();    } @@ -3380,7 +3383,7 @@ SDValue SelectionDAG::FoldConstantVectorArithmetic(unsigned Opcode, SDLoc DL,      // Legalize the (integer) scalar constant if necessary.      if (LegalSVT != SVT) -      ScalarResult = getNode(ISD::ANY_EXTEND, DL, LegalSVT, ScalarResult); +      ScalarResult = getNode(ISD::SIGN_EXTEND, DL, LegalSVT, ScalarResult);      // Scalar folding only succeeded if the result is a constant or UNDEF.      if (ScalarResult.getOpcode() != ISD::UNDEF && diff --git a/llvm/test/CodeGen/AArch64/fold-constants.ll b/llvm/test/CodeGen/AArch64/fold-constants.ll index 3f70f0a7e9f..c0fec4d171c 100644 --- a/llvm/test/CodeGen/AArch64/fold-constants.ll +++ b/llvm/test/CodeGen/AArch64/fold-constants.ll @@ -16,3 +16,19 @@ entry:    %vget_lane = extractelement <1 x i64> %4, i32 0    ret i64 %vget_lane  } + +; PR25763 - folding constant vector comparisons with sign-extended result +define <8 x i16> @dotests_458() { +; CHECK-LABEL: dotests_458 +; CHECK:       movi d0, #0x00000000ff0000 +; CHECK-NEXT:  sshll v0.8h, v0.8b, #0 +; CHECK-NEXT:  ret +entry: +  %vclz_v.i = call <8 x i8> @llvm.ctlz.v8i8(<8 x i8> <i8 127, i8 38, i8 -1, i8 -128, i8 127, i8 0, i8 0, i8 0>, i1 false) #6 +  %vsra_n = lshr <8 x i8> %vclz_v.i, <i8 5, i8 5, i8 5, i8 5, i8 5, i8 5, i8 5, i8 5> +  %name_6 = or <8 x i8> %vsra_n, <i8 127, i8 -128, i8 -1, i8 67, i8 84, i8 127, i8 -1, i8 0> +  %cmp.i603 = icmp slt <8 x i8> %name_6, <i8 -57, i8 -128, i8 127, i8 -128, i8 -1, i8 0, i8 -1, i8 -1> +  %vmovl.i4.i = sext <8 x i1> %cmp.i603 to <8 x i16> +  ret <8 x i16> %vmovl.i4.i +} +declare <8 x i8> @llvm.ctlz.v8i8(<8 x i8>, i1)  | 

