[clang-tidy][NFC]remove deps of clang in clang tidy test (#116588)
[llvm-project.git] / clang / lib / AST / OpenMPClause.cpp
blob4246ba95d827f1c13e176db2b7ff0069a0210b2b
1 //===- OpenMPClause.cpp - Classes for OpenMP clauses ----------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This file implements the subclesses of Stmt class declared in OpenMPClause.h
11 //===----------------------------------------------------------------------===//
13 #include "clang/AST/OpenMPClause.h"
14 #include "clang/AST/ASTContext.h"
15 #include "clang/AST/Attr.h"
16 #include "clang/AST/Decl.h"
17 #include "clang/AST/DeclOpenMP.h"
18 #include "clang/Basic/LLVM.h"
19 #include "clang/Basic/OpenMPKinds.h"
20 #include "clang/Basic/TargetInfo.h"
21 #include "llvm/ADT/SmallPtrSet.h"
22 #include "llvm/Support/ErrorHandling.h"
23 #include <algorithm>
24 #include <cassert>
25 #include <optional>
27 using namespace clang;
28 using namespace llvm;
29 using namespace omp;
31 OMPClause::child_range OMPClause::children() {
32 switch (getClauseKind()) {
33 default:
34 break;
35 #define GEN_CLANG_CLAUSE_CLASS
36 #define CLAUSE_CLASS(Enum, Str, Class) \
37 case Enum: \
38 return static_cast<Class *>(this)->children();
39 #include "llvm/Frontend/OpenMP/OMP.inc"
41 llvm_unreachable("unknown OMPClause");
44 OMPClause::child_range OMPClause::used_children() {
45 switch (getClauseKind()) {
46 #define GEN_CLANG_CLAUSE_CLASS
47 #define CLAUSE_CLASS(Enum, Str, Class) \
48 case Enum: \
49 return static_cast<Class *>(this)->used_children();
50 #define CLAUSE_NO_CLASS(Enum, Str) \
51 case Enum: \
52 break;
53 #include "llvm/Frontend/OpenMP/OMP.inc"
55 llvm_unreachable("unknown OMPClause");
58 OMPClauseWithPreInit *OMPClauseWithPreInit::get(OMPClause *C) {
59 auto *Res = OMPClauseWithPreInit::get(const_cast<const OMPClause *>(C));
60 return Res ? const_cast<OMPClauseWithPreInit *>(Res) : nullptr;
63 const OMPClauseWithPreInit *OMPClauseWithPreInit::get(const OMPClause *C) {
64 switch (C->getClauseKind()) {
65 case OMPC_schedule:
66 return static_cast<const OMPScheduleClause *>(C);
67 case OMPC_dist_schedule:
68 return static_cast<const OMPDistScheduleClause *>(C);
69 case OMPC_firstprivate:
70 return static_cast<const OMPFirstprivateClause *>(C);
71 case OMPC_lastprivate:
72 return static_cast<const OMPLastprivateClause *>(C);
73 case OMPC_reduction:
74 return static_cast<const OMPReductionClause *>(C);
75 case OMPC_task_reduction:
76 return static_cast<const OMPTaskReductionClause *>(C);
77 case OMPC_in_reduction:
78 return static_cast<const OMPInReductionClause *>(C);
79 case OMPC_linear:
80 return static_cast<const OMPLinearClause *>(C);
81 case OMPC_if:
82 return static_cast<const OMPIfClause *>(C);
83 case OMPC_num_threads:
84 return static_cast<const OMPNumThreadsClause *>(C);
85 case OMPC_num_teams:
86 return static_cast<const OMPNumTeamsClause *>(C);
87 case OMPC_thread_limit:
88 return static_cast<const OMPThreadLimitClause *>(C);
89 case OMPC_device:
90 return static_cast<const OMPDeviceClause *>(C);
91 case OMPC_grainsize:
92 return static_cast<const OMPGrainsizeClause *>(C);
93 case OMPC_num_tasks:
94 return static_cast<const OMPNumTasksClause *>(C);
95 case OMPC_final:
96 return static_cast<const OMPFinalClause *>(C);
97 case OMPC_priority:
98 return static_cast<const OMPPriorityClause *>(C);
99 case OMPC_novariants:
100 return static_cast<const OMPNovariantsClause *>(C);
101 case OMPC_nocontext:
102 return static_cast<const OMPNocontextClause *>(C);
103 case OMPC_filter:
104 return static_cast<const OMPFilterClause *>(C);
105 case OMPC_ompx_dyn_cgroup_mem:
106 return static_cast<const OMPXDynCGroupMemClause *>(C);
107 case OMPC_default:
108 case OMPC_proc_bind:
109 case OMPC_safelen:
110 case OMPC_simdlen:
111 case OMPC_sizes:
112 case OMPC_allocator:
113 case OMPC_allocate:
114 case OMPC_collapse:
115 case OMPC_private:
116 case OMPC_shared:
117 case OMPC_aligned:
118 case OMPC_copyin:
119 case OMPC_copyprivate:
120 case OMPC_ordered:
121 case OMPC_nowait:
122 case OMPC_untied:
123 case OMPC_mergeable:
124 case OMPC_threadprivate:
125 case OMPC_flush:
126 case OMPC_depobj:
127 case OMPC_read:
128 case OMPC_write:
129 case OMPC_update:
130 case OMPC_capture:
131 case OMPC_compare:
132 case OMPC_fail:
133 case OMPC_seq_cst:
134 case OMPC_acq_rel:
135 case OMPC_acquire:
136 case OMPC_release:
137 case OMPC_relaxed:
138 case OMPC_depend:
139 case OMPC_threads:
140 case OMPC_simd:
141 case OMPC_map:
142 case OMPC_nogroup:
143 case OMPC_hint:
144 case OMPC_defaultmap:
145 case OMPC_unknown:
146 case OMPC_uniform:
147 case OMPC_to:
148 case OMPC_from:
149 case OMPC_use_device_ptr:
150 case OMPC_use_device_addr:
151 case OMPC_is_device_ptr:
152 case OMPC_has_device_addr:
153 case OMPC_unified_address:
154 case OMPC_unified_shared_memory:
155 case OMPC_reverse_offload:
156 case OMPC_dynamic_allocators:
157 case OMPC_atomic_default_mem_order:
158 case OMPC_at:
159 case OMPC_severity:
160 case OMPC_message:
161 case OMPC_device_type:
162 case OMPC_match:
163 case OMPC_nontemporal:
164 case OMPC_order:
165 case OMPC_destroy:
166 case OMPC_detach:
167 case OMPC_inclusive:
168 case OMPC_exclusive:
169 case OMPC_uses_allocators:
170 case OMPC_affinity:
171 case OMPC_when:
172 case OMPC_bind:
173 case OMPC_ompx_bare:
174 break;
175 default:
176 break;
179 return nullptr;
182 OMPClauseWithPostUpdate *OMPClauseWithPostUpdate::get(OMPClause *C) {
183 auto *Res = OMPClauseWithPostUpdate::get(const_cast<const OMPClause *>(C));
184 return Res ? const_cast<OMPClauseWithPostUpdate *>(Res) : nullptr;
187 const OMPClauseWithPostUpdate *OMPClauseWithPostUpdate::get(const OMPClause *C) {
188 switch (C->getClauseKind()) {
189 case OMPC_lastprivate:
190 return static_cast<const OMPLastprivateClause *>(C);
191 case OMPC_reduction:
192 return static_cast<const OMPReductionClause *>(C);
193 case OMPC_task_reduction:
194 return static_cast<const OMPTaskReductionClause *>(C);
195 case OMPC_in_reduction:
196 return static_cast<const OMPInReductionClause *>(C);
197 case OMPC_linear:
198 return static_cast<const OMPLinearClause *>(C);
199 case OMPC_schedule:
200 case OMPC_dist_schedule:
201 case OMPC_firstprivate:
202 case OMPC_default:
203 case OMPC_proc_bind:
204 case OMPC_if:
205 case OMPC_final:
206 case OMPC_num_threads:
207 case OMPC_safelen:
208 case OMPC_simdlen:
209 case OMPC_sizes:
210 case OMPC_allocator:
211 case OMPC_allocate:
212 case OMPC_collapse:
213 case OMPC_private:
214 case OMPC_shared:
215 case OMPC_aligned:
216 case OMPC_copyin:
217 case OMPC_copyprivate:
218 case OMPC_ordered:
219 case OMPC_nowait:
220 case OMPC_untied:
221 case OMPC_mergeable:
222 case OMPC_threadprivate:
223 case OMPC_flush:
224 case OMPC_depobj:
225 case OMPC_read:
226 case OMPC_write:
227 case OMPC_update:
228 case OMPC_capture:
229 case OMPC_compare:
230 case OMPC_fail:
231 case OMPC_seq_cst:
232 case OMPC_acq_rel:
233 case OMPC_acquire:
234 case OMPC_release:
235 case OMPC_relaxed:
236 case OMPC_depend:
237 case OMPC_device:
238 case OMPC_threads:
239 case OMPC_simd:
240 case OMPC_map:
241 case OMPC_num_teams:
242 case OMPC_thread_limit:
243 case OMPC_priority:
244 case OMPC_grainsize:
245 case OMPC_nogroup:
246 case OMPC_num_tasks:
247 case OMPC_hint:
248 case OMPC_defaultmap:
249 case OMPC_unknown:
250 case OMPC_uniform:
251 case OMPC_to:
252 case OMPC_from:
253 case OMPC_use_device_ptr:
254 case OMPC_use_device_addr:
255 case OMPC_is_device_ptr:
256 case OMPC_has_device_addr:
257 case OMPC_unified_address:
258 case OMPC_unified_shared_memory:
259 case OMPC_reverse_offload:
260 case OMPC_dynamic_allocators:
261 case OMPC_atomic_default_mem_order:
262 case OMPC_at:
263 case OMPC_severity:
264 case OMPC_message:
265 case OMPC_device_type:
266 case OMPC_match:
267 case OMPC_nontemporal:
268 case OMPC_order:
269 case OMPC_destroy:
270 case OMPC_novariants:
271 case OMPC_nocontext:
272 case OMPC_detach:
273 case OMPC_inclusive:
274 case OMPC_exclusive:
275 case OMPC_uses_allocators:
276 case OMPC_affinity:
277 case OMPC_when:
278 case OMPC_bind:
279 break;
280 default:
281 break;
284 return nullptr;
287 /// Gets the address of the original, non-captured, expression used in the
288 /// clause as the preinitializer.
289 static Stmt **getAddrOfExprAsWritten(Stmt *S) {
290 if (!S)
291 return nullptr;
292 if (auto *DS = dyn_cast<DeclStmt>(S)) {
293 assert(DS->isSingleDecl() && "Only single expression must be captured.");
294 if (auto *OED = dyn_cast<OMPCapturedExprDecl>(DS->getSingleDecl()))
295 return OED->getInitAddress();
297 return nullptr;
300 OMPClause::child_range OMPIfClause::used_children() {
301 if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
302 return child_range(C, C + 1);
303 return child_range(&Condition, &Condition + 1);
306 OMPClause::child_range OMPGrainsizeClause::used_children() {
307 if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
308 return child_range(C, C + 1);
309 return child_range(&Grainsize, &Grainsize + 1);
312 OMPClause::child_range OMPNumTasksClause::used_children() {
313 if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
314 return child_range(C, C + 1);
315 return child_range(&NumTasks, &NumTasks + 1);
318 OMPClause::child_range OMPFinalClause::used_children() {
319 if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
320 return child_range(C, C + 1);
321 return children();
324 OMPClause::child_range OMPPriorityClause::used_children() {
325 if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
326 return child_range(C, C + 1);
327 return child_range(&Priority, &Priority + 1);
330 OMPClause::child_range OMPNovariantsClause::used_children() {
331 if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
332 return child_range(C, C + 1);
333 return children();
336 OMPClause::child_range OMPNocontextClause::used_children() {
337 if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
338 return child_range(C, C + 1);
339 return children();
342 OMPOrderedClause *OMPOrderedClause::Create(const ASTContext &C, Expr *Num,
343 unsigned NumLoops,
344 SourceLocation StartLoc,
345 SourceLocation LParenLoc,
346 SourceLocation EndLoc) {
347 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * NumLoops));
348 auto *Clause =
349 new (Mem) OMPOrderedClause(Num, NumLoops, StartLoc, LParenLoc, EndLoc);
350 for (unsigned I = 0; I < NumLoops; ++I) {
351 Clause->setLoopNumIterations(I, nullptr);
352 Clause->setLoopCounter(I, nullptr);
354 return Clause;
357 OMPOrderedClause *OMPOrderedClause::CreateEmpty(const ASTContext &C,
358 unsigned NumLoops) {
359 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * NumLoops));
360 auto *Clause = new (Mem) OMPOrderedClause(NumLoops);
361 for (unsigned I = 0; I < NumLoops; ++I) {
362 Clause->setLoopNumIterations(I, nullptr);
363 Clause->setLoopCounter(I, nullptr);
365 return Clause;
368 void OMPOrderedClause::setLoopNumIterations(unsigned NumLoop,
369 Expr *NumIterations) {
370 assert(NumLoop < NumberOfLoops && "out of loops number.");
371 getTrailingObjects<Expr *>()[NumLoop] = NumIterations;
374 ArrayRef<Expr *> OMPOrderedClause::getLoopNumIterations() const {
375 return llvm::ArrayRef(getTrailingObjects<Expr *>(), NumberOfLoops);
378 void OMPOrderedClause::setLoopCounter(unsigned NumLoop, Expr *Counter) {
379 assert(NumLoop < NumberOfLoops && "out of loops number.");
380 getTrailingObjects<Expr *>()[NumberOfLoops + NumLoop] = Counter;
383 Expr *OMPOrderedClause::getLoopCounter(unsigned NumLoop) {
384 assert(NumLoop < NumberOfLoops && "out of loops number.");
385 return getTrailingObjects<Expr *>()[NumberOfLoops + NumLoop];
388 const Expr *OMPOrderedClause::getLoopCounter(unsigned NumLoop) const {
389 assert(NumLoop < NumberOfLoops && "out of loops number.");
390 return getTrailingObjects<Expr *>()[NumberOfLoops + NumLoop];
393 OMPUpdateClause *OMPUpdateClause::Create(const ASTContext &C,
394 SourceLocation StartLoc,
395 SourceLocation EndLoc) {
396 return new (C) OMPUpdateClause(StartLoc, EndLoc, /*IsExtended=*/false);
399 OMPUpdateClause *
400 OMPUpdateClause::Create(const ASTContext &C, SourceLocation StartLoc,
401 SourceLocation LParenLoc, SourceLocation ArgumentLoc,
402 OpenMPDependClauseKind DK, SourceLocation EndLoc) {
403 void *Mem =
404 C.Allocate(totalSizeToAlloc<SourceLocation, OpenMPDependClauseKind>(2, 1),
405 alignof(OMPUpdateClause));
406 auto *Clause =
407 new (Mem) OMPUpdateClause(StartLoc, EndLoc, /*IsExtended=*/true);
408 Clause->setLParenLoc(LParenLoc);
409 Clause->setArgumentLoc(ArgumentLoc);
410 Clause->setDependencyKind(DK);
411 return Clause;
414 OMPUpdateClause *OMPUpdateClause::CreateEmpty(const ASTContext &C,
415 bool IsExtended) {
416 if (!IsExtended)
417 return new (C) OMPUpdateClause(/*IsExtended=*/false);
418 void *Mem =
419 C.Allocate(totalSizeToAlloc<SourceLocation, OpenMPDependClauseKind>(2, 1),
420 alignof(OMPUpdateClause));
421 auto *Clause = new (Mem) OMPUpdateClause(/*IsExtended=*/true);
422 Clause->IsExtended = true;
423 return Clause;
426 void OMPPrivateClause::setPrivateCopies(ArrayRef<Expr *> VL) {
427 assert(VL.size() == varlist_size() &&
428 "Number of private copies is not the same as the preallocated buffer");
429 std::copy(VL.begin(), VL.end(), varlist_end());
432 OMPPrivateClause *
433 OMPPrivateClause::Create(const ASTContext &C, SourceLocation StartLoc,
434 SourceLocation LParenLoc, SourceLocation EndLoc,
435 ArrayRef<Expr *> VL, ArrayRef<Expr *> PrivateVL) {
436 // Allocate space for private variables and initializer expressions.
437 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * VL.size()));
438 OMPPrivateClause *Clause =
439 new (Mem) OMPPrivateClause(StartLoc, LParenLoc, EndLoc, VL.size());
440 Clause->setVarRefs(VL);
441 Clause->setPrivateCopies(PrivateVL);
442 return Clause;
445 OMPPrivateClause *OMPPrivateClause::CreateEmpty(const ASTContext &C,
446 unsigned N) {
447 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * N));
448 return new (Mem) OMPPrivateClause(N);
451 void OMPFirstprivateClause::setPrivateCopies(ArrayRef<Expr *> VL) {
452 assert(VL.size() == varlist_size() &&
453 "Number of private copies is not the same as the preallocated buffer");
454 std::copy(VL.begin(), VL.end(), varlist_end());
457 void OMPFirstprivateClause::setInits(ArrayRef<Expr *> VL) {
458 assert(VL.size() == varlist_size() &&
459 "Number of inits is not the same as the preallocated buffer");
460 std::copy(VL.begin(), VL.end(), getPrivateCopies().end());
463 OMPFirstprivateClause *
464 OMPFirstprivateClause::Create(const ASTContext &C, SourceLocation StartLoc,
465 SourceLocation LParenLoc, SourceLocation EndLoc,
466 ArrayRef<Expr *> VL, ArrayRef<Expr *> PrivateVL,
467 ArrayRef<Expr *> InitVL, Stmt *PreInit) {
468 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(3 * VL.size()));
469 OMPFirstprivateClause *Clause =
470 new (Mem) OMPFirstprivateClause(StartLoc, LParenLoc, EndLoc, VL.size());
471 Clause->setVarRefs(VL);
472 Clause->setPrivateCopies(PrivateVL);
473 Clause->setInits(InitVL);
474 Clause->setPreInitStmt(PreInit);
475 return Clause;
478 OMPFirstprivateClause *OMPFirstprivateClause::CreateEmpty(const ASTContext &C,
479 unsigned N) {
480 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(3 * N));
481 return new (Mem) OMPFirstprivateClause(N);
484 void OMPLastprivateClause::setPrivateCopies(ArrayRef<Expr *> PrivateCopies) {
485 assert(PrivateCopies.size() == varlist_size() &&
486 "Number of private copies is not the same as the preallocated buffer");
487 std::copy(PrivateCopies.begin(), PrivateCopies.end(), varlist_end());
490 void OMPLastprivateClause::setSourceExprs(ArrayRef<Expr *> SrcExprs) {
491 assert(SrcExprs.size() == varlist_size() && "Number of source expressions is "
492 "not the same as the "
493 "preallocated buffer");
494 std::copy(SrcExprs.begin(), SrcExprs.end(), getPrivateCopies().end());
497 void OMPLastprivateClause::setDestinationExprs(ArrayRef<Expr *> DstExprs) {
498 assert(DstExprs.size() == varlist_size() && "Number of destination "
499 "expressions is not the same as "
500 "the preallocated buffer");
501 std::copy(DstExprs.begin(), DstExprs.end(), getSourceExprs().end());
504 void OMPLastprivateClause::setAssignmentOps(ArrayRef<Expr *> AssignmentOps) {
505 assert(AssignmentOps.size() == varlist_size() &&
506 "Number of assignment expressions is not the same as the preallocated "
507 "buffer");
508 std::copy(AssignmentOps.begin(), AssignmentOps.end(),
509 getDestinationExprs().end());
512 OMPLastprivateClause *OMPLastprivateClause::Create(
513 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
514 SourceLocation EndLoc, ArrayRef<Expr *> VL, ArrayRef<Expr *> SrcExprs,
515 ArrayRef<Expr *> DstExprs, ArrayRef<Expr *> AssignmentOps,
516 OpenMPLastprivateModifier LPKind, SourceLocation LPKindLoc,
517 SourceLocation ColonLoc, Stmt *PreInit, Expr *PostUpdate) {
518 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * VL.size()));
519 OMPLastprivateClause *Clause = new (Mem) OMPLastprivateClause(
520 StartLoc, LParenLoc, EndLoc, LPKind, LPKindLoc, ColonLoc, VL.size());
521 Clause->setVarRefs(VL);
522 Clause->setSourceExprs(SrcExprs);
523 Clause->setDestinationExprs(DstExprs);
524 Clause->setAssignmentOps(AssignmentOps);
525 Clause->setPreInitStmt(PreInit);
526 Clause->setPostUpdateExpr(PostUpdate);
527 return Clause;
530 OMPLastprivateClause *OMPLastprivateClause::CreateEmpty(const ASTContext &C,
531 unsigned N) {
532 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * N));
533 return new (Mem) OMPLastprivateClause(N);
536 OMPSharedClause *OMPSharedClause::Create(const ASTContext &C,
537 SourceLocation StartLoc,
538 SourceLocation LParenLoc,
539 SourceLocation EndLoc,
540 ArrayRef<Expr *> VL) {
541 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size()));
542 OMPSharedClause *Clause =
543 new (Mem) OMPSharedClause(StartLoc, LParenLoc, EndLoc, VL.size());
544 Clause->setVarRefs(VL);
545 return Clause;
548 OMPSharedClause *OMPSharedClause::CreateEmpty(const ASTContext &C, unsigned N) {
549 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
550 return new (Mem) OMPSharedClause(N);
553 void OMPLinearClause::setPrivates(ArrayRef<Expr *> PL) {
554 assert(PL.size() == varlist_size() &&
555 "Number of privates is not the same as the preallocated buffer");
556 std::copy(PL.begin(), PL.end(), varlist_end());
559 void OMPLinearClause::setInits(ArrayRef<Expr *> IL) {
560 assert(IL.size() == varlist_size() &&
561 "Number of inits is not the same as the preallocated buffer");
562 std::copy(IL.begin(), IL.end(), getPrivates().end());
565 void OMPLinearClause::setUpdates(ArrayRef<Expr *> UL) {
566 assert(UL.size() == varlist_size() &&
567 "Number of updates is not the same as the preallocated buffer");
568 std::copy(UL.begin(), UL.end(), getInits().end());
571 void OMPLinearClause::setFinals(ArrayRef<Expr *> FL) {
572 assert(FL.size() == varlist_size() &&
573 "Number of final updates is not the same as the preallocated buffer");
574 std::copy(FL.begin(), FL.end(), getUpdates().end());
577 void OMPLinearClause::setUsedExprs(ArrayRef<Expr *> UE) {
578 assert(
579 UE.size() == varlist_size() + 1 &&
580 "Number of used expressions is not the same as the preallocated buffer");
581 std::copy(UE.begin(), UE.end(), getFinals().end() + 2);
584 OMPLinearClause *OMPLinearClause::Create(
585 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
586 OpenMPLinearClauseKind Modifier, SourceLocation ModifierLoc,
587 SourceLocation ColonLoc, SourceLocation StepModifierLoc,
588 SourceLocation EndLoc, ArrayRef<Expr *> VL, ArrayRef<Expr *> PL,
589 ArrayRef<Expr *> IL, Expr *Step, Expr *CalcStep, Stmt *PreInit,
590 Expr *PostUpdate) {
591 // Allocate space for 5 lists (Vars, Inits, Updates, Finals), 2 expressions
592 // (Step and CalcStep), list of used expression + step.
593 void *Mem =
594 C.Allocate(totalSizeToAlloc<Expr *>(5 * VL.size() + 2 + VL.size() + 1));
595 OMPLinearClause *Clause =
596 new (Mem) OMPLinearClause(StartLoc, LParenLoc, Modifier, ModifierLoc,
597 ColonLoc, StepModifierLoc, EndLoc, VL.size());
598 Clause->setVarRefs(VL);
599 Clause->setPrivates(PL);
600 Clause->setInits(IL);
601 // Fill update and final expressions with zeroes, they are provided later,
602 // after the directive construction.
603 std::fill(Clause->getInits().end(), Clause->getInits().end() + VL.size(),
604 nullptr);
605 std::fill(Clause->getUpdates().end(), Clause->getUpdates().end() + VL.size(),
606 nullptr);
607 std::fill(Clause->getUsedExprs().begin(), Clause->getUsedExprs().end(),
608 nullptr);
609 Clause->setStep(Step);
610 Clause->setCalcStep(CalcStep);
611 Clause->setPreInitStmt(PreInit);
612 Clause->setPostUpdateExpr(PostUpdate);
613 return Clause;
616 OMPLinearClause *OMPLinearClause::CreateEmpty(const ASTContext &C,
617 unsigned NumVars) {
618 // Allocate space for 5 lists (Vars, Inits, Updates, Finals), 2 expressions
619 // (Step and CalcStep), list of used expression + step.
620 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * NumVars + 2 + NumVars +1));
621 return new (Mem) OMPLinearClause(NumVars);
624 OMPClause::child_range OMPLinearClause::used_children() {
625 // Range includes only non-nullptr elements.
626 return child_range(
627 reinterpret_cast<Stmt **>(getUsedExprs().begin()),
628 reinterpret_cast<Stmt **>(llvm::find(getUsedExprs(), nullptr)));
631 OMPAlignedClause *
632 OMPAlignedClause::Create(const ASTContext &C, SourceLocation StartLoc,
633 SourceLocation LParenLoc, SourceLocation ColonLoc,
634 SourceLocation EndLoc, ArrayRef<Expr *> VL, Expr *A) {
635 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size() + 1));
636 OMPAlignedClause *Clause = new (Mem)
637 OMPAlignedClause(StartLoc, LParenLoc, ColonLoc, EndLoc, VL.size());
638 Clause->setVarRefs(VL);
639 Clause->setAlignment(A);
640 return Clause;
643 OMPAlignedClause *OMPAlignedClause::CreateEmpty(const ASTContext &C,
644 unsigned NumVars) {
645 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(NumVars + 1));
646 return new (Mem) OMPAlignedClause(NumVars);
649 OMPAlignClause *OMPAlignClause::Create(const ASTContext &C, Expr *A,
650 SourceLocation StartLoc,
651 SourceLocation LParenLoc,
652 SourceLocation EndLoc) {
653 return new (C) OMPAlignClause(A, StartLoc, LParenLoc, EndLoc);
656 void OMPCopyinClause::setSourceExprs(ArrayRef<Expr *> SrcExprs) {
657 assert(SrcExprs.size() == varlist_size() && "Number of source expressions is "
658 "not the same as the "
659 "preallocated buffer");
660 std::copy(SrcExprs.begin(), SrcExprs.end(), varlist_end());
663 void OMPCopyinClause::setDestinationExprs(ArrayRef<Expr *> DstExprs) {
664 assert(DstExprs.size() == varlist_size() && "Number of destination "
665 "expressions is not the same as "
666 "the preallocated buffer");
667 std::copy(DstExprs.begin(), DstExprs.end(), getSourceExprs().end());
670 void OMPCopyinClause::setAssignmentOps(ArrayRef<Expr *> AssignmentOps) {
671 assert(AssignmentOps.size() == varlist_size() &&
672 "Number of assignment expressions is not the same as the preallocated "
673 "buffer");
674 std::copy(AssignmentOps.begin(), AssignmentOps.end(),
675 getDestinationExprs().end());
678 OMPCopyinClause *OMPCopyinClause::Create(
679 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
680 SourceLocation EndLoc, ArrayRef<Expr *> VL, ArrayRef<Expr *> SrcExprs,
681 ArrayRef<Expr *> DstExprs, ArrayRef<Expr *> AssignmentOps) {
682 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(4 * VL.size()));
683 OMPCopyinClause *Clause =
684 new (Mem) OMPCopyinClause(StartLoc, LParenLoc, EndLoc, VL.size());
685 Clause->setVarRefs(VL);
686 Clause->setSourceExprs(SrcExprs);
687 Clause->setDestinationExprs(DstExprs);
688 Clause->setAssignmentOps(AssignmentOps);
689 return Clause;
692 OMPCopyinClause *OMPCopyinClause::CreateEmpty(const ASTContext &C, unsigned N) {
693 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(4 * N));
694 return new (Mem) OMPCopyinClause(N);
697 void OMPCopyprivateClause::setSourceExprs(ArrayRef<Expr *> SrcExprs) {
698 assert(SrcExprs.size() == varlist_size() && "Number of source expressions is "
699 "not the same as the "
700 "preallocated buffer");
701 std::copy(SrcExprs.begin(), SrcExprs.end(), varlist_end());
704 void OMPCopyprivateClause::setDestinationExprs(ArrayRef<Expr *> DstExprs) {
705 assert(DstExprs.size() == varlist_size() && "Number of destination "
706 "expressions is not the same as "
707 "the preallocated buffer");
708 std::copy(DstExprs.begin(), DstExprs.end(), getSourceExprs().end());
711 void OMPCopyprivateClause::setAssignmentOps(ArrayRef<Expr *> AssignmentOps) {
712 assert(AssignmentOps.size() == varlist_size() &&
713 "Number of assignment expressions is not the same as the preallocated "
714 "buffer");
715 std::copy(AssignmentOps.begin(), AssignmentOps.end(),
716 getDestinationExprs().end());
719 OMPCopyprivateClause *OMPCopyprivateClause::Create(
720 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
721 SourceLocation EndLoc, ArrayRef<Expr *> VL, ArrayRef<Expr *> SrcExprs,
722 ArrayRef<Expr *> DstExprs, ArrayRef<Expr *> AssignmentOps) {
723 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(4 * VL.size()));
724 OMPCopyprivateClause *Clause =
725 new (Mem) OMPCopyprivateClause(StartLoc, LParenLoc, EndLoc, VL.size());
726 Clause->setVarRefs(VL);
727 Clause->setSourceExprs(SrcExprs);
728 Clause->setDestinationExprs(DstExprs);
729 Clause->setAssignmentOps(AssignmentOps);
730 return Clause;
733 OMPCopyprivateClause *OMPCopyprivateClause::CreateEmpty(const ASTContext &C,
734 unsigned N) {
735 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(4 * N));
736 return new (Mem) OMPCopyprivateClause(N);
739 void OMPReductionClause::setPrivates(ArrayRef<Expr *> Privates) {
740 assert(Privates.size() == varlist_size() &&
741 "Number of private copies is not the same as the preallocated buffer");
742 std::copy(Privates.begin(), Privates.end(), varlist_end());
745 void OMPReductionClause::setLHSExprs(ArrayRef<Expr *> LHSExprs) {
746 assert(
747 LHSExprs.size() == varlist_size() &&
748 "Number of LHS expressions is not the same as the preallocated buffer");
749 std::copy(LHSExprs.begin(), LHSExprs.end(), getPrivates().end());
752 void OMPReductionClause::setRHSExprs(ArrayRef<Expr *> RHSExprs) {
753 assert(
754 RHSExprs.size() == varlist_size() &&
755 "Number of RHS expressions is not the same as the preallocated buffer");
756 std::copy(RHSExprs.begin(), RHSExprs.end(), getLHSExprs().end());
759 void OMPReductionClause::setReductionOps(ArrayRef<Expr *> ReductionOps) {
760 assert(ReductionOps.size() == varlist_size() && "Number of reduction "
761 "expressions is not the same "
762 "as the preallocated buffer");
763 std::copy(ReductionOps.begin(), ReductionOps.end(), getRHSExprs().end());
766 void OMPReductionClause::setInscanCopyOps(ArrayRef<Expr *> Ops) {
767 assert(Modifier == OMPC_REDUCTION_inscan && "Expected inscan reduction.");
768 assert(Ops.size() == varlist_size() && "Number of copy "
769 "expressions is not the same "
770 "as the preallocated buffer");
771 llvm::copy(Ops, getReductionOps().end());
774 void OMPReductionClause::setInscanCopyArrayTemps(
775 ArrayRef<Expr *> CopyArrayTemps) {
776 assert(Modifier == OMPC_REDUCTION_inscan && "Expected inscan reduction.");
777 assert(CopyArrayTemps.size() == varlist_size() &&
778 "Number of copy temp expressions is not the same as the preallocated "
779 "buffer");
780 llvm::copy(CopyArrayTemps, getInscanCopyOps().end());
783 void OMPReductionClause::setInscanCopyArrayElems(
784 ArrayRef<Expr *> CopyArrayElems) {
785 assert(Modifier == OMPC_REDUCTION_inscan && "Expected inscan reduction.");
786 assert(CopyArrayElems.size() == varlist_size() &&
787 "Number of copy temp expressions is not the same as the preallocated "
788 "buffer");
789 llvm::copy(CopyArrayElems, getInscanCopyArrayTemps().end());
792 OMPReductionClause *OMPReductionClause::Create(
793 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
794 SourceLocation ModifierLoc, SourceLocation EndLoc, SourceLocation ColonLoc,
795 OpenMPReductionClauseModifier Modifier, ArrayRef<Expr *> VL,
796 NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo,
797 ArrayRef<Expr *> Privates, ArrayRef<Expr *> LHSExprs,
798 ArrayRef<Expr *> RHSExprs, ArrayRef<Expr *> ReductionOps,
799 ArrayRef<Expr *> CopyOps, ArrayRef<Expr *> CopyArrayTemps,
800 ArrayRef<Expr *> CopyArrayElems, Stmt *PreInit, Expr *PostUpdate) {
801 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(
802 (Modifier == OMPC_REDUCTION_inscan ? 8 : 5) * VL.size()));
803 auto *Clause = new (Mem)
804 OMPReductionClause(StartLoc, LParenLoc, ModifierLoc, EndLoc, ColonLoc,
805 Modifier, VL.size(), QualifierLoc, NameInfo);
806 Clause->setVarRefs(VL);
807 Clause->setPrivates(Privates);
808 Clause->setLHSExprs(LHSExprs);
809 Clause->setRHSExprs(RHSExprs);
810 Clause->setReductionOps(ReductionOps);
811 Clause->setPreInitStmt(PreInit);
812 Clause->setPostUpdateExpr(PostUpdate);
813 if (Modifier == OMPC_REDUCTION_inscan) {
814 Clause->setInscanCopyOps(CopyOps);
815 Clause->setInscanCopyArrayTemps(CopyArrayTemps);
816 Clause->setInscanCopyArrayElems(CopyArrayElems);
817 } else {
818 assert(CopyOps.empty() &&
819 "copy operations are expected in inscan reductions only.");
820 assert(CopyArrayTemps.empty() &&
821 "copy array temps are expected in inscan reductions only.");
822 assert(CopyArrayElems.empty() &&
823 "copy array temps are expected in inscan reductions only.");
825 return Clause;
828 OMPReductionClause *
829 OMPReductionClause::CreateEmpty(const ASTContext &C, unsigned N,
830 OpenMPReductionClauseModifier Modifier) {
831 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(
832 (Modifier == OMPC_REDUCTION_inscan ? 8 : 5) * N));
833 auto *Clause = new (Mem) OMPReductionClause(N);
834 Clause->setModifier(Modifier);
835 return Clause;
838 void OMPTaskReductionClause::setPrivates(ArrayRef<Expr *> Privates) {
839 assert(Privates.size() == varlist_size() &&
840 "Number of private copies is not the same as the preallocated buffer");
841 std::copy(Privates.begin(), Privates.end(), varlist_end());
844 void OMPTaskReductionClause::setLHSExprs(ArrayRef<Expr *> LHSExprs) {
845 assert(
846 LHSExprs.size() == varlist_size() &&
847 "Number of LHS expressions is not the same as the preallocated buffer");
848 std::copy(LHSExprs.begin(), LHSExprs.end(), getPrivates().end());
851 void OMPTaskReductionClause::setRHSExprs(ArrayRef<Expr *> RHSExprs) {
852 assert(
853 RHSExprs.size() == varlist_size() &&
854 "Number of RHS expressions is not the same as the preallocated buffer");
855 std::copy(RHSExprs.begin(), RHSExprs.end(), getLHSExprs().end());
858 void OMPTaskReductionClause::setReductionOps(ArrayRef<Expr *> ReductionOps) {
859 assert(ReductionOps.size() == varlist_size() && "Number of task reduction "
860 "expressions is not the same "
861 "as the preallocated buffer");
862 std::copy(ReductionOps.begin(), ReductionOps.end(), getRHSExprs().end());
865 OMPTaskReductionClause *OMPTaskReductionClause::Create(
866 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
867 SourceLocation EndLoc, SourceLocation ColonLoc, ArrayRef<Expr *> VL,
868 NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo,
869 ArrayRef<Expr *> Privates, ArrayRef<Expr *> LHSExprs,
870 ArrayRef<Expr *> RHSExprs, ArrayRef<Expr *> ReductionOps, Stmt *PreInit,
871 Expr *PostUpdate) {
872 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * VL.size()));
873 OMPTaskReductionClause *Clause = new (Mem) OMPTaskReductionClause(
874 StartLoc, LParenLoc, EndLoc, ColonLoc, VL.size(), QualifierLoc, NameInfo);
875 Clause->setVarRefs(VL);
876 Clause->setPrivates(Privates);
877 Clause->setLHSExprs(LHSExprs);
878 Clause->setRHSExprs(RHSExprs);
879 Clause->setReductionOps(ReductionOps);
880 Clause->setPreInitStmt(PreInit);
881 Clause->setPostUpdateExpr(PostUpdate);
882 return Clause;
885 OMPTaskReductionClause *OMPTaskReductionClause::CreateEmpty(const ASTContext &C,
886 unsigned N) {
887 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * N));
888 return new (Mem) OMPTaskReductionClause(N);
891 void OMPInReductionClause::setPrivates(ArrayRef<Expr *> Privates) {
892 assert(Privates.size() == varlist_size() &&
893 "Number of private copies is not the same as the preallocated buffer");
894 std::copy(Privates.begin(), Privates.end(), varlist_end());
897 void OMPInReductionClause::setLHSExprs(ArrayRef<Expr *> LHSExprs) {
898 assert(
899 LHSExprs.size() == varlist_size() &&
900 "Number of LHS expressions is not the same as the preallocated buffer");
901 std::copy(LHSExprs.begin(), LHSExprs.end(), getPrivates().end());
904 void OMPInReductionClause::setRHSExprs(ArrayRef<Expr *> RHSExprs) {
905 assert(
906 RHSExprs.size() == varlist_size() &&
907 "Number of RHS expressions is not the same as the preallocated buffer");
908 std::copy(RHSExprs.begin(), RHSExprs.end(), getLHSExprs().end());
911 void OMPInReductionClause::setReductionOps(ArrayRef<Expr *> ReductionOps) {
912 assert(ReductionOps.size() == varlist_size() && "Number of in reduction "
913 "expressions is not the same "
914 "as the preallocated buffer");
915 std::copy(ReductionOps.begin(), ReductionOps.end(), getRHSExprs().end());
918 void OMPInReductionClause::setTaskgroupDescriptors(
919 ArrayRef<Expr *> TaskgroupDescriptors) {
920 assert(TaskgroupDescriptors.size() == varlist_size() &&
921 "Number of in reduction descriptors is not the same as the "
922 "preallocated buffer");
923 std::copy(TaskgroupDescriptors.begin(), TaskgroupDescriptors.end(),
924 getReductionOps().end());
927 OMPInReductionClause *OMPInReductionClause::Create(
928 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
929 SourceLocation EndLoc, SourceLocation ColonLoc, ArrayRef<Expr *> VL,
930 NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo,
931 ArrayRef<Expr *> Privates, ArrayRef<Expr *> LHSExprs,
932 ArrayRef<Expr *> RHSExprs, ArrayRef<Expr *> ReductionOps,
933 ArrayRef<Expr *> TaskgroupDescriptors, Stmt *PreInit, Expr *PostUpdate) {
934 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(6 * VL.size()));
935 OMPInReductionClause *Clause = new (Mem) OMPInReductionClause(
936 StartLoc, LParenLoc, EndLoc, ColonLoc, VL.size(), QualifierLoc, NameInfo);
937 Clause->setVarRefs(VL);
938 Clause->setPrivates(Privates);
939 Clause->setLHSExprs(LHSExprs);
940 Clause->setRHSExprs(RHSExprs);
941 Clause->setReductionOps(ReductionOps);
942 Clause->setTaskgroupDescriptors(TaskgroupDescriptors);
943 Clause->setPreInitStmt(PreInit);
944 Clause->setPostUpdateExpr(PostUpdate);
945 return Clause;
948 OMPInReductionClause *OMPInReductionClause::CreateEmpty(const ASTContext &C,
949 unsigned N) {
950 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(6 * N));
951 return new (Mem) OMPInReductionClause(N);
954 OMPSizesClause *OMPSizesClause::Create(const ASTContext &C,
955 SourceLocation StartLoc,
956 SourceLocation LParenLoc,
957 SourceLocation EndLoc,
958 ArrayRef<Expr *> Sizes) {
959 OMPSizesClause *Clause = CreateEmpty(C, Sizes.size());
960 Clause->setLocStart(StartLoc);
961 Clause->setLParenLoc(LParenLoc);
962 Clause->setLocEnd(EndLoc);
963 Clause->setSizesRefs(Sizes);
964 return Clause;
967 OMPSizesClause *OMPSizesClause::CreateEmpty(const ASTContext &C,
968 unsigned NumSizes) {
969 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(NumSizes));
970 return new (Mem) OMPSizesClause(NumSizes);
973 OMPPermutationClause *OMPPermutationClause::Create(const ASTContext &C,
974 SourceLocation StartLoc,
975 SourceLocation LParenLoc,
976 SourceLocation EndLoc,
977 ArrayRef<Expr *> Args) {
978 OMPPermutationClause *Clause = CreateEmpty(C, Args.size());
979 Clause->setLocStart(StartLoc);
980 Clause->setLParenLoc(LParenLoc);
981 Clause->setLocEnd(EndLoc);
982 Clause->setArgRefs(Args);
983 return Clause;
986 OMPPermutationClause *OMPPermutationClause::CreateEmpty(const ASTContext &C,
987 unsigned NumLoops) {
988 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(NumLoops));
989 return new (Mem) OMPPermutationClause(NumLoops);
992 OMPFullClause *OMPFullClause::Create(const ASTContext &C,
993 SourceLocation StartLoc,
994 SourceLocation EndLoc) {
995 OMPFullClause *Clause = CreateEmpty(C);
996 Clause->setLocStart(StartLoc);
997 Clause->setLocEnd(EndLoc);
998 return Clause;
1001 OMPFullClause *OMPFullClause::CreateEmpty(const ASTContext &C) {
1002 return new (C) OMPFullClause();
1005 OMPPartialClause *OMPPartialClause::Create(const ASTContext &C,
1006 SourceLocation StartLoc,
1007 SourceLocation LParenLoc,
1008 SourceLocation EndLoc,
1009 Expr *Factor) {
1010 OMPPartialClause *Clause = CreateEmpty(C);
1011 Clause->setLocStart(StartLoc);
1012 Clause->setLParenLoc(LParenLoc);
1013 Clause->setLocEnd(EndLoc);
1014 Clause->setFactor(Factor);
1015 return Clause;
1018 OMPPartialClause *OMPPartialClause::CreateEmpty(const ASTContext &C) {
1019 return new (C) OMPPartialClause();
1022 OMPAllocateClause *
1023 OMPAllocateClause::Create(const ASTContext &C, SourceLocation StartLoc,
1024 SourceLocation LParenLoc, Expr *Allocator,
1025 SourceLocation ColonLoc,
1026 OpenMPAllocateClauseModifier AllocatorModifier,
1027 SourceLocation AllocatorModifierLoc,
1028 SourceLocation EndLoc, ArrayRef<Expr *> VL) {
1030 // Allocate space for private variables and initializer expressions.
1031 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size()));
1032 auto *Clause = new (Mem) OMPAllocateClause(
1033 StartLoc, LParenLoc, Allocator, ColonLoc, AllocatorModifier,
1034 AllocatorModifierLoc, EndLoc, VL.size());
1036 Clause->setVarRefs(VL);
1037 return Clause;
1040 OMPAllocateClause *OMPAllocateClause::CreateEmpty(const ASTContext &C,
1041 unsigned N) {
1042 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
1043 return new (Mem) OMPAllocateClause(N);
1046 OMPFlushClause *OMPFlushClause::Create(const ASTContext &C,
1047 SourceLocation StartLoc,
1048 SourceLocation LParenLoc,
1049 SourceLocation EndLoc,
1050 ArrayRef<Expr *> VL) {
1051 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size() + 1));
1052 OMPFlushClause *Clause =
1053 new (Mem) OMPFlushClause(StartLoc, LParenLoc, EndLoc, VL.size());
1054 Clause->setVarRefs(VL);
1055 return Clause;
1058 OMPFlushClause *OMPFlushClause::CreateEmpty(const ASTContext &C, unsigned N) {
1059 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
1060 return new (Mem) OMPFlushClause(N);
1063 OMPDepobjClause *OMPDepobjClause::Create(const ASTContext &C,
1064 SourceLocation StartLoc,
1065 SourceLocation LParenLoc,
1066 SourceLocation RParenLoc,
1067 Expr *Depobj) {
1068 auto *Clause = new (C) OMPDepobjClause(StartLoc, LParenLoc, RParenLoc);
1069 Clause->setDepobj(Depobj);
1070 return Clause;
1073 OMPDepobjClause *OMPDepobjClause::CreateEmpty(const ASTContext &C) {
1074 return new (C) OMPDepobjClause();
1077 OMPDependClause *
1078 OMPDependClause::Create(const ASTContext &C, SourceLocation StartLoc,
1079 SourceLocation LParenLoc, SourceLocation EndLoc,
1080 DependDataTy Data, Expr *DepModifier,
1081 ArrayRef<Expr *> VL, unsigned NumLoops) {
1082 void *Mem = C.Allocate(
1083 totalSizeToAlloc<Expr *>(VL.size() + /*depend-modifier*/ 1 + NumLoops),
1084 alignof(OMPDependClause));
1085 OMPDependClause *Clause = new (Mem)
1086 OMPDependClause(StartLoc, LParenLoc, EndLoc, VL.size(), NumLoops);
1087 Clause->setDependencyKind(Data.DepKind);
1088 Clause->setDependencyLoc(Data.DepLoc);
1089 Clause->setColonLoc(Data.ColonLoc);
1090 Clause->setOmpAllMemoryLoc(Data.OmpAllMemoryLoc);
1091 Clause->setModifier(DepModifier);
1092 Clause->setVarRefs(VL);
1093 for (unsigned I = 0 ; I < NumLoops; ++I)
1094 Clause->setLoopData(I, nullptr);
1095 return Clause;
1098 OMPDependClause *OMPDependClause::CreateEmpty(const ASTContext &C, unsigned N,
1099 unsigned NumLoops) {
1100 void *Mem =
1101 C.Allocate(totalSizeToAlloc<Expr *>(N + /*depend-modifier*/ 1 + NumLoops),
1102 alignof(OMPDependClause));
1103 return new (Mem) OMPDependClause(N, NumLoops);
1106 void OMPDependClause::setLoopData(unsigned NumLoop, Expr *Cnt) {
1107 assert((getDependencyKind() == OMPC_DEPEND_sink ||
1108 getDependencyKind() == OMPC_DEPEND_source) &&
1109 NumLoop < NumLoops &&
1110 "Expected sink or source depend + loop index must be less number of "
1111 "loops.");
1112 auto *It = std::next(getVarRefs().end(), NumLoop + 1);
1113 *It = Cnt;
1116 Expr *OMPDependClause::getLoopData(unsigned NumLoop) {
1117 assert((getDependencyKind() == OMPC_DEPEND_sink ||
1118 getDependencyKind() == OMPC_DEPEND_source) &&
1119 NumLoop < NumLoops &&
1120 "Expected sink or source depend + loop index must be less number of "
1121 "loops.");
1122 auto *It = std::next(getVarRefs().end(), NumLoop + 1);
1123 return *It;
1126 const Expr *OMPDependClause::getLoopData(unsigned NumLoop) const {
1127 assert((getDependencyKind() == OMPC_DEPEND_sink ||
1128 getDependencyKind() == OMPC_DEPEND_source) &&
1129 NumLoop < NumLoops &&
1130 "Expected sink or source depend + loop index must be less number of "
1131 "loops.");
1132 const auto *It = std::next(getVarRefs().end(), NumLoop + 1);
1133 return *It;
1136 void OMPDependClause::setModifier(Expr *DepModifier) {
1137 *getVarRefs().end() = DepModifier;
1139 Expr *OMPDependClause::getModifier() { return *getVarRefs().end(); }
1141 unsigned OMPClauseMappableExprCommon::getComponentsTotalNumber(
1142 MappableExprComponentListsRef ComponentLists) {
1143 unsigned TotalNum = 0u;
1144 for (auto &C : ComponentLists)
1145 TotalNum += C.size();
1146 return TotalNum;
1149 unsigned OMPClauseMappableExprCommon::getUniqueDeclarationsTotalNumber(
1150 ArrayRef<const ValueDecl *> Declarations) {
1151 llvm::SmallPtrSet<const ValueDecl *, 8> UniqueDecls;
1152 for (const ValueDecl *D : Declarations) {
1153 const ValueDecl *VD = D ? cast<ValueDecl>(D->getCanonicalDecl()) : nullptr;
1154 UniqueDecls.insert(VD);
1156 return UniqueDecls.size();
1159 OMPMapClause *OMPMapClause::Create(
1160 const ASTContext &C, const OMPVarListLocTy &Locs, ArrayRef<Expr *> Vars,
1161 ArrayRef<ValueDecl *> Declarations,
1162 MappableExprComponentListsRef ComponentLists, ArrayRef<Expr *> UDMapperRefs,
1163 Expr *IteratorModifier, ArrayRef<OpenMPMapModifierKind> MapModifiers,
1164 ArrayRef<SourceLocation> MapModifiersLoc,
1165 NestedNameSpecifierLoc UDMQualifierLoc, DeclarationNameInfo MapperId,
1166 OpenMPMapClauseKind Type, bool TypeIsImplicit, SourceLocation TypeLoc) {
1167 OMPMappableExprListSizeTy Sizes;
1168 Sizes.NumVars = Vars.size();
1169 Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1170 Sizes.NumComponentLists = ComponentLists.size();
1171 Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1173 // We need to allocate:
1174 // 2 x NumVars x Expr* - we have an original list expression and an associated
1175 // user-defined mapper for each clause list entry.
1176 // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1177 // with each component list.
1178 // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1179 // number of lists for each unique declaration and the size of each component
1180 // list.
1181 // NumComponents x MappableComponent - the total of all the components in all
1182 // the lists.
1183 void *Mem = C.Allocate(
1184 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1185 OMPClauseMappableExprCommon::MappableComponent>(
1186 2 * Sizes.NumVars + 1, Sizes.NumUniqueDeclarations,
1187 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1188 Sizes.NumComponents));
1189 OMPMapClause *Clause = new (Mem)
1190 OMPMapClause(MapModifiers, MapModifiersLoc, UDMQualifierLoc, MapperId,
1191 Type, TypeIsImplicit, TypeLoc, Locs, Sizes);
1193 Clause->setVarRefs(Vars);
1194 Clause->setUDMapperRefs(UDMapperRefs);
1195 Clause->setIteratorModifier(IteratorModifier);
1196 Clause->setClauseInfo(Declarations, ComponentLists);
1197 Clause->setMapType(Type);
1198 Clause->setMapLoc(TypeLoc);
1199 return Clause;
1202 OMPMapClause *
1203 OMPMapClause::CreateEmpty(const ASTContext &C,
1204 const OMPMappableExprListSizeTy &Sizes) {
1205 void *Mem = C.Allocate(
1206 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1207 OMPClauseMappableExprCommon::MappableComponent>(
1208 2 * Sizes.NumVars + 1, Sizes.NumUniqueDeclarations,
1209 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1210 Sizes.NumComponents));
1211 OMPMapClause *Clause = new (Mem) OMPMapClause(Sizes);
1212 Clause->setIteratorModifier(nullptr);
1213 return Clause;
1216 OMPToClause *OMPToClause::Create(
1217 const ASTContext &C, const OMPVarListLocTy &Locs, ArrayRef<Expr *> Vars,
1218 ArrayRef<ValueDecl *> Declarations,
1219 MappableExprComponentListsRef ComponentLists, ArrayRef<Expr *> UDMapperRefs,
1220 ArrayRef<OpenMPMotionModifierKind> MotionModifiers,
1221 ArrayRef<SourceLocation> MotionModifiersLoc,
1222 NestedNameSpecifierLoc UDMQualifierLoc, DeclarationNameInfo MapperId) {
1223 OMPMappableExprListSizeTy Sizes;
1224 Sizes.NumVars = Vars.size();
1225 Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1226 Sizes.NumComponentLists = ComponentLists.size();
1227 Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1229 // We need to allocate:
1230 // 2 x NumVars x Expr* - we have an original list expression and an associated
1231 // user-defined mapper for each clause list entry.
1232 // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1233 // with each component list.
1234 // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1235 // number of lists for each unique declaration and the size of each component
1236 // list.
1237 // NumComponents x MappableComponent - the total of all the components in all
1238 // the lists.
1239 void *Mem = C.Allocate(
1240 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1241 OMPClauseMappableExprCommon::MappableComponent>(
1242 2 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1243 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1244 Sizes.NumComponents));
1246 auto *Clause = new (Mem) OMPToClause(MotionModifiers, MotionModifiersLoc,
1247 UDMQualifierLoc, MapperId, Locs, Sizes);
1249 Clause->setVarRefs(Vars);
1250 Clause->setUDMapperRefs(UDMapperRefs);
1251 Clause->setClauseInfo(Declarations, ComponentLists);
1252 return Clause;
1255 OMPToClause *OMPToClause::CreateEmpty(const ASTContext &C,
1256 const OMPMappableExprListSizeTy &Sizes) {
1257 void *Mem = C.Allocate(
1258 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1259 OMPClauseMappableExprCommon::MappableComponent>(
1260 2 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1261 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1262 Sizes.NumComponents));
1263 return new (Mem) OMPToClause(Sizes);
1266 OMPFromClause *OMPFromClause::Create(
1267 const ASTContext &C, const OMPVarListLocTy &Locs, ArrayRef<Expr *> Vars,
1268 ArrayRef<ValueDecl *> Declarations,
1269 MappableExprComponentListsRef ComponentLists, ArrayRef<Expr *> UDMapperRefs,
1270 ArrayRef<OpenMPMotionModifierKind> MotionModifiers,
1271 ArrayRef<SourceLocation> MotionModifiersLoc,
1272 NestedNameSpecifierLoc UDMQualifierLoc, DeclarationNameInfo MapperId) {
1273 OMPMappableExprListSizeTy Sizes;
1274 Sizes.NumVars = Vars.size();
1275 Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1276 Sizes.NumComponentLists = ComponentLists.size();
1277 Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1279 // We need to allocate:
1280 // 2 x NumVars x Expr* - we have an original list expression and an associated
1281 // user-defined mapper for each clause list entry.
1282 // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1283 // with each component list.
1284 // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1285 // number of lists for each unique declaration and the size of each component
1286 // list.
1287 // NumComponents x MappableComponent - the total of all the components in all
1288 // the lists.
1289 void *Mem = C.Allocate(
1290 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1291 OMPClauseMappableExprCommon::MappableComponent>(
1292 2 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1293 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1294 Sizes.NumComponents));
1296 auto *Clause =
1297 new (Mem) OMPFromClause(MotionModifiers, MotionModifiersLoc,
1298 UDMQualifierLoc, MapperId, Locs, Sizes);
1300 Clause->setVarRefs(Vars);
1301 Clause->setUDMapperRefs(UDMapperRefs);
1302 Clause->setClauseInfo(Declarations, ComponentLists);
1303 return Clause;
1306 OMPFromClause *
1307 OMPFromClause::CreateEmpty(const ASTContext &C,
1308 const OMPMappableExprListSizeTy &Sizes) {
1309 void *Mem = C.Allocate(
1310 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1311 OMPClauseMappableExprCommon::MappableComponent>(
1312 2 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1313 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1314 Sizes.NumComponents));
1315 return new (Mem) OMPFromClause(Sizes);
1318 void OMPUseDevicePtrClause::setPrivateCopies(ArrayRef<Expr *> VL) {
1319 assert(VL.size() == varlist_size() &&
1320 "Number of private copies is not the same as the preallocated buffer");
1321 std::copy(VL.begin(), VL.end(), varlist_end());
1324 void OMPUseDevicePtrClause::setInits(ArrayRef<Expr *> VL) {
1325 assert(VL.size() == varlist_size() &&
1326 "Number of inits is not the same as the preallocated buffer");
1327 std::copy(VL.begin(), VL.end(), getPrivateCopies().end());
1330 OMPUseDevicePtrClause *OMPUseDevicePtrClause::Create(
1331 const ASTContext &C, const OMPVarListLocTy &Locs, ArrayRef<Expr *> Vars,
1332 ArrayRef<Expr *> PrivateVars, ArrayRef<Expr *> Inits,
1333 ArrayRef<ValueDecl *> Declarations,
1334 MappableExprComponentListsRef ComponentLists) {
1335 OMPMappableExprListSizeTy Sizes;
1336 Sizes.NumVars = Vars.size();
1337 Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1338 Sizes.NumComponentLists = ComponentLists.size();
1339 Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1341 // We need to allocate:
1342 // NumVars x Expr* - we have an original list expression for each clause
1343 // list entry.
1344 // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1345 // with each component list.
1346 // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1347 // number of lists for each unique declaration and the size of each component
1348 // list.
1349 // NumComponents x MappableComponent - the total of all the components in all
1350 // the lists.
1351 void *Mem = C.Allocate(
1352 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1353 OMPClauseMappableExprCommon::MappableComponent>(
1354 3 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1355 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1356 Sizes.NumComponents));
1358 OMPUseDevicePtrClause *Clause = new (Mem) OMPUseDevicePtrClause(Locs, Sizes);
1360 Clause->setVarRefs(Vars);
1361 Clause->setPrivateCopies(PrivateVars);
1362 Clause->setInits(Inits);
1363 Clause->setClauseInfo(Declarations, ComponentLists);
1364 return Clause;
1367 OMPUseDevicePtrClause *
1368 OMPUseDevicePtrClause::CreateEmpty(const ASTContext &C,
1369 const OMPMappableExprListSizeTy &Sizes) {
1370 void *Mem = C.Allocate(
1371 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1372 OMPClauseMappableExprCommon::MappableComponent>(
1373 3 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1374 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1375 Sizes.NumComponents));
1376 return new (Mem) OMPUseDevicePtrClause(Sizes);
1379 OMPUseDeviceAddrClause *
1380 OMPUseDeviceAddrClause::Create(const ASTContext &C, const OMPVarListLocTy &Locs,
1381 ArrayRef<Expr *> Vars,
1382 ArrayRef<ValueDecl *> Declarations,
1383 MappableExprComponentListsRef ComponentLists) {
1384 OMPMappableExprListSizeTy Sizes;
1385 Sizes.NumVars = Vars.size();
1386 Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1387 Sizes.NumComponentLists = ComponentLists.size();
1388 Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1390 // We need to allocate:
1391 // 3 x NumVars x Expr* - we have an original list expression for each clause
1392 // list entry and an equal number of private copies and inits.
1393 // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1394 // with each component list.
1395 // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1396 // number of lists for each unique declaration and the size of each component
1397 // list.
1398 // NumComponents x MappableComponent - the total of all the components in all
1399 // the lists.
1400 void *Mem = C.Allocate(
1401 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1402 OMPClauseMappableExprCommon::MappableComponent>(
1403 Sizes.NumVars, Sizes.NumUniqueDeclarations,
1404 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1405 Sizes.NumComponents));
1407 auto *Clause = new (Mem) OMPUseDeviceAddrClause(Locs, Sizes);
1409 Clause->setVarRefs(Vars);
1410 Clause->setClauseInfo(Declarations, ComponentLists);
1411 return Clause;
1414 OMPUseDeviceAddrClause *
1415 OMPUseDeviceAddrClause::CreateEmpty(const ASTContext &C,
1416 const OMPMappableExprListSizeTy &Sizes) {
1417 void *Mem = C.Allocate(
1418 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1419 OMPClauseMappableExprCommon::MappableComponent>(
1420 Sizes.NumVars, Sizes.NumUniqueDeclarations,
1421 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1422 Sizes.NumComponents));
1423 return new (Mem) OMPUseDeviceAddrClause(Sizes);
1426 OMPIsDevicePtrClause *
1427 OMPIsDevicePtrClause::Create(const ASTContext &C, const OMPVarListLocTy &Locs,
1428 ArrayRef<Expr *> Vars,
1429 ArrayRef<ValueDecl *> Declarations,
1430 MappableExprComponentListsRef ComponentLists) {
1431 OMPMappableExprListSizeTy Sizes;
1432 Sizes.NumVars = Vars.size();
1433 Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1434 Sizes.NumComponentLists = ComponentLists.size();
1435 Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1437 // We need to allocate:
1438 // NumVars x Expr* - we have an original list expression for each clause list
1439 // entry.
1440 // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1441 // with each component list.
1442 // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1443 // number of lists for each unique declaration and the size of each component
1444 // list.
1445 // NumComponents x MappableComponent - the total of all the components in all
1446 // the lists.
1447 void *Mem = C.Allocate(
1448 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1449 OMPClauseMappableExprCommon::MappableComponent>(
1450 Sizes.NumVars, Sizes.NumUniqueDeclarations,
1451 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1452 Sizes.NumComponents));
1454 OMPIsDevicePtrClause *Clause = new (Mem) OMPIsDevicePtrClause(Locs, Sizes);
1456 Clause->setVarRefs(Vars);
1457 Clause->setClauseInfo(Declarations, ComponentLists);
1458 return Clause;
1461 OMPIsDevicePtrClause *
1462 OMPIsDevicePtrClause::CreateEmpty(const ASTContext &C,
1463 const OMPMappableExprListSizeTy &Sizes) {
1464 void *Mem = C.Allocate(
1465 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1466 OMPClauseMappableExprCommon::MappableComponent>(
1467 Sizes.NumVars, Sizes.NumUniqueDeclarations,
1468 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1469 Sizes.NumComponents));
1470 return new (Mem) OMPIsDevicePtrClause(Sizes);
1473 OMPHasDeviceAddrClause *
1474 OMPHasDeviceAddrClause::Create(const ASTContext &C, const OMPVarListLocTy &Locs,
1475 ArrayRef<Expr *> Vars,
1476 ArrayRef<ValueDecl *> Declarations,
1477 MappableExprComponentListsRef ComponentLists) {
1478 OMPMappableExprListSizeTy Sizes;
1479 Sizes.NumVars = Vars.size();
1480 Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1481 Sizes.NumComponentLists = ComponentLists.size();
1482 Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1484 // We need to allocate:
1485 // NumVars x Expr* - we have an original list expression for each clause list
1486 // entry.
1487 // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1488 // with each component list.
1489 // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1490 // number of lists for each unique declaration and the size of each component
1491 // list.
1492 // NumComponents x MappableComponent - the total of all the components in all
1493 // the lists.
1494 void *Mem = C.Allocate(
1495 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1496 OMPClauseMappableExprCommon::MappableComponent>(
1497 Sizes.NumVars, Sizes.NumUniqueDeclarations,
1498 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1499 Sizes.NumComponents));
1501 auto *Clause = new (Mem) OMPHasDeviceAddrClause(Locs, Sizes);
1503 Clause->setVarRefs(Vars);
1504 Clause->setClauseInfo(Declarations, ComponentLists);
1505 return Clause;
1508 OMPHasDeviceAddrClause *
1509 OMPHasDeviceAddrClause::CreateEmpty(const ASTContext &C,
1510 const OMPMappableExprListSizeTy &Sizes) {
1511 void *Mem = C.Allocate(
1512 totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1513 OMPClauseMappableExprCommon::MappableComponent>(
1514 Sizes.NumVars, Sizes.NumUniqueDeclarations,
1515 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1516 Sizes.NumComponents));
1517 return new (Mem) OMPHasDeviceAddrClause(Sizes);
1520 OMPNontemporalClause *OMPNontemporalClause::Create(const ASTContext &C,
1521 SourceLocation StartLoc,
1522 SourceLocation LParenLoc,
1523 SourceLocation EndLoc,
1524 ArrayRef<Expr *> VL) {
1525 // Allocate space for nontemporal variables + private references.
1526 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * VL.size()));
1527 auto *Clause =
1528 new (Mem) OMPNontemporalClause(StartLoc, LParenLoc, EndLoc, VL.size());
1529 Clause->setVarRefs(VL);
1530 return Clause;
1533 OMPNontemporalClause *OMPNontemporalClause::CreateEmpty(const ASTContext &C,
1534 unsigned N) {
1535 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * N));
1536 return new (Mem) OMPNontemporalClause(N);
1539 void OMPNontemporalClause::setPrivateRefs(ArrayRef<Expr *> VL) {
1540 assert(VL.size() == varlist_size() && "Number of private references is not "
1541 "the same as the preallocated buffer");
1542 std::copy(VL.begin(), VL.end(), varlist_end());
1545 OMPInclusiveClause *OMPInclusiveClause::Create(const ASTContext &C,
1546 SourceLocation StartLoc,
1547 SourceLocation LParenLoc,
1548 SourceLocation EndLoc,
1549 ArrayRef<Expr *> VL) {
1550 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size()));
1551 auto *Clause =
1552 new (Mem) OMPInclusiveClause(StartLoc, LParenLoc, EndLoc, VL.size());
1553 Clause->setVarRefs(VL);
1554 return Clause;
1557 OMPInclusiveClause *OMPInclusiveClause::CreateEmpty(const ASTContext &C,
1558 unsigned N) {
1559 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
1560 return new (Mem) OMPInclusiveClause(N);
1563 OMPExclusiveClause *OMPExclusiveClause::Create(const ASTContext &C,
1564 SourceLocation StartLoc,
1565 SourceLocation LParenLoc,
1566 SourceLocation EndLoc,
1567 ArrayRef<Expr *> VL) {
1568 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size()));
1569 auto *Clause =
1570 new (Mem) OMPExclusiveClause(StartLoc, LParenLoc, EndLoc, VL.size());
1571 Clause->setVarRefs(VL);
1572 return Clause;
1575 OMPExclusiveClause *OMPExclusiveClause::CreateEmpty(const ASTContext &C,
1576 unsigned N) {
1577 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
1578 return new (Mem) OMPExclusiveClause(N);
1581 void OMPUsesAllocatorsClause::setAllocatorsData(
1582 ArrayRef<OMPUsesAllocatorsClause::Data> Data) {
1583 assert(Data.size() == NumOfAllocators &&
1584 "Size of allocators data is not the same as the preallocated buffer.");
1585 for (unsigned I = 0, E = Data.size(); I < E; ++I) {
1586 const OMPUsesAllocatorsClause::Data &D = Data[I];
1587 getTrailingObjects<Expr *>()[I * static_cast<int>(ExprOffsets::Total) +
1588 static_cast<int>(ExprOffsets::Allocator)] =
1589 D.Allocator;
1590 getTrailingObjects<Expr *>()[I * static_cast<int>(ExprOffsets::Total) +
1591 static_cast<int>(
1592 ExprOffsets::AllocatorTraits)] =
1593 D.AllocatorTraits;
1594 getTrailingObjects<
1595 SourceLocation>()[I * static_cast<int>(ParenLocsOffsets::Total) +
1596 static_cast<int>(ParenLocsOffsets::LParen)] =
1597 D.LParenLoc;
1598 getTrailingObjects<
1599 SourceLocation>()[I * static_cast<int>(ParenLocsOffsets::Total) +
1600 static_cast<int>(ParenLocsOffsets::RParen)] =
1601 D.RParenLoc;
1605 OMPUsesAllocatorsClause::Data
1606 OMPUsesAllocatorsClause::getAllocatorData(unsigned I) const {
1607 OMPUsesAllocatorsClause::Data Data;
1608 Data.Allocator =
1609 getTrailingObjects<Expr *>()[I * static_cast<int>(ExprOffsets::Total) +
1610 static_cast<int>(ExprOffsets::Allocator)];
1611 Data.AllocatorTraits =
1612 getTrailingObjects<Expr *>()[I * static_cast<int>(ExprOffsets::Total) +
1613 static_cast<int>(
1614 ExprOffsets::AllocatorTraits)];
1615 Data.LParenLoc = getTrailingObjects<
1616 SourceLocation>()[I * static_cast<int>(ParenLocsOffsets::Total) +
1617 static_cast<int>(ParenLocsOffsets::LParen)];
1618 Data.RParenLoc = getTrailingObjects<
1619 SourceLocation>()[I * static_cast<int>(ParenLocsOffsets::Total) +
1620 static_cast<int>(ParenLocsOffsets::RParen)];
1621 return Data;
1624 OMPUsesAllocatorsClause *
1625 OMPUsesAllocatorsClause::Create(const ASTContext &C, SourceLocation StartLoc,
1626 SourceLocation LParenLoc, SourceLocation EndLoc,
1627 ArrayRef<OMPUsesAllocatorsClause::Data> Data) {
1628 void *Mem = C.Allocate(totalSizeToAlloc<Expr *, SourceLocation>(
1629 static_cast<int>(ExprOffsets::Total) * Data.size(),
1630 static_cast<int>(ParenLocsOffsets::Total) * Data.size()));
1631 auto *Clause = new (Mem)
1632 OMPUsesAllocatorsClause(StartLoc, LParenLoc, EndLoc, Data.size());
1633 Clause->setAllocatorsData(Data);
1634 return Clause;
1637 OMPUsesAllocatorsClause *
1638 OMPUsesAllocatorsClause::CreateEmpty(const ASTContext &C, unsigned N) {
1639 void *Mem = C.Allocate(totalSizeToAlloc<Expr *, SourceLocation>(
1640 static_cast<int>(ExprOffsets::Total) * N,
1641 static_cast<int>(ParenLocsOffsets::Total) * N));
1642 return new (Mem) OMPUsesAllocatorsClause(N);
1645 OMPAffinityClause *
1646 OMPAffinityClause::Create(const ASTContext &C, SourceLocation StartLoc,
1647 SourceLocation LParenLoc, SourceLocation ColonLoc,
1648 SourceLocation EndLoc, Expr *Modifier,
1649 ArrayRef<Expr *> Locators) {
1650 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(Locators.size() + 1));
1651 auto *Clause = new (Mem)
1652 OMPAffinityClause(StartLoc, LParenLoc, ColonLoc, EndLoc, Locators.size());
1653 Clause->setModifier(Modifier);
1654 Clause->setVarRefs(Locators);
1655 return Clause;
1658 OMPAffinityClause *OMPAffinityClause::CreateEmpty(const ASTContext &C,
1659 unsigned N) {
1660 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N + 1));
1661 return new (Mem) OMPAffinityClause(N);
1664 OMPInitClause *OMPInitClause::Create(const ASTContext &C, Expr *InteropVar,
1665 OMPInteropInfo &InteropInfo,
1666 SourceLocation StartLoc,
1667 SourceLocation LParenLoc,
1668 SourceLocation VarLoc,
1669 SourceLocation EndLoc) {
1671 void *Mem =
1672 C.Allocate(totalSizeToAlloc<Expr *>(InteropInfo.PreferTypes.size() + 1));
1673 auto *Clause = new (Mem) OMPInitClause(
1674 InteropInfo.IsTarget, InteropInfo.IsTargetSync, StartLoc, LParenLoc,
1675 VarLoc, EndLoc, InteropInfo.PreferTypes.size() + 1);
1676 Clause->setInteropVar(InteropVar);
1677 llvm::copy(InteropInfo.PreferTypes, Clause->getTrailingObjects<Expr *>() + 1);
1678 return Clause;
1681 OMPInitClause *OMPInitClause::CreateEmpty(const ASTContext &C, unsigned N) {
1682 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
1683 return new (Mem) OMPInitClause(N);
1686 OMPBindClause *
1687 OMPBindClause::Create(const ASTContext &C, OpenMPBindClauseKind K,
1688 SourceLocation KLoc, SourceLocation StartLoc,
1689 SourceLocation LParenLoc, SourceLocation EndLoc) {
1690 return new (C) OMPBindClause(K, KLoc, StartLoc, LParenLoc, EndLoc);
1693 OMPBindClause *OMPBindClause::CreateEmpty(const ASTContext &C) {
1694 return new (C) OMPBindClause();
1697 OMPDoacrossClause *
1698 OMPDoacrossClause::Create(const ASTContext &C, SourceLocation StartLoc,
1699 SourceLocation LParenLoc, SourceLocation EndLoc,
1700 OpenMPDoacrossClauseModifier DepType,
1701 SourceLocation DepLoc, SourceLocation ColonLoc,
1702 ArrayRef<Expr *> VL, unsigned NumLoops) {
1703 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size() + NumLoops),
1704 alignof(OMPDoacrossClause));
1705 OMPDoacrossClause *Clause = new (Mem)
1706 OMPDoacrossClause(StartLoc, LParenLoc, EndLoc, VL.size(), NumLoops);
1707 Clause->setDependenceType(DepType);
1708 Clause->setDependenceLoc(DepLoc);
1709 Clause->setColonLoc(ColonLoc);
1710 Clause->setVarRefs(VL);
1711 for (unsigned I = 0; I < NumLoops; ++I)
1712 Clause->setLoopData(I, nullptr);
1713 return Clause;
1716 OMPDoacrossClause *OMPDoacrossClause::CreateEmpty(const ASTContext &C,
1717 unsigned N,
1718 unsigned NumLoops) {
1719 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N + NumLoops),
1720 alignof(OMPDoacrossClause));
1721 return new (Mem) OMPDoacrossClause(N, NumLoops);
1724 void OMPDoacrossClause::setLoopData(unsigned NumLoop, Expr *Cnt) {
1725 assert(NumLoop < NumLoops && "Loop index must be less number of loops.");
1726 auto *It = std::next(getVarRefs().end(), NumLoop);
1727 *It = Cnt;
1730 Expr *OMPDoacrossClause::getLoopData(unsigned NumLoop) {
1731 assert(NumLoop < NumLoops && "Loop index must be less number of loops.");
1732 auto *It = std::next(getVarRefs().end(), NumLoop);
1733 return *It;
1736 const Expr *OMPDoacrossClause::getLoopData(unsigned NumLoop) const {
1737 assert(NumLoop < NumLoops && "Loop index must be less number of loops.");
1738 const auto *It = std::next(getVarRefs().end(), NumLoop);
1739 return *It;
1742 OMPAbsentClause *OMPAbsentClause::Create(const ASTContext &C,
1743 ArrayRef<OpenMPDirectiveKind> DKVec,
1744 SourceLocation Loc,
1745 SourceLocation LLoc,
1746 SourceLocation RLoc) {
1747 void *Mem = C.Allocate(totalSizeToAlloc<OpenMPDirectiveKind>(DKVec.size()),
1748 alignof(OMPAbsentClause));
1749 auto *AC = new (Mem) OMPAbsentClause(Loc, LLoc, RLoc, DKVec.size());
1750 AC->setDirectiveKinds(DKVec);
1751 return AC;
1754 OMPAbsentClause *OMPAbsentClause::CreateEmpty(const ASTContext &C, unsigned K) {
1755 void *Mem = C.Allocate(totalSizeToAlloc<OpenMPDirectiveKind>(K),
1756 alignof(OMPAbsentClause));
1757 return new (Mem) OMPAbsentClause(K);
1760 OMPContainsClause *OMPContainsClause::Create(
1761 const ASTContext &C, ArrayRef<OpenMPDirectiveKind> DKVec,
1762 SourceLocation Loc, SourceLocation LLoc, SourceLocation RLoc) {
1763 void *Mem = C.Allocate(totalSizeToAlloc<OpenMPDirectiveKind>(DKVec.size()),
1764 alignof(OMPContainsClause));
1765 auto *CC = new (Mem) OMPContainsClause(Loc, LLoc, RLoc, DKVec.size());
1766 CC->setDirectiveKinds(DKVec);
1767 return CC;
1770 OMPContainsClause *OMPContainsClause::CreateEmpty(const ASTContext &C,
1771 unsigned K) {
1772 void *Mem = C.Allocate(totalSizeToAlloc<OpenMPDirectiveKind>(K),
1773 alignof(OMPContainsClause));
1774 return new (Mem) OMPContainsClause(K);
1777 OMPNumTeamsClause *OMPNumTeamsClause::Create(
1778 const ASTContext &C, OpenMPDirectiveKind CaptureRegion,
1779 SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc,
1780 ArrayRef<Expr *> VL, Stmt *PreInit) {
1781 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size()));
1782 OMPNumTeamsClause *Clause =
1783 new (Mem) OMPNumTeamsClause(C, StartLoc, LParenLoc, EndLoc, VL.size());
1784 Clause->setVarRefs(VL);
1785 Clause->setPreInitStmt(PreInit, CaptureRegion);
1786 return Clause;
1789 OMPNumTeamsClause *OMPNumTeamsClause::CreateEmpty(const ASTContext &C,
1790 unsigned N) {
1791 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
1792 return new (Mem) OMPNumTeamsClause(N);
1795 OMPThreadLimitClause *OMPThreadLimitClause::Create(
1796 const ASTContext &C, OpenMPDirectiveKind CaptureRegion,
1797 SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc,
1798 ArrayRef<Expr *> VL, Stmt *PreInit) {
1799 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size()));
1800 OMPThreadLimitClause *Clause =
1801 new (Mem) OMPThreadLimitClause(C, StartLoc, LParenLoc, EndLoc, VL.size());
1802 Clause->setVarRefs(VL);
1803 Clause->setPreInitStmt(PreInit, CaptureRegion);
1804 return Clause;
1807 OMPThreadLimitClause *OMPThreadLimitClause::CreateEmpty(const ASTContext &C,
1808 unsigned N) {
1809 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
1810 return new (Mem) OMPThreadLimitClause(N);
1813 //===----------------------------------------------------------------------===//
1814 // OpenMP clauses printing methods
1815 //===----------------------------------------------------------------------===//
1817 void OMPClausePrinter::VisitOMPIfClause(OMPIfClause *Node) {
1818 OS << "if(";
1819 if (Node->getNameModifier() != OMPD_unknown)
1820 OS << getOpenMPDirectiveName(Node->getNameModifier()) << ": ";
1821 Node->getCondition()->printPretty(OS, nullptr, Policy, 0);
1822 OS << ")";
1825 void OMPClausePrinter::VisitOMPFinalClause(OMPFinalClause *Node) {
1826 OS << "final(";
1827 Node->getCondition()->printPretty(OS, nullptr, Policy, 0);
1828 OS << ")";
1831 void OMPClausePrinter::VisitOMPNumThreadsClause(OMPNumThreadsClause *Node) {
1832 OS << "num_threads(";
1833 Node->getNumThreads()->printPretty(OS, nullptr, Policy, 0);
1834 OS << ")";
1837 void OMPClausePrinter::VisitOMPAlignClause(OMPAlignClause *Node) {
1838 OS << "align(";
1839 Node->getAlignment()->printPretty(OS, nullptr, Policy, 0);
1840 OS << ")";
1843 void OMPClausePrinter::VisitOMPSafelenClause(OMPSafelenClause *Node) {
1844 OS << "safelen(";
1845 Node->getSafelen()->printPretty(OS, nullptr, Policy, 0);
1846 OS << ")";
1849 void OMPClausePrinter::VisitOMPSimdlenClause(OMPSimdlenClause *Node) {
1850 OS << "simdlen(";
1851 Node->getSimdlen()->printPretty(OS, nullptr, Policy, 0);
1852 OS << ")";
1855 void OMPClausePrinter::VisitOMPSizesClause(OMPSizesClause *Node) {
1856 OS << "sizes(";
1857 bool First = true;
1858 for (auto *Size : Node->getSizesRefs()) {
1859 if (!First)
1860 OS << ", ";
1861 Size->printPretty(OS, nullptr, Policy, 0);
1862 First = false;
1864 OS << ")";
1867 void OMPClausePrinter::VisitOMPPermutationClause(OMPPermutationClause *Node) {
1868 OS << "permutation(";
1869 llvm::interleaveComma(Node->getArgsRefs(), OS, [&](const Expr *E) {
1870 E->printPretty(OS, nullptr, Policy, 0);
1872 OS << ")";
1875 void OMPClausePrinter::VisitOMPFullClause(OMPFullClause *Node) { OS << "full"; }
1877 void OMPClausePrinter::VisitOMPPartialClause(OMPPartialClause *Node) {
1878 OS << "partial";
1880 if (Expr *Factor = Node->getFactor()) {
1881 OS << '(';
1882 Factor->printPretty(OS, nullptr, Policy, 0);
1883 OS << ')';
1887 void OMPClausePrinter::VisitOMPAllocatorClause(OMPAllocatorClause *Node) {
1888 OS << "allocator(";
1889 Node->getAllocator()->printPretty(OS, nullptr, Policy, 0);
1890 OS << ")";
1893 void OMPClausePrinter::VisitOMPCollapseClause(OMPCollapseClause *Node) {
1894 OS << "collapse(";
1895 Node->getNumForLoops()->printPretty(OS, nullptr, Policy, 0);
1896 OS << ")";
1899 void OMPClausePrinter::VisitOMPDetachClause(OMPDetachClause *Node) {
1900 OS << "detach(";
1901 Node->getEventHandler()->printPretty(OS, nullptr, Policy, 0);
1902 OS << ")";
1905 void OMPClausePrinter::VisitOMPDefaultClause(OMPDefaultClause *Node) {
1906 OS << "default("
1907 << getOpenMPSimpleClauseTypeName(OMPC_default,
1908 unsigned(Node->getDefaultKind()))
1909 << ")";
1912 void OMPClausePrinter::VisitOMPProcBindClause(OMPProcBindClause *Node) {
1913 OS << "proc_bind("
1914 << getOpenMPSimpleClauseTypeName(OMPC_proc_bind,
1915 unsigned(Node->getProcBindKind()))
1916 << ")";
1919 void OMPClausePrinter::VisitOMPUnifiedAddressClause(OMPUnifiedAddressClause *) {
1920 OS << "unified_address";
1923 void OMPClausePrinter::VisitOMPUnifiedSharedMemoryClause(
1924 OMPUnifiedSharedMemoryClause *) {
1925 OS << "unified_shared_memory";
1928 void OMPClausePrinter::VisitOMPReverseOffloadClause(OMPReverseOffloadClause *) {
1929 OS << "reverse_offload";
1932 void OMPClausePrinter::VisitOMPDynamicAllocatorsClause(
1933 OMPDynamicAllocatorsClause *) {
1934 OS << "dynamic_allocators";
1937 void OMPClausePrinter::VisitOMPAtomicDefaultMemOrderClause(
1938 OMPAtomicDefaultMemOrderClause *Node) {
1939 OS << "atomic_default_mem_order("
1940 << getOpenMPSimpleClauseTypeName(OMPC_atomic_default_mem_order,
1941 Node->getAtomicDefaultMemOrderKind())
1942 << ")";
1945 void OMPClausePrinter::VisitOMPAtClause(OMPAtClause *Node) {
1946 OS << "at(" << getOpenMPSimpleClauseTypeName(OMPC_at, Node->getAtKind())
1947 << ")";
1950 void OMPClausePrinter::VisitOMPSeverityClause(OMPSeverityClause *Node) {
1951 OS << "severity("
1952 << getOpenMPSimpleClauseTypeName(OMPC_severity, Node->getSeverityKind())
1953 << ")";
1956 void OMPClausePrinter::VisitOMPMessageClause(OMPMessageClause *Node) {
1957 OS << "message(\""
1958 << cast<StringLiteral>(Node->getMessageString())->getString() << "\")";
1961 void OMPClausePrinter::VisitOMPScheduleClause(OMPScheduleClause *Node) {
1962 OS << "schedule(";
1963 if (Node->getFirstScheduleModifier() != OMPC_SCHEDULE_MODIFIER_unknown) {
1964 OS << getOpenMPSimpleClauseTypeName(OMPC_schedule,
1965 Node->getFirstScheduleModifier());
1966 if (Node->getSecondScheduleModifier() != OMPC_SCHEDULE_MODIFIER_unknown) {
1967 OS << ", ";
1968 OS << getOpenMPSimpleClauseTypeName(OMPC_schedule,
1969 Node->getSecondScheduleModifier());
1971 OS << ": ";
1973 OS << getOpenMPSimpleClauseTypeName(OMPC_schedule, Node->getScheduleKind());
1974 if (auto *E = Node->getChunkSize()) {
1975 OS << ", ";
1976 E->printPretty(OS, nullptr, Policy);
1978 OS << ")";
1981 void OMPClausePrinter::VisitOMPOrderedClause(OMPOrderedClause *Node) {
1982 OS << "ordered";
1983 if (auto *Num = Node->getNumForLoops()) {
1984 OS << "(";
1985 Num->printPretty(OS, nullptr, Policy, 0);
1986 OS << ")";
1990 void OMPClausePrinter::VisitOMPNowaitClause(OMPNowaitClause *) {
1991 OS << "nowait";
1994 void OMPClausePrinter::VisitOMPUntiedClause(OMPUntiedClause *) {
1995 OS << "untied";
1998 void OMPClausePrinter::VisitOMPNogroupClause(OMPNogroupClause *) {
1999 OS << "nogroup";
2002 void OMPClausePrinter::VisitOMPMergeableClause(OMPMergeableClause *) {
2003 OS << "mergeable";
2006 void OMPClausePrinter::VisitOMPReadClause(OMPReadClause *) { OS << "read"; }
2008 void OMPClausePrinter::VisitOMPWriteClause(OMPWriteClause *) { OS << "write"; }
2010 void OMPClausePrinter::VisitOMPUpdateClause(OMPUpdateClause *Node) {
2011 OS << "update";
2012 if (Node->isExtended()) {
2013 OS << "(";
2014 OS << getOpenMPSimpleClauseTypeName(Node->getClauseKind(),
2015 Node->getDependencyKind());
2016 OS << ")";
2020 void OMPClausePrinter::VisitOMPCaptureClause(OMPCaptureClause *) {
2021 OS << "capture";
2024 void OMPClausePrinter::VisitOMPCompareClause(OMPCompareClause *) {
2025 OS << "compare";
2028 void OMPClausePrinter::VisitOMPFailClause(OMPFailClause *Node) {
2029 OS << "fail";
2030 if (Node) {
2031 OS << "(";
2032 OS << getOpenMPSimpleClauseTypeName(
2033 Node->getClauseKind(), static_cast<int>(Node->getFailParameter()));
2034 OS << ")";
2038 void OMPClausePrinter::VisitOMPAbsentClause(OMPAbsentClause *Node) {
2039 OS << "absent(";
2040 bool First = true;
2041 for (auto &D : Node->getDirectiveKinds()) {
2042 if (!First)
2043 OS << ", ";
2044 OS << getOpenMPDirectiveName(D);
2045 First = false;
2047 OS << ")";
2050 void OMPClausePrinter::VisitOMPHoldsClause(OMPHoldsClause *Node) {
2051 OS << "holds(";
2052 Node->getExpr()->printPretty(OS, nullptr, Policy, 0);
2053 OS << ")";
2056 void OMPClausePrinter::VisitOMPContainsClause(OMPContainsClause *Node) {
2057 OS << "contains(";
2058 bool First = true;
2059 for (auto &D : Node->getDirectiveKinds()) {
2060 if (!First)
2061 OS << ", ";
2062 OS << getOpenMPDirectiveName(D);
2063 First = false;
2065 OS << ")";
2068 void OMPClausePrinter::VisitOMPNoOpenMPClause(OMPNoOpenMPClause *) {
2069 OS << "no_openmp";
2072 void OMPClausePrinter::VisitOMPNoOpenMPRoutinesClause(
2073 OMPNoOpenMPRoutinesClause *) {
2074 OS << "no_openmp_routines";
2077 void OMPClausePrinter::VisitOMPNoParallelismClause(OMPNoParallelismClause *) {
2078 OS << "no_parallelism";
2081 void OMPClausePrinter::VisitOMPSeqCstClause(OMPSeqCstClause *) {
2082 OS << "seq_cst";
2085 void OMPClausePrinter::VisitOMPAcqRelClause(OMPAcqRelClause *) {
2086 OS << "acq_rel";
2089 void OMPClausePrinter::VisitOMPAcquireClause(OMPAcquireClause *) {
2090 OS << "acquire";
2093 void OMPClausePrinter::VisitOMPReleaseClause(OMPReleaseClause *) {
2094 OS << "release";
2097 void OMPClausePrinter::VisitOMPRelaxedClause(OMPRelaxedClause *) {
2098 OS << "relaxed";
2101 void OMPClausePrinter::VisitOMPWeakClause(OMPWeakClause *) { OS << "weak"; }
2103 void OMPClausePrinter::VisitOMPThreadsClause(OMPThreadsClause *) {
2104 OS << "threads";
2107 void OMPClausePrinter::VisitOMPSIMDClause(OMPSIMDClause *) { OS << "simd"; }
2109 void OMPClausePrinter::VisitOMPDeviceClause(OMPDeviceClause *Node) {
2110 OS << "device(";
2111 OpenMPDeviceClauseModifier Modifier = Node->getModifier();
2112 if (Modifier != OMPC_DEVICE_unknown) {
2113 OS << getOpenMPSimpleClauseTypeName(Node->getClauseKind(), Modifier)
2114 << ": ";
2116 Node->getDevice()->printPretty(OS, nullptr, Policy, 0);
2117 OS << ")";
2120 void OMPClausePrinter::VisitOMPNumTeamsClause(OMPNumTeamsClause *Node) {
2121 if (!Node->varlist_empty()) {
2122 OS << "num_teams";
2123 VisitOMPClauseList(Node, '(');
2124 OS << ")";
2128 void OMPClausePrinter::VisitOMPThreadLimitClause(OMPThreadLimitClause *Node) {
2129 if (!Node->varlist_empty()) {
2130 OS << "thread_limit";
2131 VisitOMPClauseList(Node, '(');
2132 OS << ")";
2136 void OMPClausePrinter::VisitOMPPriorityClause(OMPPriorityClause *Node) {
2137 OS << "priority(";
2138 Node->getPriority()->printPretty(OS, nullptr, Policy, 0);
2139 OS << ")";
2142 void OMPClausePrinter::VisitOMPGrainsizeClause(OMPGrainsizeClause *Node) {
2143 OS << "grainsize(";
2144 OpenMPGrainsizeClauseModifier Modifier = Node->getModifier();
2145 if (Modifier != OMPC_GRAINSIZE_unknown) {
2146 OS << getOpenMPSimpleClauseTypeName(Node->getClauseKind(), Modifier)
2147 << ": ";
2149 Node->getGrainsize()->printPretty(OS, nullptr, Policy, 0);
2150 OS << ")";
2153 void OMPClausePrinter::VisitOMPNumTasksClause(OMPNumTasksClause *Node) {
2154 OS << "num_tasks(";
2155 OpenMPNumTasksClauseModifier Modifier = Node->getModifier();
2156 if (Modifier != OMPC_NUMTASKS_unknown) {
2157 OS << getOpenMPSimpleClauseTypeName(Node->getClauseKind(), Modifier)
2158 << ": ";
2160 Node->getNumTasks()->printPretty(OS, nullptr, Policy, 0);
2161 OS << ")";
2164 void OMPClausePrinter::VisitOMPHintClause(OMPHintClause *Node) {
2165 OS << "hint(";
2166 Node->getHint()->printPretty(OS, nullptr, Policy, 0);
2167 OS << ")";
2170 void OMPClausePrinter::VisitOMPInitClause(OMPInitClause *Node) {
2171 OS << "init(";
2172 bool First = true;
2173 for (const Expr *E : Node->prefs()) {
2174 if (First)
2175 OS << "prefer_type(";
2176 else
2177 OS << ",";
2178 E->printPretty(OS, nullptr, Policy);
2179 First = false;
2181 if (!First)
2182 OS << "), ";
2183 if (Node->getIsTarget())
2184 OS << "target";
2185 if (Node->getIsTargetSync()) {
2186 if (Node->getIsTarget())
2187 OS << ", ";
2188 OS << "targetsync";
2190 OS << " : ";
2191 Node->getInteropVar()->printPretty(OS, nullptr, Policy);
2192 OS << ")";
2195 void OMPClausePrinter::VisitOMPUseClause(OMPUseClause *Node) {
2196 OS << "use(";
2197 Node->getInteropVar()->printPretty(OS, nullptr, Policy);
2198 OS << ")";
2201 void OMPClausePrinter::VisitOMPDestroyClause(OMPDestroyClause *Node) {
2202 OS << "destroy";
2203 if (Expr *E = Node->getInteropVar()) {
2204 OS << "(";
2205 E->printPretty(OS, nullptr, Policy);
2206 OS << ")";
2210 void OMPClausePrinter::VisitOMPNovariantsClause(OMPNovariantsClause *Node) {
2211 OS << "novariants";
2212 if (Expr *E = Node->getCondition()) {
2213 OS << "(";
2214 E->printPretty(OS, nullptr, Policy, 0);
2215 OS << ")";
2219 void OMPClausePrinter::VisitOMPNocontextClause(OMPNocontextClause *Node) {
2220 OS << "nocontext";
2221 if (Expr *E = Node->getCondition()) {
2222 OS << "(";
2223 E->printPretty(OS, nullptr, Policy, 0);
2224 OS << ")";
2228 template<typename T>
2229 void OMPClausePrinter::VisitOMPClauseList(T *Node, char StartSym) {
2230 for (typename T::varlist_iterator I = Node->varlist_begin(),
2231 E = Node->varlist_end();
2232 I != E; ++I) {
2233 assert(*I && "Expected non-null Stmt");
2234 OS << (I == Node->varlist_begin() ? StartSym : ',');
2235 if (auto *DRE = dyn_cast<DeclRefExpr>(*I)) {
2236 if (isa<OMPCapturedExprDecl>(DRE->getDecl()))
2237 DRE->printPretty(OS, nullptr, Policy, 0);
2238 else
2239 DRE->getDecl()->printQualifiedName(OS);
2240 } else
2241 (*I)->printPretty(OS, nullptr, Policy, 0);
2245 void OMPClausePrinter::VisitOMPAllocateClause(OMPAllocateClause *Node) {
2246 if (Node->varlist_empty())
2247 return;
2248 OS << "allocate";
2249 OpenMPAllocateClauseModifier Modifier = Node->getAllocatorModifier();
2250 if (Expr *Allocator = Node->getAllocator()) {
2251 OS << "(";
2252 if (Modifier == OMPC_ALLOCATE_allocator) {
2253 OS << getOpenMPSimpleClauseTypeName(Node->getClauseKind(), Modifier);
2254 OS << "(";
2255 Allocator->printPretty(OS, nullptr, Policy, 0);
2256 OS << ")";
2257 } else {
2258 Allocator->printPretty(OS, nullptr, Policy, 0);
2260 OS << ":";
2261 VisitOMPClauseList(Node, ' ');
2262 } else {
2263 VisitOMPClauseList(Node, '(');
2265 OS << ")";
2268 void OMPClausePrinter::VisitOMPPrivateClause(OMPPrivateClause *Node) {
2269 if (!Node->varlist_empty()) {
2270 OS << "private";
2271 VisitOMPClauseList(Node, '(');
2272 OS << ")";
2276 void OMPClausePrinter::VisitOMPFirstprivateClause(OMPFirstprivateClause *Node) {
2277 if (!Node->varlist_empty()) {
2278 OS << "firstprivate";
2279 VisitOMPClauseList(Node, '(');
2280 OS << ")";
2284 void OMPClausePrinter::VisitOMPLastprivateClause(OMPLastprivateClause *Node) {
2285 if (!Node->varlist_empty()) {
2286 OS << "lastprivate";
2287 OpenMPLastprivateModifier LPKind = Node->getKind();
2288 if (LPKind != OMPC_LASTPRIVATE_unknown) {
2289 OS << "("
2290 << getOpenMPSimpleClauseTypeName(OMPC_lastprivate, Node->getKind())
2291 << ":";
2293 VisitOMPClauseList(Node, LPKind == OMPC_LASTPRIVATE_unknown ? '(' : ' ');
2294 OS << ")";
2298 void OMPClausePrinter::VisitOMPSharedClause(OMPSharedClause *Node) {
2299 if (!Node->varlist_empty()) {
2300 OS << "shared";
2301 VisitOMPClauseList(Node, '(');
2302 OS << ")";
2306 void OMPClausePrinter::VisitOMPReductionClause(OMPReductionClause *Node) {
2307 if (!Node->varlist_empty()) {
2308 OS << "reduction(";
2309 if (Node->getModifierLoc().isValid())
2310 OS << getOpenMPSimpleClauseTypeName(OMPC_reduction, Node->getModifier())
2311 << ", ";
2312 NestedNameSpecifier *QualifierLoc =
2313 Node->getQualifierLoc().getNestedNameSpecifier();
2314 OverloadedOperatorKind OOK =
2315 Node->getNameInfo().getName().getCXXOverloadedOperator();
2316 if (QualifierLoc == nullptr && OOK != OO_None) {
2317 // Print reduction identifier in C format
2318 OS << getOperatorSpelling(OOK);
2319 } else {
2320 // Use C++ format
2321 if (QualifierLoc != nullptr)
2322 QualifierLoc->print(OS, Policy);
2323 OS << Node->getNameInfo();
2325 OS << ":";
2326 VisitOMPClauseList(Node, ' ');
2327 OS << ")";
2331 void OMPClausePrinter::VisitOMPTaskReductionClause(
2332 OMPTaskReductionClause *Node) {
2333 if (!Node->varlist_empty()) {
2334 OS << "task_reduction(";
2335 NestedNameSpecifier *QualifierLoc =
2336 Node->getQualifierLoc().getNestedNameSpecifier();
2337 OverloadedOperatorKind OOK =
2338 Node->getNameInfo().getName().getCXXOverloadedOperator();
2339 if (QualifierLoc == nullptr && OOK != OO_None) {
2340 // Print reduction identifier in C format
2341 OS << getOperatorSpelling(OOK);
2342 } else {
2343 // Use C++ format
2344 if (QualifierLoc != nullptr)
2345 QualifierLoc->print(OS, Policy);
2346 OS << Node->getNameInfo();
2348 OS << ":";
2349 VisitOMPClauseList(Node, ' ');
2350 OS << ")";
2354 void OMPClausePrinter::VisitOMPInReductionClause(OMPInReductionClause *Node) {
2355 if (!Node->varlist_empty()) {
2356 OS << "in_reduction(";
2357 NestedNameSpecifier *QualifierLoc =
2358 Node->getQualifierLoc().getNestedNameSpecifier();
2359 OverloadedOperatorKind OOK =
2360 Node->getNameInfo().getName().getCXXOverloadedOperator();
2361 if (QualifierLoc == nullptr && OOK != OO_None) {
2362 // Print reduction identifier in C format
2363 OS << getOperatorSpelling(OOK);
2364 } else {
2365 // Use C++ format
2366 if (QualifierLoc != nullptr)
2367 QualifierLoc->print(OS, Policy);
2368 OS << Node->getNameInfo();
2370 OS << ":";
2371 VisitOMPClauseList(Node, ' ');
2372 OS << ")";
2376 void OMPClausePrinter::VisitOMPLinearClause(OMPLinearClause *Node) {
2377 if (!Node->varlist_empty()) {
2378 OS << "linear";
2379 VisitOMPClauseList(Node, '(');
2380 if (Node->getModifierLoc().isValid() || Node->getStep() != nullptr) {
2381 OS << ": ";
2383 if (Node->getModifierLoc().isValid()) {
2384 OS << getOpenMPSimpleClauseTypeName(OMPC_linear, Node->getModifier());
2386 if (Node->getStep() != nullptr) {
2387 if (Node->getModifierLoc().isValid()) {
2388 OS << ", ";
2390 OS << "step(";
2391 Node->getStep()->printPretty(OS, nullptr, Policy, 0);
2392 OS << ")";
2394 OS << ")";
2398 void OMPClausePrinter::VisitOMPAlignedClause(OMPAlignedClause *Node) {
2399 if (!Node->varlist_empty()) {
2400 OS << "aligned";
2401 VisitOMPClauseList(Node, '(');
2402 if (Node->getAlignment() != nullptr) {
2403 OS << ": ";
2404 Node->getAlignment()->printPretty(OS, nullptr, Policy, 0);
2406 OS << ")";
2410 void OMPClausePrinter::VisitOMPCopyinClause(OMPCopyinClause *Node) {
2411 if (!Node->varlist_empty()) {
2412 OS << "copyin";
2413 VisitOMPClauseList(Node, '(');
2414 OS << ")";
2418 void OMPClausePrinter::VisitOMPCopyprivateClause(OMPCopyprivateClause *Node) {
2419 if (!Node->varlist_empty()) {
2420 OS << "copyprivate";
2421 VisitOMPClauseList(Node, '(');
2422 OS << ")";
2426 void OMPClausePrinter::VisitOMPFlushClause(OMPFlushClause *Node) {
2427 if (!Node->varlist_empty()) {
2428 VisitOMPClauseList(Node, '(');
2429 OS << ")";
2433 void OMPClausePrinter::VisitOMPDepobjClause(OMPDepobjClause *Node) {
2434 OS << "(";
2435 Node->getDepobj()->printPretty(OS, nullptr, Policy, 0);
2436 OS << ")";
2439 void OMPClausePrinter::VisitOMPDependClause(OMPDependClause *Node) {
2440 OS << "depend(";
2441 if (Expr *DepModifier = Node->getModifier()) {
2442 DepModifier->printPretty(OS, nullptr, Policy);
2443 OS << ", ";
2445 OpenMPDependClauseKind DepKind = Node->getDependencyKind();
2446 OpenMPDependClauseKind PrintKind = DepKind;
2447 bool IsOmpAllMemory = false;
2448 if (PrintKind == OMPC_DEPEND_outallmemory) {
2449 PrintKind = OMPC_DEPEND_out;
2450 IsOmpAllMemory = true;
2451 } else if (PrintKind == OMPC_DEPEND_inoutallmemory) {
2452 PrintKind = OMPC_DEPEND_inout;
2453 IsOmpAllMemory = true;
2455 OS << getOpenMPSimpleClauseTypeName(Node->getClauseKind(), PrintKind);
2456 if (!Node->varlist_empty() || IsOmpAllMemory)
2457 OS << " :";
2458 VisitOMPClauseList(Node, ' ');
2459 if (IsOmpAllMemory) {
2460 OS << (Node->varlist_empty() ? " " : ",");
2461 OS << "omp_all_memory";
2463 OS << ")";
2466 template <typename T>
2467 static void PrintMapper(raw_ostream &OS, T *Node,
2468 const PrintingPolicy &Policy) {
2469 OS << '(';
2470 NestedNameSpecifier *MapperNNS =
2471 Node->getMapperQualifierLoc().getNestedNameSpecifier();
2472 if (MapperNNS)
2473 MapperNNS->print(OS, Policy);
2474 OS << Node->getMapperIdInfo() << ')';
2477 template <typename T>
2478 static void PrintIterator(raw_ostream &OS, T *Node,
2479 const PrintingPolicy &Policy) {
2480 if (Expr *IteratorModifier = Node->getIteratorModifier())
2481 IteratorModifier->printPretty(OS, nullptr, Policy);
2484 void OMPClausePrinter::VisitOMPMapClause(OMPMapClause *Node) {
2485 if (!Node->varlist_empty()) {
2486 OS << "map(";
2487 if (Node->getMapType() != OMPC_MAP_unknown) {
2488 for (unsigned I = 0; I < NumberOfOMPMapClauseModifiers; ++I) {
2489 if (Node->getMapTypeModifier(I) != OMPC_MAP_MODIFIER_unknown) {
2490 if (Node->getMapTypeModifier(I) == OMPC_MAP_MODIFIER_iterator) {
2491 PrintIterator(OS, Node, Policy);
2492 } else {
2493 OS << getOpenMPSimpleClauseTypeName(OMPC_map,
2494 Node->getMapTypeModifier(I));
2495 if (Node->getMapTypeModifier(I) == OMPC_MAP_MODIFIER_mapper)
2496 PrintMapper(OS, Node, Policy);
2498 OS << ',';
2501 OS << getOpenMPSimpleClauseTypeName(OMPC_map, Node->getMapType());
2502 OS << ':';
2504 VisitOMPClauseList(Node, ' ');
2505 OS << ")";
2509 template <typename T> void OMPClausePrinter::VisitOMPMotionClause(T *Node) {
2510 if (Node->varlist_empty())
2511 return;
2512 OS << getOpenMPClauseName(Node->getClauseKind());
2513 unsigned ModifierCount = 0;
2514 for (unsigned I = 0; I < NumberOfOMPMotionModifiers; ++I) {
2515 if (Node->getMotionModifier(I) != OMPC_MOTION_MODIFIER_unknown)
2516 ++ModifierCount;
2518 if (ModifierCount) {
2519 OS << '(';
2520 for (unsigned I = 0; I < NumberOfOMPMotionModifiers; ++I) {
2521 if (Node->getMotionModifier(I) != OMPC_MOTION_MODIFIER_unknown) {
2522 OS << getOpenMPSimpleClauseTypeName(Node->getClauseKind(),
2523 Node->getMotionModifier(I));
2524 if (Node->getMotionModifier(I) == OMPC_MOTION_MODIFIER_mapper)
2525 PrintMapper(OS, Node, Policy);
2526 if (I < ModifierCount - 1)
2527 OS << ", ";
2530 OS << ':';
2531 VisitOMPClauseList(Node, ' ');
2532 } else {
2533 VisitOMPClauseList(Node, '(');
2535 OS << ")";
2538 void OMPClausePrinter::VisitOMPToClause(OMPToClause *Node) {
2539 VisitOMPMotionClause(Node);
2542 void OMPClausePrinter::VisitOMPFromClause(OMPFromClause *Node) {
2543 VisitOMPMotionClause(Node);
2546 void OMPClausePrinter::VisitOMPDistScheduleClause(OMPDistScheduleClause *Node) {
2547 OS << "dist_schedule(" << getOpenMPSimpleClauseTypeName(
2548 OMPC_dist_schedule, Node->getDistScheduleKind());
2549 if (auto *E = Node->getChunkSize()) {
2550 OS << ", ";
2551 E->printPretty(OS, nullptr, Policy);
2553 OS << ")";
2556 void OMPClausePrinter::VisitOMPDefaultmapClause(OMPDefaultmapClause *Node) {
2557 OS << "defaultmap(";
2558 OS << getOpenMPSimpleClauseTypeName(OMPC_defaultmap,
2559 Node->getDefaultmapModifier());
2560 if (Node->getDefaultmapKind() != OMPC_DEFAULTMAP_unknown) {
2561 OS << ": ";
2562 OS << getOpenMPSimpleClauseTypeName(OMPC_defaultmap,
2563 Node->getDefaultmapKind());
2565 OS << ")";
2568 void OMPClausePrinter::VisitOMPUseDevicePtrClause(OMPUseDevicePtrClause *Node) {
2569 if (!Node->varlist_empty()) {
2570 OS << "use_device_ptr";
2571 VisitOMPClauseList(Node, '(');
2572 OS << ")";
2576 void OMPClausePrinter::VisitOMPUseDeviceAddrClause(
2577 OMPUseDeviceAddrClause *Node) {
2578 if (!Node->varlist_empty()) {
2579 OS << "use_device_addr";
2580 VisitOMPClauseList(Node, '(');
2581 OS << ")";
2585 void OMPClausePrinter::VisitOMPIsDevicePtrClause(OMPIsDevicePtrClause *Node) {
2586 if (!Node->varlist_empty()) {
2587 OS << "is_device_ptr";
2588 VisitOMPClauseList(Node, '(');
2589 OS << ")";
2593 void OMPClausePrinter::VisitOMPHasDeviceAddrClause(OMPHasDeviceAddrClause *Node) {
2594 if (!Node->varlist_empty()) {
2595 OS << "has_device_addr";
2596 VisitOMPClauseList(Node, '(');
2597 OS << ")";
2601 void OMPClausePrinter::VisitOMPNontemporalClause(OMPNontemporalClause *Node) {
2602 if (!Node->varlist_empty()) {
2603 OS << "nontemporal";
2604 VisitOMPClauseList(Node, '(');
2605 OS << ")";
2609 void OMPClausePrinter::VisitOMPOrderClause(OMPOrderClause *Node) {
2610 OS << "order(";
2611 if (Node->getModifier() != OMPC_ORDER_MODIFIER_unknown) {
2612 OS << getOpenMPSimpleClauseTypeName(OMPC_order, Node->getModifier());
2613 OS << ": ";
2615 OS << getOpenMPSimpleClauseTypeName(OMPC_order, Node->getKind()) << ")";
2618 void OMPClausePrinter::VisitOMPInclusiveClause(OMPInclusiveClause *Node) {
2619 if (!Node->varlist_empty()) {
2620 OS << "inclusive";
2621 VisitOMPClauseList(Node, '(');
2622 OS << ")";
2626 void OMPClausePrinter::VisitOMPExclusiveClause(OMPExclusiveClause *Node) {
2627 if (!Node->varlist_empty()) {
2628 OS << "exclusive";
2629 VisitOMPClauseList(Node, '(');
2630 OS << ")";
2634 void OMPClausePrinter::VisitOMPUsesAllocatorsClause(
2635 OMPUsesAllocatorsClause *Node) {
2636 if (Node->getNumberOfAllocators() == 0)
2637 return;
2638 OS << "uses_allocators(";
2639 for (unsigned I = 0, E = Node->getNumberOfAllocators(); I < E; ++I) {
2640 OMPUsesAllocatorsClause::Data Data = Node->getAllocatorData(I);
2641 Data.Allocator->printPretty(OS, nullptr, Policy);
2642 if (Data.AllocatorTraits) {
2643 OS << "(";
2644 Data.AllocatorTraits->printPretty(OS, nullptr, Policy);
2645 OS << ")";
2647 if (I < E - 1)
2648 OS << ",";
2650 OS << ")";
2653 void OMPClausePrinter::VisitOMPAffinityClause(OMPAffinityClause *Node) {
2654 if (Node->varlist_empty())
2655 return;
2656 OS << "affinity";
2657 char StartSym = '(';
2658 if (Expr *Modifier = Node->getModifier()) {
2659 OS << "(";
2660 Modifier->printPretty(OS, nullptr, Policy);
2661 OS << " :";
2662 StartSym = ' ';
2664 VisitOMPClauseList(Node, StartSym);
2665 OS << ")";
2668 void OMPClausePrinter::VisitOMPFilterClause(OMPFilterClause *Node) {
2669 OS << "filter(";
2670 Node->getThreadID()->printPretty(OS, nullptr, Policy, 0);
2671 OS << ")";
2674 void OMPClausePrinter::VisitOMPBindClause(OMPBindClause *Node) {
2675 OS << "bind("
2676 << getOpenMPSimpleClauseTypeName(OMPC_bind, unsigned(Node->getBindKind()))
2677 << ")";
2680 void OMPClausePrinter::VisitOMPXDynCGroupMemClause(
2681 OMPXDynCGroupMemClause *Node) {
2682 OS << "ompx_dyn_cgroup_mem(";
2683 Node->getSize()->printPretty(OS, nullptr, Policy, 0);
2684 OS << ")";
2687 void OMPClausePrinter::VisitOMPDoacrossClause(OMPDoacrossClause *Node) {
2688 OS << "doacross(";
2689 OpenMPDoacrossClauseModifier DepType = Node->getDependenceType();
2691 switch (DepType) {
2692 case OMPC_DOACROSS_source:
2693 OS << "source:";
2694 break;
2695 case OMPC_DOACROSS_sink:
2696 OS << "sink:";
2697 break;
2698 case OMPC_DOACROSS_source_omp_cur_iteration:
2699 OS << "source: omp_cur_iteration";
2700 break;
2701 case OMPC_DOACROSS_sink_omp_cur_iteration:
2702 OS << "sink: omp_cur_iteration - 1";
2703 break;
2704 default:
2705 llvm_unreachable("unknown docaross modifier");
2707 VisitOMPClauseList(Node, ' ');
2708 OS << ")";
2711 void OMPClausePrinter::VisitOMPXAttributeClause(OMPXAttributeClause *Node) {
2712 OS << "ompx_attribute(";
2713 bool IsFirst = true;
2714 for (auto &Attr : Node->getAttrs()) {
2715 if (!IsFirst)
2716 OS << ", ";
2717 Attr->printPretty(OS, Policy);
2718 IsFirst = false;
2720 OS << ")";
2723 void OMPClausePrinter::VisitOMPXBareClause(OMPXBareClause *Node) {
2724 OS << "ompx_bare";
2727 void OMPTraitInfo::getAsVariantMatchInfo(ASTContext &ASTCtx,
2728 VariantMatchInfo &VMI) const {
2729 for (const OMPTraitSet &Set : Sets) {
2730 for (const OMPTraitSelector &Selector : Set.Selectors) {
2732 // User conditions are special as we evaluate the condition here.
2733 if (Selector.Kind == TraitSelector::user_condition) {
2734 assert(Selector.ScoreOrCondition &&
2735 "Ill-formed user condition, expected condition expression!");
2736 assert(Selector.Properties.size() == 1 &&
2737 Selector.Properties.front().Kind ==
2738 TraitProperty::user_condition_unknown &&
2739 "Ill-formed user condition, expected unknown trait property!");
2741 if (std::optional<APSInt> CondVal =
2742 Selector.ScoreOrCondition->getIntegerConstantExpr(ASTCtx))
2743 VMI.addTrait(CondVal->isZero() ? TraitProperty::user_condition_false
2744 : TraitProperty::user_condition_true,
2745 "<condition>");
2746 else
2747 VMI.addTrait(TraitProperty::user_condition_false, "<condition>");
2748 continue;
2751 std::optional<llvm::APSInt> Score;
2752 llvm::APInt *ScorePtr = nullptr;
2753 if (Selector.ScoreOrCondition) {
2754 if ((Score = Selector.ScoreOrCondition->getIntegerConstantExpr(ASTCtx)))
2755 ScorePtr = &*Score;
2756 else
2757 VMI.addTrait(TraitProperty::user_condition_false,
2758 "<non-constant-score>");
2761 for (const OMPTraitProperty &Property : Selector.Properties)
2762 VMI.addTrait(Set.Kind, Property.Kind, Property.RawString, ScorePtr);
2764 if (Set.Kind != TraitSet::construct)
2765 continue;
2767 // TODO: This might not hold once we implement SIMD properly.
2768 assert(Selector.Properties.size() == 1 &&
2769 Selector.Properties.front().Kind ==
2770 getOpenMPContextTraitPropertyForSelector(
2771 Selector.Kind) &&
2772 "Ill-formed construct selector!");
2777 void OMPTraitInfo::print(llvm::raw_ostream &OS,
2778 const PrintingPolicy &Policy) const {
2779 bool FirstSet = true;
2780 for (const OMPTraitSet &Set : Sets) {
2781 if (!FirstSet)
2782 OS << ", ";
2783 FirstSet = false;
2784 OS << getOpenMPContextTraitSetName(Set.Kind) << "={";
2786 bool FirstSelector = true;
2787 for (const OMPTraitSelector &Selector : Set.Selectors) {
2788 if (!FirstSelector)
2789 OS << ", ";
2790 FirstSelector = false;
2791 OS << getOpenMPContextTraitSelectorName(Selector.Kind);
2793 bool AllowsTraitScore = false;
2794 bool RequiresProperty = false;
2795 isValidTraitSelectorForTraitSet(
2796 Selector.Kind, Set.Kind, AllowsTraitScore, RequiresProperty);
2798 if (!RequiresProperty)
2799 continue;
2801 OS << "(";
2802 if (Selector.Kind == TraitSelector::user_condition) {
2803 if (Selector.ScoreOrCondition)
2804 Selector.ScoreOrCondition->printPretty(OS, nullptr, Policy);
2805 else
2806 OS << "...";
2807 } else {
2809 if (Selector.ScoreOrCondition) {
2810 OS << "score(";
2811 Selector.ScoreOrCondition->printPretty(OS, nullptr, Policy);
2812 OS << "): ";
2815 bool FirstProperty = true;
2816 for (const OMPTraitProperty &Property : Selector.Properties) {
2817 if (!FirstProperty)
2818 OS << ", ";
2819 FirstProperty = false;
2820 OS << getOpenMPContextTraitPropertyName(Property.Kind,
2821 Property.RawString);
2824 OS << ")";
2826 OS << "}";
2830 std::string OMPTraitInfo::getMangledName() const {
2831 std::string MangledName;
2832 llvm::raw_string_ostream OS(MangledName);
2833 for (const OMPTraitSet &Set : Sets) {
2834 OS << '$' << 'S' << unsigned(Set.Kind);
2835 for (const OMPTraitSelector &Selector : Set.Selectors) {
2837 bool AllowsTraitScore = false;
2838 bool RequiresProperty = false;
2839 isValidTraitSelectorForTraitSet(
2840 Selector.Kind, Set.Kind, AllowsTraitScore, RequiresProperty);
2841 OS << '$' << 's' << unsigned(Selector.Kind);
2843 if (!RequiresProperty ||
2844 Selector.Kind == TraitSelector::user_condition)
2845 continue;
2847 for (const OMPTraitProperty &Property : Selector.Properties)
2848 OS << '$' << 'P'
2849 << getOpenMPContextTraitPropertyName(Property.Kind,
2850 Property.RawString);
2853 return MangledName;
2856 OMPTraitInfo::OMPTraitInfo(StringRef MangledName) {
2857 unsigned long U;
2858 do {
2859 if (!MangledName.consume_front("$S"))
2860 break;
2861 if (MangledName.consumeInteger(10, U))
2862 break;
2863 Sets.push_back(OMPTraitSet());
2864 OMPTraitSet &Set = Sets.back();
2865 Set.Kind = TraitSet(U);
2866 do {
2867 if (!MangledName.consume_front("$s"))
2868 break;
2869 if (MangledName.consumeInteger(10, U))
2870 break;
2871 Set.Selectors.push_back(OMPTraitSelector());
2872 OMPTraitSelector &Selector = Set.Selectors.back();
2873 Selector.Kind = TraitSelector(U);
2874 do {
2875 if (!MangledName.consume_front("$P"))
2876 break;
2877 Selector.Properties.push_back(OMPTraitProperty());
2878 OMPTraitProperty &Property = Selector.Properties.back();
2879 std::pair<StringRef, StringRef> PropRestPair = MangledName.split('$');
2880 Property.RawString = PropRestPair.first;
2881 Property.Kind = getOpenMPContextTraitPropertyKind(
2882 Set.Kind, Selector.Kind, PropRestPair.first);
2883 MangledName = MangledName.drop_front(PropRestPair.first.size());
2884 } while (true);
2885 } while (true);
2886 } while (true);
2889 llvm::raw_ostream &clang::operator<<(llvm::raw_ostream &OS,
2890 const OMPTraitInfo &TI) {
2891 LangOptions LO;
2892 PrintingPolicy Policy(LO);
2893 TI.print(OS, Policy);
2894 return OS;
2896 llvm::raw_ostream &clang::operator<<(llvm::raw_ostream &OS,
2897 const OMPTraitInfo *TI) {
2898 return TI ? OS << *TI : OS;
2901 TargetOMPContext::TargetOMPContext(
2902 ASTContext &ASTCtx, std::function<void(StringRef)> &&DiagUnknownTrait,
2903 const FunctionDecl *CurrentFunctionDecl,
2904 ArrayRef<llvm::omp::TraitProperty> ConstructTraits)
2905 : OMPContext(ASTCtx.getLangOpts().OpenMPIsTargetDevice,
2906 ASTCtx.getTargetInfo().getTriple()),
2907 FeatureValidityCheck([&](StringRef FeatureName) {
2908 return ASTCtx.getTargetInfo().isValidFeatureName(FeatureName);
2910 DiagUnknownTrait(std::move(DiagUnknownTrait)) {
2911 ASTCtx.getFunctionFeatureMap(FeatureMap, CurrentFunctionDecl);
2913 for (llvm::omp::TraitProperty Property : ConstructTraits)
2914 addTrait(Property);
2917 bool TargetOMPContext::matchesISATrait(StringRef RawString) const {
2918 auto It = FeatureMap.find(RawString);
2919 if (It != FeatureMap.end())
2920 return It->second;
2921 if (!FeatureValidityCheck(RawString))
2922 DiagUnknownTrait(RawString);
2923 return false;