Index: lib/Transforms/InstCombine/InstCombineVectorOps.cpp =================================================================== --- lib/Transforms/InstCombine/InstCombineVectorOps.cpp +++ lib/Transforms/InstCombine/InstCombineVectorOps.cpp @@ -322,6 +322,18 @@ return BinaryOperator::CreateWithCopiedFlags(BO->getOpcode(), newEI0, newEI1, BO); } + } else if (CmpInst *CI = dyn_cast(I)) { + if (CI->hasOneUse() && + cheapToScalarize(CI, isa(EI.getOperand(1)))) { + Value *newEI0 = + Builder.CreateExtractElement(CI->getOperand(0), EI.getOperand(1), + EI.getName()+".lhs"); + Value *newEI1 = + Builder.CreateExtractElement(CI->getOperand(1), EI.getOperand(1), + EI.getName()+".rhs"); + return CmpInst::Create(CI->getOpcode(), CI->getPredicate(), + newEI0, newEI1, CI->getName()); + } } else if (InsertElementInst *IE = dyn_cast(I)) { // Extracting the inserted element? if (IE->getOperand(2) == EI.getOperand(1)) Index: test/Transforms/InstCombine/scalarization.ll =================================================================== --- test/Transforms/InstCombine/scalarization.ll +++ test/Transforms/InstCombine/scalarization.ll @@ -86,8 +86,8 @@ define i1 @extractelt_vector_icmp_constrhs(<2 x i32> %arg) { ; CHECK-LABEL: @extractelt_vector_icmp_constrhs( -; CHECK-NEXT: [[CMP:%.*]] = icmp eq <2 x i32> [[ARG:%.*]], zeroinitializer -; CHECK-NEXT: [[EXT:%.*]] = extractelement <2 x i1> [[CMP]], i32 0 +; CHECK-NEXT: [[EXT_LHS:%.*]] = extractelement <2 x i32> [[ARG:%.*]], i32 0 +; CHECK-NEXT: [[EXT:%.*]] = icmp eq i32 [[EXT_LHS]], 0 ; CHECK-NEXT: ret i1 [[EXT]] ; %cmp = icmp eq <2 x i32> %arg, zeroinitializer @@ -97,8 +97,8 @@ define i1 @extractelt_vector_fcmp_constrhs(<2 x float> %arg) { ; CHECK-LABEL: @extractelt_vector_fcmp_constrhs( -; CHECK-NEXT: [[CMP:%.*]] = fcmp oeq <2 x float> [[ARG:%.*]], zeroinitializer -; CHECK-NEXT: [[EXT:%.*]] = extractelement <2 x i1> [[CMP]], i32 0 +; CHECK-NEXT: [[EXT_LHS:%.*]] = extractelement <2 x float> [[ARG:%.*]], i32 0 +; CHECK-NEXT: [[EXT:%.*]] = fcmp oeq float [[EXT_LHS]], 0.000000e+00 ; CHECK-NEXT: ret i1 [[EXT]] ; %cmp = fcmp oeq <2 x float> %arg, zeroinitializer @@ -108,8 +108,8 @@ define i1 @extractelt_vector_icmp_constrhs_dynidx(<2 x i32> %arg, i32 %idx) { ; CHECK-LABEL: @extractelt_vector_icmp_constrhs_dynidx( -; CHECK-NEXT: [[CMP:%.*]] = icmp eq <2 x i32> [[ARG:%.*]], zeroinitializer -; CHECK-NEXT: [[EXT:%.*]] = extractelement <2 x i1> [[CMP]], i32 [[IDX:%.*]] +; CHECK-NEXT: [[EXT_LHS:%.*]] = extractelement <2 x i32> [[ARG:%.*]], i32 [[IDX:%.*]] +; CHECK-NEXT: [[EXT:%.*]] = icmp eq i32 [[EXT_LHS]], 0 ; CHECK-NEXT: ret i1 [[EXT]] ; %cmp = icmp eq <2 x i32> %arg, zeroinitializer @@ -119,8 +119,8 @@ define i1 @extractelt_vector_fcmp_constrhs_dynidx(<2 x float> %arg, i32 %idx) { ; CHECK-LABEL: @extractelt_vector_fcmp_constrhs_dynidx( -; CHECK-NEXT: [[CMP:%.*]] = fcmp oeq <2 x float> [[ARG:%.*]], zeroinitializer -; CHECK-NEXT: [[EXT:%.*]] = extractelement <2 x i1> [[CMP]], i32 [[IDX:%.*]] +; CHECK-NEXT: [[EXT_LHS:%.*]] = extractelement <2 x float> [[ARG:%.*]], i32 [[IDX:%.*]] +; CHECK-NEXT: [[EXT:%.*]] = fcmp oeq float [[EXT_LHS]], 0.000000e+00 ; CHECK-NEXT: ret i1 [[EXT]] ; %cmp = fcmp oeq <2 x float> %arg, zeroinitializer