brintos

brintos / llvm-project-archived public Read only

0
0
Text · 17.5 KiB · 7028873 Raw
396 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 22; RUN: opt -passes='loop-mssa(licm)' -S < %s | FileCheck %s --check-prefixes=CHECK,NOT_CONSTRAINED3; RUN: opt -passes='loop-mssa(licm)' -licm-max-num-int-reassociations=1 -S < %s | FileCheck %s --check-prefixes=CHECK,CONSTRAINED4 5;6; A simple loop:7;8;  int j;9;10;  for (j = 0; j <= i; j++)11;    cells[j] = d1 * cells[j + 1] * delta;12;13; ...should be transformed by the LICM pass into this:14;15;  int j;16;  const uint64_t d1d = d1 * delta;17;18;  for (j = 0; j <= i; j++)19;    cells[j] = d1d * cells[j + 1];20;21 22define void @innermost_loop_1d_shouldhoist(i32 %i, i64 %d1, i64 %delta, ptr %cells) {23; CHECK-LABEL: define void @innermost_loop_1d_shouldhoist24; CHECK-SAME: (i32 [[I:%.*]], i64 [[D1:%.*]], i64 [[DELTA:%.*]], ptr [[CELLS:%.*]]) {25; CHECK-NEXT:  entry:26; CHECK-NEXT:    [[MUL_1:%.*]] = mul nuw nsw i64 [[DELTA]], [[D1]]27; CHECK-NEXT:    br label [[FOR_COND:%.*]]28; CHECK:       for.cond:29; CHECK-NEXT:    [[J:%.*]] = phi i32 [ 0, [[ENTRY:%.*]] ], [ [[ADD_J_1:%.*]], [[FOR_BODY:%.*]] ]30; CHECK-NEXT:    [[CMP_NOT:%.*]] = icmp sgt i32 [[J]], [[I]]31; CHECK-NEXT:    br i1 [[CMP_NOT]], label [[FOR_END:%.*]], label [[FOR_BODY]]32; CHECK:       for.body:33; CHECK-NEXT:    [[ADD_J_1]] = add nuw nsw i32 [[J]], 134; CHECK-NEXT:    [[IDXPROM_J_1:%.*]] = zext i32 [[ADD_J_1]] to i6435; CHECK-NEXT:    [[ARRAYIDX_J_1:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J_1]]36; CHECK-NEXT:    [[CELL_1:%.*]] = load i64, ptr [[ARRAYIDX_J_1]], align 837; CHECK-NEXT:    [[MUL_2:%.*]] = mul i64 [[MUL_1]], [[CELL_1]]38; CHECK-NEXT:    [[IDXPROM_J:%.*]] = zext i32 [[J]] to i6439; CHECK-NEXT:    [[ARRAYIDX_J:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J]]40; CHECK-NEXT:    store i64 [[MUL_2]], ptr [[ARRAYIDX_J]], align 841; CHECK-NEXT:    br label [[FOR_COND]]42; CHECK:       for.end:43; CHECK-NEXT:    ret void44;45entry:46  br label %for.cond47 48for.cond:49  %j = phi i32 [ 0, %entry ], [ %add.j.1, %for.body ]50  %cmp.not = icmp sgt i32 %j, %i51  br i1 %cmp.not, label %for.end, label %for.body52 53for.body:54  %add.j.1 = add nuw nsw i32 %j, 155  %idxprom.j.1 = zext i32 %add.j.1 to i6456  %arrayidx.j.1 = getelementptr inbounds i64, ptr %cells, i64 %idxprom.j.157  %cell.1 = load i64, ptr %arrayidx.j.1, align 858  %mul.1 = mul nsw nuw i64 %delta, %d159  %mul.2 = mul i64 %mul.1, %cell.160  %idxprom.j = zext i32 %j to i6461  %arrayidx.j = getelementptr inbounds i64, ptr %cells, i64 %idxprom.j62  store i64 %mul.2, ptr %arrayidx.j, align 863  br label %for.cond64 65for.end:66  ret void67}68 69;70; The following loop will be modified by the 'Reassociate expressions' pass,71;72;  int j;73;  const uint64_t d1d = d1 * delta;74;  const uint64_t d2d = d2 * delta;75;76;  for (j = 0; j <= i; j++)77;    cells[j] = d1d * cells[j + 1] + d2d * cells[j];78;79; ...into this:80;81;  int j;82;83;  for (j = 0; j <= i; j++)84;    cells[j] = (d1 * cells[j + 1] + d2 * cells[j]) * delta;85;86; We expect the LICM pass to undo this transformation.87;88 89define void @innermost_loop_2d(i32 %i, i64 %d1, i64 %d2, i64 %delta, ptr %cells) {90; NOT_CONSTRAINED-LABEL: define void @innermost_loop_2d91; NOT_CONSTRAINED-SAME: (i32 [[I:%.*]], i64 [[D1:%.*]], i64 [[D2:%.*]], i64 [[DELTA:%.*]], ptr [[CELLS:%.*]]) {92; NOT_CONSTRAINED-NEXT:  entry:93; NOT_CONSTRAINED-NEXT:    [[FACTOR_OP_MUL:%.*]] = mul i64 [[D1]], [[DELTA]]94; NOT_CONSTRAINED-NEXT:    [[FACTOR_OP_MUL1:%.*]] = mul i64 [[D2]], [[DELTA]]95; NOT_CONSTRAINED-NEXT:    br label [[FOR_COND:%.*]]96; NOT_CONSTRAINED:       for.cond:97; NOT_CONSTRAINED-NEXT:    [[J:%.*]] = phi i32 [ 0, [[ENTRY:%.*]] ], [ [[ADD_J_1:%.*]], [[FOR_BODY:%.*]] ]98; NOT_CONSTRAINED-NEXT:    [[CMP_NOT:%.*]] = icmp sgt i32 [[J]], [[I]]99; NOT_CONSTRAINED-NEXT:    br i1 [[CMP_NOT]], label [[FOR_END:%.*]], label [[FOR_BODY]]100; NOT_CONSTRAINED:       for.body:101; NOT_CONSTRAINED-NEXT:    [[ADD_J_1]] = add nuw nsw i32 [[J]], 1102; NOT_CONSTRAINED-NEXT:    [[IDXPROM_J_1:%.*]] = zext i32 [[ADD_J_1]] to i64103; NOT_CONSTRAINED-NEXT:    [[ARRAYIDX_J_1:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J_1]]104; NOT_CONSTRAINED-NEXT:    [[CELL_1:%.*]] = load i64, ptr [[ARRAYIDX_J_1]], align 8105; NOT_CONSTRAINED-NEXT:    [[MUL_1:%.*]] = mul i64 [[CELL_1]], [[FACTOR_OP_MUL]]106; NOT_CONSTRAINED-NEXT:    [[IDXPROM_J:%.*]] = zext i32 [[J]] to i64107; NOT_CONSTRAINED-NEXT:    [[ARRAYIDX_J:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J]]108; NOT_CONSTRAINED-NEXT:    [[CELL_2:%.*]] = load i64, ptr [[ARRAYIDX_J]], align 8109; NOT_CONSTRAINED-NEXT:    [[MUL_2:%.*]] = mul i64 [[CELL_2]], [[FACTOR_OP_MUL1]]110; NOT_CONSTRAINED-NEXT:    [[REASS_ADD:%.*]] = add i64 [[MUL_2]], [[MUL_1]]111; NOT_CONSTRAINED-NEXT:    store i64 [[REASS_ADD]], ptr [[ARRAYIDX_J]], align 8112; NOT_CONSTRAINED-NEXT:    br label [[FOR_COND]]113; NOT_CONSTRAINED:       for.end:114; NOT_CONSTRAINED-NEXT:    ret void115;116; CONSTRAINED-LABEL: define void @innermost_loop_2d117; CONSTRAINED-SAME: (i32 [[I:%.*]], i64 [[D1:%.*]], i64 [[D2:%.*]], i64 [[DELTA:%.*]], ptr [[CELLS:%.*]]) {118; CONSTRAINED-NEXT:  entry:119; CONSTRAINED-NEXT:    br label [[FOR_COND:%.*]]120; CONSTRAINED:       for.cond:121; CONSTRAINED-NEXT:    [[J:%.*]] = phi i32 [ 0, [[ENTRY:%.*]] ], [ [[ADD_J_1:%.*]], [[FOR_BODY:%.*]] ]122; CONSTRAINED-NEXT:    [[CMP_NOT:%.*]] = icmp sgt i32 [[J]], [[I]]123; CONSTRAINED-NEXT:    br i1 [[CMP_NOT]], label [[FOR_END:%.*]], label [[FOR_BODY]]124; CONSTRAINED:       for.body:125; CONSTRAINED-NEXT:    [[ADD_J_1]] = add nuw nsw i32 [[J]], 1126; CONSTRAINED-NEXT:    [[IDXPROM_J_1:%.*]] = zext i32 [[ADD_J_1]] to i64127; CONSTRAINED-NEXT:    [[ARRAYIDX_J_1:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J_1]]128; CONSTRAINED-NEXT:    [[CELL_1:%.*]] = load i64, ptr [[ARRAYIDX_J_1]], align 8129; CONSTRAINED-NEXT:    [[MUL_1:%.*]] = mul i64 [[CELL_1]], [[D1]]130; CONSTRAINED-NEXT:    [[IDXPROM_J:%.*]] = zext i32 [[J]] to i64131; CONSTRAINED-NEXT:    [[ARRAYIDX_J:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J]]132; CONSTRAINED-NEXT:    [[CELL_2:%.*]] = load i64, ptr [[ARRAYIDX_J]], align 8133; CONSTRAINED-NEXT:    [[MUL_2:%.*]] = mul nuw nsw i64 [[CELL_2]], [[D2]]134; CONSTRAINED-NEXT:    [[REASS_ADD:%.*]] = add nuw nsw i64 [[MUL_2]], [[MUL_1]]135; CONSTRAINED-NEXT:    [[REASS_MUL:%.*]] = mul i64 [[REASS_ADD]], [[DELTA]]136; CONSTRAINED-NEXT:    store i64 [[REASS_MUL]], ptr [[ARRAYIDX_J]], align 8137; CONSTRAINED-NEXT:    br label [[FOR_COND]]138; CONSTRAINED:       for.end:139; CONSTRAINED-NEXT:    ret void140;141entry:142  br label %for.cond143 144for.cond:145  %j = phi i32 [ 0, %entry ], [ %add.j.1, %for.body ]146  %cmp.not = icmp sgt i32 %j, %i147  br i1 %cmp.not, label %for.end, label %for.body148 149for.body:150  %add.j.1 = add nuw nsw i32 %j, 1151  %idxprom.j.1 = zext i32 %add.j.1 to i64152  %arrayidx.j.1 = getelementptr inbounds i64, ptr %cells, i64 %idxprom.j.1153  %cell.1 = load i64, ptr %arrayidx.j.1, align 8154  %mul.1 = mul i64 %cell.1, %d1155  %idxprom.j = zext i32 %j to i64156  %arrayidx.j = getelementptr inbounds i64, ptr %cells, i64 %idxprom.j157  %cell.2 = load i64, ptr %arrayidx.j, align 8158  %mul.2 = mul nsw nuw i64 %cell.2, %d2159  %reass.add = add nsw nuw i64 %mul.2, %mul.1160  %reass.mul = mul i64 %reass.add, %delta161  store i64 %reass.mul, ptr %arrayidx.j, align 8162  br label %for.cond163 164for.end:165  ret void166}167 168;169; The following loop will be modified by the 'Reassociate expressions' pass,170;171;  int j;172;  const uint64_t d1d = d1 * delta;173;  const uint64_t d2d = d2 * delta;174;  const uint64_t d3d = d3 * delta;175;176;  for (j = 0; j <= i; j++)177;    cells[j] = d1d * cells[j + 1] + d2d * cells[j] + d3d * cells[j + 2];178;179; ...into this:180;181;  int j;182;183;  for (j = 0; j <= i; j++)184;    cells[j] = (d1 * cells[j + 1] + d2 * cells[j] + d3 * cells[j + 2]) * delta;185;186; We expect the LICM pass to undo this transformation.187;188 189 190define void @innermost_loop_3d(i32 %i, i64 %d1, i64 %d2, i64 %d3, i64 %delta, ptr %cells) {191; NOT_CONSTRAINED-LABEL: define void @innermost_loop_3d192; NOT_CONSTRAINED-SAME: (i32 [[I:%.*]], i64 [[D1:%.*]], i64 [[D2:%.*]], i64 [[D3:%.*]], i64 [[DELTA:%.*]], ptr [[CELLS:%.*]]) {193; NOT_CONSTRAINED-NEXT:  entry:194; NOT_CONSTRAINED-NEXT:    [[FACTOR_OP_MUL:%.*]] = mul i64 [[D3]], [[DELTA]]195; NOT_CONSTRAINED-NEXT:    [[FACTOR_OP_MUL1:%.*]] = mul i64 [[D1]], [[DELTA]]196; NOT_CONSTRAINED-NEXT:    [[FACTOR_OP_MUL2:%.*]] = mul i64 [[D2]], [[DELTA]]197; NOT_CONSTRAINED-NEXT:    br label [[FOR_COND:%.*]]198; NOT_CONSTRAINED:       for.cond:199; NOT_CONSTRAINED-NEXT:    [[J:%.*]] = phi i32 [ 0, [[ENTRY:%.*]] ], [ [[ADD_J_1:%.*]], [[FOR_BODY:%.*]] ]200; NOT_CONSTRAINED-NEXT:    [[CMP_NOT:%.*]] = icmp sgt i32 [[J]], [[I]]201; NOT_CONSTRAINED-NEXT:    br i1 [[CMP_NOT]], label [[FOR_END:%.*]], label [[FOR_BODY]]202; NOT_CONSTRAINED:       for.body:203; NOT_CONSTRAINED-NEXT:    [[ADD_J_1]] = add nuw nsw i32 [[J]], 1204; NOT_CONSTRAINED-NEXT:    [[IDXPROM_J_1:%.*]] = zext i32 [[ADD_J_1]] to i64205; NOT_CONSTRAINED-NEXT:    [[ARRAYIDX_J_1:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J_1]]206; NOT_CONSTRAINED-NEXT:    [[CELL_1:%.*]] = load i64, ptr [[ARRAYIDX_J_1]], align 8207; NOT_CONSTRAINED-NEXT:    [[MUL_1:%.*]] = mul i64 [[CELL_1]], [[FACTOR_OP_MUL1]]208; NOT_CONSTRAINED-NEXT:    [[IDXPROM_J:%.*]] = zext i32 [[J]] to i64209; NOT_CONSTRAINED-NEXT:    [[ARRAYIDX_J:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J]]210; NOT_CONSTRAINED-NEXT:    [[CELL_2:%.*]] = load i64, ptr [[ARRAYIDX_J]], align 8211; NOT_CONSTRAINED-NEXT:    [[MUL_2:%.*]] = mul i64 [[CELL_2]], [[FACTOR_OP_MUL2]]212; NOT_CONSTRAINED-NEXT:    [[ADD_J_2:%.*]] = add nuw nsw i32 [[J]], 2213; NOT_CONSTRAINED-NEXT:    [[IDXPROM_J_2:%.*]] = zext i32 [[ADD_J_2]] to i64214; NOT_CONSTRAINED-NEXT:    [[ARRAYIDX_J_2:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J_2]]215; NOT_CONSTRAINED-NEXT:    [[CELL_3:%.*]] = load i64, ptr [[ARRAYIDX_J_2]], align 8216; NOT_CONSTRAINED-NEXT:    [[MUL_3:%.*]] = mul i64 [[CELL_3]], [[FACTOR_OP_MUL]]217; NOT_CONSTRAINED-NEXT:    [[REASS_ADD:%.*]] = add i64 [[MUL_2]], [[MUL_1]]218; NOT_CONSTRAINED-NEXT:    [[REASS_ADD1:%.*]] = add i64 [[REASS_ADD]], [[MUL_3]]219; NOT_CONSTRAINED-NEXT:    store i64 [[REASS_ADD1]], ptr [[ARRAYIDX_J_2]], align 8220; NOT_CONSTRAINED-NEXT:    br label [[FOR_COND]]221; NOT_CONSTRAINED:       for.end:222; NOT_CONSTRAINED-NEXT:    ret void223;224; CONSTRAINED-LABEL: define void @innermost_loop_3d225; CONSTRAINED-SAME: (i32 [[I:%.*]], i64 [[D1:%.*]], i64 [[D2:%.*]], i64 [[D3:%.*]], i64 [[DELTA:%.*]], ptr [[CELLS:%.*]]) {226; CONSTRAINED-NEXT:  entry:227; CONSTRAINED-NEXT:    br label [[FOR_COND:%.*]]228; CONSTRAINED:       for.cond:229; CONSTRAINED-NEXT:    [[J:%.*]] = phi i32 [ 0, [[ENTRY:%.*]] ], [ [[ADD_J_1:%.*]], [[FOR_BODY:%.*]] ]230; CONSTRAINED-NEXT:    [[CMP_NOT:%.*]] = icmp sgt i32 [[J]], [[I]]231; CONSTRAINED-NEXT:    br i1 [[CMP_NOT]], label [[FOR_END:%.*]], label [[FOR_BODY]]232; CONSTRAINED:       for.body:233; CONSTRAINED-NEXT:    [[ADD_J_1]] = add nuw nsw i32 [[J]], 1234; CONSTRAINED-NEXT:    [[IDXPROM_J_1:%.*]] = zext i32 [[ADD_J_1]] to i64235; CONSTRAINED-NEXT:    [[ARRAYIDX_J_1:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J_1]]236; CONSTRAINED-NEXT:    [[CELL_1:%.*]] = load i64, ptr [[ARRAYIDX_J_1]], align 8237; CONSTRAINED-NEXT:    [[MUL_1:%.*]] = mul i64 [[CELL_1]], [[D1]]238; CONSTRAINED-NEXT:    [[IDXPROM_J:%.*]] = zext i32 [[J]] to i64239; CONSTRAINED-NEXT:    [[ARRAYIDX_J:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J]]240; CONSTRAINED-NEXT:    [[CELL_2:%.*]] = load i64, ptr [[ARRAYIDX_J]], align 8241; CONSTRAINED-NEXT:    [[MUL_2:%.*]] = mul i64 [[CELL_2]], [[D2]]242; CONSTRAINED-NEXT:    [[ADD_J_2:%.*]] = add nuw nsw i32 [[J]], 2243; CONSTRAINED-NEXT:    [[IDXPROM_J_2:%.*]] = zext i32 [[ADD_J_2]] to i64244; CONSTRAINED-NEXT:    [[ARRAYIDX_J_2:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J_2]]245; CONSTRAINED-NEXT:    [[CELL_3:%.*]] = load i64, ptr [[ARRAYIDX_J_2]], align 8246; CONSTRAINED-NEXT:    [[MUL_3:%.*]] = mul nuw nsw i64 [[CELL_3]], [[D3]]247; CONSTRAINED-NEXT:    [[REASS_ADD:%.*]] = add nuw nsw i64 [[MUL_2]], [[MUL_1]]248; CONSTRAINED-NEXT:    [[REASS_ADD1:%.*]] = add nuw nsw i64 [[REASS_ADD]], [[MUL_3]]249; CONSTRAINED-NEXT:    [[REASS_MUL:%.*]] = mul nuw nsw i64 [[REASS_ADD1]], [[DELTA]]250; CONSTRAINED-NEXT:    store i64 [[REASS_MUL]], ptr [[ARRAYIDX_J_2]], align 8251; CONSTRAINED-NEXT:    br label [[FOR_COND]]252; CONSTRAINED:       for.end:253; CONSTRAINED-NEXT:    ret void254;255entry:256  br label %for.cond257 258for.cond:259  %j = phi i32 [ 0, %entry ], [ %add.j.1, %for.body ]260  %cmp.not = icmp sgt i32 %j, %i261  br i1 %cmp.not, label %for.end, label %for.body262 263for.body:264  %add.j.1 = add nuw nsw i32 %j, 1265  %idxprom.j.1 = zext i32 %add.j.1 to i64266  %arrayidx.j.1 = getelementptr inbounds i64, ptr %cells, i64 %idxprom.j.1267  %cell.1 = load i64, ptr %arrayidx.j.1, align 8268  %mul.1 = mul i64 %cell.1, %d1269  %idxprom.j = zext i32 %j to i64270  %arrayidx.j = getelementptr inbounds i64, ptr %cells, i64 %idxprom.j271  %cell.2 = load i64, ptr %arrayidx.j, align 8272  %mul.2 = mul i64 %cell.2, %d2273  %add.j.2 = add nuw nsw i32 %j, 2274  %idxprom.j.2 = zext i32 %add.j.2 to i64275  %arrayidx.j.2 = getelementptr inbounds i64, ptr %cells, i64 %idxprom.j.2276  %cell.3 = load i64, ptr %arrayidx.j.2, align 8277  %mul.3 = mul nsw nuw i64 %cell.3, %d3278  %reass.add = add nsw nuw i64 %mul.2, %mul.1279  %reass.add1 = add nsw nuw i64 %reass.add, %mul.3280  %reass.mul = mul nsw nuw i64 %reass.add1, %delta281  store i64 %reass.mul, ptr %arrayidx.j.2, align 8282  br label %for.cond283 284for.end:285  ret void286}287 288;289; The following loop will not be modified by the LICM pass:290;291;  int j;292;293;  for (j = 0; j <= i; j++)294;    cells[j] = (d1 * cells[j + 1] + d2 * cells[j] +295;                cells[j] * cells[j + 1]) * delta;296;297; This case differs as one of the multiplications involves no invariants.298;299 300define void @innermost_loop_3d_reassociated_different(i32 %i, i64 %d1, i64 %d2, i64 %delta, ptr %cells) {301; CHECK-LABEL: define void @innermost_loop_3d_reassociated_different302; CHECK-SAME: (i32 [[I:%.*]], i64 [[D1:%.*]], i64 [[D2:%.*]], i64 [[DELTA:%.*]], ptr [[CELLS:%.*]]) {303; CHECK-NEXT:  entry:304; CHECK-NEXT:    br label [[FOR_COND:%.*]]305; CHECK:       for.cond:306; CHECK-NEXT:    [[J:%.*]] = phi i32 [ 0, [[ENTRY:%.*]] ], [ [[ADD_J_1:%.*]], [[FOR_BODY:%.*]] ]307; CHECK-NEXT:    [[CMP_NOT:%.*]] = icmp sgt i32 [[J]], [[I]]308; CHECK-NEXT:    br i1 [[CMP_NOT]], label [[FOR_END:%.*]], label [[FOR_BODY]]309; CHECK:       for.body:310; CHECK-NEXT:    [[ADD_J_1]] = add nuw nsw i32 [[J]], 1311; CHECK-NEXT:    [[IDXPROM_J_1:%.*]] = zext i32 [[ADD_J_1]] to i64312; CHECK-NEXT:    [[ARRAYIDX_J_1:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J_1]]313; CHECK-NEXT:    [[CELL_1:%.*]] = load i64, ptr [[ARRAYIDX_J_1]], align 8314; CHECK-NEXT:    [[IDXPROM_J_2:%.*]] = zext i32 [[ADD_J_1]] to i64315; CHECK-NEXT:    [[ARRAYIDX_J_2:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J_2]]316; CHECK-NEXT:    [[CELL_2:%.*]] = load i64, ptr [[ARRAYIDX_J_2]], align 8317; CHECK-NEXT:    [[CELL_3:%.*]] = load i64, ptr [[ARRAYIDX_J_2]], align 8318; CHECK-NEXT:    [[IDXPROM_J:%.*]] = zext i32 [[J]] to i64319; CHECK-NEXT:    [[ARRAYIDX_J:%.*]] = getelementptr inbounds i64, ptr [[CELLS]], i64 [[IDXPROM_J]]320; CHECK-NEXT:    [[CELL_4:%.*]] = load i64, ptr [[ARRAYIDX_J]], align 8321; CHECK-NEXT:    [[MUL_1:%.*]] = mul i64 [[CELL_1]], [[D1]]322; CHECK-NEXT:    [[MUL_2:%.*]] = mul i64 [[CELL_4]], [[D2]]323; CHECK-NEXT:    [[EXTRA_MUL:%.*]] = mul i64 [[CELL_3]], [[CELL_2]]324; CHECK-NEXT:    [[REASS_ADD:%.*]] = add i64 [[EXTRA_MUL]], [[MUL_1]]325; CHECK-NEXT:    [[EXTRA_ADD:%.*]] = add i64 [[REASS_ADD]], [[MUL_2]]326; CHECK-NEXT:    [[REASS_MUL:%.*]] = mul i64 [[EXTRA_ADD]], [[DELTA]]327; CHECK-NEXT:    store i64 [[REASS_MUL]], ptr [[ARRAYIDX_J]], align 8328; CHECK-NEXT:    br label [[FOR_COND]]329; CHECK:       for.end:330; CHECK-NEXT:    ret void331;332entry:333  br label %for.cond334 335for.cond:336  %j = phi i32 [ 0, %entry ], [ %add.j.1, %for.body ]337  %cmp.not = icmp sgt i32 %j, %i338  br i1 %cmp.not, label %for.end, label %for.body339 340for.body:341  %add.j.1 = add nuw nsw i32 %j, 1342  %idxprom.j.1 = zext i32 %add.j.1 to i64343  %arrayidx.j.1 = getelementptr inbounds i64, ptr %cells, i64 %idxprom.j.1344  %cell.1 = load i64, ptr %arrayidx.j.1, align 8345  %idxprom.j.2 = zext i32 %add.j.1 to i64346  %arrayidx.j.2 = getelementptr inbounds i64, ptr %cells, i64 %idxprom.j.2347  %cell.2 = load i64, ptr %arrayidx.j.2, align 8348  %idxprom.j.3 = zext i32 %add.j.1 to i64349  %cell.3 = load i64, ptr %arrayidx.j.2, align 8350  %idxprom.j = zext i32 %j to i64351  %arrayidx.j = getelementptr inbounds i64, ptr %cells, i64 %idxprom.j352  %cell.4 = load i64, ptr %arrayidx.j, align 8353  %mul.1 = mul i64 %cell.1, %d1354  %mul.2 = mul i64 %cell.4, %d2355  %extra.mul = mul i64 %cell.3, %cell.2356  %reass.add = add i64 %extra.mul, %mul.1357  %extra.add = add i64 %reass.add, %mul.2358  %reass.mul = mul i64 %extra.add, %delta359  store i64 %reass.mul, ptr %arrayidx.j, align 8360  br label %for.cond361 362for.end:363  ret void364}365 366; Make sure we drop poison flags on the mul in the loop.367define i32 @pr85457(i32 %x, i32 %y) {368; CHECK-LABEL: define i32 @pr85457369; CHECK-SAME: (i32 [[X:%.*]], i32 [[Y:%.*]]) {370; CHECK-NEXT:  entry:371; CHECK-NEXT:    [[FACTOR_OP_MUL:%.*]] = mul i32 [[X]], [[Y]]372; CHECK-NEXT:    br label [[LOOP:%.*]]373; CHECK:       loop:374; CHECK-NEXT:    [[IV:%.*]] = phi i32 [ 1, [[ENTRY:%.*]] ], [ [[IV_NEXT:%.*]], [[LOOP]] ]375; CHECK-NEXT:    [[IV_NEXT]] = add nuw nsw i32 [[IV]], 1376; CHECK-NEXT:    [[MUL0:%.*]] = mul i32 [[FACTOR_OP_MUL]], [[IV]]377; CHECK-NEXT:    [[CMP:%.*]] = icmp slt i32 [[MUL0]], 1378; CHECK-NEXT:    br i1 [[CMP]], label [[EXIT:%.*]], label [[LOOP]]379; CHECK:       exit:380; CHECK-NEXT:    ret i32 0381;382entry:383  br label %loop384 385loop:386  %iv = phi i32 [ 1, %entry ], [ %iv.next, %loop ]387  %iv.next = add nuw nsw i32 %iv, 1388  %mul0 = mul nuw nsw i32 %x, %iv389  %mul1 = mul nuw i32 %mul0, %y390  %cmp = icmp slt i32 %mul1, 1391  br i1 %cmp, label %exit, label %loop392 393exit:394  ret i32 0395}396