1; RUN: opt %loadPolly -pass-remarks-analysis="polly-scops" -polly-scops \ 2; RUN: -polly-precise-inbounds -disable-output < %s 2>&1 | FileCheck %s 3; 4; CHECK: remark: <unknown>:0:0: SCoP begins here. 5; CHECK-NEXT: remark: <unknown>:0:0: Use user assumption: [i, N, M] -> { : N <= i or (N > i and N >= 0) } 6; CHECK-NEXT: remark: <unknown>:0:0: Inbounds assumption: [i, N, M] -> { : N <= i or (N > i and M <= 100) } 7; CHECK-NEXT: remark: <unknown>:0:0: SCoP ends here. 8; 9; void f(int *restrict A, int *restrict B, int i, int N, int M, int C[100][100]) { 10; for (; i < N; i++) { 11; __builtin_assume(N >= 0); 12; for (int j = 0; j != M; j++) { 13; __builtin_assume(N >= 0); 14; C[i][j] += A[i * M + j] + B[i + j]; 15; } 16; } 17; } 18; 19 20 21; RUN: opt %loadPolly -pass-remarks-analysis="polly-scops" -polly-scops \ 22; RUN: -polly-precise-inbounds -disable-output < %s 2>&1 -pass-remarks-output=%t.yaml 23; RUN: cat %t.yaml | FileCheck -check-prefix=YAML %s 24; YAML: --- !Analysis 25; YAML: Pass: polly-scops 26; YAML: Name: ScopEntry 27; YAML: Function: f 28; YAML: Args: 29; YAML: - String: SCoP begins here. 30; YAML: ... 31; YAML: --- !Analysis 32; YAML: Pass: polly-scops 33; YAML: Name: UserAssumption 34; YAML: Function: f 35; YAML: Args: 36; YAML: - String: 'Use user assumption: ' 37; YAML: - String: '[i, N, M] -> { : N <= i or (N > i and N >= 0) }' 38; YAML: ... 39; YAML: --- !Analysis 40; YAML: Pass: polly-scops 41; YAML: Name: AssumpRestrict 42; YAML: Function: f 43; YAML: Args: 44; YAML: - String: 'Inbounds assumption: [i, N, M] -> { : N <= i or (N > i and M <= 100) }' 45; YAML: ... 46; YAML: --- !Analysis 47; YAML: Pass: polly-scops 48; YAML: Name: ScopEnd 49; YAML: Function: f 50; YAML: Args: 51; YAML: - String: SCoP ends here. 52; YAML: ... 53 54target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128" 55 56define void @f(i32* noalias %A, i32* noalias %B, i32 %i, i32 %N, i32 %M, [100 x i32]* %C) { 57entry: 58 %tmp = zext i32 %M to i64 59 %tmp6 = sext i32 %i to i64 60 %tmp7 = sext i32 %N to i64 61 %tmp8 = sext i32 %M to i64 62 br label %for.cond 63 64for.cond: ; preds = %for.inc.15, %entry 65 %indvars.iv3 = phi i64 [ %indvars.iv.next4, %for.inc.15 ], [ %tmp6, %entry ] 66 %cmp = icmp slt i64 %indvars.iv3, %tmp7 67 br i1 %cmp, label %for.body, label %for.end.17 68 69for.body: ; preds = %for.cond 70 %cmp1 = icmp sgt i32 %N, -1 71 call void @llvm.assume(i1 %cmp1) 72 br label %for.cond.2 73 74for.cond.2: ; preds = %for.inc, %for.body 75 %indvars.iv = phi i64 [ %indvars.iv.next, %for.inc ], [ 0, %for.body ] 76 %cmp3 = icmp eq i64 %indvars.iv, %tmp 77 br i1 %cmp3, label %for.end, label %for.body.4 78 79for.body.4: ; preds = %for.cond.2 80 %tmp9 = mul nsw i64 %indvars.iv3, %tmp8 81 %tmp10 = add nsw i64 %tmp9, %indvars.iv 82 %arrayidx = getelementptr inbounds i32, i32* %A, i64 %tmp10 83 %tmp11 = load i32, i32* %arrayidx, align 4 84 %tmp12 = add nsw i64 %indvars.iv3, %indvars.iv 85 %arrayidx8 = getelementptr inbounds i32, i32* %B, i64 %tmp12 86 %tmp13 = load i32, i32* %arrayidx8, align 4 87 %add9 = add nsw i32 %tmp11, %tmp13 88 %arrayidx13 = getelementptr inbounds [100 x i32], [100 x i32]* %C, i64 %indvars.iv3, i64 %indvars.iv 89 %tmp14 = load i32, i32* %arrayidx13, align 4 90 %add14 = add nsw i32 %tmp14, %add9 91 store i32 %add14, i32* %arrayidx13, align 4 92 br label %for.inc 93 94for.inc: ; preds = %for.body.4 95 %indvars.iv.next = add nuw nsw i64 %indvars.iv, 1 96 br label %for.cond.2 97 98for.end: ; preds = %for.cond.2 99 br label %for.inc.15 100 101for.inc.15: ; preds = %for.end 102 %indvars.iv.next4 = add nsw i64 %indvars.iv3, 1 103 br label %for.cond 104 105for.end.17: ; preds = %for.cond 106 ret void 107} 108 109declare void @llvm.assume(i1) #1 110 111