; NOTE: Assertions have been autogenerated by utils/update_test_checks.py ; RUN: opt < %s -passes=instcombine -S | FileCheck %s define void @f(i64 %val, i32 %limit, ptr %ptr) { ; CHECK-LABEL: @f( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[TMP0:%.*]] = trunc i64 [[VAL:%.*]] to i32 ; CHECK-NEXT: br label [[LOOP:%.*]] ; CHECK: loop: ; CHECK-NEXT: [[TMP1:%.*]] = phi i32 [ [[TMP0]], [[ENTRY:%.*]] ], [ [[TMP5:%.*]], [[LOOP]] ] ; CHECK-NEXT: [[END:%.*]] = icmp ult i32 [[TMP1]], [[LIMIT:%.*]] ; CHECK-NEXT: [[TMP2:%.*]] = add i32 [[TMP1]], 10 ; CHECK-NEXT: [[TMP3:%.*]] = sext i32 [[TMP1]] to i64 ; CHECK-NEXT: [[TMP4:%.*]] = getelementptr i32, ptr [[PTR:%.*]], i64 [[TMP3]] ; CHECK-NEXT: store i32 [[TMP2]], ptr [[TMP4]], align 4 ; CHECK-NEXT: [[TMP5]] = add i32 [[TMP1]], 16 ; CHECK-NEXT: br i1 [[END]], label [[LOOP]], label [[RET:%.*]] ; CHECK: ret: ; CHECK-NEXT: ret void ; entry: %tempvector = insertelement <16 x i64> undef, i64 %val, i32 0 %vector = shufflevector <16 x i64> %tempvector, <16 x i64> undef, <16 x i32> zeroinitializer %0 = add <16 x i64> %vector, %1 = trunc <16 x i64> %0 to <16 x i32> br label %loop loop: %2 = phi <16 x i32> [ %1, %entry ], [ %inc, %loop ] %elt = extractelement <16 x i32> %2, i32 0 %end = icmp ult i32 %elt, %limit %3 = add i32 10, %elt %4 = sext i32 %elt to i64 %5 = getelementptr i32, ptr %ptr, i64 %4 store i32 %3, ptr %5 %inc = add <16 x i32> %2, br i1 %end, label %loop, label %ret ret: ret void } define void @copy(i64 %val, i32 %limit, ptr %ptr) { ; CHECK-LABEL: @copy( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[TMP0:%.*]] = trunc i64 [[VAL:%.*]] to i32 ; CHECK-NEXT: br label [[LOOP:%.*]] ; CHECK: loop: ; CHECK-NEXT: [[TMP1:%.*]] = phi i32 [ [[TMP0]], [[ENTRY:%.*]] ], [ [[TMP5:%.*]], [[LOOP]] ] ; CHECK-NEXT: [[END:%.*]] = icmp ult i32 [[TMP1]], [[LIMIT:%.*]] ; CHECK-NEXT: [[TMP2:%.*]] = add i32 [[TMP1]], 10 ; CHECK-NEXT: [[TMP3:%.*]] = sext i32 [[TMP1]] to i64 ; CHECK-NEXT: [[TMP4:%.*]] = getelementptr i32, ptr [[PTR:%.*]], i64 [[TMP3]] ; CHECK-NEXT: store i32 [[TMP2]], ptr [[TMP4]], align 4 ; CHECK-NEXT: [[TMP5]] = add i32 [[TMP1]], 16 ; CHECK-NEXT: br i1 [[END]], label [[LOOP]], label [[RET:%.*]] ; CHECK: ret: ; CHECK-NEXT: ret void ; entry: %tempvector = insertelement <16 x i64> undef, i64 %val, i32 0 %vector = shufflevector <16 x i64> %tempvector, <16 x i64> undef, <16 x i32> zeroinitializer %0 = add <16 x i64> %vector, %1 = trunc <16 x i64> %0 to <16 x i32> br label %loop loop: %2 = phi <16 x i32> [ %1, %entry ], [ %inc, %loop ] %elt = extractelement <16 x i32> %2, i32 0 %eltcopy = extractelement <16 x i32> %2, i32 0 %end = icmp ult i32 %elt, %limit %3 = add i32 10, %eltcopy %4 = sext i32 %elt to i64 %5 = getelementptr i32, ptr %ptr, i64 %4 store i32 %3, ptr %5 %inc = add <16 x i32> %2, br i1 %end, label %loop, label %ret ret: ret void } define void @nocopy(i64 %val, i32 %limit, ptr %ptr) { ; CHECK-LABEL: @nocopy( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[TMP0:%.*]] = trunc i64 [[VAL:%.*]] to i32 ; CHECK-NEXT: [[TMP1:%.*]] = insertelement <16 x i32> undef, i32 [[TMP0]], i64 0 ; CHECK-NEXT: [[TMP2:%.*]] = shufflevector <16 x i32> [[TMP1]], <16 x i32> poison, <16 x i32> zeroinitializer ; CHECK-NEXT: [[TMP3:%.*]] = add <16 x i32> [[TMP2]], ; CHECK-NEXT: br label [[LOOP:%.*]] ; CHECK: loop: ; CHECK-NEXT: [[TMP4:%.*]] = phi <16 x i32> [ [[TMP3]], [[ENTRY:%.*]] ], [ [[INC:%.*]], [[LOOP]] ] ; CHECK-NEXT: [[ELT:%.*]] = extractelement <16 x i32> [[TMP4]], i64 0 ; CHECK-NEXT: [[ELTCOPY:%.*]] = extractelement <16 x i32> [[TMP4]], i64 1 ; CHECK-NEXT: [[END:%.*]] = icmp ult i32 [[ELT]], [[LIMIT:%.*]] ; CHECK-NEXT: [[TMP5:%.*]] = add i32 [[ELTCOPY]], 10 ; CHECK-NEXT: [[TMP6:%.*]] = sext i32 [[ELT]] to i64 ; CHECK-NEXT: [[TMP7:%.*]] = getelementptr i32, ptr [[PTR:%.*]], i64 [[TMP6]] ; CHECK-NEXT: store i32 [[TMP5]], ptr [[TMP7]], align 4 ; CHECK-NEXT: [[INC]] = add <16 x i32> [[TMP4]], ; CHECK-NEXT: br i1 [[END]], label [[LOOP]], label [[RET:%.*]] ; CHECK: ret: ; CHECK-NEXT: ret void ; entry: %tempvector = insertelement <16 x i64> undef, i64 %val, i32 0 %vector = shufflevector <16 x i64> %tempvector, <16 x i64> undef, <16 x i32> zeroinitializer %0 = add <16 x i64> %vector, %1 = trunc <16 x i64> %0 to <16 x i32> br label %loop loop: %2 = phi <16 x i32> [ %1, %entry ], [ %inc, %loop ] %elt = extractelement <16 x i32> %2, i32 0 %eltcopy = extractelement <16 x i32> %2, i32 1 %end = icmp ult i32 %elt, %limit %3 = add i32 10, %eltcopy %4 = sext i32 %elt to i64 %5 = getelementptr i32, ptr %ptr, i64 %4 store i32 %3, ptr %5 %inc = add <16 x i32> %2, br i1 %end, label %loop, label %ret ret: ret void } define i1 @g(<3 x i32> %input_2, i1 %c1) { ; CHECK-LABEL: @g( ; CHECK-NEXT: entry: ; CHECK-NEXT: [[TMP0:%.*]] = extractelement <3 x i32> [[INPUT_2:%.*]], i64 0 ; CHECK-NEXT: br label [[FOR_COND:%.*]] ; CHECK: for.cond: ; CHECK-NEXT: [[TMP1:%.*]] = phi i32 [ [[TMP0]], [[ENTRY:%.*]] ], [ [[TMP4:%.*]], [[FOR_BODY:%.*]] ] ; CHECK-NEXT: [[TMP2:%.*]] = phi i32 [ poison, [[ENTRY]] ], [ [[TMP3:%.*]], [[FOR_BODY]] ] ; CHECK-NEXT: br i1 [[C1:%.*]], label [[FOR_END:%.*]], label [[FOR_BODY]] ; CHECK: for.body: ; CHECK-NEXT: [[TMP3]] = add i32 [[TMP2]], -1 ; CHECK-NEXT: [[SUB44_ELT:%.*]] = sub i32 0, [[TMP2]] ; CHECK-NEXT: [[TMP4]] = sdiv i32 [[TMP1]], [[SUB44_ELT]] ; CHECK-NEXT: br label [[FOR_COND]] ; CHECK: for.end: ; CHECK-NEXT: [[TOBOOL313:%.*]] = icmp eq i32 [[TMP1]], 0 ; CHECK-NEXT: ret i1 [[TOBOOL313]] ; entry: br label %for.cond for.cond: %input_2.addr.0 = phi <3 x i32> [ %input_2, %entry ], [ %div45, %for.body ] %input_1.addr.1 = phi <3 x i32> [ poison, %entry ], [ %dec43, %for.body ] br i1 %c1, label %for.end, label %for.body for.body: %dec43 = add <3 x i32> %input_1.addr.1, %sub44 = sub <3 x i32> , %dec43 %div45 = sdiv <3 x i32> %input_2.addr.0, %sub44 br label %for.cond for.end: %0 = extractelement <3 x i32> %input_2.addr.0, i32 0 %.89 = select i1 false, i32 0, i32 %0 %tobool313 = icmp eq i32 %.89, 0 ret i1 %tobool313 }