1132 lines · plain
1; RUN: llc --mtriple=thumbv7em -mattr=+fp-armv8 -O3 %s -o - | \2; RUN: FileCheck %s --check-prefix=CHECK --check-prefix=CHECK-DEFAULT --check-prefix=CHECK-T23 4; RUN: llc --mtriple=thumbv7em -mattr=+fp-armv8 -O3 -lsr-preferred-addressing-mode=none %s -o - | \5; RUN: FileCheck %s --check-prefix=CHECK --check-prefix=DISABLED6 7; RUN: llc -mtriple=thumbv8m.main -mattr=+fp-armv8,+dsp -O3 %s -o - | \8; RUN: FileCheck %s --check-prefix=CHECK --check-prefix=CHECK-DEFAULT --check-prefix=CHECK-T29 10; RUN: llc -mtriple=thumbv8m.main -mattr=+fp-armv8,+dsp -lsr-preferred-addressing-mode=postindexed %s -o - | \11; RUN: FileCheck %s --check-prefix=CHECK --check-prefix=DISABLED12 13; RUN: llc -mtriple=thumbv8m.main -mattr=+fp-armv8,+dsp -lsr-preferred-addressing-mode=preindexed %s -o - | \14; RUN: FileCheck %s --check-prefixes=CHECK,CHECK-T215 16; RUN: llc -mtriple=thumbv8m.base %s -o - | FileCheck %s --check-prefix=CHECK --check-prefix=DISABLED17; RUN: llc -mtriple=thumbv8 %s -o - | FileCheck %s --check-prefix=CHECK --check-prefix=DISABLED18 19; RUN: llc -mtriple=thumbv8m.main -mattr=+fp-armv8,+dsp -O3 -lsr-complexity-limit=2147483647 %s -o - | \20; RUN: FileCheck %s --check-prefix=CHECK --check-prefix=CHECK-COMPLEX --check-prefix=CHECK-T221 22; Tests to check that post increment addressing modes are used instead of23; updating base pointers with add instructions.24 25; TODO: I think we should be able to use post inc addressing with VLDM26; instructions.27; CHECK-LABEL: test_fma28; CHECK: @ %loop29 30; CHECK-DEFAULT: vldr s{{.*}}, #8]31; CHECK-DEFAULT: vldr s{{.*}}, #8]32; CHECK-DEFAULT: vldr s{{.*}}, #12]33; CHECK-DEFAULT: vldr s{{.*}}, #12]34 35; CHECK-COMPLEX: vldr s{{.*}}, #8]36; CHECK-COMPLEX: vldr s{{.*}}, #8]37; CHECK-COMPLEX: vldr s{{.*}}, #12]38; CHECK-COMPLEX: vldr s{{.*}}, #12]39 40define float @test_fma(ptr %a, ptr %b, i32 %N) {41entry:42 br label %loop43 44loop:45 %i = phi i32 [ 0, %entry ], [ %i.next, %loop ]46 %idx.1 = phi i32 [ 0, %entry ], [ %idx.next, %loop ]47 %res = phi float [ 0.0, %entry ], [ %fma.2, %loop ]48 %gep.a.1 = getelementptr inbounds float, ptr %a, i32 %idx.149 %a.1 = load float, ptr %gep.a.150 %gep.b.1 = getelementptr inbounds float, ptr %b, i32 %idx.151 %b.1 = load float, ptr %gep.b.152 %fmul.1 = fmul float %a.1, %b.153 %fma.1 = fadd float %fmul.1, %res54 %idx.2 = or disjoint i32 %idx.1, 155 %gep.a.2 = getelementptr inbounds float, ptr %a, i32 %idx.256 %a.2 = load float, ptr %gep.a.257 %gep.b.2 = getelementptr inbounds float, ptr %b, i32 %idx.258 %b.2 = load float, ptr %gep.b.259 %fmul.2 = fmul float %a.2, %b.260 %fma.2 = fadd float %fmul.2, %fma.161 %i.next = add nsw nuw i32 %i, -262 %idx.next = add nsw nuw i32 %idx.1, 263 %cmp = icmp ult i32 %i.next, %N64 br i1 %cmp, label %loop, label %exit65 66exit:67 ret float %fma.268}69 70; CHECK-LABEL: convolve_16bit71; TODO: Both arrays should use indexing72; CHECK-DEFAULT: ldr{{.*}}, #8]!73; CHECK-DEFAULT-NOT: ldr{{.*}}]!74 75; CHECK-COMPLEX: ldr{{.*}}, #8]!76; CHECK-COMPLEX-NOT: ldr{{.*}}]!77 78; DISABLED-NOT: ldr{{.*}}]!79; DISABLED-NOT: str{{.*}}]!80 81define void @convolve_16bit(ptr nocapture readonly %input_image, ptr nocapture readonly %filter,82 i32 %filter_dim, i32 %out_width, i32 %out_height,83 ptr nocapture readonly %convolved) {84entry:85 %cmp92 = icmp eq i32 %out_height, 086 br i1 %cmp92, label %for.cond.cleanup, label %for.cond1.preheader.lr.ph87 88for.cond1.preheader.lr.ph: ; preds = %entry89 %xtraiter = and i32 %filter_dim, 390 %unroll_iter = sub i32 %filter_dim, %xtraiter91 br label %for.cond1.preheader92 93for.cond1.preheader: ; preds = %for.cond.cleanup3, %for.cond1.preheader.lr.ph94 %res_y.093 = phi i32 [ 0, %for.cond1.preheader.lr.ph ], [ %add28, %for.cond.cleanup3 ]95 %arrayidx22 = getelementptr inbounds ptr, ptr %convolved, i32 %res_y.09396 %tmp3 = load ptr, ptr %arrayidx22, align 497 br label %for.cond9.preheader.us.us.preheader98 99for.cond9.preheader.us.us.preheader: ; preds = %for.cond5.for.cond.cleanup7_crit_edge.us, %for.cond5.preheader.lr.ph100 %res_x.060.us = phi i32 [ %add25.us, %for.cond5.for.cond.cleanup7_crit_edge.us ], [ 0, %for.cond1.preheader ]101 br label %for.cond9.preheader.us.us102 103for.cond9.preheader.us.us: ; preds = %for.cond9.for.cond.cleanup11_crit_edge.us.us, %for.cond9.preheader.us.us.preheader104 %filter_y.056.us.us = phi i32 [ %inc20.us.us, %for.cond9.for.cond.cleanup11_crit_edge.us.us.unr-lcssa ], [ 0, %for.cond9.preheader.us.us.preheader ]105 %result_element.055.us.us = phi i32 [ %add18.us.us.3, %for.cond9.for.cond.cleanup11_crit_edge.us.us.unr-lcssa ], [ 0, %for.cond9.preheader.us.us.preheader ]106 %add.us.us = add i32 %filter_y.056.us.us, %res_y.093107 %arrayidx.us.us = getelementptr inbounds ptr, ptr %filter, i32 %filter_y.056.us.us108 %tmp5 = load ptr, ptr %arrayidx.us.us, align 4109 %arrayidx15.us.us = getelementptr inbounds ptr, ptr %input_image, i32 %add.us.us110 %tmp6 = load ptr, ptr %arrayidx15.us.us, align 4111 br label %for.body12.us.us112 113for.body12.us.us: ; preds = %for.body12.us.us, %for.cond9.preheader.us.us114 %filter_x.053.us.us = phi i32 [ %inc.us.us.3, %for.body12.us.us ], [ 0, %for.cond9.preheader.us.us ]115 %result_element.152.us.us = phi i32 [ %add18.us.us.3, %for.body12.us.us ], [ %result_element.055.us.us, %for.cond9.preheader.us.us ]116 %niter = phi i32 [ %niter.nsub.3, %for.body12.us.us ], [ %unroll_iter, %for.cond9.preheader.us.us ]117 %add13.us.us = add i32 %filter_x.053.us.us, %res_x.060.us118 %arrayidx14.us.us = getelementptr inbounds i16, ptr %tmp5, i32 %filter_x.053.us.us119 %tmp9 = load i16, ptr %arrayidx14.us.us, align 2120 %conv.us.us = sext i16 %tmp9 to i32121 %arrayidx16.us.us = getelementptr inbounds i16, ptr %tmp6, i32 %add13.us.us122 %tmp10 = load i16, ptr %arrayidx16.us.us, align 2123 %conv17.us.us = sext i16 %tmp10 to i32124 %mul.us.us = mul nsw i32 %conv17.us.us, %conv.us.us125 %add18.us.us = add nsw i32 %mul.us.us, %result_element.152.us.us126 %inc.us.us = or disjoint i32 %filter_x.053.us.us, 1127 %add13.us.us.1 = add i32 %inc.us.us, %res_x.060.us128 %arrayidx14.us.us.1 = getelementptr inbounds i16, ptr %tmp5, i32 %inc.us.us129 %tmp11 = load i16, ptr %arrayidx14.us.us.1, align 2130 %conv.us.us.1 = sext i16 %tmp11 to i32131 %arrayidx16.us.us.1 = getelementptr inbounds i16, ptr %tmp6, i32 %add13.us.us.1132 %tmp12 = load i16, ptr %arrayidx16.us.us.1, align 2133 %conv17.us.us.1 = sext i16 %tmp12 to i32134 %mul.us.us.1 = mul nsw i32 %conv17.us.us.1, %conv.us.us.1135 %add18.us.us.1 = add nsw i32 %mul.us.us.1, %add18.us.us136 %inc.us.us.1 = or disjoint i32 %filter_x.053.us.us, 2137 %add13.us.us.2 = add i32 %inc.us.us.1, %res_x.060.us138 %arrayidx14.us.us.2 = getelementptr inbounds i16, ptr %tmp5, i32 %inc.us.us.1139 %tmp13 = load i16, ptr %arrayidx14.us.us.2, align 2140 %conv.us.us.2 = sext i16 %tmp13 to i32141 %arrayidx16.us.us.2 = getelementptr inbounds i16, ptr %tmp6, i32 %add13.us.us.2142 %tmp14 = load i16, ptr %arrayidx16.us.us.2, align 2143 %conv17.us.us.2 = sext i16 %tmp14 to i32144 %mul.us.us.2 = mul nsw i32 %conv17.us.us.2, %conv.us.us.2145 %add18.us.us.2 = add nsw i32 %mul.us.us.2, %add18.us.us.1146 %inc.us.us.2 = or disjoint i32 %filter_x.053.us.us, 3147 %add13.us.us.3 = add i32 %inc.us.us.2, %res_x.060.us148 %arrayidx14.us.us.3 = getelementptr inbounds i16, ptr %tmp5, i32 %inc.us.us.2149 %tmp15 = load i16, ptr %arrayidx14.us.us.3, align 2150 %conv.us.us.3 = sext i16 %tmp15 to i32151 %arrayidx16.us.us.3 = getelementptr inbounds i16, ptr %tmp6, i32 %add13.us.us.3152 %tmp16 = load i16, ptr %arrayidx16.us.us.3, align 2153 %conv17.us.us.3 = sext i16 %tmp16 to i32154 %mul.us.us.3 = mul nsw i32 %conv17.us.us.3, %conv.us.us.3155 %add18.us.us.3 = add nsw i32 %mul.us.us.3, %add18.us.us.2156 %inc.us.us.3 = add i32 %filter_x.053.us.us, 4157 %niter.nsub.3 = add i32 %niter, -4158 %niter.ncmp.3 = icmp eq i32 %niter.nsub.3, 0159 br i1 %niter.ncmp.3, label %for.cond9.for.cond.cleanup11_crit_edge.us.us.unr-lcssa, label %for.body12.us.us160 161for.cond9.for.cond.cleanup11_crit_edge.us.us.unr-lcssa: ; preds = %for.body12.us.us, %for.cond9.preheader.us.us162 %inc20.us.us = add nuw i32 %filter_y.056.us.us, 1163 %exitcond98 = icmp eq i32 %inc20.us.us, %filter_dim164 br i1 %exitcond98, label %for.cond5.for.cond.cleanup7_crit_edge.us, label %for.cond9.preheader.us.us165 166for.cond5.for.cond.cleanup7_crit_edge.us: ; preds = %for.cond9.for.cond.cleanup11_crit_edge.us.us167 %arrayidx23.us = getelementptr inbounds i32, ptr %tmp3, i32 %res_x.060.us168 store i32 %add18.us.us.3, ptr %arrayidx23.us, align 4169 %add25.us = add nuw i32 %res_x.060.us, 1170 %exitcond99 = icmp eq i32 %add25.us, %out_width171 br i1 %exitcond99, label %for.cond.cleanup3, label %for.cond9.preheader.us.us.preheader172 173for.cond.cleanup3: ; preds = %for.cond5.for.cond.cleanup7_crit_edge.us, %for.cond5.preheader.preheader, %for.cond1.preheader174 %add28 = add nuw i32 %res_y.093, 1175 %exitcond100 = icmp eq i32 %add28, %out_height176 br i1 %exitcond100, label %for.cond.cleanup, label %for.cond1.preheader177 178for.cond.cleanup: ; preds = %for.cond.cleanup3, %entry179 ret void180}181 182; CHECK-LABEL: mul_8x8183; CHECK: @ %for.body184 185; CHECK-DEFAULT: str{{.*}}, #16]!186; CHECK-DEFAULT: ldrb{{.*}}, #4]!187; CHECK-DEFAULT: ldrb{{.*}}, #4]!188 189; CHECK-COMPLEX: str{{.*}}, #16]!190; CHECK-COMPLEX: ldrb{{.*}}, #4]!191; CHECK-COMPLEX: ldrb{{.*}}, #4]!192 193; DISABLED-NOT: ldr{{.*}}]!194; DISABLED-NOT: str{{.*}}]!195 196; CHECK-T2: @ %for.body.epil197; CHECK-T2: ldrb{{.*}}, #1]!198; CHECK-T2: ldrb{{.*}}, #1]!199; CHECK-T2: str{{.*}}, #4]!200 201define void @mul_8x8(ptr nocapture readonly %A, ptr nocapture readonly %B, ptr nocapture %C, i32 %N) {202entry:203 %cmp9 = icmp eq i32 %N, 0204 br i1 %cmp9, label %for.cond.cleanup, label %for.body.preheader205 206for.body.preheader: ; preds = %entry207 %tmp = add i32 %N, -1208 %xtraiter = and i32 %N, 3209 %tmp1 = icmp ult i32 %tmp, 3210 br i1 %tmp1, label %for.cond.cleanup.loopexit.unr-lcssa, label %for.body.preheader.new211 212for.body.preheader.new: ; preds = %for.body.preheader213 %unroll_iter = sub i32 %N, %xtraiter214 br label %for.body215 216for.cond.cleanup.loopexit.unr-lcssa: ; preds = %for.body, %for.body.preheader217 %i.010.unr = phi i32 [ 0, %for.body.preheader ], [ %inc.3, %for.body ]218 %lcmp.mod = icmp eq i32 %xtraiter, 0219 br i1 %lcmp.mod, label %for.cond.cleanup, label %for.body.epil220 221for.body.epil: ; preds = %for.body.epil, %for.cond.cleanup.loopexit.unr-lcssa222 %i.010.epil = phi i32 [ %inc.epil, %for.body.epil ], [ %i.010.unr, %for.cond.cleanup.loopexit.unr-lcssa ]223 %epil.iter = phi i32 [ %epil.iter.sub, %for.body.epil ], [ %xtraiter, %for.cond.cleanup.loopexit.unr-lcssa ]224 %arrayidx.epil = getelementptr inbounds i8, ptr %A, i32 %i.010.epil225 %tmp2 = load i8, ptr %arrayidx.epil, align 1226 %conv.epil = zext i8 %tmp2 to i32227 %arrayidx1.epil = getelementptr inbounds i8, ptr %B, i32 %i.010.epil228 %tmp3 = load i8, ptr %arrayidx1.epil, align 1229 %conv2.epil = zext i8 %tmp3 to i32230 %mul.epil = mul nuw nsw i32 %conv2.epil, %conv.epil231 %arrayidx3.epil = getelementptr inbounds i32, ptr %C, i32 %i.010.epil232 store i32 %mul.epil, ptr %arrayidx3.epil, align 4233 %inc.epil = add nuw i32 %i.010.epil, 1234 %epil.iter.sub = add i32 %epil.iter, -1235 %epil.iter.cmp = icmp eq i32 %epil.iter.sub, 0236 br i1 %epil.iter.cmp, label %for.cond.cleanup, label %for.body.epil237 238for.cond.cleanup: ; preds = %for.body.epil, %for.cond.cleanup.loopexit.unr-lcssa, %entry239 ret void240 241for.body: ; preds = %for.body, %for.body.preheader.new242 %i.010 = phi i32 [ 0, %for.body.preheader.new ], [ %inc.3, %for.body ]243 %niter = phi i32 [ %unroll_iter, %for.body.preheader.new ], [ %niter.nsub.3, %for.body ]244 %arrayidx = getelementptr inbounds i8, ptr %A, i32 %i.010245 %tmp4 = load i8, ptr %arrayidx, align 1246 %conv = zext i8 %tmp4 to i32247 %arrayidx1 = getelementptr inbounds i8, ptr %B, i32 %i.010248 %tmp5 = load i8, ptr %arrayidx1, align 1249 %conv2 = zext i8 %tmp5 to i32250 %mul = mul nuw nsw i32 %conv2, %conv251 %arrayidx3 = getelementptr inbounds i32, ptr %C, i32 %i.010252 store i32 %mul, ptr %arrayidx3, align 4253 %inc = or disjoint i32 %i.010, 1254 %arrayidx.1 = getelementptr inbounds i8, ptr %A, i32 %inc255 %tmp6 = load i8, ptr %arrayidx.1, align 1256 %conv.1 = zext i8 %tmp6 to i32257 %arrayidx1.1 = getelementptr inbounds i8, ptr %B, i32 %inc258 %tmp7 = load i8, ptr %arrayidx1.1, align 1259 %conv2.1 = zext i8 %tmp7 to i32260 %mul.1 = mul nuw nsw i32 %conv2.1, %conv.1261 %arrayidx3.1 = getelementptr inbounds i32, ptr %C, i32 %inc262 store i32 %mul.1, ptr %arrayidx3.1, align 4263 %inc.1 = or disjoint i32 %i.010, 2264 %arrayidx.2 = getelementptr inbounds i8, ptr %A, i32 %inc.1265 %tmp8 = load i8, ptr %arrayidx.2, align 1266 %conv.2 = zext i8 %tmp8 to i32267 %arrayidx1.2 = getelementptr inbounds i8, ptr %B, i32 %inc.1268 %tmp9 = load i8, ptr %arrayidx1.2, align 1269 %conv2.2 = zext i8 %tmp9 to i32270 %mul.2 = mul nuw nsw i32 %conv2.2, %conv.2271 %arrayidx3.2 = getelementptr inbounds i32, ptr %C, i32 %inc.1272 store i32 %mul.2, ptr %arrayidx3.2, align 4273 %inc.2 = or disjoint i32 %i.010, 3274 %arrayidx.3 = getelementptr inbounds i8, ptr %A, i32 %inc.2275 %tmp10 = load i8, ptr %arrayidx.3, align 1276 %conv.3 = zext i8 %tmp10 to i32277 %arrayidx1.3 = getelementptr inbounds i8, ptr %B, i32 %inc.2278 %tmp11 = load i8, ptr %arrayidx1.3, align 1279 %conv2.3 = zext i8 %tmp11 to i32280 %mul.3 = mul nuw nsw i32 %conv2.3, %conv.3281 %arrayidx3.3 = getelementptr inbounds i32, ptr %C, i32 %inc.2282 store i32 %mul.3, ptr %arrayidx3.3, align 4283 %inc.3 = add i32 %i.010, 4284 %niter.nsub.3 = add i32 %niter, -4285 %niter.ncmp.3 = icmp eq i32 %niter.nsub.3, 0286 br i1 %niter.ncmp.3, label %for.cond.cleanup.loopexit.unr-lcssa, label %for.body287}288 289; CHECK-LABEL: mul_16x8290; CHECK: @ %for.body 291 292; CHECK-DEFAULT: str{{.*}}, #16]!293; CHECK-DEFAULT: ldrsh{{.*}}, #8]!294 295; CHECK-COMPLEX: ldrsh{{.*}}, #8]!296; CHECK-COMPLEX: str{{.*}}, #16]!297; CHECK-COMPLEX: ldrb{{.*}}, #4]!298 299; DISABLED-NOT: ldr{{.*}}]!300; DISABLED-NOT: str{{.*}}]!301 302; CHECK-T2: @ %for.body.epil303; CHECK-T2: ldrsh{{.*}}, #2]!304; CHECK-T2: ldrb{{.*}}, #1]!305; CHECK-T2: str{{.*}}, #4]!306 307define void @mul_16x8(ptr nocapture readonly %A, ptr nocapture readonly %B, ptr nocapture %C, i32 %N) {308entry:309 %cmp9 = icmp eq i32 %N, 0310 br i1 %cmp9, label %for.cond.cleanup, label %for.body.preheader311 312for.body.preheader: ; preds = %entry313 %tmp = add i32 %N, -1314 %xtraiter = and i32 %N, 3315 %tmp1 = icmp ult i32 %tmp, 3316 br i1 %tmp1, label %for.cond.cleanup.loopexit.unr-lcssa, label %for.body.preheader.new317 318for.body.preheader.new: ; preds = %for.body.preheader319 %unroll_iter = sub i32 %N, %xtraiter320 br label %for.body321 322for.cond.cleanup.loopexit.unr-lcssa: ; preds = %for.body, %for.body.preheader323 %i.010.unr = phi i32 [ 0, %for.body.preheader ], [ %inc.3, %for.body ]324 %lcmp.mod = icmp eq i32 %xtraiter, 0325 br i1 %lcmp.mod, label %for.cond.cleanup, label %for.body.epil326 327for.body.epil: ; preds = %for.body.epil, %for.cond.cleanup.loopexit.unr-lcssa328 %i.010.epil = phi i32 [ %inc.epil, %for.body.epil ], [ %i.010.unr, %for.cond.cleanup.loopexit.unr-lcssa ]329 %epil.iter = phi i32 [ %epil.iter.sub, %for.body.epil ], [ %xtraiter, %for.cond.cleanup.loopexit.unr-lcssa ]330 %arrayidx.epil = getelementptr inbounds i16, ptr %A, i32 %i.010.epil331 %tmp2 = load i16, ptr %arrayidx.epil, align 2332 %conv.epil = sext i16 %tmp2 to i32333 %arrayidx1.epil = getelementptr inbounds i8, ptr %B, i32 %i.010.epil334 %tmp3 = load i8, ptr %arrayidx1.epil, align 1335 %conv2.epil = zext i8 %tmp3 to i32336 %mul.epil = mul nsw i32 %conv2.epil, %conv.epil337 %arrayidx3.epil = getelementptr inbounds i32, ptr %C, i32 %i.010.epil338 store i32 %mul.epil, ptr %arrayidx3.epil, align 4339 %inc.epil = add nuw i32 %i.010.epil, 1340 %epil.iter.sub = add i32 %epil.iter, -1341 %epil.iter.cmp = icmp eq i32 %epil.iter.sub, 0342 br i1 %epil.iter.cmp, label %for.cond.cleanup, label %for.body.epil343 344for.cond.cleanup: ; preds = %for.body.epil, %for.cond.cleanup.loopexit.unr-lcssa, %entry345 ret void346 347for.body: ; preds = %for.body, %for.body.preheader.new348 %i.010 = phi i32 [ 0, %for.body.preheader.new ], [ %inc.3, %for.body ]349 %niter = phi i32 [ %unroll_iter, %for.body.preheader.new ], [ %niter.nsub.3, %for.body ]350 %arrayidx = getelementptr inbounds i16, ptr %A, i32 %i.010351 %tmp4 = load i16, ptr %arrayidx, align 2352 %conv = sext i16 %tmp4 to i32353 %arrayidx1 = getelementptr inbounds i8, ptr %B, i32 %i.010354 %tmp5 = load i8, ptr %arrayidx1, align 1355 %conv2 = zext i8 %tmp5 to i32356 %mul = mul nsw i32 %conv2, %conv357 %arrayidx3 = getelementptr inbounds i32, ptr %C, i32 %i.010358 store i32 %mul, ptr %arrayidx3, align 4359 %inc = or disjoint i32 %i.010, 1360 %arrayidx.1 = getelementptr inbounds i16, ptr %A, i32 %inc361 %tmp6 = load i16, ptr %arrayidx.1, align 2362 %conv.1 = sext i16 %tmp6 to i32363 %arrayidx1.1 = getelementptr inbounds i8, ptr %B, i32 %inc364 %tmp7 = load i8, ptr %arrayidx1.1, align 1365 %conv2.1 = zext i8 %tmp7 to i32366 %mul.1 = mul nsw i32 %conv2.1, %conv.1367 %arrayidx3.1 = getelementptr inbounds i32, ptr %C, i32 %inc368 store i32 %mul.1, ptr %arrayidx3.1, align 4369 %inc.1 = or disjoint i32 %i.010, 2370 %arrayidx.2 = getelementptr inbounds i16, ptr %A, i32 %inc.1371 %tmp8 = load i16, ptr %arrayidx.2, align 2372 %conv.2 = sext i16 %tmp8 to i32373 %arrayidx1.2 = getelementptr inbounds i8, ptr %B, i32 %inc.1374 %tmp9 = load i8, ptr %arrayidx1.2, align 1375 %conv2.2 = zext i8 %tmp9 to i32376 %mul.2 = mul nsw i32 %conv2.2, %conv.2377 %arrayidx3.2 = getelementptr inbounds i32, ptr %C, i32 %inc.1378 store i32 %mul.2, ptr %arrayidx3.2, align 4379 %inc.2 = or disjoint i32 %i.010, 3380 %arrayidx.3 = getelementptr inbounds i16, ptr %A, i32 %inc.2381 %tmp10 = load i16, ptr %arrayidx.3, align 2382 %conv.3 = sext i16 %tmp10 to i32383 %arrayidx1.3 = getelementptr inbounds i8, ptr %B, i32 %inc.2384 %tmp11 = load i8, ptr %arrayidx1.3, align 1385 %conv2.3 = zext i8 %tmp11 to i32386 %mul.3 = mul nsw i32 %conv2.3, %conv.3387 %arrayidx3.3 = getelementptr inbounds i32, ptr %C, i32 %inc.2388 store i32 %mul.3, ptr %arrayidx3.3, align 4389 %inc.3 = add i32 %i.010, 4390 %niter.nsub.3 = add i32 %niter, -4391 %niter.ncmp.3 = icmp eq i32 %niter.nsub.3, 0392 br i1 %niter.ncmp.3, label %for.cond.cleanup.loopexit.unr-lcssa, label %for.body393}394 395; CHECK-LABEL: mul_16x16396; CHECK: @ %for.body397 398; TODO: pre-indexed loads399; CHECK-DEFAULT-NOT: ldrsh{{.*}}]!400; CHECK-DEFAULT: str{{.*}}, #16]!401; CHECK-DEFAULT-NOT: ldrsh{{.*}}]!402 403; CHECK-COMPLEX: ldrsh{{.*}}]!404; CHECK-COMPLEX: ldrsh{{.*}}]!405; CHECK-COMPLEX: str{{.*}}]!406 407; DISABLED-NOT: ldr{{.*}}]!408; DISABLED-NOT: str{{.*}}]!409 410; CHECK-T2: @ %for.body.epil411; CHECK-T2: ldrsh{{.*}}, #2]!412; CHECK-T2: ldrsh{{.*}}, #2]!413; CHECK-T2: str{{.*}}, #4]!414 415define void @mul_16x16(ptr nocapture readonly %A, ptr nocapture readonly %B, ptr nocapture %C, i32 %N) {416entry:417 %cmp9 = icmp eq i32 %N, 0418 br i1 %cmp9, label %for.cond.cleanup, label %for.body.preheader419 420for.body.preheader: ; preds = %entry421 %tmp = add i32 %N, -1422 %xtraiter = and i32 %N, 3423 %tmp1 = icmp ult i32 %tmp, 3424 br i1 %tmp1, label %for.cond.cleanup.loopexit.unr-lcssa, label %for.body.preheader.new425 426for.body.preheader.new: ; preds = %for.body.preheader427 %unroll_iter = sub i32 %N, %xtraiter428 br label %for.body429 430for.cond.cleanup.loopexit.unr-lcssa: ; preds = %for.body, %for.body.preheader431 %i.010.unr = phi i32 [ 0, %for.body.preheader ], [ %inc.3, %for.body ]432 %lcmp.mod = icmp eq i32 %xtraiter, 0433 br i1 %lcmp.mod, label %for.cond.cleanup, label %for.body.epil434 435for.body.epil: ; preds = %for.body.epil, %for.cond.cleanup.loopexit.unr-lcssa436 %i.010.epil = phi i32 [ %inc.epil, %for.body.epil ], [ %i.010.unr, %for.cond.cleanup.loopexit.unr-lcssa ]437 %epil.iter = phi i32 [ %epil.iter.sub, %for.body.epil ], [ %xtraiter, %for.cond.cleanup.loopexit.unr-lcssa ]438 %arrayidx.epil = getelementptr inbounds i16, ptr %A, i32 %i.010.epil439 %tmp2 = load i16, ptr %arrayidx.epil, align 2440 %conv.epil = sext i16 %tmp2 to i32441 %arrayidx1.epil = getelementptr inbounds i16, ptr %B, i32 %i.010.epil442 %tmp3 = load i16, ptr %arrayidx1.epil, align 2443 %conv2.epil = sext i16 %tmp3 to i32444 %mul.epil = mul nsw i32 %conv2.epil, %conv.epil445 %arrayidx3.epil = getelementptr inbounds i32, ptr %C, i32 %i.010.epil446 store i32 %mul.epil, ptr %arrayidx3.epil, align 4447 %inc.epil = add nuw i32 %i.010.epil, 1448 %epil.iter.sub = add i32 %epil.iter, -1449 %epil.iter.cmp = icmp eq i32 %epil.iter.sub, 0450 br i1 %epil.iter.cmp, label %for.cond.cleanup, label %for.body.epil451 452for.cond.cleanup: ; preds = %for.body.epil, %for.cond.cleanup.loopexit.unr-lcssa, %entry453 ret void454 455for.body: ; preds = %for.body, %for.body.preheader.new456 %i.010 = phi i32 [ 0, %for.body.preheader.new ], [ %inc.3, %for.body ]457 %niter = phi i32 [ %unroll_iter, %for.body.preheader.new ], [ %niter.nsub.3, %for.body ]458 %arrayidx = getelementptr inbounds i16, ptr %A, i32 %i.010459 %tmp4 = load i16, ptr %arrayidx, align 2460 %conv = sext i16 %tmp4 to i32461 %arrayidx1 = getelementptr inbounds i16, ptr %B, i32 %i.010462 %tmp5 = load i16, ptr %arrayidx1, align 2463 %conv2 = sext i16 %tmp5 to i32464 %mul = mul nsw i32 %conv2, %conv465 %arrayidx3 = getelementptr inbounds i32, ptr %C, i32 %i.010466 store i32 %mul, ptr %arrayidx3, align 4467 %inc = or disjoint i32 %i.010, 1468 %arrayidx.1 = getelementptr inbounds i16, ptr %A, i32 %inc469 %tmp6 = load i16, ptr %arrayidx.1, align 2470 %conv.1 = sext i16 %tmp6 to i32471 %arrayidx1.1 = getelementptr inbounds i16, ptr %B, i32 %inc472 %tmp7 = load i16, ptr %arrayidx1.1, align 2473 %conv2.1 = sext i16 %tmp7 to i32474 %mul.1 = mul nsw i32 %conv2.1, %conv.1475 %arrayidx3.1 = getelementptr inbounds i32, ptr %C, i32 %inc476 store i32 %mul.1, ptr %arrayidx3.1, align 4477 %inc.1 = or disjoint i32 %i.010, 2478 %arrayidx.2 = getelementptr inbounds i16, ptr %A, i32 %inc.1479 %tmp8 = load i16, ptr %arrayidx.2, align 2480 %conv.2 = sext i16 %tmp8 to i32481 %arrayidx1.2 = getelementptr inbounds i16, ptr %B, i32 %inc.1482 %tmp9 = load i16, ptr %arrayidx1.2, align 2483 %conv2.2 = sext i16 %tmp9 to i32484 %mul.2 = mul nsw i32 %conv2.2, %conv.2485 %arrayidx3.2 = getelementptr inbounds i32, ptr %C, i32 %inc.1486 store i32 %mul.2, ptr %arrayidx3.2, align 4487 %inc.2 = or disjoint i32 %i.010, 3488 %arrayidx.3 = getelementptr inbounds i16, ptr %A, i32 %inc.2489 %tmp10 = load i16, ptr %arrayidx.3, align 2490 %conv.3 = sext i16 %tmp10 to i32491 %arrayidx1.3 = getelementptr inbounds i16, ptr %B, i32 %inc.2492 %tmp11 = load i16, ptr %arrayidx1.3, align 2493 %conv2.3 = sext i16 %tmp11 to i32494 %mul.3 = mul nsw i32 %conv2.3, %conv.3495 %arrayidx3.3 = getelementptr inbounds i32, ptr %C, i32 %inc.2496 store i32 %mul.3, ptr %arrayidx3.3, align 4497 %inc.3 = add i32 %i.010, 4498 %niter.nsub.3 = add i32 %niter, -4499 %niter.ncmp.3 = icmp eq i32 %niter.nsub.3, 0500 br i1 %niter.ncmp.3, label %for.cond.cleanup.loopexit.unr-lcssa, label %for.body501}502 503; CHECK-LABEL: mul_8x8_2d504; CHECK: @ %for.body4.us505 506; CHECK-DEFAULT: ldr{{.*}}, #16]!507; CHECK-DEFAULT: ldrb{{.*}}, #4]!508 509; DISABLED-NOT: ldr{{.*}}]!510; DISABLED-NOT: str{{.*}}]!511 512; CHECK-T2: @ %for.body4.us.epil513; CHECK-T2: ldrb{{.*}}, #1]!514; CHECK-T2: ldr{{.*}}, #4]!515 516define void @mul_8x8_2d(ptr nocapture readonly %A, ptr nocapture readonly %B, ptr nocapture readonly %C, i32 %N, i32 %M) {517entry:518 %cmp24 = icmp eq i32 %N, 0519 %cmp222 = icmp eq i32 %M, 0520 %or.cond = or i1 %cmp24, %cmp222521 br i1 %or.cond, label %for.cond.cleanup, label %for.cond1.preheader.us.preheader522 523for.cond1.preheader.us.preheader: ; preds = %entry524 %tmp = add i32 %M, -1525 %xtraiter = and i32 %M, 3526 %tmp1 = icmp ult i32 %tmp, 3527 %unroll_iter = sub i32 %M, %xtraiter528 %lcmp.mod = icmp eq i32 %xtraiter, 0529 br label %for.cond1.preheader.us530 531for.cond1.preheader.us: ; preds = %for.cond1.for.cond.cleanup3_crit_edge.us, %for.cond1.preheader.us.preheader532 %i.025.us = phi i32 [ %inc11.us, %for.cond1.for.cond.cleanup3_crit_edge.us ], [ 0, %for.cond1.preheader.us.preheader ]533 %arrayidx.us = getelementptr inbounds i8, ptr %A, i32 %i.025.us534 %arrayidx5.us = getelementptr inbounds ptr, ptr %B, i32 %i.025.us535 %arrayidx8.us = getelementptr inbounds ptr, ptr %C, i32 %i.025.us536 %.pre = load ptr, ptr %arrayidx5.us, align 4537 %.pre30 = load ptr, ptr %arrayidx8.us, align 4538 br i1 %tmp1, label %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa, label %for.body4.us539 540for.body4.us: ; preds = %for.body4.us, %for.cond1.preheader.us541 %j.023.us = phi i32 [ %inc.us.3, %for.body4.us ], [ 0, %for.cond1.preheader.us ]542 %niter = phi i32 [ %niter.nsub.3, %for.body4.us ], [ %unroll_iter, %for.cond1.preheader.us ]543 %tmp2 = load i8, ptr %arrayidx.us, align 1544 %conv.us = zext i8 %tmp2 to i32545 %arrayidx6.us = getelementptr inbounds i8, ptr %.pre, i32 %j.023.us546 %tmp3 = load i8, ptr %arrayidx6.us, align 1547 %conv7.us = zext i8 %tmp3 to i32548 %mul.us = mul nuw nsw i32 %conv7.us, %conv.us549 %arrayidx9.us = getelementptr inbounds i32, ptr %.pre30, i32 %j.023.us550 %tmp4 = load i32, ptr %arrayidx9.us, align 4551 %add.us = add nsw i32 %tmp4, %mul.us552 store i32 %add.us, ptr %arrayidx9.us, align 4553 %inc.us = or disjoint i32 %j.023.us, 1554 %tmp5 = load i8, ptr %arrayidx.us, align 1555 %conv.us.1 = zext i8 %tmp5 to i32556 %arrayidx6.us.1 = getelementptr inbounds i8, ptr %.pre, i32 %inc.us557 %tmp6 = load i8, ptr %arrayidx6.us.1, align 1558 %conv7.us.1 = zext i8 %tmp6 to i32559 %mul.us.1 = mul nuw nsw i32 %conv7.us.1, %conv.us.1560 %arrayidx9.us.1 = getelementptr inbounds i32, ptr %.pre30, i32 %inc.us561 %tmp7 = load i32, ptr %arrayidx9.us.1, align 4562 %add.us.1 = add nsw i32 %tmp7, %mul.us.1563 store i32 %add.us.1, ptr %arrayidx9.us.1, align 4564 %inc.us.1 = or disjoint i32 %j.023.us, 2565 %tmp8 = load i8, ptr %arrayidx.us, align 1566 %conv.us.2 = zext i8 %tmp8 to i32567 %arrayidx6.us.2 = getelementptr inbounds i8, ptr %.pre, i32 %inc.us.1568 %tmp9 = load i8, ptr %arrayidx6.us.2, align 1569 %conv7.us.2 = zext i8 %tmp9 to i32570 %mul.us.2 = mul nuw nsw i32 %conv7.us.2, %conv.us.2571 %arrayidx9.us.2 = getelementptr inbounds i32, ptr %.pre30, i32 %inc.us.1572 %tmp10 = load i32, ptr %arrayidx9.us.2, align 4573 %add.us.2 = add nsw i32 %tmp10, %mul.us.2574 store i32 %add.us.2, ptr %arrayidx9.us.2, align 4575 %inc.us.2 = or disjoint i32 %j.023.us, 3576 %tmp11 = load i8, ptr %arrayidx.us, align 1577 %conv.us.3 = zext i8 %tmp11 to i32578 %arrayidx6.us.3 = getelementptr inbounds i8, ptr %.pre, i32 %inc.us.2579 %tmp12 = load i8, ptr %arrayidx6.us.3, align 1580 %conv7.us.3 = zext i8 %tmp12 to i32581 %mul.us.3 = mul nuw nsw i32 %conv7.us.3, %conv.us.3582 %arrayidx9.us.3 = getelementptr inbounds i32, ptr %.pre30, i32 %inc.us.2583 %tmp13 = load i32, ptr %arrayidx9.us.3, align 4584 %add.us.3 = add nsw i32 %tmp13, %mul.us.3585 store i32 %add.us.3, ptr %arrayidx9.us.3, align 4586 %inc.us.3 = add i32 %j.023.us, 4587 %niter.nsub.3 = add i32 %niter, -4588 %niter.ncmp.3 = icmp eq i32 %niter.nsub.3, 0589 br i1 %niter.ncmp.3, label %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa, label %for.body4.us590 591for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa: ; preds = %for.body4.us, %for.cond1.preheader.us592 %j.023.us.unr = phi i32 [ 0, %for.cond1.preheader.us ], [ %inc.us.3, %for.body4.us ]593 br i1 %lcmp.mod, label %for.cond1.for.cond.cleanup3_crit_edge.us, label %for.body4.us.epil594 595for.body4.us.epil: ; preds = %for.body4.us.epil, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa596 %j.023.us.epil = phi i32 [ %inc.us.epil, %for.body4.us.epil ], [ %j.023.us.unr, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa ]597 %epil.iter = phi i32 [ %epil.iter.sub, %for.body4.us.epil ], [ %xtraiter, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa ]598 %tmp14 = load i8, ptr %arrayidx.us, align 1599 %conv.us.epil = zext i8 %tmp14 to i32600 %arrayidx6.us.epil = getelementptr inbounds i8, ptr %.pre, i32 %j.023.us.epil601 %tmp15 = load i8, ptr %arrayidx6.us.epil, align 1602 %conv7.us.epil = zext i8 %tmp15 to i32603 %mul.us.epil = mul nuw nsw i32 %conv7.us.epil, %conv.us.epil604 %arrayidx9.us.epil = getelementptr inbounds i32, ptr %.pre30, i32 %j.023.us.epil605 %tmp16 = load i32, ptr %arrayidx9.us.epil, align 4606 %add.us.epil = add nsw i32 %tmp16, %mul.us.epil607 store i32 %add.us.epil, ptr %arrayidx9.us.epil, align 4608 %inc.us.epil = add nuw i32 %j.023.us.epil, 1609 %epil.iter.sub = add i32 %epil.iter, -1610 %epil.iter.cmp = icmp eq i32 %epil.iter.sub, 0611 br i1 %epil.iter.cmp, label %for.cond1.for.cond.cleanup3_crit_edge.us, label %for.body4.us.epil612 613for.cond1.for.cond.cleanup3_crit_edge.us: ; preds = %for.body4.us.epil, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa614 %inc11.us = add nuw i32 %i.025.us, 1615 %exitcond28 = icmp eq i32 %inc11.us, %N616 br i1 %exitcond28, label %for.cond.cleanup, label %for.cond1.preheader.us617 618for.cond.cleanup: ; preds = %for.cond1.for.cond.cleanup3_crit_edge.us, %entry619 ret void620}621 622; CHECK-LABEL: mul_16x16_2d623; CHECK: @ %for.body4.us624 625; CHECK-DEFAULT: ldr{{.*}}, #16]!626; CHECK-DEFAULT: ldrsh{{.*}}, #8]!627 628; DISABLED-NOT: ldr{{.*}}]!629; DISABLED-NOT: str{{.*}}]!630 631; CHECK-T2: @ %for.body4.us.epil632; CHECK-T2: ldrsh{{.*}}, #2]!633; CHECK-T2: ldr{{.*}}, #4]!634 635define void @mul_16x16_2d(ptr nocapture readonly %A, ptr nocapture readonly %B, ptr nocapture readonly %C, i32 %N, i32 %M) {636entry:637 %cmp24 = icmp eq i32 %N, 0638 %cmp222 = icmp eq i32 %M, 0639 %or.cond = or i1 %cmp24, %cmp222640 br i1 %or.cond, label %for.cond.cleanup, label %for.cond1.preheader.us.preheader641 642for.cond1.preheader.us.preheader: ; preds = %entry643 %tmp = add i32 %M, -1644 %xtraiter = and i32 %M, 3645 %tmp1 = icmp ult i32 %tmp, 3646 %unroll_iter = sub i32 %M, %xtraiter647 %lcmp.mod = icmp eq i32 %xtraiter, 0648 br label %for.cond1.preheader.us649 650for.cond1.preheader.us: ; preds = %for.cond1.for.cond.cleanup3_crit_edge.us, %for.cond1.preheader.us.preheader651 %i.025.us = phi i32 [ %inc11.us, %for.cond1.for.cond.cleanup3_crit_edge.us ], [ 0, %for.cond1.preheader.us.preheader ]652 %arrayidx.us = getelementptr inbounds i16, ptr %A, i32 %i.025.us653 %tmp2 = load i16, ptr %arrayidx.us, align 2654 %conv.us = sext i16 %tmp2 to i32655 %arrayidx5.us = getelementptr inbounds ptr, ptr %B, i32 %i.025.us656 %tmp3 = load ptr, ptr %arrayidx5.us, align 4657 %arrayidx8.us = getelementptr inbounds ptr, ptr %C, i32 %i.025.us658 %tmp4 = load ptr, ptr %arrayidx8.us, align 4659 br i1 %tmp1, label %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa, label %for.body4.us660 661for.body4.us: ; preds = %for.body4.us, %for.cond1.preheader.us662 %j.023.us = phi i32 [ %inc.us.3, %for.body4.us ], [ 0, %for.cond1.preheader.us ]663 %niter = phi i32 [ %niter.nsub.3, %for.body4.us ], [ %unroll_iter, %for.cond1.preheader.us ]664 %arrayidx6.us = getelementptr inbounds i16, ptr %tmp3, i32 %j.023.us665 %tmp5 = load i16, ptr %arrayidx6.us, align 2666 %conv7.us = sext i16 %tmp5 to i32667 %mul.us = mul nsw i32 %conv7.us, %conv.us668 %arrayidx9.us = getelementptr inbounds i32, ptr %tmp4, i32 %j.023.us669 %tmp6 = load i32, ptr %arrayidx9.us, align 4670 %add.us = add nsw i32 %tmp6, %mul.us671 store i32 %add.us, ptr %arrayidx9.us, align 4672 %inc.us = or disjoint i32 %j.023.us, 1673 %arrayidx6.us.1 = getelementptr inbounds i16, ptr %tmp3, i32 %inc.us674 %tmp7 = load i16, ptr %arrayidx6.us.1, align 2675 %conv7.us.1 = sext i16 %tmp7 to i32676 %mul.us.1 = mul nsw i32 %conv7.us.1, %conv.us677 %arrayidx9.us.1 = getelementptr inbounds i32, ptr %tmp4, i32 %inc.us678 %tmp8 = load i32, ptr %arrayidx9.us.1, align 4679 %add.us.1 = add nsw i32 %tmp8, %mul.us.1680 store i32 %add.us.1, ptr %arrayidx9.us.1, align 4681 %inc.us.1 = or disjoint i32 %j.023.us, 2682 %arrayidx6.us.2 = getelementptr inbounds i16, ptr %tmp3, i32 %inc.us.1683 %tmp9 = load i16, ptr %arrayidx6.us.2, align 2684 %conv7.us.2 = sext i16 %tmp9 to i32685 %mul.us.2 = mul nsw i32 %conv7.us.2, %conv.us686 %arrayidx9.us.2 = getelementptr inbounds i32, ptr %tmp4, i32 %inc.us.1687 %tmp10 = load i32, ptr %arrayidx9.us.2, align 4688 %add.us.2 = add nsw i32 %tmp10, %mul.us.2689 store i32 %add.us.2, ptr %arrayidx9.us.2, align 4690 %inc.us.2 = or disjoint i32 %j.023.us, 3691 %arrayidx6.us.3 = getelementptr inbounds i16, ptr %tmp3, i32 %inc.us.2692 %tmp11 = load i16, ptr %arrayidx6.us.3, align 2693 %conv7.us.3 = sext i16 %tmp11 to i32694 %mul.us.3 = mul nsw i32 %conv7.us.3, %conv.us695 %arrayidx9.us.3 = getelementptr inbounds i32, ptr %tmp4, i32 %inc.us.2696 %tmp12 = load i32, ptr %arrayidx9.us.3, align 4697 %add.us.3 = add nsw i32 %tmp12, %mul.us.3698 store i32 %add.us.3, ptr %arrayidx9.us.3, align 4699 %inc.us.3 = add i32 %j.023.us, 4700 %niter.nsub.3 = add i32 %niter, -4701 %niter.ncmp.3 = icmp eq i32 %niter.nsub.3, 0702 br i1 %niter.ncmp.3, label %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa, label %for.body4.us703 704for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa: ; preds = %for.body4.us, %for.cond1.preheader.us705 %j.023.us.unr = phi i32 [ 0, %for.cond1.preheader.us ], [ %inc.us.3, %for.body4.us ]706 br i1 %lcmp.mod, label %for.cond1.for.cond.cleanup3_crit_edge.us, label %for.body4.us.epil707 708for.body4.us.epil: ; preds = %for.body4.us.epil, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa709 %j.023.us.epil = phi i32 [ %inc.us.epil, %for.body4.us.epil ], [ %j.023.us.unr, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa ]710 %epil.iter = phi i32 [ %epil.iter.sub, %for.body4.us.epil ], [ %xtraiter, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa ]711 %arrayidx6.us.epil = getelementptr inbounds i16, ptr %tmp3, i32 %j.023.us.epil712 %tmp13 = load i16, ptr %arrayidx6.us.epil, align 2713 %conv7.us.epil = sext i16 %tmp13 to i32714 %mul.us.epil = mul nsw i32 %conv7.us.epil, %conv.us715 %arrayidx9.us.epil = getelementptr inbounds i32, ptr %tmp4, i32 %j.023.us.epil716 %tmp14 = load i32, ptr %arrayidx9.us.epil, align 4717 %add.us.epil = add nsw i32 %tmp14, %mul.us.epil718 store i32 %add.us.epil, ptr %arrayidx9.us.epil, align 4719 %inc.us.epil = add nuw i32 %j.023.us.epil, 1720 %epil.iter.sub = add i32 %epil.iter, -1721 %epil.iter.cmp = icmp eq i32 %epil.iter.sub, 0722 br i1 %epil.iter.cmp, label %for.cond1.for.cond.cleanup3_crit_edge.us, label %for.body4.us.epil723 724for.cond1.for.cond.cleanup3_crit_edge.us: ; preds = %for.body4.us.epil, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa725 %inc11.us = add nuw i32 %i.025.us, 1726 %exitcond28 = icmp eq i32 %inc11.us, %N727 br i1 %exitcond28, label %for.cond.cleanup, label %for.cond1.preheader.us728 729for.cond.cleanup: ; preds = %for.cond1.for.cond.cleanup3_crit_edge.us, %entry730 ret void731}732 733; CHECK-LABEL: mac_8x8_2d734; CHECK: @ %for.body4.us735 736; TODO: Both input arrays could use pre-indexed loads.737; TODO: pre-indexed stores.738; CHECK-DEFAULT: ldrb{{.*}}, #4]!739; CHECK-DEFAULT-NOT: ldr{{.*}}]!740; CHECK-DEFAULT-NOT: str{{.*}}]!741 742; TODO: Increased complexity shouldn't prevent indexed accesses.743; CHECK-COMPLEX-NOT: ldr{{.*}}]!744; CHECK-COMPLEX-NOT: str{{.*}}]!745 746; DISABLED-NOT: ldr{{.*}}]!747; DISABLED-NOT: str{{.*}}]!748 749; CHECK-T2: @ %for.body4.us.epil750; CHECK-T2: ldrb{{.*}}, #1]!751 752define void @mac_8x8_2d(ptr nocapture readonly %A, ptr nocapture readonly %B, ptr nocapture %C, i32 %N, i32 %M) {753entry:754 %cmp22 = icmp eq i32 %N, 0755 %cmp220 = icmp eq i32 %M, 0756 %or.cond = or i1 %cmp22, %cmp220757 br i1 %or.cond, label %for.cond.cleanup, label %for.cond1.preheader.us.preheader758 759for.cond1.preheader.us.preheader: ; preds = %entry760 %tmp = add i32 %M, -1761 %xtraiter = and i32 %M, 3762 %tmp1 = icmp ult i32 %tmp, 3763 %unroll_iter = sub i32 %M, %xtraiter764 %lcmp.mod = icmp eq i32 %xtraiter, 0765 br label %for.cond1.preheader.us766 767for.cond1.preheader.us: ; preds = %for.cond1.for.cond.cleanup3_crit_edge.us, %for.cond1.preheader.us.preheader768 %i.023.us = phi i32 [ %inc10.us, %for.cond1.for.cond.cleanup3_crit_edge.us ], [ 0, %for.cond1.preheader.us.preheader ]769 %arrayidx.us = getelementptr inbounds i8, ptr %A, i32 %i.023.us770 %arrayidx5.us = getelementptr inbounds ptr, ptr %B, i32 %i.023.us771 %arrayidx8.us = getelementptr inbounds i32, ptr %C, i32 %i.023.us772 %.pre = load ptr, ptr %arrayidx5.us, align 4773 %.pre28 = load i32, ptr %arrayidx8.us, align 4774 br i1 %tmp1, label %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa, label %for.body4.us775 776for.body4.us: ; preds = %for.body4.us, %for.cond1.preheader.us777 %tmp2 = phi i32 [ %add.us.3, %for.body4.us ], [ %.pre28, %for.cond1.preheader.us ]778 %j.021.us = phi i32 [ %inc.us.3, %for.body4.us ], [ 0, %for.cond1.preheader.us ]779 %niter = phi i32 [ %niter.nsub.3, %for.body4.us ], [ %unroll_iter, %for.cond1.preheader.us ]780 %tmp3 = load i8, ptr %arrayidx.us, align 1781 %conv.us = zext i8 %tmp3 to i32782 %arrayidx6.us = getelementptr inbounds i8, ptr %.pre, i32 %j.021.us783 %tmp4 = load i8, ptr %arrayidx6.us, align 1784 %conv7.us = zext i8 %tmp4 to i32785 %mul.us = mul nuw nsw i32 %conv7.us, %conv.us786 %add.us = add nsw i32 %mul.us, %tmp2787 store i32 %add.us, ptr %arrayidx8.us, align 4788 %inc.us = or disjoint i32 %j.021.us, 1789 %tmp5 = load i8, ptr %arrayidx.us, align 1790 %conv.us.1 = zext i8 %tmp5 to i32791 %arrayidx6.us.1 = getelementptr inbounds i8, ptr %.pre, i32 %inc.us792 %tmp6 = load i8, ptr %arrayidx6.us.1, align 1793 %conv7.us.1 = zext i8 %tmp6 to i32794 %mul.us.1 = mul nuw nsw i32 %conv7.us.1, %conv.us.1795 %add.us.1 = add nsw i32 %mul.us.1, %add.us796 store i32 %add.us.1, ptr %arrayidx8.us, align 4797 %inc.us.1 = or disjoint i32 %j.021.us, 2798 %tmp7 = load i8, ptr %arrayidx.us, align 1799 %conv.us.2 = zext i8 %tmp7 to i32800 %arrayidx6.us.2 = getelementptr inbounds i8, ptr %.pre, i32 %inc.us.1801 %tmp8 = load i8, ptr %arrayidx6.us.2, align 1802 %conv7.us.2 = zext i8 %tmp8 to i32803 %mul.us.2 = mul nuw nsw i32 %conv7.us.2, %conv.us.2804 %add.us.2 = add nsw i32 %mul.us.2, %add.us.1805 store i32 %add.us.2, ptr %arrayidx8.us, align 4806 %inc.us.2 = or disjoint i32 %j.021.us, 3807 %tmp9 = load i8, ptr %arrayidx.us, align 1808 %conv.us.3 = zext i8 %tmp9 to i32809 %arrayidx6.us.3 = getelementptr inbounds i8, ptr %.pre, i32 %inc.us.2810 %tmp10 = load i8, ptr %arrayidx6.us.3, align 1811 %conv7.us.3 = zext i8 %tmp10 to i32812 %mul.us.3 = mul nuw nsw i32 %conv7.us.3, %conv.us.3813 %add.us.3 = add nsw i32 %mul.us.3, %add.us.2814 store i32 %add.us.3, ptr %arrayidx8.us, align 4815 %inc.us.3 = add i32 %j.021.us, 4816 %niter.nsub.3 = add i32 %niter, -4817 %niter.ncmp.3 = icmp eq i32 %niter.nsub.3, 0818 br i1 %niter.ncmp.3, label %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa, label %for.body4.us819 820for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa: ; preds = %for.body4.us, %for.cond1.preheader.us821 %.unr = phi i32 [ %.pre28, %for.cond1.preheader.us ], [ %add.us.3, %for.body4.us ]822 %j.021.us.unr = phi i32 [ 0, %for.cond1.preheader.us ], [ %inc.us.3, %for.body4.us ]823 br i1 %lcmp.mod, label %for.cond1.for.cond.cleanup3_crit_edge.us, label %for.body4.us.epil824 825for.body4.us.epil: ; preds = %for.body4.us.epil, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa826 %tmp11 = phi i32 [ %add.us.epil, %for.body4.us.epil ], [ %.unr, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa ]827 %j.021.us.epil = phi i32 [ %inc.us.epil, %for.body4.us.epil ], [ %j.021.us.unr, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa ]828 %epil.iter = phi i32 [ %epil.iter.sub, %for.body4.us.epil ], [ %xtraiter, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa ]829 %tmp12 = load i8, ptr %arrayidx.us, align 1830 %conv.us.epil = zext i8 %tmp12 to i32831 %arrayidx6.us.epil = getelementptr inbounds i8, ptr %.pre, i32 %j.021.us.epil832 %tmp13 = load i8, ptr %arrayidx6.us.epil, align 1833 %conv7.us.epil = zext i8 %tmp13 to i32834 %mul.us.epil = mul nuw nsw i32 %conv7.us.epil, %conv.us.epil835 %add.us.epil = add nsw i32 %mul.us.epil, %tmp11836 store i32 %add.us.epil, ptr %arrayidx8.us, align 4837 %inc.us.epil = add nuw i32 %j.021.us.epil, 1838 %epil.iter.sub = add i32 %epil.iter, -1839 %epil.iter.cmp = icmp eq i32 %epil.iter.sub, 0840 br i1 %epil.iter.cmp, label %for.cond1.for.cond.cleanup3_crit_edge.us, label %for.body4.us.epil841 842for.cond1.for.cond.cleanup3_crit_edge.us: ; preds = %for.body4.us.epil, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa843 %inc10.us = add nuw i32 %i.023.us, 1844 %exitcond26 = icmp eq i32 %inc10.us, %N845 br i1 %exitcond26, label %for.cond.cleanup, label %for.cond1.preheader.us846 847for.cond.cleanup: ; preds = %for.cond1.for.cond.cleanup3_crit_edge.us, %entry848 ret void849}850 851; CHECK-LABEL: mac_16x16_2d852; CHECK: @ %for.body4.us853 854; TODO: pre-indexed loads for both input arrays.855; CHECK-DEFAULT: ldrsh{{.*}}, #8]!856; CHECK-DEFAULT-NOT: ldr{{.*}}]!857 858; TODO: increased complexity should lead to better codegen.859; CHECK-COMPLEX-NOT: ldr{{.*}}]!860 861; DISABLED-NOT: ldr{{.*}}]!862 863; CHECK-T2: @ %for.body4.us.epil864; CHECK-T2: ldrsh{{.*}}, #2]!865 866define void @mac_16x16_2d(ptr nocapture readonly %A, ptr nocapture readonly %B, ptr nocapture %C, i32 %N, i32 %M) {867entry:868 %cmp23 = icmp eq i32 %N, 0869 %cmp220 = icmp eq i32 %M, 0870 %or.cond = or i1 %cmp23, %cmp220871 br i1 %or.cond, label %for.cond.cleanup, label %for.cond1.preheader.us.preheader872 873for.cond1.preheader.us.preheader: ; preds = %entry874 %tmp = add i32 %M, -1875 %xtraiter = and i32 %M, 3876 %tmp1 = icmp ult i32 %tmp, 3877 %unroll_iter = sub i32 %M, %xtraiter878 %lcmp.mod = icmp eq i32 %xtraiter, 0879 br label %for.cond1.preheader.us880 881for.cond1.preheader.us: ; preds = %for.cond1.for.cond.cleanup3_crit_edge.us, %for.cond1.preheader.us.preheader882 %i.024.us = phi i32 [ %inc10.us, %for.cond1.for.cond.cleanup3_crit_edge.us ], [ 0, %for.cond1.preheader.us.preheader ]883 %arrayidx.us = getelementptr inbounds i16, ptr %A, i32 %i.024.us884 %tmp2 = load i16, ptr %arrayidx.us, align 2885 %conv.us = sext i16 %tmp2 to i32886 %arrayidx5.us = getelementptr inbounds ptr, ptr %B, i32 %i.024.us887 %tmp3 = load ptr, ptr %arrayidx5.us, align 4888 %arrayidx8.us = getelementptr inbounds i32, ptr %C, i32 %i.024.us889 %arrayidx8.promoted.us = load i32, ptr %arrayidx8.us, align 4890 br i1 %tmp1, label %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa, label %for.body4.us891 892for.body4.us: ; preds = %for.body4.us, %for.cond1.preheader.us893 %add22.us = phi i32 [ %add.us.3, %for.body4.us ], [ %arrayidx8.promoted.us, %for.cond1.preheader.us ]894 %j.021.us = phi i32 [ %inc.us.3, %for.body4.us ], [ 0, %for.cond1.preheader.us ]895 %niter = phi i32 [ %niter.nsub.3, %for.body4.us ], [ %unroll_iter, %for.cond1.preheader.us ]896 %arrayidx6.us = getelementptr inbounds i16, ptr %tmp3, i32 %j.021.us897 %tmp4 = load i16, ptr %arrayidx6.us, align 2898 %conv7.us = sext i16 %tmp4 to i32899 %mul.us = mul nsw i32 %conv7.us, %conv.us900 %add.us = add nsw i32 %mul.us, %add22.us901 %inc.us = or disjoint i32 %j.021.us, 1902 %arrayidx6.us.1 = getelementptr inbounds i16, ptr %tmp3, i32 %inc.us903 %tmp5 = load i16, ptr %arrayidx6.us.1, align 2904 %conv7.us.1 = sext i16 %tmp5 to i32905 %mul.us.1 = mul nsw i32 %conv7.us.1, %conv.us906 %add.us.1 = add nsw i32 %mul.us.1, %add.us907 %inc.us.1 = or disjoint i32 %j.021.us, 2908 %arrayidx6.us.2 = getelementptr inbounds i16, ptr %tmp3, i32 %inc.us.1909 %tmp6 = load i16, ptr %arrayidx6.us.2, align 2910 %conv7.us.2 = sext i16 %tmp6 to i32911 %mul.us.2 = mul nsw i32 %conv7.us.2, %conv.us912 %add.us.2 = add nsw i32 %mul.us.2, %add.us.1913 %inc.us.2 = or disjoint i32 %j.021.us, 3914 %arrayidx6.us.3 = getelementptr inbounds i16, ptr %tmp3, i32 %inc.us.2915 %tmp7 = load i16, ptr %arrayidx6.us.3, align 2916 %conv7.us.3 = sext i16 %tmp7 to i32917 %mul.us.3 = mul nsw i32 %conv7.us.3, %conv.us918 %add.us.3 = add nsw i32 %mul.us.3, %add.us.2919 %inc.us.3 = add i32 %j.021.us, 4920 %niter.nsub.3 = add i32 %niter, -4921 %niter.ncmp.3 = icmp eq i32 %niter.nsub.3, 0922 br i1 %niter.ncmp.3, label %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa, label %for.body4.us923 924for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa: ; preds = %for.body4.us, %for.cond1.preheader.us925 %add.us.lcssa.ph = phi i32 [ undef, %for.cond1.preheader.us ], [ %add.us.3, %for.body4.us ]926 %add22.us.unr = phi i32 [ %arrayidx8.promoted.us, %for.cond1.preheader.us ], [ %add.us.3, %for.body4.us ]927 %j.021.us.unr = phi i32 [ 0, %for.cond1.preheader.us ], [ %inc.us.3, %for.body4.us ]928 br i1 %lcmp.mod, label %for.cond1.for.cond.cleanup3_crit_edge.us, label %for.body4.us.epil929 930for.body4.us.epil: ; preds = %for.body4.us.epil, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa931 %add22.us.epil = phi i32 [ %add.us.epil, %for.body4.us.epil ], [ %add22.us.unr, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa ]932 %j.021.us.epil = phi i32 [ %inc.us.epil, %for.body4.us.epil ], [ %j.021.us.unr, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa ]933 %epil.iter = phi i32 [ %epil.iter.sub, %for.body4.us.epil ], [ %xtraiter, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa ]934 %arrayidx6.us.epil = getelementptr inbounds i16, ptr %tmp3, i32 %j.021.us.epil935 %tmp8 = load i16, ptr %arrayidx6.us.epil, align 2936 %conv7.us.epil = sext i16 %tmp8 to i32937 %mul.us.epil = mul nsw i32 %conv7.us.epil, %conv.us938 %add.us.epil = add nsw i32 %mul.us.epil, %add22.us.epil939 %inc.us.epil = add nuw i32 %j.021.us.epil, 1940 %epil.iter.sub = add i32 %epil.iter, -1941 %epil.iter.cmp = icmp eq i32 %epil.iter.sub, 0942 br i1 %epil.iter.cmp, label %for.cond1.for.cond.cleanup3_crit_edge.us, label %for.body4.us.epil943 944for.cond1.for.cond.cleanup3_crit_edge.us: ; preds = %for.body4.us.epil, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa945 %add.us.lcssa = phi i32 [ %add.us.lcssa.ph, %for.cond1.for.cond.cleanup3_crit_edge.us.unr-lcssa ], [ %add.us.epil, %for.body4.us.epil ]946 store i32 %add.us.lcssa, ptr %arrayidx8.us, align 4947 %inc10.us = add nuw i32 %i.024.us, 1948 %exitcond27 = icmp eq i32 %inc10.us, %N949 br i1 %exitcond27, label %for.cond.cleanup, label %for.cond1.preheader.us950 951for.cond.cleanup: ; preds = %for.cond1.for.cond.cleanup3_crit_edge.us, %entry952 ret void953}954 955; CHECK-LABEL: mul32x32_backwards956; CHECK: @ %for.body957 958; TODO: post increments for decreasing addresses959; CHECK-DEFAULT-NOT: ldr{{.*}}]!960; CHECK-DEFAULT-NOT: str{{.*}}]!961 962; CHECK-COMPLEX-NOT: ldr{{.*}}]!963; CHECK-COMPLEX-NOT: str{{.*}}]!964 965define void @mul32x32_backwards(ptr nocapture %a, ptr nocapture readonly %b, ptr nocapture readonly %c, i32 %N) {966entry:967 %i.08 = add i32 %N, -1968 %cmp9 = icmp sgt i32 %i.08, -1969 br i1 %cmp9, label %for.body.preheader, label %for.cond.cleanup970 971for.body.preheader: ; preds = %entry972 %xtraiter = and i32 %N, 3973 %lcmp.mod = icmp eq i32 %xtraiter, 0974 br i1 %lcmp.mod, label %for.body.prol.loopexit, label %for.body.prol975 976for.body.prol: ; preds = %for.body.prol, %for.body.preheader977 %i.010.prol = phi i32 [ %i.0.prol, %for.body.prol ], [ %i.08, %for.body.preheader ]978 %prol.iter = phi i32 [ %prol.iter.sub, %for.body.prol ], [ %xtraiter, %for.body.preheader ]979 %arrayidx.prol = getelementptr inbounds i32, ptr %b, i32 %i.010.prol980 %tmp = load i32, ptr %arrayidx.prol, align 4981 %arrayidx1.prol = getelementptr inbounds i32, ptr %c, i32 %i.010.prol982 %tmp1 = load i32, ptr %arrayidx1.prol, align 4983 %mul.prol = mul nsw i32 %tmp1, %tmp984 %arrayidx2.prol = getelementptr inbounds i32, ptr %a, i32 %i.010.prol985 store i32 %mul.prol, ptr %arrayidx2.prol, align 4986 %i.0.prol = add i32 %i.010.prol, -1987 %prol.iter.sub = add i32 %prol.iter, -1988 %prol.iter.cmp = icmp eq i32 %prol.iter.sub, 0989 br i1 %prol.iter.cmp, label %for.body.prol.loopexit, label %for.body.prol990 991for.body.prol.loopexit: ; preds = %for.body.prol, %for.body.preheader992 %i.010.unr = phi i32 [ %i.08, %for.body.preheader ], [ %i.0.prol, %for.body.prol ]993 %tmp2 = icmp ult i32 %i.08, 3994 br i1 %tmp2, label %for.cond.cleanup, label %for.body995 996for.cond.cleanup: ; preds = %for.body, %for.body.prol.loopexit, %entry997 ret void998 999for.body: ; preds = %for.body, %for.body.prol.loopexit1000 %i.010 = phi i32 [ %i.0.3, %for.body ], [ %i.010.unr, %for.body.prol.loopexit ]1001 %arrayidx = getelementptr inbounds i32, ptr %b, i32 %i.0101002 %tmp3 = load i32, ptr %arrayidx, align 41003 %arrayidx1 = getelementptr inbounds i32, ptr %c, i32 %i.0101004 %tmp4 = load i32, ptr %arrayidx1, align 41005 %mul = mul nsw i32 %tmp4, %tmp31006 %arrayidx2 = getelementptr inbounds i32, ptr %a, i32 %i.0101007 store i32 %mul, ptr %arrayidx2, align 41008 %i.0 = add i32 %i.010, -11009 %arrayidx.1 = getelementptr inbounds i32, ptr %b, i32 %i.01010 %tmp5 = load i32, ptr %arrayidx.1, align 41011 %arrayidx1.1 = getelementptr inbounds i32, ptr %c, i32 %i.01012 %tmp6 = load i32, ptr %arrayidx1.1, align 41013 %mul.1 = mul nsw i32 %tmp6, %tmp51014 %arrayidx2.1 = getelementptr inbounds i32, ptr %a, i32 %i.01015 store i32 %mul.1, ptr %arrayidx2.1, align 41016 %i.0.1 = add i32 %i.010, -21017 %arrayidx.2 = getelementptr inbounds i32, ptr %b, i32 %i.0.11018 %tmp7 = load i32, ptr %arrayidx.2, align 41019 %arrayidx1.2 = getelementptr inbounds i32, ptr %c, i32 %i.0.11020 %tmp8 = load i32, ptr %arrayidx1.2, align 41021 %mul.2 = mul nsw i32 %tmp8, %tmp71022 %arrayidx2.2 = getelementptr inbounds i32, ptr %a, i32 %i.0.11023 store i32 %mul.2, ptr %arrayidx2.2, align 41024 %i.0.2 = add i32 %i.010, -31025 %arrayidx.3 = getelementptr inbounds i32, ptr %b, i32 %i.0.21026 %tmp9 = load i32, ptr %arrayidx.3, align 41027 %arrayidx1.3 = getelementptr inbounds i32, ptr %c, i32 %i.0.21028 %tmp10 = load i32, ptr %arrayidx1.3, align 41029 %mul.3 = mul nsw i32 %tmp10, %tmp91030 %arrayidx2.3 = getelementptr inbounds i32, ptr %a, i32 %i.0.21031 store i32 %mul.3, ptr %arrayidx2.3, align 41032 %i.0.3 = add i32 %i.010, -41033 %cmp.3 = icmp sgt i32 %i.0.3, -11034 br i1 %cmp.3, label %for.body, label %for.cond.cleanup1035}1036 1037; CHECK-LABEL: mul32x32_forwards1038; CHECK: @ %for.body1039 1040; TODO: Would be good for the complexity limit didn't have to be increased to1041; enable the pre-indexed accesses.1042 1043; CHECK-DEFAULT-NOT: ldr{{.*}}]!1044; CHECK-DEFAULT-NOT: str{{.*}}]!1045 1046; CHECK-COMPLEX: ldr{{.*}}, #16]!1047; CHECK-COMPLEX: ldr{{.*}}, #16]!1048; CHECK-COMPLEX: str{{.*}}, #16]!1049 1050; CHECK-T2: @ %for.body.epil1051; CHECK-T2: ldr{{.*}}, #4]!1052; CHECK-T2: ldr{{.*}}, #4]!1053; CHECK-T2: str{{.*}}, #4]!1054 1055define void @mul32x32_forwards(ptr nocapture %a, ptr nocapture readonly %b, ptr nocapture readonly %c, i32 %N) {1056entry:1057 %cmp8 = icmp eq i32 %N, 01058 br i1 %cmp8, label %for.cond.cleanup, label %for.body.preheader1059 1060for.body.preheader: ; preds = %entry1061 %tmp = add i32 %N, -11062 %xtraiter = and i32 %N, 31063 %tmp1 = icmp ult i32 %tmp, 31064 br i1 %tmp1, label %for.cond.cleanup.loopexit.unr-lcssa, label %for.body.preheader.new1065 1066for.body.preheader.new: ; preds = %for.body.preheader1067 %unroll_iter = sub i32 %N, %xtraiter1068 br label %for.body1069 1070for.cond.cleanup.loopexit.unr-lcssa: ; preds = %for.body, %for.body.preheader1071 %i.09.unr = phi i32 [ 0, %for.body.preheader ], [ %inc.3, %for.body ]1072 %lcmp.mod = icmp eq i32 %xtraiter, 01073 br i1 %lcmp.mod, label %for.cond.cleanup, label %for.body.epil1074 1075for.body.epil: ; preds = %for.body.epil, %for.cond.cleanup.loopexit.unr-lcssa1076 %i.09.epil = phi i32 [ %inc.epil, %for.body.epil ], [ %i.09.unr, %for.cond.cleanup.loopexit.unr-lcssa ]1077 %epil.iter = phi i32 [ %epil.iter.sub, %for.body.epil ], [ %xtraiter, %for.cond.cleanup.loopexit.unr-lcssa ]1078 %arrayidx.epil = getelementptr inbounds i32, ptr %b, i32 %i.09.epil1079 %tmp2 = load i32, ptr %arrayidx.epil, align 41080 %arrayidx1.epil = getelementptr inbounds i32, ptr %c, i32 %i.09.epil1081 %tmp3 = load i32, ptr %arrayidx1.epil, align 41082 %mul.epil = mul nsw i32 %tmp3, %tmp21083 %arrayidx2.epil = getelementptr inbounds i32, ptr %a, i32 %i.09.epil1084 store i32 %mul.epil, ptr %arrayidx2.epil, align 41085 %inc.epil = add nuw nsw i32 %i.09.epil, 11086 %epil.iter.sub = add i32 %epil.iter, -11087 %epil.iter.cmp = icmp eq i32 %epil.iter.sub, 01088 br i1 %epil.iter.cmp, label %for.cond.cleanup, label %for.body.epil1089 1090for.cond.cleanup: ; preds = %for.body.epil, %for.cond.cleanup.loopexit.unr-lcssa, %entry1091 ret void1092 1093for.body: ; preds = %for.body, %for.body.preheader.new1094 %i.09 = phi i32 [ 0, %for.body.preheader.new ], [ %inc.3, %for.body ]1095 %niter = phi i32 [ %unroll_iter, %for.body.preheader.new ], [ %niter.nsub.3, %for.body ]1096 %arrayidx = getelementptr inbounds i32, ptr %b, i32 %i.091097 %tmp4 = load i32, ptr %arrayidx, align 41098 %arrayidx1 = getelementptr inbounds i32, ptr %c, i32 %i.091099 %tmp5 = load i32, ptr %arrayidx1, align 41100 %mul = mul nsw i32 %tmp5, %tmp41101 %arrayidx2 = getelementptr inbounds i32, ptr %a, i32 %i.091102 store i32 %mul, ptr %arrayidx2, align 41103 %inc = or disjoint i32 %i.09, 11104 %arrayidx.1 = getelementptr inbounds i32, ptr %b, i32 %inc1105 %tmp6 = load i32, ptr %arrayidx.1, align 41106 %arrayidx1.1 = getelementptr inbounds i32, ptr %c, i32 %inc1107 %tmp7 = load i32, ptr %arrayidx1.1, align 41108 %mul.1 = mul nsw i32 %tmp7, %tmp61109 %arrayidx2.1 = getelementptr inbounds i32, ptr %a, i32 %inc1110 store i32 %mul.1, ptr %arrayidx2.1, align 41111 %inc.1 = or disjoint i32 %i.09, 21112 %arrayidx.2 = getelementptr inbounds i32, ptr %b, i32 %inc.11113 %tmp8 = load i32, ptr %arrayidx.2, align 41114 %arrayidx1.2 = getelementptr inbounds i32, ptr %c, i32 %inc.11115 %tmp9 = load i32, ptr %arrayidx1.2, align 41116 %mul.2 = mul nsw i32 %tmp9, %tmp81117 %arrayidx2.2 = getelementptr inbounds i32, ptr %a, i32 %inc.11118 store i32 %mul.2, ptr %arrayidx2.2, align 41119 %inc.2 = or disjoint i32 %i.09, 31120 %arrayidx.3 = getelementptr inbounds i32, ptr %b, i32 %inc.21121 %tmp10 = load i32, ptr %arrayidx.3, align 41122 %arrayidx1.3 = getelementptr inbounds i32, ptr %c, i32 %inc.21123 %tmp11 = load i32, ptr %arrayidx1.3, align 41124 %mul.3 = mul nsw i32 %tmp11, %tmp101125 %arrayidx2.3 = getelementptr inbounds i32, ptr %a, i32 %inc.21126 store i32 %mul.3, ptr %arrayidx2.3, align 41127 %inc.3 = add nuw nsw i32 %i.09, 41128 %niter.nsub.3 = add i32 %niter, -41129 %niter.ncmp.3 = icmp eq i32 %niter.nsub.3, 01130 br i1 %niter.ncmp.3, label %for.cond.cleanup.loopexit.unr-lcssa, label %for.body1131}1132