xref: /freebsd/contrib/llvm-project/clang/lib/AST/OpenMPClause.cpp (revision ec0ea6efa1ad229d75c394c1a9b9cac33af2b1d3)
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
10 //
11 //===----------------------------------------------------------------------===//
12 
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/Casting.h"
23 #include "llvm/Support/ErrorHandling.h"
24 #include <algorithm>
25 #include <cassert>
26 
27 using namespace clang;
28 using namespace llvm;
29 using namespace omp;
30 
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"
40   }
41   llvm_unreachable("unknown OMPClause");
42 }
43 
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"
54   }
55   llvm_unreachable("unknown OMPClause");
56 }
57 
58 OMPClauseWithPreInit *OMPClauseWithPreInit::get(OMPClause *C) {
59   auto *Res = OMPClauseWithPreInit::get(const_cast<const OMPClause *>(C));
60   return Res ? const_cast<OMPClauseWithPreInit *>(Res) : nullptr;
61 }
62 
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_default:
106   case OMPC_proc_bind:
107   case OMPC_safelen:
108   case OMPC_simdlen:
109   case OMPC_sizes:
110   case OMPC_allocator:
111   case OMPC_allocate:
112   case OMPC_collapse:
113   case OMPC_private:
114   case OMPC_shared:
115   case OMPC_aligned:
116   case OMPC_copyin:
117   case OMPC_copyprivate:
118   case OMPC_ordered:
119   case OMPC_nowait:
120   case OMPC_untied:
121   case OMPC_mergeable:
122   case OMPC_threadprivate:
123   case OMPC_flush:
124   case OMPC_depobj:
125   case OMPC_read:
126   case OMPC_write:
127   case OMPC_update:
128   case OMPC_capture:
129   case OMPC_seq_cst:
130   case OMPC_acq_rel:
131   case OMPC_acquire:
132   case OMPC_release:
133   case OMPC_relaxed:
134   case OMPC_depend:
135   case OMPC_threads:
136   case OMPC_simd:
137   case OMPC_map:
138   case OMPC_nogroup:
139   case OMPC_hint:
140   case OMPC_defaultmap:
141   case OMPC_unknown:
142   case OMPC_uniform:
143   case OMPC_to:
144   case OMPC_from:
145   case OMPC_use_device_ptr:
146   case OMPC_use_device_addr:
147   case OMPC_is_device_ptr:
148   case OMPC_unified_address:
149   case OMPC_unified_shared_memory:
150   case OMPC_reverse_offload:
151   case OMPC_dynamic_allocators:
152   case OMPC_atomic_default_mem_order:
153   case OMPC_device_type:
154   case OMPC_match:
155   case OMPC_nontemporal:
156   case OMPC_order:
157   case OMPC_destroy:
158   case OMPC_detach:
159   case OMPC_inclusive:
160   case OMPC_exclusive:
161   case OMPC_uses_allocators:
162   case OMPC_affinity:
163     break;
164   default:
165     break;
166   }
167 
168   return nullptr;
169 }
170 
171 OMPClauseWithPostUpdate *OMPClauseWithPostUpdate::get(OMPClause *C) {
172   auto *Res = OMPClauseWithPostUpdate::get(const_cast<const OMPClause *>(C));
173   return Res ? const_cast<OMPClauseWithPostUpdate *>(Res) : nullptr;
174 }
175 
176 const OMPClauseWithPostUpdate *OMPClauseWithPostUpdate::get(const OMPClause *C) {
177   switch (C->getClauseKind()) {
178   case OMPC_lastprivate:
179     return static_cast<const OMPLastprivateClause *>(C);
180   case OMPC_reduction:
181     return static_cast<const OMPReductionClause *>(C);
182   case OMPC_task_reduction:
183     return static_cast<const OMPTaskReductionClause *>(C);
184   case OMPC_in_reduction:
185     return static_cast<const OMPInReductionClause *>(C);
186   case OMPC_linear:
187     return static_cast<const OMPLinearClause *>(C);
188   case OMPC_schedule:
189   case OMPC_dist_schedule:
190   case OMPC_firstprivate:
191   case OMPC_default:
192   case OMPC_proc_bind:
193   case OMPC_if:
194   case OMPC_final:
195   case OMPC_num_threads:
196   case OMPC_safelen:
197   case OMPC_simdlen:
198   case OMPC_sizes:
199   case OMPC_allocator:
200   case OMPC_allocate:
201   case OMPC_collapse:
202   case OMPC_private:
203   case OMPC_shared:
204   case OMPC_aligned:
205   case OMPC_copyin:
206   case OMPC_copyprivate:
207   case OMPC_ordered:
208   case OMPC_nowait:
209   case OMPC_untied:
210   case OMPC_mergeable:
211   case OMPC_threadprivate:
212   case OMPC_flush:
213   case OMPC_depobj:
214   case OMPC_read:
215   case OMPC_write:
216   case OMPC_update:
217   case OMPC_capture:
218   case OMPC_seq_cst:
219   case OMPC_acq_rel:
220   case OMPC_acquire:
221   case OMPC_release:
222   case OMPC_relaxed:
223   case OMPC_depend:
224   case OMPC_device:
225   case OMPC_threads:
226   case OMPC_simd:
227   case OMPC_map:
228   case OMPC_num_teams:
229   case OMPC_thread_limit:
230   case OMPC_priority:
231   case OMPC_grainsize:
232   case OMPC_nogroup:
233   case OMPC_num_tasks:
234   case OMPC_hint:
235   case OMPC_defaultmap:
236   case OMPC_unknown:
237   case OMPC_uniform:
238   case OMPC_to:
239   case OMPC_from:
240   case OMPC_use_device_ptr:
241   case OMPC_use_device_addr:
242   case OMPC_is_device_ptr:
243   case OMPC_unified_address:
244   case OMPC_unified_shared_memory:
245   case OMPC_reverse_offload:
246   case OMPC_dynamic_allocators:
247   case OMPC_atomic_default_mem_order:
248   case OMPC_device_type:
249   case OMPC_match:
250   case OMPC_nontemporal:
251   case OMPC_order:
252   case OMPC_destroy:
253   case OMPC_novariants:
254   case OMPC_nocontext:
255   case OMPC_detach:
256   case OMPC_inclusive:
257   case OMPC_exclusive:
258   case OMPC_uses_allocators:
259   case OMPC_affinity:
260     break;
261   default:
262     break;
263   }
264 
265   return nullptr;
266 }
267 
268 /// Gets the address of the original, non-captured, expression used in the
269 /// clause as the preinitializer.
270 static Stmt **getAddrOfExprAsWritten(Stmt *S) {
271   if (!S)
272     return nullptr;
273   if (auto *DS = dyn_cast<DeclStmt>(S)) {
274     assert(DS->isSingleDecl() && "Only single expression must be captured.");
275     if (auto *OED = dyn_cast<OMPCapturedExprDecl>(DS->getSingleDecl()))
276       return OED->getInitAddress();
277   }
278   return nullptr;
279 }
280 
281 OMPClause::child_range OMPIfClause::used_children() {
282   if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
283     return child_range(C, C + 1);
284   return child_range(&Condition, &Condition + 1);
285 }
286 
287 OMPClause::child_range OMPGrainsizeClause::used_children() {
288   if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
289     return child_range(C, C + 1);
290   return child_range(&Grainsize, &Grainsize + 1);
291 }
292 
293 OMPClause::child_range OMPNumTasksClause::used_children() {
294   if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
295     return child_range(C, C + 1);
296   return child_range(&NumTasks, &NumTasks + 1);
297 }
298 
299 OMPClause::child_range OMPFinalClause::used_children() {
300   if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
301     return child_range(C, C + 1);
302   return child_range(&Condition, &Condition + 1);
303 }
304 
305 OMPClause::child_range OMPPriorityClause::used_children() {
306   if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
307     return child_range(C, C + 1);
308   return child_range(&Priority, &Priority + 1);
309 }
310 
311 OMPClause::child_range OMPNovariantsClause::used_children() {
312   if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
313     return child_range(C, C + 1);
314   return child_range(&Condition, &Condition + 1);
315 }
316 
317 OMPClause::child_range OMPNocontextClause::used_children() {
318   if (Stmt **C = getAddrOfExprAsWritten(getPreInitStmt()))
319     return child_range(C, C + 1);
320   return child_range(&Condition, &Condition + 1);
321 }
322 
323 OMPOrderedClause *OMPOrderedClause::Create(const ASTContext &C, Expr *Num,
324                                            unsigned NumLoops,
325                                            SourceLocation StartLoc,
326                                            SourceLocation LParenLoc,
327                                            SourceLocation EndLoc) {
328   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * NumLoops));
329   auto *Clause =
330       new (Mem) OMPOrderedClause(Num, NumLoops, StartLoc, LParenLoc, EndLoc);
331   for (unsigned I = 0; I < NumLoops; ++I) {
332     Clause->setLoopNumIterations(I, nullptr);
333     Clause->setLoopCounter(I, nullptr);
334   }
335   return Clause;
336 }
337 
338 OMPOrderedClause *OMPOrderedClause::CreateEmpty(const ASTContext &C,
339                                                 unsigned NumLoops) {
340   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * NumLoops));
341   auto *Clause = new (Mem) OMPOrderedClause(NumLoops);
342   for (unsigned I = 0; I < NumLoops; ++I) {
343     Clause->setLoopNumIterations(I, nullptr);
344     Clause->setLoopCounter(I, nullptr);
345   }
346   return Clause;
347 }
348 
349 void OMPOrderedClause::setLoopNumIterations(unsigned NumLoop,
350                                             Expr *NumIterations) {
351   assert(NumLoop < NumberOfLoops && "out of loops number.");
352   getTrailingObjects<Expr *>()[NumLoop] = NumIterations;
353 }
354 
355 ArrayRef<Expr *> OMPOrderedClause::getLoopNumIterations() const {
356   return llvm::makeArrayRef(getTrailingObjects<Expr *>(), NumberOfLoops);
357 }
358 
359 void OMPOrderedClause::setLoopCounter(unsigned NumLoop, Expr *Counter) {
360   assert(NumLoop < NumberOfLoops && "out of loops number.");
361   getTrailingObjects<Expr *>()[NumberOfLoops + NumLoop] = Counter;
362 }
363 
364 Expr *OMPOrderedClause::getLoopCounter(unsigned NumLoop) {
365   assert(NumLoop < NumberOfLoops && "out of loops number.");
366   return getTrailingObjects<Expr *>()[NumberOfLoops + NumLoop];
367 }
368 
369 const Expr *OMPOrderedClause::getLoopCounter(unsigned NumLoop) const {
370   assert(NumLoop < NumberOfLoops && "out of loops number.");
371   return getTrailingObjects<Expr *>()[NumberOfLoops + NumLoop];
372 }
373 
374 OMPUpdateClause *OMPUpdateClause::Create(const ASTContext &C,
375                                          SourceLocation StartLoc,
376                                          SourceLocation EndLoc) {
377   return new (C) OMPUpdateClause(StartLoc, EndLoc, /*IsExtended=*/false);
378 }
379 
380 OMPUpdateClause *
381 OMPUpdateClause::Create(const ASTContext &C, SourceLocation StartLoc,
382                         SourceLocation LParenLoc, SourceLocation ArgumentLoc,
383                         OpenMPDependClauseKind DK, SourceLocation EndLoc) {
384   void *Mem =
385       C.Allocate(totalSizeToAlloc<SourceLocation, OpenMPDependClauseKind>(2, 1),
386                  alignof(OMPUpdateClause));
387   auto *Clause =
388       new (Mem) OMPUpdateClause(StartLoc, EndLoc, /*IsExtended=*/true);
389   Clause->setLParenLoc(LParenLoc);
390   Clause->setArgumentLoc(ArgumentLoc);
391   Clause->setDependencyKind(DK);
392   return Clause;
393 }
394 
395 OMPUpdateClause *OMPUpdateClause::CreateEmpty(const ASTContext &C,
396                                               bool IsExtended) {
397   if (!IsExtended)
398     return new (C) OMPUpdateClause(/*IsExtended=*/false);
399   void *Mem =
400       C.Allocate(totalSizeToAlloc<SourceLocation, OpenMPDependClauseKind>(2, 1),
401                  alignof(OMPUpdateClause));
402   auto *Clause = new (Mem) OMPUpdateClause(/*IsExtended=*/true);
403   Clause->IsExtended = true;
404   return Clause;
405 }
406 
407 void OMPPrivateClause::setPrivateCopies(ArrayRef<Expr *> VL) {
408   assert(VL.size() == varlist_size() &&
409          "Number of private copies is not the same as the preallocated buffer");
410   std::copy(VL.begin(), VL.end(), varlist_end());
411 }
412 
413 OMPPrivateClause *
414 OMPPrivateClause::Create(const ASTContext &C, SourceLocation StartLoc,
415                          SourceLocation LParenLoc, SourceLocation EndLoc,
416                          ArrayRef<Expr *> VL, ArrayRef<Expr *> PrivateVL) {
417   // Allocate space for private variables and initializer expressions.
418   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * VL.size()));
419   OMPPrivateClause *Clause =
420       new (Mem) OMPPrivateClause(StartLoc, LParenLoc, EndLoc, VL.size());
421   Clause->setVarRefs(VL);
422   Clause->setPrivateCopies(PrivateVL);
423   return Clause;
424 }
425 
426 OMPPrivateClause *OMPPrivateClause::CreateEmpty(const ASTContext &C,
427                                                 unsigned N) {
428   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * N));
429   return new (Mem) OMPPrivateClause(N);
430 }
431 
432 void OMPFirstprivateClause::setPrivateCopies(ArrayRef<Expr *> VL) {
433   assert(VL.size() == varlist_size() &&
434          "Number of private copies is not the same as the preallocated buffer");
435   std::copy(VL.begin(), VL.end(), varlist_end());
436 }
437 
438 void OMPFirstprivateClause::setInits(ArrayRef<Expr *> VL) {
439   assert(VL.size() == varlist_size() &&
440          "Number of inits is not the same as the preallocated buffer");
441   std::copy(VL.begin(), VL.end(), getPrivateCopies().end());
442 }
443 
444 OMPFirstprivateClause *
445 OMPFirstprivateClause::Create(const ASTContext &C, SourceLocation StartLoc,
446                               SourceLocation LParenLoc, SourceLocation EndLoc,
447                               ArrayRef<Expr *> VL, ArrayRef<Expr *> PrivateVL,
448                               ArrayRef<Expr *> InitVL, Stmt *PreInit) {
449   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(3 * VL.size()));
450   OMPFirstprivateClause *Clause =
451       new (Mem) OMPFirstprivateClause(StartLoc, LParenLoc, EndLoc, VL.size());
452   Clause->setVarRefs(VL);
453   Clause->setPrivateCopies(PrivateVL);
454   Clause->setInits(InitVL);
455   Clause->setPreInitStmt(PreInit);
456   return Clause;
457 }
458 
459 OMPFirstprivateClause *OMPFirstprivateClause::CreateEmpty(const ASTContext &C,
460                                                           unsigned N) {
461   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(3 * N));
462   return new (Mem) OMPFirstprivateClause(N);
463 }
464 
465 void OMPLastprivateClause::setPrivateCopies(ArrayRef<Expr *> PrivateCopies) {
466   assert(PrivateCopies.size() == varlist_size() &&
467          "Number of private copies is not the same as the preallocated buffer");
468   std::copy(PrivateCopies.begin(), PrivateCopies.end(), varlist_end());
469 }
470 
471 void OMPLastprivateClause::setSourceExprs(ArrayRef<Expr *> SrcExprs) {
472   assert(SrcExprs.size() == varlist_size() && "Number of source expressions is "
473                                               "not the same as the "
474                                               "preallocated buffer");
475   std::copy(SrcExprs.begin(), SrcExprs.end(), getPrivateCopies().end());
476 }
477 
478 void OMPLastprivateClause::setDestinationExprs(ArrayRef<Expr *> DstExprs) {
479   assert(DstExprs.size() == varlist_size() && "Number of destination "
480                                               "expressions is not the same as "
481                                               "the preallocated buffer");
482   std::copy(DstExprs.begin(), DstExprs.end(), getSourceExprs().end());
483 }
484 
485 void OMPLastprivateClause::setAssignmentOps(ArrayRef<Expr *> AssignmentOps) {
486   assert(AssignmentOps.size() == varlist_size() &&
487          "Number of assignment expressions is not the same as the preallocated "
488          "buffer");
489   std::copy(AssignmentOps.begin(), AssignmentOps.end(),
490             getDestinationExprs().end());
491 }
492 
493 OMPLastprivateClause *OMPLastprivateClause::Create(
494     const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
495     SourceLocation EndLoc, ArrayRef<Expr *> VL, ArrayRef<Expr *> SrcExprs,
496     ArrayRef<Expr *> DstExprs, ArrayRef<Expr *> AssignmentOps,
497     OpenMPLastprivateModifier LPKind, SourceLocation LPKindLoc,
498     SourceLocation ColonLoc, Stmt *PreInit, Expr *PostUpdate) {
499   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * VL.size()));
500   OMPLastprivateClause *Clause = new (Mem) OMPLastprivateClause(
501       StartLoc, LParenLoc, EndLoc, LPKind, LPKindLoc, ColonLoc, VL.size());
502   Clause->setVarRefs(VL);
503   Clause->setSourceExprs(SrcExprs);
504   Clause->setDestinationExprs(DstExprs);
505   Clause->setAssignmentOps(AssignmentOps);
506   Clause->setPreInitStmt(PreInit);
507   Clause->setPostUpdateExpr(PostUpdate);
508   return Clause;
509 }
510 
511 OMPLastprivateClause *OMPLastprivateClause::CreateEmpty(const ASTContext &C,
512                                                         unsigned N) {
513   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * N));
514   return new (Mem) OMPLastprivateClause(N);
515 }
516 
517 OMPSharedClause *OMPSharedClause::Create(const ASTContext &C,
518                                          SourceLocation StartLoc,
519                                          SourceLocation LParenLoc,
520                                          SourceLocation EndLoc,
521                                          ArrayRef<Expr *> VL) {
522   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size()));
523   OMPSharedClause *Clause =
524       new (Mem) OMPSharedClause(StartLoc, LParenLoc, EndLoc, VL.size());
525   Clause->setVarRefs(VL);
526   return Clause;
527 }
528 
529 OMPSharedClause *OMPSharedClause::CreateEmpty(const ASTContext &C, unsigned N) {
530   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
531   return new (Mem) OMPSharedClause(N);
532 }
533 
534 void OMPLinearClause::setPrivates(ArrayRef<Expr *> PL) {
535   assert(PL.size() == varlist_size() &&
536          "Number of privates is not the same as the preallocated buffer");
537   std::copy(PL.begin(), PL.end(), varlist_end());
538 }
539 
540 void OMPLinearClause::setInits(ArrayRef<Expr *> IL) {
541   assert(IL.size() == varlist_size() &&
542          "Number of inits is not the same as the preallocated buffer");
543   std::copy(IL.begin(), IL.end(), getPrivates().end());
544 }
545 
546 void OMPLinearClause::setUpdates(ArrayRef<Expr *> UL) {
547   assert(UL.size() == varlist_size() &&
548          "Number of updates is not the same as the preallocated buffer");
549   std::copy(UL.begin(), UL.end(), getInits().end());
550 }
551 
552 void OMPLinearClause::setFinals(ArrayRef<Expr *> FL) {
553   assert(FL.size() == varlist_size() &&
554          "Number of final updates is not the same as the preallocated buffer");
555   std::copy(FL.begin(), FL.end(), getUpdates().end());
556 }
557 
558 void OMPLinearClause::setUsedExprs(ArrayRef<Expr *> UE) {
559   assert(
560       UE.size() == varlist_size() + 1 &&
561       "Number of used expressions is not the same as the preallocated buffer");
562   std::copy(UE.begin(), UE.end(), getFinals().end() + 2);
563 }
564 
565 OMPLinearClause *OMPLinearClause::Create(
566     const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
567     OpenMPLinearClauseKind Modifier, SourceLocation ModifierLoc,
568     SourceLocation ColonLoc, SourceLocation EndLoc, ArrayRef<Expr *> VL,
569     ArrayRef<Expr *> PL, ArrayRef<Expr *> IL, Expr *Step, Expr *CalcStep,
570     Stmt *PreInit, Expr *PostUpdate) {
571   // Allocate space for 5 lists (Vars, Inits, Updates, Finals), 2 expressions
572   // (Step and CalcStep), list of used expression + step.
573   void *Mem =
574       C.Allocate(totalSizeToAlloc<Expr *>(5 * VL.size() + 2 + VL.size() + 1));
575   OMPLinearClause *Clause = new (Mem) OMPLinearClause(
576       StartLoc, LParenLoc, Modifier, ModifierLoc, ColonLoc, EndLoc, VL.size());
577   Clause->setVarRefs(VL);
578   Clause->setPrivates(PL);
579   Clause->setInits(IL);
580   // Fill update and final expressions with zeroes, they are provided later,
581   // after the directive construction.
582   std::fill(Clause->getInits().end(), Clause->getInits().end() + VL.size(),
583             nullptr);
584   std::fill(Clause->getUpdates().end(), Clause->getUpdates().end() + VL.size(),
585             nullptr);
586   std::fill(Clause->getUsedExprs().begin(), Clause->getUsedExprs().end(),
587             nullptr);
588   Clause->setStep(Step);
589   Clause->setCalcStep(CalcStep);
590   Clause->setPreInitStmt(PreInit);
591   Clause->setPostUpdateExpr(PostUpdate);
592   return Clause;
593 }
594 
595 OMPLinearClause *OMPLinearClause::CreateEmpty(const ASTContext &C,
596                                               unsigned NumVars) {
597   // Allocate space for 5 lists (Vars, Inits, Updates, Finals), 2 expressions
598   // (Step and CalcStep), list of used expression + step.
599   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * NumVars + 2 + NumVars  +1));
600   return new (Mem) OMPLinearClause(NumVars);
601 }
602 
603 OMPClause::child_range OMPLinearClause::used_children() {
604   // Range includes only non-nullptr elements.
605   return child_range(
606       reinterpret_cast<Stmt **>(getUsedExprs().begin()),
607       reinterpret_cast<Stmt **>(llvm::find(getUsedExprs(), nullptr)));
608 }
609 
610 OMPAlignedClause *
611 OMPAlignedClause::Create(const ASTContext &C, SourceLocation StartLoc,
612                          SourceLocation LParenLoc, SourceLocation ColonLoc,
613                          SourceLocation EndLoc, ArrayRef<Expr *> VL, Expr *A) {
614   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size() + 1));
615   OMPAlignedClause *Clause = new (Mem)
616       OMPAlignedClause(StartLoc, LParenLoc, ColonLoc, EndLoc, VL.size());
617   Clause->setVarRefs(VL);
618   Clause->setAlignment(A);
619   return Clause;
620 }
621 
622 OMPAlignedClause *OMPAlignedClause::CreateEmpty(const ASTContext &C,
623                                                 unsigned NumVars) {
624   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(NumVars + 1));
625   return new (Mem) OMPAlignedClause(NumVars);
626 }
627 
628 void OMPCopyinClause::setSourceExprs(ArrayRef<Expr *> SrcExprs) {
629   assert(SrcExprs.size() == varlist_size() && "Number of source expressions is "
630                                               "not the same as the "
631                                               "preallocated buffer");
632   std::copy(SrcExprs.begin(), SrcExprs.end(), varlist_end());
633 }
634 
635 void OMPCopyinClause::setDestinationExprs(ArrayRef<Expr *> DstExprs) {
636   assert(DstExprs.size() == varlist_size() && "Number of destination "
637                                               "expressions is not the same as "
638                                               "the preallocated buffer");
639   std::copy(DstExprs.begin(), DstExprs.end(), getSourceExprs().end());
640 }
641 
642 void OMPCopyinClause::setAssignmentOps(ArrayRef<Expr *> AssignmentOps) {
643   assert(AssignmentOps.size() == varlist_size() &&
644          "Number of assignment expressions is not the same as the preallocated "
645          "buffer");
646   std::copy(AssignmentOps.begin(), AssignmentOps.end(),
647             getDestinationExprs().end());
648 }
649 
650 OMPCopyinClause *OMPCopyinClause::Create(
651     const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
652     SourceLocation EndLoc, ArrayRef<Expr *> VL, ArrayRef<Expr *> SrcExprs,
653     ArrayRef<Expr *> DstExprs, ArrayRef<Expr *> AssignmentOps) {
654   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(4 * VL.size()));
655   OMPCopyinClause *Clause =
656       new (Mem) OMPCopyinClause(StartLoc, LParenLoc, EndLoc, VL.size());
657   Clause->setVarRefs(VL);
658   Clause->setSourceExprs(SrcExprs);
659   Clause->setDestinationExprs(DstExprs);
660   Clause->setAssignmentOps(AssignmentOps);
661   return Clause;
662 }
663 
664 OMPCopyinClause *OMPCopyinClause::CreateEmpty(const ASTContext &C, unsigned N) {
665   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(4 * N));
666   return new (Mem) OMPCopyinClause(N);
667 }
668 
669 void OMPCopyprivateClause::setSourceExprs(ArrayRef<Expr *> SrcExprs) {
670   assert(SrcExprs.size() == varlist_size() && "Number of source expressions is "
671                                               "not the same as the "
672                                               "preallocated buffer");
673   std::copy(SrcExprs.begin(), SrcExprs.end(), varlist_end());
674 }
675 
676 void OMPCopyprivateClause::setDestinationExprs(ArrayRef<Expr *> DstExprs) {
677   assert(DstExprs.size() == varlist_size() && "Number of destination "
678                                               "expressions is not the same as "
679                                               "the preallocated buffer");
680   std::copy(DstExprs.begin(), DstExprs.end(), getSourceExprs().end());
681 }
682 
683 void OMPCopyprivateClause::setAssignmentOps(ArrayRef<Expr *> AssignmentOps) {
684   assert(AssignmentOps.size() == varlist_size() &&
685          "Number of assignment expressions is not the same as the preallocated "
686          "buffer");
687   std::copy(AssignmentOps.begin(), AssignmentOps.end(),
688             getDestinationExprs().end());
689 }
690 
691 OMPCopyprivateClause *OMPCopyprivateClause::Create(
692     const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
693     SourceLocation EndLoc, ArrayRef<Expr *> VL, ArrayRef<Expr *> SrcExprs,
694     ArrayRef<Expr *> DstExprs, ArrayRef<Expr *> AssignmentOps) {
695   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(4 * VL.size()));
696   OMPCopyprivateClause *Clause =
697       new (Mem) OMPCopyprivateClause(StartLoc, LParenLoc, EndLoc, VL.size());
698   Clause->setVarRefs(VL);
699   Clause->setSourceExprs(SrcExprs);
700   Clause->setDestinationExprs(DstExprs);
701   Clause->setAssignmentOps(AssignmentOps);
702   return Clause;
703 }
704 
705 OMPCopyprivateClause *OMPCopyprivateClause::CreateEmpty(const ASTContext &C,
706                                                         unsigned N) {
707   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(4 * N));
708   return new (Mem) OMPCopyprivateClause(N);
709 }
710 
711 void OMPReductionClause::setPrivates(ArrayRef<Expr *> Privates) {
712   assert(Privates.size() == varlist_size() &&
713          "Number of private copies is not the same as the preallocated buffer");
714   std::copy(Privates.begin(), Privates.end(), varlist_end());
715 }
716 
717 void OMPReductionClause::setLHSExprs(ArrayRef<Expr *> LHSExprs) {
718   assert(
719       LHSExprs.size() == varlist_size() &&
720       "Number of LHS expressions is not the same as the preallocated buffer");
721   std::copy(LHSExprs.begin(), LHSExprs.end(), getPrivates().end());
722 }
723 
724 void OMPReductionClause::setRHSExprs(ArrayRef<Expr *> RHSExprs) {
725   assert(
726       RHSExprs.size() == varlist_size() &&
727       "Number of RHS expressions is not the same as the preallocated buffer");
728   std::copy(RHSExprs.begin(), RHSExprs.end(), getLHSExprs().end());
729 }
730 
731 void OMPReductionClause::setReductionOps(ArrayRef<Expr *> ReductionOps) {
732   assert(ReductionOps.size() == varlist_size() && "Number of reduction "
733                                                   "expressions is not the same "
734                                                   "as the preallocated buffer");
735   std::copy(ReductionOps.begin(), ReductionOps.end(), getRHSExprs().end());
736 }
737 
738 void OMPReductionClause::setInscanCopyOps(ArrayRef<Expr *> Ops) {
739   assert(Modifier == OMPC_REDUCTION_inscan && "Expected inscan reduction.");
740   assert(Ops.size() == varlist_size() && "Number of copy "
741                                          "expressions is not the same "
742                                          "as the preallocated buffer");
743   llvm::copy(Ops, getReductionOps().end());
744 }
745 
746 void OMPReductionClause::setInscanCopyArrayTemps(
747     ArrayRef<Expr *> CopyArrayTemps) {
748   assert(Modifier == OMPC_REDUCTION_inscan && "Expected inscan reduction.");
749   assert(CopyArrayTemps.size() == varlist_size() &&
750          "Number of copy temp expressions is not the same as the preallocated "
751          "buffer");
752   llvm::copy(CopyArrayTemps, getInscanCopyOps().end());
753 }
754 
755 void OMPReductionClause::setInscanCopyArrayElems(
756     ArrayRef<Expr *> CopyArrayElems) {
757   assert(Modifier == OMPC_REDUCTION_inscan && "Expected inscan reduction.");
758   assert(CopyArrayElems.size() == varlist_size() &&
759          "Number of copy temp expressions is not the same as the preallocated "
760          "buffer");
761   llvm::copy(CopyArrayElems, getInscanCopyArrayTemps().end());
762 }
763 
764 OMPReductionClause *OMPReductionClause::Create(
765     const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
766     SourceLocation ModifierLoc, SourceLocation EndLoc, SourceLocation ColonLoc,
767     OpenMPReductionClauseModifier Modifier, ArrayRef<Expr *> VL,
768     NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo,
769     ArrayRef<Expr *> Privates, ArrayRef<Expr *> LHSExprs,
770     ArrayRef<Expr *> RHSExprs, ArrayRef<Expr *> ReductionOps,
771     ArrayRef<Expr *> CopyOps, ArrayRef<Expr *> CopyArrayTemps,
772     ArrayRef<Expr *> CopyArrayElems, Stmt *PreInit, Expr *PostUpdate) {
773   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(
774       (Modifier == OMPC_REDUCTION_inscan ? 8 : 5) * VL.size()));
775   auto *Clause = new (Mem)
776       OMPReductionClause(StartLoc, LParenLoc, ModifierLoc, EndLoc, ColonLoc,
777                          Modifier, VL.size(), QualifierLoc, NameInfo);
778   Clause->setVarRefs(VL);
779   Clause->setPrivates(Privates);
780   Clause->setLHSExprs(LHSExprs);
781   Clause->setRHSExprs(RHSExprs);
782   Clause->setReductionOps(ReductionOps);
783   Clause->setPreInitStmt(PreInit);
784   Clause->setPostUpdateExpr(PostUpdate);
785   if (Modifier == OMPC_REDUCTION_inscan) {
786     Clause->setInscanCopyOps(CopyOps);
787     Clause->setInscanCopyArrayTemps(CopyArrayTemps);
788     Clause->setInscanCopyArrayElems(CopyArrayElems);
789   } else {
790     assert(CopyOps.empty() &&
791            "copy operations are expected in inscan reductions only.");
792     assert(CopyArrayTemps.empty() &&
793            "copy array temps are expected in inscan reductions only.");
794     assert(CopyArrayElems.empty() &&
795            "copy array temps are expected in inscan reductions only.");
796   }
797   return Clause;
798 }
799 
800 OMPReductionClause *
801 OMPReductionClause::CreateEmpty(const ASTContext &C, unsigned N,
802                                 OpenMPReductionClauseModifier Modifier) {
803   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(
804       (Modifier == OMPC_REDUCTION_inscan ? 8 : 5) * N));
805   auto *Clause = new (Mem) OMPReductionClause(N);
806   Clause->setModifier(Modifier);
807   return Clause;
808 }
809 
810 void OMPTaskReductionClause::setPrivates(ArrayRef<Expr *> Privates) {
811   assert(Privates.size() == varlist_size() &&
812          "Number of private copies is not the same as the preallocated buffer");
813   std::copy(Privates.begin(), Privates.end(), varlist_end());
814 }
815 
816 void OMPTaskReductionClause::setLHSExprs(ArrayRef<Expr *> LHSExprs) {
817   assert(
818       LHSExprs.size() == varlist_size() &&
819       "Number of LHS expressions is not the same as the preallocated buffer");
820   std::copy(LHSExprs.begin(), LHSExprs.end(), getPrivates().end());
821 }
822 
823 void OMPTaskReductionClause::setRHSExprs(ArrayRef<Expr *> RHSExprs) {
824   assert(
825       RHSExprs.size() == varlist_size() &&
826       "Number of RHS expressions is not the same as the preallocated buffer");
827   std::copy(RHSExprs.begin(), RHSExprs.end(), getLHSExprs().end());
828 }
829 
830 void OMPTaskReductionClause::setReductionOps(ArrayRef<Expr *> ReductionOps) {
831   assert(ReductionOps.size() == varlist_size() && "Number of task reduction "
832                                                   "expressions is not the same "
833                                                   "as the preallocated buffer");
834   std::copy(ReductionOps.begin(), ReductionOps.end(), getRHSExprs().end());
835 }
836 
837 OMPTaskReductionClause *OMPTaskReductionClause::Create(
838     const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
839     SourceLocation EndLoc, SourceLocation ColonLoc, ArrayRef<Expr *> VL,
840     NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo,
841     ArrayRef<Expr *> Privates, ArrayRef<Expr *> LHSExprs,
842     ArrayRef<Expr *> RHSExprs, ArrayRef<Expr *> ReductionOps, Stmt *PreInit,
843     Expr *PostUpdate) {
844   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * VL.size()));
845   OMPTaskReductionClause *Clause = new (Mem) OMPTaskReductionClause(
846       StartLoc, LParenLoc, EndLoc, ColonLoc, VL.size(), QualifierLoc, NameInfo);
847   Clause->setVarRefs(VL);
848   Clause->setPrivates(Privates);
849   Clause->setLHSExprs(LHSExprs);
850   Clause->setRHSExprs(RHSExprs);
851   Clause->setReductionOps(ReductionOps);
852   Clause->setPreInitStmt(PreInit);
853   Clause->setPostUpdateExpr(PostUpdate);
854   return Clause;
855 }
856 
857 OMPTaskReductionClause *OMPTaskReductionClause::CreateEmpty(const ASTContext &C,
858                                                             unsigned N) {
859   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * N));
860   return new (Mem) OMPTaskReductionClause(N);
861 }
862 
863 void OMPInReductionClause::setPrivates(ArrayRef<Expr *> Privates) {
864   assert(Privates.size() == varlist_size() &&
865          "Number of private copies is not the same as the preallocated buffer");
866   std::copy(Privates.begin(), Privates.end(), varlist_end());
867 }
868 
869 void OMPInReductionClause::setLHSExprs(ArrayRef<Expr *> LHSExprs) {
870   assert(
871       LHSExprs.size() == varlist_size() &&
872       "Number of LHS expressions is not the same as the preallocated buffer");
873   std::copy(LHSExprs.begin(), LHSExprs.end(), getPrivates().end());
874 }
875 
876 void OMPInReductionClause::setRHSExprs(ArrayRef<Expr *> RHSExprs) {
877   assert(
878       RHSExprs.size() == varlist_size() &&
879       "Number of RHS expressions is not the same as the preallocated buffer");
880   std::copy(RHSExprs.begin(), RHSExprs.end(), getLHSExprs().end());
881 }
882 
883 void OMPInReductionClause::setReductionOps(ArrayRef<Expr *> ReductionOps) {
884   assert(ReductionOps.size() == varlist_size() && "Number of in reduction "
885                                                   "expressions is not the same "
886                                                   "as the preallocated buffer");
887   std::copy(ReductionOps.begin(), ReductionOps.end(), getRHSExprs().end());
888 }
889 
890 void OMPInReductionClause::setTaskgroupDescriptors(
891     ArrayRef<Expr *> TaskgroupDescriptors) {
892   assert(TaskgroupDescriptors.size() == varlist_size() &&
893          "Number of in reduction descriptors is not the same as the "
894          "preallocated buffer");
895   std::copy(TaskgroupDescriptors.begin(), TaskgroupDescriptors.end(),
896             getReductionOps().end());
897 }
898 
899 OMPInReductionClause *OMPInReductionClause::Create(
900     const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc,
901     SourceLocation EndLoc, SourceLocation ColonLoc, ArrayRef<Expr *> VL,
902     NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo,
903     ArrayRef<Expr *> Privates, ArrayRef<Expr *> LHSExprs,
904     ArrayRef<Expr *> RHSExprs, ArrayRef<Expr *> ReductionOps,
905     ArrayRef<Expr *> TaskgroupDescriptors, Stmt *PreInit, Expr *PostUpdate) {
906   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(6 * VL.size()));
907   OMPInReductionClause *Clause = new (Mem) OMPInReductionClause(
908       StartLoc, LParenLoc, EndLoc, ColonLoc, VL.size(), QualifierLoc, NameInfo);
909   Clause->setVarRefs(VL);
910   Clause->setPrivates(Privates);
911   Clause->setLHSExprs(LHSExprs);
912   Clause->setRHSExprs(RHSExprs);
913   Clause->setReductionOps(ReductionOps);
914   Clause->setTaskgroupDescriptors(TaskgroupDescriptors);
915   Clause->setPreInitStmt(PreInit);
916   Clause->setPostUpdateExpr(PostUpdate);
917   return Clause;
918 }
919 
920 OMPInReductionClause *OMPInReductionClause::CreateEmpty(const ASTContext &C,
921                                                         unsigned N) {
922   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(6 * N));
923   return new (Mem) OMPInReductionClause(N);
924 }
925 
926 OMPSizesClause *OMPSizesClause::Create(const ASTContext &C,
927                                        SourceLocation StartLoc,
928                                        SourceLocation LParenLoc,
929                                        SourceLocation EndLoc,
930                                        ArrayRef<Expr *> Sizes) {
931   OMPSizesClause *Clause = CreateEmpty(C, Sizes.size());
932   Clause->setLocStart(StartLoc);
933   Clause->setLParenLoc(LParenLoc);
934   Clause->setLocEnd(EndLoc);
935   Clause->setSizesRefs(Sizes);
936   return Clause;
937 }
938 
939 OMPSizesClause *OMPSizesClause::CreateEmpty(const ASTContext &C,
940                                             unsigned NumSizes) {
941   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(NumSizes));
942   return new (Mem) OMPSizesClause(NumSizes);
943 }
944 
945 OMPFullClause *OMPFullClause::Create(const ASTContext &C,
946                                      SourceLocation StartLoc,
947                                      SourceLocation EndLoc) {
948   OMPFullClause *Clause = CreateEmpty(C);
949   Clause->setLocStart(StartLoc);
950   Clause->setLocEnd(EndLoc);
951   return Clause;
952 }
953 
954 OMPFullClause *OMPFullClause::CreateEmpty(const ASTContext &C) {
955   return new (C) OMPFullClause();
956 }
957 
958 OMPPartialClause *OMPPartialClause::Create(const ASTContext &C,
959                                            SourceLocation StartLoc,
960                                            SourceLocation LParenLoc,
961                                            SourceLocation EndLoc,
962                                            Expr *Factor) {
963   OMPPartialClause *Clause = CreateEmpty(C);
964   Clause->setLocStart(StartLoc);
965   Clause->setLParenLoc(LParenLoc);
966   Clause->setLocEnd(EndLoc);
967   Clause->setFactor(Factor);
968   return Clause;
969 }
970 
971 OMPPartialClause *OMPPartialClause::CreateEmpty(const ASTContext &C) {
972   return new (C) OMPPartialClause();
973 }
974 
975 OMPAllocateClause *
976 OMPAllocateClause::Create(const ASTContext &C, SourceLocation StartLoc,
977                           SourceLocation LParenLoc, Expr *Allocator,
978                           SourceLocation ColonLoc, SourceLocation EndLoc,
979                           ArrayRef<Expr *> VL) {
980   // Allocate space for private variables and initializer expressions.
981   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size()));
982   auto *Clause = new (Mem) OMPAllocateClause(StartLoc, LParenLoc, Allocator,
983                                              ColonLoc, EndLoc, VL.size());
984   Clause->setVarRefs(VL);
985   return Clause;
986 }
987 
988 OMPAllocateClause *OMPAllocateClause::CreateEmpty(const ASTContext &C,
989                                                   unsigned N) {
990   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
991   return new (Mem) OMPAllocateClause(N);
992 }
993 
994 OMPFlushClause *OMPFlushClause::Create(const ASTContext &C,
995                                        SourceLocation StartLoc,
996                                        SourceLocation LParenLoc,
997                                        SourceLocation EndLoc,
998                                        ArrayRef<Expr *> VL) {
999   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size() + 1));
1000   OMPFlushClause *Clause =
1001       new (Mem) OMPFlushClause(StartLoc, LParenLoc, EndLoc, VL.size());
1002   Clause->setVarRefs(VL);
1003   return Clause;
1004 }
1005 
1006 OMPFlushClause *OMPFlushClause::CreateEmpty(const ASTContext &C, unsigned N) {
1007   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
1008   return new (Mem) OMPFlushClause(N);
1009 }
1010 
1011 OMPDepobjClause *OMPDepobjClause::Create(const ASTContext &C,
1012                                          SourceLocation StartLoc,
1013                                          SourceLocation LParenLoc,
1014                                          SourceLocation RParenLoc,
1015                                          Expr *Depobj) {
1016   auto *Clause = new (C) OMPDepobjClause(StartLoc, LParenLoc, RParenLoc);
1017   Clause->setDepobj(Depobj);
1018   return Clause;
1019 }
1020 
1021 OMPDepobjClause *OMPDepobjClause::CreateEmpty(const ASTContext &C) {
1022   return new (C) OMPDepobjClause();
1023 }
1024 
1025 OMPDependClause *
1026 OMPDependClause::Create(const ASTContext &C, SourceLocation StartLoc,
1027                         SourceLocation LParenLoc, SourceLocation EndLoc,
1028                         Expr *DepModifier, OpenMPDependClauseKind DepKind,
1029                         SourceLocation DepLoc, SourceLocation ColonLoc,
1030                         ArrayRef<Expr *> VL, unsigned NumLoops) {
1031   void *Mem = C.Allocate(
1032       totalSizeToAlloc<Expr *>(VL.size() + /*depend-modifier*/ 1 + NumLoops),
1033       alignof(OMPDependClause));
1034   OMPDependClause *Clause = new (Mem)
1035       OMPDependClause(StartLoc, LParenLoc, EndLoc, VL.size(), NumLoops);
1036   Clause->setVarRefs(VL);
1037   Clause->setDependencyKind(DepKind);
1038   Clause->setDependencyLoc(DepLoc);
1039   Clause->setColonLoc(ColonLoc);
1040   Clause->setModifier(DepModifier);
1041   for (unsigned I = 0 ; I < NumLoops; ++I)
1042     Clause->setLoopData(I, nullptr);
1043   return Clause;
1044 }
1045 
1046 OMPDependClause *OMPDependClause::CreateEmpty(const ASTContext &C, unsigned N,
1047                                               unsigned NumLoops) {
1048   void *Mem =
1049       C.Allocate(totalSizeToAlloc<Expr *>(N + /*depend-modifier*/ 1 + NumLoops),
1050                  alignof(OMPDependClause));
1051   return new (Mem) OMPDependClause(N, NumLoops);
1052 }
1053 
1054 void OMPDependClause::setLoopData(unsigned NumLoop, Expr *Cnt) {
1055   assert((getDependencyKind() == OMPC_DEPEND_sink ||
1056           getDependencyKind() == OMPC_DEPEND_source) &&
1057          NumLoop < NumLoops &&
1058          "Expected sink or source depend + loop index must be less number of "
1059          "loops.");
1060   auto *It = std::next(getVarRefs().end(), NumLoop + 1);
1061   *It = Cnt;
1062 }
1063 
1064 Expr *OMPDependClause::getLoopData(unsigned NumLoop) {
1065   assert((getDependencyKind() == OMPC_DEPEND_sink ||
1066           getDependencyKind() == OMPC_DEPEND_source) &&
1067          NumLoop < NumLoops &&
1068          "Expected sink or source depend + loop index must be less number of "
1069          "loops.");
1070   auto *It = std::next(getVarRefs().end(), NumLoop + 1);
1071   return *It;
1072 }
1073 
1074 const Expr *OMPDependClause::getLoopData(unsigned NumLoop) const {
1075   assert((getDependencyKind() == OMPC_DEPEND_sink ||
1076           getDependencyKind() == OMPC_DEPEND_source) &&
1077          NumLoop < NumLoops &&
1078          "Expected sink or source depend + loop index must be less number of "
1079          "loops.");
1080   const auto *It = std::next(getVarRefs().end(), NumLoop + 1);
1081   return *It;
1082 }
1083 
1084 void OMPDependClause::setModifier(Expr *DepModifier) {
1085   *getVarRefs().end() = DepModifier;
1086 }
1087 Expr *OMPDependClause::getModifier() { return *getVarRefs().end(); }
1088 
1089 unsigned OMPClauseMappableExprCommon::getComponentsTotalNumber(
1090     MappableExprComponentListsRef ComponentLists) {
1091   unsigned TotalNum = 0u;
1092   for (auto &C : ComponentLists)
1093     TotalNum += C.size();
1094   return TotalNum;
1095 }
1096 
1097 unsigned OMPClauseMappableExprCommon::getUniqueDeclarationsTotalNumber(
1098     ArrayRef<const ValueDecl *> Declarations) {
1099   unsigned TotalNum = 0u;
1100   llvm::SmallPtrSet<const ValueDecl *, 8> Cache;
1101   for (const ValueDecl *D : Declarations) {
1102     const ValueDecl *VD = D ? cast<ValueDecl>(D->getCanonicalDecl()) : nullptr;
1103     if (Cache.count(VD))
1104       continue;
1105     ++TotalNum;
1106     Cache.insert(VD);
1107   }
1108   return TotalNum;
1109 }
1110 
1111 OMPMapClause *OMPMapClause::Create(
1112     const ASTContext &C, const OMPVarListLocTy &Locs, ArrayRef<Expr *> Vars,
1113     ArrayRef<ValueDecl *> Declarations,
1114     MappableExprComponentListsRef ComponentLists, ArrayRef<Expr *> UDMapperRefs,
1115     ArrayRef<OpenMPMapModifierKind> MapModifiers,
1116     ArrayRef<SourceLocation> MapModifiersLoc,
1117     NestedNameSpecifierLoc UDMQualifierLoc, DeclarationNameInfo MapperId,
1118     OpenMPMapClauseKind Type, bool TypeIsImplicit, SourceLocation TypeLoc) {
1119   OMPMappableExprListSizeTy Sizes;
1120   Sizes.NumVars = Vars.size();
1121   Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1122   Sizes.NumComponentLists = ComponentLists.size();
1123   Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1124 
1125   // We need to allocate:
1126   // 2 x NumVars x Expr* - we have an original list expression and an associated
1127   // user-defined mapper for each clause list entry.
1128   // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1129   // with each component list.
1130   // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1131   // number of lists for each unique declaration and the size of each component
1132   // list.
1133   // NumComponents x MappableComponent - the total of all the components in all
1134   // the lists.
1135   void *Mem = C.Allocate(
1136       totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1137                        OMPClauseMappableExprCommon::MappableComponent>(
1138           2 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1139           Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1140           Sizes.NumComponents));
1141   OMPMapClause *Clause = new (Mem)
1142       OMPMapClause(MapModifiers, MapModifiersLoc, UDMQualifierLoc, MapperId,
1143                    Type, TypeIsImplicit, TypeLoc, Locs, Sizes);
1144 
1145   Clause->setVarRefs(Vars);
1146   Clause->setUDMapperRefs(UDMapperRefs);
1147   Clause->setClauseInfo(Declarations, ComponentLists);
1148   Clause->setMapType(Type);
1149   Clause->setMapLoc(TypeLoc);
1150   return Clause;
1151 }
1152 
1153 OMPMapClause *
1154 OMPMapClause::CreateEmpty(const ASTContext &C,
1155                           const OMPMappableExprListSizeTy &Sizes) {
1156   void *Mem = C.Allocate(
1157       totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1158                        OMPClauseMappableExprCommon::MappableComponent>(
1159           2 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1160           Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1161           Sizes.NumComponents));
1162   return new (Mem) OMPMapClause(Sizes);
1163 }
1164 
1165 OMPToClause *OMPToClause::Create(
1166     const ASTContext &C, const OMPVarListLocTy &Locs, ArrayRef<Expr *> Vars,
1167     ArrayRef<ValueDecl *> Declarations,
1168     MappableExprComponentListsRef ComponentLists, ArrayRef<Expr *> UDMapperRefs,
1169     ArrayRef<OpenMPMotionModifierKind> MotionModifiers,
1170     ArrayRef<SourceLocation> MotionModifiersLoc,
1171     NestedNameSpecifierLoc UDMQualifierLoc, DeclarationNameInfo MapperId) {
1172   OMPMappableExprListSizeTy Sizes;
1173   Sizes.NumVars = Vars.size();
1174   Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1175   Sizes.NumComponentLists = ComponentLists.size();
1176   Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1177 
1178   // We need to allocate:
1179   // 2 x NumVars x Expr* - we have an original list expression and an associated
1180   // user-defined mapper for each clause list entry.
1181   // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1182   // with each component list.
1183   // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1184   // number of lists for each unique declaration and the size of each component
1185   // list.
1186   // NumComponents x MappableComponent - the total of all the components in all
1187   // the lists.
1188   void *Mem = C.Allocate(
1189       totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1190                        OMPClauseMappableExprCommon::MappableComponent>(
1191           2 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1192           Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1193           Sizes.NumComponents));
1194 
1195   auto *Clause = new (Mem) OMPToClause(MotionModifiers, MotionModifiersLoc,
1196                                        UDMQualifierLoc, MapperId, Locs, Sizes);
1197 
1198   Clause->setVarRefs(Vars);
1199   Clause->setUDMapperRefs(UDMapperRefs);
1200   Clause->setClauseInfo(Declarations, ComponentLists);
1201   return Clause;
1202 }
1203 
1204 OMPToClause *OMPToClause::CreateEmpty(const ASTContext &C,
1205                                       const OMPMappableExprListSizeTy &Sizes) {
1206   void *Mem = C.Allocate(
1207       totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1208                        OMPClauseMappableExprCommon::MappableComponent>(
1209           2 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1210           Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1211           Sizes.NumComponents));
1212   return new (Mem) OMPToClause(Sizes);
1213 }
1214 
1215 OMPFromClause *OMPFromClause::Create(
1216     const ASTContext &C, const OMPVarListLocTy &Locs, ArrayRef<Expr *> Vars,
1217     ArrayRef<ValueDecl *> Declarations,
1218     MappableExprComponentListsRef ComponentLists, ArrayRef<Expr *> UDMapperRefs,
1219     ArrayRef<OpenMPMotionModifierKind> MotionModifiers,
1220     ArrayRef<SourceLocation> MotionModifiersLoc,
1221     NestedNameSpecifierLoc UDMQualifierLoc, DeclarationNameInfo MapperId) {
1222   OMPMappableExprListSizeTy Sizes;
1223   Sizes.NumVars = Vars.size();
1224   Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1225   Sizes.NumComponentLists = ComponentLists.size();
1226   Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1227 
1228   // We need to allocate:
1229   // 2 x NumVars x Expr* - we have an original list expression and an associated
1230   // user-defined mapper for each clause list entry.
1231   // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1232   // with each component list.
1233   // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1234   // number of lists for each unique declaration and the size of each component
1235   // list.
1236   // NumComponents x MappableComponent - the total of all the components in all
1237   // the lists.
1238   void *Mem = C.Allocate(
1239       totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1240                        OMPClauseMappableExprCommon::MappableComponent>(
1241           2 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1242           Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1243           Sizes.NumComponents));
1244 
1245   auto *Clause =
1246       new (Mem) OMPFromClause(MotionModifiers, MotionModifiersLoc,
1247                               UDMQualifierLoc, MapperId, Locs, Sizes);
1248 
1249   Clause->setVarRefs(Vars);
1250   Clause->setUDMapperRefs(UDMapperRefs);
1251   Clause->setClauseInfo(Declarations, ComponentLists);
1252   return Clause;
1253 }
1254 
1255 OMPFromClause *
1256 OMPFromClause::CreateEmpty(const ASTContext &C,
1257                            const OMPMappableExprListSizeTy &Sizes) {
1258   void *Mem = C.Allocate(
1259       totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1260                        OMPClauseMappableExprCommon::MappableComponent>(
1261           2 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1262           Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1263           Sizes.NumComponents));
1264   return new (Mem) OMPFromClause(Sizes);
1265 }
1266 
1267 void OMPUseDevicePtrClause::setPrivateCopies(ArrayRef<Expr *> VL) {
1268   assert(VL.size() == varlist_size() &&
1269          "Number of private copies is not the same as the preallocated buffer");
1270   std::copy(VL.begin(), VL.end(), varlist_end());
1271 }
1272 
1273 void OMPUseDevicePtrClause::setInits(ArrayRef<Expr *> VL) {
1274   assert(VL.size() == varlist_size() &&
1275          "Number of inits is not the same as the preallocated buffer");
1276   std::copy(VL.begin(), VL.end(), getPrivateCopies().end());
1277 }
1278 
1279 OMPUseDevicePtrClause *OMPUseDevicePtrClause::Create(
1280     const ASTContext &C, const OMPVarListLocTy &Locs, ArrayRef<Expr *> Vars,
1281     ArrayRef<Expr *> PrivateVars, ArrayRef<Expr *> Inits,
1282     ArrayRef<ValueDecl *> Declarations,
1283     MappableExprComponentListsRef ComponentLists) {
1284   OMPMappableExprListSizeTy Sizes;
1285   Sizes.NumVars = Vars.size();
1286   Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1287   Sizes.NumComponentLists = ComponentLists.size();
1288   Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1289 
1290   // We need to allocate:
1291   // NumVars x Expr* - we have an original list expression for each clause
1292   // list entry.
1293   // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1294   // with each component list.
1295   // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1296   // number of lists for each unique declaration and the size of each component
1297   // list.
1298   // NumComponents x MappableComponent - the total of all the components in all
1299   // the lists.
1300   void *Mem = C.Allocate(
1301       totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1302                        OMPClauseMappableExprCommon::MappableComponent>(
1303           3 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1304           Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1305           Sizes.NumComponents));
1306 
1307   OMPUseDevicePtrClause *Clause = new (Mem) OMPUseDevicePtrClause(Locs, Sizes);
1308 
1309   Clause->setVarRefs(Vars);
1310   Clause->setPrivateCopies(PrivateVars);
1311   Clause->setInits(Inits);
1312   Clause->setClauseInfo(Declarations, ComponentLists);
1313   return Clause;
1314 }
1315 
1316 OMPUseDevicePtrClause *
1317 OMPUseDevicePtrClause::CreateEmpty(const ASTContext &C,
1318                                    const OMPMappableExprListSizeTy &Sizes) {
1319   void *Mem = C.Allocate(
1320       totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1321                        OMPClauseMappableExprCommon::MappableComponent>(
1322           3 * Sizes.NumVars, Sizes.NumUniqueDeclarations,
1323           Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1324           Sizes.NumComponents));
1325   return new (Mem) OMPUseDevicePtrClause(Sizes);
1326 }
1327 
1328 OMPUseDeviceAddrClause *
1329 OMPUseDeviceAddrClause::Create(const ASTContext &C, const OMPVarListLocTy &Locs,
1330                                ArrayRef<Expr *> Vars,
1331                                ArrayRef<ValueDecl *> Declarations,
1332                                MappableExprComponentListsRef ComponentLists) {
1333   OMPMappableExprListSizeTy Sizes;
1334   Sizes.NumVars = Vars.size();
1335   Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1336   Sizes.NumComponentLists = ComponentLists.size();
1337   Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1338 
1339   // We need to allocate:
1340   // 3 x NumVars x Expr* - we have an original list expression for each clause
1341   // list entry and an equal number of private copies and inits.
1342   // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1343   // with each component list.
1344   // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1345   // number of lists for each unique declaration and the size of each component
1346   // list.
1347   // NumComponents x MappableComponent - the total of all the components in all
1348   // the lists.
1349   void *Mem = C.Allocate(
1350       totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1351                        OMPClauseMappableExprCommon::MappableComponent>(
1352           Sizes.NumVars, Sizes.NumUniqueDeclarations,
1353           Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1354           Sizes.NumComponents));
1355 
1356   auto *Clause = new (Mem) OMPUseDeviceAddrClause(Locs, Sizes);
1357 
1358   Clause->setVarRefs(Vars);
1359   Clause->setClauseInfo(Declarations, ComponentLists);
1360   return Clause;
1361 }
1362 
1363 OMPUseDeviceAddrClause *
1364 OMPUseDeviceAddrClause::CreateEmpty(const ASTContext &C,
1365                                     const OMPMappableExprListSizeTy &Sizes) {
1366   void *Mem = C.Allocate(
1367       totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1368                        OMPClauseMappableExprCommon::MappableComponent>(
1369           Sizes.NumVars, Sizes.NumUniqueDeclarations,
1370           Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1371           Sizes.NumComponents));
1372   return new (Mem) OMPUseDeviceAddrClause(Sizes);
1373 }
1374 
1375 OMPIsDevicePtrClause *
1376 OMPIsDevicePtrClause::Create(const ASTContext &C, const OMPVarListLocTy &Locs,
1377                              ArrayRef<Expr *> Vars,
1378                              ArrayRef<ValueDecl *> Declarations,
1379                              MappableExprComponentListsRef ComponentLists) {
1380   OMPMappableExprListSizeTy Sizes;
1381   Sizes.NumVars = Vars.size();
1382   Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations);
1383   Sizes.NumComponentLists = ComponentLists.size();
1384   Sizes.NumComponents = getComponentsTotalNumber(ComponentLists);
1385 
1386   // We need to allocate:
1387   // NumVars x Expr* - we have an original list expression for each clause list
1388   // entry.
1389   // NumUniqueDeclarations x ValueDecl* - unique base declarations associated
1390   // with each component list.
1391   // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the
1392   // number of lists for each unique declaration and the size of each component
1393   // list.
1394   // NumComponents x MappableComponent - the total of all the components in all
1395   // the lists.
1396   void *Mem = C.Allocate(
1397       totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1398                        OMPClauseMappableExprCommon::MappableComponent>(
1399           Sizes.NumVars, Sizes.NumUniqueDeclarations,
1400           Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1401           Sizes.NumComponents));
1402 
1403   OMPIsDevicePtrClause *Clause = new (Mem) OMPIsDevicePtrClause(Locs, Sizes);
1404 
1405   Clause->setVarRefs(Vars);
1406   Clause->setClauseInfo(Declarations, ComponentLists);
1407   return Clause;
1408 }
1409 
1410 OMPIsDevicePtrClause *
1411 OMPIsDevicePtrClause::CreateEmpty(const ASTContext &C,
1412                                   const OMPMappableExprListSizeTy &Sizes) {
1413   void *Mem = C.Allocate(
1414       totalSizeToAlloc<Expr *, ValueDecl *, unsigned,
1415                        OMPClauseMappableExprCommon::MappableComponent>(
1416           Sizes.NumVars, Sizes.NumUniqueDeclarations,
1417           Sizes.NumUniqueDeclarations + Sizes.NumComponentLists,
1418           Sizes.NumComponents));
1419   return new (Mem) OMPIsDevicePtrClause(Sizes);
1420 }
1421 
1422 OMPNontemporalClause *OMPNontemporalClause::Create(const ASTContext &C,
1423                                                    SourceLocation StartLoc,
1424                                                    SourceLocation LParenLoc,
1425                                                    SourceLocation EndLoc,
1426                                                    ArrayRef<Expr *> VL) {
1427   // Allocate space for nontemporal variables + private references.
1428   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * VL.size()));
1429   auto *Clause =
1430       new (Mem) OMPNontemporalClause(StartLoc, LParenLoc, EndLoc, VL.size());
1431   Clause->setVarRefs(VL);
1432   return Clause;
1433 }
1434 
1435 OMPNontemporalClause *OMPNontemporalClause::CreateEmpty(const ASTContext &C,
1436                                                         unsigned N) {
1437   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * N));
1438   return new (Mem) OMPNontemporalClause(N);
1439 }
1440 
1441 void OMPNontemporalClause::setPrivateRefs(ArrayRef<Expr *> VL) {
1442   assert(VL.size() == varlist_size() && "Number of private references is not "
1443                                         "the same as the preallocated buffer");
1444   std::copy(VL.begin(), VL.end(), varlist_end());
1445 }
1446 
1447 OMPInclusiveClause *OMPInclusiveClause::Create(const ASTContext &C,
1448                                                SourceLocation StartLoc,
1449                                                SourceLocation LParenLoc,
1450                                                SourceLocation EndLoc,
1451                                                ArrayRef<Expr *> VL) {
1452   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size()));
1453   auto *Clause =
1454       new (Mem) OMPInclusiveClause(StartLoc, LParenLoc, EndLoc, VL.size());
1455   Clause->setVarRefs(VL);
1456   return Clause;
1457 }
1458 
1459 OMPInclusiveClause *OMPInclusiveClause::CreateEmpty(const ASTContext &C,
1460                                                     unsigned N) {
1461   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
1462   return new (Mem) OMPInclusiveClause(N);
1463 }
1464 
1465 OMPExclusiveClause *OMPExclusiveClause::Create(const ASTContext &C,
1466                                                SourceLocation StartLoc,
1467                                                SourceLocation LParenLoc,
1468                                                SourceLocation EndLoc,
1469                                                ArrayRef<Expr *> VL) {
1470   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size()));
1471   auto *Clause =
1472       new (Mem) OMPExclusiveClause(StartLoc, LParenLoc, EndLoc, VL.size());
1473   Clause->setVarRefs(VL);
1474   return Clause;
1475 }
1476 
1477 OMPExclusiveClause *OMPExclusiveClause::CreateEmpty(const ASTContext &C,
1478                                                     unsigned N) {
1479   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
1480   return new (Mem) OMPExclusiveClause(N);
1481 }
1482 
1483 void OMPUsesAllocatorsClause::setAllocatorsData(
1484     ArrayRef<OMPUsesAllocatorsClause::Data> Data) {
1485   assert(Data.size() == NumOfAllocators &&
1486          "Size of allocators data is not the same as the preallocated buffer.");
1487   for (unsigned I = 0, E = Data.size(); I < E; ++I) {
1488     const OMPUsesAllocatorsClause::Data &D = Data[I];
1489     getTrailingObjects<Expr *>()[I * static_cast<int>(ExprOffsets::Total) +
1490                                  static_cast<int>(ExprOffsets::Allocator)] =
1491         D.Allocator;
1492     getTrailingObjects<Expr *>()[I * static_cast<int>(ExprOffsets::Total) +
1493                                  static_cast<int>(
1494                                      ExprOffsets::AllocatorTraits)] =
1495         D.AllocatorTraits;
1496     getTrailingObjects<
1497         SourceLocation>()[I * static_cast<int>(ParenLocsOffsets::Total) +
1498                           static_cast<int>(ParenLocsOffsets::LParen)] =
1499         D.LParenLoc;
1500     getTrailingObjects<
1501         SourceLocation>()[I * static_cast<int>(ParenLocsOffsets::Total) +
1502                           static_cast<int>(ParenLocsOffsets::RParen)] =
1503         D.RParenLoc;
1504   }
1505 }
1506 
1507 OMPUsesAllocatorsClause::Data
1508 OMPUsesAllocatorsClause::getAllocatorData(unsigned I) const {
1509   OMPUsesAllocatorsClause::Data Data;
1510   Data.Allocator =
1511       getTrailingObjects<Expr *>()[I * static_cast<int>(ExprOffsets::Total) +
1512                                    static_cast<int>(ExprOffsets::Allocator)];
1513   Data.AllocatorTraits =
1514       getTrailingObjects<Expr *>()[I * static_cast<int>(ExprOffsets::Total) +
1515                                    static_cast<int>(
1516                                        ExprOffsets::AllocatorTraits)];
1517   Data.LParenLoc = getTrailingObjects<
1518       SourceLocation>()[I * static_cast<int>(ParenLocsOffsets::Total) +
1519                         static_cast<int>(ParenLocsOffsets::LParen)];
1520   Data.RParenLoc = getTrailingObjects<
1521       SourceLocation>()[I * static_cast<int>(ParenLocsOffsets::Total) +
1522                         static_cast<int>(ParenLocsOffsets::RParen)];
1523   return Data;
1524 }
1525 
1526 OMPUsesAllocatorsClause *
1527 OMPUsesAllocatorsClause::Create(const ASTContext &C, SourceLocation StartLoc,
1528                                 SourceLocation LParenLoc, SourceLocation EndLoc,
1529                                 ArrayRef<OMPUsesAllocatorsClause::Data> Data) {
1530   void *Mem = C.Allocate(totalSizeToAlloc<Expr *, SourceLocation>(
1531       static_cast<int>(ExprOffsets::Total) * Data.size(),
1532       static_cast<int>(ParenLocsOffsets::Total) * Data.size()));
1533   auto *Clause = new (Mem)
1534       OMPUsesAllocatorsClause(StartLoc, LParenLoc, EndLoc, Data.size());
1535   Clause->setAllocatorsData(Data);
1536   return Clause;
1537 }
1538 
1539 OMPUsesAllocatorsClause *
1540 OMPUsesAllocatorsClause::CreateEmpty(const ASTContext &C, unsigned N) {
1541   void *Mem = C.Allocate(totalSizeToAlloc<Expr *, SourceLocation>(
1542       static_cast<int>(ExprOffsets::Total) * N,
1543       static_cast<int>(ParenLocsOffsets::Total) * N));
1544   return new (Mem) OMPUsesAllocatorsClause(N);
1545 }
1546 
1547 OMPAffinityClause *
1548 OMPAffinityClause::Create(const ASTContext &C, SourceLocation StartLoc,
1549                           SourceLocation LParenLoc, SourceLocation ColonLoc,
1550                           SourceLocation EndLoc, Expr *Modifier,
1551                           ArrayRef<Expr *> Locators) {
1552   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(Locators.size() + 1));
1553   auto *Clause = new (Mem)
1554       OMPAffinityClause(StartLoc, LParenLoc, ColonLoc, EndLoc, Locators.size());
1555   Clause->setModifier(Modifier);
1556   Clause->setVarRefs(Locators);
1557   return Clause;
1558 }
1559 
1560 OMPAffinityClause *OMPAffinityClause::CreateEmpty(const ASTContext &C,
1561                                                   unsigned N) {
1562   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N + 1));
1563   return new (Mem) OMPAffinityClause(N);
1564 }
1565 
1566 OMPInitClause *OMPInitClause::Create(const ASTContext &C, Expr *InteropVar,
1567                                      ArrayRef<Expr *> PrefExprs, bool IsTarget,
1568                                      bool IsTargetSync, SourceLocation StartLoc,
1569                                      SourceLocation LParenLoc,
1570                                      SourceLocation VarLoc,
1571                                      SourceLocation EndLoc) {
1572 
1573   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(PrefExprs.size() + 1));
1574   auto *Clause =
1575       new (Mem) OMPInitClause(IsTarget, IsTargetSync, StartLoc, LParenLoc,
1576                               VarLoc, EndLoc, PrefExprs.size() + 1);
1577   Clause->setInteropVar(InteropVar);
1578   llvm::copy(PrefExprs, Clause->getTrailingObjects<Expr *>() + 1);
1579   return Clause;
1580 }
1581 
1582 OMPInitClause *OMPInitClause::CreateEmpty(const ASTContext &C, unsigned N) {
1583   void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N));
1584   return new (Mem) OMPInitClause(N);
1585 }
1586 
1587 //===----------------------------------------------------------------------===//
1588 //  OpenMP clauses printing methods
1589 //===----------------------------------------------------------------------===//
1590 
1591 void OMPClausePrinter::VisitOMPIfClause(OMPIfClause *Node) {
1592   OS << "if(";
1593   if (Node->getNameModifier() != OMPD_unknown)
1594     OS << getOpenMPDirectiveName(Node->getNameModifier()) << ": ";
1595   Node->getCondition()->printPretty(OS, nullptr, Policy, 0);
1596   OS << ")";
1597 }
1598 
1599 void OMPClausePrinter::VisitOMPFinalClause(OMPFinalClause *Node) {
1600   OS << "final(";
1601   Node->getCondition()->printPretty(OS, nullptr, Policy, 0);
1602   OS << ")";
1603 }
1604 
1605 void OMPClausePrinter::VisitOMPNumThreadsClause(OMPNumThreadsClause *Node) {
1606   OS << "num_threads(";
1607   Node->getNumThreads()->printPretty(OS, nullptr, Policy, 0);
1608   OS << ")";
1609 }
1610 
1611 void OMPClausePrinter::VisitOMPSafelenClause(OMPSafelenClause *Node) {
1612   OS << "safelen(";
1613   Node->getSafelen()->printPretty(OS, nullptr, Policy, 0);
1614   OS << ")";
1615 }
1616 
1617 void OMPClausePrinter::VisitOMPSimdlenClause(OMPSimdlenClause *Node) {
1618   OS << "simdlen(";
1619   Node->getSimdlen()->printPretty(OS, nullptr, Policy, 0);
1620   OS << ")";
1621 }
1622 
1623 void OMPClausePrinter::VisitOMPSizesClause(OMPSizesClause *Node) {
1624   OS << "sizes(";
1625   bool First = true;
1626   for (auto Size : Node->getSizesRefs()) {
1627     if (!First)
1628       OS << ", ";
1629     Size->printPretty(OS, nullptr, Policy, 0);
1630     First = false;
1631   }
1632   OS << ")";
1633 }
1634 
1635 void OMPClausePrinter::VisitOMPFullClause(OMPFullClause *Node) { OS << "full"; }
1636 
1637 void OMPClausePrinter::VisitOMPPartialClause(OMPPartialClause *Node) {
1638   OS << "partial";
1639 
1640   if (Expr *Factor = Node->getFactor()) {
1641     OS << '(';
1642     Factor->printPretty(OS, nullptr, Policy, 0);
1643     OS << ')';
1644   }
1645 }
1646 
1647 void OMPClausePrinter::VisitOMPAllocatorClause(OMPAllocatorClause *Node) {
1648   OS << "allocator(";
1649   Node->getAllocator()->printPretty(OS, nullptr, Policy, 0);
1650   OS << ")";
1651 }
1652 
1653 void OMPClausePrinter::VisitOMPCollapseClause(OMPCollapseClause *Node) {
1654   OS << "collapse(";
1655   Node->getNumForLoops()->printPretty(OS, nullptr, Policy, 0);
1656   OS << ")";
1657 }
1658 
1659 void OMPClausePrinter::VisitOMPDetachClause(OMPDetachClause *Node) {
1660   OS << "detach(";
1661   Node->getEventHandler()->printPretty(OS, nullptr, Policy, 0);
1662   OS << ")";
1663 }
1664 
1665 void OMPClausePrinter::VisitOMPDefaultClause(OMPDefaultClause *Node) {
1666   OS << "default("
1667      << getOpenMPSimpleClauseTypeName(OMPC_default,
1668                                       unsigned(Node->getDefaultKind()))
1669      << ")";
1670 }
1671 
1672 void OMPClausePrinter::VisitOMPProcBindClause(OMPProcBindClause *Node) {
1673   OS << "proc_bind("
1674      << getOpenMPSimpleClauseTypeName(OMPC_proc_bind,
1675                                       unsigned(Node->getProcBindKind()))
1676      << ")";
1677 }
1678 
1679 void OMPClausePrinter::VisitOMPUnifiedAddressClause(OMPUnifiedAddressClause *) {
1680   OS << "unified_address";
1681 }
1682 
1683 void OMPClausePrinter::VisitOMPUnifiedSharedMemoryClause(
1684     OMPUnifiedSharedMemoryClause *) {
1685   OS << "unified_shared_memory";
1686 }
1687 
1688 void OMPClausePrinter::VisitOMPReverseOffloadClause(OMPReverseOffloadClause *) {
1689   OS << "reverse_offload";
1690 }
1691 
1692 void OMPClausePrinter::VisitOMPDynamicAllocatorsClause(
1693     OMPDynamicAllocatorsClause *) {
1694   OS << "dynamic_allocators";
1695 }
1696 
1697 void OMPClausePrinter::VisitOMPAtomicDefaultMemOrderClause(
1698     OMPAtomicDefaultMemOrderClause *Node) {
1699   OS << "atomic_default_mem_order("
1700      << getOpenMPSimpleClauseTypeName(OMPC_atomic_default_mem_order,
1701                                       Node->getAtomicDefaultMemOrderKind())
1702      << ")";
1703 }
1704 
1705 void OMPClausePrinter::VisitOMPScheduleClause(OMPScheduleClause *Node) {
1706   OS << "schedule(";
1707   if (Node->getFirstScheduleModifier() != OMPC_SCHEDULE_MODIFIER_unknown) {
1708     OS << getOpenMPSimpleClauseTypeName(OMPC_schedule,
1709                                         Node->getFirstScheduleModifier());
1710     if (Node->getSecondScheduleModifier() != OMPC_SCHEDULE_MODIFIER_unknown) {
1711       OS << ", ";
1712       OS << getOpenMPSimpleClauseTypeName(OMPC_schedule,
1713                                           Node->getSecondScheduleModifier());
1714     }
1715     OS << ": ";
1716   }
1717   OS << getOpenMPSimpleClauseTypeName(OMPC_schedule, Node->getScheduleKind());
1718   if (auto *E = Node->getChunkSize()) {
1719     OS << ", ";
1720     E->printPretty(OS, nullptr, Policy);
1721   }
1722   OS << ")";
1723 }
1724 
1725 void OMPClausePrinter::VisitOMPOrderedClause(OMPOrderedClause *Node) {
1726   OS << "ordered";
1727   if (auto *Num = Node->getNumForLoops()) {
1728     OS << "(";
1729     Num->printPretty(OS, nullptr, Policy, 0);
1730     OS << ")";
1731   }
1732 }
1733 
1734 void OMPClausePrinter::VisitOMPNowaitClause(OMPNowaitClause *) {
1735   OS << "nowait";
1736 }
1737 
1738 void OMPClausePrinter::VisitOMPUntiedClause(OMPUntiedClause *) {
1739   OS << "untied";
1740 }
1741 
1742 void OMPClausePrinter::VisitOMPNogroupClause(OMPNogroupClause *) {
1743   OS << "nogroup";
1744 }
1745 
1746 void OMPClausePrinter::VisitOMPMergeableClause(OMPMergeableClause *) {
1747   OS << "mergeable";
1748 }
1749 
1750 void OMPClausePrinter::VisitOMPReadClause(OMPReadClause *) { OS << "read"; }
1751 
1752 void OMPClausePrinter::VisitOMPWriteClause(OMPWriteClause *) { OS << "write"; }
1753 
1754 void OMPClausePrinter::VisitOMPUpdateClause(OMPUpdateClause *Node) {
1755   OS << "update";
1756   if (Node->isExtended()) {
1757     OS << "(";
1758     OS << getOpenMPSimpleClauseTypeName(Node->getClauseKind(),
1759                                         Node->getDependencyKind());
1760     OS << ")";
1761   }
1762 }
1763 
1764 void OMPClausePrinter::VisitOMPCaptureClause(OMPCaptureClause *) {
1765   OS << "capture";
1766 }
1767 
1768 void OMPClausePrinter::VisitOMPSeqCstClause(OMPSeqCstClause *) {
1769   OS << "seq_cst";
1770 }
1771 
1772 void OMPClausePrinter::VisitOMPAcqRelClause(OMPAcqRelClause *) {
1773   OS << "acq_rel";
1774 }
1775 
1776 void OMPClausePrinter::VisitOMPAcquireClause(OMPAcquireClause *) {
1777   OS << "acquire";
1778 }
1779 
1780 void OMPClausePrinter::VisitOMPReleaseClause(OMPReleaseClause *) {
1781   OS << "release";
1782 }
1783 
1784 void OMPClausePrinter::VisitOMPRelaxedClause(OMPRelaxedClause *) {
1785   OS << "relaxed";
1786 }
1787 
1788 void OMPClausePrinter::VisitOMPThreadsClause(OMPThreadsClause *) {
1789   OS << "threads";
1790 }
1791 
1792 void OMPClausePrinter::VisitOMPSIMDClause(OMPSIMDClause *) { OS << "simd"; }
1793 
1794 void OMPClausePrinter::VisitOMPDeviceClause(OMPDeviceClause *Node) {
1795   OS << "device(";
1796   OpenMPDeviceClauseModifier Modifier = Node->getModifier();
1797   if (Modifier != OMPC_DEVICE_unknown) {
1798     OS << getOpenMPSimpleClauseTypeName(Node->getClauseKind(), Modifier)
1799        << ": ";
1800   }
1801   Node->getDevice()->printPretty(OS, nullptr, Policy, 0);
1802   OS << ")";
1803 }
1804 
1805 void OMPClausePrinter::VisitOMPNumTeamsClause(OMPNumTeamsClause *Node) {
1806   OS << "num_teams(";
1807   Node->getNumTeams()->printPretty(OS, nullptr, Policy, 0);
1808   OS << ")";
1809 }
1810 
1811 void OMPClausePrinter::VisitOMPThreadLimitClause(OMPThreadLimitClause *Node) {
1812   OS << "thread_limit(";
1813   Node->getThreadLimit()->printPretty(OS, nullptr, Policy, 0);
1814   OS << ")";
1815 }
1816 
1817 void OMPClausePrinter::VisitOMPPriorityClause(OMPPriorityClause *Node) {
1818   OS << "priority(";
1819   Node->getPriority()->printPretty(OS, nullptr, Policy, 0);
1820   OS << ")";
1821 }
1822 
1823 void OMPClausePrinter::VisitOMPGrainsizeClause(OMPGrainsizeClause *Node) {
1824   OS << "grainsize(";
1825   Node->getGrainsize()->printPretty(OS, nullptr, Policy, 0);
1826   OS << ")";
1827 }
1828 
1829 void OMPClausePrinter::VisitOMPNumTasksClause(OMPNumTasksClause *Node) {
1830   OS << "num_tasks(";
1831   Node->getNumTasks()->printPretty(OS, nullptr, Policy, 0);
1832   OS << ")";
1833 }
1834 
1835 void OMPClausePrinter::VisitOMPHintClause(OMPHintClause *Node) {
1836   OS << "hint(";
1837   Node->getHint()->printPretty(OS, nullptr, Policy, 0);
1838   OS << ")";
1839 }
1840 
1841 void OMPClausePrinter::VisitOMPInitClause(OMPInitClause *Node) {
1842   OS << "init(";
1843   bool First = true;
1844   for (const Expr *E : Node->prefs()) {
1845     if (First)
1846       OS << "prefer_type(";
1847     else
1848       OS << ",";
1849     E->printPretty(OS, nullptr, Policy);
1850     First = false;
1851   }
1852   if (!First)
1853     OS << "), ";
1854   if (Node->getIsTarget())
1855     OS << "target";
1856   if (Node->getIsTargetSync()) {
1857     if (Node->getIsTarget())
1858       OS << ", ";
1859     OS << "targetsync";
1860   }
1861   OS << " : ";
1862   Node->getInteropVar()->printPretty(OS, nullptr, Policy);
1863   OS << ")";
1864 }
1865 
1866 void OMPClausePrinter::VisitOMPUseClause(OMPUseClause *Node) {
1867   OS << "use(";
1868   Node->getInteropVar()->printPretty(OS, nullptr, Policy);
1869   OS << ")";
1870 }
1871 
1872 void OMPClausePrinter::VisitOMPDestroyClause(OMPDestroyClause *Node) {
1873   OS << "destroy";
1874   if (Expr *E = Node->getInteropVar()) {
1875     OS << "(";
1876     E->printPretty(OS, nullptr, Policy);
1877     OS << ")";
1878   }
1879 }
1880 
1881 void OMPClausePrinter::VisitOMPNovariantsClause(OMPNovariantsClause *Node) {
1882   OS << "novariants";
1883   if (Expr *E = Node->getCondition()) {
1884     OS << "(";
1885     E->printPretty(OS, nullptr, Policy, 0);
1886     OS << ")";
1887   }
1888 }
1889 
1890 void OMPClausePrinter::VisitOMPNocontextClause(OMPNocontextClause *Node) {
1891   OS << "nocontext";
1892   if (Expr *E = Node->getCondition()) {
1893     OS << "(";
1894     E->printPretty(OS, nullptr, Policy, 0);
1895     OS << ")";
1896   }
1897 }
1898 
1899 template<typename T>
1900 void OMPClausePrinter::VisitOMPClauseList(T *Node, char StartSym) {
1901   for (typename T::varlist_iterator I = Node->varlist_begin(),
1902                                     E = Node->varlist_end();
1903        I != E; ++I) {
1904     assert(*I && "Expected non-null Stmt");
1905     OS << (I == Node->varlist_begin() ? StartSym : ',');
1906     if (auto *DRE = dyn_cast<DeclRefExpr>(*I)) {
1907       if (isa<OMPCapturedExprDecl>(DRE->getDecl()))
1908         DRE->printPretty(OS, nullptr, Policy, 0);
1909       else
1910         DRE->getDecl()->printQualifiedName(OS);
1911     } else
1912       (*I)->printPretty(OS, nullptr, Policy, 0);
1913   }
1914 }
1915 
1916 void OMPClausePrinter::VisitOMPAllocateClause(OMPAllocateClause *Node) {
1917   if (Node->varlist_empty())
1918     return;
1919   OS << "allocate";
1920   if (Expr *Allocator = Node->getAllocator()) {
1921     OS << "(";
1922     Allocator->printPretty(OS, nullptr, Policy, 0);
1923     OS << ":";
1924     VisitOMPClauseList(Node, ' ');
1925   } else {
1926     VisitOMPClauseList(Node, '(');
1927   }
1928   OS << ")";
1929 }
1930 
1931 void OMPClausePrinter::VisitOMPPrivateClause(OMPPrivateClause *Node) {
1932   if (!Node->varlist_empty()) {
1933     OS << "private";
1934     VisitOMPClauseList(Node, '(');
1935     OS << ")";
1936   }
1937 }
1938 
1939 void OMPClausePrinter::VisitOMPFirstprivateClause(OMPFirstprivateClause *Node) {
1940   if (!Node->varlist_empty()) {
1941     OS << "firstprivate";
1942     VisitOMPClauseList(Node, '(');
1943     OS << ")";
1944   }
1945 }
1946 
1947 void OMPClausePrinter::VisitOMPLastprivateClause(OMPLastprivateClause *Node) {
1948   if (!Node->varlist_empty()) {
1949     OS << "lastprivate";
1950     OpenMPLastprivateModifier LPKind = Node->getKind();
1951     if (LPKind != OMPC_LASTPRIVATE_unknown) {
1952       OS << "("
1953          << getOpenMPSimpleClauseTypeName(OMPC_lastprivate, Node->getKind())
1954          << ":";
1955     }
1956     VisitOMPClauseList(Node, LPKind == OMPC_LASTPRIVATE_unknown ? '(' : ' ');
1957     OS << ")";
1958   }
1959 }
1960 
1961 void OMPClausePrinter::VisitOMPSharedClause(OMPSharedClause *Node) {
1962   if (!Node->varlist_empty()) {
1963     OS << "shared";
1964     VisitOMPClauseList(Node, '(');
1965     OS << ")";
1966   }
1967 }
1968 
1969 void OMPClausePrinter::VisitOMPReductionClause(OMPReductionClause *Node) {
1970   if (!Node->varlist_empty()) {
1971     OS << "reduction(";
1972     if (Node->getModifierLoc().isValid())
1973       OS << getOpenMPSimpleClauseTypeName(OMPC_reduction, Node->getModifier())
1974          << ", ";
1975     NestedNameSpecifier *QualifierLoc =
1976         Node->getQualifierLoc().getNestedNameSpecifier();
1977     OverloadedOperatorKind OOK =
1978         Node->getNameInfo().getName().getCXXOverloadedOperator();
1979     if (QualifierLoc == nullptr && OOK != OO_None) {
1980       // Print reduction identifier in C format
1981       OS << getOperatorSpelling(OOK);
1982     } else {
1983       // Use C++ format
1984       if (QualifierLoc != nullptr)
1985         QualifierLoc->print(OS, Policy);
1986       OS << Node->getNameInfo();
1987     }
1988     OS << ":";
1989     VisitOMPClauseList(Node, ' ');
1990     OS << ")";
1991   }
1992 }
1993 
1994 void OMPClausePrinter::VisitOMPTaskReductionClause(
1995     OMPTaskReductionClause *Node) {
1996   if (!Node->varlist_empty()) {
1997     OS << "task_reduction(";
1998     NestedNameSpecifier *QualifierLoc =
1999         Node->getQualifierLoc().getNestedNameSpecifier();
2000     OverloadedOperatorKind OOK =
2001         Node->getNameInfo().getName().getCXXOverloadedOperator();
2002     if (QualifierLoc == nullptr && OOK != OO_None) {
2003       // Print reduction identifier in C format
2004       OS << getOperatorSpelling(OOK);
2005     } else {
2006       // Use C++ format
2007       if (QualifierLoc != nullptr)
2008         QualifierLoc->print(OS, Policy);
2009       OS << Node->getNameInfo();
2010     }
2011     OS << ":";
2012     VisitOMPClauseList(Node, ' ');
2013     OS << ")";
2014   }
2015 }
2016 
2017 void OMPClausePrinter::VisitOMPInReductionClause(OMPInReductionClause *Node) {
2018   if (!Node->varlist_empty()) {
2019     OS << "in_reduction(";
2020     NestedNameSpecifier *QualifierLoc =
2021         Node->getQualifierLoc().getNestedNameSpecifier();
2022     OverloadedOperatorKind OOK =
2023         Node->getNameInfo().getName().getCXXOverloadedOperator();
2024     if (QualifierLoc == nullptr && OOK != OO_None) {
2025       // Print reduction identifier in C format
2026       OS << getOperatorSpelling(OOK);
2027     } else {
2028       // Use C++ format
2029       if (QualifierLoc != nullptr)
2030         QualifierLoc->print(OS, Policy);
2031       OS << Node->getNameInfo();
2032     }
2033     OS << ":";
2034     VisitOMPClauseList(Node, ' ');
2035     OS << ")";
2036   }
2037 }
2038 
2039 void OMPClausePrinter::VisitOMPLinearClause(OMPLinearClause *Node) {
2040   if (!Node->varlist_empty()) {
2041     OS << "linear";
2042     if (Node->getModifierLoc().isValid()) {
2043       OS << '('
2044          << getOpenMPSimpleClauseTypeName(OMPC_linear, Node->getModifier());
2045     }
2046     VisitOMPClauseList(Node, '(');
2047     if (Node->getModifierLoc().isValid())
2048       OS << ')';
2049     if (Node->getStep() != nullptr) {
2050       OS << ": ";
2051       Node->getStep()->printPretty(OS, nullptr, Policy, 0);
2052     }
2053     OS << ")";
2054   }
2055 }
2056 
2057 void OMPClausePrinter::VisitOMPAlignedClause(OMPAlignedClause *Node) {
2058   if (!Node->varlist_empty()) {
2059     OS << "aligned";
2060     VisitOMPClauseList(Node, '(');
2061     if (Node->getAlignment() != nullptr) {
2062       OS << ": ";
2063       Node->getAlignment()->printPretty(OS, nullptr, Policy, 0);
2064     }
2065     OS << ")";
2066   }
2067 }
2068 
2069 void OMPClausePrinter::VisitOMPCopyinClause(OMPCopyinClause *Node) {
2070   if (!Node->varlist_empty()) {
2071     OS << "copyin";
2072     VisitOMPClauseList(Node, '(');
2073     OS << ")";
2074   }
2075 }
2076 
2077 void OMPClausePrinter::VisitOMPCopyprivateClause(OMPCopyprivateClause *Node) {
2078   if (!Node->varlist_empty()) {
2079     OS << "copyprivate";
2080     VisitOMPClauseList(Node, '(');
2081     OS << ")";
2082   }
2083 }
2084 
2085 void OMPClausePrinter::VisitOMPFlushClause(OMPFlushClause *Node) {
2086   if (!Node->varlist_empty()) {
2087     VisitOMPClauseList(Node, '(');
2088     OS << ")";
2089   }
2090 }
2091 
2092 void OMPClausePrinter::VisitOMPDepobjClause(OMPDepobjClause *Node) {
2093   OS << "(";
2094   Node->getDepobj()->printPretty(OS, nullptr, Policy, 0);
2095   OS << ")";
2096 }
2097 
2098 void OMPClausePrinter::VisitOMPDependClause(OMPDependClause *Node) {
2099   OS << "depend(";
2100   if (Expr *DepModifier = Node->getModifier()) {
2101     DepModifier->printPretty(OS, nullptr, Policy);
2102     OS << ", ";
2103   }
2104   OS << getOpenMPSimpleClauseTypeName(Node->getClauseKind(),
2105                                       Node->getDependencyKind());
2106   if (!Node->varlist_empty()) {
2107     OS << " :";
2108     VisitOMPClauseList(Node, ' ');
2109   }
2110   OS << ")";
2111 }
2112 
2113 template <typename T>
2114 static void PrintMapper(raw_ostream &OS, T *Node,
2115                         const PrintingPolicy &Policy) {
2116   OS << '(';
2117   NestedNameSpecifier *MapperNNS =
2118       Node->getMapperQualifierLoc().getNestedNameSpecifier();
2119   if (MapperNNS)
2120     MapperNNS->print(OS, Policy);
2121   OS << Node->getMapperIdInfo() << ')';
2122 }
2123 
2124 void OMPClausePrinter::VisitOMPMapClause(OMPMapClause *Node) {
2125   if (!Node->varlist_empty()) {
2126     OS << "map(";
2127     if (Node->getMapType() != OMPC_MAP_unknown) {
2128       for (unsigned I = 0; I < NumberOfOMPMapClauseModifiers; ++I) {
2129         if (Node->getMapTypeModifier(I) != OMPC_MAP_MODIFIER_unknown) {
2130           OS << getOpenMPSimpleClauseTypeName(OMPC_map,
2131                                               Node->getMapTypeModifier(I));
2132           if (Node->getMapTypeModifier(I) == OMPC_MAP_MODIFIER_mapper)
2133             PrintMapper(OS, Node, Policy);
2134           OS << ',';
2135         }
2136       }
2137       OS << getOpenMPSimpleClauseTypeName(OMPC_map, Node->getMapType());
2138       OS << ':';
2139     }
2140     VisitOMPClauseList(Node, ' ');
2141     OS << ")";
2142   }
2143 }
2144 
2145 template <typename T> void OMPClausePrinter::VisitOMPMotionClause(T *Node) {
2146   if (Node->varlist_empty())
2147     return;
2148   OS << getOpenMPClauseName(Node->getClauseKind());
2149   unsigned ModifierCount = 0;
2150   for (unsigned I = 0; I < NumberOfOMPMotionModifiers; ++I) {
2151     if (Node->getMotionModifier(I) != OMPC_MOTION_MODIFIER_unknown)
2152       ++ModifierCount;
2153   }
2154   if (ModifierCount) {
2155     OS << '(';
2156     for (unsigned I = 0; I < NumberOfOMPMotionModifiers; ++I) {
2157       if (Node->getMotionModifier(I) != OMPC_MOTION_MODIFIER_unknown) {
2158         OS << getOpenMPSimpleClauseTypeName(Node->getClauseKind(),
2159                                             Node->getMotionModifier(I));
2160         if (Node->getMotionModifier(I) == OMPC_MOTION_MODIFIER_mapper)
2161           PrintMapper(OS, Node, Policy);
2162         if (I < ModifierCount - 1)
2163           OS << ", ";
2164       }
2165     }
2166     OS << ':';
2167     VisitOMPClauseList(Node, ' ');
2168   } else {
2169     VisitOMPClauseList(Node, '(');
2170   }
2171   OS << ")";
2172 }
2173 
2174 void OMPClausePrinter::VisitOMPToClause(OMPToClause *Node) {
2175   VisitOMPMotionClause(Node);
2176 }
2177 
2178 void OMPClausePrinter::VisitOMPFromClause(OMPFromClause *Node) {
2179   VisitOMPMotionClause(Node);
2180 }
2181 
2182 void OMPClausePrinter::VisitOMPDistScheduleClause(OMPDistScheduleClause *Node) {
2183   OS << "dist_schedule(" << getOpenMPSimpleClauseTypeName(
2184                            OMPC_dist_schedule, Node->getDistScheduleKind());
2185   if (auto *E = Node->getChunkSize()) {
2186     OS << ", ";
2187     E->printPretty(OS, nullptr, Policy);
2188   }
2189   OS << ")";
2190 }
2191 
2192 void OMPClausePrinter::VisitOMPDefaultmapClause(OMPDefaultmapClause *Node) {
2193   OS << "defaultmap(";
2194   OS << getOpenMPSimpleClauseTypeName(OMPC_defaultmap,
2195                                       Node->getDefaultmapModifier());
2196   if (Node->getDefaultmapKind() != OMPC_DEFAULTMAP_unknown) {
2197     OS << ": ";
2198     OS << getOpenMPSimpleClauseTypeName(OMPC_defaultmap,
2199                                         Node->getDefaultmapKind());
2200   }
2201   OS << ")";
2202 }
2203 
2204 void OMPClausePrinter::VisitOMPUseDevicePtrClause(OMPUseDevicePtrClause *Node) {
2205   if (!Node->varlist_empty()) {
2206     OS << "use_device_ptr";
2207     VisitOMPClauseList(Node, '(');
2208     OS << ")";
2209   }
2210 }
2211 
2212 void OMPClausePrinter::VisitOMPUseDeviceAddrClause(
2213     OMPUseDeviceAddrClause *Node) {
2214   if (!Node->varlist_empty()) {
2215     OS << "use_device_addr";
2216     VisitOMPClauseList(Node, '(');
2217     OS << ")";
2218   }
2219 }
2220 
2221 void OMPClausePrinter::VisitOMPIsDevicePtrClause(OMPIsDevicePtrClause *Node) {
2222   if (!Node->varlist_empty()) {
2223     OS << "is_device_ptr";
2224     VisitOMPClauseList(Node, '(');
2225     OS << ")";
2226   }
2227 }
2228 
2229 void OMPClausePrinter::VisitOMPNontemporalClause(OMPNontemporalClause *Node) {
2230   if (!Node->varlist_empty()) {
2231     OS << "nontemporal";
2232     VisitOMPClauseList(Node, '(');
2233     OS << ")";
2234   }
2235 }
2236 
2237 void OMPClausePrinter::VisitOMPOrderClause(OMPOrderClause *Node) {
2238   OS << "order(" << getOpenMPSimpleClauseTypeName(OMPC_order, Node->getKind())
2239      << ")";
2240 }
2241 
2242 void OMPClausePrinter::VisitOMPInclusiveClause(OMPInclusiveClause *Node) {
2243   if (!Node->varlist_empty()) {
2244     OS << "inclusive";
2245     VisitOMPClauseList(Node, '(');
2246     OS << ")";
2247   }
2248 }
2249 
2250 void OMPClausePrinter::VisitOMPExclusiveClause(OMPExclusiveClause *Node) {
2251   if (!Node->varlist_empty()) {
2252     OS << "exclusive";
2253     VisitOMPClauseList(Node, '(');
2254     OS << ")";
2255   }
2256 }
2257 
2258 void OMPClausePrinter::VisitOMPUsesAllocatorsClause(
2259     OMPUsesAllocatorsClause *Node) {
2260   if (Node->getNumberOfAllocators() == 0)
2261     return;
2262   OS << "uses_allocators(";
2263   for (unsigned I = 0, E = Node->getNumberOfAllocators(); I < E; ++I) {
2264     OMPUsesAllocatorsClause::Data Data = Node->getAllocatorData(I);
2265     Data.Allocator->printPretty(OS, nullptr, Policy);
2266     if (Data.AllocatorTraits) {
2267       OS << "(";
2268       Data.AllocatorTraits->printPretty(OS, nullptr, Policy);
2269       OS << ")";
2270     }
2271     if (I < E - 1)
2272       OS << ",";
2273   }
2274   OS << ")";
2275 }
2276 
2277 void OMPClausePrinter::VisitOMPAffinityClause(OMPAffinityClause *Node) {
2278   if (Node->varlist_empty())
2279     return;
2280   OS << "affinity";
2281   char StartSym = '(';
2282   if (Expr *Modifier = Node->getModifier()) {
2283     OS << "(";
2284     Modifier->printPretty(OS, nullptr, Policy);
2285     OS << " :";
2286     StartSym = ' ';
2287   }
2288   VisitOMPClauseList(Node, StartSym);
2289   OS << ")";
2290 }
2291 
2292 void OMPClausePrinter::VisitOMPFilterClause(OMPFilterClause *Node) {
2293   OS << "filter(";
2294   Node->getThreadID()->printPretty(OS, nullptr, Policy, 0);
2295   OS << ")";
2296 }
2297 
2298 void OMPTraitInfo::getAsVariantMatchInfo(ASTContext &ASTCtx,
2299                                          VariantMatchInfo &VMI) const {
2300   for (const OMPTraitSet &Set : Sets) {
2301     for (const OMPTraitSelector &Selector : Set.Selectors) {
2302 
2303       // User conditions are special as we evaluate the condition here.
2304       if (Selector.Kind == TraitSelector::user_condition) {
2305         assert(Selector.ScoreOrCondition &&
2306                "Ill-formed user condition, expected condition expression!");
2307         assert(Selector.Properties.size() == 1 &&
2308                Selector.Properties.front().Kind ==
2309                    TraitProperty::user_condition_unknown &&
2310                "Ill-formed user condition, expected unknown trait property!");
2311 
2312         if (Optional<APSInt> CondVal =
2313                 Selector.ScoreOrCondition->getIntegerConstantExpr(ASTCtx))
2314           VMI.addTrait(CondVal->isNullValue()
2315                            ? TraitProperty::user_condition_false
2316                            : TraitProperty::user_condition_true,
2317                        "<condition>");
2318         else
2319           VMI.addTrait(TraitProperty::user_condition_false, "<condition>");
2320         continue;
2321       }
2322 
2323       Optional<llvm::APSInt> Score;
2324       llvm::APInt *ScorePtr = nullptr;
2325       if (Selector.ScoreOrCondition) {
2326         if ((Score = Selector.ScoreOrCondition->getIntegerConstantExpr(ASTCtx)))
2327           ScorePtr = &*Score;
2328         else
2329           VMI.addTrait(TraitProperty::user_condition_false,
2330                        "<non-constant-score>");
2331       }
2332 
2333       for (const OMPTraitProperty &Property : Selector.Properties)
2334         VMI.addTrait(Set.Kind, Property.Kind, Property.RawString, ScorePtr);
2335 
2336       if (Set.Kind != TraitSet::construct)
2337         continue;
2338 
2339       // TODO: This might not hold once we implement SIMD properly.
2340       assert(Selector.Properties.size() == 1 &&
2341              Selector.Properties.front().Kind ==
2342                  getOpenMPContextTraitPropertyForSelector(
2343                      Selector.Kind) &&
2344              "Ill-formed construct selector!");
2345 
2346       VMI.ConstructTraits.push_back(Selector.Properties.front().Kind);
2347     }
2348   }
2349 }
2350 
2351 void OMPTraitInfo::print(llvm::raw_ostream &OS,
2352                          const PrintingPolicy &Policy) const {
2353   bool FirstSet = true;
2354   for (const OMPTraitSet &Set : Sets) {
2355     if (!FirstSet)
2356       OS << ", ";
2357     FirstSet = false;
2358     OS << getOpenMPContextTraitSetName(Set.Kind) << "={";
2359 
2360     bool FirstSelector = true;
2361     for (const OMPTraitSelector &Selector : Set.Selectors) {
2362       if (!FirstSelector)
2363         OS << ", ";
2364       FirstSelector = false;
2365       OS << getOpenMPContextTraitSelectorName(Selector.Kind);
2366 
2367       bool AllowsTraitScore = false;
2368       bool RequiresProperty = false;
2369       isValidTraitSelectorForTraitSet(
2370           Selector.Kind, Set.Kind, AllowsTraitScore, RequiresProperty);
2371 
2372       if (!RequiresProperty)
2373         continue;
2374 
2375       OS << "(";
2376       if (Selector.Kind == TraitSelector::user_condition) {
2377         if (Selector.ScoreOrCondition)
2378           Selector.ScoreOrCondition->printPretty(OS, nullptr, Policy);
2379         else
2380           OS << "...";
2381       } else {
2382 
2383         if (Selector.ScoreOrCondition) {
2384           OS << "score(";
2385           Selector.ScoreOrCondition->printPretty(OS, nullptr, Policy);
2386           OS << "): ";
2387         }
2388 
2389         bool FirstProperty = true;
2390         for (const OMPTraitProperty &Property : Selector.Properties) {
2391           if (!FirstProperty)
2392             OS << ", ";
2393           FirstProperty = false;
2394           OS << getOpenMPContextTraitPropertyName(Property.Kind,
2395                                                   Property.RawString);
2396         }
2397       }
2398       OS << ")";
2399     }
2400     OS << "}";
2401   }
2402 }
2403 
2404 std::string OMPTraitInfo::getMangledName() const {
2405   std::string MangledName;
2406   llvm::raw_string_ostream OS(MangledName);
2407   for (const OMPTraitSet &Set : Sets) {
2408     OS << '$' << 'S' << unsigned(Set.Kind);
2409     for (const OMPTraitSelector &Selector : Set.Selectors) {
2410 
2411       bool AllowsTraitScore = false;
2412       bool RequiresProperty = false;
2413       isValidTraitSelectorForTraitSet(
2414           Selector.Kind, Set.Kind, AllowsTraitScore, RequiresProperty);
2415       OS << '$' << 's' << unsigned(Selector.Kind);
2416 
2417       if (!RequiresProperty ||
2418           Selector.Kind == TraitSelector::user_condition)
2419         continue;
2420 
2421       for (const OMPTraitProperty &Property : Selector.Properties)
2422         OS << '$' << 'P'
2423            << getOpenMPContextTraitPropertyName(Property.Kind,
2424                                                 Property.RawString);
2425     }
2426   }
2427   return OS.str();
2428 }
2429 
2430 OMPTraitInfo::OMPTraitInfo(StringRef MangledName) {
2431   unsigned long U;
2432   do {
2433     if (!MangledName.consume_front("$S"))
2434       break;
2435     if (MangledName.consumeInteger(10, U))
2436       break;
2437     Sets.push_back(OMPTraitSet());
2438     OMPTraitSet &Set = Sets.back();
2439     Set.Kind = TraitSet(U);
2440     do {
2441       if (!MangledName.consume_front("$s"))
2442         break;
2443       if (MangledName.consumeInteger(10, U))
2444         break;
2445       Set.Selectors.push_back(OMPTraitSelector());
2446       OMPTraitSelector &Selector = Set.Selectors.back();
2447       Selector.Kind = TraitSelector(U);
2448       do {
2449         if (!MangledName.consume_front("$P"))
2450           break;
2451         Selector.Properties.push_back(OMPTraitProperty());
2452         OMPTraitProperty &Property = Selector.Properties.back();
2453         std::pair<StringRef, StringRef> PropRestPair = MangledName.split('$');
2454         Property.RawString = PropRestPair.first;
2455         Property.Kind = getOpenMPContextTraitPropertyKind(
2456             Set.Kind, Selector.Kind, PropRestPair.first);
2457         MangledName = MangledName.drop_front(PropRestPair.first.size());
2458       } while (true);
2459     } while (true);
2460   } while (true);
2461 }
2462 
2463 llvm::raw_ostream &clang::operator<<(llvm::raw_ostream &OS,
2464                                      const OMPTraitInfo &TI) {
2465   LangOptions LO;
2466   PrintingPolicy Policy(LO);
2467   TI.print(OS, Policy);
2468   return OS;
2469 }
2470 llvm::raw_ostream &clang::operator<<(llvm::raw_ostream &OS,
2471                                      const OMPTraitInfo *TI) {
2472   return TI ? OS << *TI : OS;
2473 }
2474 
2475 TargetOMPContext::TargetOMPContext(
2476     ASTContext &ASTCtx, std::function<void(StringRef)> &&DiagUnknownTrait,
2477     const FunctionDecl *CurrentFunctionDecl)
2478     : OMPContext(ASTCtx.getLangOpts().OpenMPIsDevice,
2479                  ASTCtx.getTargetInfo().getTriple()),
2480       FeatureValidityCheck([&](StringRef FeatureName) {
2481         return ASTCtx.getTargetInfo().isValidFeatureName(FeatureName);
2482       }),
2483       DiagUnknownTrait(std::move(DiagUnknownTrait)) {
2484   ASTCtx.getFunctionFeatureMap(FeatureMap, CurrentFunctionDecl);
2485 }
2486 
2487 bool TargetOMPContext::matchesISATrait(StringRef RawString) const {
2488   auto It = FeatureMap.find(RawString);
2489   if (It != FeatureMap.end())
2490     return It->second;
2491   if (!FeatureValidityCheck(RawString))
2492     DiagUnknownTrait(RawString);
2493   return false;
2494 }
2495