1176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines// RUN: %clang_cc1 -triple x86_64-apple-darwin -std=c++11 -emit-llvm -o - %s | FileCheck %s
2176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
3176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines// Verify while loop is recognized after unroll pragma.
4176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinesvoid while_test(int *List, int Length) {
5176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  // CHECK: define {{.*}} @_Z10while_test
6176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  int i = 0;
7176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
8176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines#pragma unroll
9176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  while (i < Length) {
1087d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar    // CHECK: br label {{.*}}, !llvm.loop ![[LOOP_1:.*]]
11176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines    List[i] = i * 2;
12176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines    i++;
13176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  }
14176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines}
15176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
16176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines// Verify do loop is recognized after multi-option pragma clang loop directive.
17176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinesvoid do_test(int *List, int Length) {
1887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar  // CHECK: define {{.*}} @_Z7do_test
19176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  int i = 0;
20176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
21176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines#pragma nounroll
22176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  do {
23176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines    // CHECK: br i1 {{.*}}, label {{.*}}, label {{.*}}, !llvm.loop ![[LOOP_2:.*]]
24176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines    List[i] = i * 2;
25176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines    i++;
26176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  } while (i < Length);
27176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines}
28176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
29176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines// Verify for loop is recognized after unroll pragma.
30176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinesvoid for_test(int *List, int Length) {
3187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar// CHECK: define {{.*}} @_Z8for_test
32176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines#pragma unroll 8
33176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  for (int i = 0; i < Length; i++) {
3487d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar    // CHECK: br label {{.*}}, !llvm.loop ![[LOOP_3:.*]]
35176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines    List[i] = i * 2;
36176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  }
37176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines}
38176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
39176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines// Verify c++11 for range loop is recognized after unroll pragma.
40176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinesvoid for_range_test() {
4187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar  // CHECK: define {{.*}} @_Z14for_range_test
42176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  double List[100];
43176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
44176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines#pragma unroll(4)
45176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  for (int i : List) {
4687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar    // CHECK: br label {{.*}}, !llvm.loop ![[LOOP_4:.*]]
47176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines    List[i] = i;
48176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  }
49176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines}
50176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
51176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines#define UNROLLCOUNT 8
52176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
53176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines// Verify defines are correctly resolved in unroll pragmas.
54176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinesvoid for_define_test(int *List, int Length, int Value) {
5587d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar// CHECK: define {{.*}} @_Z15for_define_test
56176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines#pragma unroll(UNROLLCOUNT)
57176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  for (int i = 0; i < Length; i++) {
5887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar    // CHECK: br label {{.*}}, !llvm.loop ![[LOOP_5:.*]]
59176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines    List[i] = i * Value;
60176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  }
61176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines}
62176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
63176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines// Verify metadata is generated when template is used.
64176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinestemplate <typename A>
65176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinesvoid for_template_test(A *List, int Length, A Value) {
6687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar// CHECK: define {{.*}} @_Z13template_test
67176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines#pragma unroll 8
68176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  for (int i = 0; i < Length; i++) {
6987d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar    // CHECK: br label {{.*}}, !llvm.loop ![[LOOP_6:.*]]
70176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines    List[i] = i * Value;
71176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  }
72176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines}
73176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
74176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines// Verify define is resolved correctly when template is used.
75176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinestemplate <typename A>
76176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinesvoid for_template_define_test(A *List, int Length, A Value) {
7787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar// CHECK: define {{.*}} @_Z24for_template_define_test
7887d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar
79176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines#pragma unroll(UNROLLCOUNT)
80176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  for (int i = 0; i < Length; i++) {
8187d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar    // CHECK: br label {{.*}}, !llvm.loop ![[LOOP_7:.*]]
82176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines    List[i] = i * Value;
83176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  }
84176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines}
85176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
86176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines#undef UNROLLCOUNT
87176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
88176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines// Use templates defined above. Test verifies metadata is generated correctly.
89176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hinesvoid template_test(double *List, int Length) {
90176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  double Value = 10;
91176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
92176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  for_template_test<double>(List, Length, Value);
93176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines  for_template_define_test<double>(List, Length, Value);
94176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines}
95176edba5311f6eff0cad2631449885ddf4fbc9eaStephen Hines
9687d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar// CHECK: ![[LOOP_1]] = distinct !{![[LOOP_1]], ![[UNROLL_ENABLE:.*]]}
9787d948ecccffea9e9e37d0d053b246e2d6d6c47bPirama Arumuga Nainar// CHECK: ![[UNROLL_ENABLE]] = !{!"llvm.loop.unroll.enable"}
980e2c34f92f00628d48968dfea096d36381f494cbStephen Hines// CHECK: ![[LOOP_2]] = distinct !{![[LOOP_2:.*]], ![[UNROLL_DISABLE:.*]]}
990e2c34f92f00628d48968dfea096d36381f494cbStephen Hines// CHECK: ![[UNROLL_DISABLE]] = !{!"llvm.loop.unroll.disable"}
1000e2c34f92f00628d48968dfea096d36381f494cbStephen Hines// CHECK: ![[LOOP_3]] = distinct !{![[LOOP_3]], ![[UNROLL_8:.*]]}
1010e2c34f92f00628d48968dfea096d36381f494cbStephen Hines// CHECK: ![[UNROLL_8]] = !{!"llvm.loop.unroll.count", i32 8}
1020e2c34f92f00628d48968dfea096d36381f494cbStephen Hines// CHECK: ![[LOOP_4]] = distinct !{![[LOOP_4]], ![[UNROLL_4:.*]]}
1030e2c34f92f00628d48968dfea096d36381f494cbStephen Hines// CHECK: ![[UNROLL_4]] = !{!"llvm.loop.unroll.count", i32 4}
1040e2c34f92f00628d48968dfea096d36381f494cbStephen Hines// CHECK: ![[LOOP_5]] = distinct !{![[LOOP_5]], ![[UNROLL_8:.*]]}
1050e2c34f92f00628d48968dfea096d36381f494cbStephen Hines// CHECK: ![[LOOP_6]] = distinct !{![[LOOP_6]], ![[UNROLL_8:.*]]}
1060e2c34f92f00628d48968dfea096d36381f494cbStephen Hines// CHECK: ![[LOOP_7]] = distinct !{![[LOOP_7]], ![[UNROLL_8:.*]]}
107