diff --git a/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp b/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp index 120c38ab8404c..1aa1d465d8da6 100644 --- a/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp +++ b/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp @@ -6684,13 +6684,24 @@ LegalizerHelper::moreElementsVector(MachineInstr &MI, unsigned TypeIdx, case TargetOpcode::G_FMAXIMUMNUM: case TargetOpcode::G_STRICT_FADD: case TargetOpcode::G_STRICT_FSUB: - case TargetOpcode::G_STRICT_FMUL: + case TargetOpcode::G_STRICT_FMUL: { + Observer.changingInstr(MI); + moreElementsVectorSrc(MI, MoreTy, 1); + moreElementsVectorSrc(MI, MoreTy, 2); + moreElementsVectorDst(MI, MoreTy, 0); + Observer.changedInstr(MI); + return Legalized; + } case TargetOpcode::G_SHL: case TargetOpcode::G_ASHR: case TargetOpcode::G_LSHR: { Observer.changingInstr(MI); moreElementsVectorSrc(MI, MoreTy, 1); - moreElementsVectorSrc(MI, MoreTy, 2); + // The shift operand may have a different scalar type from the source and + // destination operands. + LLT ShiftMoreTy = MoreTy.changeElementType( + MRI.getType(MI.getOperand(2).getReg()).getElementType()); + moreElementsVectorSrc(MI, ShiftMoreTy, 2); moreElementsVectorDst(MI, MoreTy, 0); Observer.changedInstr(MI); return Legalized; @@ -6806,12 +6817,10 @@ LegalizerHelper::moreElementsVector(MachineInstr &MI, unsigned TypeIdx, LLT DstExtTy; if (TypeIdx == 0) { DstExtTy = MoreTy; - SrcExtTy = LLT::fixed_vector( - MoreTy.getNumElements(), + SrcExtTy = MoreTy.changeElementType( MRI.getType(MI.getOperand(1).getReg()).getElementType()); } else { - DstExtTy = LLT::fixed_vector( - MoreTy.getNumElements(), + DstExtTy = MoreTy.changeElementType( MRI.getType(MI.getOperand(0).getReg()).getElementType()); SrcExtTy = MoreTy; } diff --git a/llvm/test/CodeGen/AArch64/shift.ll b/llvm/test/CodeGen/AArch64/shift.ll index 9827cb3526f99..98c7f673ecd01 100644 --- a/llvm/test/CodeGen/AArch64/shift.ll +++ b/llvm/test/CodeGen/AArch64/shift.ll @@ -1033,6 +1033,37 @@ define <2 x i128> @lshr_v2i128(<2 x i128> %0, <2 x i128> %1){ ret <2 x i128> %3 } +define <2 x i8> @pr168848(<2 x i1> %shift) { +; CHECK-SD-LABEL: pr168848: +; CHECK-SD: // %bb.0: // %entry +; CHECK-SD-NEXT: movi v1.2s, #1 +; CHECK-SD-NEXT: and v0.8b, v0.8b, v1.8b +; CHECK-SD-NEXT: ushl v0.2s, v1.2s, v0.2s +; CHECK-SD-NEXT: ret +; +; CHECK-GI-LABEL: pr168848: +; CHECK-GI: // %bb.0: // %entry +; CHECK-GI-NEXT: movi v1.2s, #1 +; CHECK-GI-NEXT: mov w8, #1 // =0x1 +; CHECK-GI-NEXT: and v0.8b, v0.8b, v1.8b +; CHECK-GI-NEXT: fmov s1, w8 +; CHECK-GI-NEXT: uzp1 v0.4h, v0.4h, v0.4h +; CHECK-GI-NEXT: mov v1.b[1], w8 +; CHECK-GI-NEXT: uzp1 v0.8b, v0.8b, v0.8b +; CHECK-GI-NEXT: ushl v0.8b, v1.8b, v0.8b +; CHECK-GI-NEXT: umov w8, v0.b[0] +; CHECK-GI-NEXT: umov w9, v0.b[1] +; CHECK-GI-NEXT: fmov s0, w8 +; CHECK-GI-NEXT: mov v0.s[1], w9 +; CHECK-GI-NEXT: // kill: def $d0 killed $d0 killed $q0 +; CHECK-GI-NEXT: ret +entry: + %shift.zext = zext <2 x i1> %shift to <2 x i32> + %ones = shl <2 x i32> splat (i32 1), %shift.zext + %ones.trunc = trunc <2 x i32> %ones to <2 x i8> + ret <2 x i8> %ones.trunc +} + ; ===== Vector with Non-Pow 2 Width ===== define <3 x i8> @shl_v3i8(<3 x i8> %0, <3 x i8> %1){