1
- ; RUN: opt -passes='print<access-info>' -disable-output < %s 2>&1 | FileCheck %s
1
+ ; NOTE: Assertions have been autogenerated by utils/update_analyze_test_checks.py UTC_ARGS: --version 5
2
+ ; RUN: opt -passes='print<access-info>' -disable-output %s 2>&1 | FileCheck %s
2
3
3
4
; Analyze this loop:
4
5
; for (i = 0; i < n; i++)
5
6
; A[i + 1] = A[i] * B[i] * C[i];
6
7
7
- target datalayout = "e-m:o-i64:64-f80:128-n8:16:32:64-S128"
8
-
9
- ; CHECK: for.body:
10
- ; CHECK: Has convergent operation in loop
11
- ; CHECK: Report: cannot add control dependency to convergent operation
12
- ; CHECK-NEXT: Dependences:
13
- ; CHECK-NEXT: Backward:
14
- ; CHECK-NEXT: %loadA = load i16, ptr %arrayidxA, align 2 ->
15
- ; CHECK-NEXT: store i16 %mul1, ptr %arrayidxA_plus_2, align 2
16
- ; CHECK: Run-time memory checks:
17
- ; CHECK-NEXT: 0:
18
- ; CHECK-NEXT: Comparing group
19
- ; CHECK-NEXT: %arrayidxA = getelementptr inbounds i16, ptr %a, i64 %storemerge3
20
- ; CHECK-NEXT: %arrayidxA_plus_2 = getelementptr inbounds i16, ptr %a, i64 %add
21
- ; CHECK-NEXT: Against group
22
- ; CHECK-NEXT: %arrayidxB = getelementptr inbounds i16, ptr %b, i64 %storemerge3
23
- ; CHECK-NEXT: 1:
24
- ; CHECK-NEXT: Comparing group
25
- ; CHECK-NEXT: %arrayidxA = getelementptr inbounds i16, ptr %a, i64 %storemerge3
26
- ; CHECK-NEXT: %arrayidxA_plus_2 = getelementptr inbounds i16, ptr %a, i64 %add
27
- ; CHECK-NEXT: Against group
28
- ; CHECK-NEXT: %arrayidxC = getelementptr inbounds i16, ptr %c, i64 %storemerge3
29
-
30
- @B = common global ptr null , align 8
31
- @A = common global ptr null , align 8
32
- @C = common global ptr null , align 8
33
-
34
- define void @f () #1 {
8
+ ; In this case, runtime checks are needed, and there is a convergent operation.
9
+ define void @rtchecks_needed (ptr %a , ptr %b , ptr %c ) {
10
+ ; CHECK-LABEL: 'rtchecks_needed'
11
+ ; CHECK-NEXT: for.body:
12
+ ; CHECK-NEXT: Has convergent operation in loop
13
+ ; CHECK-NEXT: Report: cannot add control dependency to convergent operation
14
+ ; CHECK-NEXT: Dependences:
15
+ ; CHECK-NEXT: Backward:
16
+ ; CHECK-NEXT: %loadA = load i16, ptr %arrayidxA, align 2 ->
17
+ ; CHECK-NEXT: store i16 %mul1, ptr %arrayidxA_plus_2, align 2
18
+ ; CHECK-EMPTY:
19
+ ; CHECK-NEXT: Run-time memory checks:
20
+ ; CHECK-NEXT: Check 0:
21
+ ; CHECK-NEXT: Comparing group ([[GRP1:0x[0-9a-f]+]]):
22
+ ; CHECK-NEXT: %arrayidxA = getelementptr inbounds i16, ptr %a, i64 %storemerge3
23
+ ; CHECK-NEXT: %arrayidxA_plus_2 = getelementptr inbounds i16, ptr %a, i64 %add
24
+ ; CHECK-NEXT: Against group ([[GRP2:0x[0-9a-f]+]]):
25
+ ; CHECK-NEXT: %arrayidxB = getelementptr inbounds i16, ptr %b, i64 %storemerge3
26
+ ; CHECK-NEXT: Check 1:
27
+ ; CHECK-NEXT: Comparing group ([[GRP1]]):
28
+ ; CHECK-NEXT: %arrayidxA = getelementptr inbounds i16, ptr %a, i64 %storemerge3
29
+ ; CHECK-NEXT: %arrayidxA_plus_2 = getelementptr inbounds i16, ptr %a, i64 %add
30
+ ; CHECK-NEXT: Against group ([[GRP3:0x[0-9a-f]+]]):
31
+ ; CHECK-NEXT: %arrayidxC = getelementptr inbounds i16, ptr %c, i64 %storemerge3
32
+ ; CHECK-NEXT: Grouped accesses:
33
+ ; CHECK-NEXT: Group [[GRP1]]:
34
+ ; CHECK-NEXT: (Low: %a High: (42 + %a))
35
+ ; CHECK-NEXT: Member: {%a,+,2}<nuw><%for.body>
36
+ ; CHECK-NEXT: Member: {(2 + %a),+,2}<nw><%for.body>
37
+ ; CHECK-NEXT: Group [[GRP2]]:
38
+ ; CHECK-NEXT: (Low: %b High: (40 + %b))
39
+ ; CHECK-NEXT: Member: {%b,+,2}<nuw><%for.body>
40
+ ; CHECK-NEXT: Group [[GRP3]]:
41
+ ; CHECK-NEXT: (Low: %c High: (40 + %c))
42
+ ; CHECK-NEXT: Member: {%c,+,2}<nuw><%for.body>
43
+ ; CHECK-EMPTY:
44
+ ; CHECK-NEXT: Non vectorizable stores to invariant address were not found in loop.
45
+ ; CHECK-NEXT: SCEV assumptions:
46
+ ; CHECK-EMPTY:
47
+ ; CHECK-NEXT: Expressions re-written:
48
+ ;
35
49
entry:
36
- %a = load ptr , ptr @A , align 8
37
- %b = load ptr , ptr @B , align 8
38
- %c = load ptr , ptr @C , align 8
39
50
br label %for.body
40
51
41
52
for.body: ; preds = %for.body, %entry
@@ -50,7 +61,7 @@ for.body: ; preds = %for.body, %entry
50
61
%arrayidxC = getelementptr inbounds i16 , ptr %c , i64 %storemerge3
51
62
%loadC = load i16 , ptr %arrayidxC , align 2
52
63
53
- call void @llvm.convergent ()
64
+ call i16 @llvm.convergent (i16 %loadC )
54
65
55
66
%mul = mul i16 %loadB , %loadA
56
67
%mul1 = mul i16 %mul , %loadC
@@ -66,7 +77,62 @@ for.end: ; preds = %for.body
66
77
ret void
67
78
}
68
79
69
- declare void @llvm.convergent () #0
80
+ ; In this case, no runtime checks are needed, and there is a convergent operation.
81
+ define void @no_rtchecks (ptr noalias %a , ptr noalias %b , ptr noalias %c , ptr noalias %d , ptr noalias %e ) {
82
+ ; CHECK-LABEL: 'no_rtchecks'
83
+ ; CHECK-NEXT: for.body:
84
+ ; CHECK-NEXT: Has convergent operation in loop
85
+ ; CHECK-NEXT: Report: cannot add control dependency to convergent operation
86
+ ; CHECK-NEXT: Dependences:
87
+ ; CHECK-NEXT: Backward:
88
+ ; CHECK-NEXT: %loadA = load i16, ptr %arrayidxA, align 4 ->
89
+ ; CHECK-NEXT: store i16 %mulA, ptr %arrayidxA_plus_4, align 4
90
+ ; CHECK-EMPTY:
91
+ ; CHECK-NEXT: Run-time memory checks:
92
+ ; CHECK-NEXT: Grouped accesses:
93
+ ; CHECK-EMPTY:
94
+ ; CHECK-NEXT: Non vectorizable stores to invariant address were not found in loop.
95
+ ; CHECK-NEXT: SCEV assumptions:
96
+ ; CHECK-EMPTY:
97
+ ; CHECK-NEXT: Expressions re-written:
98
+ ;
99
+ entry:
100
+ br label %for.body
101
+
102
+ for.body: ; preds = %for.body, %entry
103
+ %ind = phi i64 [ 0 , %entry ], [ %add , %for.body ]
104
+
105
+ %arrayidxA = getelementptr inbounds i16 , ptr %a , i64 %ind
106
+ %loadA = load i16 , ptr %arrayidxA , align 4
107
+
108
+ %arrayidxB = getelementptr inbounds i16 , ptr %b , i64 %ind
109
+ %loadB = load i16 , ptr %arrayidxB , align 4
110
+
111
+ %mulA = mul i16 %loadB , %loadA
112
+
113
+ %add = add nuw nsw i64 %ind , 1
114
+ %arrayidxA_plus_4 = getelementptr inbounds i16 , ptr %a , i64 %add
115
+ store i16 %mulA , ptr %arrayidxA_plus_4 , align 4
116
+
117
+ %arrayidxD = getelementptr inbounds i16 , ptr %d , i64 %ind
118
+ %loadD = load i16 , ptr %arrayidxD , align 4
119
+
120
+ %arrayidxE = getelementptr inbounds i16 , ptr %e , i64 %ind
121
+ %loadE = load i16 , ptr %arrayidxE , align 4
122
+
123
+ %convergentD = call i16 @llvm.convergent (i16 %loadD )
124
+ %mulC = mul i16 %convergentD , %loadE
125
+
126
+ %arrayidxC = getelementptr inbounds i16 , ptr %c , i64 %ind
127
+ store i16 %mulC , ptr %arrayidxC , align 4
128
+
129
+ %exitcond = icmp eq i64 %add , 20
130
+ br i1 %exitcond , label %for.end , label %for.body
131
+
132
+ for.end: ; preds = %for.body
133
+ ret void
134
+ }
135
+
136
+ declare i16 @llvm.convergent (i16 ) #0
70
137
71
138
attributes #0 = { nounwind readnone convergent }
72
- attributes #1 = { nounwind convergent }
0 commit comments