<div dir="ltr"><span style="font-size:12.8000001907349px">Hi, </span><div style="font-size:12.8000001907349px"><br></div><div style="font-size:12.8000001907349px">I want to use loop unrolling pass, however, I find that loop unrolling will introduces conditional branch at end of every "unrolled" part. For example, consider the following code</div><div style="font-size:12.8000001907349px"><br></div><div style="font-size:12.8000001907349px"><div><i>void foo( int n, int array_x[])</i></div><div><i>{</i></div><div><i>    for (int i=0; i < n; i++)</i></div><div><i><span style="white-space:pre-wrap">        </span>    array_x[i] = i; </i></div><div><i>}</i></div></div><div style="font-size:12.8000001907349px"><br></div><div style="font-size:12.8000001907349px">Then I use this command "opt-3.5 try.bc -mem2reg -loops -loop-simplify -loop-rotate -lcssa -indvars -loop-unroll -unroll-count=3 -simplifycfg -S", it gives me this IR:</div><div style="font-size:12.8000001907349px"><br></div><div style="font-size:12.8000001907349px"><div><i>define void @_Z3fooiPi(i32 %n, i32* %array_x) #0 {</i></div><div><i>  %1 = icmp slt i32 0, %n</i></div><div><i>  br i1 %1, label %.<a href="http://lr.ph/" target="_blank">lr.ph</a>, label %._crit_edge</i></div><div><i><br></i></div><div><i>.<a href="http://lr.ph/" target="_blank">lr.ph</a>:                                           ; preds = %0, %7</i></div><div><i>  %indvars.iv = phi i64 [ %indvars.iv.next.2, %7 ], [ 0, %0 ]</i></div><div><i>  %2 = getelementptr inbounds i32* %array_x, i64 %indvars.iv</i></div><div><i>  %3 = trunc i64 %indvars.iv to i32</i></div><div><i>  store i32 %3, i32* %2</i></div><div><i>  %indvars.iv.next = add nuw nsw i64 %indvars.iv, 1</i></div><div><i>  %lftr.wideiv = trunc i64 %indvars.iv.next to i32</i></div><div><i>  %exitcond = icmp ne i32 %lftr.wideiv, %n</i></div><div><i>  br i1 %exitcond, label %4, label %._crit_edge</i></div><div><i><br></i></div><div><i>._crit_edge:                                      ; preds = %.<a href="http://lr.ph/" target="_blank">lr.ph</a>, %4, %7, %0</i></div><div><i>  ret void</i></div><div><i><br></i></div><div><i>; <label>:4                                       ; preds = %.<a href="http://lr.ph/" target="_blank">lr.ph</a></i></div><div><i>  %5 = getelementptr inbounds i32* %array_x, i64 %indvars.iv.next</i></div><div><i>  %6 = trunc i64 %indvars.iv.next to i32</i></div><div><i>  store i32 %6, i32* %5</i></div><div><i>  %indvars.iv.next.1 = add nuw nsw i64 %indvars.iv.next, 1</i></div><div><i>  %lftr.wideiv.1 = trunc i64 %indvars.iv.next.1 to i32</i></div><div><i>  %exitcond.1 = icmp ne i32 %lftr.wideiv.1, %n</i></div><div><i>  br i1 %exitcond.1, label %7, label %._crit_edge</i></div><div><i><br></i></div><div><i>; <label>:7                                       ; preds = %4</i></div><div><i>  %8 = getelementptr inbounds i32* %array_x, i64 %indvars.iv.next.1</i></div><div><i>  %9 = trunc i64 %indvars.iv.next.1 to i32</i></div><div><i>  store i32 %9, i32* %8</i></div><div><i>  %indvars.iv.next.2 = add nuw nsw i64 %indvars.iv.next.1, 1</i></div><div><i>  %lftr.wideiv.2 = trunc i64 %indvars.iv.next.2 to i32</i></div><div><i>  %exitcond.2 = icmp ne i32 %lftr.wideiv.2, %n</i></div><div><i>  br i1 %exitcond.2, label %.<a href="http://lr.ph/" target="_blank">lr.ph</a>, label %._crit_edge</i></div><div><i>}</i></div></div><div style="font-size:12.8000001907349px"><br></div><div style="font-size:12.8000001907349px">As you can see, at the end of BB <label>4 and BB<label>7 there are "add", "icmp" and "br" instrcutions to check the boundary. I understand this is for the correctness. However, I would expect the loop unrolling can change my code to something like this:</div><div style="font-size:12.8000001907349px"><br></div><div style="font-size:12.8000001907349px"><div><i>void foo( int n, int array_x[])</i></div><div><i>{</i></div><div><i>    int j = n%3;</i></div><div><i>    int m = n - j;</i></div><div><i>    for (int i=0; i < m; i+=3){</i></div><div><i><span style="white-space:pre-wrap">   </span>    array_x[i] = i;</i></div><div><i><span style="white-space:pre-wrap">        </span>    array_x[i+1] = i+1;</i></div><div><i><span style="white-space:pre-wrap">    </span>    array_x[i+2] = i+2; </i></div><div><i>    }</i></div><div><i>    for(i=m; i<n; i++)</i></div><div><i><span style="white-space:pre-wrap">    </span>    array_x[i] = i;        </i></div><div><i>}</i></div></div><div style="font-size:12.8000001907349px"><br></div><div style="font-size:12.8000001907349px">In this case, the BB<label>4 and BB<label>7 will do not have the "add", "icmp" and "br" instructions because these BBs can be merged together.</div><div style="font-size:12.8000001907349px"><br></div><div style="font-size:12.8000001907349px">How can I achieve this? Thanks.</div><div style="font-size:12.8000001907349px"><br></div><div style="font-size:12.8000001907349px">Regards,</div><div style="font-size:12.8000001907349px"><br></div><div style="font-size:12.8000001907349px">Xiangyang</div></div>