clang  7.0.0svn
SemaOpenMP.cpp
Go to the documentation of this file.
1 //===--- SemaOpenMP.cpp - Semantic Analysis for OpenMP constructs ---------===//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 /// \file
10 /// This file implements semantic analysis for OpenMP directives and
11 /// clauses.
12 ///
13 //===----------------------------------------------------------------------===//
14 
15 #include "TreeTransform.h"
16 #include "clang/AST/ASTContext.h"
19 #include "clang/AST/Decl.h"
20 #include "clang/AST/DeclCXX.h"
21 #include "clang/AST/DeclOpenMP.h"
22 #include "clang/AST/StmtCXX.h"
23 #include "clang/AST/StmtOpenMP.h"
24 #include "clang/AST/StmtVisitor.h"
27 #include "clang/Sema/Lookup.h"
28 #include "clang/Sema/Scope.h"
29 #include "clang/Sema/ScopeInfo.h"
31 #include "llvm/ADT/PointerEmbeddedInt.h"
32 using namespace clang;
33 
34 //===----------------------------------------------------------------------===//
35 // Stack of data-sharing attributes for variables
36 //===----------------------------------------------------------------------===//
37 
39  Sema &SemaRef, Expr *E,
41  OpenMPClauseKind CKind, bool NoDiagnose);
42 
43 namespace {
44 /// Default data sharing attributes, which can be applied to directive.
46  DSA_unspecified = 0, /// Data sharing attribute not specified.
47  DSA_none = 1 << 0, /// Default data sharing attribute 'none'.
48  DSA_shared = 1 << 1, /// Default data sharing attribute 'shared'.
49 };
50 
51 /// Attributes of the defaultmap clause.
53  DMA_unspecified, /// Default mapping is not specified.
54  DMA_tofrom_scalar, /// Default mapping is 'tofrom:scalar'.
55 };
56 
57 /// Stack for tracking declarations used in OpenMP directives and
58 /// clauses and their data-sharing attributes.
59 class DSAStackTy {
60 public:
61  struct DSAVarData {
64  const Expr *RefExpr = nullptr;
65  DeclRefExpr *PrivateCopy = nullptr;
66  SourceLocation ImplicitDSALoc;
67  DSAVarData() = default;
68  DSAVarData(OpenMPDirectiveKind DKind, OpenMPClauseKind CKind,
69  const Expr *RefExpr, DeclRefExpr *PrivateCopy,
70  SourceLocation ImplicitDSALoc)
71  : DKind(DKind), CKind(CKind), RefExpr(RefExpr),
72  PrivateCopy(PrivateCopy), ImplicitDSALoc(ImplicitDSALoc) {}
73  };
74  using OperatorOffsetTy =
76 
77 private:
78  struct DSAInfo {
79  OpenMPClauseKind Attributes = OMPC_unknown;
80  /// Pointer to a reference expression and a flag which shows that the
81  /// variable is marked as lastprivate(true) or not (false).
82  llvm::PointerIntPair<const Expr *, 1, bool> RefExpr;
83  DeclRefExpr *PrivateCopy = nullptr;
84  };
85  using DeclSAMapTy = llvm::SmallDenseMap<const ValueDecl *, DSAInfo, 8>;
86  using AlignedMapTy = llvm::SmallDenseMap<const ValueDecl *, const Expr *, 8>;
87  using LCDeclInfo = std::pair<unsigned, VarDecl *>;
88  using LoopControlVariablesMapTy =
89  llvm::SmallDenseMap<const ValueDecl *, LCDeclInfo, 8>;
90  /// Struct that associates a component with the clause kind where they are
91  /// found.
92  struct MappedExprComponentTy {
95  };
96  using MappedExprComponentsTy =
97  llvm::DenseMap<const ValueDecl *, MappedExprComponentTy>;
98  using CriticalsWithHintsTy =
99  llvm::StringMap<std::pair<const OMPCriticalDirective *, llvm::APSInt>>;
100  using DoacrossDependMapTy =
101  llvm::DenseMap<OMPDependClause *, OperatorOffsetTy>;
102  struct ReductionData {
103  using BOKPtrType = llvm::PointerEmbeddedInt<BinaryOperatorKind, 16>;
104  SourceRange ReductionRange;
105  llvm::PointerUnion<const Expr *, BOKPtrType> ReductionOp;
106  ReductionData() = default;
107  void set(BinaryOperatorKind BO, SourceRange RR) {
108  ReductionRange = RR;
109  ReductionOp = BO;
110  }
111  void set(const Expr *RefExpr, SourceRange RR) {
112  ReductionRange = RR;
113  ReductionOp = RefExpr;
114  }
115  };
116  using DeclReductionMapTy =
117  llvm::SmallDenseMap<const ValueDecl *, ReductionData, 4>;
118 
119  struct SharingMapTy {
120  DeclSAMapTy SharingMap;
121  DeclReductionMapTy ReductionMap;
122  AlignedMapTy AlignedMap;
123  MappedExprComponentsTy MappedExprComponents;
124  LoopControlVariablesMapTy LCVMap;
125  DefaultDataSharingAttributes DefaultAttr = DSA_unspecified;
126  SourceLocation DefaultAttrLoc;
127  DefaultMapAttributes DefaultMapAttr = DMA_unspecified;
128  SourceLocation DefaultMapAttrLoc;
130  DeclarationNameInfo DirectiveName;
131  Scope *CurScope = nullptr;
132  SourceLocation ConstructLoc;
133  /// Set of 'depend' clauses with 'sink|source' dependence kind. Required to
134  /// get the data (loop counters etc.) about enclosing loop-based construct.
135  /// This data is required during codegen.
136  DoacrossDependMapTy DoacrossDepends;
137  /// first argument (Expr *) contains optional argument of the
138  /// 'ordered' clause, the second one is true if the regions has 'ordered'
139  /// clause, false otherwise.
140  llvm::PointerIntPair<const Expr *, 1, bool> OrderedRegion;
141  bool NowaitRegion = false;
142  bool CancelRegion = false;
143  unsigned AssociatedLoops = 1;
144  SourceLocation InnerTeamsRegionLoc;
145  /// Reference to the taskgroup task_reduction reference expression.
146  Expr *TaskgroupReductionRef = nullptr;
147  SharingMapTy(OpenMPDirectiveKind DKind, DeclarationNameInfo Name,
148  Scope *CurScope, SourceLocation Loc)
149  : Directive(DKind), DirectiveName(Name), CurScope(CurScope),
150  ConstructLoc(Loc) {}
151  SharingMapTy() = default;
152  };
153 
154  using StackTy = SmallVector<SharingMapTy, 4>;
155 
156  /// Stack of used declaration and their data-sharing attributes.
157  DeclSAMapTy Threadprivates;
158  const FunctionScopeInfo *CurrentNonCapturingFunctionScope = nullptr;
160  /// true, if check for DSA must be from parent directive, false, if
161  /// from current directive.
162  OpenMPClauseKind ClauseKindMode = OMPC_unknown;
163  Sema &SemaRef;
164  bool ForceCapturing = false;
165  CriticalsWithHintsTy Criticals;
166 
167  using iterator = StackTy::const_reverse_iterator;
168 
169  DSAVarData getDSA(iterator &Iter, ValueDecl *D) const;
170 
171  /// Checks if the variable is a local for OpenMP region.
172  bool isOpenMPLocal(VarDecl *D, iterator Iter) const;
173 
174  bool isStackEmpty() const {
175  return Stack.empty() ||
176  Stack.back().second != CurrentNonCapturingFunctionScope ||
177  Stack.back().first.empty();
178  }
179 
180 public:
181  explicit DSAStackTy(Sema &S) : SemaRef(S) {}
182 
183  bool isClauseParsingMode() const { return ClauseKindMode != OMPC_unknown; }
184  OpenMPClauseKind getClauseParsingMode() const {
185  assert(isClauseParsingMode() && "Must be in clause parsing mode.");
186  return ClauseKindMode;
187  }
188  void setClauseParsingMode(OpenMPClauseKind K) { ClauseKindMode = K; }
189 
190  bool isForceVarCapturing() const { return ForceCapturing; }
191  void setForceVarCapturing(bool V) { ForceCapturing = V; }
192 
193  void push(OpenMPDirectiveKind DKind, const DeclarationNameInfo &DirName,
194  Scope *CurScope, SourceLocation Loc) {
195  if (Stack.empty() ||
196  Stack.back().second != CurrentNonCapturingFunctionScope)
197  Stack.emplace_back(StackTy(), CurrentNonCapturingFunctionScope);
198  Stack.back().first.emplace_back(DKind, DirName, CurScope, Loc);
199  Stack.back().first.back().DefaultAttrLoc = Loc;
200  }
201 
202  void pop() {
203  assert(!Stack.back().first.empty() &&
204  "Data-sharing attributes stack is empty!");
205  Stack.back().first.pop_back();
206  }
207 
208  /// Start new OpenMP region stack in new non-capturing function.
209  void pushFunction() {
210  const FunctionScopeInfo *CurFnScope = SemaRef.getCurFunction();
211  assert(!isa<CapturingScopeInfo>(CurFnScope));
212  CurrentNonCapturingFunctionScope = CurFnScope;
213  }
214  /// Pop region stack for non-capturing function.
215  void popFunction(const FunctionScopeInfo *OldFSI) {
216  if (!Stack.empty() && Stack.back().second == OldFSI) {
217  assert(Stack.back().first.empty());
218  Stack.pop_back();
219  }
220  CurrentNonCapturingFunctionScope = nullptr;
221  for (const FunctionScopeInfo *FSI : llvm::reverse(SemaRef.FunctionScopes)) {
222  if (!isa<CapturingScopeInfo>(FSI)) {
223  CurrentNonCapturingFunctionScope = FSI;
224  break;
225  }
226  }
227  }
228 
229  void addCriticalWithHint(const OMPCriticalDirective *D, llvm::APSInt Hint) {
230  Criticals.try_emplace(D->getDirectiveName().getAsString(), D, Hint);
231  }
232  const std::pair<const OMPCriticalDirective *, llvm::APSInt>
233  getCriticalWithHint(const DeclarationNameInfo &Name) const {
234  auto I = Criticals.find(Name.getAsString());
235  if (I != Criticals.end())
236  return I->second;
237  return std::make_pair(nullptr, llvm::APSInt());
238  }
239  /// If 'aligned' declaration for given variable \a D was not seen yet,
240  /// add it and return NULL; otherwise return previous occurrence's expression
241  /// for diagnostics.
242  const Expr *addUniqueAligned(const ValueDecl *D, const Expr *NewDE);
243 
244  /// Register specified variable as loop control variable.
245  void addLoopControlVariable(const ValueDecl *D, VarDecl *Capture);
246  /// Check if the specified variable is a loop control variable for
247  /// current region.
248  /// \return The index of the loop control variable in the list of associated
249  /// for-loops (from outer to inner).
250  const LCDeclInfo isLoopControlVariable(const ValueDecl *D) const;
251  /// Check if the specified variable is a loop control variable for
252  /// parent region.
253  /// \return The index of the loop control variable in the list of associated
254  /// for-loops (from outer to inner).
255  const LCDeclInfo isParentLoopControlVariable(const ValueDecl *D) const;
256  /// Get the loop control variable for the I-th loop (or nullptr) in
257  /// parent directive.
258  const ValueDecl *getParentLoopControlVariable(unsigned I) const;
259 
260  /// Adds explicit data sharing attribute to the specified declaration.
261  void addDSA(const ValueDecl *D, const Expr *E, OpenMPClauseKind A,
262  DeclRefExpr *PrivateCopy = nullptr);
263 
264  /// Adds additional information for the reduction items with the reduction id
265  /// represented as an operator.
266  void addTaskgroupReductionData(const ValueDecl *D, SourceRange SR,
267  BinaryOperatorKind BOK);
268  /// Adds additional information for the reduction items with the reduction id
269  /// represented as reduction identifier.
270  void addTaskgroupReductionData(const ValueDecl *D, SourceRange SR,
271  const Expr *ReductionRef);
272  /// Returns the location and reduction operation from the innermost parent
273  /// region for the given \p D.
274  const DSAVarData
275  getTopMostTaskgroupReductionData(const ValueDecl *D, SourceRange &SR,
276  BinaryOperatorKind &BOK,
277  Expr *&TaskgroupDescriptor) const;
278  /// Returns the location and reduction operation from the innermost parent
279  /// region for the given \p D.
280  const DSAVarData
281  getTopMostTaskgroupReductionData(const ValueDecl *D, SourceRange &SR,
282  const Expr *&ReductionRef,
283  Expr *&TaskgroupDescriptor) const;
284  /// Return reduction reference expression for the current taskgroup.
285  Expr *getTaskgroupReductionRef() const {
286  assert(Stack.back().first.back().Directive == OMPD_taskgroup &&
287  "taskgroup reference expression requested for non taskgroup "
288  "directive.");
289  return Stack.back().first.back().TaskgroupReductionRef;
290  }
291  /// Checks if the given \p VD declaration is actually a taskgroup reduction
292  /// descriptor variable at the \p Level of OpenMP regions.
293  bool isTaskgroupReductionRef(const ValueDecl *VD, unsigned Level) const {
294  return Stack.back().first[Level].TaskgroupReductionRef &&
295  cast<DeclRefExpr>(Stack.back().first[Level].TaskgroupReductionRef)
296  ->getDecl() == VD;
297  }
298 
299  /// Returns data sharing attributes from top of the stack for the
300  /// specified declaration.
301  const DSAVarData getTopDSA(ValueDecl *D, bool FromParent);
302  /// Returns data-sharing attributes for the specified declaration.
303  const DSAVarData getImplicitDSA(ValueDecl *D, bool FromParent) const;
304  /// Checks if the specified variables has data-sharing attributes which
305  /// match specified \a CPred predicate in any directive which matches \a DPred
306  /// predicate.
307  const DSAVarData
308  hasDSA(ValueDecl *D, const llvm::function_ref<bool(OpenMPClauseKind)> CPred,
309  const llvm::function_ref<bool(OpenMPDirectiveKind)> DPred,
310  bool FromParent) const;
311  /// Checks if the specified variables has data-sharing attributes which
312  /// match specified \a CPred predicate in any innermost directive which
313  /// matches \a DPred predicate.
314  const DSAVarData
315  hasInnermostDSA(ValueDecl *D,
316  const llvm::function_ref<bool(OpenMPClauseKind)> CPred,
317  const llvm::function_ref<bool(OpenMPDirectiveKind)> DPred,
318  bool FromParent) const;
319  /// Checks if the specified variables has explicit data-sharing
320  /// attributes which match specified \a CPred predicate at the specified
321  /// OpenMP region.
322  bool hasExplicitDSA(const ValueDecl *D,
323  const llvm::function_ref<bool(OpenMPClauseKind)> CPred,
324  unsigned Level, bool NotLastprivate = false) const;
325 
326  /// Returns true if the directive at level \Level matches in the
327  /// specified \a DPred predicate.
328  bool hasExplicitDirective(
329  const llvm::function_ref<bool(OpenMPDirectiveKind)> DPred,
330  unsigned Level) const;
331 
332  /// Finds a directive which matches specified \a DPred predicate.
333  bool hasDirective(
334  const llvm::function_ref<bool(
336  DPred,
337  bool FromParent) const;
338 
339  /// Returns currently analyzed directive.
340  OpenMPDirectiveKind getCurrentDirective() const {
341  return isStackEmpty() ? OMPD_unknown : Stack.back().first.back().Directive;
342  }
343  /// Returns directive kind at specified level.
344  OpenMPDirectiveKind getDirective(unsigned Level) const {
345  assert(!isStackEmpty() && "No directive at specified level.");
346  return Stack.back().first[Level].Directive;
347  }
348  /// Returns parent directive.
349  OpenMPDirectiveKind getParentDirective() const {
350  if (isStackEmpty() || Stack.back().first.size() == 1)
351  return OMPD_unknown;
352  return std::next(Stack.back().first.rbegin())->Directive;
353  }
354 
355  /// Set default data sharing attribute to none.
356  void setDefaultDSANone(SourceLocation Loc) {
357  assert(!isStackEmpty());
358  Stack.back().first.back().DefaultAttr = DSA_none;
359  Stack.back().first.back().DefaultAttrLoc = Loc;
360  }
361  /// Set default data sharing attribute to shared.
362  void setDefaultDSAShared(SourceLocation Loc) {
363  assert(!isStackEmpty());
364  Stack.back().first.back().DefaultAttr = DSA_shared;
365  Stack.back().first.back().DefaultAttrLoc = Loc;
366  }
367  /// Set default data mapping attribute to 'tofrom:scalar'.
368  void setDefaultDMAToFromScalar(SourceLocation Loc) {
369  assert(!isStackEmpty());
370  Stack.back().first.back().DefaultMapAttr = DMA_tofrom_scalar;
371  Stack.back().first.back().DefaultMapAttrLoc = Loc;
372  }
373 
374  DefaultDataSharingAttributes getDefaultDSA() const {
375  return isStackEmpty() ? DSA_unspecified
376  : Stack.back().first.back().DefaultAttr;
377  }
378  SourceLocation getDefaultDSALocation() const {
379  return isStackEmpty() ? SourceLocation()
380  : Stack.back().first.back().DefaultAttrLoc;
381  }
382  DefaultMapAttributes getDefaultDMA() const {
383  return isStackEmpty() ? DMA_unspecified
384  : Stack.back().first.back().DefaultMapAttr;
385  }
386  DefaultMapAttributes getDefaultDMAAtLevel(unsigned Level) const {
387  return Stack.back().first[Level].DefaultMapAttr;
388  }
389  SourceLocation getDefaultDMALocation() const {
390  return isStackEmpty() ? SourceLocation()
391  : Stack.back().first.back().DefaultMapAttrLoc;
392  }
393 
394  /// Checks if the specified variable is a threadprivate.
395  bool isThreadPrivate(VarDecl *D) {
396  const DSAVarData DVar = getTopDSA(D, false);
397  return isOpenMPThreadPrivate(DVar.CKind);
398  }
399 
400  /// Marks current region as ordered (it has an 'ordered' clause).
401  void setOrderedRegion(bool IsOrdered, const Expr *Param) {
402  assert(!isStackEmpty());
403  Stack.back().first.back().OrderedRegion.setInt(IsOrdered);
404  Stack.back().first.back().OrderedRegion.setPointer(Param);
405  }
406  /// Returns true, if parent region is ordered (has associated
407  /// 'ordered' clause), false - otherwise.
408  bool isParentOrderedRegion() const {
409  if (isStackEmpty() || Stack.back().first.size() == 1)
410  return false;
411  return std::next(Stack.back().first.rbegin())->OrderedRegion.getInt();
412  }
413  /// Returns optional parameter for the ordered region.
414  const Expr *getParentOrderedRegionParam() const {
415  if (isStackEmpty() || Stack.back().first.size() == 1)
416  return nullptr;
417  return std::next(Stack.back().first.rbegin())->OrderedRegion.getPointer();
418  }
419  /// Marks current region as nowait (it has a 'nowait' clause).
420  void setNowaitRegion(bool IsNowait = true) {
421  assert(!isStackEmpty());
422  Stack.back().first.back().NowaitRegion = IsNowait;
423  }
424  /// Returns true, if parent region is nowait (has associated
425  /// 'nowait' clause), false - otherwise.
426  bool isParentNowaitRegion() const {
427  if (isStackEmpty() || Stack.back().first.size() == 1)
428  return false;
429  return std::next(Stack.back().first.rbegin())->NowaitRegion;
430  }
431  /// Marks parent region as cancel region.
432  void setParentCancelRegion(bool Cancel = true) {
433  if (!isStackEmpty() && Stack.back().first.size() > 1) {
434  auto &StackElemRef = *std::next(Stack.back().first.rbegin());
435  StackElemRef.CancelRegion |= StackElemRef.CancelRegion || Cancel;
436  }
437  }
438  /// Return true if current region has inner cancel construct.
439  bool isCancelRegion() const {
440  return isStackEmpty() ? false : Stack.back().first.back().CancelRegion;
441  }
442 
443  /// Set collapse value for the region.
444  void setAssociatedLoops(unsigned Val) {
445  assert(!isStackEmpty());
446  Stack.back().first.back().AssociatedLoops = Val;
447  }
448  /// Return collapse value for region.
449  unsigned getAssociatedLoops() const {
450  return isStackEmpty() ? 0 : Stack.back().first.back().AssociatedLoops;
451  }
452 
453  /// Marks current target region as one with closely nested teams
454  /// region.
455  void setParentTeamsRegionLoc(SourceLocation TeamsRegionLoc) {
456  if (!isStackEmpty() && Stack.back().first.size() > 1) {
457  std::next(Stack.back().first.rbegin())->InnerTeamsRegionLoc =
458  TeamsRegionLoc;
459  }
460  }
461  /// Returns true, if current region has closely nested teams region.
462  bool hasInnerTeamsRegion() const {
463  return getInnerTeamsRegionLoc().isValid();
464  }
465  /// Returns location of the nested teams region (if any).
466  SourceLocation getInnerTeamsRegionLoc() const {
467  return isStackEmpty() ? SourceLocation()
468  : Stack.back().first.back().InnerTeamsRegionLoc;
469  }
470 
471  Scope *getCurScope() const {
472  return isStackEmpty() ? nullptr : Stack.back().first.back().CurScope;
473  }
474  SourceLocation getConstructLoc() const {
475  return isStackEmpty() ? SourceLocation()
476  : Stack.back().first.back().ConstructLoc;
477  }
478 
479  /// Do the check specified in \a Check to all component lists and return true
480  /// if any issue is found.
481  bool checkMappableExprComponentListsForDecl(
482  const ValueDecl *VD, bool CurrentRegionOnly,
483  const llvm::function_ref<
486  Check) const {
487  if (isStackEmpty())
488  return false;
489  auto SI = Stack.back().first.rbegin();
490  auto SE = Stack.back().first.rend();
491 
492  if (SI == SE)
493  return false;
494 
495  if (CurrentRegionOnly)
496  SE = std::next(SI);
497  else
498  std::advance(SI, 1);
499 
500  for (; SI != SE; ++SI) {
501  auto MI = SI->MappedExprComponents.find(VD);
502  if (MI != SI->MappedExprComponents.end())
504  MI->second.Components)
505  if (Check(L, MI->second.Kind))
506  return true;
507  }
508  return false;
509  }
510 
511  /// Do the check specified in \a Check to all component lists at a given level
512  /// and return true if any issue is found.
513  bool checkMappableExprComponentListsForDeclAtLevel(
514  const ValueDecl *VD, unsigned Level,
515  const llvm::function_ref<
518  Check) const {
519  if (isStackEmpty())
520  return false;
521 
522  auto StartI = Stack.back().first.begin();
523  auto EndI = Stack.back().first.end();
524  if (std::distance(StartI, EndI) <= (int)Level)
525  return false;
526  std::advance(StartI, Level);
527 
528  auto MI = StartI->MappedExprComponents.find(VD);
529  if (MI != StartI->MappedExprComponents.end())
531  MI->second.Components)
532  if (Check(L, MI->second.Kind))
533  return true;
534  return false;
535  }
536 
537  /// Create a new mappable expression component list associated with a given
538  /// declaration and initialize it with the provided list of components.
539  void addMappableExpressionComponents(
540  const ValueDecl *VD,
542  OpenMPClauseKind WhereFoundClauseKind) {
543  assert(!isStackEmpty() &&
544  "Not expecting to retrieve components from a empty stack!");
545  MappedExprComponentTy &MEC =
546  Stack.back().first.back().MappedExprComponents[VD];
547  // Create new entry and append the new components there.
548  MEC.Components.resize(MEC.Components.size() + 1);
549  MEC.Components.back().append(Components.begin(), Components.end());
550  MEC.Kind = WhereFoundClauseKind;
551  }
552 
553  unsigned getNestingLevel() const {
554  assert(!isStackEmpty());
555  return Stack.back().first.size() - 1;
556  }
557  void addDoacrossDependClause(OMPDependClause *C,
558  const OperatorOffsetTy &OpsOffs) {
559  assert(!isStackEmpty() && Stack.back().first.size() > 1);
560  SharingMapTy &StackElem = *std::next(Stack.back().first.rbegin());
561  assert(isOpenMPWorksharingDirective(StackElem.Directive));
562  StackElem.DoacrossDepends.try_emplace(C, OpsOffs);
563  }
564  llvm::iterator_range<DoacrossDependMapTy::const_iterator>
565  getDoacrossDependClauses() const {
566  assert(!isStackEmpty());
567  const SharingMapTy &StackElem = Stack.back().first.back();
568  if (isOpenMPWorksharingDirective(StackElem.Directive)) {
569  const DoacrossDependMapTy &Ref = StackElem.DoacrossDepends;
570  return llvm::make_range(Ref.begin(), Ref.end());
571  }
572  return llvm::make_range(StackElem.DoacrossDepends.end(),
573  StackElem.DoacrossDepends.end());
574  }
575 };
576 bool isParallelOrTaskRegion(OpenMPDirectiveKind DKind) {
577  return isOpenMPParallelDirective(DKind) || isOpenMPTaskingDirective(DKind) ||
578  isOpenMPTeamsDirective(DKind) || DKind == OMPD_unknown;
579 }
580 
581 } // namespace
582 
583 static const Expr *getExprAsWritten(const Expr *E) {
584  if (const auto *ExprTemp = dyn_cast<ExprWithCleanups>(E))
585  E = ExprTemp->getSubExpr();
586 
587  if (const auto *MTE = dyn_cast<MaterializeTemporaryExpr>(E))
588  E = MTE->GetTemporaryExpr();
589 
590  while (const auto *Binder = dyn_cast<CXXBindTemporaryExpr>(E))
591  E = Binder->getSubExpr();
592 
593  if (const auto *ICE = dyn_cast<ImplicitCastExpr>(E))
594  E = ICE->getSubExprAsWritten();
595  return E->IgnoreParens();
596 }
597 
599  return const_cast<Expr *>(getExprAsWritten(const_cast<const Expr *>(E)));
600 }
601 
602 static const ValueDecl *getCanonicalDecl(const ValueDecl *D) {
603  if (const auto *CED = dyn_cast<OMPCapturedExprDecl>(D))
604  if (const auto *ME = dyn_cast<MemberExpr>(getExprAsWritten(CED->getInit())))
605  D = ME->getMemberDecl();
606  const auto *VD = dyn_cast<VarDecl>(D);
607  const auto *FD = dyn_cast<FieldDecl>(D);
608  if (VD != nullptr) {
609  VD = VD->getCanonicalDecl();
610  D = VD;
611  } else {
612  assert(FD);
613  FD = FD->getCanonicalDecl();
614  D = FD;
615  }
616  return D;
617 }
618 
620  return const_cast<ValueDecl *>(
621  getCanonicalDecl(const_cast<const ValueDecl *>(D)));
622 }
623 
624 DSAStackTy::DSAVarData DSAStackTy::getDSA(iterator &Iter,
625  ValueDecl *D) const {
626  D = getCanonicalDecl(D);
627  auto *VD = dyn_cast<VarDecl>(D);
628  const auto *FD = dyn_cast<FieldDecl>(D);
629  DSAVarData DVar;
630  if (isStackEmpty() || Iter == Stack.back().first.rend()) {
631  // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
632  // in a region but not in construct]
633  // File-scope or namespace-scope variables referenced in called routines
634  // in the region are shared unless they appear in a threadprivate
635  // directive.
636  if (VD && !VD->isFunctionOrMethodVarDecl() && !isa<ParmVarDecl>(VD))
637  DVar.CKind = OMPC_shared;
638 
639  // OpenMP [2.9.1.2, Data-sharing Attribute Rules for Variables Referenced
640  // in a region but not in construct]
641  // Variables with static storage duration that are declared in called
642  // routines in the region are shared.
643  if (VD && VD->hasGlobalStorage())
644  DVar.CKind = OMPC_shared;
645 
646  // Non-static data members are shared by default.
647  if (FD)
648  DVar.CKind = OMPC_shared;
649 
650  return DVar;
651  }
652 
653  // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
654  // in a Construct, C/C++, predetermined, p.1]
655  // Variables with automatic storage duration that are declared in a scope
656  // inside the construct are private.
657  if (VD && isOpenMPLocal(VD, Iter) && VD->isLocalVarDecl() &&
658  (VD->getStorageClass() == SC_Auto || VD->getStorageClass() == SC_None)) {
659  DVar.CKind = OMPC_private;
660  return DVar;
661  }
662 
663  DVar.DKind = Iter->Directive;
664  // Explicitly specified attributes and local variables with predetermined
665  // attributes.
666  if (Iter->SharingMap.count(D)) {
667  const DSAInfo &Data = Iter->SharingMap.lookup(D);
668  DVar.RefExpr = Data.RefExpr.getPointer();
669  DVar.PrivateCopy = Data.PrivateCopy;
670  DVar.CKind = Data.Attributes;
671  DVar.ImplicitDSALoc = Iter->DefaultAttrLoc;
672  return DVar;
673  }
674 
675  // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
676  // in a Construct, C/C++, implicitly determined, p.1]
677  // In a parallel or task construct, the data-sharing attributes of these
678  // variables are determined by the default clause, if present.
679  switch (Iter->DefaultAttr) {
680  case DSA_shared:
681  DVar.CKind = OMPC_shared;
682  DVar.ImplicitDSALoc = Iter->DefaultAttrLoc;
683  return DVar;
684  case DSA_none:
685  return DVar;
686  case DSA_unspecified:
687  // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
688  // in a Construct, implicitly determined, p.2]
689  // In a parallel construct, if no default clause is present, these
690  // variables are shared.
691  DVar.ImplicitDSALoc = Iter->DefaultAttrLoc;
692  if (isOpenMPParallelDirective(DVar.DKind) ||
693  isOpenMPTeamsDirective(DVar.DKind)) {
694  DVar.CKind = OMPC_shared;
695  return DVar;
696  }
697 
698  // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
699  // in a Construct, implicitly determined, p.4]
700  // In a task construct, if no default clause is present, a variable that in
701  // the enclosing context is determined to be shared by all implicit tasks
702  // bound to the current team is shared.
703  if (isOpenMPTaskingDirective(DVar.DKind)) {
704  DSAVarData DVarTemp;
705  iterator I = Iter, E = Stack.back().first.rend();
706  do {
707  ++I;
708  // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables
709  // Referenced in a Construct, implicitly determined, p.6]
710  // In a task construct, if no default clause is present, a variable
711  // whose data-sharing attribute is not determined by the rules above is
712  // firstprivate.
713  DVarTemp = getDSA(I, D);
714  if (DVarTemp.CKind != OMPC_shared) {
715  DVar.RefExpr = nullptr;
716  DVar.CKind = OMPC_firstprivate;
717  return DVar;
718  }
719  } while (I != E && !isParallelOrTaskRegion(I->Directive));
720  DVar.CKind =
721  (DVarTemp.CKind == OMPC_unknown) ? OMPC_firstprivate : OMPC_shared;
722  return DVar;
723  }
724  }
725  // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
726  // in a Construct, implicitly determined, p.3]
727  // For constructs other than task, if no default clause is present, these
728  // variables inherit their data-sharing attributes from the enclosing
729  // context.
730  return getDSA(++Iter, D);
731 }
732 
733 const Expr *DSAStackTy::addUniqueAligned(const ValueDecl *D,
734  const Expr *NewDE) {
735  assert(!isStackEmpty() && "Data sharing attributes stack is empty");
736  D = getCanonicalDecl(D);
737  SharingMapTy &StackElem = Stack.back().first.back();
738  auto It = StackElem.AlignedMap.find(D);
739  if (It == StackElem.AlignedMap.end()) {
740  assert(NewDE && "Unexpected nullptr expr to be added into aligned map");
741  StackElem.AlignedMap[D] = NewDE;
742  return nullptr;
743  }
744  assert(It->second && "Unexpected nullptr expr in the aligned map");
745  return It->second;
746 }
747 
748 void DSAStackTy::addLoopControlVariable(const ValueDecl *D, VarDecl *Capture) {
749  assert(!isStackEmpty() && "Data-sharing attributes stack is empty");
750  D = getCanonicalDecl(D);
751  SharingMapTy &StackElem = Stack.back().first.back();
752  StackElem.LCVMap.try_emplace(
753  D, LCDeclInfo(StackElem.LCVMap.size() + 1, Capture));
754 }
755 
756 const DSAStackTy::LCDeclInfo
757 DSAStackTy::isLoopControlVariable(const ValueDecl *D) const {
758  assert(!isStackEmpty() && "Data-sharing attributes stack is empty");
759  D = getCanonicalDecl(D);
760  const SharingMapTy &StackElem = Stack.back().first.back();
761  auto It = StackElem.LCVMap.find(D);
762  if (It != StackElem.LCVMap.end())
763  return It->second;
764  return {0, nullptr};
765 }
766 
767 const DSAStackTy::LCDeclInfo
768 DSAStackTy::isParentLoopControlVariable(const ValueDecl *D) const {
769  assert(!isStackEmpty() && Stack.back().first.size() > 1 &&
770  "Data-sharing attributes stack is empty");
771  D = getCanonicalDecl(D);
772  const SharingMapTy &StackElem = *std::next(Stack.back().first.rbegin());
773  auto It = StackElem.LCVMap.find(D);
774  if (It != StackElem.LCVMap.end())
775  return It->second;
776  return {0, nullptr};
777 }
778 
779 const ValueDecl *DSAStackTy::getParentLoopControlVariable(unsigned I) const {
780  assert(!isStackEmpty() && Stack.back().first.size() > 1 &&
781  "Data-sharing attributes stack is empty");
782  const SharingMapTy &StackElem = *std::next(Stack.back().first.rbegin());
783  if (StackElem.LCVMap.size() < I)
784  return nullptr;
785  for (const auto &Pair : StackElem.LCVMap)
786  if (Pair.second.first == I)
787  return Pair.first;
788  return nullptr;
789 }
790 
791 void DSAStackTy::addDSA(const ValueDecl *D, const Expr *E, OpenMPClauseKind A,
792  DeclRefExpr *PrivateCopy) {
793  D = getCanonicalDecl(D);
794  if (A == OMPC_threadprivate) {
795  DSAInfo &Data = Threadprivates[D];
796  Data.Attributes = A;
797  Data.RefExpr.setPointer(E);
798  Data.PrivateCopy = nullptr;
799  } else {
800  assert(!isStackEmpty() && "Data-sharing attributes stack is empty");
801  DSAInfo &Data = Stack.back().first.back().SharingMap[D];
802  assert(Data.Attributes == OMPC_unknown || (A == Data.Attributes) ||
803  (A == OMPC_firstprivate && Data.Attributes == OMPC_lastprivate) ||
804  (A == OMPC_lastprivate && Data.Attributes == OMPC_firstprivate) ||
805  (isLoopControlVariable(D).first && A == OMPC_private));
806  if (A == OMPC_lastprivate && Data.Attributes == OMPC_firstprivate) {
807  Data.RefExpr.setInt(/*IntVal=*/true);
808  return;
809  }
810  const bool IsLastprivate =
811  A == OMPC_lastprivate || Data.Attributes == OMPC_lastprivate;
812  Data.Attributes = A;
813  Data.RefExpr.setPointerAndInt(E, IsLastprivate);
814  Data.PrivateCopy = PrivateCopy;
815  if (PrivateCopy) {
816  DSAInfo &Data =
817  Stack.back().first.back().SharingMap[PrivateCopy->getDecl()];
818  Data.Attributes = A;
819  Data.RefExpr.setPointerAndInt(PrivateCopy, IsLastprivate);
820  Data.PrivateCopy = nullptr;
821  }
822  }
823 }
824 
825 /// Build a variable declaration for OpenMP loop iteration variable.
827  StringRef Name, const AttrVec *Attrs = nullptr,
828  DeclRefExpr *OrigRef = nullptr) {
829  DeclContext *DC = SemaRef.CurContext;
830  IdentifierInfo *II = &SemaRef.PP.getIdentifierTable().get(Name);
831  TypeSourceInfo *TInfo = SemaRef.Context.getTrivialTypeSourceInfo(Type, Loc);
832  auto *Decl =
833  VarDecl::Create(SemaRef.Context, DC, Loc, Loc, II, Type, TInfo, SC_None);
834  if (Attrs) {
835  for (specific_attr_iterator<AlignedAttr> I(Attrs->begin()), E(Attrs->end());
836  I != E; ++I)
837  Decl->addAttr(*I);
838  }
839  Decl->setImplicit();
840  if (OrigRef) {
841  Decl->addAttr(
842  OMPReferencedVarAttr::CreateImplicit(SemaRef.Context, OrigRef));
843  }
844  return Decl;
845 }
846 
848  SourceLocation Loc,
849  bool RefersToCapture = false) {
850  D->setReferenced();
851  D->markUsed(S.Context);
853  SourceLocation(), D, RefersToCapture, Loc, Ty,
854  VK_LValue);
855 }
856 
857 void DSAStackTy::addTaskgroupReductionData(const ValueDecl *D, SourceRange SR,
858  BinaryOperatorKind BOK) {
859  D = getCanonicalDecl(D);
860  assert(!isStackEmpty() && "Data-sharing attributes stack is empty");
861  assert(
862  Stack.back().first.back().SharingMap[D].Attributes == OMPC_reduction &&
863  "Additional reduction info may be specified only for reduction items.");
864  ReductionData &ReductionData = Stack.back().first.back().ReductionMap[D];
865  assert(ReductionData.ReductionRange.isInvalid() &&
866  Stack.back().first.back().Directive == OMPD_taskgroup &&
867  "Additional reduction info may be specified only once for reduction "
868  "items.");
869  ReductionData.set(BOK, SR);
870  Expr *&TaskgroupReductionRef =
871  Stack.back().first.back().TaskgroupReductionRef;
872  if (!TaskgroupReductionRef) {
873  VarDecl *VD = buildVarDecl(SemaRef, SR.getBegin(),
874  SemaRef.Context.VoidPtrTy, ".task_red.");
875  TaskgroupReductionRef =
876  buildDeclRefExpr(SemaRef, VD, SemaRef.Context.VoidPtrTy, SR.getBegin());
877  }
878 }
879 
880 void DSAStackTy::addTaskgroupReductionData(const ValueDecl *D, SourceRange SR,
881  const Expr *ReductionRef) {
882  D = getCanonicalDecl(D);
883  assert(!isStackEmpty() && "Data-sharing attributes stack is empty");
884  assert(
885  Stack.back().first.back().SharingMap[D].Attributes == OMPC_reduction &&
886  "Additional reduction info may be specified only for reduction items.");
887  ReductionData &ReductionData = Stack.back().first.back().ReductionMap[D];
888  assert(ReductionData.ReductionRange.isInvalid() &&
889  Stack.back().first.back().Directive == OMPD_taskgroup &&
890  "Additional reduction info may be specified only once for reduction "
891  "items.");
892  ReductionData.set(ReductionRef, SR);
893  Expr *&TaskgroupReductionRef =
894  Stack.back().first.back().TaskgroupReductionRef;
895  if (!TaskgroupReductionRef) {
896  VarDecl *VD = buildVarDecl(SemaRef, SR.getBegin(),
897  SemaRef.Context.VoidPtrTy, ".task_red.");
898  TaskgroupReductionRef =
899  buildDeclRefExpr(SemaRef, VD, SemaRef.Context.VoidPtrTy, SR.getBegin());
900  }
901 }
902 
903 const DSAStackTy::DSAVarData DSAStackTy::getTopMostTaskgroupReductionData(
904  const ValueDecl *D, SourceRange &SR, BinaryOperatorKind &BOK,
905  Expr *&TaskgroupDescriptor) const {
906  D = getCanonicalDecl(D);
907  assert(!isStackEmpty() && "Data-sharing attributes stack is empty.");
908  if (Stack.back().first.empty())
909  return DSAVarData();
910  for (iterator I = std::next(Stack.back().first.rbegin(), 1),
911  E = Stack.back().first.rend();
912  I != E; std::advance(I, 1)) {
913  const DSAInfo &Data = I->SharingMap.lookup(D);
914  if (Data.Attributes != OMPC_reduction || I->Directive != OMPD_taskgroup)
915  continue;
916  const ReductionData &ReductionData = I->ReductionMap.lookup(D);
917  if (!ReductionData.ReductionOp ||
918  ReductionData.ReductionOp.is<const Expr *>())
919  return DSAVarData();
920  SR = ReductionData.ReductionRange;
921  BOK = ReductionData.ReductionOp.get<ReductionData::BOKPtrType>();
922  assert(I->TaskgroupReductionRef && "taskgroup reduction reference "
923  "expression for the descriptor is not "
924  "set.");
925  TaskgroupDescriptor = I->TaskgroupReductionRef;
926  return DSAVarData(OMPD_taskgroup, OMPC_reduction, Data.RefExpr.getPointer(),
927  Data.PrivateCopy, I->DefaultAttrLoc);
928  }
929  return DSAVarData();
930 }
931 
932 const DSAStackTy::DSAVarData DSAStackTy::getTopMostTaskgroupReductionData(
933  const ValueDecl *D, SourceRange &SR, const Expr *&ReductionRef,
934  Expr *&TaskgroupDescriptor) const {
935  D = getCanonicalDecl(D);
936  assert(!isStackEmpty() && "Data-sharing attributes stack is empty.");
937  if (Stack.back().first.empty())
938  return DSAVarData();
939  for (iterator I = std::next(Stack.back().first.rbegin(), 1),
940  E = Stack.back().first.rend();
941  I != E; std::advance(I, 1)) {
942  const DSAInfo &Data = I->SharingMap.lookup(D);
943  if (Data.Attributes != OMPC_reduction || I->Directive != OMPD_taskgroup)
944  continue;
945  const ReductionData &ReductionData = I->ReductionMap.lookup(D);
946  if (!ReductionData.ReductionOp ||
947  !ReductionData.ReductionOp.is<const Expr *>())
948  return DSAVarData();
949  SR = ReductionData.ReductionRange;
950  ReductionRef = ReductionData.ReductionOp.get<const Expr *>();
951  assert(I->TaskgroupReductionRef && "taskgroup reduction reference "
952  "expression for the descriptor is not "
953  "set.");
954  TaskgroupDescriptor = I->TaskgroupReductionRef;
955  return DSAVarData(OMPD_taskgroup, OMPC_reduction, Data.RefExpr.getPointer(),
956  Data.PrivateCopy, I->DefaultAttrLoc);
957  }
958  return DSAVarData();
959 }
960 
961 bool DSAStackTy::isOpenMPLocal(VarDecl *D, iterator Iter) const {
962  D = D->getCanonicalDecl();
963  if (!isStackEmpty()) {
964  iterator I = Iter, E = Stack.back().first.rend();
965  Scope *TopScope = nullptr;
966  while (I != E && !isParallelOrTaskRegion(I->Directive) &&
967  !isOpenMPTargetExecutionDirective(I->Directive))
968  ++I;
969  if (I == E)
970  return false;
971  TopScope = I->CurScope ? I->CurScope->getParent() : nullptr;
972  Scope *CurScope = getCurScope();
973  while (CurScope != TopScope && !CurScope->isDeclScope(D))
974  CurScope = CurScope->getParent();
975  return CurScope != TopScope;
976  }
977  return false;
978 }
979 
980 const DSAStackTy::DSAVarData DSAStackTy::getTopDSA(ValueDecl *D,
981  bool FromParent) {
982  D = getCanonicalDecl(D);
983  DSAVarData DVar;
984 
985  auto *VD = dyn_cast<VarDecl>(D);
986  auto TI = Threadprivates.find(D);
987  if (TI != Threadprivates.end()) {
988  DVar.RefExpr = TI->getSecond().RefExpr.getPointer();
989  DVar.CKind = OMPC_threadprivate;
990  return DVar;
991  }
992  if (VD && VD->hasAttr<OMPThreadPrivateDeclAttr>()) {
993  DVar.RefExpr = buildDeclRefExpr(
994  SemaRef, VD, D->getType().getNonReferenceType(),
995  VD->getAttr<OMPThreadPrivateDeclAttr>()->getLocation());
996  DVar.CKind = OMPC_threadprivate;
997  addDSA(D, DVar.RefExpr, OMPC_threadprivate);
998  return DVar;
999  }
1000  // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1001  // in a Construct, C/C++, predetermined, p.1]
1002  // Variables appearing in threadprivate directives are threadprivate.
1003  if ((VD && VD->getTLSKind() != VarDecl::TLS_None &&
1004  !(VD->hasAttr<OMPThreadPrivateDeclAttr>() &&
1005  SemaRef.getLangOpts().OpenMPUseTLS &&
1006  SemaRef.getASTContext().getTargetInfo().isTLSSupported())) ||
1007  (VD && VD->getStorageClass() == SC_Register &&
1008  VD->hasAttr<AsmLabelAttr>() && !VD->isLocalVarDecl())) {
1009  DVar.RefExpr = buildDeclRefExpr(
1010  SemaRef, VD, D->getType().getNonReferenceType(), D->getLocation());
1011  DVar.CKind = OMPC_threadprivate;
1012  addDSA(D, DVar.RefExpr, OMPC_threadprivate);
1013  return DVar;
1014  }
1015  if (SemaRef.getLangOpts().OpenMPCUDAMode && VD &&
1016  VD->isLocalVarDeclOrParm() && !isStackEmpty() &&
1017  !isLoopControlVariable(D).first) {
1018  iterator IterTarget =
1019  std::find_if(Stack.back().first.rbegin(), Stack.back().first.rend(),
1020  [](const SharingMapTy &Data) {
1021  return isOpenMPTargetExecutionDirective(Data.Directive);
1022  });
1023  if (IterTarget != Stack.back().first.rend()) {
1024  iterator ParentIterTarget = std::next(IterTarget, 1);
1025  for (iterator Iter = Stack.back().first.rbegin();
1026  Iter != ParentIterTarget; std::advance(Iter, 1)) {
1027  if (isOpenMPLocal(VD, Iter)) {
1028  DVar.RefExpr =
1029  buildDeclRefExpr(SemaRef, VD, D->getType().getNonReferenceType(),
1030  D->getLocation());
1031  DVar.CKind = OMPC_threadprivate;
1032  return DVar;
1033  }
1034  }
1035  if (!isClauseParsingMode() || IterTarget != Stack.back().first.rbegin()) {
1036  auto DSAIter = IterTarget->SharingMap.find(D);
1037  if (DSAIter != IterTarget->SharingMap.end() &&
1038  isOpenMPPrivate(DSAIter->getSecond().Attributes)) {
1039  DVar.RefExpr = DSAIter->getSecond().RefExpr.getPointer();
1040  DVar.CKind = OMPC_threadprivate;
1041  return DVar;
1042  }
1043  iterator End = Stack.back().first.rend();
1044  if (!SemaRef.isOpenMPCapturedByRef(
1045  D, std::distance(ParentIterTarget, End))) {
1046  DVar.RefExpr =
1047  buildDeclRefExpr(SemaRef, VD, D->getType().getNonReferenceType(),
1048  IterTarget->ConstructLoc);
1049  DVar.CKind = OMPC_threadprivate;
1050  return DVar;
1051  }
1052  }
1053  }
1054  }
1055 
1056  if (isStackEmpty())
1057  // Not in OpenMP execution region and top scope was already checked.
1058  return DVar;
1059 
1060  // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1061  // in a Construct, C/C++, predetermined, p.4]
1062  // Static data members are shared.
1063  // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1064  // in a Construct, C/C++, predetermined, p.7]
1065  // Variables with static storage duration that are declared in a scope
1066  // inside the construct are shared.
1067  auto &&MatchesAlways = [](OpenMPDirectiveKind) { return true; };
1068  if (VD && VD->isStaticDataMember()) {
1069  DSAVarData DVarTemp = hasDSA(D, isOpenMPPrivate, MatchesAlways, FromParent);
1070  if (DVarTemp.CKind != OMPC_unknown && DVarTemp.RefExpr)
1071  return DVar;
1072 
1073  DVar.CKind = OMPC_shared;
1074  return DVar;
1075  }
1076 
1078  bool IsConstant = Type.isConstant(SemaRef.getASTContext());
1079  Type = SemaRef.getASTContext().getBaseElementType(Type);
1080  // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1081  // in a Construct, C/C++, predetermined, p.6]
1082  // Variables with const qualified type having no mutable member are
1083  // shared.
1084  const CXXRecordDecl *RD =
1085  SemaRef.getLangOpts().CPlusPlus ? Type->getAsCXXRecordDecl() : nullptr;
1086  if (const auto *CTSD = dyn_cast_or_null<ClassTemplateSpecializationDecl>(RD))
1087  if (const ClassTemplateDecl *CTD = CTSD->getSpecializedTemplate())
1088  RD = CTD->getTemplatedDecl();
1089  if (IsConstant &&
1090  !(SemaRef.getLangOpts().CPlusPlus && RD && RD->hasDefinition() &&
1091  RD->hasMutableFields())) {
1092  // Variables with const-qualified type having no mutable member may be
1093  // listed in a firstprivate clause, even if they are static data members.
1094  DSAVarData DVarTemp =
1095  hasDSA(D, [](OpenMPClauseKind C) { return C == OMPC_firstprivate; },
1096  MatchesAlways, FromParent);
1097  if (DVarTemp.CKind == OMPC_firstprivate && DVarTemp.RefExpr)
1098  return DVarTemp;
1099 
1100  DVar.CKind = OMPC_shared;
1101  return DVar;
1102  }
1103 
1104  // Explicitly specified attributes and local variables with predetermined
1105  // attributes.
1106  iterator I = Stack.back().first.rbegin();
1107  iterator EndI = Stack.back().first.rend();
1108  if (FromParent && I != EndI)
1109  std::advance(I, 1);
1110  auto It = I->SharingMap.find(D);
1111  if (It != I->SharingMap.end()) {
1112  const DSAInfo &Data = It->getSecond();
1113  DVar.RefExpr = Data.RefExpr.getPointer();
1114  DVar.PrivateCopy = Data.PrivateCopy;
1115  DVar.CKind = Data.Attributes;
1116  DVar.ImplicitDSALoc = I->DefaultAttrLoc;
1117  DVar.DKind = I->Directive;
1118  }
1119 
1120  return DVar;
1121 }
1122 
1123 const DSAStackTy::DSAVarData DSAStackTy::getImplicitDSA(ValueDecl *D,
1124  bool FromParent) const {
1125  if (isStackEmpty()) {
1126  iterator I;
1127  return getDSA(I, D);
1128  }
1129  D = getCanonicalDecl(D);
1130  iterator StartI = Stack.back().first.rbegin();
1131  iterator EndI = Stack.back().first.rend();
1132  if (FromParent && StartI != EndI)
1133  std::advance(StartI, 1);
1134  return getDSA(StartI, D);
1135 }
1136 
1137 const DSAStackTy::DSAVarData
1138 DSAStackTy::hasDSA(ValueDecl *D,
1139  const llvm::function_ref<bool(OpenMPClauseKind)> CPred,
1140  const llvm::function_ref<bool(OpenMPDirectiveKind)> DPred,
1141  bool FromParent) const {
1142  if (isStackEmpty())
1143  return {};
1144  D = getCanonicalDecl(D);
1145  iterator I = Stack.back().first.rbegin();
1146  iterator EndI = Stack.back().first.rend();
1147  if (FromParent && I != EndI)
1148  std::advance(I, 1);
1149  for (; I != EndI; std::advance(I, 1)) {
1150  if (!DPred(I->Directive) && !isParallelOrTaskRegion(I->Directive))
1151  continue;
1152  iterator NewI = I;
1153  DSAVarData DVar = getDSA(NewI, D);
1154  if (I == NewI && CPred(DVar.CKind))
1155  return DVar;
1156  }
1157  return {};
1158 }
1159 
1160 const DSAStackTy::DSAVarData DSAStackTy::hasInnermostDSA(
1161  ValueDecl *D, const llvm::function_ref<bool(OpenMPClauseKind)> CPred,
1162  const llvm::function_ref<bool(OpenMPDirectiveKind)> DPred,
1163  bool FromParent) const {
1164  if (isStackEmpty())
1165  return {};
1166  D = getCanonicalDecl(D);
1167  iterator StartI = Stack.back().first.rbegin();
1168  iterator EndI = Stack.back().first.rend();
1169  if (FromParent && StartI != EndI)
1170  std::advance(StartI, 1);
1171  if (StartI == EndI || !DPred(StartI->Directive))
1172  return {};
1173  iterator NewI = StartI;
1174  DSAVarData DVar = getDSA(NewI, D);
1175  return (NewI == StartI && CPred(DVar.CKind)) ? DVar : DSAVarData();
1176 }
1177 
1178 bool DSAStackTy::hasExplicitDSA(
1179  const ValueDecl *D, const llvm::function_ref<bool(OpenMPClauseKind)> CPred,
1180  unsigned Level, bool NotLastprivate) const {
1181  if (isStackEmpty())
1182  return false;
1183  D = getCanonicalDecl(D);
1184  auto StartI = Stack.back().first.begin();
1185  auto EndI = Stack.back().first.end();
1186  if (std::distance(StartI, EndI) <= (int)Level)
1187  return false;
1188  std::advance(StartI, Level);
1189  auto I = StartI->SharingMap.find(D);
1190  return (I != StartI->SharingMap.end()) &&
1191  I->getSecond().RefExpr.getPointer() &&
1192  CPred(I->getSecond().Attributes) &&
1193  (!NotLastprivate || !I->getSecond().RefExpr.getInt());
1194 }
1195 
1196 bool DSAStackTy::hasExplicitDirective(
1197  const llvm::function_ref<bool(OpenMPDirectiveKind)> DPred,
1198  unsigned Level) const {
1199  if (isStackEmpty())
1200  return false;
1201  auto StartI = Stack.back().first.begin();
1202  auto EndI = Stack.back().first.end();
1203  if (std::distance(StartI, EndI) <= (int)Level)
1204  return false;
1205  std::advance(StartI, Level);
1206  return DPred(StartI->Directive);
1207 }
1208 
1209 bool DSAStackTy::hasDirective(
1210  const llvm::function_ref<bool(OpenMPDirectiveKind,
1212  DPred,
1213  bool FromParent) const {
1214  // We look only in the enclosing region.
1215  if (isStackEmpty())
1216  return false;
1217  auto StartI = std::next(Stack.back().first.rbegin());
1218  auto EndI = Stack.back().first.rend();
1219  if (FromParent && StartI != EndI)
1220  StartI = std::next(StartI);
1221  for (auto I = StartI, EE = EndI; I != EE; ++I) {
1222  if (DPred(I->Directive, I->DirectiveName, I->ConstructLoc))
1223  return true;
1224  }
1225  return false;
1226 }
1227 
1228 void Sema::InitDataSharingAttributesStack() {
1229  VarDataSharingAttributesStack = new DSAStackTy(*this);
1230 }
1231 
1232 #define DSAStack static_cast<DSAStackTy *>(VarDataSharingAttributesStack)
1233 
1234 void Sema::pushOpenMPFunctionRegion() {
1235  DSAStack->pushFunction();
1236 }
1237 
1238 void Sema::popOpenMPFunctionRegion(const FunctionScopeInfo *OldFSI) {
1239  DSAStack->popFunction(OldFSI);
1240 }
1241 
1244  for (const Decl *D : VD->redecls()) {
1245  if (!D->hasAttrs())
1246  continue;
1247  if (const auto *Attr = D->getAttr<OMPDeclareTargetDeclAttr>())
1248  return Attr->getMapType();
1249  }
1250  return llvm::None;
1251 }
1252 
1253 bool Sema::isOpenMPCapturedByRef(const ValueDecl *D, unsigned Level) const {
1254  assert(LangOpts.OpenMP && "OpenMP is not allowed");
1255 
1256  ASTContext &Ctx = getASTContext();
1257  bool IsByRef = true;
1258 
1259  // Find the directive that is associated with the provided scope.
1260  D = cast<ValueDecl>(D->getCanonicalDecl());
1261  QualType Ty = D->getType();
1262 
1263  if (DSAStack->hasExplicitDirective(isOpenMPTargetExecutionDirective, Level)) {
1264  // This table summarizes how a given variable should be passed to the device
1265  // given its type and the clauses where it appears. This table is based on
1266  // the description in OpenMP 4.5 [2.10.4, target Construct] and
1267  // OpenMP 4.5 [2.15.5, Data-mapping Attribute Rules and Clauses].
1268  //
1269  // =========================================================================
1270  // | type | defaultmap | pvt | first | is_device_ptr | map | res. |
1271  // | |(tofrom:scalar)| | pvt | | | |
1272  // =========================================================================
1273  // | scl | | | | - | | bycopy|
1274  // | scl | | - | x | - | - | bycopy|
1275  // | scl | | x | - | - | - | null |
1276  // | scl | x | | | - | | byref |
1277  // | scl | x | - | x | - | - | bycopy|
1278  // | scl | x | x | - | - | - | null |
1279  // | scl | | - | - | - | x | byref |
1280  // | scl | x | - | - | - | x | byref |
1281  //
1282  // | agg | n.a. | | | - | | byref |
1283  // | agg | n.a. | - | x | - | - | byref |
1284  // | agg | n.a. | x | - | - | - | null |
1285  // | agg | n.a. | - | - | - | x | byref |
1286  // | agg | n.a. | - | - | - | x[] | byref |
1287  //
1288  // | ptr | n.a. | | | - | | bycopy|
1289  // | ptr | n.a. | - | x | - | - | bycopy|
1290  // | ptr | n.a. | x | - | - | - | null |
1291  // | ptr | n.a. | - | - | - | x | byref |
1292  // | ptr | n.a. | - | - | - | x[] | bycopy|
1293  // | ptr | n.a. | - | - | x | | bycopy|
1294  // | ptr | n.a. | - | - | x | x | bycopy|
1295  // | ptr | n.a. | - | - | x | x[] | bycopy|
1296  // =========================================================================
1297  // Legend:
1298  // scl - scalar
1299  // ptr - pointer
1300  // agg - aggregate
1301  // x - applies
1302  // - - invalid in this combination
1303  // [] - mapped with an array section
1304  // byref - should be mapped by reference
1305  // byval - should be mapped by value
1306  // null - initialize a local variable to null on the device
1307  //
1308  // Observations:
1309  // - All scalar declarations that show up in a map clause have to be passed
1310  // by reference, because they may have been mapped in the enclosing data
1311  // environment.
1312  // - If the scalar value does not fit the size of uintptr, it has to be
1313  // passed by reference, regardless the result in the table above.
1314  // - For pointers mapped by value that have either an implicit map or an
1315  // array section, the runtime library may pass the NULL value to the
1316  // device instead of the value passed to it by the compiler.
1317 
1318  if (Ty->isReferenceType())
1319  Ty = Ty->castAs<ReferenceType>()->getPointeeType();
1320 
1321  // Locate map clauses and see if the variable being captured is referred to
1322  // in any of those clauses. Here we only care about variables, not fields,
1323  // because fields are part of aggregates.
1324  bool IsVariableUsedInMapClause = false;
1325  bool IsVariableAssociatedWithSection = false;
1326 
1327  DSAStack->checkMappableExprComponentListsForDeclAtLevel(
1328  D, Level,
1329  [&IsVariableUsedInMapClause, &IsVariableAssociatedWithSection, D](
1331  MapExprComponents,
1332  OpenMPClauseKind WhereFoundClauseKind) {
1333  // Only the map clause information influences how a variable is
1334  // captured. E.g. is_device_ptr does not require changing the default
1335  // behavior.
1336  if (WhereFoundClauseKind != OMPC_map)
1337  return false;
1338 
1339  auto EI = MapExprComponents.rbegin();
1340  auto EE = MapExprComponents.rend();
1341 
1342  assert(EI != EE && "Invalid map expression!");
1343 
1344  if (isa<DeclRefExpr>(EI->getAssociatedExpression()))
1345  IsVariableUsedInMapClause |= EI->getAssociatedDeclaration() == D;
1346 
1347  ++EI;
1348  if (EI == EE)
1349  return false;
1350 
1351  if (isa<ArraySubscriptExpr>(EI->getAssociatedExpression()) ||
1352  isa<OMPArraySectionExpr>(EI->getAssociatedExpression()) ||
1353  isa<MemberExpr>(EI->getAssociatedExpression())) {
1354  IsVariableAssociatedWithSection = true;
1355  // There is nothing more we need to know about this variable.
1356  return true;
1357  }
1358 
1359  // Keep looking for more map info.
1360  return false;
1361  });
1362 
1363  if (IsVariableUsedInMapClause) {
1364  // If variable is identified in a map clause it is always captured by
1365  // reference except if it is a pointer that is dereferenced somehow.
1366  IsByRef = !(Ty->isPointerType() && IsVariableAssociatedWithSection);
1367  } else {
1368  // By default, all the data that has a scalar type is mapped by copy
1369  // (except for reduction variables).
1370  IsByRef =
1371  !Ty->isScalarType() ||
1372  DSAStack->getDefaultDMAAtLevel(Level) == DMA_tofrom_scalar ||
1373  DSAStack->hasExplicitDSA(
1374  D, [](OpenMPClauseKind K) { return K == OMPC_reduction; }, Level);
1375  }
1376  }
1377 
1378  if (IsByRef && Ty.getNonReferenceType()->isScalarType()) {
1379  IsByRef =
1380  !DSAStack->hasExplicitDSA(
1381  D,
1382  [](OpenMPClauseKind K) -> bool { return K == OMPC_firstprivate; },
1383  Level, /*NotLastprivate=*/true) &&
1384  // If the variable is artificial and must be captured by value - try to
1385  // capture by value.
1386  !(isa<OMPCapturedExprDecl>(D) && !D->hasAttr<OMPCaptureNoInitAttr>() &&
1387  !cast<OMPCapturedExprDecl>(D)->getInit()->isGLValue());
1388  }
1389 
1390  // When passing data by copy, we need to make sure it fits the uintptr size
1391  // and alignment, because the runtime library only deals with uintptr types.
1392  // If it does not fit the uintptr size, we need to pass the data by reference
1393  // instead.
1394  if (!IsByRef &&
1395  (Ctx.getTypeSizeInChars(Ty) >
1396  Ctx.getTypeSizeInChars(Ctx.getUIntPtrType()) ||
1397  Ctx.getDeclAlign(D) > Ctx.getTypeAlignInChars(Ctx.getUIntPtrType()))) {
1398  IsByRef = true;
1399  }
1400 
1401  return IsByRef;
1402 }
1403 
1404 unsigned Sema::getOpenMPNestingLevel() const {
1405  assert(getLangOpts().OpenMP);
1406  return DSAStack->getNestingLevel();
1407 }
1408 
1410  return (isOpenMPTargetExecutionDirective(DSAStack->getCurrentDirective()) &&
1411  !DSAStack->isClauseParsingMode()) ||
1412  DSAStack->hasDirective(
1414  SourceLocation) -> bool {
1415  return isOpenMPTargetExecutionDirective(K);
1416  },
1417  false);
1418 }
1419 
1421  assert(LangOpts.OpenMP && "OpenMP is not allowed");
1422  D = getCanonicalDecl(D);
1423 
1424  // If we are attempting to capture a global variable in a directive with
1425  // 'target' we return true so that this global is also mapped to the device.
1426  //
1427  auto *VD = dyn_cast<VarDecl>(D);
1428  if (VD && !VD->hasLocalStorage() && isInOpenMPTargetExecutionDirective()) {
1429  // If the declaration is enclosed in a 'declare target' directive,
1430  // then it should not be captured.
1431  //
1433  return nullptr;
1434  return VD;
1435  }
1436 
1437  if (DSAStack->getCurrentDirective() != OMPD_unknown &&
1438  (!DSAStack->isClauseParsingMode() ||
1439  DSAStack->getParentDirective() != OMPD_unknown)) {
1440  auto &&Info = DSAStack->isLoopControlVariable(D);
1441  if (Info.first ||
1442  (VD && VD->hasLocalStorage() &&
1443  isParallelOrTaskRegion(DSAStack->getCurrentDirective())) ||
1444  (VD && DSAStack->isForceVarCapturing()))
1445  return VD ? VD : Info.second;
1446  DSAStackTy::DSAVarData DVarPrivate =
1447  DSAStack->getTopDSA(D, DSAStack->isClauseParsingMode());
1448  if (DVarPrivate.CKind != OMPC_unknown && isOpenMPPrivate(DVarPrivate.CKind))
1449  return VD ? VD : cast<VarDecl>(DVarPrivate.PrivateCopy->getDecl());
1450  DVarPrivate = DSAStack->hasDSA(D, isOpenMPPrivate,
1451  [](OpenMPDirectiveKind) { return true; },
1452  DSAStack->isClauseParsingMode());
1453  if (DVarPrivate.CKind != OMPC_unknown)
1454  return VD ? VD : cast<VarDecl>(DVarPrivate.PrivateCopy->getDecl());
1455  }
1456  return nullptr;
1457 }
1458 
1459 void Sema::adjustOpenMPTargetScopeIndex(unsigned &FunctionScopesIndex,
1460  unsigned Level) const {
1462  getOpenMPCaptureRegions(Regions, DSAStack->getDirective(Level));
1463  FunctionScopesIndex -= Regions.size();
1464 }
1465 
1466 bool Sema::isOpenMPPrivateDecl(const ValueDecl *D, unsigned Level) const {
1467  assert(LangOpts.OpenMP && "OpenMP is not allowed");
1468  return DSAStack->hasExplicitDSA(
1469  D, [](OpenMPClauseKind K) { return K == OMPC_private; }, Level) ||
1470  (DSAStack->isClauseParsingMode() &&
1471  DSAStack->getClauseParsingMode() == OMPC_private) ||
1472  // Consider taskgroup reduction descriptor variable a private to avoid
1473  // possible capture in the region.
1474  (DSAStack->hasExplicitDirective(
1475  [](OpenMPDirectiveKind K) { return K == OMPD_taskgroup; },
1476  Level) &&
1477  DSAStack->isTaskgroupReductionRef(D, Level));
1478 }
1479 
1481  unsigned Level) {
1482  assert(LangOpts.OpenMP && "OpenMP is not allowed");
1483  D = getCanonicalDecl(D);
1485  for (unsigned I = DSAStack->getNestingLevel() + 1; I > Level; --I) {
1486  const unsigned NewLevel = I - 1;
1487  if (DSAStack->hasExplicitDSA(D,
1488  [&OMPC](const OpenMPClauseKind K) {
1489  if (isOpenMPPrivate(K)) {
1490  OMPC = K;
1491  return true;
1492  }
1493  return false;
1494  },
1495  NewLevel))
1496  break;
1497  if (DSAStack->checkMappableExprComponentListsForDeclAtLevel(
1498  D, NewLevel,
1500  OpenMPClauseKind) { return true; })) {
1501  OMPC = OMPC_map;
1502  break;
1503  }
1504  if (DSAStack->hasExplicitDirective(isOpenMPTargetExecutionDirective,
1505  NewLevel)) {
1506  OMPC = OMPC_map;
1507  if (D->getType()->isScalarType() &&
1508  DSAStack->getDefaultDMAAtLevel(NewLevel) !=
1509  DefaultMapAttributes::DMA_tofrom_scalar)
1510  OMPC = OMPC_firstprivate;
1511  break;
1512  }
1513  }
1514  if (OMPC != OMPC_unknown)
1515  FD->addAttr(OMPCaptureKindAttr::CreateImplicit(Context, OMPC));
1516 }
1517 
1519  unsigned Level) const {
1520  assert(LangOpts.OpenMP && "OpenMP is not allowed");
1521  // Return true if the current level is no longer enclosed in a target region.
1522 
1523  const auto *VD = dyn_cast<VarDecl>(D);
1524  return VD && !VD->hasLocalStorage() &&
1525  DSAStack->hasExplicitDirective(isOpenMPTargetExecutionDirective,
1526  Level);
1527 }
1528 
1529 void Sema::DestroyDataSharingAttributesStack() { delete DSAStack; }
1530 
1532  const DeclarationNameInfo &DirName,
1533  Scope *CurScope, SourceLocation Loc) {
1534  DSAStack->push(DKind, DirName, CurScope, Loc);
1535  PushExpressionEvaluationContext(
1536  ExpressionEvaluationContext::PotentiallyEvaluated);
1537 }
1538 
1540  DSAStack->setClauseParsingMode(K);
1541 }
1542 
1544  DSAStack->setClauseParsingMode(/*K=*/OMPC_unknown);
1545 }
1546 
1547 void Sema::EndOpenMPDSABlock(Stmt *CurDirective) {
1548  // OpenMP [2.14.3.5, Restrictions, C/C++, p.1]
1549  // A variable of class type (or array thereof) that appears in a lastprivate
1550  // clause requires an accessible, unambiguous default constructor for the
1551  // class type, unless the list item is also specified in a firstprivate
1552  // clause.
1553  if (const auto *D = dyn_cast_or_null<OMPExecutableDirective>(CurDirective)) {
1554  for (OMPClause *C : D->clauses()) {
1555  if (auto *Clause = dyn_cast<OMPLastprivateClause>(C)) {
1556  SmallVector<Expr *, 8> PrivateCopies;
1557  for (Expr *DE : Clause->varlists()) {
1558  if (DE->isValueDependent() || DE->isTypeDependent()) {
1559  PrivateCopies.push_back(nullptr);
1560  continue;
1561  }
1562  auto *DRE = cast<DeclRefExpr>(DE->IgnoreParens());
1563  auto *VD = cast<VarDecl>(DRE->getDecl());
1564  QualType Type = VD->getType().getNonReferenceType();
1565  const DSAStackTy::DSAVarData DVar =
1566  DSAStack->getTopDSA(VD, /*FromParent=*/false);
1567  if (DVar.CKind == OMPC_lastprivate) {
1568  // Generate helper private variable and initialize it with the
1569  // default value. The address of the original variable is replaced
1570  // by the address of the new private variable in CodeGen. This new
1571  // variable is not added to IdResolver, so the code in the OpenMP
1572  // region uses original variable for proper diagnostics.
1573  VarDecl *VDPrivate = buildVarDecl(
1574  *this, DE->getExprLoc(), Type.getUnqualifiedType(),
1575  VD->getName(), VD->hasAttrs() ? &VD->getAttrs() : nullptr, DRE);
1576  ActOnUninitializedDecl(VDPrivate);
1577  if (VDPrivate->isInvalidDecl())
1578  continue;
1579  PrivateCopies.push_back(buildDeclRefExpr(
1580  *this, VDPrivate, DE->getType(), DE->getExprLoc()));
1581  } else {
1582  // The variable is also a firstprivate, so initialization sequence
1583  // for private copy is generated already.
1584  PrivateCopies.push_back(nullptr);
1585  }
1586  }
1587  // Set initializers to private copies if no errors were found.
1588  if (PrivateCopies.size() == Clause->varlist_size())
1589  Clause->setPrivateCopies(PrivateCopies);
1590  }
1591  }
1592  }
1593 
1594  DSAStack->pop();
1595  DiscardCleanupsInEvaluationContext();
1596  PopExpressionEvaluationContext();
1597 }
1598 
1599 static bool FinishOpenMPLinearClause(OMPLinearClause &Clause, DeclRefExpr *IV,
1600  Expr *NumIterations, Sema &SemaRef,
1601  Scope *S, DSAStackTy *Stack);
1602 
1603 namespace {
1604 
1605 class VarDeclFilterCCC final : public CorrectionCandidateCallback {
1606 private:
1607  Sema &SemaRef;
1608 
1609 public:
1610  explicit VarDeclFilterCCC(Sema &S) : SemaRef(S) {}
1611  bool ValidateCandidate(const TypoCorrection &Candidate) override {
1612  NamedDecl *ND = Candidate.getCorrectionDecl();
1613  if (const auto *VD = dyn_cast_or_null<VarDecl>(ND)) {
1614  return VD->hasGlobalStorage() &&
1615  SemaRef.isDeclInScope(ND, SemaRef.getCurLexicalContext(),
1616  SemaRef.getCurScope());
1617  }
1618  return false;
1619  }
1620 };
1621 
1622 class VarOrFuncDeclFilterCCC final : public CorrectionCandidateCallback {
1623 private:
1624  Sema &SemaRef;
1625 
1626 public:
1627  explicit VarOrFuncDeclFilterCCC(Sema &S) : SemaRef(S) {}
1628  bool ValidateCandidate(const TypoCorrection &Candidate) override {
1629  NamedDecl *ND = Candidate.getCorrectionDecl();
1630  if (ND && (isa<VarDecl>(ND) || isa<FunctionDecl>(ND))) {
1631  return SemaRef.isDeclInScope(ND, SemaRef.getCurLexicalContext(),
1632  SemaRef.getCurScope());
1633  }
1634  return false;
1635  }
1636 };
1637 
1638 } // namespace
1639 
1641  CXXScopeSpec &ScopeSpec,
1642  const DeclarationNameInfo &Id) {
1643  LookupResult Lookup(*this, Id, LookupOrdinaryName);
1644  LookupParsedName(Lookup, CurScope, &ScopeSpec, true);
1645 
1646  if (Lookup.isAmbiguous())
1647  return ExprError();
1648 
1649  VarDecl *VD;
1650  if (!Lookup.isSingleResult()) {
1651  if (TypoCorrection Corrected = CorrectTypo(
1652  Id, LookupOrdinaryName, CurScope, nullptr,
1653  llvm::make_unique<VarDeclFilterCCC>(*this), CTK_ErrorRecovery)) {
1654  diagnoseTypo(Corrected,
1655  PDiag(Lookup.empty()
1656  ? diag::err_undeclared_var_use_suggest
1657  : diag::err_omp_expected_var_arg_suggest)
1658  << Id.getName());
1659  VD = Corrected.getCorrectionDeclAs<VarDecl>();
1660  } else {
1661  Diag(Id.getLoc(), Lookup.empty() ? diag::err_undeclared_var_use
1662  : diag::err_omp_expected_var_arg)
1663  << Id.getName();
1664  return ExprError();
1665  }
1666  } else if (!(VD = Lookup.getAsSingle<VarDecl>())) {
1667  Diag(Id.getLoc(), diag::err_omp_expected_var_arg) << Id.getName();
1668  Diag(Lookup.getFoundDecl()->getLocation(), diag::note_declared_at);
1669  return ExprError();
1670  }
1671  Lookup.suppressDiagnostics();
1672 
1673  // OpenMP [2.9.2, Syntax, C/C++]
1674  // Variables must be file-scope, namespace-scope, or static block-scope.
1675  if (!VD->hasGlobalStorage()) {
1676  Diag(Id.getLoc(), diag::err_omp_global_var_arg)
1677  << getOpenMPDirectiveName(OMPD_threadprivate) << !VD->isStaticLocal();
1678  bool IsDecl =
1680  Diag(VD->getLocation(),
1681  IsDecl ? diag::note_previous_decl : diag::note_defined_here)
1682  << VD;
1683  return ExprError();
1684  }
1685 
1686  VarDecl *CanonicalVD = VD->getCanonicalDecl();
1687  NamedDecl *ND = CanonicalVD;
1688  // OpenMP [2.9.2, Restrictions, C/C++, p.2]
1689  // A threadprivate directive for file-scope variables must appear outside
1690  // any definition or declaration.
1691  if (CanonicalVD->getDeclContext()->isTranslationUnit() &&
1692  !getCurLexicalContext()->isTranslationUnit()) {
1693  Diag(Id.getLoc(), diag::err_omp_var_scope)
1694  << getOpenMPDirectiveName(OMPD_threadprivate) << VD;
1695  bool IsDecl =
1697  Diag(VD->getLocation(),
1698  IsDecl ? diag::note_previous_decl : diag::note_defined_here)
1699  << VD;
1700  return ExprError();
1701  }
1702  // OpenMP [2.9.2, Restrictions, C/C++, p.3]
1703  // A threadprivate directive for static class member variables must appear
1704  // in the class definition, in the same scope in which the member
1705  // variables are declared.
1706  if (CanonicalVD->isStaticDataMember() &&
1707  !CanonicalVD->getDeclContext()->Equals(getCurLexicalContext())) {
1708  Diag(Id.getLoc(), diag::err_omp_var_scope)
1709  << getOpenMPDirectiveName(OMPD_threadprivate) << VD;
1710  bool IsDecl =
1712  Diag(VD->getLocation(),
1713  IsDecl ? diag::note_previous_decl : diag::note_defined_here)
1714  << VD;
1715  return ExprError();
1716  }
1717  // OpenMP [2.9.2, Restrictions, C/C++, p.4]
1718  // A threadprivate directive for namespace-scope variables must appear
1719  // outside any definition or declaration other than the namespace
1720  // definition itself.
1721  if (CanonicalVD->getDeclContext()->isNamespace() &&
1722  (!getCurLexicalContext()->isFileContext() ||
1723  !getCurLexicalContext()->Encloses(CanonicalVD->getDeclContext()))) {
1724  Diag(Id.getLoc(), diag::err_omp_var_scope)
1725  << getOpenMPDirectiveName(OMPD_threadprivate) << VD;
1726  bool IsDecl =
1728  Diag(VD->getLocation(),
1729  IsDecl ? diag::note_previous_decl : diag::note_defined_here)
1730  << VD;
1731  return ExprError();
1732  }
1733  // OpenMP [2.9.2, Restrictions, C/C++, p.6]
1734  // A threadprivate directive for static block-scope variables must appear
1735  // in the scope of the variable and not in a nested scope.
1736  if (CanonicalVD->isStaticLocal() && CurScope &&
1737  !isDeclInScope(ND, getCurLexicalContext(), CurScope)) {
1738  Diag(Id.getLoc(), diag::err_omp_var_scope)
1739  << getOpenMPDirectiveName(OMPD_threadprivate) << VD;
1740  bool IsDecl =
1742  Diag(VD->getLocation(),
1743  IsDecl ? diag::note_previous_decl : diag::note_defined_here)
1744  << VD;
1745  return ExprError();
1746  }
1747 
1748  // OpenMP [2.9.2, Restrictions, C/C++, p.2-6]
1749  // A threadprivate directive must lexically precede all references to any
1750  // of the variables in its list.
1751  if (VD->isUsed() && !DSAStack->isThreadPrivate(VD)) {
1752  Diag(Id.getLoc(), diag::err_omp_var_used)
1753  << getOpenMPDirectiveName(OMPD_threadprivate) << VD;
1754  return ExprError();
1755  }
1756 
1757  QualType ExprType = VD->getType().getNonReferenceType();
1758  return DeclRefExpr::Create(Context, NestedNameSpecifierLoc(),
1759  SourceLocation(), VD,
1760  /*RefersToEnclosingVariableOrCapture=*/false,
1761  Id.getLoc(), ExprType, VK_LValue);
1762 }
1763 
1766  ArrayRef<Expr *> VarList) {
1767  if (OMPThreadPrivateDecl *D = CheckOMPThreadPrivateDecl(Loc, VarList)) {
1768  CurContext->addDecl(D);
1769  return DeclGroupPtrTy::make(DeclGroupRef(D));
1770  }
1771  return nullptr;
1772 }
1773 
1774 namespace {
1775 class LocalVarRefChecker final
1776  : public ConstStmtVisitor<LocalVarRefChecker, bool> {
1777  Sema &SemaRef;
1778 
1779 public:
1780  bool VisitDeclRefExpr(const DeclRefExpr *E) {
1781  if (const auto *VD = dyn_cast<VarDecl>(E->getDecl())) {
1782  if (VD->hasLocalStorage()) {
1783  SemaRef.Diag(E->getLocStart(),
1784  diag::err_omp_local_var_in_threadprivate_init)
1785  << E->getSourceRange();
1786  SemaRef.Diag(VD->getLocation(), diag::note_defined_here)
1787  << VD << VD->getSourceRange();
1788  return true;
1789  }
1790  }
1791  return false;
1792  }
1793  bool VisitStmt(const Stmt *S) {
1794  for (const Stmt *Child : S->children()) {
1795  if (Child && Visit(Child))
1796  return true;
1797  }
1798  return false;
1799  }
1800  explicit LocalVarRefChecker(Sema &SemaRef) : SemaRef(SemaRef) {}
1801 };
1802 } // namespace
1803 
1807  for (Expr *RefExpr : VarList) {
1808  auto *DE = cast<DeclRefExpr>(RefExpr);
1809  auto *VD = cast<VarDecl>(DE->getDecl());
1810  SourceLocation ILoc = DE->getExprLoc();
1811 
1812  // Mark variable as used.
1813  VD->setReferenced();
1814  VD->markUsed(Context);
1815 
1816  QualType QType = VD->getType();
1817  if (QType->isDependentType() || QType->isInstantiationDependentType()) {
1818  // It will be analyzed later.
1819  Vars.push_back(DE);
1820  continue;
1821  }
1822 
1823  // OpenMP [2.9.2, Restrictions, C/C++, p.10]
1824  // A threadprivate variable must not have an incomplete type.
1825  if (RequireCompleteType(ILoc, VD->getType(),
1826  diag::err_omp_threadprivate_incomplete_type)) {
1827  continue;
1828  }
1829 
1830  // OpenMP [2.9.2, Restrictions, C/C++, p.10]
1831  // A threadprivate variable must not have a reference type.
1832  if (VD->getType()->isReferenceType()) {
1833  Diag(ILoc, diag::err_omp_ref_type_arg)
1834  << getOpenMPDirectiveName(OMPD_threadprivate) << VD->getType();
1835  bool IsDecl =
1836  VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
1837  Diag(VD->getLocation(),
1838  IsDecl ? diag::note_previous_decl : diag::note_defined_here)
1839  << VD;
1840  continue;
1841  }
1842 
1843  // Check if this is a TLS variable. If TLS is not being supported, produce
1844  // the corresponding diagnostic.
1845  if ((VD->getTLSKind() != VarDecl::TLS_None &&
1846  !(VD->hasAttr<OMPThreadPrivateDeclAttr>() &&
1847  getLangOpts().OpenMPUseTLS &&
1848  getASTContext().getTargetInfo().isTLSSupported())) ||
1849  (VD->getStorageClass() == SC_Register && VD->hasAttr<AsmLabelAttr>() &&
1850  !VD->isLocalVarDecl())) {
1851  Diag(ILoc, diag::err_omp_var_thread_local)
1852  << VD << ((VD->getTLSKind() != VarDecl::TLS_None) ? 0 : 1);
1853  bool IsDecl =
1854  VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
1855  Diag(VD->getLocation(),
1856  IsDecl ? diag::note_previous_decl : diag::note_defined_here)
1857  << VD;
1858  continue;
1859  }
1860 
1861  // Check if initial value of threadprivate variable reference variable with
1862  // local storage (it is not supported by runtime).
1863  if (const Expr *Init = VD->getAnyInitializer()) {
1864  LocalVarRefChecker Checker(*this);
1865  if (Checker.Visit(Init))
1866  continue;
1867  }
1868 
1869  Vars.push_back(RefExpr);
1870  DSAStack->addDSA(VD, DE, OMPC_threadprivate);
1871  VD->addAttr(OMPThreadPrivateDeclAttr::CreateImplicit(
1872  Context, SourceRange(Loc, Loc)));
1873  if (ASTMutationListener *ML = Context.getASTMutationListener())
1874  ML->DeclarationMarkedOpenMPThreadPrivate(VD);
1875  }
1876  OMPThreadPrivateDecl *D = nullptr;
1877  if (!Vars.empty()) {
1878  D = OMPThreadPrivateDecl::Create(Context, getCurLexicalContext(), Loc,
1879  Vars);
1880  D->setAccess(AS_public);
1881  }
1882  return D;
1883 }
1884 
1885 static void reportOriginalDsa(Sema &SemaRef, const DSAStackTy *Stack,
1886  const ValueDecl *D,
1887  const DSAStackTy::DSAVarData &DVar,
1888  bool IsLoopIterVar = false) {
1889  if (DVar.RefExpr) {
1890  SemaRef.Diag(DVar.RefExpr->getExprLoc(), diag::note_omp_explicit_dsa)
1891  << getOpenMPClauseName(DVar.CKind);
1892  return;
1893  }
1894  enum {
1895  PDSA_StaticMemberShared,
1896  PDSA_StaticLocalVarShared,
1897  PDSA_LoopIterVarPrivate,
1898  PDSA_LoopIterVarLinear,
1899  PDSA_LoopIterVarLastprivate,
1900  PDSA_ConstVarShared,
1901  PDSA_GlobalVarShared,
1902  PDSA_TaskVarFirstprivate,
1903  PDSA_LocalVarPrivate,
1904  PDSA_Implicit
1905  } Reason = PDSA_Implicit;
1906  bool ReportHint = false;
1907  auto ReportLoc = D->getLocation();
1908  auto *VD = dyn_cast<VarDecl>(D);
1909  if (IsLoopIterVar) {
1910  if (DVar.CKind == OMPC_private)
1911  Reason = PDSA_LoopIterVarPrivate;
1912  else if (DVar.CKind == OMPC_lastprivate)
1913  Reason = PDSA_LoopIterVarLastprivate;
1914  else
1915  Reason = PDSA_LoopIterVarLinear;
1916  } else if (isOpenMPTaskingDirective(DVar.DKind) &&
1917  DVar.CKind == OMPC_firstprivate) {
1918  Reason = PDSA_TaskVarFirstprivate;
1919  ReportLoc = DVar.ImplicitDSALoc;
1920  } else if (VD && VD->isStaticLocal())
1921  Reason = PDSA_StaticLocalVarShared;
1922  else if (VD && VD->isStaticDataMember())
1923  Reason = PDSA_StaticMemberShared;
1924  else if (VD && VD->isFileVarDecl())
1925  Reason = PDSA_GlobalVarShared;
1926  else if (D->getType().isConstant(SemaRef.getASTContext()))
1927  Reason = PDSA_ConstVarShared;
1928  else if (VD && VD->isLocalVarDecl() && DVar.CKind == OMPC_private) {
1929  ReportHint = true;
1930  Reason = PDSA_LocalVarPrivate;
1931  }
1932  if (Reason != PDSA_Implicit) {
1933  SemaRef.Diag(ReportLoc, diag::note_omp_predetermined_dsa)
1934  << Reason << ReportHint
1935  << getOpenMPDirectiveName(Stack->getCurrentDirective());
1936  } else if (DVar.ImplicitDSALoc.isValid()) {
1937  SemaRef.Diag(DVar.ImplicitDSALoc, diag::note_omp_implicit_dsa)
1938  << getOpenMPClauseName(DVar.CKind);
1939  }
1940 }
1941 
1942 namespace {
1943 class DSAAttrChecker final : public StmtVisitor<DSAAttrChecker, void> {
1944  DSAStackTy *Stack;
1945  Sema &SemaRef;
1946  bool ErrorFound = false;
1947  CapturedStmt *CS = nullptr;
1948  llvm::SmallVector<Expr *, 4> ImplicitFirstprivate;
1949  llvm::SmallVector<Expr *, 4> ImplicitMap;
1950  Sema::VarsWithInheritedDSAType VarsWithInheritedDSA;
1951  llvm::SmallDenseSet<const ValueDecl *, 4> ImplicitDeclarations;
1952 
1953 public:
1954  void VisitDeclRefExpr(DeclRefExpr *E) {
1955  if (E->isTypeDependent() || E->isValueDependent() ||
1957  return;
1958  if (auto *VD = dyn_cast<VarDecl>(E->getDecl())) {
1959  VD = VD->getCanonicalDecl();
1960  // Skip internally declared variables.
1961  if (VD->hasLocalStorage() && !CS->capturesVariable(VD))
1962  return;
1963 
1964  DSAStackTy::DSAVarData DVar = Stack->getTopDSA(VD, /*FromParent=*/false);
1965  // Check if the variable has explicit DSA set and stop analysis if it so.
1966  if (DVar.RefExpr || !ImplicitDeclarations.insert(VD).second)
1967  return;
1968 
1969  // Skip internally declared static variables.
1972  if (VD->hasGlobalStorage() && !CS->capturesVariable(VD) &&
1973  (!Res || *Res != OMPDeclareTargetDeclAttr::MT_Link))
1974  return;
1975 
1976  SourceLocation ELoc = E->getExprLoc();
1977  OpenMPDirectiveKind DKind = Stack->getCurrentDirective();
1978  // The default(none) clause requires that each variable that is referenced
1979  // in the construct, and does not have a predetermined data-sharing
1980  // attribute, must have its data-sharing attribute explicitly determined
1981  // by being listed in a data-sharing attribute clause.
1982  if (DVar.CKind == OMPC_unknown && Stack->getDefaultDSA() == DSA_none &&
1983  isParallelOrTaskRegion(DKind) &&
1984  VarsWithInheritedDSA.count(VD) == 0) {
1985  VarsWithInheritedDSA[VD] = E;
1986  return;
1987  }
1988 
1989  if (isOpenMPTargetExecutionDirective(DKind) &&
1990  !Stack->isLoopControlVariable(VD).first) {
1991  if (!Stack->checkMappableExprComponentListsForDecl(
1992  VD, /*CurrentRegionOnly=*/true,
1994  StackComponents,
1995  OpenMPClauseKind) {
1996  // Variable is used if it has been marked as an array, array
1997  // section or the variable iself.
1998  return StackComponents.size() == 1 ||
1999  std::all_of(
2000  std::next(StackComponents.rbegin()),
2001  StackComponents.rend(),
2002  [](const OMPClauseMappableExprCommon::
2003  MappableComponent &MC) {
2004  return MC.getAssociatedDeclaration() ==
2005  nullptr &&
2006  (isa<OMPArraySectionExpr>(
2007  MC.getAssociatedExpression()) ||
2008  isa<ArraySubscriptExpr>(
2009  MC.getAssociatedExpression()));
2010  });
2011  })) {
2012  bool IsFirstprivate = false;
2013  // By default lambdas are captured as firstprivates.
2014  if (const auto *RD =
2015  VD->getType().getNonReferenceType()->getAsCXXRecordDecl())
2016  IsFirstprivate = RD->isLambda();
2017  IsFirstprivate =
2018  IsFirstprivate ||
2019  (VD->getType().getNonReferenceType()->isScalarType() &&
2020  Stack->getDefaultDMA() != DMA_tofrom_scalar && !Res);
2021  if (IsFirstprivate)
2022  ImplicitFirstprivate.emplace_back(E);
2023  else
2024  ImplicitMap.emplace_back(E);
2025  return;
2026  }
2027  }
2028 
2029  // OpenMP [2.9.3.6, Restrictions, p.2]
2030  // A list item that appears in a reduction clause of the innermost
2031  // enclosing worksharing or parallel construct may not be accessed in an
2032  // explicit task.
2033  DVar = Stack->hasInnermostDSA(
2034  VD, [](OpenMPClauseKind C) { return C == OMPC_reduction; },
2035  [](OpenMPDirectiveKind K) {
2036  return isOpenMPParallelDirective(K) ||
2038  },
2039  /*FromParent=*/true);
2040  if (isOpenMPTaskingDirective(DKind) && DVar.CKind == OMPC_reduction) {
2041  ErrorFound = true;
2042  SemaRef.Diag(ELoc, diag::err_omp_reduction_in_task);
2043  reportOriginalDsa(SemaRef, Stack, VD, DVar);
2044  return;
2045  }
2046 
2047  // Define implicit data-sharing attributes for task.
2048  DVar = Stack->getImplicitDSA(VD, /*FromParent=*/false);
2049  if (isOpenMPTaskingDirective(DKind) && DVar.CKind != OMPC_shared &&
2050  !Stack->isLoopControlVariable(VD).first)
2051  ImplicitFirstprivate.push_back(E);
2052  }
2053  }
2054  void VisitMemberExpr(MemberExpr *E) {
2055  if (E->isTypeDependent() || E->isValueDependent() ||
2057  return;
2058  auto *FD = dyn_cast<FieldDecl>(E->getMemberDecl());
2059  OpenMPDirectiveKind DKind = Stack->getCurrentDirective();
2060  if (isa<CXXThisExpr>(E->getBase()->IgnoreParens())) {
2061  if (!FD)
2062  return;
2063  DSAStackTy::DSAVarData DVar = Stack->getTopDSA(FD, /*FromParent=*/false);
2064  // Check if the variable has explicit DSA set and stop analysis if it
2065  // so.
2066  if (DVar.RefExpr || !ImplicitDeclarations.insert(FD).second)
2067  return;
2068 
2069  if (isOpenMPTargetExecutionDirective(DKind) &&
2070  !Stack->isLoopControlVariable(FD).first &&
2071  !Stack->checkMappableExprComponentListsForDecl(
2072  FD, /*CurrentRegionOnly=*/true,
2074  StackComponents,
2075  OpenMPClauseKind) {
2076  return isa<CXXThisExpr>(
2077  cast<MemberExpr>(
2078  StackComponents.back().getAssociatedExpression())
2079  ->getBase()
2080  ->IgnoreParens());
2081  })) {
2082  // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C/C++, p.3]
2083  // A bit-field cannot appear in a map clause.
2084  //
2085  if (FD->isBitField())
2086  return;
2087  ImplicitMap.emplace_back(E);
2088  return;
2089  }
2090 
2091  SourceLocation ELoc = E->getExprLoc();
2092  // OpenMP [2.9.3.6, Restrictions, p.2]
2093  // A list item that appears in a reduction clause of the innermost
2094  // enclosing worksharing or parallel construct may not be accessed in
2095  // an explicit task.
2096  DVar = Stack->hasInnermostDSA(
2097  FD, [](OpenMPClauseKind C) { return C == OMPC_reduction; },
2098  [](OpenMPDirectiveKind K) {
2099  return isOpenMPParallelDirective(K) ||
2101  },
2102  /*FromParent=*/true);
2103  if (isOpenMPTaskingDirective(DKind) && DVar.CKind == OMPC_reduction) {
2104  ErrorFound = true;
2105  SemaRef.Diag(ELoc, diag::err_omp_reduction_in_task);
2106  reportOriginalDsa(SemaRef, Stack, FD, DVar);
2107  return;
2108  }
2109 
2110  // Define implicit data-sharing attributes for task.
2111  DVar = Stack->getImplicitDSA(FD, /*FromParent=*/false);
2112  if (isOpenMPTaskingDirective(DKind) && DVar.CKind != OMPC_shared &&
2113  !Stack->isLoopControlVariable(FD).first)
2114  ImplicitFirstprivate.push_back(E);
2115  return;
2116  }
2117  if (isOpenMPTargetExecutionDirective(DKind)) {
2119  if (!checkMapClauseExpressionBase(SemaRef, E, CurComponents, OMPC_map,
2120  /*NoDiagnose=*/true))
2121  return;
2122  const auto *VD = cast<ValueDecl>(
2123  CurComponents.back().getAssociatedDeclaration()->getCanonicalDecl());
2124  if (!Stack->checkMappableExprComponentListsForDecl(
2125  VD, /*CurrentRegionOnly=*/true,
2126  [&CurComponents](
2128  StackComponents,
2129  OpenMPClauseKind) {
2130  auto CCI = CurComponents.rbegin();
2131  auto CCE = CurComponents.rend();
2132  for (const auto &SC : llvm::reverse(StackComponents)) {
2133  // Do both expressions have the same kind?
2134  if (CCI->getAssociatedExpression()->getStmtClass() !=
2135  SC.getAssociatedExpression()->getStmtClass())
2136  if (!(isa<OMPArraySectionExpr>(
2137  SC.getAssociatedExpression()) &&
2138  isa<ArraySubscriptExpr>(
2139  CCI->getAssociatedExpression())))
2140  return false;
2141 
2142  const Decl *CCD = CCI->getAssociatedDeclaration();
2143  const Decl *SCD = SC.getAssociatedDeclaration();
2144  CCD = CCD ? CCD->getCanonicalDecl() : nullptr;
2145  SCD = SCD ? SCD->getCanonicalDecl() : nullptr;
2146  if (SCD != CCD)
2147  return false;
2148  std::advance(CCI, 1);
2149  if (CCI == CCE)
2150  break;
2151  }
2152  return true;
2153  })) {
2154  Visit(E->getBase());
2155  }
2156  } else {
2157  Visit(E->getBase());
2158  }
2159  }
2160  void VisitOMPExecutableDirective(OMPExecutableDirective *S) {
2161  for (OMPClause *C : S->clauses()) {
2162  // Skip analysis of arguments of implicitly defined firstprivate clause
2163  // for task|target directives.
2164  // Skip analysis of arguments of implicitly defined map clause for target
2165  // directives.
2166  if (C && !((isa<OMPFirstprivateClause>(C) || isa<OMPMapClause>(C)) &&
2167  C->isImplicit())) {
2168  for (Stmt *CC : C->children()) {
2169  if (CC)
2170  Visit(CC);
2171  }
2172  }
2173  }
2174  }
2175  void VisitStmt(Stmt *S) {
2176  for (Stmt *C : S->children()) {
2177  if (C && !isa<OMPExecutableDirective>(C))
2178  Visit(C);
2179  }
2180  }
2181 
2182  bool isErrorFound() const { return ErrorFound; }
2183  ArrayRef<Expr *> getImplicitFirstprivate() const {
2184  return ImplicitFirstprivate;
2185  }
2186  ArrayRef<Expr *> getImplicitMap() const { return ImplicitMap; }
2187  const Sema::VarsWithInheritedDSAType &getVarsWithInheritedDSA() const {
2188  return VarsWithInheritedDSA;
2189  }
2190 
2191  DSAAttrChecker(DSAStackTy *S, Sema &SemaRef, CapturedStmt *CS)
2192  : Stack(S), SemaRef(SemaRef), ErrorFound(false), CS(CS) {}
2193 };
2194 } // namespace
2195 
2197  switch (DKind) {
2198  case OMPD_parallel:
2199  case OMPD_parallel_for:
2200  case OMPD_parallel_for_simd:
2201  case OMPD_parallel_sections:
2202  case OMPD_teams:
2203  case OMPD_teams_distribute:
2204  case OMPD_teams_distribute_simd: {
2205  QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
2206  QualType KmpInt32PtrTy =
2207  Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
2208  Sema::CapturedParamNameType Params[] = {
2209  std::make_pair(".global_tid.", KmpInt32PtrTy),
2210  std::make_pair(".bound_tid.", KmpInt32PtrTy),
2211  std::make_pair(StringRef(), QualType()) // __context with shared vars
2212  };
2213  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2214  Params);
2215  break;
2216  }
2217  case OMPD_target_teams:
2218  case OMPD_target_parallel:
2219  case OMPD_target_parallel_for:
2220  case OMPD_target_parallel_for_simd:
2221  case OMPD_target_teams_distribute:
2222  case OMPD_target_teams_distribute_simd: {
2223  QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
2224  QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
2225  QualType KmpInt32PtrTy =
2226  Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
2227  QualType Args[] = {VoidPtrTy};
2229  EPI.Variadic = true;
2230  QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
2231  Sema::CapturedParamNameType Params[] = {
2232  std::make_pair(".global_tid.", KmpInt32Ty),
2233  std::make_pair(".part_id.", KmpInt32PtrTy),
2234  std::make_pair(".privates.", VoidPtrTy),
2235  std::make_pair(
2236  ".copy_fn.",
2237  Context.getPointerType(CopyFnType).withConst().withRestrict()),
2238  std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
2239  std::make_pair(StringRef(), QualType()) // __context with shared vars
2240  };
2241  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2242  Params);
2243  // Mark this captured region as inlined, because we don't use outlined
2244  // function directly.
2245  getCurCapturedRegion()->TheCapturedDecl->addAttr(
2246  AlwaysInlineAttr::CreateImplicit(
2247  Context, AlwaysInlineAttr::Keyword_forceinline));
2248  Sema::CapturedParamNameType ParamsTarget[] = {
2249  std::make_pair(StringRef(), QualType()) // __context with shared vars
2250  };
2251  // Start a captured region for 'target' with no implicit parameters.
2252  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2253  ParamsTarget);
2254  Sema::CapturedParamNameType ParamsTeamsOrParallel[] = {
2255  std::make_pair(".global_tid.", KmpInt32PtrTy),
2256  std::make_pair(".bound_tid.", KmpInt32PtrTy),
2257  std::make_pair(StringRef(), QualType()) // __context with shared vars
2258  };
2259  // Start a captured region for 'teams' or 'parallel'. Both regions have
2260  // the same implicit parameters.
2261  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2262  ParamsTeamsOrParallel);
2263  break;
2264  }
2265  case OMPD_target:
2266  case OMPD_target_simd: {
2267  QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
2268  QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
2269  QualType KmpInt32PtrTy =
2270  Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
2271  QualType Args[] = {VoidPtrTy};
2273  EPI.Variadic = true;
2274  QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
2275  Sema::CapturedParamNameType Params[] = {
2276  std::make_pair(".global_tid.", KmpInt32Ty),
2277  std::make_pair(".part_id.", KmpInt32PtrTy),
2278  std::make_pair(".privates.", VoidPtrTy),
2279  std::make_pair(
2280  ".copy_fn.",
2281  Context.getPointerType(CopyFnType).withConst().withRestrict()),
2282  std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
2283  std::make_pair(StringRef(), QualType()) // __context with shared vars
2284  };
2285  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2286  Params);
2287  // Mark this captured region as inlined, because we don't use outlined
2288  // function directly.
2289  getCurCapturedRegion()->TheCapturedDecl->addAttr(
2290  AlwaysInlineAttr::CreateImplicit(
2291  Context, AlwaysInlineAttr::Keyword_forceinline));
2292  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2293  std::make_pair(StringRef(), QualType()));
2294  break;
2295  }
2296  case OMPD_simd:
2297  case OMPD_for:
2298  case OMPD_for_simd:
2299  case OMPD_sections:
2300  case OMPD_section:
2301  case OMPD_single:
2302  case OMPD_master:
2303  case OMPD_critical:
2304  case OMPD_taskgroup:
2305  case OMPD_distribute:
2306  case OMPD_distribute_simd:
2307  case OMPD_ordered:
2308  case OMPD_atomic:
2309  case OMPD_target_data: {
2310  Sema::CapturedParamNameType Params[] = {
2311  std::make_pair(StringRef(), QualType()) // __context with shared vars
2312  };
2313  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2314  Params);
2315  break;
2316  }
2317  case OMPD_task: {
2318  QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
2319  QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
2320  QualType KmpInt32PtrTy =
2321  Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
2322  QualType Args[] = {VoidPtrTy};
2324  EPI.Variadic = true;
2325  QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
2326  Sema::CapturedParamNameType Params[] = {
2327  std::make_pair(".global_tid.", KmpInt32Ty),
2328  std::make_pair(".part_id.", KmpInt32PtrTy),
2329  std::make_pair(".privates.", VoidPtrTy),
2330  std::make_pair(
2331  ".copy_fn.",
2332  Context.getPointerType(CopyFnType).withConst().withRestrict()),
2333  std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
2334  std::make_pair(StringRef(), QualType()) // __context with shared vars
2335  };
2336  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2337  Params);
2338  // Mark this captured region as inlined, because we don't use outlined
2339  // function directly.
2340  getCurCapturedRegion()->TheCapturedDecl->addAttr(
2341  AlwaysInlineAttr::CreateImplicit(
2342  Context, AlwaysInlineAttr::Keyword_forceinline));
2343  break;
2344  }
2345  case OMPD_taskloop:
2346  case OMPD_taskloop_simd: {
2347  QualType KmpInt32Ty =
2348  Context.getIntTypeForBitwidth(/*DestWidth=*/32, /*Signed=*/1)
2349  .withConst();
2350  QualType KmpUInt64Ty =
2351  Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/0)
2352  .withConst();
2353  QualType KmpInt64Ty =
2354  Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/1)
2355  .withConst();
2356  QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
2357  QualType KmpInt32PtrTy =
2358  Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
2359  QualType Args[] = {VoidPtrTy};
2361  EPI.Variadic = true;
2362  QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
2363  Sema::CapturedParamNameType Params[] = {
2364  std::make_pair(".global_tid.", KmpInt32Ty),
2365  std::make_pair(".part_id.", KmpInt32PtrTy),
2366  std::make_pair(".privates.", VoidPtrTy),
2367  std::make_pair(
2368  ".copy_fn.",
2369  Context.getPointerType(CopyFnType).withConst().withRestrict()),
2370  std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
2371  std::make_pair(".lb.", KmpUInt64Ty),
2372  std::make_pair(".ub.", KmpUInt64Ty),
2373  std::make_pair(".st.", KmpInt64Ty),
2374  std::make_pair(".liter.", KmpInt32Ty),
2375  std::make_pair(".reductions.", VoidPtrTy),
2376  std::make_pair(StringRef(), QualType()) // __context with shared vars
2377  };
2378  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2379  Params);
2380  // Mark this captured region as inlined, because we don't use outlined
2381  // function directly.
2382  getCurCapturedRegion()->TheCapturedDecl->addAttr(
2383  AlwaysInlineAttr::CreateImplicit(
2384  Context, AlwaysInlineAttr::Keyword_forceinline));
2385  break;
2386  }
2387  case OMPD_distribute_parallel_for_simd:
2388  case OMPD_distribute_parallel_for: {
2389  QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
2390  QualType KmpInt32PtrTy =
2391  Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
2392  Sema::CapturedParamNameType Params[] = {
2393  std::make_pair(".global_tid.", KmpInt32PtrTy),
2394  std::make_pair(".bound_tid.", KmpInt32PtrTy),
2395  std::make_pair(".previous.lb.", Context.getSizeType().withConst()),
2396  std::make_pair(".previous.ub.", Context.getSizeType().withConst()),
2397  std::make_pair(StringRef(), QualType()) // __context with shared vars
2398  };
2399  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2400  Params);
2401  break;
2402  }
2403  case OMPD_target_teams_distribute_parallel_for:
2404  case OMPD_target_teams_distribute_parallel_for_simd: {
2405  QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
2406  QualType KmpInt32PtrTy =
2407  Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
2408  QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
2409 
2410  QualType Args[] = {VoidPtrTy};
2412  EPI.Variadic = true;
2413  QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
2414  Sema::CapturedParamNameType Params[] = {
2415  std::make_pair(".global_tid.", KmpInt32Ty),
2416  std::make_pair(".part_id.", KmpInt32PtrTy),
2417  std::make_pair(".privates.", VoidPtrTy),
2418  std::make_pair(
2419  ".copy_fn.",
2420  Context.getPointerType(CopyFnType).withConst().withRestrict()),
2421  std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
2422  std::make_pair(StringRef(), QualType()) // __context with shared vars
2423  };
2424  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2425  Params);
2426  // Mark this captured region as inlined, because we don't use outlined
2427  // function directly.
2428  getCurCapturedRegion()->TheCapturedDecl->addAttr(
2429  AlwaysInlineAttr::CreateImplicit(
2430  Context, AlwaysInlineAttr::Keyword_forceinline));
2431  Sema::CapturedParamNameType ParamsTarget[] = {
2432  std::make_pair(StringRef(), QualType()) // __context with shared vars
2433  };
2434  // Start a captured region for 'target' with no implicit parameters.
2435  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2436  ParamsTarget);
2437 
2438  Sema::CapturedParamNameType ParamsTeams[] = {
2439  std::make_pair(".global_tid.", KmpInt32PtrTy),
2440  std::make_pair(".bound_tid.", KmpInt32PtrTy),
2441  std::make_pair(StringRef(), QualType()) // __context with shared vars
2442  };
2443  // Start a captured region for 'target' with no implicit parameters.
2444  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2445  ParamsTeams);
2446 
2447  Sema::CapturedParamNameType ParamsParallel[] = {
2448  std::make_pair(".global_tid.", KmpInt32PtrTy),
2449  std::make_pair(".bound_tid.", KmpInt32PtrTy),
2450  std::make_pair(".previous.lb.", Context.getSizeType().withConst()),
2451  std::make_pair(".previous.ub.", Context.getSizeType().withConst()),
2452  std::make_pair(StringRef(), QualType()) // __context with shared vars
2453  };
2454  // Start a captured region for 'teams' or 'parallel'. Both regions have
2455  // the same implicit parameters.
2456  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2457  ParamsParallel);
2458  break;
2459  }
2460 
2461  case OMPD_teams_distribute_parallel_for:
2462  case OMPD_teams_distribute_parallel_for_simd: {
2463  QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
2464  QualType KmpInt32PtrTy =
2465  Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
2466 
2467  Sema::CapturedParamNameType ParamsTeams[] = {
2468  std::make_pair(".global_tid.", KmpInt32PtrTy),
2469  std::make_pair(".bound_tid.", KmpInt32PtrTy),
2470  std::make_pair(StringRef(), QualType()) // __context with shared vars
2471  };
2472  // Start a captured region for 'target' with no implicit parameters.
2473  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2474  ParamsTeams);
2475 
2476  Sema::CapturedParamNameType ParamsParallel[] = {
2477  std::make_pair(".global_tid.", KmpInt32PtrTy),
2478  std::make_pair(".bound_tid.", KmpInt32PtrTy),
2479  std::make_pair(".previous.lb.", Context.getSizeType().withConst()),
2480  std::make_pair(".previous.ub.", Context.getSizeType().withConst()),
2481  std::make_pair(StringRef(), QualType()) // __context with shared vars
2482  };
2483  // Start a captured region for 'teams' or 'parallel'. Both regions have
2484  // the same implicit parameters.
2485  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2486  ParamsParallel);
2487  break;
2488  }
2489  case OMPD_target_update:
2490  case OMPD_target_enter_data:
2491  case OMPD_target_exit_data: {
2492  QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
2493  QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
2494  QualType KmpInt32PtrTy =
2495  Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
2496  QualType Args[] = {VoidPtrTy};
2498  EPI.Variadic = true;
2499  QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
2500  Sema::CapturedParamNameType Params[] = {
2501  std::make_pair(".global_tid.", KmpInt32Ty),
2502  std::make_pair(".part_id.", KmpInt32PtrTy),
2503  std::make_pair(".privates.", VoidPtrTy),
2504  std::make_pair(
2505  ".copy_fn.",
2506  Context.getPointerType(CopyFnType).withConst().withRestrict()),
2507  std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
2508  std::make_pair(StringRef(), QualType()) // __context with shared vars
2509  };
2510  ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
2511  Params);
2512  // Mark this captured region as inlined, because we don't use outlined
2513  // function directly.
2514  getCurCapturedRegion()->TheCapturedDecl->addAttr(
2515  AlwaysInlineAttr::CreateImplicit(
2516  Context, AlwaysInlineAttr::Keyword_forceinline));
2517  break;
2518  }
2519  case OMPD_threadprivate:
2520  case OMPD_taskyield:
2521  case OMPD_barrier:
2522  case OMPD_taskwait:
2523  case OMPD_cancellation_point:
2524  case OMPD_cancel:
2525  case OMPD_flush:
2526  case OMPD_declare_reduction:
2527  case OMPD_declare_simd:
2528  case OMPD_declare_target:
2529  case OMPD_end_declare_target:
2530  llvm_unreachable("OpenMP Directive is not allowed");
2531  case OMPD_unknown:
2532  llvm_unreachable("Unknown OpenMP directive");
2533  }
2534 }
2535 
2537  SmallVector<OpenMPDirectiveKind, 4> CaptureRegions;
2538  getOpenMPCaptureRegions(CaptureRegions, DKind);
2539  return CaptureRegions.size();
2540 }
2541 
2543  Expr *CaptureExpr, bool WithInit,
2544  bool AsExpression) {
2545  assert(CaptureExpr);
2546  ASTContext &C = S.getASTContext();
2547  Expr *Init = AsExpression ? CaptureExpr : CaptureExpr->IgnoreImpCasts();
2548  QualType Ty = Init->getType();
2549  if (CaptureExpr->getObjectKind() == OK_Ordinary && CaptureExpr->isGLValue()) {
2550  if (S.getLangOpts().CPlusPlus) {
2551  Ty = C.getLValueReferenceType(Ty);
2552  } else {
2553  Ty = C.getPointerType(Ty);
2554  ExprResult Res =
2555  S.CreateBuiltinUnaryOp(CaptureExpr->getExprLoc(), UO_AddrOf, Init);
2556  if (!Res.isUsable())
2557  return nullptr;
2558  Init = Res.get();
2559  }
2560  WithInit = true;
2561  }
2562  auto *CED = OMPCapturedExprDecl::Create(C, S.CurContext, Id, Ty,
2563  CaptureExpr->getLocStart());
2564  if (!WithInit)
2565  CED->addAttr(OMPCaptureNoInitAttr::CreateImplicit(C));
2566  S.CurContext->addHiddenDecl(CED);
2567  S.AddInitializerToDecl(CED, Init, /*DirectInit=*/false);
2568  return CED;
2569 }
2570 
2571 static DeclRefExpr *buildCapture(Sema &S, ValueDecl *D, Expr *CaptureExpr,
2572  bool WithInit) {
2573  OMPCapturedExprDecl *CD;
2574  if (VarDecl *VD = S.isOpenMPCapturedDecl(D))
2575  CD = cast<OMPCapturedExprDecl>(VD);
2576  else
2577  CD = buildCaptureDecl(S, D->getIdentifier(), CaptureExpr, WithInit,
2578  /*AsExpression=*/false);
2579  return buildDeclRefExpr(S, CD, CD->getType().getNonReferenceType(),
2580  CaptureExpr->getExprLoc());
2581 }
2582 
2583 static ExprResult buildCapture(Sema &S, Expr *CaptureExpr, DeclRefExpr *&Ref) {
2584  CaptureExpr = S.DefaultLvalueConversion(CaptureExpr).get();
2585  if (!Ref) {
2587  S, &S.getASTContext().Idents.get(".capture_expr."), CaptureExpr,
2588  /*WithInit=*/true, /*AsExpression=*/true);
2589  Ref = buildDeclRefExpr(S, CD, CD->getType().getNonReferenceType(),
2590  CaptureExpr->getExprLoc());
2591  }
2592  ExprResult Res = Ref;
2593  if (!S.getLangOpts().CPlusPlus &&
2594  CaptureExpr->getObjectKind() == OK_Ordinary && CaptureExpr->isGLValue() &&
2595  Ref->getType()->isPointerType()) {
2596  Res = S.CreateBuiltinUnaryOp(CaptureExpr->getExprLoc(), UO_Deref, Ref);
2597  if (!Res.isUsable())
2598  return ExprError();
2599  }
2600  return S.DefaultLvalueConversion(Res.get());
2601 }
2602 
2603 namespace {
2604 // OpenMP directives parsed in this section are represented as a
2605 // CapturedStatement with an associated statement. If a syntax error
2606 // is detected during the parsing of the associated statement, the
2607 // compiler must abort processing and close the CapturedStatement.
2608 //
2609 // Combined directives such as 'target parallel' have more than one
2610 // nested CapturedStatements. This RAII ensures that we unwind out
2611 // of all the nested CapturedStatements when an error is found.
2612 class CaptureRegionUnwinderRAII {
2613 private:
2614  Sema &S;
2615  bool &ErrorFound;
2617 
2618 public:
2619  CaptureRegionUnwinderRAII(Sema &S, bool &ErrorFound,
2620  OpenMPDirectiveKind DKind)
2621  : S(S), ErrorFound(ErrorFound), DKind(DKind) {}
2622  ~CaptureRegionUnwinderRAII() {
2623  if (ErrorFound) {
2624  int ThisCaptureLevel = S.getOpenMPCaptureLevels(DKind);
2625  while (--ThisCaptureLevel >= 0)
2627  }
2628  }
2629 };
2630 } // namespace
2631 
2633  ArrayRef<OMPClause *> Clauses) {
2634  bool ErrorFound = false;
2635  CaptureRegionUnwinderRAII CaptureRegionUnwinder(
2636  *this, ErrorFound, DSAStack->getCurrentDirective());
2637  if (!S.isUsable()) {
2638  ErrorFound = true;
2639  return StmtError();
2640  }
2641 
2642  SmallVector<OpenMPDirectiveKind, 4> CaptureRegions;
2643  getOpenMPCaptureRegions(CaptureRegions, DSAStack->getCurrentDirective());
2644  OMPOrderedClause *OC = nullptr;
2645  OMPScheduleClause *SC = nullptr;
2648  // This is required for proper codegen.
2649  for (OMPClause *Clause : Clauses) {
2650  if (isOpenMPTaskingDirective(DSAStack->getCurrentDirective()) &&
2651  Clause->getClauseKind() == OMPC_in_reduction) {
2652  // Capture taskgroup task_reduction descriptors inside the tasking regions
2653  // with the corresponding in_reduction items.
2654  auto *IRC = cast<OMPInReductionClause>(Clause);
2655  for (Expr *E : IRC->taskgroup_descriptors())
2656  if (E)
2657  MarkDeclarationsReferencedInExpr(E);
2658  }
2659  if (isOpenMPPrivate(Clause->getClauseKind()) ||
2660  Clause->getClauseKind() == OMPC_copyprivate ||
2661  (getLangOpts().OpenMPUseTLS &&
2662  getASTContext().getTargetInfo().isTLSSupported() &&
2663  Clause->getClauseKind() == OMPC_copyin)) {
2664  DSAStack->setForceVarCapturing(Clause->getClauseKind() == OMPC_copyin);
2665  // Mark all variables in private list clauses as used in inner region.
2666  for (Stmt *VarRef : Clause->children()) {
2667  if (auto *E = cast_or_null<Expr>(VarRef)) {
2668  MarkDeclarationsReferencedInExpr(E);
2669  }
2670  }
2671  DSAStack->setForceVarCapturing(/*V=*/false);
2672  } else if (CaptureRegions.size() > 1 ||
2673  CaptureRegions.back() != OMPD_unknown) {
2674  if (auto *C = OMPClauseWithPreInit::get(Clause))
2675  PICs.push_back(C);
2676  if (auto *C = OMPClauseWithPostUpdate::get(Clause)) {
2677  if (Expr *E = C->getPostUpdateExpr())
2678  MarkDeclarationsReferencedInExpr(E);
2679  }
2680  }
2681  if (Clause->getClauseKind() == OMPC_schedule)
2682  SC = cast<OMPScheduleClause>(Clause);
2683  else if (Clause->getClauseKind() == OMPC_ordered)
2684  OC = cast<OMPOrderedClause>(Clause);
2685  else if (Clause->getClauseKind() == OMPC_linear)
2686  LCs.push_back(cast<OMPLinearClause>(Clause));
2687  }
2688  // OpenMP, 2.7.1 Loop Construct, Restrictions
2689  // The nonmonotonic modifier cannot be specified if an ordered clause is
2690  // specified.
2691  if (SC &&
2692  (SC->getFirstScheduleModifier() == OMPC_SCHEDULE_MODIFIER_nonmonotonic ||
2693  SC->getSecondScheduleModifier() ==
2694  OMPC_SCHEDULE_MODIFIER_nonmonotonic) &&
2695  OC) {
2696  Diag(SC->getFirstScheduleModifier() == OMPC_SCHEDULE_MODIFIER_nonmonotonic
2699  diag::err_omp_schedule_nonmonotonic_ordered)
2700  << SourceRange(OC->getLocStart(), OC->getLocEnd());
2701  ErrorFound = true;
2702  }
2703  if (!LCs.empty() && OC && OC->getNumForLoops()) {
2704  for (const OMPLinearClause *C : LCs) {
2705  Diag(C->getLocStart(), diag::err_omp_linear_ordered)
2706  << SourceRange(OC->getLocStart(), OC->getLocEnd());
2707  }
2708  ErrorFound = true;
2709  }
2710  if (isOpenMPWorksharingDirective(DSAStack->getCurrentDirective()) &&
2711  isOpenMPSimdDirective(DSAStack->getCurrentDirective()) && OC &&
2712  OC->getNumForLoops()) {
2713  Diag(OC->getLocStart(), diag::err_omp_ordered_simd)
2714  << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
2715  ErrorFound = true;
2716  }
2717  if (ErrorFound) {
2718  return StmtError();
2719  }
2720  StmtResult SR = S;
2721  for (OpenMPDirectiveKind ThisCaptureRegion : llvm::reverse(CaptureRegions)) {
2722  // Mark all variables in private list clauses as used in inner region.
2723  // Required for proper codegen of combined directives.
2724  // TODO: add processing for other clauses.
2725  if (ThisCaptureRegion != OMPD_unknown) {
2726  for (const clang::OMPClauseWithPreInit *C : PICs) {
2727  OpenMPDirectiveKind CaptureRegion = C->getCaptureRegion();
2728  // Find the particular capture region for the clause if the
2729  // directive is a combined one with multiple capture regions.
2730  // If the directive is not a combined one, the capture region
2731  // associated with the clause is OMPD_unknown and is generated
2732  // only once.
2733  if (CaptureRegion == ThisCaptureRegion ||
2734  CaptureRegion == OMPD_unknown) {
2735  if (auto *DS = cast_or_null<DeclStmt>(C->getPreInitStmt())) {
2736  for (Decl *D : DS->decls())
2737  MarkVariableReferenced(D->getLocation(), cast<VarDecl>(D));
2738  }
2739  }
2740  }
2741  }
2742  SR = ActOnCapturedRegionEnd(SR.get());
2743  }
2744  return SR;
2745 }
2746 
2747 static bool checkCancelRegion(Sema &SemaRef, OpenMPDirectiveKind CurrentRegion,
2748  OpenMPDirectiveKind CancelRegion,
2749  SourceLocation StartLoc) {
2750  // CancelRegion is only needed for cancel and cancellation_point.
2751  if (CurrentRegion != OMPD_cancel && CurrentRegion != OMPD_cancellation_point)
2752  return false;
2753 
2754  if (CancelRegion == OMPD_parallel || CancelRegion == OMPD_for ||
2755  CancelRegion == OMPD_sections || CancelRegion == OMPD_taskgroup)
2756  return false;
2757 
2758  SemaRef.Diag(StartLoc, diag::err_omp_wrong_cancel_region)
2759  << getOpenMPDirectiveName(CancelRegion);
2760  return true;
2761 }
2762 
2763 static bool checkNestingOfRegions(Sema &SemaRef, const DSAStackTy *Stack,
2764  OpenMPDirectiveKind CurrentRegion,
2765  const DeclarationNameInfo &CurrentName,
2766  OpenMPDirectiveKind CancelRegion,
2767  SourceLocation StartLoc) {
2768  if (Stack->getCurScope()) {
2769  OpenMPDirectiveKind ParentRegion = Stack->getParentDirective();
2770  OpenMPDirectiveKind OffendingRegion = ParentRegion;
2771  bool NestingProhibited = false;
2772  bool CloseNesting = true;
2773  bool OrphanSeen = false;
2774  enum {
2775  NoRecommend,
2776  ShouldBeInParallelRegion,
2777  ShouldBeInOrderedRegion,
2778  ShouldBeInTargetRegion,
2779  ShouldBeInTeamsRegion
2780  } Recommend = NoRecommend;
2781  if (isOpenMPSimdDirective(ParentRegion) && CurrentRegion != OMPD_ordered) {
2782  // OpenMP [2.16, Nesting of Regions]
2783  // OpenMP constructs may not be nested inside a simd region.
2784  // OpenMP [2.8.1,simd Construct, Restrictions]
2785  // An ordered construct with the simd clause is the only OpenMP
2786  // construct that can appear in the simd region.
2787  // Allowing a SIMD construct nested in another SIMD construct is an
2788  // extension. The OpenMP 4.5 spec does not allow it. Issue a warning
2789  // message.
2790  SemaRef.Diag(StartLoc, (CurrentRegion != OMPD_simd)
2791  ? diag::err_omp_prohibited_region_simd
2792  : diag::warn_omp_nesting_simd);
2793  return CurrentRegion != OMPD_simd;
2794  }
2795  if (ParentRegion == OMPD_atomic) {
2796  // OpenMP [2.16, Nesting of Regions]
2797  // OpenMP constructs may not be nested inside an atomic region.
2798  SemaRef.Diag(StartLoc, diag::err_omp_prohibited_region_atomic);
2799  return true;
2800  }
2801  if (CurrentRegion == OMPD_section) {
2802  // OpenMP [2.7.2, sections Construct, Restrictions]
2803  // Orphaned section directives are prohibited. That is, the section
2804  // directives must appear within the sections construct and must not be
2805  // encountered elsewhere in the sections region.
2806  if (ParentRegion != OMPD_sections &&
2807  ParentRegion != OMPD_parallel_sections) {
2808  SemaRef.Diag(StartLoc, diag::err_omp_orphaned_section_directive)
2809  << (ParentRegion != OMPD_unknown)
2810  << getOpenMPDirectiveName(ParentRegion);
2811  return true;
2812  }
2813  return false;
2814  }
2815  // Allow some constructs (except teams) to be orphaned (they could be
2816  // used in functions, called from OpenMP regions with the required
2817  // preconditions).
2818  if (ParentRegion == OMPD_unknown &&
2819  !isOpenMPNestingTeamsDirective(CurrentRegion))
2820  return false;
2821  if (CurrentRegion == OMPD_cancellation_point ||
2822  CurrentRegion == OMPD_cancel) {
2823  // OpenMP [2.16, Nesting of Regions]
2824  // A cancellation point construct for which construct-type-clause is
2825  // taskgroup must be nested inside a task construct. A cancellation
2826  // point construct for which construct-type-clause is not taskgroup must
2827  // be closely nested inside an OpenMP construct that matches the type
2828  // specified in construct-type-clause.
2829  // A cancel construct for which construct-type-clause is taskgroup must be
2830  // nested inside a task construct. A cancel construct for which
2831  // construct-type-clause is not taskgroup must be closely nested inside an
2832  // OpenMP construct that matches the type specified in
2833  // construct-type-clause.
2834  NestingProhibited =
2835  !((CancelRegion == OMPD_parallel &&
2836  (ParentRegion == OMPD_parallel ||
2837  ParentRegion == OMPD_target_parallel)) ||
2838  (CancelRegion == OMPD_for &&
2839  (ParentRegion == OMPD_for || ParentRegion == OMPD_parallel_for ||
2840  ParentRegion == OMPD_target_parallel_for ||
2841  ParentRegion == OMPD_distribute_parallel_for ||
2842  ParentRegion == OMPD_teams_distribute_parallel_for ||
2843  ParentRegion == OMPD_target_teams_distribute_parallel_for)) ||
2844  (CancelRegion == OMPD_taskgroup && ParentRegion == OMPD_task) ||
2845  (CancelRegion == OMPD_sections &&
2846  (ParentRegion == OMPD_section || ParentRegion == OMPD_sections ||
2847  ParentRegion == OMPD_parallel_sections)));
2848  } else if (CurrentRegion == OMPD_master) {
2849  // OpenMP [2.16, Nesting of Regions]
2850  // A master region may not be closely nested inside a worksharing,
2851  // atomic, or explicit task region.
2852  NestingProhibited = isOpenMPWorksharingDirective(ParentRegion) ||
2853  isOpenMPTaskingDirective(ParentRegion);
2854  } else if (CurrentRegion == OMPD_critical && CurrentName.getName()) {
2855  // OpenMP [2.16, Nesting of Regions]
2856  // A critical region may not be nested (closely or otherwise) inside a
2857  // critical region with the same name. Note that this restriction is not
2858  // sufficient to prevent deadlock.
2859  SourceLocation PreviousCriticalLoc;
2860  bool DeadLock = Stack->hasDirective(
2861  [CurrentName, &PreviousCriticalLoc](OpenMPDirectiveKind K,
2862  const DeclarationNameInfo &DNI,
2863  SourceLocation Loc) {
2864  if (K == OMPD_critical && DNI.getName() == CurrentName.getName()) {
2865  PreviousCriticalLoc = Loc;
2866  return true;
2867  }
2868  return false;
2869  },
2870  false /* skip top directive */);
2871  if (DeadLock) {
2872  SemaRef.Diag(StartLoc,
2873  diag::err_omp_prohibited_region_critical_same_name)
2874  << CurrentName.getName();
2875  if (PreviousCriticalLoc.isValid())
2876  SemaRef.Diag(PreviousCriticalLoc,
2877  diag::note_omp_previous_critical_region);
2878  return true;
2879  }
2880  } else if (CurrentRegion == OMPD_barrier) {
2881  // OpenMP [2.16, Nesting of Regions]
2882  // A barrier region may not be closely nested inside a worksharing,
2883  // explicit task, critical, ordered, atomic, or master region.
2884  NestingProhibited = isOpenMPWorksharingDirective(ParentRegion) ||
2885  isOpenMPTaskingDirective(ParentRegion) ||
2886  ParentRegion == OMPD_master ||
2887  ParentRegion == OMPD_critical ||
2888  ParentRegion == OMPD_ordered;
2889  } else if (isOpenMPWorksharingDirective(CurrentRegion) &&
2890  !isOpenMPParallelDirective(CurrentRegion) &&
2891  !isOpenMPTeamsDirective(CurrentRegion)) {
2892  // OpenMP [2.16, Nesting of Regions]
2893  // A worksharing region may not be closely nested inside a worksharing,
2894  // explicit task, critical, ordered, atomic, or master region.
2895  NestingProhibited = isOpenMPWorksharingDirective(ParentRegion) ||
2896  isOpenMPTaskingDirective(ParentRegion) ||
2897  ParentRegion == OMPD_master ||
2898  ParentRegion == OMPD_critical ||
2899  ParentRegion == OMPD_ordered;
2900  Recommend = ShouldBeInParallelRegion;
2901  } else if (CurrentRegion == OMPD_ordered) {
2902  // OpenMP [2.16, Nesting of Regions]
2903  // An ordered region may not be closely nested inside a critical,
2904  // atomic, or explicit task region.
2905  // An ordered region must be closely nested inside a loop region (or
2906  // parallel loop region) with an ordered clause.
2907  // OpenMP [2.8.1,simd Construct, Restrictions]
2908  // An ordered construct with the simd clause is the only OpenMP construct
2909  // that can appear in the simd region.
2910  NestingProhibited = ParentRegion == OMPD_critical ||
2911  isOpenMPTaskingDirective(ParentRegion) ||
2912  !(isOpenMPSimdDirective(ParentRegion) ||
2913  Stack->isParentOrderedRegion());
2914  Recommend = ShouldBeInOrderedRegion;
2915  } else if (isOpenMPNestingTeamsDirective(CurrentRegion)) {
2916  // OpenMP [2.16, Nesting of Regions]
2917  // If specified, a teams construct must be contained within a target
2918  // construct.
2919  NestingProhibited = ParentRegion != OMPD_target;
2920  OrphanSeen = ParentRegion == OMPD_unknown;
2921  Recommend = ShouldBeInTargetRegion;
2922  }
2923  if (!NestingProhibited &&
2924  !isOpenMPTargetExecutionDirective(CurrentRegion) &&
2925  !isOpenMPTargetDataManagementDirective(CurrentRegion) &&
2926  (ParentRegion == OMPD_teams || ParentRegion == OMPD_target_teams)) {
2927  // OpenMP [2.16, Nesting of Regions]
2928  // distribute, parallel, parallel sections, parallel workshare, and the
2929  // parallel loop and parallel loop SIMD constructs are the only OpenMP
2930  // constructs that can be closely nested in the teams region.
2931  NestingProhibited = !isOpenMPParallelDirective(CurrentRegion) &&
2932  !isOpenMPDistributeDirective(CurrentRegion);
2933  Recommend = ShouldBeInParallelRegion;
2934  }
2935  if (!NestingProhibited &&
2936  isOpenMPNestingDistributeDirective(CurrentRegion)) {
2937  // OpenMP 4.5 [2.17 Nesting of Regions]
2938  // The region associated with the distribute construct must be strictly
2939  // nested inside a teams region
2940  NestingProhibited =
2941  (ParentRegion != OMPD_teams && ParentRegion != OMPD_target_teams);
2942  Recommend = ShouldBeInTeamsRegion;
2943  }
2944  if (!NestingProhibited &&
2945  (isOpenMPTargetExecutionDirective(CurrentRegion) ||
2946  isOpenMPTargetDataManagementDirective(CurrentRegion))) {
2947  // OpenMP 4.5 [2.17 Nesting of Regions]
2948  // If a target, target update, target data, target enter data, or
2949  // target exit data construct is encountered during execution of a
2950  // target region, the behavior is unspecified.
2951  NestingProhibited = Stack->hasDirective(
2952  [&OffendingRegion](OpenMPDirectiveKind K, const DeclarationNameInfo &,
2953  SourceLocation) {
2955  OffendingRegion = K;
2956  return true;
2957  }
2958  return false;
2959  },
2960  false /* don't skip top directive */);
2961  CloseNesting = false;
2962  }
2963  if (NestingProhibited) {
2964  if (OrphanSeen) {
2965  SemaRef.Diag(StartLoc, diag::err_omp_orphaned_device_directive)
2966  << getOpenMPDirectiveName(CurrentRegion) << Recommend;
2967  } else {
2968  SemaRef.Diag(StartLoc, diag::err_omp_prohibited_region)
2969  << CloseNesting << getOpenMPDirectiveName(OffendingRegion)
2970  << Recommend << getOpenMPDirectiveName(CurrentRegion);
2971  }
2972  return true;
2973  }
2974  }
2975  return false;
2976 }
2977 
2979  ArrayRef<OMPClause *> Clauses,
2980  ArrayRef<OpenMPDirectiveKind> AllowedNameModifiers) {
2981  bool ErrorFound = false;
2982  unsigned NamedModifiersNumber = 0;
2984  OMPD_unknown + 1);
2985  SmallVector<SourceLocation, 4> NameModifierLoc;
2986  for (const OMPClause *C : Clauses) {
2987  if (const auto *IC = dyn_cast_or_null<OMPIfClause>(C)) {
2988  // At most one if clause without a directive-name-modifier can appear on
2989  // the directive.
2990  OpenMPDirectiveKind CurNM = IC->getNameModifier();
2991  if (FoundNameModifiers[CurNM]) {
2992  S.Diag(C->getLocStart(), diag::err_omp_more_one_clause)
2993  << getOpenMPDirectiveName(Kind) << getOpenMPClauseName(OMPC_if)
2994  << (CurNM != OMPD_unknown) << getOpenMPDirectiveName(CurNM);
2995  ErrorFound = true;
2996  } else if (CurNM != OMPD_unknown) {
2997  NameModifierLoc.push_back(IC->getNameModifierLoc());
2998  ++NamedModifiersNumber;
2999  }
3000  FoundNameModifiers[CurNM] = IC;
3001  if (CurNM == OMPD_unknown)
3002  continue;
3003  // Check if the specified name modifier is allowed for the current
3004  // directive.
3005  // At most one if clause with the particular directive-name-modifier can
3006  // appear on the directive.
3007  bool MatchFound = false;
3008  for (auto NM : AllowedNameModifiers) {
3009  if (CurNM == NM) {
3010  MatchFound = true;
3011  break;
3012  }
3013  }
3014  if (!MatchFound) {
3015  S.Diag(IC->getNameModifierLoc(),
3016  diag::err_omp_wrong_if_directive_name_modifier)
3018  ErrorFound = true;
3019  }
3020  }
3021  }
3022  // If any if clause on the directive includes a directive-name-modifier then
3023  // all if clauses on the directive must include a directive-name-modifier.
3024  if (FoundNameModifiers[OMPD_unknown] && NamedModifiersNumber > 0) {
3025  if (NamedModifiersNumber == AllowedNameModifiers.size()) {
3026  S.Diag(FoundNameModifiers[OMPD_unknown]->getLocStart(),
3027  diag::err_omp_no_more_if_clause);
3028  } else {
3029  std::string Values;
3030  std::string Sep(", ");
3031  unsigned AllowedCnt = 0;
3032  unsigned TotalAllowedNum =
3033  AllowedNameModifiers.size() - NamedModifiersNumber;
3034  for (unsigned Cnt = 0, End = AllowedNameModifiers.size(); Cnt < End;
3035  ++Cnt) {
3036  OpenMPDirectiveKind NM = AllowedNameModifiers[Cnt];
3037  if (!FoundNameModifiers[NM]) {
3038  Values += "'";
3039  Values += getOpenMPDirectiveName(NM);
3040  Values += "'";
3041  if (AllowedCnt + 2 == TotalAllowedNum)
3042  Values += " or ";
3043  else if (AllowedCnt + 1 != TotalAllowedNum)
3044  Values += Sep;
3045  ++AllowedCnt;
3046  }
3047  }
3048  S.Diag(FoundNameModifiers[OMPD_unknown]->getCondition()->getLocStart(),
3049  diag::err_omp_unnamed_if_clause)
3050  << (TotalAllowedNum > 1) << Values;
3051  }
3052  for (SourceLocation Loc : NameModifierLoc) {
3053  S.Diag(Loc, diag::note_omp_previous_named_if_clause);
3054  }
3055  ErrorFound = true;
3056  }
3057  return ErrorFound;
3058 }
3059 
3062  OpenMPDirectiveKind CancelRegion, ArrayRef<OMPClause *> Clauses,
3063  Stmt *AStmt, SourceLocation StartLoc, SourceLocation EndLoc) {
3064  StmtResult Res = StmtError();
3065  // First check CancelRegion which is then used in checkNestingOfRegions.
3066  if (checkCancelRegion(*this, Kind, CancelRegion, StartLoc) ||
3067  checkNestingOfRegions(*this, DSAStack, Kind, DirName, CancelRegion,
3068  StartLoc))
3069  return StmtError();
3070 
3071  llvm::SmallVector<OMPClause *, 8> ClausesWithImplicit;
3072  VarsWithInheritedDSAType VarsWithInheritedDSA;
3073  bool ErrorFound = false;
3074  ClausesWithImplicit.append(Clauses.begin(), Clauses.end());
3075  if (AStmt && !CurContext->isDependentContext()) {
3076  assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
3077 
3078  // Check default data sharing attributes for referenced variables.
3079  DSAAttrChecker DSAChecker(DSAStack, *this, cast<CapturedStmt>(AStmt));
3080  int ThisCaptureLevel = getOpenMPCaptureLevels(Kind);
3081  Stmt *S = AStmt;
3082  while (--ThisCaptureLevel >= 0)
3083  S = cast<CapturedStmt>(S)->getCapturedStmt();
3084  DSAChecker.Visit(S);
3085  if (DSAChecker.isErrorFound())
3086  return StmtError();
3087  // Generate list of implicitly defined firstprivate variables.
3088  VarsWithInheritedDSA = DSAChecker.getVarsWithInheritedDSA();
3089 
3090  SmallVector<Expr *, 4> ImplicitFirstprivates(
3091  DSAChecker.getImplicitFirstprivate().begin(),
3092  DSAChecker.getImplicitFirstprivate().end());
3093  SmallVector<Expr *, 4> ImplicitMaps(DSAChecker.getImplicitMap().begin(),
3094  DSAChecker.getImplicitMap().end());
3095  // Mark taskgroup task_reduction descriptors as implicitly firstprivate.
3096  for (OMPClause *C : Clauses) {
3097  if (auto *IRC = dyn_cast<OMPInReductionClause>(C)) {
3098  for (Expr *E : IRC->taskgroup_descriptors())
3099  if (E)
3100  ImplicitFirstprivates.emplace_back(E);
3101  }
3102  }
3103  if (!ImplicitFirstprivates.empty()) {
3104  if (OMPClause *Implicit = ActOnOpenMPFirstprivateClause(
3105  ImplicitFirstprivates, SourceLocation(), SourceLocation(),
3106  SourceLocation())) {
3107  ClausesWithImplicit.push_back(Implicit);
3108  ErrorFound = cast<OMPFirstprivateClause>(Implicit)->varlist_size() !=
3109  ImplicitFirstprivates.size();
3110  } else {
3111  ErrorFound = true;
3112  }
3113  }
3114  if (!ImplicitMaps.empty()) {
3115  if (OMPClause *Implicit = ActOnOpenMPMapClause(
3116  OMPC_MAP_unknown, OMPC_MAP_tofrom, /*IsMapTypeImplicit=*/true,
3117  SourceLocation(), SourceLocation(), ImplicitMaps,
3119  ClausesWithImplicit.emplace_back(Implicit);
3120  ErrorFound |=
3121  cast<OMPMapClause>(Implicit)->varlist_size() != ImplicitMaps.size();
3122  } else {
3123  ErrorFound = true;
3124  }
3125  }
3126  }
3127 
3128  llvm::SmallVector<OpenMPDirectiveKind, 4> AllowedNameModifiers;
3129  switch (Kind) {
3130  case OMPD_parallel:
3131  Res = ActOnOpenMPParallelDirective(ClausesWithImplicit, AStmt, StartLoc,
3132  EndLoc);
3133  AllowedNameModifiers.push_back(OMPD_parallel);
3134  break;
3135  case OMPD_simd:
3136  Res = ActOnOpenMPSimdDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc,
3137  VarsWithInheritedDSA);
3138  break;
3139  case OMPD_for:
3140  Res = ActOnOpenMPForDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc,
3141  VarsWithInheritedDSA);
3142  break;
3143  case OMPD_for_simd:
3144  Res = ActOnOpenMPForSimdDirective(ClausesWithImplicit, AStmt, StartLoc,
3145  EndLoc, VarsWithInheritedDSA);
3146  break;
3147  case OMPD_sections:
3148  Res = ActOnOpenMPSectionsDirective(ClausesWithImplicit, AStmt, StartLoc,
3149  EndLoc);
3150  break;
3151  case OMPD_section:
3152  assert(ClausesWithImplicit.empty() &&
3153  "No clauses are allowed for 'omp section' directive");
3154  Res = ActOnOpenMPSectionDirective(AStmt, StartLoc, EndLoc);
3155  break;
3156  case OMPD_single:
3157  Res = ActOnOpenMPSingleDirective(ClausesWithImplicit, AStmt, StartLoc,
3158  EndLoc);
3159  break;
3160  case OMPD_master:
3161  assert(ClausesWithImplicit.empty() &&
3162  "No clauses are allowed for 'omp master' directive");
3163  Res = ActOnOpenMPMasterDirective(AStmt, StartLoc, EndLoc);
3164  break;
3165  case OMPD_critical:
3166  Res = ActOnOpenMPCriticalDirective(DirName, ClausesWithImplicit, AStmt,
3167  StartLoc, EndLoc);
3168  break;
3169  case OMPD_parallel_for:
3170  Res = ActOnOpenMPParallelForDirective(ClausesWithImplicit, AStmt, StartLoc,
3171  EndLoc, VarsWithInheritedDSA);
3172  AllowedNameModifiers.push_back(OMPD_parallel);
3173  break;
3174  case OMPD_parallel_for_simd:
3175  Res = ActOnOpenMPParallelForSimdDirective(
3176  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3177  AllowedNameModifiers.push_back(OMPD_parallel);
3178  break;
3179  case OMPD_parallel_sections:
3180  Res = ActOnOpenMPParallelSectionsDirective(ClausesWithImplicit, AStmt,
3181  StartLoc, EndLoc);
3182  AllowedNameModifiers.push_back(OMPD_parallel);
3183  break;
3184  case OMPD_task:
3185  Res =
3186  ActOnOpenMPTaskDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc);
3187  AllowedNameModifiers.push_back(OMPD_task);
3188  break;
3189  case OMPD_taskyield:
3190  assert(ClausesWithImplicit.empty() &&
3191  "No clauses are allowed for 'omp taskyield' directive");
3192  assert(AStmt == nullptr &&
3193  "No associated statement allowed for 'omp taskyield' directive");
3194  Res = ActOnOpenMPTaskyieldDirective(StartLoc, EndLoc);
3195  break;
3196  case OMPD_barrier:
3197  assert(ClausesWithImplicit.empty() &&
3198  "No clauses are allowed for 'omp barrier' directive");
3199  assert(AStmt == nullptr &&
3200  "No associated statement allowed for 'omp barrier' directive");
3201  Res = ActOnOpenMPBarrierDirective(StartLoc, EndLoc);
3202  break;
3203  case OMPD_taskwait:
3204  assert(ClausesWithImplicit.empty() &&
3205  "No clauses are allowed for 'omp taskwait' directive");
3206  assert(AStmt == nullptr &&
3207  "No associated statement allowed for 'omp taskwait' directive");
3208  Res = ActOnOpenMPTaskwaitDirective(StartLoc, EndLoc);
3209  break;
3210  case OMPD_taskgroup:
3211  Res = ActOnOpenMPTaskgroupDirective(ClausesWithImplicit, AStmt, StartLoc,
3212  EndLoc);
3213  break;
3214  case OMPD_flush:
3215  assert(AStmt == nullptr &&
3216  "No associated statement allowed for 'omp flush' directive");
3217  Res = ActOnOpenMPFlushDirective(ClausesWithImplicit, StartLoc, EndLoc);
3218  break;
3219  case OMPD_ordered:
3220  Res = ActOnOpenMPOrderedDirective(ClausesWithImplicit, AStmt, StartLoc,
3221  EndLoc);
3222  break;
3223  case OMPD_atomic:
3224  Res = ActOnOpenMPAtomicDirective(ClausesWithImplicit, AStmt, StartLoc,
3225  EndLoc);
3226  break;
3227  case OMPD_teams:
3228  Res =
3229  ActOnOpenMPTeamsDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc);
3230  break;
3231  case OMPD_target:
3232  Res = ActOnOpenMPTargetDirective(ClausesWithImplicit, AStmt, StartLoc,
3233  EndLoc);
3234  AllowedNameModifiers.push_back(OMPD_target);
3235  break;
3236  case OMPD_target_parallel:
3237  Res = ActOnOpenMPTargetParallelDirective(ClausesWithImplicit, AStmt,
3238  StartLoc, EndLoc);
3239  AllowedNameModifiers.push_back(OMPD_target);
3240  AllowedNameModifiers.push_back(OMPD_parallel);
3241  break;
3242  case OMPD_target_parallel_for:
3243  Res = ActOnOpenMPTargetParallelForDirective(
3244  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3245  AllowedNameModifiers.push_back(OMPD_target);
3246  AllowedNameModifiers.push_back(OMPD_parallel);
3247  break;
3248  case OMPD_cancellation_point:
3249  assert(ClausesWithImplicit.empty() &&
3250  "No clauses are allowed for 'omp cancellation point' directive");
3251  assert(AStmt == nullptr && "No associated statement allowed for 'omp "
3252  "cancellation point' directive");
3253  Res = ActOnOpenMPCancellationPointDirective(StartLoc, EndLoc, CancelRegion);
3254  break;
3255  case OMPD_cancel:
3256  assert(AStmt == nullptr &&
3257  "No associated statement allowed for 'omp cancel' directive");
3258  Res = ActOnOpenMPCancelDirective(ClausesWithImplicit, StartLoc, EndLoc,
3259  CancelRegion);
3260  AllowedNameModifiers.push_back(OMPD_cancel);
3261  break;
3262  case OMPD_target_data:
3263  Res = ActOnOpenMPTargetDataDirective(ClausesWithImplicit, AStmt, StartLoc,
3264  EndLoc);
3265  AllowedNameModifiers.push_back(OMPD_target_data);
3266  break;
3267  case OMPD_target_enter_data:
3268  Res = ActOnOpenMPTargetEnterDataDirective(ClausesWithImplicit, StartLoc,
3269  EndLoc, AStmt);
3270  AllowedNameModifiers.push_back(OMPD_target_enter_data);
3271  break;
3272  case OMPD_target_exit_data:
3273  Res = ActOnOpenMPTargetExitDataDirective(ClausesWithImplicit, StartLoc,
3274  EndLoc, AStmt);
3275  AllowedNameModifiers.push_back(OMPD_target_exit_data);
3276  break;
3277  case OMPD_taskloop:
3278  Res = ActOnOpenMPTaskLoopDirective(ClausesWithImplicit, AStmt, StartLoc,
3279  EndLoc, VarsWithInheritedDSA);
3280  AllowedNameModifiers.push_back(OMPD_taskloop);
3281  break;
3282  case OMPD_taskloop_simd:
3283  Res = ActOnOpenMPTaskLoopSimdDirective(ClausesWithImplicit, AStmt, StartLoc,
3284  EndLoc, VarsWithInheritedDSA);
3285  AllowedNameModifiers.push_back(OMPD_taskloop);
3286  break;
3287  case OMPD_distribute:
3288  Res = ActOnOpenMPDistributeDirective(ClausesWithImplicit, AStmt, StartLoc,
3289  EndLoc, VarsWithInheritedDSA);
3290  break;
3291  case OMPD_target_update:
3292  Res = ActOnOpenMPTargetUpdateDirective(ClausesWithImplicit, StartLoc,
3293  EndLoc, AStmt);
3294  AllowedNameModifiers.push_back(OMPD_target_update);
3295  break;
3296  case OMPD_distribute_parallel_for:
3297  Res = ActOnOpenMPDistributeParallelForDirective(
3298  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3299  AllowedNameModifiers.push_back(OMPD_parallel);
3300  break;
3301  case OMPD_distribute_parallel_for_simd:
3302  Res = ActOnOpenMPDistributeParallelForSimdDirective(
3303  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3304  AllowedNameModifiers.push_back(OMPD_parallel);
3305  break;
3306  case OMPD_distribute_simd:
3307  Res = ActOnOpenMPDistributeSimdDirective(
3308  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3309  break;
3310  case OMPD_target_parallel_for_simd:
3311  Res = ActOnOpenMPTargetParallelForSimdDirective(
3312  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3313  AllowedNameModifiers.push_back(OMPD_target);
3314  AllowedNameModifiers.push_back(OMPD_parallel);
3315  break;
3316  case OMPD_target_simd:
3317  Res = ActOnOpenMPTargetSimdDirective(ClausesWithImplicit, AStmt, StartLoc,
3318  EndLoc, VarsWithInheritedDSA);
3319  AllowedNameModifiers.push_back(OMPD_target);
3320  break;
3321  case OMPD_teams_distribute:
3322  Res = ActOnOpenMPTeamsDistributeDirective(
3323  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3324  break;
3325  case OMPD_teams_distribute_simd:
3326  Res = ActOnOpenMPTeamsDistributeSimdDirective(
3327  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3328  break;
3329  case OMPD_teams_distribute_parallel_for_simd:
3330  Res = ActOnOpenMPTeamsDistributeParallelForSimdDirective(
3331  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3332  AllowedNameModifiers.push_back(OMPD_parallel);
3333  break;
3334  case OMPD_teams_distribute_parallel_for:
3335  Res = ActOnOpenMPTeamsDistributeParallelForDirective(
3336  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3337  AllowedNameModifiers.push_back(OMPD_parallel);
3338  break;
3339  case OMPD_target_teams:
3340  Res = ActOnOpenMPTargetTeamsDirective(ClausesWithImplicit, AStmt, StartLoc,
3341  EndLoc);
3342  AllowedNameModifiers.push_back(OMPD_target);
3343  break;
3344  case OMPD_target_teams_distribute:
3345  Res = ActOnOpenMPTargetTeamsDistributeDirective(
3346  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3347  AllowedNameModifiers.push_back(OMPD_target);
3348  break;
3349  case OMPD_target_teams_distribute_parallel_for:
3350  Res = ActOnOpenMPTargetTeamsDistributeParallelForDirective(
3351  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3352  AllowedNameModifiers.push_back(OMPD_target);
3353  AllowedNameModifiers.push_back(OMPD_parallel);
3354  break;
3355  case OMPD_target_teams_distribute_parallel_for_simd:
3356  Res = ActOnOpenMPTargetTeamsDistributeParallelForSimdDirective(
3357  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3358  AllowedNameModifiers.push_back(OMPD_target);
3359  AllowedNameModifiers.push_back(OMPD_parallel);
3360  break;
3361  case OMPD_target_teams_distribute_simd:
3362  Res = ActOnOpenMPTargetTeamsDistributeSimdDirective(
3363  ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
3364  AllowedNameModifiers.push_back(OMPD_target);
3365  break;
3366  case OMPD_declare_target:
3367  case OMPD_end_declare_target:
3368  case OMPD_threadprivate:
3369  case OMPD_declare_reduction:
3370  case OMPD_declare_simd:
3371  llvm_unreachable("OpenMP Directive is not allowed");
3372  case OMPD_unknown:
3373  llvm_unreachable("Unknown OpenMP directive");
3374  }
3375 
3376  for (const auto &P : VarsWithInheritedDSA) {
3377  Diag(P.second->getExprLoc(), diag::err_omp_no_dsa_for_variable)
3378  << P.first << P.second->getSourceRange();
3379  }
3380  ErrorFound = !VarsWithInheritedDSA.empty() || ErrorFound;
3381 
3382  if (!AllowedNameModifiers.empty())
3383  ErrorFound = checkIfClauses(*this, Kind, Clauses, AllowedNameModifiers) ||
3384  ErrorFound;
3385 
3386  if (ErrorFound)
3387  return StmtError();
3388  return Res;
3389 }
3390 
3392  DeclGroupPtrTy DG, OMPDeclareSimdDeclAttr::BranchStateTy BS, Expr *Simdlen,
3393  ArrayRef<Expr *> Uniforms, ArrayRef<Expr *> Aligneds,
3394  ArrayRef<Expr *> Alignments, ArrayRef<Expr *> Linears,
3395  ArrayRef<unsigned> LinModifiers, ArrayRef<Expr *> Steps, SourceRange SR) {
3396  assert(Aligneds.size() == Alignments.size());
3397  assert(Linears.size() == LinModifiers.size());
3398  assert(Linears.size() == Steps.size());
3399  if (!DG || DG.get().isNull())
3400  return DeclGroupPtrTy();
3401 
3402  if (!DG.get().isSingleDecl()) {
3403  Diag(SR.getBegin(), diag::err_omp_single_decl_in_declare_simd);
3404  return DG;
3405  }
3406  Decl *ADecl = DG.get().getSingleDecl();
3407  if (auto *FTD = dyn_cast<FunctionTemplateDecl>(ADecl))
3408  ADecl = FTD->getTemplatedDecl();
3409 
3410  auto *FD = dyn_cast<FunctionDecl>(ADecl);
3411  if (!FD) {
3412  Diag(ADecl->getLocation(), diag::err_omp_function_expected);
3413  return DeclGroupPtrTy();
3414  }
3415 
3416  // OpenMP [2.8.2, declare simd construct, Description]
3417  // The parameter of the simdlen clause must be a constant positive integer
3418  // expression.
3419  ExprResult SL;
3420  if (Simdlen)
3421  SL = VerifyPositiveIntegerConstantInClause(Simdlen, OMPC_simdlen);
3422  // OpenMP [2.8.2, declare simd construct, Description]
3423  // The special this pointer can be used as if was one of the arguments to the
3424  // function in any of the linear, aligned, or uniform clauses.
3425  // The uniform clause declares one or more arguments to have an invariant
3426  // value for all concurrent invocations of the function in the execution of a
3427  // single SIMD loop.
3428  llvm::DenseMap<const Decl *, const Expr *> UniformedArgs;
3429  const Expr *UniformedLinearThis = nullptr;
3430  for (const Expr *E : Uniforms) {
3431  E = E->IgnoreParenImpCasts();
3432  if (const auto *DRE = dyn_cast<DeclRefExpr>(E))
3433  if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl()))
3434  if (FD->getNumParams() > PVD->getFunctionScopeIndex() &&
3435  FD->getParamDecl(PVD->getFunctionScopeIndex())
3436  ->getCanonicalDecl() == PVD->getCanonicalDecl()) {
3437  UniformedArgs.try_emplace(PVD->getCanonicalDecl(), E);
3438  continue;
3439  }
3440  if (isa<CXXThisExpr>(E)) {
3441  UniformedLinearThis = E;
3442  continue;
3443  }
3444  Diag(E->getExprLoc(), diag::err_omp_param_or_this_in_clause)
3445  << FD->getDeclName() << (isa<CXXMethodDecl>(ADecl) ? 1 : 0);
3446  }
3447  // OpenMP [2.8.2, declare simd construct, Description]
3448  // The aligned clause declares that the object to which each list item points
3449  // is aligned to the number of bytes expressed in the optional parameter of
3450  // the aligned clause.
3451  // The special this pointer can be used as if was one of the arguments to the
3452  // function in any of the linear, aligned, or uniform clauses.
3453  // The type of list items appearing in the aligned clause must be array,
3454  // pointer, reference to array, or reference to pointer.
3455  llvm::DenseMap<const Decl *, const Expr *> AlignedArgs;
3456  const Expr *AlignedThis = nullptr;
3457  for (const Expr *E : Aligneds) {
3458  E = E->IgnoreParenImpCasts();
3459  if (const auto *DRE = dyn_cast<DeclRefExpr>(E))
3460  if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl())) {
3461  const VarDecl *CanonPVD = PVD->getCanonicalDecl();
3462  if (FD->getNumParams() > PVD->getFunctionScopeIndex() &&
3463  FD->getParamDecl(PVD->getFunctionScopeIndex())
3464  ->getCanonicalDecl() == CanonPVD) {
3465  // OpenMP [2.8.1, simd construct, Restrictions]
3466  // A list-item cannot appear in more than one aligned clause.
3467  if (AlignedArgs.count(CanonPVD) > 0) {
3468  Diag(E->getExprLoc(), diag::err_omp_aligned_twice)
3469  << 1 << E->getSourceRange();
3470  Diag(AlignedArgs[CanonPVD]->getExprLoc(),
3471  diag::note_omp_explicit_dsa)
3472  << getOpenMPClauseName(OMPC_aligned);
3473  continue;
3474  }
3475  AlignedArgs[CanonPVD] = E;
3476  QualType QTy = PVD->getType()
3477  .getNonReferenceType()
3478  .getUnqualifiedType()
3479  .getCanonicalType();
3480  const Type *Ty = QTy.getTypePtrOrNull();
3481  if (!Ty || (!Ty->isArrayType() && !Ty->isPointerType())) {
3482  Diag(E->getExprLoc(), diag::err_omp_aligned_expected_array_or_ptr)
3483  << QTy << getLangOpts().CPlusPlus << E->getSourceRange();
3484  Diag(PVD->getLocation(), diag::note_previous_decl) << PVD;
3485  }
3486  continue;
3487  }
3488  }
3489  if (isa<CXXThisExpr>(E)) {
3490  if (AlignedThis) {
3491  Diag(E->getExprLoc(), diag::err_omp_aligned_twice)
3492  << 2 << E->getSourceRange();
3493  Diag(AlignedThis->getExprLoc(), diag::note_omp_explicit_dsa)
3494  << getOpenMPClauseName(OMPC_aligned);
3495  }
3496  AlignedThis = E;
3497  continue;
3498  }
3499  Diag(E->getExprLoc(), diag::err_omp_param_or_this_in_clause)
3500  << FD->getDeclName() << (isa<CXXMethodDecl>(ADecl) ? 1 : 0);
3501  }
3502  // The optional parameter of the aligned clause, alignment, must be a constant
3503  // positive integer expression. If no optional parameter is specified,
3504  // implementation-defined default alignments for SIMD instructions on the
3505  // target platforms are assumed.
3506  SmallVector<const Expr *, 4> NewAligns;
3507  for (Expr *E : Alignments) {
3508  ExprResult Align;
3509  if (E)
3510  Align = VerifyPositiveIntegerConstantInClause(E, OMPC_aligned);
3511  NewAligns.push_back(Align.get());
3512  }
3513  // OpenMP [2.8.2, declare simd construct, Description]
3514  // The linear clause declares one or more list items to be private to a SIMD
3515  // lane and to have a linear relationship with respect to the iteration space
3516  // of a loop.
3517  // The special this pointer can be used as if was one of the arguments to the
3518  // function in any of the linear, aligned, or uniform clauses.
3519  // When a linear-step expression is specified in a linear clause it must be
3520  // either a constant integer expression or an integer-typed parameter that is
3521  // specified in a uniform clause on the directive.
3522  llvm::DenseMap<const Decl *, const Expr *> LinearArgs;
3523  const bool IsUniformedThis = UniformedLinearThis != nullptr;
3524  auto MI = LinModifiers.begin();
3525  for (const Expr *E : Linears) {
3526  auto LinKind = static_cast<OpenMPLinearClauseKind>(*MI);
3527  ++MI;
3528  E = E->IgnoreParenImpCasts();
3529  if (const auto *DRE = dyn_cast<DeclRefExpr>(E))
3530  if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl())) {
3531  const VarDecl *CanonPVD = PVD->getCanonicalDecl();
3532  if (FD->getNumParams() > PVD->getFunctionScopeIndex() &&
3533  FD->getParamDecl(PVD->getFunctionScopeIndex())
3534  ->getCanonicalDecl() == CanonPVD) {
3535  // OpenMP [2.15.3.7, linear Clause, Restrictions]
3536  // A list-item cannot appear in more than one linear clause.
3537  if (LinearArgs.count(CanonPVD) > 0) {
3538  Diag(E->getExprLoc(), diag::err_omp_wrong_dsa)
3539  << getOpenMPClauseName(OMPC_linear)
3540  << getOpenMPClauseName(OMPC_linear) << E->getSourceRange();
3541  Diag(LinearArgs[CanonPVD]->getExprLoc(),
3542  diag::note_omp_explicit_dsa)
3543  << getOpenMPClauseName(OMPC_linear);
3544  continue;
3545  }
3546  // Each argument can appear in at most one uniform or linear clause.
3547  if (UniformedArgs.count(CanonPVD) > 0) {
3548  Diag(E->getExprLoc(), diag::err_omp_wrong_dsa)
3549  << getOpenMPClauseName(OMPC_linear)
3551  Diag(UniformedArgs[CanonPVD]->getExprLoc(),
3552  diag::note_omp_explicit_dsa)
3554  continue;
3555  }
3556  LinearArgs[CanonPVD] = E;
3557  if (E->isValueDependent() || E->isTypeDependent() ||
3558  E->isInstantiationDependent() ||
3560  continue;
3561  (void)CheckOpenMPLinearDecl(CanonPVD, E->getExprLoc(), LinKind,
3562  PVD->getOriginalType());
3563  continue;
3564  }
3565  }
3566  if (isa<CXXThisExpr>(E)) {
3567  if (UniformedLinearThis) {
3568  Diag(E->getExprLoc(), diag::err_omp_wrong_dsa)
3569  << getOpenMPClauseName(OMPC_linear)
3570  << getOpenMPClauseName(IsUniformedThis ? OMPC_uniform : OMPC_linear)
3571  << E->getSourceRange();
3572  Diag(UniformedLinearThis->getExprLoc(), diag::note_omp_explicit_dsa)
3573  << getOpenMPClauseName(IsUniformedThis ? OMPC_uniform
3574  : OMPC_linear);
3575  continue;
3576  }
3577  UniformedLinearThis = E;
3578  if (E->isValueDependent() || E->isTypeDependent() ||
3580  continue;
3581  (void)CheckOpenMPLinearDecl(/*D=*/nullptr, E->getExprLoc(), LinKind,
3582  E->getType());
3583  continue;
3584  }
3585  Diag(E->getExprLoc(), diag::err_omp_param_or_this_in_clause)
3586  << FD->getDeclName() << (isa<CXXMethodDecl>(ADecl) ? 1 : 0);
3587  }
3588  Expr *Step = nullptr;
3589  Expr *NewStep = nullptr;
3590  SmallVector<Expr *, 4> NewSteps;
3591  for (Expr *E : Steps) {
3592  // Skip the same step expression, it was checked already.
3593  if (Step == E || !E) {
3594  NewSteps.push_back(E ? NewStep : nullptr);
3595  continue;
3596  }
3597  Step = E;
3598  if (const auto *DRE = dyn_cast<DeclRefExpr>(Step))
3599  if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl())) {
3600  const VarDecl *CanonPVD = PVD->getCanonicalDecl();
3601  if (UniformedArgs.count(CanonPVD) == 0) {
3602  Diag(Step->getExprLoc(), diag::err_omp_expected_uniform_param)
3603  << Step->getSourceRange();
3604  } else if (E->isValueDependent() || E->isTypeDependent() ||
3605  E->isInstantiationDependent() ||
3607  CanonPVD->getType()->hasIntegerRepresentation()) {
3608  NewSteps.push_back(Step);
3609  } else {
3610  Diag(Step->getExprLoc(), diag::err_omp_expected_int_param)
3611  << Step->getSourceRange();
3612  }
3613  continue;
3614  }
3615  NewStep = Step;
3616  if (Step && !Step->isValueDependent() && !Step->isTypeDependent() &&
3617  !Step->isInstantiationDependent() &&
3619  NewStep = PerformOpenMPImplicitIntegerConversion(Step->getExprLoc(), Step)
3620  .get();
3621  if (NewStep)
3622  NewStep = VerifyIntegerConstantExpression(NewStep).get();
3623  }
3624  NewSteps.push_back(NewStep);
3625  }
3626  auto *NewAttr = OMPDeclareSimdDeclAttr::CreateImplicit(
3627  Context, BS, SL.get(), const_cast<Expr **>(Uniforms.data()),
3628  Uniforms.size(), const_cast<Expr **>(Aligneds.data()), Aligneds.size(),
3629  const_cast<Expr **>(NewAligns.data()), NewAligns.size(),
3630  const_cast<Expr **>(Linears.data()), Linears.size(),
3631  const_cast<unsigned *>(LinModifiers.data()), LinModifiers.size(),
3632  NewSteps.data(), NewSteps.size(), SR);
3633  ADecl->addAttr(NewAttr);
3634  return ConvertDeclToDeclGroup(ADecl);
3635 }
3636 
3638  Stmt *AStmt,
3639  SourceLocation StartLoc,
3640  SourceLocation EndLoc) {
3641  if (!AStmt)
3642  return StmtError();
3643 
3644  auto *CS = cast<CapturedStmt>(AStmt);
3645  // 1.2.2 OpenMP Language Terminology
3646  // Structured block - An executable statement with a single entry at the
3647  // top and a single exit at the bottom.
3648  // The point of exit cannot be a branch out of the structured block.
3649  // longjmp() and throw() must not violate the entry/exit criteria.
3650  CS->getCapturedDecl()->setNothrow();
3651 
3652  setFunctionHasBranchProtectedScope();
3653 
3654  return OMPParallelDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
3655  DSAStack->isCancelRegion());
3656 }
3657 
3658 namespace {
3659 /// Helper class for checking canonical form of the OpenMP loops and
3660 /// extracting iteration space of each loop in the loop nest, that will be used
3661 /// for IR generation.
3662 class OpenMPIterationSpaceChecker {
3663  /// Reference to Sema.
3664  Sema &SemaRef;
3665  /// A location for diagnostics (when there is no some better location).
3666  SourceLocation DefaultLoc;
3667  /// A location for diagnostics (when increment is not compatible).
3668  SourceLocation ConditionLoc;
3669  /// A source location for referring to loop init later.
3670  SourceRange InitSrcRange;
3671  /// A source location for referring to condition later.
3672  SourceRange ConditionSrcRange;
3673  /// A source location for referring to increment later.
3674  SourceRange IncrementSrcRange;
3675  /// Loop variable.
3676  ValueDecl *LCDecl = nullptr;
3677  /// Reference to loop variable.
3678  Expr *LCRef = nullptr;
3679  /// Lower bound (initializer for the var).
3680  Expr *LB = nullptr;
3681  /// Upper bound.
3682  Expr *UB = nullptr;
3683  /// Loop step (increment).
3684  Expr *Step = nullptr;
3685  /// This flag is true when condition is one of:
3686  /// Var < UB
3687  /// Var <= UB
3688  /// UB > Var
3689  /// UB >= Var
3690  bool TestIsLessOp = false;
3691  /// This flag is true when condition is strict ( < or > ).
3692  bool TestIsStrictOp = false;
3693  /// This flag is true when step is subtracted on each iteration.
3694  bool SubtractStep = false;
3695 
3696 public:
3697  OpenMPIterationSpaceChecker(Sema &SemaRef, SourceLocation DefaultLoc)
3698  : SemaRef(SemaRef), DefaultLoc(DefaultLoc), ConditionLoc(DefaultLoc) {}
3699  /// Check init-expr for canonical loop form and save loop counter
3700  /// variable - #Var and its initialization value - #LB.
3701  bool checkAndSetInit(Stmt *S, bool EmitDiags = true);
3702  /// Check test-expr for canonical form, save upper-bound (#UB), flags
3703  /// for less/greater and for strict/non-strict comparison.
3704  bool checkAndSetCond(Expr *S);
3705  /// Check incr-expr for canonical loop form and return true if it
3706  /// does not conform, otherwise save loop step (#Step).
3707  bool checkAndSetInc(Expr *S);
3708  /// Return the loop counter variable.
3709  ValueDecl *getLoopDecl() const { return LCDecl; }
3710  /// Return the reference expression to loop counter variable.
3711  Expr *getLoopDeclRefExpr() const { return LCRef; }
3712  /// Source range of the loop init.
3713  SourceRange getInitSrcRange() const { return InitSrcRange; }
3714  /// Source range of the loop condition.
3715  SourceRange getConditionSrcRange() const { return ConditionSrcRange; }
3716  /// Source range of the loop increment.
3717  SourceRange getIncrementSrcRange() const { return IncrementSrcRange; }
3718  /// True if the step should be subtracted.
3719  bool shouldSubtractStep() const { return SubtractStep; }
3720  /// Build the expression to calculate the number of iterations.
3721  Expr *buildNumIterations(
3722  Scope *S, const bool LimitedType,
3723  llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const;
3724  /// Build the precondition expression for the loops.
3725  Expr *
3726  buildPreCond(Scope *S, Expr *Cond,
3727  llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const;
3728  /// Build reference expression to the counter be used for codegen.
3729  DeclRefExpr *
3730  buildCounterVar(llvm::MapVector<const Expr *, DeclRefExpr *> &Captures,
3731  DSAStackTy &DSA) const;
3732  /// Build reference expression to the private counter be used for
3733  /// codegen.
3734  Expr *buildPrivateCounterVar() const;
3735  /// Build initialization of the counter be used for codegen.
3736  Expr *buildCounterInit() const;
3737  /// Build step of the counter be used for codegen.
3738  Expr *buildCounterStep() const;
3739  /// Return true if any expression is dependent.
3740  bool dependent() const;
3741 
3742 private:
3743  /// Check the right-hand side of an assignment in the increment
3744  /// expression.
3745  bool checkAndSetIncRHS(Expr *RHS);
3746  /// Helper to set loop counter variable and its initializer.
3747  bool setLCDeclAndLB(ValueDecl *NewLCDecl, Expr *NewDeclRefExpr, Expr *NewLB);
3748  /// Helper to set upper bound.
3749  bool setUB(Expr *NewUB, bool LessOp, bool StrictOp, SourceRange SR,
3750  SourceLocation SL);
3751  /// Helper to set loop increment.
3752  bool setStep(Expr *NewStep, bool Subtract);
3753 };
3754 
3755 bool OpenMPIterationSpaceChecker::dependent() const {
3756  if (!LCDecl) {
3757  assert(!LB && !UB && !Step);
3758  return false;
3759  }
3760  return LCDecl->getType()->isDependentType() ||
3761  (LB && LB->isValueDependent()) || (UB && UB->isValueDependent()) ||
3762  (Step && Step->isValueDependent());
3763 }
3764 
3765 bool OpenMPIterationSpaceChecker::setLCDeclAndLB(ValueDecl *NewLCDecl,
3766  Expr *NewLCRefExpr,
3767  Expr *NewLB) {
3768  // State consistency checking to ensure correct usage.
3769  assert(LCDecl == nullptr && LB == nullptr && LCRef == nullptr &&
3770  UB == nullptr && Step == nullptr && !TestIsLessOp && !TestIsStrictOp);
3771  if (!NewLCDecl || !NewLB)
3772  return true;
3773  LCDecl = getCanonicalDecl(NewLCDecl);
3774  LCRef = NewLCRefExpr;
3775  if (auto *CE = dyn_cast_or_null<CXXConstructExpr>(NewLB))
3776  if (const CXXConstructorDecl *Ctor = CE->getConstructor())
3777  if ((Ctor->isCopyOrMoveConstructor() ||
3778  Ctor->isConvertingConstructor(/*AllowExplicit=*/false)) &&
3779  CE->getNumArgs() > 0 && CE->getArg(0) != nullptr)
3780  NewLB = CE->getArg(0)->IgnoreParenImpCasts();
3781  LB = NewLB;
3782  return false;
3783 }
3784 
3785 bool OpenMPIterationSpaceChecker::setUB(Expr *NewUB, bool LessOp, bool StrictOp,
3786  SourceRange SR, SourceLocation SL) {
3787  // State consistency checking to ensure correct usage.
3788  assert(LCDecl != nullptr && LB != nullptr && UB == nullptr &&
3789  Step == nullptr && !TestIsLessOp && !TestIsStrictOp);
3790  if (!NewUB)
3791  return true;
3792  UB = NewUB;
3793  TestIsLessOp = LessOp;
3794  TestIsStrictOp = StrictOp;
3795  ConditionSrcRange = SR;
3796  ConditionLoc = SL;
3797  return false;
3798 }
3799 
3800 bool OpenMPIterationSpaceChecker::setStep(Expr *NewStep, bool Subtract) {
3801  // State consistency checking to ensure correct usage.
3802  assert(LCDecl != nullptr && LB != nullptr && Step == nullptr);
3803  if (!NewStep)
3804  return true;
3805  if (!NewStep->isValueDependent()) {
3806  // Check that the step is integer expression.
3807  SourceLocation StepLoc = NewStep->getLocStart();
3809  StepLoc, getExprAsWritten(NewStep));
3810  if (Val.isInvalid())
3811  return true;
3812  NewStep = Val.get();
3813 
3814  // OpenMP [2.6, Canonical Loop Form, Restrictions]
3815  // If test-expr is of form var relational-op b and relational-op is < or
3816  // <= then incr-expr must cause var to increase on each iteration of the
3817  // loop. If test-expr is of form var relational-op b and relational-op is
3818  // > or >= then incr-expr must cause var to decrease on each iteration of
3819  // the loop.
3820  // If test-expr is of form b relational-op var and relational-op is < or
3821  // <= then incr-expr must cause var to decrease on each iteration of the
3822  // loop. If test-expr is of form b relational-op var and relational-op is
3823  // > or >= then incr-expr must cause var to increase on each iteration of
3824  // the loop.
3825  llvm::APSInt Result;
3826  bool IsConstant = NewStep->isIntegerConstantExpr(Result, SemaRef.Context);
3827  bool IsUnsigned = !NewStep->getType()->hasSignedIntegerRepresentation();
3828  bool IsConstNeg =
3829  IsConstant && Result.isSigned() && (Subtract != Result.isNegative());
3830  bool IsConstPos =
3831  IsConstant && Result.isSigned() && (Subtract == Result.isNegative());
3832  bool IsConstZero = IsConstant && !Result.getBoolValue();
3833  if (UB && (IsConstZero ||
3834  (TestIsLessOp ? (IsConstNeg || (IsUnsigned && Subtract))
3835  : (IsConstPos || (IsUnsigned && !Subtract))))) {
3836  SemaRef.Diag(NewStep->getExprLoc(),
3837  diag::err_omp_loop_incr_not_compatible)
3838  << LCDecl << TestIsLessOp << NewStep->getSourceRange();
3839  SemaRef.Diag(ConditionLoc,
3840  diag::note_omp_loop_cond_requres_compatible_incr)
3841  << TestIsLessOp << ConditionSrcRange;
3842  return true;
3843  }
3844  if (TestIsLessOp == Subtract) {
3845  NewStep =
3846  SemaRef.CreateBuiltinUnaryOp(NewStep->getExprLoc(), UO_Minus, NewStep)
3847  .get();
3848  Subtract = !Subtract;
3849  }
3850  }
3851 
3852  Step = NewStep;
3853  SubtractStep = Subtract;
3854  return false;
3855 }
3856 
3857 bool OpenMPIterationSpaceChecker::checkAndSetInit(Stmt *S, bool EmitDiags) {
3858  // Check init-expr for canonical loop form and save loop counter
3859  // variable - #Var and its initialization value - #LB.
3860  // OpenMP [2.6] Canonical loop form. init-expr may be one of the following:
3861  // var = lb
3862  // integer-type var = lb
3863  // random-access-iterator-type var = lb
3864  // pointer-type var = lb
3865  //
3866  if (!S) {
3867  if (EmitDiags) {
3868  SemaRef.Diag(DefaultLoc, diag::err_omp_loop_not_canonical_init);
3869  }
3870  return true;
3871  }
3872  if (auto *ExprTemp = dyn_cast<ExprWithCleanups>(S))
3873  if (!ExprTemp->cleanupsHaveSideEffects())
3874  S = ExprTemp->getSubExpr();
3875 
3876  InitSrcRange = S->getSourceRange();
3877  if (Expr *E = dyn_cast<Expr>(S))
3878  S = E->IgnoreParens();
3879  if (auto *BO = dyn_cast<BinaryOperator>(S)) {
3880  if (BO->getOpcode() == BO_Assign) {
3881  Expr *LHS = BO->getLHS()->IgnoreParens();
3882  if (auto *DRE = dyn_cast<DeclRefExpr>(LHS)) {
3883  if (auto *CED = dyn_cast<OMPCapturedExprDecl>(DRE->getDecl()))
3884  if (auto *ME = dyn_cast<MemberExpr>(getExprAsWritten(CED->getInit())))
3885  return setLCDeclAndLB(ME->getMemberDecl(), ME, BO->getRHS());
3886  return setLCDeclAndLB(DRE->getDecl(), DRE, BO->getRHS());
3887  }
3888  if (auto *ME = dyn_cast<MemberExpr>(LHS)) {
3889  if (ME->isArrow() &&
3890  isa<CXXThisExpr>(ME->getBase()->IgnoreParenImpCasts()))
3891  return setLCDeclAndLB(ME->getMemberDecl(), ME, BO->getRHS());
3892  }
3893  }
3894  } else if (auto *DS = dyn_cast<DeclStmt>(S)) {
3895  if (DS->isSingleDecl()) {
3896  if (auto *Var = dyn_cast_or_null<VarDecl>(DS->getSingleDecl())) {
3897  if (Var->hasInit() && !Var->getType()->isReferenceType()) {
3898  // Accept non-canonical init form here but emit ext. warning.
3899  if (Var->getInitStyle() != VarDecl::CInit && EmitDiags)
3900  SemaRef.Diag(S->getLocStart(),
3901  diag::ext_omp_loop_not_canonical_init)
3902  << S->getSourceRange();
3903  return setLCDeclAndLB(Var, nullptr, Var->getInit());
3904  }
3905  }
3906  }
3907  } else if (auto *CE = dyn_cast<CXXOperatorCallExpr>(S)) {
3908  if (CE->getOperator() == OO_Equal) {
3909  Expr *LHS = CE->getArg(0);
3910  if (auto *DRE = dyn_cast<DeclRefExpr>(LHS)) {
3911  if (auto *CED = dyn_cast<OMPCapturedExprDecl>(DRE->getDecl()))
3912  if (auto *ME = dyn_cast<MemberExpr>(getExprAsWritten(CED->getInit())))
3913  return setLCDeclAndLB(ME->getMemberDecl(), ME, BO->getRHS());
3914  return setLCDeclAndLB(DRE->getDecl(), DRE, CE->getArg(1));
3915  }
3916  if (auto *ME = dyn_cast<MemberExpr>(LHS)) {
3917  if (ME->isArrow() &&
3918  isa<CXXThisExpr>(ME->getBase()->IgnoreParenImpCasts()))
3919  return setLCDeclAndLB(ME->getMemberDecl(), ME, BO->getRHS());
3920  }
3921  }
3922  }
3923 
3924  if (dependent() || SemaRef.CurContext->isDependentContext())
3925  return false;
3926  if (EmitDiags) {
3927  SemaRef.Diag(S->getLocStart(), diag::err_omp_loop_not_canonical_init)
3928  << S->getSourceRange();
3929  }
3930  return true;
3931 }
3932 
3933 /// Ignore parenthesizes, implicit casts, copy constructor and return the
3934 /// variable (which may be the loop variable) if possible.
3935 static const ValueDecl *getInitLCDecl(const Expr *E) {
3936  if (!E)
3937  return nullptr;
3938  E = getExprAsWritten(E);
3939  if (const auto *CE = dyn_cast_or_null<CXXConstructExpr>(E))
3940  if (const CXXConstructorDecl *Ctor = CE->getConstructor())
3941  if ((Ctor->isCopyOrMoveConstructor() ||
3942  Ctor->isConvertingConstructor(/*AllowExplicit=*/false)) &&
3943  CE->getNumArgs() > 0 && CE->getArg(0) != nullptr)
3944  E = CE->getArg(0)->IgnoreParenImpCasts();
3945  if (const auto *DRE = dyn_cast_or_null<DeclRefExpr>(E)) {
3946  if (const auto *VD = dyn_cast<VarDecl>(DRE->getDecl()))
3947  return getCanonicalDecl(VD);
3948  }
3949  if (const auto *ME = dyn_cast_or_null<MemberExpr>(E))
3950  if (ME->isArrow() && isa<CXXThisExpr>(ME->getBase()->IgnoreParenImpCasts()))
3951  return getCanonicalDecl(ME->getMemberDecl());
3952  return nullptr;
3953 }
3954 
3955 bool OpenMPIterationSpaceChecker::checkAndSetCond(Expr *S) {
3956  // Check test-expr for canonical form, save upper-bound UB, flags for
3957  // less/greater and for strict/non-strict comparison.
3958  // OpenMP [2.6] Canonical loop form. Test-expr may be one of the following:
3959  // var relational-op b
3960  // b relational-op var
3961  //
3962  if (!S) {
3963  SemaRef.Diag(DefaultLoc, diag::err_omp_loop_not_canonical_cond) << LCDecl;
3964  return true;
3965  }
3966  S = getExprAsWritten(S);
3967  SourceLocation CondLoc = S->getLocStart();
3968  if (auto *BO = dyn_cast<BinaryOperator>(S)) {
3969  if (BO->isRelationalOp()) {
3970  if (getInitLCDecl(BO->getLHS()) == LCDecl)
3971  return setUB(BO->getRHS(),
3972  (BO->getOpcode() == BO_LT || BO->getOpcode() == BO_LE),
3973  (BO->getOpcode() == BO_LT || BO->getOpcode() == BO_GT),
3974  BO->getSourceRange(), BO->getOperatorLoc());
3975  if (getInitLCDecl(BO->getRHS()) == LCDecl)
3976  return setUB(BO->getLHS(),
3977  (BO->getOpcode() == BO_GT || BO->getOpcode() == BO_GE),
3978  (BO->getOpcode() == BO_LT || BO->getOpcode() == BO_GT),
3979  BO->getSourceRange(), BO->getOperatorLoc());
3980  }
3981  } else if (auto *CE = dyn_cast<CXXOperatorCallExpr>(S)) {
3982  if (CE->getNumArgs() == 2) {
3983  auto Op = CE->getOperator();
3984  switch (Op) {
3985  case OO_Greater:
3986  case OO_GreaterEqual:
3987  case OO_Less:
3988  case OO_LessEqual:
3989  if (getInitLCDecl(CE->getArg(0)) == LCDecl)
3990  return setUB(CE->getArg(1), Op == OO_Less || Op == OO_LessEqual,
3991  Op == OO_Less || Op == OO_Greater, CE->getSourceRange(),
3992  CE->getOperatorLoc());
3993  if (getInitLCDecl(CE->getArg(1)) == LCDecl)
3994  return setUB(CE->getArg(0), Op == OO_Greater || Op == OO_GreaterEqual,
3995  Op == OO_Less || Op == OO_Greater, CE->getSourceRange(),
3996  CE->getOperatorLoc());
3997  break;
3998  default:
3999  break;
4000  }
4001  }
4002  }
4003  if (dependent() || SemaRef.CurContext->isDependentContext())
4004  return false;
4005  SemaRef.Diag(CondLoc, diag::err_omp_loop_not_canonical_cond)
4006  << S->getSourceRange() << LCDecl;
4007  return true;
4008 }
4009 
4010 bool OpenMPIterationSpaceChecker::checkAndSetIncRHS(Expr *RHS) {
4011  // RHS of canonical loop form increment can be:
4012  // var + incr
4013  // incr + var
4014  // var - incr
4015  //
4016  RHS = RHS->IgnoreParenImpCasts();
4017  if (auto *BO = dyn_cast<BinaryOperator>(RHS)) {
4018  if (BO->isAdditiveOp()) {
4019  bool IsAdd = BO->getOpcode() == BO_Add;
4020  if (getInitLCDecl(BO->getLHS()) == LCDecl)
4021  return setStep(BO->getRHS(), !IsAdd);
4022  if (IsAdd && getInitLCDecl(BO->getRHS()) == LCDecl)
4023  return setStep(BO->getLHS(), /*Subtract=*/false);
4024  }
4025  } else if (auto *CE = dyn_cast<CXXOperatorCallExpr>(RHS)) {
4026  bool IsAdd = CE->getOperator() == OO_Plus;
4027  if ((IsAdd || CE->getOperator() == OO_Minus) && CE->getNumArgs() == 2) {
4028  if (getInitLCDecl(CE->getArg(0)) == LCDecl)
4029  return setStep(CE->getArg(1), !IsAdd);
4030  if (IsAdd && getInitLCDecl(CE->getArg(1)) == LCDecl)
4031  return setStep(CE->getArg(0), /*Subtract=*/false);
4032  }
4033  }
4034  if (dependent() || SemaRef.CurContext->isDependentContext())
4035  return false;
4036  SemaRef.Diag(RHS->getLocStart(), diag::err_omp_loop_not_canonical_incr)
4037  << RHS->getSourceRange() << LCDecl;
4038  return true;
4039 }
4040 
4041 bool OpenMPIterationSpaceChecker::checkAndSetInc(Expr *S) {
4042  // Check incr-expr for canonical loop form and return true if it
4043  // does not conform.
4044  // OpenMP [2.6] Canonical loop form. Test-expr may be one of the following:
4045  // ++var
4046  // var++
4047  // --var
4048  // var--
4049  // var += incr
4050  // var -= incr
4051  // var = var + incr
4052  // var = incr + var
4053  // var = var - incr
4054  //
4055  if (!S) {
4056  SemaRef.Diag(DefaultLoc, diag::err_omp_loop_not_canonical_incr) << LCDecl;
4057  return true;
4058  }
4059  if (auto *ExprTemp = dyn_cast<ExprWithCleanups>(S))
4060  if (!ExprTemp->cleanupsHaveSideEffects())
4061  S = ExprTemp->getSubExpr();
4062 
4063  IncrementSrcRange = S->getSourceRange();
4064  S = S->IgnoreParens();
4065  if (auto *UO = dyn_cast<UnaryOperator>(S)) {
4066  if (UO->isIncrementDecrementOp() &&
4067  getInitLCDecl(UO->getSubExpr()) == LCDecl)
4068  return setStep(SemaRef
4069  .ActOnIntegerConstant(UO->getLocStart(),
4070  (UO->isDecrementOp() ? -1 : 1))
4071  .get(),
4072  /*Subtract=*/false);
4073  } else if (auto *BO = dyn_cast<BinaryOperator>(S)) {
4074  switch (BO->getOpcode()) {
4075  case BO_AddAssign:
4076  case BO_SubAssign:
4077  if (getInitLCDecl(BO->getLHS()) == LCDecl)
4078  return setStep(BO->getRHS(), BO->getOpcode() == BO_SubAssign);
4079  break;
4080  case BO_Assign:
4081  if (getInitLCDecl(BO->getLHS()) == LCDecl)
4082  return checkAndSetIncRHS(BO->getRHS());
4083  break;
4084  default:
4085  break;
4086  }
4087  } else if (auto *CE = dyn_cast<CXXOperatorCallExpr>(S)) {
4088  switch (CE->getOperator()) {
4089  case OO_PlusPlus:
4090  case OO_MinusMinus:
4091  if (getInitLCDecl(CE->getArg(0)) == LCDecl)
4092  return setStep(SemaRef
4093  .ActOnIntegerConstant(
4094  CE->getLocStart(),
4095  ((CE->getOperator() == OO_MinusMinus) ? -1 : 1))
4096  .get(),
4097  /*Subtract=*/false);
4098  break;
4099  case OO_PlusEqual:
4100  case OO_MinusEqual:
4101  if (getInitLCDecl(CE->getArg(0)) == LCDecl)
4102  return setStep(CE->getArg(1), CE->getOperator() == OO_MinusEqual);
4103  break;
4104  case OO_Equal:
4105  if (getInitLCDecl(CE->getArg(0)) == LCDecl)
4106  return checkAndSetIncRHS(CE->getArg(1));
4107  break;
4108  default:
4109  break;
4110  }
4111  }
4112  if (dependent() || SemaRef.CurContext->isDependentContext())
4113  return false;
4114  SemaRef.Diag(S->getLocStart(), diag::err_omp_loop_not_canonical_incr)
4115  << S->getSourceRange() << LCDecl;
4116  return true;
4117 }
4118 
4119 static ExprResult
4120 tryBuildCapture(Sema &SemaRef, Expr *Capture,
4121  llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
4122  if (SemaRef.CurContext->isDependentContext())
4123  return ExprResult(Capture);
4124  if (Capture->isEvaluatable(SemaRef.Context, Expr::SE_AllowSideEffects))
4125  return SemaRef.PerformImplicitConversion(
4126  Capture->IgnoreImpCasts(), Capture->getType(), Sema::AA_Converting,
4127  /*AllowExplicit=*/true);
4128  auto I = Captures.find(Capture);
4129  if (I != Captures.end())
4130  return buildCapture(SemaRef, Capture, I->second);
4131  DeclRefExpr *Ref = nullptr;
4132  ExprResult Res = buildCapture(SemaRef, Capture, Ref);
4133  Captures[Capture] = Ref;
4134  return Res;
4135 }
4136 
4137 /// Build the expression to calculate the number of iterations.
4138 Expr *OpenMPIterationSpaceChecker::buildNumIterations(
4139  Scope *S, const bool LimitedType,
4140  llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const {
4141  ExprResult Diff;
4142  QualType VarType = LCDecl->getType().getNonReferenceType();
4143  if (VarType->isIntegerType() || VarType->isPointerType() ||
4144  SemaRef.getLangOpts().CPlusPlus) {
4145  // Upper - Lower
4146  Expr *UBExpr = TestIsLessOp ? UB : LB;
4147  Expr *LBExpr = TestIsLessOp ? LB : UB;
4148  Expr *Upper = tryBuildCapture(SemaRef, UBExpr, Captures).get();
4149  Expr *Lower = tryBuildCapture(SemaRef, LBExpr, Captures).get();
4150  if (!Upper || !Lower)
4151  return nullptr;
4152 
4153  Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Sub, Upper, Lower);
4154 
4155  if (!Diff.isUsable() && VarType->getAsCXXRecordDecl()) {
4156  // BuildBinOp already emitted error, this one is to point user to upper
4157  // and lower bound, and to tell what is passed to 'operator-'.
4158  SemaRef.Diag(Upper->getLocStart(), diag::err_omp_loop_diff_cxx)
4159  << Upper->getSourceRange() << Lower->getSourceRange();
4160  return nullptr;
4161  }
4162  }
4163 
4164  if (!Diff.isUsable())
4165  return nullptr;
4166 
4167  // Upper - Lower [- 1]
4168  if (TestIsStrictOp)
4169  Diff = SemaRef.BuildBinOp(
4170  S, DefaultLoc, BO_Sub, Diff.get(),
4171  SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get());
4172  if (!Diff.isUsable())
4173  return nullptr;
4174 
4175  // Upper - Lower [- 1] + Step
4176  ExprResult NewStep = tryBuildCapture(SemaRef, Step, Captures);
4177  if (!NewStep.isUsable())
4178  return nullptr;
4179  Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Add, Diff.get(), NewStep.get());
4180  if (!Diff.isUsable())
4181  return nullptr;
4182 
4183  // Parentheses (for dumping/debugging purposes only).
4184  Diff = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Diff.get());
4185  if (!Diff.isUsable())
4186  return nullptr;
4187 
4188  // (Upper - Lower [- 1] + Step) / Step
4189  Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Div, Diff.get(), NewStep.get());
4190  if (!Diff.isUsable())
4191  return nullptr;
4192 
4193  // OpenMP runtime requires 32-bit or 64-bit loop variables.
4194  QualType Type = Diff.get()->getType();
4195  ASTContext &C = SemaRef.Context;
4196  bool UseVarType = VarType->hasIntegerRepresentation() &&
4197  C.getTypeSize(Type) > C.getTypeSize(VarType);
4198  if (!Type->isIntegerType() || UseVarType) {
4199  unsigned NewSize =
4200  UseVarType ? C.getTypeSize(VarType) : C.getTypeSize(Type);
4201  bool IsSigned = UseVarType ? VarType->hasSignedIntegerRepresentation()
4203  Type = C.getIntTypeForBitwidth(NewSize, IsSigned);
4204  if (!SemaRef.Context.hasSameType(Diff.get()->getType(), Type)) {
4205  Diff = SemaRef.PerformImplicitConversion(
4206  Diff.get(), Type, Sema::AA_Converting, /*AllowExplicit=*/true);
4207  if (!Diff.isUsable())
4208  return nullptr;
4209  }
4210  }
4211  if (LimitedType) {
4212  unsigned NewSize = (C.getTypeSize(Type) > 32) ? 64 : 32;
4213  if (NewSize != C.getTypeSize(Type)) {
4214  if (NewSize < C.getTypeSize(Type)) {
4215  assert(NewSize == 64 && "incorrect loop var size");
4216  SemaRef.Diag(DefaultLoc, diag::warn_omp_loop_64_bit_var)
4217  << InitSrcRange << ConditionSrcRange;
4218  }
4219  QualType NewType = C.getIntTypeForBitwidth(
4220  NewSize, Type->hasSignedIntegerRepresentation() ||
4221  C.getTypeSize(Type) < NewSize);
4222  if (!SemaRef.Context.hasSameType(Diff.get()->getType(), NewType)) {
4223  Diff = SemaRef.PerformImplicitConversion(Diff.get(), NewType,
4224  Sema::AA_Converting, true);
4225  if (!Diff.isUsable())
4226  return nullptr;
4227  }
4228  }
4229  }
4230 
4231  return Diff.get();
4232 }
4233 
4234 Expr *OpenMPIterationSpaceChecker::buildPreCond(
4235  Scope *S, Expr *Cond,
4236  llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const {
4237  // Try to build LB <op> UB, where <op> is <, >, <=, or >=.
4238  bool Suppress = SemaRef.getDiagnostics().getSuppressAllDiagnostics();
4239  SemaRef.getDiagnostics().setSuppressAllDiagnostics(/*Val=*/true);
4240 
4241  ExprResult NewLB = tryBuildCapture(SemaRef, LB, Captures);
4242  ExprResult NewUB = tryBuildCapture(SemaRef, UB, Captures);
4243  if (!NewLB.isUsable() || !NewUB.isUsable())
4244  return nullptr;
4245 
4246  ExprResult CondExpr =
4247  SemaRef.BuildBinOp(S, DefaultLoc,
4248  TestIsLessOp ? (TestIsStrictOp ? BO_LT : BO_LE)
4249  : (TestIsStrictOp ? BO_GT : BO_GE),
4250  NewLB.get(), NewUB.get());
4251  if (CondExpr.isUsable()) {
4252  if (!SemaRef.Context.hasSameUnqualifiedType(CondExpr.get()->getType(),
4253  SemaRef.Context.BoolTy))
4254  CondExpr = SemaRef.PerformImplicitConversion(
4255  CondExpr.get(), SemaRef.Context.BoolTy, /*Action=*/Sema::AA_Casting,
4256  /*AllowExplicit=*/true);
4257  }
4258  SemaRef.getDiagnostics().setSuppressAllDiagnostics(Suppress);
4259  // Otherwise use original loop conditon and evaluate it in runtime.
4260  return CondExpr.isUsable() ? CondExpr.get() : Cond;
4261 }
4262 
4263 /// Build reference expression to the counter be used for codegen.
4264 DeclRefExpr *OpenMPIterationSpaceChecker::buildCounterVar(
4265  llvm::MapVector<const Expr *, DeclRefExpr *> &Captures, DSAStackTy &DSA) const {
4266  auto *VD = dyn_cast<VarDecl>(LCDecl);
4267  if (!VD) {
4268  VD = SemaRef.isOpenMPCapturedDecl(LCDecl);
4270  SemaRef, VD, VD->getType().getNonReferenceType(), DefaultLoc);
4271  const DSAStackTy::DSAVarData Data =
4272  DSA.getTopDSA(LCDecl, /*FromParent=*/false);
4273  // If the loop control decl is explicitly marked as private, do not mark it
4274  // as captured again.
4275  if (!isOpenMPPrivate(Data.CKind) || !Data.RefExpr)
4276  Captures.insert(std::make_pair(LCRef, Ref));
4277  return Ref;
4278  }
4279  return buildDeclRefExpr(SemaRef, VD, VD->getType().getNonReferenceType(),
4280  DefaultLoc);
4281 }
4282 
4283 Expr *OpenMPIterationSpaceChecker::buildPrivateCounterVar() const {
4284  if (LCDecl && !LCDecl->isInvalidDecl()) {
4285  QualType Type = LCDecl->getType().getNonReferenceType();
4286  VarDecl *PrivateVar = buildVarDecl(
4287  SemaRef, DefaultLoc, Type, LCDecl->getName(),
4288  LCDecl->hasAttrs() ? &LCDecl->getAttrs() : nullptr,
4289  isa<VarDecl>(LCDecl)
4290  ? buildDeclRefExpr(SemaRef, cast<VarDecl>(LCDecl), Type, DefaultLoc)
4291  : nullptr);
4292  if (PrivateVar->isInvalidDecl())
4293  return nullptr;
4294  return buildDeclRefExpr(SemaRef, PrivateVar, Type, DefaultLoc);
4295  }
4296  return nullptr;
4297 }
4298 
4299 /// Build initialization of the counter to be used for codegen.
4301 
4302 /// Build step of the counter be used for codegen.
4303 Expr *OpenMPIterationSpaceChecker::buildCounterStep() const { return Step; }
4304 
4305 /// Iteration space of a single for loop.
4306 struct LoopIterationSpace final {
4307  /// Condition of the loop.
4308  Expr *PreCond = nullptr;
4309  /// This expression calculates the number of iterations in the loop.
4310  /// It is always possible to calculate it before starting the loop.
4311  Expr *NumIterations = nullptr;
4312  /// The loop counter variable.
4313  Expr *CounterVar = nullptr;
4314  /// Private loop counter variable.
4315  Expr *PrivateCounterVar = nullptr;
4316  /// This is initializer for the initial value of #CounterVar.
4317  Expr *CounterInit = nullptr;
4318  /// This is step for the #CounterVar used to generate its update:
4319  /// #CounterVar = #CounterInit + #CounterStep * CurrentIteration.
4320  Expr *CounterStep = nullptr;
4321  /// Should step be subtracted?
4322  bool Subtract = false;
4323  /// Source range of the loop init.
4324  SourceRange InitSrcRange;
4325  /// Source range of the loop condition.
4326  SourceRange CondSrcRange;
4327  /// Source range of the loop increment.
4328  SourceRange IncSrcRange;
4329 };
4330 
4331 } // namespace
4332 
4334  assert(getLangOpts().OpenMP && "OpenMP is not active.");
4335  assert(Init && "Expected loop in canonical form.");
4336  unsigned AssociatedLoops = DSAStack->getAssociatedLoops();
4337  if (AssociatedLoops > 0 &&
4338  isOpenMPLoopDirective(DSAStack->getCurrentDirective())) {
4339  OpenMPIterationSpaceChecker ISC(*this, ForLoc);
4340  if (!ISC.checkAndSetInit(Init, /*EmitDiags=*/false)) {
4341  if (ValueDecl *D = ISC.getLoopDecl()) {
4342  auto *VD = dyn_cast<VarDecl>(D);
4343  if (!VD) {
4344  if (VarDecl *Private = isOpenMPCapturedDecl(D)) {
4345  VD = Private;
4346  } else {
4347  DeclRefExpr *Ref = buildCapture(*this, D, ISC.getLoopDeclRefExpr(),
4348  /*WithInit=*/false);
4349  VD = cast<VarDecl>(Ref->getDecl());
4350  }
4351  }
4352  DSAStack->addLoopControlVariable(D, VD);
4353  }
4354  }
4355  DSAStack->setAssociatedLoops(AssociatedLoops - 1);
4356  }
4357 }
4358 
4359 /// Called on a for stmt to check and extract its iteration space
4360 /// for further processing (such as collapsing).
4362  OpenMPDirectiveKind DKind, Stmt *S, Sema &SemaRef, DSAStackTy &DSA,
4363  unsigned CurrentNestedLoopCount, unsigned NestedLoopCount,
4364  Expr *CollapseLoopCountExpr, Expr *OrderedLoopCountExpr,
4365  Sema::VarsWithInheritedDSAType &VarsWithImplicitDSA,
4366  LoopIterationSpace &ResultIterSpace,
4367  llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
4368  // OpenMP [2.6, Canonical Loop Form]
4369  // for (init-expr; test-expr; incr-expr) structured-block
4370  auto *For = dyn_cast_or_null<ForStmt>(S);
4371  if (!For) {
4372  SemaRef.Diag(S->getLocStart(), diag::err_omp_not_for)
4373  << (CollapseLoopCountExpr != nullptr || OrderedLoopCountExpr != nullptr)
4374  << getOpenMPDirectiveName(DKind) << NestedLoopCount
4375  << (CurrentNestedLoopCount > 0) << CurrentNestedLoopCount;
4376  if (NestedLoopCount > 1) {
4377  if (CollapseLoopCountExpr && OrderedLoopCountExpr)
4378  SemaRef.Diag(DSA.getConstructLoc(),
4379  diag::note_omp_collapse_ordered_expr)
4380  << 2 << CollapseLoopCountExpr->getSourceRange()
4381  << OrderedLoopCountExpr->getSourceRange();
4382  else if (CollapseLoopCountExpr)
4383  SemaRef.Diag(CollapseLoopCountExpr->getExprLoc(),
4384  diag::note_omp_collapse_ordered_expr)
4385  << 0 << CollapseLoopCountExpr->getSourceRange();
4386  else
4387  SemaRef.Diag(OrderedLoopCountExpr->getExprLoc(),
4388  diag::note_omp_collapse_ordered_expr)
4389  << 1 << OrderedLoopCountExpr->getSourceRange();
4390  }
4391  return true;
4392  }
4393  assert(For->getBody());
4394 
4395  OpenMPIterationSpaceChecker ISC(SemaRef, For->getForLoc());
4396 
4397  // Check init.
4398  Stmt *Init = For->getInit();
4399  if (ISC.checkAndSetInit(Init))
4400  return true;
4401 
4402  bool HasErrors = false;
4403 
4404  // Check loop variable's type.
4405  if (ValueDecl *LCDecl = ISC.getLoopDecl()) {
4406  Expr *LoopDeclRefExpr = ISC.getLoopDeclRefExpr();
4407 
4408  // OpenMP [2.6, Canonical Loop Form]
4409  // Var is one of the following:
4410  // A variable of signed or unsigned integer type.
4411  // For C++, a variable of a random access iterator type.
4412  // For C, a variable of a pointer type.
4413  QualType VarType = LCDecl->getType().getNonReferenceType();
4414  if (!VarType->isDependentType() && !VarType->isIntegerType() &&
4415  !VarType->isPointerType() &&
4416  !(SemaRef.getLangOpts().CPlusPlus && VarType->isOverloadableType())) {
4417  SemaRef.Diag(Init->getLocStart(), diag::err_omp_loop_variable_type)
4418  << SemaRef.getLangOpts().CPlusPlus;
4419  HasErrors = true;
4420  }
4421 
4422  // OpenMP, 2.14.1.1 Data-sharing Attribute Rules for Variables Referenced in
4423  // a Construct
4424  // The loop iteration variable(s) in the associated for-loop(s) of a for or
4425  // parallel for construct is (are) private.
4426  // The loop iteration variable in the associated for-loop of a simd
4427  // construct with just one associated for-loop is linear with a
4428  // constant-linear-step that is the increment of the associated for-loop.
4429  // Exclude loop var from the list of variables with implicitly defined data
4430  // sharing attributes.
4431  VarsWithImplicitDSA.erase(LCDecl);
4432 
4433  // OpenMP [2.14.1.1, Data-sharing Attribute Rules for Variables Referenced
4434  // in a Construct, C/C++].
4435  // The loop iteration variable in the associated for-loop of a simd
4436  // construct with just one associated for-loop may be listed in a linear
4437  // clause with a constant-linear-step that is the increment of the
4438  // associated for-loop.
4439  // The loop iteration variable(s) in the associated for-loop(s) of a for or
4440  // parallel for construct may be listed in a private or lastprivate clause.
4441  DSAStackTy::DSAVarData DVar = DSA.getTopDSA(LCDecl, false);
4442  // If LoopVarRefExpr is nullptr it means the corresponding loop variable is
4443  // declared in the loop and it is predetermined as a private.
4444  OpenMPClauseKind PredeterminedCKind =
4445  isOpenMPSimdDirective(DKind)
4446  ? ((NestedLoopCount == 1) ? OMPC_linear : OMPC_lastprivate)
4447  : OMPC_private;
4448  if (((isOpenMPSimdDirective(DKind) && DVar.CKind != OMPC_unknown &&
4449  DVar.CKind != PredeterminedCKind) ||
4450  ((isOpenMPWorksharingDirective(DKind) || DKind == OMPD_taskloop ||
4451  isOpenMPDistributeDirective(DKind)) &&
4452  !isOpenMPSimdDirective(DKind) && DVar.CKind != OMPC_unknown &&
4453  DVar.CKind != OMPC_private && DVar.CKind != OMPC_lastprivate)) &&
4454  (DVar.CKind != OMPC_private || DVar.RefExpr != nullptr)) {
4455  SemaRef.Diag(Init->getLocStart(), diag::err_omp_loop_var_dsa)
4456  << getOpenMPClauseName(DVar.CKind) << getOpenMPDirectiveName(DKind)
4457  << getOpenMPClauseName(PredeterminedCKind);
4458  if (DVar.RefExpr == nullptr)
4459  DVar.CKind = PredeterminedCKind;
4460  reportOriginalDsa(SemaRef, &DSA, LCDecl, DVar, /*IsLoopIterVar=*/true);
4461  HasErrors = true;
4462  } else if (LoopDeclRefExpr != nullptr) {
4463  // Make the loop iteration variable private (for worksharing constructs),
4464  // linear (for simd directives with the only one associated loop) or
4465  // lastprivate (for simd directives with several collapsed or ordered
4466  // loops).
4467  if (DVar.CKind == OMPC_unknown)
4468  DVar = DSA.hasDSA(LCDecl, isOpenMPPrivate,
4469  [](OpenMPDirectiveKind) -> bool { return true; },
4470  /*FromParent=*/false);
4471  DSA.addDSA(LCDecl, LoopDeclRefExpr, PredeterminedCKind);
4472  }
4473 
4474  assert(isOpenMPLoopDirective(DKind) && "DSA for non-loop vars");
4475 
4476  // Check test-expr.
4477  HasErrors |= ISC.checkAndSetCond(For->getCond());
4478 
4479  // Check incr-expr.
4480  HasErrors |= ISC.checkAndSetInc(For->getInc());
4481  }
4482 
4483  if (ISC.dependent() || SemaRef.CurContext->isDependentContext() || HasErrors)
4484  return HasErrors;
4485 
4486  // Build the loop's iteration space representation.
4487  ResultIterSpace.PreCond =
4488  ISC.buildPreCond(DSA.getCurScope(), For->getCond(), Captures);
4489  ResultIterSpace.NumIterations = ISC.buildNumIterations(
4490  DSA.getCurScope(),
4491  (isOpenMPWorksharingDirective(DKind) ||
4493  Captures);
4494  ResultIterSpace.CounterVar = ISC.buildCounterVar(Captures, DSA);
4495  ResultIterSpace.PrivateCounterVar = ISC.buildPrivateCounterVar();
4496  ResultIterSpace.CounterInit = ISC.buildCounterInit();
4497  ResultIterSpace.CounterStep = ISC.buildCounterStep();
4498  ResultIterSpace.InitSrcRange = ISC.getInitSrcRange();
4499  ResultIterSpace.CondSrcRange = ISC.getConditionSrcRange();
4500  ResultIterSpace.IncSrcRange = ISC.getIncrementSrcRange();
4501  ResultIterSpace.Subtract = ISC.shouldSubtractStep();
4502 
4503  HasErrors |= (ResultIterSpace.PreCond == nullptr ||
4504  ResultIterSpace.NumIterations == nullptr ||
4505  ResultIterSpace.CounterVar == nullptr ||
4506  ResultIterSpace.PrivateCounterVar == nullptr ||
4507  ResultIterSpace.CounterInit == nullptr ||
4508  ResultIterSpace.CounterStep == nullptr);
4509 
4510  return HasErrors;
4511 }
4512 
4513 /// Build 'VarRef = Start.
4514 static ExprResult
4516  ExprResult Start,
4517  llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
4518  // Build 'VarRef = Start.
4519  ExprResult NewStart = tryBuildCapture(SemaRef, Start.get(), Captures);
4520  if (!NewStart.isUsable())
4521  return ExprError();
4522  if (!SemaRef.Context.hasSameType(NewStart.get()->getType(),
4523  VarRef.get()->getType())) {
4524  NewStart = SemaRef.PerformImplicitConversion(
4525  NewStart.get(), VarRef.get()->getType(), Sema::AA_Converting,
4526  /*AllowExplicit=*/true);
4527  if (!NewStart.isUsable())
4528  return ExprError();
4529  }
4530 
4531  ExprResult Init =
4532  SemaRef.BuildBinOp(S, Loc, BO_Assign, VarRef.get(), NewStart.get());
4533  return Init;
4534 }
4535 
4536 /// Build 'VarRef = Start + Iter * Step'.
4538  Sema &SemaRef, Scope *S, SourceLocation Loc, ExprResult VarRef,
4539  ExprResult Start, ExprResult Iter, ExprResult Step, bool Subtract,
4540  llvm::MapVector<const Expr *, DeclRefExpr *> *Captures = nullptr) {
4541  // Add parentheses (for debugging purposes only).
4542  Iter = SemaRef.ActOnParenExpr(Loc, Loc, Iter.get());
4543  if (!VarRef.isUsable() || !Start.isUsable() || !Iter.isUsable() ||
4544  !Step.isUsable())
4545  return ExprError();
4546 
4547  ExprResult NewStep = Step;
4548  if (Captures)
4549  NewStep = tryBuildCapture(SemaRef, Step.get(), *Captures);
4550  if (NewStep.isInvalid())
4551  return ExprError();
4552  ExprResult Update =
4553  SemaRef.BuildBinOp(S, Loc, BO_Mul, Iter.get(), NewStep.get());
4554  if (!Update.isUsable())
4555  return ExprError();
4556 
4557  // Try to build 'VarRef = Start, VarRef (+|-)= Iter * Step' or
4558  // 'VarRef = Start (+|-) Iter * Step'.
4559  ExprResult NewStart = Start;
4560  if (Captures)
4561  NewStart = tryBuildCapture(SemaRef, Start.get(), *Captures);
4562  if (NewStart.isInvalid())
4563  return ExprError();
4564 
4565  // First attempt: try to build 'VarRef = Start, VarRef += Iter * Step'.
4566  ExprResult SavedUpdate = Update;
4567  ExprResult UpdateVal;
4568  if (VarRef.get()->getType()->isOverloadableType() ||
4569  NewStart.get()->getType()->isOverloadableType() ||
4570  Update.get()->getType()->isOverloadableType()) {
4571  bool Suppress = SemaRef.getDiagnostics().getSuppressAllDiagnostics();
4572  SemaRef.getDiagnostics().setSuppressAllDiagnostics(/*Val=*/true);
4573  Update =
4574  SemaRef.BuildBinOp(S, Loc, BO_Assign, VarRef.get(), NewStart.get());
4575  if (Update.isUsable()) {
4576  UpdateVal =
4577  SemaRef.BuildBinOp(S, Loc, Subtract ? BO_SubAssign : BO_AddAssign,
4578  VarRef.get(), SavedUpdate.get());
4579  if (UpdateVal.isUsable()) {
4580  Update = SemaRef.CreateBuiltinBinOp(Loc, BO_Comma, Update.get(),
4581  UpdateVal.get());
4582  }
4583  }
4584  SemaRef.getDiagnostics().setSuppressAllDiagnostics(Suppress);
4585  }
4586 
4587  // Second attempt: try to build 'VarRef = Start (+|-) Iter * Step'.
4588  if (!Update.isUsable() || !UpdateVal.isUsable()) {
4589  Update = SemaRef.BuildBinOp(S, Loc, Subtract ? BO_Sub : BO_Add,
4590  NewStart.get(), SavedUpdate.get());
4591  if (!Update.isUsable())
4592  return ExprError();
4593 
4594  if (!SemaRef.Context.hasSameType(Update.get()->getType(),
4595  VarRef.get()->getType())) {
4596  Update = SemaRef.PerformImplicitConversion(
4597  Update.get(), VarRef.get()->getType(), Sema::AA_Converting, true);
4598  if (!Update.isUsable())
4599  return ExprError();
4600  }
4601 
4602  Update = SemaRef.BuildBinOp(S, Loc, BO_Assign, VarRef.get(), Update.get());
4603  }
4604  return Update;
4605 }
4606 
4607 /// Convert integer expression \a E to make it have at least \a Bits
4608 /// bits.
4609 static ExprResult widenIterationCount(unsigned Bits, Expr *E, Sema &SemaRef) {
4610  if (E == nullptr)
4611  return ExprError();
4612  ASTContext &C = SemaRef.Context;
4613  QualType OldType = E->getType();
4614  unsigned HasBits = C.getTypeSize(OldType);
4615  if (HasBits >= Bits)
4616  return ExprResult(E);
4617  // OK to convert to signed, because new type has more bits than old.
4618  QualType NewType = C.getIntTypeForBitwidth(Bits, /* Signed */ true);
4619  return SemaRef.PerformImplicitConversion(E, NewType, Sema::AA_Converting,
4620  true);
4621 }
4622 
4623 /// Check if the given expression \a E is a constant integer that fits
4624 /// into \a Bits bits.
4625 static bool fitsInto(unsigned Bits, bool Signed, const Expr *E, Sema &SemaRef) {
4626  if (E == nullptr)
4627  return false;
4628  llvm::APSInt Result;
4629  if (E->isIntegerConstantExpr(Result, SemaRef.Context))
4630  return Signed ? Result.isSignedIntN(Bits) : Result.isIntN(Bits);
4631  return false;
4632 }
4633 
4634 /// Build preinits statement for the given declarations.
4635 static Stmt *buildPreInits(ASTContext &Context,
4636  MutableArrayRef<Decl *> PreInits) {
4637  if (!PreInits.empty()) {
4638  return new (Context) DeclStmt(
4639  DeclGroupRef::Create(Context, PreInits.begin(), PreInits.size()),
4641  }
4642  return nullptr;
4643 }
4644 
4645 /// Build preinits statement for the given declarations.
4646 static Stmt *
4648  const llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
4649  if (!Captures.empty()) {
4650  SmallVector<Decl *, 16> PreInits;
4651  for (const auto &Pair : Captures)
4652  PreInits.push_back(Pair.second->getDecl());
4653  return buildPreInits(Context, PreInits);
4654  }
4655  return nullptr;
4656 }
4657 
4658 /// Build postupdate expression for the given list of postupdates expressions.
4659 static Expr *buildPostUpdate(Sema &S, ArrayRef<Expr *> PostUpdates) {
4660  Expr *PostUpdate = nullptr;
4661  if (!PostUpdates.empty()) {
4662  for (Expr *E : PostUpdates) {
4663  Expr *ConvE = S.BuildCStyleCastExpr(
4664  E->getExprLoc(),
4666  E->getExprLoc(), E)
4667  .get();
4668  PostUpdate = PostUpdate
4669  ? S.CreateBuiltinBinOp(ConvE->getExprLoc(), BO_Comma,
4670  PostUpdate, ConvE)
4671  .get()
4672  : ConvE;
4673  }
4674  }
4675  return PostUpdate;
4676 }
4677 
4678 /// Called on a for stmt to check itself and nested loops (if any).
4679 /// \return Returns 0 if one of the collapsed stmts is not canonical for loop,
4680 /// number of collapsed loops otherwise.
4681 static unsigned
4682 checkOpenMPLoop(OpenMPDirectiveKind DKind, Expr *CollapseLoopCountExpr,
4683  Expr *OrderedLoopCountExpr, Stmt *AStmt, Sema &SemaRef,
4684  DSAStackTy &DSA,
4685  Sema::VarsWithInheritedDSAType &VarsWithImplicitDSA,
4687  unsigned NestedLoopCount = 1;
4688  if (CollapseLoopCountExpr) {
4689  // Found 'collapse' clause - calculate collapse number.
4690  llvm::APSInt Result;
4691  if (CollapseLoopCountExpr->EvaluateAsInt(Result, SemaRef.getASTContext()))
4692  NestedLoopCount = Result.getLimitedValue();
4693  }
4694  if (OrderedLoopCountExpr) {
4695  // Found 'ordered' clause - calculate collapse number.
4696  llvm::APSInt Result;
4697  if (OrderedLoopCountExpr->EvaluateAsInt(Result, SemaRef.getASTContext())) {
4698  if (Result.getLimitedValue() < NestedLoopCount) {
4699  SemaRef.Diag(OrderedLoopCountExpr->getExprLoc(),
4700  diag::err_omp_wrong_ordered_loop_count)
4701  << OrderedLoopCountExpr->getSourceRange();
4702  SemaRef.Diag(CollapseLoopCountExpr->getExprLoc(),
4703  diag::note_collapse_loop_count)
4704  << CollapseLoopCountExpr->getSourceRange();
4705  }
4706  NestedLoopCount = Result.getLimitedValue();
4707  }
4708  }
4709  // This is helper routine for loop directives (e.g., 'for', 'simd',
4710  // 'for simd', etc.).
4711  llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
4713  IterSpaces.resize(NestedLoopCount);
4714  Stmt *CurStmt = AStmt->IgnoreContainers(/* IgnoreCaptured */ true);
4715  for (unsigned Cnt = 0; Cnt < NestedLoopCount; ++Cnt) {
4716  if (checkOpenMPIterationSpace(DKind, CurStmt, SemaRef, DSA, Cnt,
4717  NestedLoopCount, CollapseLoopCountExpr,
4718  OrderedLoopCountExpr, VarsWithImplicitDSA,
4719  IterSpaces[Cnt], Captures))
4720  return 0;
4721  // Move on to the next nested for loop, or to the loop body.
4722  // OpenMP [2.8.1, simd construct, Restrictions]
4723  // All loops associated with the construct must be perfectly nested; that
4724  // is, there must be no intervening code nor any OpenMP directive between
4725  // any two loops.
4726  CurStmt = cast<ForStmt>(CurStmt)->getBody()->IgnoreContainers();
4727  }
4728 
4729  Built.clear(/* size */ NestedLoopCount);
4730 
4731  if (SemaRef.CurContext->isDependentContext())
4732  return NestedLoopCount;
4733 
4734  // An example of what is generated for the following code:
4735  //
4736  // #pragma omp simd collapse(2) ordered(2)
4737  // for (i = 0; i < NI; ++i)
4738  // for (k = 0; k < NK; ++k)
4739  // for (j = J0; j < NJ; j+=2) {
4740  // <loop body>
4741  // }
4742  //
4743  // We generate the code below.
4744  // Note: the loop body may be outlined in CodeGen.
4745  // Note: some counters may be C++ classes, operator- is used to find number of
4746  // iterations and operator+= to calculate counter value.
4747  // Note: decltype(NumIterations) must be integer type (in 'omp for', only i32
4748  // or i64 is currently supported).
4749  //
4750  // #define NumIterations (NI * ((NJ - J0 - 1 + 2) / 2))
4751  // for (int[32|64]_t IV = 0; IV < NumIterations; ++IV ) {
4752  // .local.i = IV / ((NJ - J0 - 1 + 2) / 2);
4753  // .local.j = J0 + (IV % ((NJ - J0 - 1 + 2) / 2)) * 2;
4754  // // similar updates for vars in clauses (e.g. 'linear')
4755  // <loop body (using local i and j)>
4756  // }
4757  // i = NI; // assign final values of counters
4758  // j = NJ;
4759  //
4760 
4761  // Last iteration number is (I1 * I2 * ... In) - 1, where I1, I2 ... In are
4762  // the iteration counts of the collapsed for loops.
4763  // Precondition tests if there is at least one iteration (all conditions are
4764  // true).
4765  auto PreCond = ExprResult(IterSpaces[0].PreCond);
4766  Expr *N0 = IterSpaces[0].NumIterations;
4767  ExprResult LastIteration32 =
4768  widenIterationCount(/*Bits=*/32,
4769  SemaRef
4770  .PerformImplicitConversion(
4771  N0->IgnoreImpCasts(), N0->getType(),
4772  Sema::AA_Converting, /*AllowExplicit=*/true)
4773  .get(),
4774  SemaRef);
4775  ExprResult LastIteration64 = widenIterationCount(
4776  /*Bits=*/64,
4777  SemaRef
4778  .PerformImplicitConversion(N0->IgnoreImpCasts(), N0->getType(),
4780  /*AllowExplicit=*/true)
4781  .get(),
4782  SemaRef);
4783 
4784  if (!LastIteration32.isUsable() || !LastIteration64.isUsable())
4785  return NestedLoopCount;
4786 
4787  ASTContext &C = SemaRef.Context;
4788  bool AllCountsNeedLessThan32Bits = C.getTypeSize(N0->getType()) < 32;
4789 
4790  Scope *CurScope = DSA.getCurScope();
4791  for (unsigned Cnt = 1; Cnt < NestedLoopCount; ++Cnt) {
4792  if (PreCond.isUsable()) {
4793  PreCond =
4794  SemaRef.BuildBinOp(CurScope, PreCond.get()->getExprLoc(), BO_LAnd,
4795  PreCond.get(), IterSpaces[Cnt].PreCond);
4796  }
4797  Expr *N = IterSpaces[Cnt].NumIterations;
4798  SourceLocation Loc = N->getExprLoc();
4799  AllCountsNeedLessThan32Bits &= C.getTypeSize(N->getType()) < 32;
4800  if (LastIteration32.isUsable())
4801  LastIteration32 = SemaRef.BuildBinOp(
4802  CurScope, Loc, BO_Mul, LastIteration32.get(),
4803  SemaRef
4806  /*AllowExplicit=*/true)
4807  .get());
4808  if (LastIteration64.isUsable())
4809  LastIteration64 = SemaRef.BuildBinOp(
4810  CurScope, Loc, BO_Mul, LastIteration64.get(),
4811  SemaRef
4814  /*AllowExplicit=*/true)
4815  .get());
4816  }
4817 
4818  // Choose either the 32-bit or 64-bit version.
4819  ExprResult LastIteration = LastIteration64;
4820  if (LastIteration32.isUsable() &&
4821  C.getTypeSize(LastIteration32.get()->getType()) == 32 &&
4822  (AllCountsNeedLessThan32Bits || NestedLoopCount == 1 ||
4823  fitsInto(
4824  /*Bits=*/32,
4825  LastIteration32.get()->getType()->hasSignedIntegerRepresentation(),
4826  LastIteration64.get(), SemaRef)))
4827  LastIteration = LastIteration32;
4828  QualType VType = LastIteration.get()->getType();
4829  QualType RealVType = VType;
4830  QualType StrideVType = VType;
4831  if (isOpenMPTaskLoopDirective(DKind)) {
4832  VType =
4833  SemaRef.Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/0);
4834  StrideVType =
4835  SemaRef.Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/1);
4836  }
4837 
4838  if (!LastIteration.isUsable())
4839  return 0;
4840 
4841  // Save the number of iterations.
4842  ExprResult NumIterations = LastIteration;
4843  {
4844  LastIteration = SemaRef.BuildBinOp(
4845  CurScope, LastIteration.get()->getExprLoc(), BO_Sub,
4846  LastIteration.get(),
4847  SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get());
4848  if (!LastIteration.isUsable())
4849  return 0;
4850  }
4851 
4852  // Calculate the last iteration number beforehand instead of doing this on
4853  // each iteration. Do not do this if the number of iterations may be kfold-ed.
4854  llvm::APSInt Result;
4855  bool IsConstant =
4856  LastIteration.get()->isIntegerConstantExpr(Result, SemaRef.Context);
4857  ExprResult CalcLastIteration;
4858  if (!IsConstant) {
4859  ExprResult SaveRef =
4860  tryBuildCapture(SemaRef, LastIteration.get(), Captures);
4861  LastIteration = SaveRef;
4862 
4863  // Prepare SaveRef + 1.
4864  NumIterations = SemaRef.BuildBinOp(
4865  CurScope, SaveRef.get()->getExprLoc(), BO_Add, SaveRef.get(),
4866  SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get());
4867  if (!NumIterations.isUsable())
4868  return 0;
4869  }
4870 
4871  SourceLocation InitLoc = IterSpaces[0].InitSrcRange.getBegin();
4872 
4873  // Build variables passed into runtime, necessary for worksharing directives.
4874  ExprResult LB, UB, IL, ST, EUB, CombLB, CombUB, PrevLB, PrevUB, CombEUB;
4876  isOpenMPDistributeDirective(DKind)) {
4877  // Lower bound variable, initialized with zero.
4878  VarDecl *LBDecl = buildVarDecl(SemaRef, InitLoc, VType, ".omp.lb");
4879  LB = buildDeclRefExpr(SemaRef, LBDecl, VType, InitLoc);
4880  SemaRef.AddInitializerToDecl(LBDecl,
4881  SemaRef.ActOnIntegerConstant(InitLoc, 0).get(),
4882  /*DirectInit*/ false);
4883 
4884  // Upper bound variable, initialized with last iteration number.
4885  VarDecl *UBDecl = buildVarDecl(SemaRef, InitLoc, VType, ".omp.ub");
4886  UB = buildDeclRefExpr(SemaRef, UBDecl, VType, InitLoc);
4887  SemaRef.AddInitializerToDecl(UBDecl, LastIteration.get(),
4888  /*DirectInit*/ false);
4889 
4890  // A 32-bit variable-flag where runtime returns 1 for the last iteration.
4891  // This will be used to implement clause 'lastprivate'.
4892  QualType Int32Ty = SemaRef.Context.getIntTypeForBitwidth(32, true);
4893  VarDecl *ILDecl = buildVarDecl(SemaRef, InitLoc, Int32Ty, ".omp.is_last");
4894  IL = buildDeclRefExpr(SemaRef, ILDecl, Int32Ty, InitLoc);
4895  SemaRef.AddInitializerToDecl(ILDecl,
4896  SemaRef.ActOnIntegerConstant(InitLoc, 0).get(),
4897  /*DirectInit*/ false);
4898 
4899  // Stride variable returned by runtime (we initialize it to 1 by default).
4900  VarDecl *STDecl =
4901  buildVarDecl(SemaRef, InitLoc, StrideVType, ".omp.stride");
4902  ST = buildDeclRefExpr(SemaRef, STDecl, StrideVType, InitLoc);
4903  SemaRef.AddInitializerToDecl(STDecl,
4904  SemaRef.ActOnIntegerConstant(InitLoc, 1).get(),
4905  /*DirectInit*/ false);
4906 
4907  // Build expression: UB = min(UB, LastIteration)
4908  // It is necessary for CodeGen of directives with static scheduling.
4909  ExprResult IsUBGreater = SemaRef.BuildBinOp(CurScope, InitLoc, BO_GT,
4910  UB.get(), LastIteration.get());
4911  ExprResult CondOp = SemaRef.ActOnConditionalOp(
4912  InitLoc, InitLoc, IsUBGreater.get(), LastIteration.get(), UB.get());
4913  EUB = SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, UB.get(),
4914  CondOp.get());
4915  EUB = SemaRef.ActOnFinishFullExpr(EUB.get());
4916 
4917  // If we have a combined directive that combines 'distribute', 'for' or
4918  // 'simd' we need to be able to access the bounds of the schedule of the
4919  // enclosing region. E.g. in 'distribute parallel for' the bounds obtained
4920  // by scheduling 'distribute' have to be passed to the schedule of 'for'.
4921  if (isOpenMPLoopBoundSharingDirective(DKind)) {
4922  // Lower bound variable, initialized with zero.
4923  VarDecl *CombLBDecl =
4924  buildVarDecl(SemaRef, InitLoc, VType, ".omp.comb.lb");
4925  CombLB = buildDeclRefExpr(SemaRef, CombLBDecl, VType, InitLoc);
4926  SemaRef.AddInitializerToDecl(
4927  CombLBDecl, SemaRef.ActOnIntegerConstant(InitLoc, 0).get(),
4928  /*DirectInit*/ false);
4929 
4930  // Upper bound variable, initialized with last iteration number.
4931  VarDecl *CombUBDecl =
4932  buildVarDecl(SemaRef, InitLoc, VType, ".omp.comb.ub");
4933  CombUB = buildDeclRefExpr(SemaRef, CombUBDecl, VType, InitLoc);
4934  SemaRef.AddInitializerToDecl(CombUBDecl, LastIteration.get(),
4935  /*DirectInit*/ false);
4936 
4937  ExprResult CombIsUBGreater = SemaRef.BuildBinOp(
4938  CurScope, InitLoc, BO_GT, CombUB.get(), LastIteration.get());
4939  ExprResult CombCondOp =
4940  SemaRef.ActOnConditionalOp(InitLoc, InitLoc, CombIsUBGreater.get(),
4941  LastIteration.get(), CombUB.get());
4942  CombEUB = SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, CombUB.get(),
4943  CombCondOp.get());
4944  CombEUB = SemaRef.ActOnFinishFullExpr(CombEUB.get());
4945 
4946  const CapturedDecl *CD = cast<CapturedStmt>(AStmt)->getCapturedDecl();
4947  // We expect to have at least 2 more parameters than the 'parallel'
4948  // directive does - the lower and upper bounds of the previous schedule.
4949  assert(CD->getNumParams() >= 4 &&
4950  "Unexpected number of parameters in loop combined directive");
4951 
4952  // Set the proper type for the bounds given what we learned from the
4953  // enclosed loops.
4954  ImplicitParamDecl *PrevLBDecl = CD->getParam(/*PrevLB=*/2);
4955  ImplicitParamDecl *PrevUBDecl = CD->getParam(/*PrevUB=*/3);
4956 
4957  // Previous lower and upper bounds are obtained from the region
4958  // parameters.
4959  PrevLB =
4960  buildDeclRefExpr(SemaRef, PrevLBDecl, PrevLBDecl->getType(), InitLoc);
4961  PrevUB =
4962  buildDeclRefExpr(SemaRef, PrevUBDecl, PrevUBDecl->getType(), InitLoc);
4963  }
4964  }
4965 
4966  // Build the iteration variable and its initialization before loop.
4967  ExprResult IV;
4968  ExprResult Init, CombInit;
4969  {
4970  VarDecl *IVDecl = buildVarDecl(SemaRef, InitLoc, RealVType, ".omp.iv");
4971  IV = buildDeclRefExpr(SemaRef, IVDecl, RealVType, InitLoc);
4972  Expr *RHS =
4973  (isOpenMPWorksharingDirective(DKind) ||
4975  ? LB.get()
4976  : SemaRef.ActOnIntegerConstant(SourceLocation(), 0).get();
4977  Init = SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, IV.get(), RHS);
4978  Init = SemaRef.ActOnFinishFullExpr(Init.get());
4979 
4980  if (isOpenMPLoopBoundSharingDirective(DKind)) {
4981  Expr *CombRHS =
4982  (isOpenMPWorksharingDirective(DKind) ||
4983  isOpenMPTaskLoopDirective(DKind) ||
4985  ? CombLB.get()
4986  : SemaRef.ActOnIntegerConstant(SourceLocation(), 0).get();
4987  CombInit =
4988  SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, IV.get(), CombRHS);
4989  CombInit = SemaRef.ActOnFinishFullExpr(CombInit.get());
4990  }
4991  }
4992 
4993  // Loop condition (IV < NumIterations) or (IV <= UB) for worksharing loops.
4994  SourceLocation CondLoc = AStmt->getLocStart();
4995  ExprResult Cond =
4996  (isOpenMPWorksharingDirective(DKind) ||
4998  ? SemaRef.BuildBinOp(CurScope, CondLoc, BO_LE, IV.get(), UB.get())
4999  : SemaRef.BuildBinOp(CurScope, CondLoc, BO_LT, IV.get(),
5000  NumIterations.get());
5001  ExprResult CombCond;
5002  if (isOpenMPLoopBoundSharingDirective(DKind)) {
5003  CombCond =
5004  SemaRef.BuildBinOp(CurScope, CondLoc, BO_LE, IV.get(), CombUB.get());
5005  }
5006  // Loop increment (IV = IV + 1)
5007  SourceLocation IncLoc = AStmt->getLocStart();
5008  ExprResult Inc =
5009  SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, IV.get(),
5010  SemaRef.ActOnIntegerConstant(IncLoc, 1).get());
5011  if (!Inc.isUsable())
5012  return 0;
5013  Inc = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, IV.get(), Inc.get());
5014  Inc = SemaRef.ActOnFinishFullExpr(Inc.get());
5015  if (!Inc.isUsable())
5016  return 0;
5017 
5018  // Increments for worksharing loops (LB = LB + ST; UB = UB + ST).
5019  // Used for directives with static scheduling.
5020  // In combined construct, add combined version that use CombLB and CombUB
5021  // base variables for the update
5022  ExprResult NextLB, NextUB, CombNextLB, CombNextUB;
5024  isOpenMPDistributeDirective(DKind)) {
5025  // LB + ST
5026  NextLB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, LB.get(), ST.get());
5027  if (!NextLB.isUsable())
5028  return 0;
5029  // LB = LB + ST
5030  NextLB =
5031  SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, LB.get(), NextLB.get());
5032  NextLB = SemaRef.ActOnFinishFullExpr(NextLB.get());
5033  if (!NextLB.isUsable())
5034  return 0;
5035  // UB + ST
5036  NextUB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, UB.get(), ST.get());
5037  if (!NextUB.isUsable())
5038  return 0;
5039  // UB = UB + ST
5040  NextUB =
5041  SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, UB.get(), NextUB.get());
5042  NextUB = SemaRef.ActOnFinishFullExpr(NextUB.get());
5043  if (!NextUB.isUsable())
5044  return 0;
5045  if (isOpenMPLoopBoundSharingDirective(DKind)) {
5046  CombNextLB =
5047  SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, CombLB.get(), ST.get());
5048  if (!NextLB.isUsable())
5049  return 0;
5050  // LB = LB + ST
5051  CombNextLB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, CombLB.get(),
5052  CombNextLB.get());
5053  CombNextLB = SemaRef.ActOnFinishFullExpr(CombNextLB.get());
5054  if (!CombNextLB.isUsable())
5055  return 0;
5056  // UB + ST
5057  CombNextUB =
5058  SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, CombUB.get(), ST.get());
5059  if (!CombNextUB.isUsable())
5060  return 0;
5061  // UB = UB + ST
5062  CombNextUB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, CombUB.get(),
5063  CombNextUB.get());
5064  CombNextUB = SemaRef.ActOnFinishFullExpr(CombNextUB.get());
5065  if (!CombNextUB.isUsable())
5066  return 0;
5067  }
5068  }
5069 
5070  // Create increment expression for distribute loop when combined in a same
5071  // directive with for as IV = IV + ST; ensure upper bound expression based
5072  // on PrevUB instead of NumIterations - used to implement 'for' when found
5073  // in combination with 'distribute', like in 'distribute parallel for'
5074  SourceLocation DistIncLoc = AStmt->getLocStart();
5075  ExprResult DistCond, DistInc, PrevEUB;
5076  if (isOpenMPLoopBoundSharingDirective(DKind)) {
5077  DistCond = SemaRef.BuildBinOp(CurScope, CondLoc, BO_LE, IV.get(), UB.get());
5078  assert(DistCond.isUsable() && "distribute cond expr was not built");
5079 
5080  DistInc =
5081  SemaRef.BuildBinOp(CurScope, DistIncLoc, BO_Add, IV.get(), ST.get());
5082  assert(DistInc.isUsable() && "distribute inc expr was not built");
5083  DistInc = SemaRef.BuildBinOp(CurScope, DistIncLoc, BO_Assign, IV.get(),
5084  DistInc.get());
5085  DistInc = SemaRef.ActOnFinishFullExpr(DistInc.get());
5086  assert(DistInc.isUsable() && "distribute inc expr was not built");
5087 
5088  // Build expression: UB = min(UB, prevUB) for #for in composite or combined
5089  // construct
5090  SourceLocation DistEUBLoc = AStmt->getLocStart();
5091  ExprResult IsUBGreater =
5092  SemaRef.BuildBinOp(CurScope, DistEUBLoc, BO_GT, UB.get(), PrevUB.get());
5093  ExprResult CondOp = SemaRef.ActOnConditionalOp(
5094  DistEUBLoc, DistEUBLoc, IsUBGreater.get(), PrevUB.get(), UB.get());
5095  PrevEUB = SemaRef.BuildBinOp(CurScope, DistIncLoc, BO_Assign, UB.get(),
5096  CondOp.get());
5097  PrevEUB = SemaRef.ActOnFinishFullExpr(PrevEUB.get());
5098  }
5099 
5100  // Build updates and final values of the loop counters.
5101  bool HasErrors = false;
5102  Built.Counters.resize(NestedLoopCount);
5103  Built.Inits.resize(NestedLoopCount);
5104  Built.Updates.resize(NestedLoopCount);
5105  Built.Finals.resize(NestedLoopCount);
5106  SmallVector<Expr *, 4> LoopMultipliers;
5107  {
5108  ExprResult Div;
5109  // Go from inner nested loop to outer.
5110  for (int Cnt = NestedLoopCount - 1; Cnt >= 0; --Cnt) {
5111  LoopIterationSpace &IS = IterSpaces[Cnt];
5112  SourceLocation UpdLoc = IS.IncSrcRange.getBegin();
5113  // Build: Iter = (IV / Div) % IS.NumIters
5114  // where Div is product of previous iterations' IS.NumIters.
5115  ExprResult Iter;
5116  if (Div.isUsable()) {
5117  Iter =
5118  SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Div, IV.get(), Div.get());
5119  } else {
5120  Iter = IV;
5121  assert((Cnt == (int)NestedLoopCount - 1) &&
5122  "unusable div expected on first iteration only");
5123  }
5124 
5125  if (Cnt != 0 && Iter.isUsable())
5126  Iter = SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Rem, Iter.get(),
5127  IS.NumIterations);
5128  if (!Iter.isUsable()) {
5129  HasErrors = true;
5130  break;
5131  }
5132 
5133  // Build update: IS.CounterVar(Private) = IS.Start + Iter * IS.Step
5134  auto *VD = cast<VarDecl>(cast<DeclRefExpr>(IS.CounterVar)->getDecl());
5135  DeclRefExpr *CounterVar = buildDeclRefExpr(
5136  SemaRef, VD, IS.CounterVar->getType(), IS.CounterVar->getExprLoc(),
5137  /*RefersToCapture=*/true);
5138  ExprResult Init = buildCounterInit(SemaRef, CurScope, UpdLoc, CounterVar,
5139  IS.CounterInit, Captures);
5140  if (!Init.isUsable()) {
5141  HasErrors = true;
5142  break;
5143  }
5145  SemaRef, CurScope, UpdLoc, CounterVar, IS.CounterInit, Iter,
5146  IS.CounterStep, IS.Subtract, &Captures);
5147  if (!Update.isUsable()) {
5148  HasErrors = true;
5149  break;
5150  }
5151 
5152  // Build final: IS.CounterVar = IS.Start + IS.NumIters * IS.Step
5154  SemaRef, CurScope, UpdLoc, CounterVar, IS.CounterInit,
5155  IS.NumIterations, IS.CounterStep, IS.Subtract, &Captures);
5156  if (!Final.isUsable()) {
5157  HasErrors = true;
5158  break;
5159  }
5160 
5161  // Build Div for the next iteration: Div <- Div * IS.NumIters
5162  if (Cnt != 0) {
5163  if (Div.isUnset())
5164  Div = IS.NumIterations;
5165  else
5166  Div = SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Mul, Div.get(),
5167  IS.NumIterations);
5168 
5169  // Add parentheses (for debugging purposes only).
5170  if (Div.isUsable())
5171  Div = tryBuildCapture(SemaRef, Div.get(), Captures);
5172  if (!Div.isUsable()) {
5173  HasErrors = true;
5174  break;
5175  }
5176  LoopMultipliers.push_back(Div.get());
5177  }
5178  if (!Update.isUsable() || !Final.isUsable()) {
5179  HasErrors = true;
5180  break;
5181  }
5182  // Save results
5183  Built.Counters[Cnt] = IS.CounterVar;
5184  Built.PrivateCounters[Cnt] = IS.PrivateCounterVar;
5185  Built.Inits[Cnt] = Init.get();
5186  Built.Updates[Cnt] = Update.get();
5187  Built.Finals[Cnt] = Final.get();
5188  }
5189  }
5190 
5191  if (HasErrors)
5192  return 0;
5193 
5194  // Save results
5195  Built.IterationVarRef = IV.get();
5196  Built.LastIteration = LastIteration.get();
5197  Built.NumIterations = NumIterations.get();
5198  Built.CalcLastIteration =
5199  SemaRef.ActOnFinishFullExpr(CalcLastIteration.get()).get();
5200  Built.PreCond = PreCond.get();
5201  Built.PreInits = buildPreInits(C, Captures);
5202  Built.Cond = Cond.get();
5203  Built.Init = Init.get();
5204  Built.Inc = Inc.get();
5205  Built.LB = LB.get();
5206  Built.UB = UB.get();
5207  Built.IL = IL.get();
5208  Built.ST = ST.get();
5209  Built.EUB = EUB.get();
5210  Built.NLB = NextLB.get();
5211  Built.NUB = NextUB.get();
5212  Built.PrevLB = PrevLB.get();
5213  Built.PrevUB = PrevUB.get();
5214  Built.DistInc = DistInc.get();
5215  Built.PrevEUB = PrevEUB.get();
5216  Built.DistCombinedFields.LB = CombLB.get();
5217  Built.DistCombinedFields.UB = CombUB.get();
5218  Built.DistCombinedFields.EUB = CombEUB.get();
5219  Built.DistCombinedFields.Init = CombInit.get();
5220  Built.DistCombinedFields.Cond = CombCond.get();
5221  Built.DistCombinedFields.NLB = CombNextLB.get();
5222  Built.DistCombinedFields.NUB = CombNextUB.get();
5223 
5224  Expr *CounterVal = SemaRef.DefaultLvalueConversion(IV.get()).get();
5225  // Fill data for doacross depend clauses.
5226  for (const auto &Pair : DSA.getDoacrossDependClauses()) {
5227  if (Pair.first->getDependencyKind() == OMPC_DEPEND_source) {
5228  Pair.first->setCounterValue(CounterVal);
5229  } else {
5230  if (NestedLoopCount != Pair.second.size() ||
5231  NestedLoopCount != LoopMultipliers.size() + 1) {
5232  // Erroneous case - clause has some problems.
5233  Pair.first->setCounterValue(CounterVal);
5234  continue;
5235  }
5236  assert(Pair.first->getDependencyKind() == OMPC_DEPEND_sink);
5237  auto I = Pair.second.rbegin();
5238  auto IS = IterSpaces.rbegin();
5239  auto ILM = LoopMultipliers.rbegin();
5240  Expr *UpCounterVal = CounterVal;
5241  Expr *Multiplier = nullptr;
5242  for (int Cnt = NestedLoopCount - 1; Cnt >= 0; --Cnt) {
5243  if (I->first) {
5244  assert(IS->CounterStep);
5245  Expr *NormalizedOffset =
5246  SemaRef
5247  .BuildBinOp(CurScope, I->first->getExprLoc(), BO_Div,
5248  I->first, IS->CounterStep)
5249  .get();
5250  if (Multiplier) {
5251  NormalizedOffset =
5252  SemaRef
5253  .BuildBinOp(CurScope, I->first->getExprLoc(), BO_Mul,
5254  NormalizedOffset, Multiplier)
5255  .get();
5256  }
5257  assert(I->second == OO_Plus || I->second == OO_Minus);
5258  BinaryOperatorKind BOK = (I->second == OO_Plus) ? BO_Add : BO_Sub;
5259  UpCounterVal = SemaRef
5260  .BuildBinOp(CurScope, I->first->getExprLoc(), BOK,
5261  UpCounterVal, NormalizedOffset)
5262  .get();
5263  }
5264  Multiplier = *ILM;
5265  ++I;
5266  ++IS;
5267  ++ILM;
5268  }
5269  Pair.first->setCounterValue(UpCounterVal);
5270  }
5271  }
5272 
5273  return NestedLoopCount;
5274 }
5275 
5277  auto CollapseClauses =
5278  OMPExecutableDirective::getClausesOfKind<OMPCollapseClause>(Clauses);
5279  if (CollapseClauses.begin() != CollapseClauses.end())
5280  return (*CollapseClauses.begin())->getNumForLoops();
5281  return nullptr;
5282 }
5283 
5285  auto OrderedClauses =
5286  OMPExecutableDirective::getClausesOfKind<OMPOrderedClause>(Clauses);
5287  if (OrderedClauses.begin() != OrderedClauses.end())
5288  return (*OrderedClauses.begin())->getNumForLoops();
5289  return nullptr;
5290 }
5291 
5293  const ArrayRef<OMPClause *> Clauses) {
5294  const OMPSafelenClause *Safelen = nullptr;
5295  const OMPSimdlenClause *Simdlen = nullptr;
5296 
5297  for (const OMPClause *Clause : Clauses) {
5298  if (Clause->getClauseKind() == OMPC_safelen)
5299  Safelen = cast<OMPSafelenClause>(Clause);
5300  else if (Clause->getClauseKind() == OMPC_simdlen)
5301  Simdlen = cast<OMPSimdlenClause>(Clause);
5302  if (Safelen && Simdlen)
5303  break;
5304  }
5305 
5306  if (Simdlen && Safelen) {
5307  llvm::APSInt SimdlenRes, SafelenRes;
5308  const Expr *SimdlenLength = Simdlen->getSimdlen();
5309  const Expr *SafelenLength = Safelen->getSafelen();
5310  if (SimdlenLength->isValueDependent() || SimdlenLength->isTypeDependent() ||
5311  SimdlenLength->isInstantiationDependent() ||
5312  SimdlenLength->containsUnexpandedParameterPack())
5313  return false;
5314  if (SafelenLength->isValueDependent() || SafelenLength->isTypeDependent() ||
5315  SafelenLength->isInstantiationDependent() ||
5316  SafelenLength->containsUnexpandedParameterPack())
5317  return false;
5318  SimdlenLength->EvaluateAsInt(SimdlenRes, S.Context);
5319  SafelenLength->EvaluateAsInt(SafelenRes, S.Context);
5320  // OpenMP 4.5 [2.8.1, simd Construct, Restrictions]
5321  // If both simdlen and safelen clauses are specified, the value of the
5322  // simdlen parameter must be less than or equal to the value of the safelen
5323  // parameter.
5324  if (SimdlenRes > SafelenRes) {
5325  S.Diag(SimdlenLength->getExprLoc(),
5326  diag::err_omp_wrong_simdlen_safelen_values)
5327  << SimdlenLength->getSourceRange() << SafelenLength->getSourceRange();
5328  return true;
5329  }
5330  }
5331  return false;
5332 }
5333 
5334 StmtResult
5336  SourceLocation StartLoc, SourceLocation EndLoc,
5337  VarsWithInheritedDSAType &VarsWithImplicitDSA) {
5338  if (!AStmt)
5339  return StmtError();
5340 
5341  assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
5343  // In presence of clause 'collapse' or 'ordered' with number of loops, it will
5344  // define the nested loops number.
5345  unsigned NestedLoopCount = checkOpenMPLoop(
5346  OMPD_simd, getCollapseNumberExpr(Clauses), getOrderedNumberExpr(Clauses),
5347  AStmt, *this, *DSAStack, VarsWithImplicitDSA, B);
5348  if (NestedLoopCount == 0)
5349  return StmtError();
5350 
5351  assert((CurContext->isDependentContext() || B.builtAll()) &&
5352  "omp simd loop exprs were not built");
5353 
5354  if (!CurContext->isDependentContext()) {
5355  // Finalize the clauses that need pre-built expressions for CodeGen.
5356  for (OMPClause *C : Clauses) {
5357  if (auto *LC = dyn_cast<OMPLinearClause>(C))
5358  if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
5359  B.NumIterations, *this, CurScope,
5360  DSAStack))
5361  return StmtError();
5362  }
5363  }
5364 
5365  if (checkSimdlenSafelenSpecified(*this, Clauses))
5366  return StmtError();
5367 
5368  setFunctionHasBranchProtectedScope();
5369  return OMPSimdDirective::Create(Context, StartLoc, EndLoc, NestedLoopCount,
5370  Clauses, AStmt, B);
5371 }
5372 
5373 StmtResult
5375  SourceLocation StartLoc, SourceLocation EndLoc,
5376  VarsWithInheritedDSAType &VarsWithImplicitDSA) {
5377  if (!AStmt)
5378  return StmtError();
5379 
5380  assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
5382  // In presence of clause 'collapse' or 'ordered' with number of loops, it will
5383  // define the nested loops number.
5384  unsigned NestedLoopCount = checkOpenMPLoop(
5385  OMPD_for, getCollapseNumberExpr(Clauses), getOrderedNumberExpr(Clauses),
5386  AStmt, *this, *DSAStack, VarsWithImplicitDSA, B);
5387  if (NestedLoopCount == 0)
5388  return StmtError();
5389 
5390  assert((CurContext->isDependentContext() || B.builtAll()) &&
5391  "omp for loop exprs were not built");
5392 
5393  if (!CurContext->isDependentContext()) {
5394  // Finalize the clauses that need pre-built expressions for CodeGen.
5395  for (OMPClause *C : Clauses) {
5396  if (auto *LC = dyn_cast<OMPLinearClause>(C))
5397  if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
5398  B.NumIterations, *this, CurScope,
5399  DSAStack))
5400  return StmtError();
5401  }
5402  }
5403 
5404  setFunctionHasBranchProtectedScope();
5405  return OMPForDirective::Create(Context, StartLoc, EndLoc, NestedLoopCount,
5406  Clauses, AStmt, B, DSAStack->isCancelRegion());
5407 }
5408 
5410  ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
5411  SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
5412  if (!AStmt)
5413  return StmtError();
5414 
5415  assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
5417  // In presence of clause 'collapse' or 'ordered' with number of loops, it will
5418  // define the nested loops number.
5419  unsigned NestedLoopCount =
5420  checkOpenMPLoop(OMPD_for_simd, getCollapseNumberExpr(Clauses),
5421  getOrderedNumberExpr(Clauses), AStmt, *this, *DSAStack,
5422  VarsWithImplicitDSA, B);
5423  if (NestedLoopCount == 0)
5424  return StmtError();
5425 
5426  assert((CurContext->isDependentContext() || B.builtAll()) &&
5427  "omp for simd loop exprs were not built");
5428 
5429  if (!CurContext->isDependentContext()) {
5430  // Finalize the clauses that need pre-built expressions for CodeGen.
5431  for (OMPClause *C : Clauses) {
5432  if (auto *LC = dyn_cast<OMPLinearClause>(C))
5433  if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
5434  B.NumIterations, *this, CurScope,
5435  DSAStack))
5436  return StmtError();
5437  }
5438  }
5439 
5440  if (checkSimdlenSafelenSpecified(*this, Clauses))
5441  return StmtError();
5442 
5443  setFunctionHasBranchProtectedScope();
5444  return OMPForSimdDirective::Create(Context, StartLoc, EndLoc, NestedLoopCount,
5445  Clauses, AStmt, B);
5446 }
5447 
5449  Stmt *AStmt,
5450  SourceLocation StartLoc,
5451  SourceLocation EndLoc) {
5452  if (!AStmt)
5453  return StmtError();
5454 
5455  assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
5456  auto BaseStmt = AStmt;
5457  while (auto *CS = dyn_cast_or_null<CapturedStmt>(BaseStmt))
5458  BaseStmt = CS->getCapturedStmt();
5459  if (auto *C = dyn_cast_or_null<CompoundStmt>(BaseStmt)) {
5460  auto S = C->children();
5461  if (S.begin() == S.end())
5462  return StmtError();
5463  // All associated statements must be '#pragma omp section' except for
5464  // the first one.
5465  for (Stmt *SectionStmt : llvm::make_range(std::next(S.begin()), S.end())) {
5466  if (!SectionStmt || !isa<OMPSectionDirective>(SectionStmt)) {
5467  if (SectionStmt)
5468  Diag(SectionStmt->getLocStart(),
5469  diag::err_omp_sections_substmt_not_section);
5470  return StmtError();
5471  }
5472  cast<OMPSectionDirective>(SectionStmt)
5473  ->setHasCancel(DSAStack->isCancelRegion());
5474  }
5475  } else {
5476  Diag(AStmt->getLocStart(), diag::err_omp_sections_not_compound_stmt);
5477  return StmtError();
5478  }
5479 
5480  setFunctionHasBranchProtectedScope();
5481 
5482  return OMPSectionsDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
5483  DSAStack->isCancelRegion());
5484 }
5485 
5487  SourceLocation StartLoc,
5488  SourceLocation EndLoc) {
5489  if (!AStmt)
5490  return StmtError();
5491 
5492  assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
5493 
5494  setFunctionHasBranchProtectedScope();
5495  DSAStack->setParentCancelRegion(DSAStack->isCancelRegion());
5496 
5497  return OMPSectionDirective::Create(Context, StartLoc, EndLoc, AStmt,
5498  DSAStack->isCancelRegion());
5499 }
5500 
5502  Stmt *AStmt,
5503  SourceLocation StartLoc,
5504  SourceLocation EndLoc) {
5505  if (!AStmt)
5506  return StmtError();
5507 
5508  assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
5509 
5510  setFunctionHasBranchProtectedScope();
5511 
5512  // OpenMP [2.7.3, single Construct, Restrictions]
5513  // The copyprivate clause must not be used with the nowait clause.
5514  const OMPClause *Nowait = nullptr;
5515  const OMPClause *Copyprivate = nullptr;
5516  for (const OMPClause *Clause : Clauses) {
5517  if (Clause->getClauseKind() == OMPC_nowait)
5518  Nowait = Clause;
5519  else if (Clause->getClauseKind() == OMPC_copyprivate)
5520  Copyprivate = Clause;
5521  if (Copyprivate && Nowait) {
5522  Diag(Copyprivate->getLocStart(),
5523  diag::err_omp_single_copyprivate_with_nowait);
5524  Diag(Nowait->getLocStart(), diag::note_omp_nowait_clause_here);
5525  return StmtError();
5526  }
5527  }
5528 
5529  return OMPSingleDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt);
5530 }
5531 
5533  SourceLocation StartLoc,
5534  SourceLocation EndLoc) {
5535  if (!AStmt)
5536  return StmtError();
5537 
5538  assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
5539 
5540  setFunctionHasBranchProtectedScope();
5541 
5542  return OMPMasterDirective::Create(Context, StartLoc, EndLoc, AStmt);
5543 }
5544 
5546  const DeclarationNameInfo &DirName, ArrayRef<OMPClause *> Clauses,
5547  Stmt *AStmt, SourceLocation StartLoc, SourceLocation EndLoc) {
5548  if (!AStmt)
5549  return StmtError();
5550 
5551  assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
5552 
5553  bool ErrorFound = false;
5554  llvm::APSInt Hint;
5555  SourceLocation HintLoc;
5556  bool DependentHint = false;
5557  for (const OMPClause *C : Clauses) {
5558  if (C->getClauseKind() == OMPC_hint) {
5559  if (!DirName.getName()) {
5560  Diag(C->getLocStart(), diag::err_omp_hint_clause_no_name);
5561  ErrorFound = true;
5562  }
5563  Expr *E = cast<OMPHintClause>(C)->getHint();
5564  if (E->isTypeDependent() || E->isValueDependent() ||
5565  E->isInstantiationDependent()) {
5566  DependentHint = true;
5567  } else {
5568  Hint = E->EvaluateKnownConstInt(Context);
5569  HintLoc = C->getLocStart();
5570  }
5571  }
5572  }
5573  if (ErrorFound)
5574  return StmtError();
5575  const auto Pair = DSAStack->getCriticalWithHint(DirName);
5576  if (Pair.first && DirName.getName() && !DependentHint) {
5577  if (llvm::APSInt::compareValues(Hint, Pair.second) != 0) {
5578  Diag(StartLoc, diag::err_omp_critical_with_hint);
5579  if (HintLoc.isValid())
5580  Diag(HintLoc, diag::note_omp_critical_hint_here)
5581  << 0 << Hint.toString(/*Radix=*/10, /*Signed=*/false);
5582  else
5583  Diag(StartLoc, diag::note_omp_critical_no_hint) << 0;
5584  if (const auto *C = Pair.first->getSingleClause<OMPHintClause>()) {
5585  Diag(C->getLocStart(), diag::note_omp_critical_hint_here)
5586  << 1
5587  << C->getHint()->EvaluateKnownConstInt(Context).toString(
5588  /*Radix=*/10, /*Signed=*/false);
5589  } else {
5590  Diag(Pair.first->getLocStart(), diag::note_omp_critical_no_hint) << 1;
5591  }
5592  }
5593  }
5594 
5595  setFunctionHasBranchProtectedScope();
5596 
5597  auto *Dir = OMPCriticalDirective::Create(Context, DirName, StartLoc, EndLoc,
5598  Clauses, AStmt);
5599  if (!Pair.first && DirName.getName() && !DependentHint)
5600  DSAStack->addCriticalWithHint(Dir, Hint);
5601  return Dir;
5602 }
5603 
5605  ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
5606  SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
5607  if (!AStmt)
5608  return StmtError();
5609 
5610  auto *CS = cast<CapturedStmt>(AStmt);
5611  // 1.2.2 OpenMP Language Terminology
5612  // Structured block - An executable statement with a single entry at the
5613  // top and a single exit at the bottom.
5614  // The point of exit cannot be a branch out of the structured block.
5615  // longjmp() and throw() must not violate the entry/exit criteria.
5616  CS->getCapturedDecl()->setNothrow();
5617 
5619  // In presence of clause 'collapse' or 'ordered' with number of loops, it will
5620  // define the nested loops number.
5621  unsigned NestedLoopCount =
5622  checkOpenMPLoop(OMPD_parallel_for, getCollapseNumberExpr(Clauses),
5623  getOrderedNumberExpr(Clauses), AStmt, *this, *DSAStack,
5624  VarsWithImplicitDSA, B);
5625  if (NestedLoopCount == 0)
5626  return StmtError();
5627 
5628  assert((CurContext->isDependentContext() || B.builtAll()) &&
5629  "omp parallel for loop exprs were not built");
5630 
5631  if (!CurContext->isDependentContext()) {
5632  // Finalize the clauses that need pre-built expressions for CodeGen.
5633  for (OMPClause *C : Clauses) {
5634  if (auto *LC = dyn_cast<OMPLinearClause>(C))
5635  if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
5636  B.NumIterations, *this, CurScope,
5637  DSAStack))
5638  return StmtError();
5639  }
5640  }
5641 
5642  setFunctionHasBranchProtectedScope();
5643  return OMPParallelForDirective::Create(Context, StartLoc, EndLoc,
5644  NestedLoopCount, Clauses, AStmt, B,
5645  DSAStack->isCancelRegion());
5646 }
5647 
5649  ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
5650  SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
5651  if (!AStmt)
5652  return StmtError();
5653 
5654  auto *CS = cast<CapturedStmt>(AStmt);
5655  // 1.2.2 OpenMP Language Terminology
5656  // Structured block - An executable statement with a single entry at the
5657  // top and a single exit at the bottom.
5658  // The point of exit cannot be a branch out of the structured block.