1 2; RUN: opt %s -analyze -scalar-evolution -enable-new-pm=0 -scalar-evolution-classify-expressions=0 2>&1 | FileCheck %s 3 4target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128" 5target triple = "x86_64-unknown-linux-gnu" 6 7; A collection of tests focused on exercising logic to prove no-unsigned wrap 8; from mustprogress semantics of loops. 9 10; CHECK: Determining loop execution counts for: @test 11; CHECK: Loop %for.body: Unpredictable backedge-taken count. 12; CHECK: Determining loop execution counts for: @test_preinc 13; CHECK: Loop %for.body: Unpredictable backedge-taken count. 14; CHECK: Determining loop execution counts for: @test_well_defined_infinite_st 15; CHECK: Loop %for.body: Unpredictable backedge-taken count. 16; CHECK: Determining loop execution counts for: @test_well_defined_infinite_ld 17; CHECK: Loop %for.body: Unpredictable backedge-taken count. 18; CHECK: Determining loop execution counts for: @test_no_mustprogress 19; CHECK: Loop %for.body: Unpredictable backedge-taken count. 20; CHECK: Determining loop execution counts for: @test_1024 21; CHECK: Loop %for.body: Unpredictable backedge-taken count. 22; CHECK: Determining loop execution counts for: @test_uneven_divide 23; CHECK: Loop %for.body: backedge-taken count is (-1 + (-1431655765 * %N)) 24; CHECK: Determining loop execution counts for: @test_non_invariant_rhs 25; CHECK: Loop %for.body: Unpredictable backedge-taken count. 26; CHECK: Determining loop execution counts for: @test_abnormal_exit 27; CHECK: Loop %for.body: Unpredictable backedge-taken count. 28; CHECK: Determining loop execution counts for: @test_other_exit 29; CHECK: Loop %for.body: <multiple exits> Unpredictable backedge-taken count. 30 31define void @test(i32 %N) mustprogress { 32entry: 33 br label %for.body 34 35for.body: 36 %iv = phi i32 [ %iv.next, %for.body ], [ 0, %entry ] 37 %iv.next = add i32 %iv, 2 38 %cmp = icmp ne i32 %iv.next, %N 39 br i1 %cmp, label %for.body, label %for.cond.cleanup 40 41for.cond.cleanup: 42 ret void 43} 44 45define void @test_preinc(i32 %N) mustprogress { 46entry: 47 br label %for.body 48 49for.body: 50 %iv = phi i32 [ %iv.next, %for.body ], [ 0, %entry ] 51 %iv.next = add i32 %iv, 2 52 %cmp = icmp ne i32 %iv, %N 53 br i1 %cmp, label %for.body, label %for.cond.cleanup 54 55for.cond.cleanup: 56 ret void 57 58} 59 60@G = external global i32 61 62define void @test_well_defined_infinite_st(i32 %N) mustprogress { 63entry: 64 br label %for.body 65 66for.body: 67 %iv = phi i32 [ %iv.next, %for.body ], [ 0, %entry ] 68 %iv.next = add i32 %iv, 2 69 store volatile i32 0, i32* @G 70 %cmp = icmp ne i32 %iv.next, %N 71 br i1 %cmp, label %for.body, label %for.cond.cleanup 72 73for.cond.cleanup: 74 ret void 75} 76 77define void @test_well_defined_infinite_ld(i32 %N) mustprogress { 78entry: 79 br label %for.body 80 81for.body: 82 %iv = phi i32 [ %iv.next, %for.body ], [ 0, %entry ] 83 %iv.next = add i32 %iv, 2 84 %val = load volatile i32, i32* @G 85 %cmp = icmp ne i32 %iv.next, %N 86 br i1 %cmp, label %for.body, label %for.cond.cleanup 87 88for.cond.cleanup: 89 ret void 90} 91 92define void @test_no_mustprogress(i32 %N) { 93entry: 94 br label %for.body 95 96for.body: 97 %iv = phi i32 [ %iv.next, %for.body ], [ 0, %entry ] 98 %iv.next = add i32 %iv, 2 99 %cmp = icmp ne i32 %iv.next, %N 100 br i1 %cmp, label %for.body, label %for.cond.cleanup 101 102for.cond.cleanup: 103 ret void 104 105} 106 107 108define void @test_1024(i32 %N) mustprogress { 109entry: 110 br label %for.body 111 112for.body: 113 %iv = phi i32 [ %iv.next, %for.body ], [ 0, %entry ] 114 %iv.next = add i32 %iv, 1024 115 %cmp = icmp ne i32 %iv.next, %N 116 br i1 %cmp, label %for.body, label %for.cond.cleanup 117 118for.cond.cleanup: 119 ret void 120} 121 122define void @test_uneven_divide(i32 %N) mustprogress { 123entry: 124 br label %for.body 125 126for.body: 127 %iv = phi i32 [ %iv.next, %for.body ], [ 0, %entry ] 128 %iv.next = add i32 %iv, 3 129 %cmp = icmp ne i32 %iv.next, %N 130 br i1 %cmp, label %for.body, label %for.cond.cleanup 131 132for.cond.cleanup: 133 ret void 134} 135 136define void @test_non_invariant_rhs() mustprogress { 137entry: 138 br label %for.body 139 140for.body: 141 %iv = phi i32 [ %iv.next, %for.body ], [ 0, %entry ] 142 %iv.next = add i32 %iv, 2 143 %N = load i32, i32* @G 144 %cmp = icmp ne i32 %iv.next, %N 145 br i1 %cmp, label %for.body, label %for.cond.cleanup 146 147for.cond.cleanup: 148 ret void 149} 150 151declare void @mayexit() 152 153define void @test_abnormal_exit(i32 %N) mustprogress { 154entry: 155 br label %for.body 156 157for.body: 158 %iv = phi i32 [ %iv.next, %for.body ], [ 0, %entry ] 159 %iv.next = add i32 %iv, 2 160 call void @mayexit() 161 %cmp = icmp ne i32 %iv.next, %N 162 br i1 %cmp, label %for.body, label %for.cond.cleanup 163 164for.cond.cleanup: 165 ret void 166} 167 168 169define void @test_other_exit(i32 %N) mustprogress { 170entry: 171 br label %for.body 172 173for.body: 174 %iv = phi i32 [ %iv.next, %for.latch ], [ 0, %entry ] 175 %iv.next = add i32 %iv, 2 176 %cmp1 = icmp ne i32 %iv.next, 20 177 br i1 %cmp1, label %for.latch, label %for.cond.cleanup 178 179for.latch: 180 %cmp2 = icmp ne i32 %iv.next, %N 181 br i1 %cmp2, label %for.body, label %for.cond.cleanup 182 183for.cond.cleanup: 184 ret void 185} 186 187 188