blob: a6235b8be8a8cea433b0c40301b1d4d736bc8366 [file] [log] [blame]
Aart Bik38a3f212017-10-20 17:02:21 -07001/*
2 * Copyright (C) 2017 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17/**
18 * Tests for zero vectorization.
19 */
20public class Main {
21
22 /// CHECK-START: void Main.staticallyAligned(int[]) loop_optimization (before)
23 /// CHECK-DAG: <<Par:l\d+>> ParameterValue loop:none
24 /// CHECK-DAG: <<One:i\d+>> IntConstant 1 loop:none
25 /// CHECK-DAG: <<Phi:i\d+>> Phi [<<One>>,<<AddI:i\d+>>] loop:<<Loop:B\d+>> outer_loop:none
26 /// CHECK-DAG: <<Get:i\d+>> ArrayGet [<<Par>>,<<Phi>>] loop:<<Loop>> outer_loop:none
27 /// CHECK-DAG: <<Add:i\d+>> Add [<<Get>>,<<One>>] loop:<<Loop>> outer_loop:none
28 /// CHECK-DAG: ArraySet [<<Par>>,<<Phi>>,<<Add>>] loop:<<Loop>> outer_loop:none
29 /// CHECK-DAG: <<AddI>> Add [<<Phi>>,<<One>>] loop:<<Loop>> outer_loop:none
30 //
31 /// CHECK-START-ARM: void Main.staticallyAligned(int[]) loop_optimization (after)
32 /// CHECK-DAG: <<Par:l\d+>> ParameterValue loop:none
33 /// CHECK-DAG: <<Zero:i\d+>> IntConstant 0 loop:none
34 /// CHECK-DAG: <<One:i\d+>> IntConstant 1 loop:none
35 /// CHECK-DAG: <<Vl:i\d+>> IntConstant 2 loop:none
36 /// CHECK-DAG: <<Repl:d\d+>> VecReplicateScalar [<<One>>] loop:none
37 /// CHECK-DAG: <<Phi:i\d+>> Phi [<<Zero>>,<<AddI:i\d+>>] loop:<<Loop:B\d+>> outer_loop:none
38 /// CHECK-DAG: <<Nrm:i\d+>> Add [<<Phi>>,<<One>>] loop:<<Loop>> outer_loop:none
39 /// CHECK-DAG: <<Load:d\d+>> VecLoad [<<Par>>,<<Nrm>>] alignment:ALIGN(8,0) loop:<<Loop>> outer_loop:none
40 /// CHECK-DAG: <<Add:d\d+>> VecAdd [<<Load>>,<<Repl>>] loop:<<Loop>> outer_loop:none
41 /// CHECK-DAG: VecStore [<<Par>>,<<Nrm>>,<<Add>>] alignment:ALIGN(8,0) loop:<<Loop>> outer_loop:none
42 /// CHECK-DAG: <<AddI>> Add [<<Phi>>,<<Vl>>] loop:<<Loop>> outer_loop:none
43 //
44 /// CHECK-NOT: ArrayGet
45 /// CHECK-NOT: ArraySet
46 static void staticallyAligned(int[] a) {
47 // Starts at offset 12 (hidden) + 1 * 4 relative to base alignment.
48 // So no peeling, aligned vector, no cleanup.
49 for (int i = 1; i < 9; i++) {
50 a[i] += 1;
51 }
52 }
53
54 /// CHECK-START: void Main.staticallyAlignedN(int[]) loop_optimization (before)
55 /// CHECK-DAG: <<One:i\d+>> IntConstant 1 loop:none
56 /// CHECK-DAG: <<Par:l\d+>> NullCheck loop:none
57 /// CHECK-DAG: <<Phi:i\d+>> Phi [<<One>>,<<AddI:i\d+>>] loop:<<Loop:B\d+>> outer_loop:none
58 /// CHECK-DAG: <<Get:i\d+>> ArrayGet [<<Par>>,<<Phi>>] loop:<<Loop>> outer_loop:none
59 /// CHECK-DAG: <<Add:i\d+>> Add [<<Get>>,<<One>>] loop:<<Loop>> outer_loop:none
60 /// CHECK-DAG: ArraySet [<<Par>>,<<Phi>>,<<Add>>] loop:<<Loop>> outer_loop:none
61 /// CHECK-DAG: <<AddI>> Add [<<Phi>>,<<One>>] loop:<<Loop>> outer_loop:none
62 //
63 /// CHECK-START-ARM: void Main.staticallyAlignedN(int[]) loop_optimization (after)
64 /// CHECK-DAG: <<Zero:i\d+>> IntConstant 0 loop:none
65 /// CHECK-DAG: <<One:i\d+>> IntConstant 1 loop:none
66 /// CHECK-DAG: <<Vl:i\d+>> IntConstant 2 loop:none
67 /// CHECK-DAG: <<Par:l\d+>> NullCheck loop:none
68 /// CHECK-DAG: <<Repl:d\d+>> VecReplicateScalar [<<One>>] loop:none
69 /// CHECK-DAG: <<Phi:i\d+>> Phi [<<Zero>>,<<AddI:i\d+>>] loop:<<Loop:B\d+>> outer_loop:none
70 /// CHECK-DAG: <<Nrm:i\d+>> Add [<<Phi>>,<<One>>] loop:<<Loop>> outer_loop:none
71 /// CHECK-DAG: <<Load:d\d+>> VecLoad [<<Par>>,<<Nrm>>] alignment:ALIGN(8,0) loop:<<Loop>> outer_loop:none
72 /// CHECK-DAG: <<Add:d\d+>> VecAdd [<<Load>>,<<Repl>>] loop:<<Loop>> outer_loop:none
73 /// CHECK-DAG: VecStore [<<Par>>,<<Nrm>>,<<Add>>] alignment:ALIGN(8,0) loop:<<Loop>> outer_loop:none
74 /// CHECK-DAG: <<AddI>> Add [<<Phi>>,<<Vl>>] loop:<<Loop>> outer_loop:none
75 /// CHECK-DAG: <<PhiC:i\d+>> Phi [<<Phi>>,<<AddIC:i\d+>>] loop:<<Clean:B\d+>> outer_loop:none
76 /// CHECK-DAG: <<NrmC:i\d+>> Add [<<PhiC>>,<<One>>] loop:<<Clean>> outer_loop:none
77 /// CHECK-DAG: <<Get:i\d+>> ArrayGet [<<Par>>,<<NrmC>>] loop:<<Clean>> outer_loop:none
78 /// CHECK-DAG: <<AddC:i\d+>> Add [<<Get>>,<<One>>] loop:<<Clean>> outer_loop:none
79 /// CHECK-DAG: ArraySet [<<Par>>,<<NrmC>>,<<AddC>>] loop:<<Clean>> outer_loop:none
80 /// CHECK-DAG: <<AddIC>> Add [<<PhiC>>,<<One>>] loop:<<Clean>> outer_loop:none
81 static void staticallyAlignedN(int[] a) {
82 // Starts at offset 12 (hidden) + 1 * 4 relative to base alignment.
83 // So no peeling, aligned vector, cleanup.
84 for (int i = 1; i < a.length; i++) {
85 a[i] += 1;
86 }
87 }
88
89 /// CHECK-START: void Main.staticallyMisaligned(int[]) loop_optimization (before)
90 /// CHECK-DAG: <<Par:l\d+>> ParameterValue loop:none
91 /// CHECK-DAG: <<Zero:i\d+>> IntConstant 0 loop:none
92 /// CHECK-DAG: <<One:i\d+>> IntConstant 1 loop:none
93 /// CHECK-DAG: <<Phi:i\d+>> Phi [<<Zero>>,<<AddI:i\d+>>] loop:<<Loop:B\d+>> outer_loop:none
94 /// CHECK-DAG: <<Get:i\d+>> ArrayGet [<<Par>>,<<Phi>>] loop:<<Loop>> outer_loop:none
95 /// CHECK-DAG: <<Add:i\d+>> Add [<<Get>>,<<One>>] loop:<<Loop>> outer_loop:none
96 /// CHECK-DAG: ArraySet [<<Par>>,<<Phi>>,<<Add>>] loop:<<Loop>> outer_loop:none
97 /// CHECK-DAG: <<AddI>> Add [<<Phi>>,<<One>>] loop:<<Loop>> outer_loop:none
98 //
99 /// CHECK-START-ARM: void Main.staticallyMisaligned(int[]) loop_optimization (after)
100 /// CHECK-DAG: <<Par:l\d+>> ParameterValue loop:none
101 /// CHECK-DAG: <<Zero:i\d+>> IntConstant 0 loop:none
102 /// CHECK-DAG: <<One:i\d+>> IntConstant 1 loop:none
103 /// CHECK-DAG: <<Vl:i\d+>> IntConstant 2 loop:none
104 /// CHECK-DAG: <<PhiP:i\d+>> Phi [<<Zero>>,<<AddIP:i\d+>>] loop:<<Peel:B\d+>> outer_loop:none
105 /// CHECK-DAG: <<Get:i\d+>> ArrayGet [<<Par>>,<<PhiP>>] loop:<<Peel>> outer_loop:none
106 /// CHECK-DAG: <<AddP:i\d+>> Add [<<Get>>,<<One>>] loop:<<Peel>> outer_loop:none
107 /// CHECK-DAG: ArraySet [<<Par>>,<<PhiP>>,<<AddP>>] loop:<<Peel>> outer_loop:none
108 /// CHECK-DAG: <<AddIP>> Add [<<PhiP>>,<<One>>] loop:<<Peel>> outer_loop:none
109 /// CHECK-DAG: <<Repl:d\d+>> VecReplicateScalar [<<One>>] loop:none
110 /// CHECK-DAG: <<Phi:i\d+>> Phi [<<PhiP>>,<<AddI:i\d+>>] loop:<<Loop:B\d+>> outer_loop:none
111 /// CHECK-DAG: <<Load:d\d+>> VecLoad [<<Par>>,<<Phi>>] alignment:ALIGN(8,0) loop:<<Loop>> outer_loop:none
112 /// CHECK-DAG: <<Add:d\d+>> VecAdd [<<Load>>,<<Repl>>] loop:<<Loop>> outer_loop:none
113 /// CHECK-DAG: VecStore [<<Par>>,<<Phi>>,<<Add>>] alignment:ALIGN(8,0) loop:<<Loop>> outer_loop:none
114 /// CHECK-DAG: <<AddI>> Add [<<Phi>>,<<Vl>>] loop:<<Loop>> outer_loop:none
115 //
116 /// CHECK-NOT: ArrayGet
117 /// CHECK-NOT: ArraySet
118 static void staticallyMisaligned(int[] a) {
119 // Starts at offset 12 (hidden) + 0 * 4 relative to base alignment.
120 // Yes, Art runtime misaligns the most common access pattern :-(
121 // Static peeling to the rescue, aligned vector, no cleanup.
122 for (int i = 0; i < 9; i++) {
123 a[i] += 1;
124 }
125 }
126
127 /// CHECK-START: void Main.staticallyMisalignedN(int[]) loop_optimization (before)
128 /// CHECK-DAG: <<Zero:i\d+>> IntConstant 0 loop:none
129 /// CHECK-DAG: <<One:i\d+>> IntConstant 1 loop:none
130 /// CHECK-DAG: <<Par:l\d+>> NullCheck loop:none
131 /// CHECK-DAG: <<Phi:i\d+>> Phi [<<Zero>>,<<AddI:i\d+>>] loop:<<Loop:B\d+>> outer_loop:none
132 /// CHECK-DAG: <<Get:i\d+>> ArrayGet [<<Par>>,<<Phi>>] loop:<<Loop>> outer_loop:none
133 /// CHECK-DAG: <<Add:i\d+>> Add [<<Get>>,<<One>>] loop:<<Loop>> outer_loop:none
134 /// CHECK-DAG: ArraySet [<<Par>>,<<Phi>>,<<Add>>] loop:<<Loop>> outer_loop:none
135 /// CHECK-DAG: <<AddI>> Add [<<Phi>>,<<One>>] loop:<<Loop>> outer_loop:none
136 //
137 /// CHECK-START-ARM: void Main.staticallyMisalignedN(int[]) loop_optimization (after)
138 /// CHECK-DAG: <<Zero:i\d+>> IntConstant 0 loop:none
139 /// CHECK-DAG: <<One:i\d+>> IntConstant 1 loop:none
140 /// CHECK-DAG: <<Vl:i\d+>> IntConstant 2 loop:none
141 /// CHECK-DAG: <<Par:l\d+>> NullCheck loop:none
142 /// CHECK-DAG: <<PhiP:i\d+>> Phi [<<Zero>>,<<AddIP:i\d+>>] loop:<<Peel:B\d+>> outer_loop:none
143 /// CHECK-DAG: <<GetP:i\d+>> ArrayGet [<<Par>>,<<PhiP>>] loop:<<Peel>> outer_loop:none
144 /// CHECK-DAG: <<AddP:i\d+>> Add [<<GetP>>,<<One>>] loop:<<Peel>> outer_loop:none
145 /// CHECK-DAG: ArraySet [<<Par>>,<<PhiP>>,<<AddP>>] loop:<<Peel>> outer_loop:none
146 /// CHECK-DAG: <<AddIP>> Add [<<PhiP>>,<<One>>] loop:<<Peel>> outer_loop:none
147 /// CHECK-DAG: <<Repl:d\d+>> VecReplicateScalar [<<One>>] loop:none
148 /// CHECK-DAG: <<Phi:i\d+>> Phi [<<PhiP>>,<<AddI:i\d+>>] loop:<<Loop:B\d+>> outer_loop:none
149 /// CHECK-DAG: <<Load:d\d+>> VecLoad [<<Par>>,<<Phi>>] alignment:ALIGN(8,0) loop:<<Loop>> outer_loop:none
150 /// CHECK-DAG: <<Add:d\d+>> VecAdd [<<Load>>,<<Repl>>] loop:<<Loop>> outer_loop:none
151 /// CHECK-DAG: VecStore [<<Par>>,<<Phi>>,<<Add>>] alignment:ALIGN(8,0) loop:<<Loop>> outer_loop:none
152 /// CHECK-DAG: <<AddI>> Add [<<Phi>>,<<Vl>>] loop:<<Loop>> outer_loop:none
153 /// CHECK-DAG: <<PhiC:i\d+>> Phi [<<Phi>>,<<AddIC:i\d+>>] loop:<<Clean:B\d+>> outer_loop:none
154 /// CHECK-DAG: <<GetC:i\d+>> ArrayGet [<<Par>>,<<PhiC>>] loop:<<Clean>> outer_loop:none
155 /// CHECK-DAG: <<AddC:i\d+>> Add [<<GetC>>,<<One>>] loop:<<Clean>> outer_loop:none
156 /// CHECK-DAG: ArraySet [<<Par>>,<<PhiC>>,<<AddC>>] loop:<<Clean>> outer_loop:none
157 /// CHECK-DAG: <<AddIC>> Add [<<PhiC>>,<<One>>] loop:<<Clean>> outer_loop:none
158 static void staticallyMisalignedN(int[] a) {
159 // Starts at offset 12 (hidden) + 0 * 4 relative to base alignment.
160 // Yes, Art runtime misaligns the most common access pattern :-(
161 // Static peeling to the rescue, aligned vector, cleanup.
162 for (int i = 0; i < a.length; i++) {
163 a[i] += 1;
164 }
165 }
166
167 /// CHECK-START: void Main.staticallyUnknownAligned(int[], int) loop_optimization (before)
168 /// CHECK-DAG: <<Par:l\d+>> ParameterValue loop:none
169 /// CHECK-DAG: <<Off:i\d+>> ParameterValue loop:none
170 /// CHECK-DAG: <<Zero:i\d+>> IntConstant 0 loop:none
171 /// CHECK-DAG: <<One:i\d+>> IntConstant 1 loop:none
172 /// CHECK-DAG: <<Phi:i\d+>> Phi [<<Zero>>,<<AddI:i\d+>>] loop:<<Loop:B\d+>> outer_loop:none
173 /// CHECK-DAG: <<Nrm:i\d+>> Add [<<Off>>,<<Phi>>] loop:<<Loop>> outer_loop:none
174 /// CHECK-DAG: <<Get:i\d+>> ArrayGet [<<Par>>,<<Nrm>>] loop:<<Loop>> outer_loop:none
175 /// CHECK-DAG: <<Add:i\d+>> Add [<<Get>>,<<One>>] loop:<<Loop>> outer_loop:none
176 /// CHECK-DAG: ArraySet [<<Par>>,<<Nrm>>,<<Add>>] loop:<<Loop>> outer_loop:none
177 /// CHECK-DAG: <<AddI>> Add [<<Phi>>,<<One>>] loop:<<Loop>> outer_loop:none
178 //
179 /// CHECK-START-ARM: void Main.staticallyUnknownAligned(int[], int) loop_optimization (after)
180 /// CHECK-DAG: <<Par:l\d+>> ParameterValue loop:none
181 /// CHECK-DAG: <<Off:i\d+>> ParameterValue loop:none
182 /// CHECK-DAG: <<Zero:i\d+>> IntConstant 0 loop:none
183 /// CHECK-DAG: <<One:i\d+>> IntConstant 1 loop:none
184 /// CHECK-DAG: <<Vl:i\d+>> IntConstant 2 loop:none
185 /// CHECK-DAG: <<PhiP:i\d+>> Phi [<<Zero>>,<<AddIP:i\d+>>] loop:<<Peel:B\d+>> outer_loop:none
186 /// CHECK-DAG: <<NrmP:i\d+>> Add [<<PhiP>>,<<Off>>] loop:<<Peel>> outer_loop:none
187 /// CHECK-DAG: <<Get:i\d+>> ArrayGet [<<Par>>,<<NrmP>>] loop:<<Peel>> outer_loop:none
188 /// CHECK-DAG: <<AddP:i\d+>> Add [<<Get>>,<<One>>] loop:<<Peel>> outer_loop:none
189 /// CHECK-DAG: ArraySet [<<Par>>,<<NrmP>>,<<AddP>>] loop:<<Peel>> outer_loop:none
190 /// CHECK-DAG: <<AddIP>> Add [<<PhiP>>,<<One>>] loop:<<Peel>> outer_loop:none
191 /// CHECK-DAG: <<Repl:d\d+>> VecReplicateScalar [<<One>>] loop:none
192 /// CHECK-DAG: <<Phi:i\d+>> Phi [<<PhiP>>,<<AddI:i\d+>>] loop:<<Loop:B\d+>> outer_loop:none
193 /// CHECK-DAG: <<Nrm:i\d+>> Add [<<Phi>>,<<Off>>] loop:<<Loop>> outer_loop:none
194 /// CHECK-DAG: <<Load:d\d+>> VecLoad [<<Par>>,<<Nrm>>] alignment:ALIGN(8,0) loop:<<Loop>> outer_loop:none
195 /// CHECK-DAG: <<Add:d\d+>> VecAdd [<<Load>>,<<Repl>>] loop:<<Loop>> outer_loop:none
196 /// CHECK-DAG: VecStore [<<Par>>,<<Nrm>>,<<Add>>] alignment:ALIGN(8,0) loop:<<Loop>> outer_loop:none
197 /// CHECK-DAG: <<AddI>> Add [<<Phi>>,<<Vl>>] loop:<<Loop>> outer_loop:none
198 /// CHECK-DAG: <<PhiC:i\d+>> Phi [<<Phi>>,<<AddIC:i\d+>>] loop:<<Clean:B\d+>> outer_loop:none
199 /// CHECK-DAG: <<NrmC:i\d+>> Add [<<PhiC>>,<<Off>>] loop:<<Clean>> outer_loop:none
200 /// CHECK-DAG: <<GetC:i\d+>> ArrayGet [<<Par>>,<<NrmC>>] loop:<<Clean>> outer_loop:none
201 /// CHECK-DAG: <<AddC:i\d+>> Add [<<GetC>>,<<One>>] loop:<<Clean>> outer_loop:none
202 /// CHECK-DAG: ArraySet [<<Par>>,<<NrmC>>,<<AddC>>] loop:<<Clean>> outer_loop:none
203 /// CHECK-DAG: <<AddIC>> Add [<<PhiC>>,<<One>>] loop:<<Clean>> outer_loop:none
204 static void staticallyUnknownAligned(int[] a, int off) {
205 // Starts at an unknown offset due to parameter off.
206 // Dynamic peeling to the rescue, aligned vector, cleanup.
207 for (int i = 0; i < 9; i++) {
208 a[off + i] += 1;
209 }
210 }
211
212 /// CHECK-START: void Main.staticallyUnknownAlignedN(int[], int, int) loop_optimization (before)
213 /// CHECK-DAG: <<Par:l\d+>> ParameterValue loop:none
214 /// CHECK-DAG: <<Off:i\d+>> ParameterValue loop:none
215 /// CHECK-DAG: <<Zero:i\d+>> IntConstant 0 loop:none
216 /// CHECK-DAG: <<One:i\d+>> IntConstant 1 loop:none
217 /// CHECK-DAG: <<Phi:i\d+>> Phi [<<Zero>>,<<AddI:i\d+>>] loop:<<Loop:B\d+>> outer_loop:none
218 /// CHECK-DAG: <<Nrm:i\d+>> Add [<<Off>>,<<Phi>>] loop:<<Loop>> outer_loop:none
219 /// CHECK-DAG: <<Get:i\d+>> ArrayGet [<<Par>>,<<Nrm>>] loop:<<Loop>> outer_loop:none
220 /// CHECK-DAG: <<Add:i\d+>> Add [<<Get>>,<<One>>] loop:<<Loop>> outer_loop:none
221 /// CHECK-DAG: ArraySet [<<Par>>,<<Nrm>>,<<Add>>] loop:<<Loop>> outer_loop:none
222 /// CHECK-DAG: <<AddI>> Add [<<Phi>>,<<One>>] loop:<<Loop>> outer_loop:none
223 //
224 /// CHECK-START-ARM: void Main.staticallyUnknownAlignedN(int[], int, int) loop_optimization (after)
225 /// CHECK-DAG: <<Par:l\d+>> ParameterValue loop:none
226 /// CHECK-DAG: <<Off:i\d+>> ParameterValue loop:none
227 /// CHECK-DAG: <<Zero:i\d+>> IntConstant 0 loop:none
228 /// CHECK-DAG: <<One:i\d+>> IntConstant 1 loop:none
229 /// CHECK-DAG: <<Vl:i\d+>> IntConstant 2 loop:none
230 /// CHECK-DAG: <<PhiP:i\d+>> Phi [<<Zero>>,<<AddIP:i\d+>>] loop:<<Peel:B\d+>> outer_loop:none
231 /// CHECK-DAG: <<NrmP:i\d+>> Add [<<PhiP>>,<<Off>>] loop:<<Peel>> outer_loop:none
232 /// CHECK-DAG: <<Get:i\d+>> ArrayGet [<<Par>>,<<NrmP>>] loop:<<Peel>> outer_loop:none
233 /// CHECK-DAG: <<AddP:i\d+>> Add [<<Get>>,<<One>>] loop:<<Peel>> outer_loop:none
234 /// CHECK-DAG: ArraySet [<<Par>>,<<NrmP>>,<<AddP>>] loop:<<Peel>> outer_loop:none
235 /// CHECK-DAG: <<AddIP>> Add [<<PhiP>>,<<One>>] loop:<<Peel>> outer_loop:none
236 /// CHECK-DAG: <<Repl:d\d+>> VecReplicateScalar [<<One>>] loop:none
237 /// CHECK-DAG: <<Phi:i\d+>> Phi [<<PhiP>>,<<AddI:i\d+>>] loop:<<Loop:B\d+>> outer_loop:none
238 /// CHECK-DAG: <<Nrm:i\d+>> Add [<<Phi>>,<<Off>>] loop:<<Loop>> outer_loop:none
239 /// CHECK-DAG: <<Load:d\d+>> VecLoad [<<Par>>,<<Nrm>>] alignment:ALIGN(8,0) loop:<<Loop>> outer_loop:none
240 /// CHECK-DAG: <<Add:d\d+>> VecAdd [<<Load>>,<<Repl>>] loop:<<Loop>> outer_loop:none
241 /// CHECK-DAG: VecStore [<<Par>>,<<Nrm>>,<<Add>>] alignment:ALIGN(8,0) loop:<<Loop>> outer_loop:none
242 /// CHECK-DAG: <<AddI>> Add [<<Phi>>,<<Vl>>] loop:<<Loop>> outer_loop:none
243 /// CHECK-DAG: <<PhiC:i\d+>> Phi [<<Phi>>,<<AddIC:i\d+>>] loop:<<Clean:B\d+>> outer_loop:none
244 /// CHECK-DAG: <<NrmC:i\d+>> Add [<<PhiC>>,<<Off>>] loop:<<Clean>> outer_loop:none
245 /// CHECK-DAG: <<GetC:i\d+>> ArrayGet [<<Par>>,<<NrmC>>] loop:<<Clean>> outer_loop:none
246 /// CHECK-DAG: <<AddC:i\d+>> Add [<<GetC>>,<<One>>] loop:<<Clean>> outer_loop:none
247 /// CHECK-DAG: ArraySet [<<Par>>,<<NrmC>>,<<AddC>>] loop:<<Clean>> outer_loop:none
248 /// CHECK-DAG: <<AddIC>> Add [<<PhiC>>,<<One>>] loop:<<Clean>> outer_loop:none
249 static void staticallyUnknownAlignedN(int[] a, int off, int n) {
250 // Starts at an unknown offset due to parameter off.
251 // Dynamic peeling to the rescue, aligned vector, cleanup.
252 for (int i = 0; i < n; i++) {
253 a[off + i] += 1;
254 }
255 }
256
257 //
258 // Test drivers.
259 //
260
261 private static void test1() {
262 int[] a = new int[9];
263 staticallyAligned(a);
264 for (int i = 0; i < a.length; i++) {
265 int e = i > 0 ? 1 : 0;
266 expectEquals(e, a[i]);
267 }
268 }
269
270 private static void test2() {
271 for (int n = 0; n <= 71; n++) {
272 int[] a = new int[n];
273 staticallyAlignedN(a);
274 for (int i = 0; i < a.length; i++) {
275 int e = i > 0 ? 1 : 0;
276 expectEquals(e, a[i]);
277 }
278 }
279 }
280
281 private static void test3() {
282 int[] a = new int[9];
283 staticallyMisaligned(a);
284 for (int i = 0; i < a.length; i++) {
285 expectEquals(1, a[i]);
286 }
287 }
288
289 private static void test4() {
290 for (int n = 0; n <= 71; n++) {
291 int[] a = new int[n];
292 staticallyMisalignedN(a);
293 for (int i = 0; i < a.length; i++) {
294 expectEquals(1, a[i]);
295 }
296 }
297 }
298
299 private static void test5() {
300 for (int off = 0; off <= 8; off++) {
301 int[] a = new int[17];
302 staticallyUnknownAligned(a, off);
303 for (int i = 0; i < a.length; i++) {
304 int e = (off <= i && i < off + 9) ? 1 : 0;
305 expectEquals(e, a[i]);
306 }
307 }
308 }
309
310 private static void test6() {
311 for (int off = 0; off <= 8; off++) {
312 for (int n = 0; n <= 9; n++) {
313 int[] a = new int[17];
314 staticallyUnknownAlignedN(a, off, n);
315 for (int i = 0; i < a.length; i++) {
316 int e = (off <= i && i < off + n) ? 1 : 0;
317 expectEquals(e, a[i]);
318 }
319 }
320 }
321 }
322
323 public static void main(String[] args) {
324 test1();
325 test2();
326 test4();
327 test5();
328 test6();
329 System.out.println("passed");
330 }
331
332 private static void expectEquals(int expected, int result) {
333 if (expected != result) {
334 throw new Error("Expected: " + expected + ", found: " + result);
335 }
336 }
337}