1! This test checks the lowering of OpenMP sections construct with several clauses present
2
3! RUN: %flang_fc1 -emit-fir -fopenmp %s -o - | FileCheck %s --check-prefix="FIRDialect"
4! RUN: %flang_fc1 -emit-fir -fopenmp %s -o - | fir-opt --fir-to-llvm-ir | FileCheck %s --check-prefix="LLVMDialect"
5! TODO before (%flang_fc1 -emit-fir -fopenmp %s -o - | fir-opt --fir-to-llvm-ir | tco | FileCheck %s --check-prefix="LLVMIR"):
6! ensure allocate clause lowering
7
8!FIRDialect: func @_QQmain() {
9!FIRDialect: %[[COUNT:.*]] = fir.address_of(@_QFEcount) : !fir.ref<i32>
10!FIRDialect: %[[DOUBLE_COUNT:.*]] = fir.address_of(@_QFEdouble_count) : !fir.ref<i32>
11!FIRDialect: %[[ETA:.*]] = fir.alloca f32 {bindc_name = "eta", uniq_name = "_QFEeta"}
12!FIRDialect: %[[CONST_1:.*]] = arith.constant 1 : i32
13!FIRDialect: omp.sections allocate(%[[CONST_1]] : i32 -> %0 : !fir.ref<i32>)  {
14!FIRDialect: omp.section {
15!FIRDialect: {{.*}} = arith.constant 5 : i32
16!FIRDialect: fir.store {{.*}} to {{.*}} : !fir.ref<i32>
17!FIRDialect: {{.*}} = fir.load %[[COUNT]] : !fir.ref<i32>
18!FIRDialect: {{.*}} = fir.load %[[DOUBLE_COUNT]] : !fir.ref<i32>
19!FIRDialect: {{.*}} = arith.muli {{.*}}, {{.*}} : i32
20!FIRDialect: {{.*}} = fir.convert {{.*}} : (i32) -> f32
21!FIRDialect: fir.store {{.*}} to %[[ETA]] : !fir.ref<f32>
22!FIRDialect: omp.terminator
23!FIRDialect: }
24!FIRDialect: omp.section {
25!FIRDialect: {{.*}} = fir.load %[[DOUBLE_COUNT]] : !fir.ref<i32>
26!FIRDialect: {{.*}} = arith.constant 1 : i32
27!FIRDialect: {{.*}} = arith.addi {{.*}} : i32
28!FIRDialect: fir.store {{.*}} to %[[DOUBLE_COUNT]] : !fir.ref<i32>
29!FIRDialect: omp.terminator
30!FIRDialect: }
31!FIRDialect: omp.section {
32!FIRDialect: {{.*}} = fir.load %[[ETA]] : !fir.ref<f32>
33!FIRDialect: {{.*}} = arith.constant 7.000000e+00 : f32
34!FIRDialect: {{.*}} = arith.subf {{.*}} : f32
35!FIRDialect: fir.store {{.*}} to %[[ETA]] : !fir.ref<f32>
36!FIRDialect: {{.*}} = fir.load %[[COUNT]] : !fir.ref<i32>
37!FIRDialect: {{.*}} = fir.convert {{.*}} : (i32) -> f32
38!FIRDialect: {{.*}} = fir.load %[[ETA]] : !fir.ref<f32>
39!FIRDialect: {{.*}} = arith.mulf {{.*}}, {{.*}} : f32
40!FIRDialect: {{.*}} = fir.convert {{.*}} : (f32) -> i32
41!FIRDialect: fir.store {{.*}} to %[[COUNT]] : !fir.ref<i32>
42!FIRDialect: {{.*}} = fir.load %[[COUNT]] : !fir.ref<i32>
43!FIRDialect: {{.*}} = fir.convert {{.*}} : (i32) -> f32
44!FIRDialect: {{.*}} = fir.load %[[ETA]] : !fir.ref<f32>
45!FIRDialect: {{.*}} = arith.subf {{.*}}, {{.*}} : f32
46!FIRDialect: {{.*}} = fir.convert {{.*}} : (f32) -> i32
47!FIRDialect: fir.store {{.*}} to %[[DOUBLE_COUNT]] : !fir.ref<i32>
48!FIRDialect: omp.terminator
49!FIRDialect: }
50!FIRDialect: omp.terminator
51!FIRDialect: }
52!FIRDialect: omp.sections nowait {
53!FIRDialect: omp.terminator
54!FIRDialect: }
55!FIRDialect: return
56!FIRDialect: }
57
58!LLVMDialect: llvm.func @_QQmain() {
59!LLVMDialect: %[[COUNT:.*]] = llvm.mlir.addressof @_QFEcount : !llvm.ptr<i32>
60!LLVMDialect: {{.*}} = builtin.unrealized_conversion_cast %[[COUNT]] : !llvm.ptr<i32> to !fir.ref<i32>
61!LLVMDialect: %[[DOUBLE_COUNT:.*]] = llvm.mlir.addressof @_QFEdouble_count : !llvm.ptr<i32>
62!LLVMDialect: %[[ALLOCATOR:.*]] = llvm.mlir.constant(1 : i64) : i64
63!LLVMDialect: %[[ETA:.*]] = llvm.alloca %[[ALLOCATOR]] x f32 {bindc_name = "eta", in_type = f32, operand_segment_sizes = dense<0> : vector<2xi32>, uniq_name = "_QFEeta"} : (i64) -> !llvm.ptr<f32>
64!LLVMDialect: %[[CONSTANT:.*]] = llvm.mlir.constant(1 : i32) : i32
65!LLVMDialect: omp.sections   allocate(%[[CONSTANT]] : i32 -> %1 : !fir.ref<i32>) {
66!LLVMDialect: omp.section {
67!LLVMDialect: {{.*}} = llvm.mlir.constant(5 : i32) : i32
68!LLVMDialect: llvm.store {{.*}}, %[[COUNT]] : !llvm.ptr<i32>
69!LLVMDialect: {{.*}} = llvm.load %[[COUNT]] : !llvm.ptr<i32>
70!LLVMDialect: {{.*}} = llvm.load %[[DOUBLE_COUNT]] : !llvm.ptr<i32>
71!LLVMDialect: {{.*}} = llvm.mul {{.*}}, {{.*}} : i32
72!LLVMDialect: {{.*}} = llvm.sitofp {{.*}} : i32 to f32
73!LLVMDialect: llvm.store {{.*}}, %[[ETA]] : !llvm.ptr<f32>
74!LLVMDialect: omp.terminator
75!LLVMDialect: }
76!LLVMDialect: omp.section {
77!LLVMDialect: {{.*}} = llvm.load %[[DOUBLE_COUNT]] : !llvm.ptr<i32>
78!LLVMDialect: {{.*}} = llvm.mlir.constant(1 : i32) : i32
79!LLVMDialect: {{.*}} = llvm.add {{.*}}, {{.*}} : i32
80!LLVMDialect: llvm.store {{.*}}, %[[DOUBLE_COUNT]] : !llvm.ptr<i32>
81!LLVMDialect: omp.terminator
82!LLVMDialect: }
83!LLVMDialect: omp.section {
84!LLVMDialect: {{.*}} = llvm.load %[[ETA]] : !llvm.ptr<f32>
85!LLVMDialect: {{.*}} = llvm.mlir.constant(7.000000e+00 : f32) : f32
86!LLVMDialect: {{.*}} = llvm.fsub {{.*}}, {{.*}} : f32
87!LLVMDialect: llvm.store {{.*}}, %[[ETA]] : !llvm.ptr<f32>
88!LLVMDialect: {{.*}} = llvm.load %[[COUNT]] : !llvm.ptr<i32>
89!LLVMDialect: {{.*}} = llvm.sitofp {{.*}} : i32 to f32
90!LLVMDialect: {{.*}} = llvm.load %[[ETA]] : !llvm.ptr<f32>
91!LLVMDialect: {{.*}} = llvm.fmul {{.*}}, {{.*}} : f32
92!LLVMDialect: {{.*}} = llvm.fptosi {{.*}} : f32 to i32
93!LLVMDialect: llvm.store {{.*}}, %[[COUNT]] : !llvm.ptr<i32>
94!LLVMDialect: {{.*}} = llvm.load %[[COUNT]] : !llvm.ptr<i32>
95!LLVMDialect: {{.*}} = llvm.sitofp {{.*}} : i32 to f32
96!LLVMDialect: {{.*}} = llvm.load %[[ETA]] : !llvm.ptr<f32>
97!LLVMDialect: {{.*}} = llvm.fsub {{.*}}, {{.*}} : f32
98!LLVMDialect: {{.*}} = llvm.fptosi {{.*}} : f32 to i32
99!LLVMDialect: llvm.store {{.*}}, %[[DOUBLE_COUNT]] : !llvm.ptr<i32>
100!LLVMDialect: omp.terminator
101!LLVMDialect: }
102!LLVMDialect: omp.terminator
103!LLVMDialect: }
104!LLVMDialect: omp.sections nowait {
105!LLVMDialect: omp.section {
106!LLVMDialect: omp.terminator
107!LLVMDialect: }
108!LLVMDialect: omp.terminator
109!LLVMDialect: }
110!LLVMDialect: llvm.return
111!LLVMDialect: }
112
113program sample
114    use omp_lib
115    integer :: count = 0, double_count = 1
116    !$omp sections private (eta, double_count) allocate(omp_high_bw_mem_alloc: count)
117        !$omp section
118            count = 1 + 4
119            eta = count * double_count
120        !$omp section
121            double_count = double_count + 1
122        !$omp section
123            eta = eta - 7
124            count = count * eta
125            double_count = count - eta
126    !$omp end sections
127
128    !$omp sections
129    !$omp end sections nowait
130end program sample
131
132!FIRDialect: func @_QPfirstprivate(%[[ARG:.*]]: !fir.ref<f32> {fir.bindc_name = "alpha"}) {
133!FIRDialect: omp.sections {
134!FIRDialect: omp.section  {
135!FIRDialect: omp.terminator
136!FIRDialect: }
137!FIRDialect: omp.terminator
138!FIRDialect: }
139!FIRDialect: omp.sections {
140!FIRDialect: omp.section  {
141!FIRDialect: %[[PRIVATE_VAR:.*]] = fir.load %[[ARG]] : !fir.ref<f32>
142!FIRDialect: %[[CONSTANT:.*]] = arith.constant 5.000000e+00 : f32
143!FIRDialect: %[[PRIVATE_VAR_2:.*]] = arith.mulf %[[PRIVATE_VAR]], %[[CONSTANT]] : f32
144!FIRDialect: fir.store %[[PRIVATE_VAR_2]] to %[[ARG]] : !fir.ref<f32>
145!FIRDialect: omp.terminator
146!FIRDialect: }
147!FIRDialect: omp.terminator
148!FIRDialect: }
149!FIRDialect: return
150!FIRDialect: }
151
152!LLVMDialect: llvm.func @_QPfirstprivate(%[[ARG:.*]]: !llvm.ptr<f32> {fir.bindc_name = "alpha"}) {
153!LLVMDialect: omp.sections   {
154!LLVMDialect: omp.section {
155!LLVMDialect: omp.terminator
156!LLVMDialect: }
157!LLVMDialect: omp.terminator
158!LLVMDialect: }
159!LLVMDialect: omp.sections {
160!LLVMDialect: omp.section {
161!LLVMDialect: {{.*}} = llvm.load %[[ARG]] : !llvm.ptr<f32>
162!LLVMDialect: {{.*}} = llvm.mlir.constant(5.000000e+00 : f32) : f32
163!LLVMDialect: {{.*}} = llvm.fmul {{.*}}, {{.*}} : f32
164!LLVMDialect: llvm.store {{.*}}, %[[ARG]] : !llvm.ptr<f32>
165!LLVMDialect: omp.terminator
166!LLVMDialect: }
167!LLVMDialect: omp.terminator
168!LLVMDialect: }
169!LLVMDialect: llvm.return
170!LLVMDialect: }
171
172subroutine firstprivate(alpha)
173    real :: alpha
174    !$omp sections firstprivate(alpha)
175    !$omp end sections
176
177    !$omp sections
178        alpha = alpha * 5
179    !$omp end sections
180end subroutine
181