1 //===--- SemaOpenMP.cpp - Semantic Analysis for OpenMP constructs ---------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 /// \file
9 /// This file implements semantic analysis for OpenMP directives and
10 /// clauses.
11 ///
12 //===----------------------------------------------------------------------===//
13 
14 #include "TreeTransform.h"
15 #include "clang/AST/ASTContext.h"
16 #include "clang/AST/ASTMutationListener.h"
17 #include "clang/AST/CXXInheritance.h"
18 #include "clang/AST/Decl.h"
19 #include "clang/AST/DeclCXX.h"
20 #include "clang/AST/DeclOpenMP.h"
21 #include "clang/AST/OpenMPClause.h"
22 #include "clang/AST/StmtCXX.h"
23 #include "clang/AST/StmtOpenMP.h"
24 #include "clang/AST/StmtVisitor.h"
25 #include "clang/AST/TypeOrdering.h"
26 #include "clang/Basic/DiagnosticSema.h"
27 #include "clang/Basic/OpenMPKinds.h"
28 #include "clang/Basic/PartialDiagnostic.h"
29 #include "clang/Basic/TargetInfo.h"
30 #include "clang/Sema/Initialization.h"
31 #include "clang/Sema/Lookup.h"
32 #include "clang/Sema/Scope.h"
33 #include "clang/Sema/ScopeInfo.h"
34 #include "clang/Sema/SemaInternal.h"
35 #include "llvm/ADT/IndexedMap.h"
36 #include "llvm/ADT/PointerEmbeddedInt.h"
37 #include "llvm/ADT/STLExtras.h"
38 #include "llvm/ADT/SmallSet.h"
39 #include "llvm/ADT/StringExtras.h"
40 #include "llvm/Frontend/OpenMP/OMPAssume.h"
41 #include "llvm/Frontend/OpenMP/OMPConstants.h"
42 #include <set>
43 
44 using namespace clang;
45 using namespace llvm::omp;
46 
47 //===----------------------------------------------------------------------===//
48 // Stack of data-sharing attributes for variables
49 //===----------------------------------------------------------------------===//
50 
51 static const Expr *checkMapClauseExpressionBase(
52     Sema &SemaRef, Expr *E,
53     OMPClauseMappableExprCommon::MappableExprComponentList &CurComponents,
54     OpenMPClauseKind CKind, OpenMPDirectiveKind DKind, bool NoDiagnose);
55 
56 namespace {
57 /// Default data sharing attributes, which can be applied to directive.
58 enum DefaultDataSharingAttributes {
59   DSA_unspecified = 0,       /// Data sharing attribute not specified.
60   DSA_none = 1 << 0,         /// Default data sharing attribute 'none'.
61   DSA_shared = 1 << 1,       /// Default data sharing attribute 'shared'.
62   DSA_private = 1 << 2,      /// Default data sharing attribute 'private'.
63   DSA_firstprivate = 1 << 3, /// Default data sharing attribute 'firstprivate'.
64 };
65 
66 /// Stack for tracking declarations used in OpenMP directives and
67 /// clauses and their data-sharing attributes.
68 class DSAStackTy {
69 public:
70   struct DSAVarData {
71     OpenMPDirectiveKind DKind = OMPD_unknown;
72     OpenMPClauseKind CKind = OMPC_unknown;
73     unsigned Modifier = 0;
74     const Expr *RefExpr = nullptr;
75     DeclRefExpr *PrivateCopy = nullptr;
76     SourceLocation ImplicitDSALoc;
77     bool AppliedToPointee = false;
78     DSAVarData() = default;
79     DSAVarData(OpenMPDirectiveKind DKind, OpenMPClauseKind CKind,
80                const Expr *RefExpr, DeclRefExpr *PrivateCopy,
81                SourceLocation ImplicitDSALoc, unsigned Modifier,
82                bool AppliedToPointee)
83         : DKind(DKind), CKind(CKind), Modifier(Modifier), RefExpr(RefExpr),
84           PrivateCopy(PrivateCopy), ImplicitDSALoc(ImplicitDSALoc),
85           AppliedToPointee(AppliedToPointee) {}
86   };
87   using OperatorOffsetTy =
88       llvm::SmallVector<std::pair<Expr *, OverloadedOperatorKind>, 4>;
89   using DoacrossDependMapTy =
90       llvm::DenseMap<OMPDependClause *, OperatorOffsetTy>;
91   /// Kind of the declaration used in the uses_allocators clauses.
92   enum class UsesAllocatorsDeclKind {
93     /// Predefined allocator
94     PredefinedAllocator,
95     /// User-defined allocator
96     UserDefinedAllocator,
97     /// The declaration that represent allocator trait
98     AllocatorTrait,
99   };
100 
101 private:
102   struct DSAInfo {
103     OpenMPClauseKind Attributes = OMPC_unknown;
104     unsigned Modifier = 0;
105     /// Pointer to a reference expression and a flag which shows that the
106     /// variable is marked as lastprivate(true) or not (false).
107     llvm::PointerIntPair<const Expr *, 1, bool> RefExpr;
108     DeclRefExpr *PrivateCopy = nullptr;
109     /// true if the attribute is applied to the pointee, not the variable
110     /// itself.
111     bool AppliedToPointee = false;
112   };
113   using DeclSAMapTy = llvm::SmallDenseMap<const ValueDecl *, DSAInfo, 8>;
114   using UsedRefMapTy = llvm::SmallDenseMap<const ValueDecl *, const Expr *, 8>;
115   using LCDeclInfo = std::pair<unsigned, VarDecl *>;
116   using LoopControlVariablesMapTy =
117       llvm::SmallDenseMap<const ValueDecl *, LCDeclInfo, 8>;
118   /// Struct that associates a component with the clause kind where they are
119   /// found.
120   struct MappedExprComponentTy {
121     OMPClauseMappableExprCommon::MappableExprComponentLists Components;
122     OpenMPClauseKind Kind = OMPC_unknown;
123   };
124   using MappedExprComponentsTy =
125       llvm::DenseMap<const ValueDecl *, MappedExprComponentTy>;
126   using CriticalsWithHintsTy =
127       llvm::StringMap<std::pair<const OMPCriticalDirective *, llvm::APSInt>>;
128   struct ReductionData {
129     using BOKPtrType = llvm::PointerEmbeddedInt<BinaryOperatorKind, 16>;
130     SourceRange ReductionRange;
131     llvm::PointerUnion<const Expr *, BOKPtrType> ReductionOp;
132     ReductionData() = default;
133     void set(BinaryOperatorKind BO, SourceRange RR) {
134       ReductionRange = RR;
135       ReductionOp = BO;
136     }
137     void set(const Expr *RefExpr, SourceRange RR) {
138       ReductionRange = RR;
139       ReductionOp = RefExpr;
140     }
141   };
142   using DeclReductionMapTy =
143       llvm::SmallDenseMap<const ValueDecl *, ReductionData, 4>;
144   struct DefaultmapInfo {
145     OpenMPDefaultmapClauseModifier ImplicitBehavior =
146         OMPC_DEFAULTMAP_MODIFIER_unknown;
147     SourceLocation SLoc;
148     DefaultmapInfo() = default;
149     DefaultmapInfo(OpenMPDefaultmapClauseModifier M, SourceLocation Loc)
150         : ImplicitBehavior(M), SLoc(Loc) {}
151   };
152 
153   struct SharingMapTy {
154     DeclSAMapTy SharingMap;
155     DeclReductionMapTy ReductionMap;
156     UsedRefMapTy AlignedMap;
157     UsedRefMapTy NontemporalMap;
158     MappedExprComponentsTy MappedExprComponents;
159     LoopControlVariablesMapTy LCVMap;
160     DefaultDataSharingAttributes DefaultAttr = DSA_unspecified;
161     SourceLocation DefaultAttrLoc;
162     DefaultmapInfo DefaultmapMap[OMPC_DEFAULTMAP_unknown];
163     OpenMPDirectiveKind Directive = OMPD_unknown;
164     DeclarationNameInfo DirectiveName;
165     Scope *CurScope = nullptr;
166     DeclContext *Context = nullptr;
167     SourceLocation ConstructLoc;
168     /// Set of 'depend' clauses with 'sink|source' dependence kind. Required to
169     /// get the data (loop counters etc.) about enclosing loop-based construct.
170     /// This data is required during codegen.
171     DoacrossDependMapTy DoacrossDepends;
172     /// First argument (Expr *) contains optional argument of the
173     /// 'ordered' clause, the second one is true if the regions has 'ordered'
174     /// clause, false otherwise.
175     llvm::Optional<std::pair<const Expr *, OMPOrderedClause *>> OrderedRegion;
176     unsigned AssociatedLoops = 1;
177     bool HasMutipleLoops = false;
178     const Decl *PossiblyLoopCounter = nullptr;
179     bool NowaitRegion = false;
180     bool UntiedRegion = false;
181     bool CancelRegion = false;
182     bool LoopStart = false;
183     bool BodyComplete = false;
184     SourceLocation PrevScanLocation;
185     SourceLocation PrevOrderedLocation;
186     SourceLocation InnerTeamsRegionLoc;
187     /// Reference to the taskgroup task_reduction reference expression.
188     Expr *TaskgroupReductionRef = nullptr;
189     llvm::DenseSet<QualType> MappedClassesQualTypes;
190     SmallVector<Expr *, 4> InnerUsedAllocators;
191     llvm::DenseSet<CanonicalDeclPtr<Decl>> ImplicitTaskFirstprivates;
192     /// List of globals marked as declare target link in this target region
193     /// (isOpenMPTargetExecutionDirective(Directive) == true).
194     llvm::SmallVector<DeclRefExpr *, 4> DeclareTargetLinkVarDecls;
195     /// List of decls used in inclusive/exclusive clauses of the scan directive.
196     llvm::DenseSet<CanonicalDeclPtr<Decl>> UsedInScanDirective;
197     llvm::DenseMap<CanonicalDeclPtr<const Decl>, UsesAllocatorsDeclKind>
198         UsesAllocatorsDecls;
199     /// Data is required on creating capture fields for implicit
200     /// default first|private clause.
201     struct ImplicitDefaultFDInfoTy {
202       /// Field decl.
203       const FieldDecl *FD = nullptr;
204       /// Nesting stack level
205       size_t StackLevel = 0;
206       /// Capture variable decl.
207       VarDecl *VD = nullptr;
208       ImplicitDefaultFDInfoTy(const FieldDecl *FD, size_t StackLevel,
209                               VarDecl *VD)
210           : FD(FD), StackLevel(StackLevel), VD(VD) {}
211     };
212     /// List of captured fields
213     llvm::SmallVector<ImplicitDefaultFDInfoTy, 8>
214         ImplicitDefaultFirstprivateFDs;
215     Expr *DeclareMapperVar = nullptr;
216     SharingMapTy(OpenMPDirectiveKind DKind, DeclarationNameInfo Name,
217                  Scope *CurScope, SourceLocation Loc)
218         : Directive(DKind), DirectiveName(Name), CurScope(CurScope),
219           ConstructLoc(Loc) {}
220     SharingMapTy() = default;
221   };
222 
223   using StackTy = SmallVector<SharingMapTy, 4>;
224 
225   /// Stack of used declaration and their data-sharing attributes.
226   DeclSAMapTy Threadprivates;
227   const FunctionScopeInfo *CurrentNonCapturingFunctionScope = nullptr;
228   SmallVector<std::pair<StackTy, const FunctionScopeInfo *>, 4> Stack;
229   /// true, if check for DSA must be from parent directive, false, if
230   /// from current directive.
231   OpenMPClauseKind ClauseKindMode = OMPC_unknown;
232   Sema &SemaRef;
233   bool ForceCapturing = false;
234   /// true if all the variables in the target executable directives must be
235   /// captured by reference.
236   bool ForceCaptureByReferenceInTargetExecutable = false;
237   CriticalsWithHintsTy Criticals;
238   unsigned IgnoredStackElements = 0;
239 
240   /// Iterators over the stack iterate in order from innermost to outermost
241   /// directive.
242   using const_iterator = StackTy::const_reverse_iterator;
243   const_iterator begin() const {
244     return Stack.empty() ? const_iterator()
245                          : Stack.back().first.rbegin() + IgnoredStackElements;
246   }
247   const_iterator end() const {
248     return Stack.empty() ? const_iterator() : Stack.back().first.rend();
249   }
250   using iterator = StackTy::reverse_iterator;
251   iterator begin() {
252     return Stack.empty() ? iterator()
253                          : Stack.back().first.rbegin() + IgnoredStackElements;
254   }
255   iterator end() {
256     return Stack.empty() ? iterator() : Stack.back().first.rend();
257   }
258 
259   // Convenience operations to get at the elements of the stack.
260 
261   bool isStackEmpty() const {
262     return Stack.empty() ||
263            Stack.back().second != CurrentNonCapturingFunctionScope ||
264            Stack.back().first.size() <= IgnoredStackElements;
265   }
266   size_t getStackSize() const {
267     return isStackEmpty() ? 0
268                           : Stack.back().first.size() - IgnoredStackElements;
269   }
270 
271   SharingMapTy *getTopOfStackOrNull() {
272     size_t Size = getStackSize();
273     if (Size == 0)
274       return nullptr;
275     return &Stack.back().first[Size - 1];
276   }
277   const SharingMapTy *getTopOfStackOrNull() const {
278     return const_cast<DSAStackTy &>(*this).getTopOfStackOrNull();
279   }
280   SharingMapTy &getTopOfStack() {
281     assert(!isStackEmpty() && "no current directive");
282     return *getTopOfStackOrNull();
283   }
284   const SharingMapTy &getTopOfStack() const {
285     return const_cast<DSAStackTy &>(*this).getTopOfStack();
286   }
287 
288   SharingMapTy *getSecondOnStackOrNull() {
289     size_t Size = getStackSize();
290     if (Size <= 1)
291       return nullptr;
292     return &Stack.back().first[Size - 2];
293   }
294   const SharingMapTy *getSecondOnStackOrNull() const {
295     return const_cast<DSAStackTy &>(*this).getSecondOnStackOrNull();
296   }
297 
298   /// Get the stack element at a certain level (previously returned by
299   /// \c getNestingLevel).
300   ///
301   /// Note that nesting levels count from outermost to innermost, and this is
302   /// the reverse of our iteration order where new inner levels are pushed at
303   /// the front of the stack.
304   SharingMapTy &getStackElemAtLevel(unsigned Level) {
305     assert(Level < getStackSize() && "no such stack element");
306     return Stack.back().first[Level];
307   }
308   const SharingMapTy &getStackElemAtLevel(unsigned Level) const {
309     return const_cast<DSAStackTy &>(*this).getStackElemAtLevel(Level);
310   }
311 
312   DSAVarData getDSA(const_iterator &Iter, ValueDecl *D) const;
313 
314   /// Checks if the variable is a local for OpenMP region.
315   bool isOpenMPLocal(VarDecl *D, const_iterator Iter) const;
316 
317   /// Vector of previously declared requires directives
318   SmallVector<const OMPRequiresDecl *, 2> RequiresDecls;
319   /// omp_allocator_handle_t type.
320   QualType OMPAllocatorHandleT;
321   /// omp_depend_t type.
322   QualType OMPDependT;
323   /// omp_event_handle_t type.
324   QualType OMPEventHandleT;
325   /// omp_alloctrait_t type.
326   QualType OMPAlloctraitT;
327   /// Expression for the predefined allocators.
328   Expr *OMPPredefinedAllocators[OMPAllocateDeclAttr::OMPUserDefinedMemAlloc] = {
329       nullptr};
330   /// Vector of previously encountered target directives
331   SmallVector<SourceLocation, 2> TargetLocations;
332   SourceLocation AtomicLocation;
333   /// Vector of declare variant construct traits.
334   SmallVector<llvm::omp::TraitProperty, 8> ConstructTraits;
335 
336 public:
337   explicit DSAStackTy(Sema &S) : SemaRef(S) {}
338 
339   /// Sets omp_allocator_handle_t type.
340   void setOMPAllocatorHandleT(QualType Ty) { OMPAllocatorHandleT = Ty; }
341   /// Gets omp_allocator_handle_t type.
342   QualType getOMPAllocatorHandleT() const { return OMPAllocatorHandleT; }
343   /// Sets omp_alloctrait_t type.
344   void setOMPAlloctraitT(QualType Ty) { OMPAlloctraitT = Ty; }
345   /// Gets omp_alloctrait_t type.
346   QualType getOMPAlloctraitT() const { return OMPAlloctraitT; }
347   /// Sets the given default allocator.
348   void setAllocator(OMPAllocateDeclAttr::AllocatorTypeTy AllocatorKind,
349                     Expr *Allocator) {
350     OMPPredefinedAllocators[AllocatorKind] = Allocator;
351   }
352   /// Returns the specified default allocator.
353   Expr *getAllocator(OMPAllocateDeclAttr::AllocatorTypeTy AllocatorKind) const {
354     return OMPPredefinedAllocators[AllocatorKind];
355   }
356   /// Sets omp_depend_t type.
357   void setOMPDependT(QualType Ty) { OMPDependT = Ty; }
358   /// Gets omp_depend_t type.
359   QualType getOMPDependT() const { return OMPDependT; }
360 
361   /// Sets omp_event_handle_t type.
362   void setOMPEventHandleT(QualType Ty) { OMPEventHandleT = Ty; }
363   /// Gets omp_event_handle_t type.
364   QualType getOMPEventHandleT() const { return OMPEventHandleT; }
365 
366   bool isClauseParsingMode() const { return ClauseKindMode != OMPC_unknown; }
367   OpenMPClauseKind getClauseParsingMode() const {
368     assert(isClauseParsingMode() && "Must be in clause parsing mode.");
369     return ClauseKindMode;
370   }
371   void setClauseParsingMode(OpenMPClauseKind K) { ClauseKindMode = K; }
372 
373   bool isBodyComplete() const {
374     const SharingMapTy *Top = getTopOfStackOrNull();
375     return Top && Top->BodyComplete;
376   }
377   void setBodyComplete() { getTopOfStack().BodyComplete = true; }
378 
379   bool isForceVarCapturing() const { return ForceCapturing; }
380   void setForceVarCapturing(bool V) { ForceCapturing = V; }
381 
382   void setForceCaptureByReferenceInTargetExecutable(bool V) {
383     ForceCaptureByReferenceInTargetExecutable = V;
384   }
385   bool isForceCaptureByReferenceInTargetExecutable() const {
386     return ForceCaptureByReferenceInTargetExecutable;
387   }
388 
389   void push(OpenMPDirectiveKind DKind, const DeclarationNameInfo &DirName,
390             Scope *CurScope, SourceLocation Loc) {
391     assert(!IgnoredStackElements &&
392            "cannot change stack while ignoring elements");
393     if (Stack.empty() ||
394         Stack.back().second != CurrentNonCapturingFunctionScope)
395       Stack.emplace_back(StackTy(), CurrentNonCapturingFunctionScope);
396     Stack.back().first.emplace_back(DKind, DirName, CurScope, Loc);
397     Stack.back().first.back().DefaultAttrLoc = Loc;
398   }
399 
400   void pop() {
401     assert(!IgnoredStackElements &&
402            "cannot change stack while ignoring elements");
403     assert(!Stack.back().first.empty() &&
404            "Data-sharing attributes stack is empty!");
405     Stack.back().first.pop_back();
406   }
407 
408   /// RAII object to temporarily leave the scope of a directive when we want to
409   /// logically operate in its parent.
410   class ParentDirectiveScope {
411     DSAStackTy &Self;
412     bool Active;
413 
414   public:
415     ParentDirectiveScope(DSAStackTy &Self, bool Activate)
416         : Self(Self), Active(false) {
417       if (Activate)
418         enable();
419     }
420     ~ParentDirectiveScope() { disable(); }
421     void disable() {
422       if (Active) {
423         --Self.IgnoredStackElements;
424         Active = false;
425       }
426     }
427     void enable() {
428       if (!Active) {
429         ++Self.IgnoredStackElements;
430         Active = true;
431       }
432     }
433   };
434 
435   /// Marks that we're started loop parsing.
436   void loopInit() {
437     assert(isOpenMPLoopDirective(getCurrentDirective()) &&
438            "Expected loop-based directive.");
439     getTopOfStack().LoopStart = true;
440   }
441   /// Start capturing of the variables in the loop context.
442   void loopStart() {
443     assert(isOpenMPLoopDirective(getCurrentDirective()) &&
444            "Expected loop-based directive.");
445     getTopOfStack().LoopStart = false;
446   }
447   /// true, if variables are captured, false otherwise.
448   bool isLoopStarted() const {
449     assert(isOpenMPLoopDirective(getCurrentDirective()) &&
450            "Expected loop-based directive.");
451     return !getTopOfStack().LoopStart;
452   }
453   /// Marks (or clears) declaration as possibly loop counter.
454   void resetPossibleLoopCounter(const Decl *D = nullptr) {
455     getTopOfStack().PossiblyLoopCounter = D ? D->getCanonicalDecl() : D;
456   }
457   /// Gets the possible loop counter decl.
458   const Decl *getPossiblyLoopCunter() const {
459     return getTopOfStack().PossiblyLoopCounter;
460   }
461   /// Start new OpenMP region stack in new non-capturing function.
462   void pushFunction() {
463     assert(!IgnoredStackElements &&
464            "cannot change stack while ignoring elements");
465     const FunctionScopeInfo *CurFnScope = SemaRef.getCurFunction();
466     assert(!isa<CapturingScopeInfo>(CurFnScope));
467     CurrentNonCapturingFunctionScope = CurFnScope;
468   }
469   /// Pop region stack for non-capturing function.
470   void popFunction(const FunctionScopeInfo *OldFSI) {
471     assert(!IgnoredStackElements &&
472            "cannot change stack while ignoring elements");
473     if (!Stack.empty() && Stack.back().second == OldFSI) {
474       assert(Stack.back().first.empty());
475       Stack.pop_back();
476     }
477     CurrentNonCapturingFunctionScope = nullptr;
478     for (const FunctionScopeInfo *FSI : llvm::reverse(SemaRef.FunctionScopes)) {
479       if (!isa<CapturingScopeInfo>(FSI)) {
480         CurrentNonCapturingFunctionScope = FSI;
481         break;
482       }
483     }
484   }
485 
486   void addCriticalWithHint(const OMPCriticalDirective *D, llvm::APSInt Hint) {
487     Criticals.try_emplace(D->getDirectiveName().getAsString(), D, Hint);
488   }
489   const std::pair<const OMPCriticalDirective *, llvm::APSInt>
490   getCriticalWithHint(const DeclarationNameInfo &Name) const {
491     auto I = Criticals.find(Name.getAsString());
492     if (I != Criticals.end())
493       return I->second;
494     return std::make_pair(nullptr, llvm::APSInt());
495   }
496   /// If 'aligned' declaration for given variable \a D was not seen yet,
497   /// add it and return NULL; otherwise return previous occurrence's expression
498   /// for diagnostics.
499   const Expr *addUniqueAligned(const ValueDecl *D, const Expr *NewDE);
500   /// If 'nontemporal' declaration for given variable \a D was not seen yet,
501   /// add it and return NULL; otherwise return previous occurrence's expression
502   /// for diagnostics.
503   const Expr *addUniqueNontemporal(const ValueDecl *D, const Expr *NewDE);
504 
505   /// Register specified variable as loop control variable.
506   void addLoopControlVariable(const ValueDecl *D, VarDecl *Capture);
507   /// Check if the specified variable is a loop control variable for
508   /// current region.
509   /// \return The index of the loop control variable in the list of associated
510   /// for-loops (from outer to inner).
511   const LCDeclInfo isLoopControlVariable(const ValueDecl *D) const;
512   /// Check if the specified variable is a loop control variable for
513   /// parent region.
514   /// \return The index of the loop control variable in the list of associated
515   /// for-loops (from outer to inner).
516   const LCDeclInfo isParentLoopControlVariable(const ValueDecl *D) const;
517   /// Check if the specified variable is a loop control variable for
518   /// current region.
519   /// \return The index of the loop control variable in the list of associated
520   /// for-loops (from outer to inner).
521   const LCDeclInfo isLoopControlVariable(const ValueDecl *D,
522                                          unsigned Level) const;
523   /// Get the loop control variable for the I-th loop (or nullptr) in
524   /// parent directive.
525   const ValueDecl *getParentLoopControlVariable(unsigned I) const;
526 
527   /// Marks the specified decl \p D as used in scan directive.
528   void markDeclAsUsedInScanDirective(ValueDecl *D) {
529     if (SharingMapTy *Stack = getSecondOnStackOrNull())
530       Stack->UsedInScanDirective.insert(D);
531   }
532 
533   /// Checks if the specified declaration was used in the inner scan directive.
534   bool isUsedInScanDirective(ValueDecl *D) const {
535     if (const SharingMapTy *Stack = getTopOfStackOrNull())
536       return Stack->UsedInScanDirective.contains(D);
537     return false;
538   }
539 
540   /// Adds explicit data sharing attribute to the specified declaration.
541   void addDSA(const ValueDecl *D, const Expr *E, OpenMPClauseKind A,
542               DeclRefExpr *PrivateCopy = nullptr, unsigned Modifier = 0,
543               bool AppliedToPointee = false);
544 
545   /// Adds additional information for the reduction items with the reduction id
546   /// represented as an operator.
547   void addTaskgroupReductionData(const ValueDecl *D, SourceRange SR,
548                                  BinaryOperatorKind BOK);
549   /// Adds additional information for the reduction items with the reduction id
550   /// represented as reduction identifier.
551   void addTaskgroupReductionData(const ValueDecl *D, SourceRange SR,
552                                  const Expr *ReductionRef);
553   /// Returns the location and reduction operation from the innermost parent
554   /// region for the given \p D.
555   const DSAVarData
556   getTopMostTaskgroupReductionData(const ValueDecl *D, SourceRange &SR,
557                                    BinaryOperatorKind &BOK,
558                                    Expr *&TaskgroupDescriptor) const;
559   /// Returns the location and reduction operation from the innermost parent
560   /// region for the given \p D.
561   const DSAVarData
562   getTopMostTaskgroupReductionData(const ValueDecl *D, SourceRange &SR,
563                                    const Expr *&ReductionRef,
564                                    Expr *&TaskgroupDescriptor) const;
565   /// Return reduction reference expression for the current taskgroup or
566   /// parallel/worksharing directives with task reductions.
567   Expr *getTaskgroupReductionRef() const {
568     assert((getTopOfStack().Directive == OMPD_taskgroup ||
569             ((isOpenMPParallelDirective(getTopOfStack().Directive) ||
570               isOpenMPWorksharingDirective(getTopOfStack().Directive)) &&
571              !isOpenMPSimdDirective(getTopOfStack().Directive))) &&
572            "taskgroup reference expression requested for non taskgroup or "
573            "parallel/worksharing directive.");
574     return getTopOfStack().TaskgroupReductionRef;
575   }
576   /// Checks if the given \p VD declaration is actually a taskgroup reduction
577   /// descriptor variable at the \p Level of OpenMP regions.
578   bool isTaskgroupReductionRef(const ValueDecl *VD, unsigned Level) const {
579     return getStackElemAtLevel(Level).TaskgroupReductionRef &&
580            cast<DeclRefExpr>(getStackElemAtLevel(Level).TaskgroupReductionRef)
581                    ->getDecl() == VD;
582   }
583 
584   /// Returns data sharing attributes from top of the stack for the
585   /// specified declaration.
586   const DSAVarData getTopDSA(ValueDecl *D, bool FromParent);
587   /// Returns data-sharing attributes for the specified declaration.
588   const DSAVarData getImplicitDSA(ValueDecl *D, bool FromParent) const;
589   /// Returns data-sharing attributes for the specified declaration.
590   const DSAVarData getImplicitDSA(ValueDecl *D, unsigned Level) const;
591   /// Checks if the specified variables has data-sharing attributes which
592   /// match specified \a CPred predicate in any directive which matches \a DPred
593   /// predicate.
594   const DSAVarData
595   hasDSA(ValueDecl *D,
596          const llvm::function_ref<bool(OpenMPClauseKind, bool,
597                                        DefaultDataSharingAttributes)>
598              CPred,
599          const llvm::function_ref<bool(OpenMPDirectiveKind)> DPred,
600          bool FromParent) const;
601   /// Checks if the specified variables has data-sharing attributes which
602   /// match specified \a CPred predicate in any innermost directive which
603   /// matches \a DPred predicate.
604   const DSAVarData
605   hasInnermostDSA(ValueDecl *D,
606                   const llvm::function_ref<bool(OpenMPClauseKind, bool)> CPred,
607                   const llvm::function_ref<bool(OpenMPDirectiveKind)> DPred,
608                   bool FromParent) const;
609   /// Checks if the specified variables has explicit data-sharing
610   /// attributes which match specified \a CPred predicate at the specified
611   /// OpenMP region.
612   bool
613   hasExplicitDSA(const ValueDecl *D,
614                  const llvm::function_ref<bool(OpenMPClauseKind, bool)> CPred,
615                  unsigned Level, bool NotLastprivate = false) const;
616 
617   /// Returns true if the directive at level \Level matches in the
618   /// specified \a DPred predicate.
619   bool hasExplicitDirective(
620       const llvm::function_ref<bool(OpenMPDirectiveKind)> DPred,
621       unsigned Level) const;
622 
623   /// Finds a directive which matches specified \a DPred predicate.
624   bool hasDirective(
625       const llvm::function_ref<bool(
626           OpenMPDirectiveKind, const DeclarationNameInfo &, SourceLocation)>
627           DPred,
628       bool FromParent) const;
629 
630   /// Returns currently analyzed directive.
631   OpenMPDirectiveKind getCurrentDirective() const {
632     const SharingMapTy *Top = getTopOfStackOrNull();
633     return Top ? Top->Directive : OMPD_unknown;
634   }
635   /// Returns directive kind at specified level.
636   OpenMPDirectiveKind getDirective(unsigned Level) const {
637     assert(!isStackEmpty() && "No directive at specified level.");
638     return getStackElemAtLevel(Level).Directive;
639   }
640   /// Returns the capture region at the specified level.
641   OpenMPDirectiveKind getCaptureRegion(unsigned Level,
642                                        unsigned OpenMPCaptureLevel) const {
643     SmallVector<OpenMPDirectiveKind, 4> CaptureRegions;
644     getOpenMPCaptureRegions(CaptureRegions, getDirective(Level));
645     return CaptureRegions[OpenMPCaptureLevel];
646   }
647   /// Returns parent directive.
648   OpenMPDirectiveKind getParentDirective() const {
649     const SharingMapTy *Parent = getSecondOnStackOrNull();
650     return Parent ? Parent->Directive : OMPD_unknown;
651   }
652 
653   /// Add requires decl to internal vector
654   void addRequiresDecl(OMPRequiresDecl *RD) { RequiresDecls.push_back(RD); }
655 
656   /// Checks if the defined 'requires' directive has specified type of clause.
657   template <typename ClauseType> bool hasRequiresDeclWithClause() const {
658     return llvm::any_of(RequiresDecls, [](const OMPRequiresDecl *D) {
659       return llvm::any_of(D->clauselists(), [](const OMPClause *C) {
660         return isa<ClauseType>(C);
661       });
662     });
663   }
664 
665   /// Checks for a duplicate clause amongst previously declared requires
666   /// directives
667   bool hasDuplicateRequiresClause(ArrayRef<OMPClause *> ClauseList) const {
668     bool IsDuplicate = false;
669     for (OMPClause *CNew : ClauseList) {
670       for (const OMPRequiresDecl *D : RequiresDecls) {
671         for (const OMPClause *CPrev : D->clauselists()) {
672           if (CNew->getClauseKind() == CPrev->getClauseKind()) {
673             SemaRef.Diag(CNew->getBeginLoc(),
674                          diag::err_omp_requires_clause_redeclaration)
675                 << getOpenMPClauseName(CNew->getClauseKind());
676             SemaRef.Diag(CPrev->getBeginLoc(),
677                          diag::note_omp_requires_previous_clause)
678                 << getOpenMPClauseName(CPrev->getClauseKind());
679             IsDuplicate = true;
680           }
681         }
682       }
683     }
684     return IsDuplicate;
685   }
686 
687   /// Add location of previously encountered target to internal vector
688   void addTargetDirLocation(SourceLocation LocStart) {
689     TargetLocations.push_back(LocStart);
690   }
691 
692   /// Add location for the first encountered atomicc directive.
693   void addAtomicDirectiveLoc(SourceLocation Loc) {
694     if (AtomicLocation.isInvalid())
695       AtomicLocation = Loc;
696   }
697 
698   /// Returns the location of the first encountered atomic directive in the
699   /// module.
700   SourceLocation getAtomicDirectiveLoc() const { return AtomicLocation; }
701 
702   // Return previously encountered target region locations.
703   ArrayRef<SourceLocation> getEncounteredTargetLocs() const {
704     return TargetLocations;
705   }
706 
707   /// Set default data sharing attribute to none.
708   void setDefaultDSANone(SourceLocation Loc) {
709     getTopOfStack().DefaultAttr = DSA_none;
710     getTopOfStack().DefaultAttrLoc = Loc;
711   }
712   /// Set default data sharing attribute to shared.
713   void setDefaultDSAShared(SourceLocation Loc) {
714     getTopOfStack().DefaultAttr = DSA_shared;
715     getTopOfStack().DefaultAttrLoc = Loc;
716   }
717   /// Set default data sharing attribute to private.
718   void setDefaultDSAPrivate(SourceLocation Loc) {
719     getTopOfStack().DefaultAttr = DSA_private;
720     getTopOfStack().DefaultAttrLoc = Loc;
721   }
722   /// Set default data sharing attribute to firstprivate.
723   void setDefaultDSAFirstPrivate(SourceLocation Loc) {
724     getTopOfStack().DefaultAttr = DSA_firstprivate;
725     getTopOfStack().DefaultAttrLoc = Loc;
726   }
727   /// Set default data mapping attribute to Modifier:Kind
728   void setDefaultDMAAttr(OpenMPDefaultmapClauseModifier M,
729                          OpenMPDefaultmapClauseKind Kind, SourceLocation Loc) {
730     DefaultmapInfo &DMI = getTopOfStack().DefaultmapMap[Kind];
731     DMI.ImplicitBehavior = M;
732     DMI.SLoc = Loc;
733   }
734   /// Check whether the implicit-behavior has been set in defaultmap
735   bool checkDefaultmapCategory(OpenMPDefaultmapClauseKind VariableCategory) {
736     if (VariableCategory == OMPC_DEFAULTMAP_unknown)
737       return getTopOfStack()
738                      .DefaultmapMap[OMPC_DEFAULTMAP_aggregate]
739                      .ImplicitBehavior != OMPC_DEFAULTMAP_MODIFIER_unknown ||
740              getTopOfStack()
741                      .DefaultmapMap[OMPC_DEFAULTMAP_scalar]
742                      .ImplicitBehavior != OMPC_DEFAULTMAP_MODIFIER_unknown ||
743              getTopOfStack()
744                      .DefaultmapMap[OMPC_DEFAULTMAP_pointer]
745                      .ImplicitBehavior != OMPC_DEFAULTMAP_MODIFIER_unknown;
746     return getTopOfStack().DefaultmapMap[VariableCategory].ImplicitBehavior !=
747            OMPC_DEFAULTMAP_MODIFIER_unknown;
748   }
749 
750   ArrayRef<llvm::omp::TraitProperty> getConstructTraits() {
751     return ConstructTraits;
752   }
753   void handleConstructTrait(ArrayRef<llvm::omp::TraitProperty> Traits,
754                             bool ScopeEntry) {
755     if (ScopeEntry)
756       ConstructTraits.append(Traits.begin(), Traits.end());
757     else
758       for (llvm::omp::TraitProperty Trait : llvm::reverse(Traits)) {
759         llvm::omp::TraitProperty Top = ConstructTraits.pop_back_val();
760         assert(Top == Trait && "Something left a trait on the stack!");
761         (void)Trait;
762         (void)Top;
763       }
764   }
765 
766   DefaultDataSharingAttributes getDefaultDSA(unsigned Level) const {
767     return getStackSize() <= Level ? DSA_unspecified
768                                    : getStackElemAtLevel(Level).DefaultAttr;
769   }
770   DefaultDataSharingAttributes getDefaultDSA() const {
771     return isStackEmpty() ? DSA_unspecified : getTopOfStack().DefaultAttr;
772   }
773   SourceLocation getDefaultDSALocation() const {
774     return isStackEmpty() ? SourceLocation() : getTopOfStack().DefaultAttrLoc;
775   }
776   OpenMPDefaultmapClauseModifier
777   getDefaultmapModifier(OpenMPDefaultmapClauseKind Kind) const {
778     return isStackEmpty()
779                ? OMPC_DEFAULTMAP_MODIFIER_unknown
780                : getTopOfStack().DefaultmapMap[Kind].ImplicitBehavior;
781   }
782   OpenMPDefaultmapClauseModifier
783   getDefaultmapModifierAtLevel(unsigned Level,
784                                OpenMPDefaultmapClauseKind Kind) const {
785     return getStackElemAtLevel(Level).DefaultmapMap[Kind].ImplicitBehavior;
786   }
787   bool isDefaultmapCapturedByRef(unsigned Level,
788                                  OpenMPDefaultmapClauseKind Kind) const {
789     OpenMPDefaultmapClauseModifier M =
790         getDefaultmapModifierAtLevel(Level, Kind);
791     if (Kind == OMPC_DEFAULTMAP_scalar || Kind == OMPC_DEFAULTMAP_pointer) {
792       return (M == OMPC_DEFAULTMAP_MODIFIER_alloc) ||
793              (M == OMPC_DEFAULTMAP_MODIFIER_to) ||
794              (M == OMPC_DEFAULTMAP_MODIFIER_from) ||
795              (M == OMPC_DEFAULTMAP_MODIFIER_tofrom);
796     }
797     return true;
798   }
799   static bool mustBeFirstprivateBase(OpenMPDefaultmapClauseModifier M,
800                                      OpenMPDefaultmapClauseKind Kind) {
801     switch (Kind) {
802     case OMPC_DEFAULTMAP_scalar:
803     case OMPC_DEFAULTMAP_pointer:
804       return (M == OMPC_DEFAULTMAP_MODIFIER_unknown) ||
805              (M == OMPC_DEFAULTMAP_MODIFIER_firstprivate) ||
806              (M == OMPC_DEFAULTMAP_MODIFIER_default);
807     case OMPC_DEFAULTMAP_aggregate:
808       return M == OMPC_DEFAULTMAP_MODIFIER_firstprivate;
809     default:
810       break;
811     }
812     llvm_unreachable("Unexpected OpenMPDefaultmapClauseKind enum");
813   }
814   bool mustBeFirstprivateAtLevel(unsigned Level,
815                                  OpenMPDefaultmapClauseKind Kind) const {
816     OpenMPDefaultmapClauseModifier M =
817         getDefaultmapModifierAtLevel(Level, Kind);
818     return mustBeFirstprivateBase(M, Kind);
819   }
820   bool mustBeFirstprivate(OpenMPDefaultmapClauseKind Kind) const {
821     OpenMPDefaultmapClauseModifier M = getDefaultmapModifier(Kind);
822     return mustBeFirstprivateBase(M, Kind);
823   }
824 
825   /// Checks if the specified variable is a threadprivate.
826   bool isThreadPrivate(VarDecl *D) {
827     const DSAVarData DVar = getTopDSA(D, false);
828     return isOpenMPThreadPrivate(DVar.CKind);
829   }
830 
831   /// Marks current region as ordered (it has an 'ordered' clause).
832   void setOrderedRegion(bool IsOrdered, const Expr *Param,
833                         OMPOrderedClause *Clause) {
834     if (IsOrdered)
835       getTopOfStack().OrderedRegion.emplace(Param, Clause);
836     else
837       getTopOfStack().OrderedRegion.reset();
838   }
839   /// Returns true, if region is ordered (has associated 'ordered' clause),
840   /// false - otherwise.
841   bool isOrderedRegion() const {
842     if (const SharingMapTy *Top = getTopOfStackOrNull())
843       return Top->OrderedRegion.hasValue();
844     return false;
845   }
846   /// Returns optional parameter for the ordered region.
847   std::pair<const Expr *, OMPOrderedClause *> getOrderedRegionParam() const {
848     if (const SharingMapTy *Top = getTopOfStackOrNull())
849       if (Top->OrderedRegion)
850         return Top->OrderedRegion.getValue();
851     return std::make_pair(nullptr, nullptr);
852   }
853   /// Returns true, if parent region is ordered (has associated
854   /// 'ordered' clause), false - otherwise.
855   bool isParentOrderedRegion() const {
856     if (const SharingMapTy *Parent = getSecondOnStackOrNull())
857       return Parent->OrderedRegion.hasValue();
858     return false;
859   }
860   /// Returns optional parameter for the ordered region.
861   std::pair<const Expr *, OMPOrderedClause *>
862   getParentOrderedRegionParam() const {
863     if (const SharingMapTy *Parent = getSecondOnStackOrNull())
864       if (Parent->OrderedRegion)
865         return Parent->OrderedRegion.getValue();
866     return std::make_pair(nullptr, nullptr);
867   }
868   /// Marks current region as nowait (it has a 'nowait' clause).
869   void setNowaitRegion(bool IsNowait = true) {
870     getTopOfStack().NowaitRegion = IsNowait;
871   }
872   /// Returns true, if parent region is nowait (has associated
873   /// 'nowait' clause), false - otherwise.
874   bool isParentNowaitRegion() const {
875     if (const SharingMapTy *Parent = getSecondOnStackOrNull())
876       return Parent->NowaitRegion;
877     return false;
878   }
879   /// Marks current region as untied (it has a 'untied' clause).
880   void setUntiedRegion(bool IsUntied = true) {
881     getTopOfStack().UntiedRegion = IsUntied;
882   }
883   /// Return true if current region is untied.
884   bool isUntiedRegion() const {
885     const SharingMapTy *Top = getTopOfStackOrNull();
886     return Top ? Top->UntiedRegion : false;
887   }
888   /// Marks parent region as cancel region.
889   void setParentCancelRegion(bool Cancel = true) {
890     if (SharingMapTy *Parent = getSecondOnStackOrNull())
891       Parent->CancelRegion |= Cancel;
892   }
893   /// Return true if current region has inner cancel construct.
894   bool isCancelRegion() const {
895     const SharingMapTy *Top = getTopOfStackOrNull();
896     return Top ? Top->CancelRegion : false;
897   }
898 
899   /// Mark that parent region already has scan directive.
900   void setParentHasScanDirective(SourceLocation Loc) {
901     if (SharingMapTy *Parent = getSecondOnStackOrNull())
902       Parent->PrevScanLocation = Loc;
903   }
904   /// Return true if current region has inner cancel construct.
905   bool doesParentHasScanDirective() const {
906     const SharingMapTy *Top = getSecondOnStackOrNull();
907     return Top ? Top->PrevScanLocation.isValid() : false;
908   }
909   /// Return true if current region has inner cancel construct.
910   SourceLocation getParentScanDirectiveLoc() const {
911     const SharingMapTy *Top = getSecondOnStackOrNull();
912     return Top ? Top->PrevScanLocation : SourceLocation();
913   }
914   /// Mark that parent region already has ordered directive.
915   void setParentHasOrderedDirective(SourceLocation Loc) {
916     if (SharingMapTy *Parent = getSecondOnStackOrNull())
917       Parent->PrevOrderedLocation = Loc;
918   }
919   /// Return true if current region has inner ordered construct.
920   bool doesParentHasOrderedDirective() const {
921     const SharingMapTy *Top = getSecondOnStackOrNull();
922     return Top ? Top->PrevOrderedLocation.isValid() : false;
923   }
924   /// Returns the location of the previously specified ordered directive.
925   SourceLocation getParentOrderedDirectiveLoc() const {
926     const SharingMapTy *Top = getSecondOnStackOrNull();
927     return Top ? Top->PrevOrderedLocation : SourceLocation();
928   }
929 
930   /// Set collapse value for the region.
931   void setAssociatedLoops(unsigned Val) {
932     getTopOfStack().AssociatedLoops = Val;
933     if (Val > 1)
934       getTopOfStack().HasMutipleLoops = true;
935   }
936   /// Return collapse value for region.
937   unsigned getAssociatedLoops() const {
938     const SharingMapTy *Top = getTopOfStackOrNull();
939     return Top ? Top->AssociatedLoops : 0;
940   }
941   /// Returns true if the construct is associated with multiple loops.
942   bool hasMutipleLoops() const {
943     const SharingMapTy *Top = getTopOfStackOrNull();
944     return Top ? Top->HasMutipleLoops : false;
945   }
946 
947   /// Marks current target region as one with closely nested teams
948   /// region.
949   void setParentTeamsRegionLoc(SourceLocation TeamsRegionLoc) {
950     if (SharingMapTy *Parent = getSecondOnStackOrNull())
951       Parent->InnerTeamsRegionLoc = TeamsRegionLoc;
952   }
953   /// Returns true, if current region has closely nested teams region.
954   bool hasInnerTeamsRegion() const {
955     return getInnerTeamsRegionLoc().isValid();
956   }
957   /// Returns location of the nested teams region (if any).
958   SourceLocation getInnerTeamsRegionLoc() const {
959     const SharingMapTy *Top = getTopOfStackOrNull();
960     return Top ? Top->InnerTeamsRegionLoc : SourceLocation();
961   }
962 
963   Scope *getCurScope() const {
964     const SharingMapTy *Top = getTopOfStackOrNull();
965     return Top ? Top->CurScope : nullptr;
966   }
967   void setContext(DeclContext *DC) { getTopOfStack().Context = DC; }
968   SourceLocation getConstructLoc() const {
969     const SharingMapTy *Top = getTopOfStackOrNull();
970     return Top ? Top->ConstructLoc : SourceLocation();
971   }
972 
973   /// Do the check specified in \a Check to all component lists and return true
974   /// if any issue is found.
975   bool checkMappableExprComponentListsForDecl(
976       const ValueDecl *VD, bool CurrentRegionOnly,
977       const llvm::function_ref<
978           bool(OMPClauseMappableExprCommon::MappableExprComponentListRef,
979                OpenMPClauseKind)>
980           Check) const {
981     if (isStackEmpty())
982       return false;
983     auto SI = begin();
984     auto SE = end();
985 
986     if (SI == SE)
987       return false;
988 
989     if (CurrentRegionOnly)
990       SE = std::next(SI);
991     else
992       std::advance(SI, 1);
993 
994     for (; SI != SE; ++SI) {
995       auto MI = SI->MappedExprComponents.find(VD);
996       if (MI != SI->MappedExprComponents.end())
997         for (OMPClauseMappableExprCommon::MappableExprComponentListRef L :
998              MI->second.Components)
999           if (Check(L, MI->second.Kind))
1000             return true;
1001     }
1002     return false;
1003   }
1004 
1005   /// Do the check specified in \a Check to all component lists at a given level
1006   /// and return true if any issue is found.
1007   bool checkMappableExprComponentListsForDeclAtLevel(
1008       const ValueDecl *VD, unsigned Level,
1009       const llvm::function_ref<
1010           bool(OMPClauseMappableExprCommon::MappableExprComponentListRef,
1011                OpenMPClauseKind)>
1012           Check) const {
1013     if (getStackSize() <= Level)
1014       return false;
1015 
1016     const SharingMapTy &StackElem = getStackElemAtLevel(Level);
1017     auto MI = StackElem.MappedExprComponents.find(VD);
1018     if (MI != StackElem.MappedExprComponents.end())
1019       for (OMPClauseMappableExprCommon::MappableExprComponentListRef L :
1020            MI->second.Components)
1021         if (Check(L, MI->second.Kind))
1022           return true;
1023     return false;
1024   }
1025 
1026   /// Create a new mappable expression component list associated with a given
1027   /// declaration and initialize it with the provided list of components.
1028   void addMappableExpressionComponents(
1029       const ValueDecl *VD,
1030       OMPClauseMappableExprCommon::MappableExprComponentListRef Components,
1031       OpenMPClauseKind WhereFoundClauseKind) {
1032     MappedExprComponentTy &MEC = getTopOfStack().MappedExprComponents[VD];
1033     // Create new entry and append the new components there.
1034     MEC.Components.resize(MEC.Components.size() + 1);
1035     MEC.Components.back().append(Components.begin(), Components.end());
1036     MEC.Kind = WhereFoundClauseKind;
1037   }
1038 
1039   unsigned getNestingLevel() const {
1040     assert(!isStackEmpty());
1041     return getStackSize() - 1;
1042   }
1043   void addDoacrossDependClause(OMPDependClause *C,
1044                                const OperatorOffsetTy &OpsOffs) {
1045     SharingMapTy *Parent = getSecondOnStackOrNull();
1046     assert(Parent && isOpenMPWorksharingDirective(Parent->Directive));
1047     Parent->DoacrossDepends.try_emplace(C, OpsOffs);
1048   }
1049   llvm::iterator_range<DoacrossDependMapTy::const_iterator>
1050   getDoacrossDependClauses() const {
1051     const SharingMapTy &StackElem = getTopOfStack();
1052     if (isOpenMPWorksharingDirective(StackElem.Directive)) {
1053       const DoacrossDependMapTy &Ref = StackElem.DoacrossDepends;
1054       return llvm::make_range(Ref.begin(), Ref.end());
1055     }
1056     return llvm::make_range(StackElem.DoacrossDepends.end(),
1057                             StackElem.DoacrossDepends.end());
1058   }
1059 
1060   // Store types of classes which have been explicitly mapped
1061   void addMappedClassesQualTypes(QualType QT) {
1062     SharingMapTy &StackElem = getTopOfStack();
1063     StackElem.MappedClassesQualTypes.insert(QT);
1064   }
1065 
1066   // Return set of mapped classes types
1067   bool isClassPreviouslyMapped(QualType QT) const {
1068     const SharingMapTy &StackElem = getTopOfStack();
1069     return StackElem.MappedClassesQualTypes.contains(QT);
1070   }
1071 
1072   /// Adds global declare target to the parent target region.
1073   void addToParentTargetRegionLinkGlobals(DeclRefExpr *E) {
1074     assert(*OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(
1075                E->getDecl()) == OMPDeclareTargetDeclAttr::MT_Link &&
1076            "Expected declare target link global.");
1077     for (auto &Elem : *this) {
1078       if (isOpenMPTargetExecutionDirective(Elem.Directive)) {
1079         Elem.DeclareTargetLinkVarDecls.push_back(E);
1080         return;
1081       }
1082     }
1083   }
1084 
1085   /// Returns the list of globals with declare target link if current directive
1086   /// is target.
1087   ArrayRef<DeclRefExpr *> getLinkGlobals() const {
1088     assert(isOpenMPTargetExecutionDirective(getCurrentDirective()) &&
1089            "Expected target executable directive.");
1090     return getTopOfStack().DeclareTargetLinkVarDecls;
1091   }
1092 
1093   /// Adds list of allocators expressions.
1094   void addInnerAllocatorExpr(Expr *E) {
1095     getTopOfStack().InnerUsedAllocators.push_back(E);
1096   }
1097   /// Return list of used allocators.
1098   ArrayRef<Expr *> getInnerAllocators() const {
1099     return getTopOfStack().InnerUsedAllocators;
1100   }
1101   /// Marks the declaration as implicitly firstprivate nin the task-based
1102   /// regions.
1103   void addImplicitTaskFirstprivate(unsigned Level, Decl *D) {
1104     getStackElemAtLevel(Level).ImplicitTaskFirstprivates.insert(D);
1105   }
1106   /// Checks if the decl is implicitly firstprivate in the task-based region.
1107   bool isImplicitTaskFirstprivate(Decl *D) const {
1108     return getTopOfStack().ImplicitTaskFirstprivates.contains(D);
1109   }
1110 
1111   /// Marks decl as used in uses_allocators clause as the allocator.
1112   void addUsesAllocatorsDecl(const Decl *D, UsesAllocatorsDeclKind Kind) {
1113     getTopOfStack().UsesAllocatorsDecls.try_emplace(D, Kind);
1114   }
1115   /// Checks if specified decl is used in uses allocator clause as the
1116   /// allocator.
1117   Optional<UsesAllocatorsDeclKind> isUsesAllocatorsDecl(unsigned Level,
1118                                                         const Decl *D) const {
1119     const SharingMapTy &StackElem = getTopOfStack();
1120     auto I = StackElem.UsesAllocatorsDecls.find(D);
1121     if (I == StackElem.UsesAllocatorsDecls.end())
1122       return None;
1123     return I->getSecond();
1124   }
1125   Optional<UsesAllocatorsDeclKind> isUsesAllocatorsDecl(const Decl *D) const {
1126     const SharingMapTy &StackElem = getTopOfStack();
1127     auto I = StackElem.UsesAllocatorsDecls.find(D);
1128     if (I == StackElem.UsesAllocatorsDecls.end())
1129       return None;
1130     return I->getSecond();
1131   }
1132 
1133   void addDeclareMapperVarRef(Expr *Ref) {
1134     SharingMapTy &StackElem = getTopOfStack();
1135     StackElem.DeclareMapperVar = Ref;
1136   }
1137   const Expr *getDeclareMapperVarRef() const {
1138     const SharingMapTy *Top = getTopOfStackOrNull();
1139     return Top ? Top->DeclareMapperVar : nullptr;
1140   }
1141   /// get captured field from ImplicitDefaultFirstprivateFDs
1142   VarDecl *getImplicitFDCapExprDecl(const FieldDecl *FD) const {
1143     const_iterator I = begin();
1144     const_iterator EndI = end();
1145     size_t StackLevel = getStackSize();
1146     for (; I != EndI; ++I) {
1147       if (I->DefaultAttr == DSA_firstprivate || I->DefaultAttr == DSA_private)
1148         break;
1149       StackLevel--;
1150     }
1151     assert((StackLevel > 0 && I != EndI) || (StackLevel == 0 && I == EndI));
1152     if (I == EndI)
1153       return nullptr;
1154     for (const auto &IFD : I->ImplicitDefaultFirstprivateFDs)
1155       if (IFD.FD == FD && IFD.StackLevel == StackLevel)
1156         return IFD.VD;
1157     return nullptr;
1158   }
1159   /// Check if capture decl is field captured in ImplicitDefaultFirstprivateFDs
1160   bool isImplicitDefaultFirstprivateFD(VarDecl *VD) const {
1161     const_iterator I = begin();
1162     const_iterator EndI = end();
1163     for (; I != EndI; ++I)
1164       if (I->DefaultAttr == DSA_firstprivate || I->DefaultAttr == DSA_private)
1165         break;
1166     if (I == EndI)
1167       return false;
1168     for (const auto &IFD : I->ImplicitDefaultFirstprivateFDs)
1169       if (IFD.VD == VD)
1170         return true;
1171     return false;
1172   }
1173   /// Store capture FD info in ImplicitDefaultFirstprivateFDs
1174   void addImplicitDefaultFirstprivateFD(const FieldDecl *FD, VarDecl *VD) {
1175     iterator I = begin();
1176     const_iterator EndI = end();
1177     size_t StackLevel = getStackSize();
1178     for (; I != EndI; ++I) {
1179       if (I->DefaultAttr == DSA_private || I->DefaultAttr == DSA_firstprivate) {
1180         I->ImplicitDefaultFirstprivateFDs.emplace_back(FD, StackLevel, VD);
1181         break;
1182       }
1183       StackLevel--;
1184     }
1185     assert((StackLevel > 0 && I != EndI) || (StackLevel == 0 && I == EndI));
1186   }
1187 };
1188 
1189 bool isImplicitTaskingRegion(OpenMPDirectiveKind DKind) {
1190   return isOpenMPParallelDirective(DKind) || isOpenMPTeamsDirective(DKind);
1191 }
1192 
1193 bool isImplicitOrExplicitTaskingRegion(OpenMPDirectiveKind DKind) {
1194   return isImplicitTaskingRegion(DKind) || isOpenMPTaskingDirective(DKind) ||
1195          DKind == OMPD_unknown;
1196 }
1197 
1198 } // namespace
1199 
1200 static const Expr *getExprAsWritten(const Expr *E) {
1201   if (const auto *FE = dyn_cast<FullExpr>(E))
1202     E = FE->getSubExpr();
1203 
1204   if (const auto *MTE = dyn_cast<MaterializeTemporaryExpr>(E))
1205     E = MTE->getSubExpr();
1206 
1207   while (const auto *Binder = dyn_cast<CXXBindTemporaryExpr>(E))
1208     E = Binder->getSubExpr();
1209 
1210   if (const auto *ICE = dyn_cast<ImplicitCastExpr>(E))
1211     E = ICE->getSubExprAsWritten();
1212   return E->IgnoreParens();
1213 }
1214 
1215 static Expr *getExprAsWritten(Expr *E) {
1216   return const_cast<Expr *>(getExprAsWritten(const_cast<const Expr *>(E)));
1217 }
1218 
1219 static const ValueDecl *getCanonicalDecl(const ValueDecl *D) {
1220   if (const auto *CED = dyn_cast<OMPCapturedExprDecl>(D))
1221     if (const auto *ME = dyn_cast<MemberExpr>(getExprAsWritten(CED->getInit())))
1222       D = ME->getMemberDecl();
1223   const auto *VD = dyn_cast<VarDecl>(D);
1224   const auto *FD = dyn_cast<FieldDecl>(D);
1225   if (VD != nullptr) {
1226     VD = VD->getCanonicalDecl();
1227     D = VD;
1228   } else {
1229     assert(FD);
1230     FD = FD->getCanonicalDecl();
1231     D = FD;
1232   }
1233   return D;
1234 }
1235 
1236 static ValueDecl *getCanonicalDecl(ValueDecl *D) {
1237   return const_cast<ValueDecl *>(
1238       getCanonicalDecl(const_cast<const ValueDecl *>(D)));
1239 }
1240 
1241 DSAStackTy::DSAVarData DSAStackTy::getDSA(const_iterator &Iter,
1242                                           ValueDecl *D) const {
1243   D = getCanonicalDecl(D);
1244   auto *VD = dyn_cast<VarDecl>(D);
1245   const auto *FD = dyn_cast<FieldDecl>(D);
1246   DSAVarData DVar;
1247   if (Iter == end()) {
1248     // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1249     // in a region but not in construct]
1250     //  File-scope or namespace-scope variables referenced in called routines
1251     //  in the region are shared unless they appear in a threadprivate
1252     //  directive.
1253     if (VD && !VD->isFunctionOrMethodVarDecl() && !isa<ParmVarDecl>(VD))
1254       DVar.CKind = OMPC_shared;
1255 
1256     // OpenMP [2.9.1.2, Data-sharing Attribute Rules for Variables Referenced
1257     // in a region but not in construct]
1258     //  Variables with static storage duration that are declared in called
1259     //  routines in the region are shared.
1260     if (VD && VD->hasGlobalStorage())
1261       DVar.CKind = OMPC_shared;
1262 
1263     // Non-static data members are shared by default.
1264     if (FD)
1265       DVar.CKind = OMPC_shared;
1266 
1267     return DVar;
1268   }
1269 
1270   // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1271   // in a Construct, C/C++, predetermined, p.1]
1272   // Variables with automatic storage duration that are declared in a scope
1273   // inside the construct are private.
1274   if (VD && isOpenMPLocal(VD, Iter) && VD->isLocalVarDecl() &&
1275       (VD->getStorageClass() == SC_Auto || VD->getStorageClass() == SC_None)) {
1276     DVar.CKind = OMPC_private;
1277     return DVar;
1278   }
1279 
1280   DVar.DKind = Iter->Directive;
1281   // Explicitly specified attributes and local variables with predetermined
1282   // attributes.
1283   if (Iter->SharingMap.count(D)) {
1284     const DSAInfo &Data = Iter->SharingMap.lookup(D);
1285     DVar.RefExpr = Data.RefExpr.getPointer();
1286     DVar.PrivateCopy = Data.PrivateCopy;
1287     DVar.CKind = Data.Attributes;
1288     DVar.ImplicitDSALoc = Iter->DefaultAttrLoc;
1289     DVar.Modifier = Data.Modifier;
1290     DVar.AppliedToPointee = Data.AppliedToPointee;
1291     return DVar;
1292   }
1293 
1294   // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1295   // in a Construct, C/C++, implicitly determined, p.1]
1296   //  In a parallel or task construct, the data-sharing attributes of these
1297   //  variables are determined by the default clause, if present.
1298   switch (Iter->DefaultAttr) {
1299   case DSA_shared:
1300     DVar.CKind = OMPC_shared;
1301     DVar.ImplicitDSALoc = Iter->DefaultAttrLoc;
1302     return DVar;
1303   case DSA_none:
1304     return DVar;
1305   case DSA_firstprivate:
1306     if (VD && VD->getStorageDuration() == SD_Static &&
1307         VD->getDeclContext()->isFileContext()) {
1308       DVar.CKind = OMPC_unknown;
1309     } else {
1310       DVar.CKind = OMPC_firstprivate;
1311     }
1312     DVar.ImplicitDSALoc = Iter->DefaultAttrLoc;
1313     return DVar;
1314   case DSA_private:
1315     // each variable with static storage duration that is declared
1316     // in a namespace or global scope and referenced in the construct,
1317     // and that does not have a predetermined data-sharing attribute
1318     if (VD && VD->getStorageDuration() == SD_Static &&
1319         VD->getDeclContext()->isFileContext()) {
1320       DVar.CKind = OMPC_unknown;
1321     } else {
1322       DVar.CKind = OMPC_private;
1323     }
1324     DVar.ImplicitDSALoc = Iter->DefaultAttrLoc;
1325     return DVar;
1326   case DSA_unspecified:
1327     // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1328     // in a Construct, implicitly determined, p.2]
1329     //  In a parallel construct, if no default clause is present, these
1330     //  variables are shared.
1331     DVar.ImplicitDSALoc = Iter->DefaultAttrLoc;
1332     if ((isOpenMPParallelDirective(DVar.DKind) &&
1333          !isOpenMPTaskLoopDirective(DVar.DKind)) ||
1334         isOpenMPTeamsDirective(DVar.DKind)) {
1335       DVar.CKind = OMPC_shared;
1336       return DVar;
1337     }
1338 
1339     // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1340     // in a Construct, implicitly determined, p.4]
1341     //  In a task construct, if no default clause is present, a variable that in
1342     //  the enclosing context is determined to be shared by all implicit tasks
1343     //  bound to the current team is shared.
1344     if (isOpenMPTaskingDirective(DVar.DKind)) {
1345       DSAVarData DVarTemp;
1346       const_iterator I = Iter, E = end();
1347       do {
1348         ++I;
1349         // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables
1350         // Referenced in a Construct, implicitly determined, p.6]
1351         //  In a task construct, if no default clause is present, a variable
1352         //  whose data-sharing attribute is not determined by the rules above is
1353         //  firstprivate.
1354         DVarTemp = getDSA(I, D);
1355         if (DVarTemp.CKind != OMPC_shared) {
1356           DVar.RefExpr = nullptr;
1357           DVar.CKind = OMPC_firstprivate;
1358           return DVar;
1359         }
1360       } while (I != E && !isImplicitTaskingRegion(I->Directive));
1361       DVar.CKind =
1362           (DVarTemp.CKind == OMPC_unknown) ? OMPC_firstprivate : OMPC_shared;
1363       return DVar;
1364     }
1365   }
1366   // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1367   // in a Construct, implicitly determined, p.3]
1368   //  For constructs other than task, if no default clause is present, these
1369   //  variables inherit their data-sharing attributes from the enclosing
1370   //  context.
1371   return getDSA(++Iter, D);
1372 }
1373 
1374 const Expr *DSAStackTy::addUniqueAligned(const ValueDecl *D,
1375                                          const Expr *NewDE) {
1376   assert(!isStackEmpty() && "Data sharing attributes stack is empty");
1377   D = getCanonicalDecl(D);
1378   SharingMapTy &StackElem = getTopOfStack();
1379   auto It = StackElem.AlignedMap.find(D);
1380   if (It == StackElem.AlignedMap.end()) {
1381     assert(NewDE && "Unexpected nullptr expr to be added into aligned map");
1382     StackElem.AlignedMap[D] = NewDE;
1383     return nullptr;
1384   }
1385   assert(It->second && "Unexpected nullptr expr in the aligned map");
1386   return It->second;
1387 }
1388 
1389 const Expr *DSAStackTy::addUniqueNontemporal(const ValueDecl *D,
1390                                              const Expr *NewDE) {
1391   assert(!isStackEmpty() && "Data sharing attributes stack is empty");
1392   D = getCanonicalDecl(D);
1393   SharingMapTy &StackElem = getTopOfStack();
1394   auto It = StackElem.NontemporalMap.find(D);
1395   if (It == StackElem.NontemporalMap.end()) {
1396     assert(NewDE && "Unexpected nullptr expr to be added into aligned map");
1397     StackElem.NontemporalMap[D] = NewDE;
1398     return nullptr;
1399   }
1400   assert(It->second && "Unexpected nullptr expr in the aligned map");
1401   return It->second;
1402 }
1403 
1404 void DSAStackTy::addLoopControlVariable(const ValueDecl *D, VarDecl *Capture) {
1405   assert(!isStackEmpty() && "Data-sharing attributes stack is empty");
1406   D = getCanonicalDecl(D);
1407   SharingMapTy &StackElem = getTopOfStack();
1408   StackElem.LCVMap.try_emplace(
1409       D, LCDeclInfo(StackElem.LCVMap.size() + 1, Capture));
1410 }
1411 
1412 const DSAStackTy::LCDeclInfo
1413 DSAStackTy::isLoopControlVariable(const ValueDecl *D) const {
1414   assert(!isStackEmpty() && "Data-sharing attributes stack is empty");
1415   D = getCanonicalDecl(D);
1416   const SharingMapTy &StackElem = getTopOfStack();
1417   auto It = StackElem.LCVMap.find(D);
1418   if (It != StackElem.LCVMap.end())
1419     return It->second;
1420   return {0, nullptr};
1421 }
1422 
1423 const DSAStackTy::LCDeclInfo
1424 DSAStackTy::isLoopControlVariable(const ValueDecl *D, unsigned Level) const {
1425   assert(!isStackEmpty() && "Data-sharing attributes stack is empty");
1426   D = getCanonicalDecl(D);
1427   for (unsigned I = Level + 1; I > 0; --I) {
1428     const SharingMapTy &StackElem = getStackElemAtLevel(I - 1);
1429     auto It = StackElem.LCVMap.find(D);
1430     if (It != StackElem.LCVMap.end())
1431       return It->second;
1432   }
1433   return {0, nullptr};
1434 }
1435 
1436 const DSAStackTy::LCDeclInfo
1437 DSAStackTy::isParentLoopControlVariable(const ValueDecl *D) const {
1438   const SharingMapTy *Parent = getSecondOnStackOrNull();
1439   assert(Parent && "Data-sharing attributes stack is empty");
1440   D = getCanonicalDecl(D);
1441   auto It = Parent->LCVMap.find(D);
1442   if (It != Parent->LCVMap.end())
1443     return It->second;
1444   return {0, nullptr};
1445 }
1446 
1447 const ValueDecl *DSAStackTy::getParentLoopControlVariable(unsigned I) const {
1448   const SharingMapTy *Parent = getSecondOnStackOrNull();
1449   assert(Parent && "Data-sharing attributes stack is empty");
1450   if (Parent->LCVMap.size() < I)
1451     return nullptr;
1452   for (const auto &Pair : Parent->LCVMap)
1453     if (Pair.second.first == I)
1454       return Pair.first;
1455   return nullptr;
1456 }
1457 
1458 void DSAStackTy::addDSA(const ValueDecl *D, const Expr *E, OpenMPClauseKind A,
1459                         DeclRefExpr *PrivateCopy, unsigned Modifier,
1460                         bool AppliedToPointee) {
1461   D = getCanonicalDecl(D);
1462   if (A == OMPC_threadprivate) {
1463     DSAInfo &Data = Threadprivates[D];
1464     Data.Attributes = A;
1465     Data.RefExpr.setPointer(E);
1466     Data.PrivateCopy = nullptr;
1467     Data.Modifier = Modifier;
1468   } else {
1469     DSAInfo &Data = getTopOfStack().SharingMap[D];
1470     assert(Data.Attributes == OMPC_unknown || (A == Data.Attributes) ||
1471            (A == OMPC_firstprivate && Data.Attributes == OMPC_lastprivate) ||
1472            (A == OMPC_lastprivate && Data.Attributes == OMPC_firstprivate) ||
1473            (isLoopControlVariable(D).first && A == OMPC_private));
1474     Data.Modifier = Modifier;
1475     if (A == OMPC_lastprivate && Data.Attributes == OMPC_firstprivate) {
1476       Data.RefExpr.setInt(/*IntVal=*/true);
1477       return;
1478     }
1479     const bool IsLastprivate =
1480         A == OMPC_lastprivate || Data.Attributes == OMPC_lastprivate;
1481     Data.Attributes = A;
1482     Data.RefExpr.setPointerAndInt(E, IsLastprivate);
1483     Data.PrivateCopy = PrivateCopy;
1484     Data.AppliedToPointee = AppliedToPointee;
1485     if (PrivateCopy) {
1486       DSAInfo &Data = getTopOfStack().SharingMap[PrivateCopy->getDecl()];
1487       Data.Modifier = Modifier;
1488       Data.Attributes = A;
1489       Data.RefExpr.setPointerAndInt(PrivateCopy, IsLastprivate);
1490       Data.PrivateCopy = nullptr;
1491       Data.AppliedToPointee = AppliedToPointee;
1492     }
1493   }
1494 }
1495 
1496 /// Build a variable declaration for OpenMP loop iteration variable.
1497 static VarDecl *buildVarDecl(Sema &SemaRef, SourceLocation Loc, QualType Type,
1498                              StringRef Name, const AttrVec *Attrs = nullptr,
1499                              DeclRefExpr *OrigRef = nullptr) {
1500   DeclContext *DC = SemaRef.CurContext;
1501   IdentifierInfo *II = &SemaRef.PP.getIdentifierTable().get(Name);
1502   TypeSourceInfo *TInfo = SemaRef.Context.getTrivialTypeSourceInfo(Type, Loc);
1503   auto *Decl =
1504       VarDecl::Create(SemaRef.Context, DC, Loc, Loc, II, Type, TInfo, SC_None);
1505   if (Attrs) {
1506     for (specific_attr_iterator<AlignedAttr> I(Attrs->begin()), E(Attrs->end());
1507          I != E; ++I)
1508       Decl->addAttr(*I);
1509   }
1510   Decl->setImplicit();
1511   if (OrigRef) {
1512     Decl->addAttr(
1513         OMPReferencedVarAttr::CreateImplicit(SemaRef.Context, OrigRef));
1514   }
1515   return Decl;
1516 }
1517 
1518 static DeclRefExpr *buildDeclRefExpr(Sema &S, VarDecl *D, QualType Ty,
1519                                      SourceLocation Loc,
1520                                      bool RefersToCapture = false) {
1521   D->setReferenced();
1522   D->markUsed(S.Context);
1523   return DeclRefExpr::Create(S.getASTContext(), NestedNameSpecifierLoc(),
1524                              SourceLocation(), D, RefersToCapture, Loc, Ty,
1525                              VK_LValue);
1526 }
1527 
1528 void DSAStackTy::addTaskgroupReductionData(const ValueDecl *D, SourceRange SR,
1529                                            BinaryOperatorKind BOK) {
1530   D = getCanonicalDecl(D);
1531   assert(!isStackEmpty() && "Data-sharing attributes stack is empty");
1532   assert(
1533       getTopOfStack().SharingMap[D].Attributes == OMPC_reduction &&
1534       "Additional reduction info may be specified only for reduction items.");
1535   ReductionData &ReductionData = getTopOfStack().ReductionMap[D];
1536   assert(ReductionData.ReductionRange.isInvalid() &&
1537          (getTopOfStack().Directive == OMPD_taskgroup ||
1538           ((isOpenMPParallelDirective(getTopOfStack().Directive) ||
1539             isOpenMPWorksharingDirective(getTopOfStack().Directive)) &&
1540            !isOpenMPSimdDirective(getTopOfStack().Directive))) &&
1541          "Additional reduction info may be specified only once for reduction "
1542          "items.");
1543   ReductionData.set(BOK, SR);
1544   Expr *&TaskgroupReductionRef = getTopOfStack().TaskgroupReductionRef;
1545   if (!TaskgroupReductionRef) {
1546     VarDecl *VD = buildVarDecl(SemaRef, SR.getBegin(),
1547                                SemaRef.Context.VoidPtrTy, ".task_red.");
1548     TaskgroupReductionRef =
1549         buildDeclRefExpr(SemaRef, VD, SemaRef.Context.VoidPtrTy, SR.getBegin());
1550   }
1551 }
1552 
1553 void DSAStackTy::addTaskgroupReductionData(const ValueDecl *D, SourceRange SR,
1554                                            const Expr *ReductionRef) {
1555   D = getCanonicalDecl(D);
1556   assert(!isStackEmpty() && "Data-sharing attributes stack is empty");
1557   assert(
1558       getTopOfStack().SharingMap[D].Attributes == OMPC_reduction &&
1559       "Additional reduction info may be specified only for reduction items.");
1560   ReductionData &ReductionData = getTopOfStack().ReductionMap[D];
1561   assert(ReductionData.ReductionRange.isInvalid() &&
1562          (getTopOfStack().Directive == OMPD_taskgroup ||
1563           ((isOpenMPParallelDirective(getTopOfStack().Directive) ||
1564             isOpenMPWorksharingDirective(getTopOfStack().Directive)) &&
1565            !isOpenMPSimdDirective(getTopOfStack().Directive))) &&
1566          "Additional reduction info may be specified only once for reduction "
1567          "items.");
1568   ReductionData.set(ReductionRef, SR);
1569   Expr *&TaskgroupReductionRef = getTopOfStack().TaskgroupReductionRef;
1570   if (!TaskgroupReductionRef) {
1571     VarDecl *VD = buildVarDecl(SemaRef, SR.getBegin(),
1572                                SemaRef.Context.VoidPtrTy, ".task_red.");
1573     TaskgroupReductionRef =
1574         buildDeclRefExpr(SemaRef, VD, SemaRef.Context.VoidPtrTy, SR.getBegin());
1575   }
1576 }
1577 
1578 const DSAStackTy::DSAVarData DSAStackTy::getTopMostTaskgroupReductionData(
1579     const ValueDecl *D, SourceRange &SR, BinaryOperatorKind &BOK,
1580     Expr *&TaskgroupDescriptor) const {
1581   D = getCanonicalDecl(D);
1582   assert(!isStackEmpty() && "Data-sharing attributes stack is empty.");
1583   for (const_iterator I = begin() + 1, E = end(); I != E; ++I) {
1584     const DSAInfo &Data = I->SharingMap.lookup(D);
1585     if (Data.Attributes != OMPC_reduction ||
1586         Data.Modifier != OMPC_REDUCTION_task)
1587       continue;
1588     const ReductionData &ReductionData = I->ReductionMap.lookup(D);
1589     if (!ReductionData.ReductionOp ||
1590         ReductionData.ReductionOp.is<const Expr *>())
1591       return DSAVarData();
1592     SR = ReductionData.ReductionRange;
1593     BOK = ReductionData.ReductionOp.get<ReductionData::BOKPtrType>();
1594     assert(I->TaskgroupReductionRef && "taskgroup reduction reference "
1595                                        "expression for the descriptor is not "
1596                                        "set.");
1597     TaskgroupDescriptor = I->TaskgroupReductionRef;
1598     return DSAVarData(I->Directive, OMPC_reduction, Data.RefExpr.getPointer(),
1599                       Data.PrivateCopy, I->DefaultAttrLoc, OMPC_REDUCTION_task,
1600                       /*AppliedToPointee=*/false);
1601   }
1602   return DSAVarData();
1603 }
1604 
1605 const DSAStackTy::DSAVarData DSAStackTy::getTopMostTaskgroupReductionData(
1606     const ValueDecl *D, SourceRange &SR, const Expr *&ReductionRef,
1607     Expr *&TaskgroupDescriptor) const {
1608   D = getCanonicalDecl(D);
1609   assert(!isStackEmpty() && "Data-sharing attributes stack is empty.");
1610   for (const_iterator I = begin() + 1, E = end(); I != E; ++I) {
1611     const DSAInfo &Data = I->SharingMap.lookup(D);
1612     if (Data.Attributes != OMPC_reduction ||
1613         Data.Modifier != OMPC_REDUCTION_task)
1614       continue;
1615     const ReductionData &ReductionData = I->ReductionMap.lookup(D);
1616     if (!ReductionData.ReductionOp ||
1617         !ReductionData.ReductionOp.is<const Expr *>())
1618       return DSAVarData();
1619     SR = ReductionData.ReductionRange;
1620     ReductionRef = ReductionData.ReductionOp.get<const Expr *>();
1621     assert(I->TaskgroupReductionRef && "taskgroup reduction reference "
1622                                        "expression for the descriptor is not "
1623                                        "set.");
1624     TaskgroupDescriptor = I->TaskgroupReductionRef;
1625     return DSAVarData(I->Directive, OMPC_reduction, Data.RefExpr.getPointer(),
1626                       Data.PrivateCopy, I->DefaultAttrLoc, OMPC_REDUCTION_task,
1627                       /*AppliedToPointee=*/false);
1628   }
1629   return DSAVarData();
1630 }
1631 
1632 bool DSAStackTy::isOpenMPLocal(VarDecl *D, const_iterator I) const {
1633   D = D->getCanonicalDecl();
1634   for (const_iterator E = end(); I != E; ++I) {
1635     if (isImplicitOrExplicitTaskingRegion(I->Directive) ||
1636         isOpenMPTargetExecutionDirective(I->Directive)) {
1637       if (I->CurScope) {
1638         Scope *TopScope = I->CurScope->getParent();
1639         Scope *CurScope = getCurScope();
1640         while (CurScope && CurScope != TopScope && !CurScope->isDeclScope(D))
1641           CurScope = CurScope->getParent();
1642         return CurScope != TopScope;
1643       }
1644       for (DeclContext *DC = D->getDeclContext(); DC; DC = DC->getParent())
1645         if (I->Context == DC)
1646           return true;
1647       return false;
1648     }
1649   }
1650   return false;
1651 }
1652 
1653 static bool isConstNotMutableType(Sema &SemaRef, QualType Type,
1654                                   bool AcceptIfMutable = true,
1655                                   bool *IsClassType = nullptr) {
1656   ASTContext &Context = SemaRef.getASTContext();
1657   Type = Type.getNonReferenceType().getCanonicalType();
1658   bool IsConstant = Type.isConstant(Context);
1659   Type = Context.getBaseElementType(Type);
1660   const CXXRecordDecl *RD = AcceptIfMutable && SemaRef.getLangOpts().CPlusPlus
1661                                 ? Type->getAsCXXRecordDecl()
1662                                 : nullptr;
1663   if (const auto *CTSD = dyn_cast_or_null<ClassTemplateSpecializationDecl>(RD))
1664     if (const ClassTemplateDecl *CTD = CTSD->getSpecializedTemplate())
1665       RD = CTD->getTemplatedDecl();
1666   if (IsClassType)
1667     *IsClassType = RD;
1668   return IsConstant && !(SemaRef.getLangOpts().CPlusPlus && RD &&
1669                          RD->hasDefinition() && RD->hasMutableFields());
1670 }
1671 
1672 static bool rejectConstNotMutableType(Sema &SemaRef, const ValueDecl *D,
1673                                       QualType Type, OpenMPClauseKind CKind,
1674                                       SourceLocation ELoc,
1675                                       bool AcceptIfMutable = true,
1676                                       bool ListItemNotVar = false) {
1677   ASTContext &Context = SemaRef.getASTContext();
1678   bool IsClassType;
1679   if (isConstNotMutableType(SemaRef, Type, AcceptIfMutable, &IsClassType)) {
1680     unsigned Diag = ListItemNotVar ? diag::err_omp_const_list_item
1681                     : IsClassType  ? diag::err_omp_const_not_mutable_variable
1682                                    : diag::err_omp_const_variable;
1683     SemaRef.Diag(ELoc, Diag) << getOpenMPClauseName(CKind);
1684     if (!ListItemNotVar && D) {
1685       const VarDecl *VD = dyn_cast<VarDecl>(D);
1686       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
1687                                VarDecl::DeclarationOnly;
1688       SemaRef.Diag(D->getLocation(),
1689                    IsDecl ? diag::note_previous_decl : diag::note_defined_here)
1690           << D;
1691     }
1692     return true;
1693   }
1694   return false;
1695 }
1696 
1697 const DSAStackTy::DSAVarData DSAStackTy::getTopDSA(ValueDecl *D,
1698                                                    bool FromParent) {
1699   D = getCanonicalDecl(D);
1700   DSAVarData DVar;
1701 
1702   auto *VD = dyn_cast<VarDecl>(D);
1703   auto TI = Threadprivates.find(D);
1704   if (TI != Threadprivates.end()) {
1705     DVar.RefExpr = TI->getSecond().RefExpr.getPointer();
1706     DVar.CKind = OMPC_threadprivate;
1707     DVar.Modifier = TI->getSecond().Modifier;
1708     return DVar;
1709   }
1710   if (VD && VD->hasAttr<OMPThreadPrivateDeclAttr>()) {
1711     DVar.RefExpr = buildDeclRefExpr(
1712         SemaRef, VD, D->getType().getNonReferenceType(),
1713         VD->getAttr<OMPThreadPrivateDeclAttr>()->getLocation());
1714     DVar.CKind = OMPC_threadprivate;
1715     addDSA(D, DVar.RefExpr, OMPC_threadprivate);
1716     return DVar;
1717   }
1718   // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1719   // in a Construct, C/C++, predetermined, p.1]
1720   //  Variables appearing in threadprivate directives are threadprivate.
1721   if ((VD && VD->getTLSKind() != VarDecl::TLS_None &&
1722        !(VD->hasAttr<OMPThreadPrivateDeclAttr>() &&
1723          SemaRef.getLangOpts().OpenMPUseTLS &&
1724          SemaRef.getASTContext().getTargetInfo().isTLSSupported())) ||
1725       (VD && VD->getStorageClass() == SC_Register &&
1726        VD->hasAttr<AsmLabelAttr>() && !VD->isLocalVarDecl())) {
1727     DVar.RefExpr = buildDeclRefExpr(
1728         SemaRef, VD, D->getType().getNonReferenceType(), D->getLocation());
1729     DVar.CKind = OMPC_threadprivate;
1730     addDSA(D, DVar.RefExpr, OMPC_threadprivate);
1731     return DVar;
1732   }
1733   if (SemaRef.getLangOpts().OpenMPCUDAMode && VD &&
1734       VD->isLocalVarDeclOrParm() && !isStackEmpty() &&
1735       !isLoopControlVariable(D).first) {
1736     const_iterator IterTarget =
1737         std::find_if(begin(), end(), [](const SharingMapTy &Data) {
1738           return isOpenMPTargetExecutionDirective(Data.Directive);
1739         });
1740     if (IterTarget != end()) {
1741       const_iterator ParentIterTarget = IterTarget + 1;
1742       for (const_iterator Iter = begin(); Iter != ParentIterTarget; ++Iter) {
1743         if (isOpenMPLocal(VD, Iter)) {
1744           DVar.RefExpr =
1745               buildDeclRefExpr(SemaRef, VD, D->getType().getNonReferenceType(),
1746                                D->getLocation());
1747           DVar.CKind = OMPC_threadprivate;
1748           return DVar;
1749         }
1750       }
1751       if (!isClauseParsingMode() || IterTarget != begin()) {
1752         auto DSAIter = IterTarget->SharingMap.find(D);
1753         if (DSAIter != IterTarget->SharingMap.end() &&
1754             isOpenMPPrivate(DSAIter->getSecond().Attributes)) {
1755           DVar.RefExpr = DSAIter->getSecond().RefExpr.getPointer();
1756           DVar.CKind = OMPC_threadprivate;
1757           return DVar;
1758         }
1759         const_iterator End = end();
1760         if (!SemaRef.isOpenMPCapturedByRef(D,
1761                                            std::distance(ParentIterTarget, End),
1762                                            /*OpenMPCaptureLevel=*/0)) {
1763           DVar.RefExpr =
1764               buildDeclRefExpr(SemaRef, VD, D->getType().getNonReferenceType(),
1765                                IterTarget->ConstructLoc);
1766           DVar.CKind = OMPC_threadprivate;
1767           return DVar;
1768         }
1769       }
1770     }
1771   }
1772 
1773   if (isStackEmpty())
1774     // Not in OpenMP execution region and top scope was already checked.
1775     return DVar;
1776 
1777   // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1778   // in a Construct, C/C++, predetermined, p.4]
1779   //  Static data members are shared.
1780   // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1781   // in a Construct, C/C++, predetermined, p.7]
1782   //  Variables with static storage duration that are declared in a scope
1783   //  inside the construct are shared.
1784   if (VD && VD->isStaticDataMember()) {
1785     // Check for explicitly specified attributes.
1786     const_iterator I = begin();
1787     const_iterator EndI = end();
1788     if (FromParent && I != EndI)
1789       ++I;
1790     if (I != EndI) {
1791       auto It = I->SharingMap.find(D);
1792       if (It != I->SharingMap.end()) {
1793         const DSAInfo &Data = It->getSecond();
1794         DVar.RefExpr = Data.RefExpr.getPointer();
1795         DVar.PrivateCopy = Data.PrivateCopy;
1796         DVar.CKind = Data.Attributes;
1797         DVar.ImplicitDSALoc = I->DefaultAttrLoc;
1798         DVar.DKind = I->Directive;
1799         DVar.Modifier = Data.Modifier;
1800         DVar.AppliedToPointee = Data.AppliedToPointee;
1801         return DVar;
1802       }
1803     }
1804 
1805     DVar.CKind = OMPC_shared;
1806     return DVar;
1807   }
1808 
1809   auto &&MatchesAlways = [](OpenMPDirectiveKind) { return true; };
1810   // The predetermined shared attribute for const-qualified types having no
1811   // mutable members was removed after OpenMP 3.1.
1812   if (SemaRef.LangOpts.OpenMP <= 31) {
1813     // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
1814     // in a Construct, C/C++, predetermined, p.6]
1815     //  Variables with const qualified type having no mutable member are
1816     //  shared.
1817     if (isConstNotMutableType(SemaRef, D->getType())) {
1818       // Variables with const-qualified type having no mutable member may be
1819       // listed in a firstprivate clause, even if they are static data members.
1820       DSAVarData DVarTemp = hasInnermostDSA(
1821           D,
1822           [](OpenMPClauseKind C, bool) {
1823             return C == OMPC_firstprivate || C == OMPC_shared;
1824           },
1825           MatchesAlways, FromParent);
1826       if (DVarTemp.CKind != OMPC_unknown && DVarTemp.RefExpr)
1827         return DVarTemp;
1828 
1829       DVar.CKind = OMPC_shared;
1830       return DVar;
1831     }
1832   }
1833 
1834   // Explicitly specified attributes and local variables with predetermined
1835   // attributes.
1836   const_iterator I = begin();
1837   const_iterator EndI = end();
1838   if (FromParent && I != EndI)
1839     ++I;
1840   if (I == EndI)
1841     return DVar;
1842   auto It = I->SharingMap.find(D);
1843   if (It != I->SharingMap.end()) {
1844     const DSAInfo &Data = It->getSecond();
1845     DVar.RefExpr = Data.RefExpr.getPointer();
1846     DVar.PrivateCopy = Data.PrivateCopy;
1847     DVar.CKind = Data.Attributes;
1848     DVar.ImplicitDSALoc = I->DefaultAttrLoc;
1849     DVar.DKind = I->Directive;
1850     DVar.Modifier = Data.Modifier;
1851     DVar.AppliedToPointee = Data.AppliedToPointee;
1852   }
1853 
1854   return DVar;
1855 }
1856 
1857 const DSAStackTy::DSAVarData DSAStackTy::getImplicitDSA(ValueDecl *D,
1858                                                         bool FromParent) const {
1859   if (isStackEmpty()) {
1860     const_iterator I;
1861     return getDSA(I, D);
1862   }
1863   D = getCanonicalDecl(D);
1864   const_iterator StartI = begin();
1865   const_iterator EndI = end();
1866   if (FromParent && StartI != EndI)
1867     ++StartI;
1868   return getDSA(StartI, D);
1869 }
1870 
1871 const DSAStackTy::DSAVarData DSAStackTy::getImplicitDSA(ValueDecl *D,
1872                                                         unsigned Level) const {
1873   if (getStackSize() <= Level)
1874     return DSAVarData();
1875   D = getCanonicalDecl(D);
1876   const_iterator StartI = std::next(begin(), getStackSize() - 1 - Level);
1877   return getDSA(StartI, D);
1878 }
1879 
1880 const DSAStackTy::DSAVarData
1881 DSAStackTy::hasDSA(ValueDecl *D,
1882                    const llvm::function_ref<bool(OpenMPClauseKind, bool,
1883                                                  DefaultDataSharingAttributes)>
1884                        CPred,
1885                    const llvm::function_ref<bool(OpenMPDirectiveKind)> DPred,
1886                    bool FromParent) const {
1887   if (isStackEmpty())
1888     return {};
1889   D = getCanonicalDecl(D);
1890   const_iterator I = begin();
1891   const_iterator EndI = end();
1892   if (FromParent && I != EndI)
1893     ++I;
1894   for (; I != EndI; ++I) {
1895     if (!DPred(I->Directive) &&
1896         !isImplicitOrExplicitTaskingRegion(I->Directive))
1897       continue;
1898     const_iterator NewI = I;
1899     DSAVarData DVar = getDSA(NewI, D);
1900     if (I == NewI && CPred(DVar.CKind, DVar.AppliedToPointee, I->DefaultAttr))
1901       return DVar;
1902   }
1903   return {};
1904 }
1905 
1906 const DSAStackTy::DSAVarData DSAStackTy::hasInnermostDSA(
1907     ValueDecl *D, const llvm::function_ref<bool(OpenMPClauseKind, bool)> CPred,
1908     const llvm::function_ref<bool(OpenMPDirectiveKind)> DPred,
1909     bool FromParent) const {
1910   if (isStackEmpty())
1911     return {};
1912   D = getCanonicalDecl(D);
1913   const_iterator StartI = begin();
1914   const_iterator EndI = end();
1915   if (FromParent && StartI != EndI)
1916     ++StartI;
1917   if (StartI == EndI || !DPred(StartI->Directive))
1918     return {};
1919   const_iterator NewI = StartI;
1920   DSAVarData DVar = getDSA(NewI, D);
1921   return (NewI == StartI && CPred(DVar.CKind, DVar.AppliedToPointee))
1922              ? DVar
1923              : DSAVarData();
1924 }
1925 
1926 bool DSAStackTy::hasExplicitDSA(
1927     const ValueDecl *D,
1928     const llvm::function_ref<bool(OpenMPClauseKind, bool)> CPred,
1929     unsigned Level, bool NotLastprivate) const {
1930   if (getStackSize() <= Level)
1931     return false;
1932   D = getCanonicalDecl(D);
1933   const SharingMapTy &StackElem = getStackElemAtLevel(Level);
1934   auto I = StackElem.SharingMap.find(D);
1935   if (I != StackElem.SharingMap.end() && I->getSecond().RefExpr.getPointer() &&
1936       CPred(I->getSecond().Attributes, I->getSecond().AppliedToPointee) &&
1937       (!NotLastprivate || !I->getSecond().RefExpr.getInt()))
1938     return true;
1939   // Check predetermined rules for the loop control variables.
1940   auto LI = StackElem.LCVMap.find(D);
1941   if (LI != StackElem.LCVMap.end())
1942     return CPred(OMPC_private, /*AppliedToPointee=*/false);
1943   return false;
1944 }
1945 
1946 bool DSAStackTy::hasExplicitDirective(
1947     const llvm::function_ref<bool(OpenMPDirectiveKind)> DPred,
1948     unsigned Level) const {
1949   if (getStackSize() <= Level)
1950     return false;
1951   const SharingMapTy &StackElem = getStackElemAtLevel(Level);
1952   return DPred(StackElem.Directive);
1953 }
1954 
1955 bool DSAStackTy::hasDirective(
1956     const llvm::function_ref<bool(OpenMPDirectiveKind,
1957                                   const DeclarationNameInfo &, SourceLocation)>
1958         DPred,
1959     bool FromParent) const {
1960   // We look only in the enclosing region.
1961   size_t Skip = FromParent ? 2 : 1;
1962   for (const_iterator I = begin() + std::min(Skip, getStackSize()), E = end();
1963        I != E; ++I) {
1964     if (DPred(I->Directive, I->DirectiveName, I->ConstructLoc))
1965       return true;
1966   }
1967   return false;
1968 }
1969 
1970 void Sema::InitDataSharingAttributesStack() {
1971   VarDataSharingAttributesStack = new DSAStackTy(*this);
1972 }
1973 
1974 #define DSAStack static_cast<DSAStackTy *>(VarDataSharingAttributesStack)
1975 
1976 void Sema::pushOpenMPFunctionRegion() { DSAStack->pushFunction(); }
1977 
1978 void Sema::popOpenMPFunctionRegion(const FunctionScopeInfo *OldFSI) {
1979   DSAStack->popFunction(OldFSI);
1980 }
1981 
1982 static bool isOpenMPDeviceDelayedContext(Sema &S) {
1983   assert(S.LangOpts.OpenMP && S.LangOpts.OpenMPIsDevice &&
1984          "Expected OpenMP device compilation.");
1985   return !S.isInOpenMPTargetExecutionDirective();
1986 }
1987 
1988 namespace {
1989 /// Status of the function emission on the host/device.
1990 enum class FunctionEmissionStatus {
1991   Emitted,
1992   Discarded,
1993   Unknown,
1994 };
1995 } // anonymous namespace
1996 
1997 Sema::SemaDiagnosticBuilder Sema::diagIfOpenMPDeviceCode(SourceLocation Loc,
1998                                                          unsigned DiagID,
1999                                                          FunctionDecl *FD) {
2000   assert(LangOpts.OpenMP && LangOpts.OpenMPIsDevice &&
2001          "Expected OpenMP device compilation.");
2002 
2003   SemaDiagnosticBuilder::Kind Kind = SemaDiagnosticBuilder::K_Nop;
2004   if (FD) {
2005     FunctionEmissionStatus FES = getEmissionStatus(FD);
2006     switch (FES) {
2007     case FunctionEmissionStatus::Emitted:
2008       Kind = SemaDiagnosticBuilder::K_Immediate;
2009       break;
2010     case FunctionEmissionStatus::Unknown:
2011       // TODO: We should always delay diagnostics here in case a target
2012       //       region is in a function we do not emit. However, as the
2013       //       current diagnostics are associated with the function containing
2014       //       the target region and we do not emit that one, we would miss out
2015       //       on diagnostics for the target region itself. We need to anchor
2016       //       the diagnostics with the new generated function *or* ensure we
2017       //       emit diagnostics associated with the surrounding function.
2018       Kind = isOpenMPDeviceDelayedContext(*this)
2019                  ? SemaDiagnosticBuilder::K_Deferred
2020                  : SemaDiagnosticBuilder::K_Immediate;
2021       break;
2022     case FunctionEmissionStatus::TemplateDiscarded:
2023     case FunctionEmissionStatus::OMPDiscarded:
2024       Kind = SemaDiagnosticBuilder::K_Nop;
2025       break;
2026     case FunctionEmissionStatus::CUDADiscarded:
2027       llvm_unreachable("CUDADiscarded unexpected in OpenMP device compilation");
2028       break;
2029     }
2030   }
2031 
2032   return SemaDiagnosticBuilder(Kind, Loc, DiagID, FD, *this);
2033 }
2034 
2035 Sema::SemaDiagnosticBuilder Sema::diagIfOpenMPHostCode(SourceLocation Loc,
2036                                                        unsigned DiagID,
2037                                                        FunctionDecl *FD) {
2038   assert(LangOpts.OpenMP && !LangOpts.OpenMPIsDevice &&
2039          "Expected OpenMP host compilation.");
2040 
2041   SemaDiagnosticBuilder::Kind Kind = SemaDiagnosticBuilder::K_Nop;
2042   if (FD) {
2043     FunctionEmissionStatus FES = getEmissionStatus(FD);
2044     switch (FES) {
2045     case FunctionEmissionStatus::Emitted:
2046       Kind = SemaDiagnosticBuilder::K_Immediate;
2047       break;
2048     case FunctionEmissionStatus::Unknown:
2049       Kind = SemaDiagnosticBuilder::K_Deferred;
2050       break;
2051     case FunctionEmissionStatus::TemplateDiscarded:
2052     case FunctionEmissionStatus::OMPDiscarded:
2053     case FunctionEmissionStatus::CUDADiscarded:
2054       Kind = SemaDiagnosticBuilder::K_Nop;
2055       break;
2056     }
2057   }
2058 
2059   return SemaDiagnosticBuilder(Kind, Loc, DiagID, FD, *this);
2060 }
2061 
2062 static OpenMPDefaultmapClauseKind
2063 getVariableCategoryFromDecl(const LangOptions &LO, const ValueDecl *VD) {
2064   if (LO.OpenMP <= 45) {
2065     if (VD->getType().getNonReferenceType()->isScalarType())
2066       return OMPC_DEFAULTMAP_scalar;
2067     return OMPC_DEFAULTMAP_aggregate;
2068   }
2069   if (VD->getType().getNonReferenceType()->isAnyPointerType())
2070     return OMPC_DEFAULTMAP_pointer;
2071   if (VD->getType().getNonReferenceType()->isScalarType())
2072     return OMPC_DEFAULTMAP_scalar;
2073   return OMPC_DEFAULTMAP_aggregate;
2074 }
2075 
2076 bool Sema::isOpenMPCapturedByRef(const ValueDecl *D, unsigned Level,
2077                                  unsigned OpenMPCaptureLevel) const {
2078   assert(LangOpts.OpenMP && "OpenMP is not allowed");
2079 
2080   ASTContext &Ctx = getASTContext();
2081   bool IsByRef = true;
2082 
2083   // Find the directive that is associated with the provided scope.
2084   D = cast<ValueDecl>(D->getCanonicalDecl());
2085   QualType Ty = D->getType();
2086 
2087   bool IsVariableUsedInMapClause = false;
2088   if (DSAStack->hasExplicitDirective(isOpenMPTargetExecutionDirective, Level)) {
2089     // This table summarizes how a given variable should be passed to the device
2090     // given its type and the clauses where it appears. This table is based on
2091     // the description in OpenMP 4.5 [2.10.4, target Construct] and
2092     // OpenMP 4.5 [2.15.5, Data-mapping Attribute Rules and Clauses].
2093     //
2094     // =========================================================================
2095     // | type |  defaultmap   | pvt | first | is_device_ptr |    map   | res.  |
2096     // |      |(tofrom:scalar)|     |  pvt  |               |          |       |
2097     // =========================================================================
2098     // | scl  |               |     |       |       -       |          | bycopy|
2099     // | scl  |               |  -  |   x   |       -       |     -    | bycopy|
2100     // | scl  |               |  x  |   -   |       -       |     -    | null  |
2101     // | scl  |       x       |     |       |       -       |          | byref |
2102     // | scl  |       x       |  -  |   x   |       -       |     -    | bycopy|
2103     // | scl  |       x       |  x  |   -   |       -       |     -    | null  |
2104     // | scl  |               |  -  |   -   |       -       |     x    | byref |
2105     // | scl  |       x       |  -  |   -   |       -       |     x    | byref |
2106     //
2107     // | agg  |      n.a.     |     |       |       -       |          | byref |
2108     // | agg  |      n.a.     |  -  |   x   |       -       |     -    | byref |
2109     // | agg  |      n.a.     |  x  |   -   |       -       |     -    | null  |
2110     // | agg  |      n.a.     |  -  |   -   |       -       |     x    | byref |
2111     // | agg  |      n.a.     |  -  |   -   |       -       |    x[]   | byref |
2112     //
2113     // | ptr  |      n.a.     |     |       |       -       |          | bycopy|
2114     // | ptr  |      n.a.     |  -  |   x   |       -       |     -    | bycopy|
2115     // | ptr  |      n.a.     |  x  |   -   |       -       |     -    | null  |
2116     // | ptr  |      n.a.     |  -  |   -   |       -       |     x    | byref |
2117     // | ptr  |      n.a.     |  -  |   -   |       -       |    x[]   | bycopy|
2118     // | ptr  |      n.a.     |  -  |   -   |       x       |          | bycopy|
2119     // | ptr  |      n.a.     |  -  |   -   |       x       |     x    | bycopy|
2120     // | ptr  |      n.a.     |  -  |   -   |       x       |    x[]   | bycopy|
2121     // =========================================================================
2122     // Legend:
2123     //  scl - scalar
2124     //  ptr - pointer
2125     //  agg - aggregate
2126     //  x - applies
2127     //  - - invalid in this combination
2128     //  [] - mapped with an array section
2129     //  byref - should be mapped by reference
2130     //  byval - should be mapped by value
2131     //  null - initialize a local variable to null on the device
2132     //
2133     // Observations:
2134     //  - All scalar declarations that show up in a map clause have to be passed
2135     //    by reference, because they may have been mapped in the enclosing data
2136     //    environment.
2137     //  - If the scalar value does not fit the size of uintptr, it has to be
2138     //    passed by reference, regardless the result in the table above.
2139     //  - For pointers mapped by value that have either an implicit map or an
2140     //    array section, the runtime library may pass the NULL value to the
2141     //    device instead of the value passed to it by the compiler.
2142 
2143     if (Ty->isReferenceType())
2144       Ty = Ty->castAs<ReferenceType>()->getPointeeType();
2145 
2146     // Locate map clauses and see if the variable being captured is referred to
2147     // in any of those clauses. Here we only care about variables, not fields,
2148     // because fields are part of aggregates.
2149     bool IsVariableAssociatedWithSection = false;
2150 
2151     DSAStack->checkMappableExprComponentListsForDeclAtLevel(
2152         D, Level,
2153         [&IsVariableUsedInMapClause, &IsVariableAssociatedWithSection,
2154          D](OMPClauseMappableExprCommon::MappableExprComponentListRef
2155                 MapExprComponents,
2156             OpenMPClauseKind WhereFoundClauseKind) {
2157           // Only the map clause information influences how a variable is
2158           // captured. E.g. is_device_ptr does not require changing the default
2159           // behavior.
2160           if (WhereFoundClauseKind != OMPC_map)
2161             return false;
2162 
2163           auto EI = MapExprComponents.rbegin();
2164           auto EE = MapExprComponents.rend();
2165 
2166           assert(EI != EE && "Invalid map expression!");
2167 
2168           if (isa<DeclRefExpr>(EI->getAssociatedExpression()))
2169             IsVariableUsedInMapClause |= EI->getAssociatedDeclaration() == D;
2170 
2171           ++EI;
2172           if (EI == EE)
2173             return false;
2174 
2175           if (isa<ArraySubscriptExpr>(EI->getAssociatedExpression()) ||
2176               isa<OMPArraySectionExpr>(EI->getAssociatedExpression()) ||
2177               isa<MemberExpr>(EI->getAssociatedExpression()) ||
2178               isa<OMPArrayShapingExpr>(EI->getAssociatedExpression())) {
2179             IsVariableAssociatedWithSection = true;
2180             // There is nothing more we need to know about this variable.
2181             return true;
2182           }
2183 
2184           // Keep looking for more map info.
2185           return false;
2186         });
2187 
2188     if (IsVariableUsedInMapClause) {
2189       // If variable is identified in a map clause it is always captured by
2190       // reference except if it is a pointer that is dereferenced somehow.
2191       IsByRef = !(Ty->isPointerType() && IsVariableAssociatedWithSection);
2192     } else {
2193       // By default, all the data that has a scalar type is mapped by copy
2194       // (except for reduction variables).
2195       // Defaultmap scalar is mutual exclusive to defaultmap pointer
2196       IsByRef = (DSAStack->isForceCaptureByReferenceInTargetExecutable() &&
2197                  !Ty->isAnyPointerType()) ||
2198                 !Ty->isScalarType() ||
2199                 DSAStack->isDefaultmapCapturedByRef(
2200                     Level, getVariableCategoryFromDecl(LangOpts, D)) ||
2201                 DSAStack->hasExplicitDSA(
2202                     D,
2203                     [](OpenMPClauseKind K, bool AppliedToPointee) {
2204                       return K == OMPC_reduction && !AppliedToPointee;
2205                     },
2206                     Level);
2207     }
2208   }
2209 
2210   if (IsByRef && Ty.getNonReferenceType()->isScalarType()) {
2211     IsByRef =
2212         ((IsVariableUsedInMapClause &&
2213           DSAStack->getCaptureRegion(Level, OpenMPCaptureLevel) ==
2214               OMPD_target) ||
2215          !(DSAStack->hasExplicitDSA(
2216                D,
2217                [](OpenMPClauseKind K, bool AppliedToPointee) -> bool {
2218                  return K == OMPC_firstprivate ||
2219                         (K == OMPC_reduction && AppliedToPointee);
2220                },
2221                Level, /*NotLastprivate=*/true) ||
2222            DSAStack->isUsesAllocatorsDecl(Level, D))) &&
2223         // If the variable is artificial and must be captured by value - try to
2224         // capture by value.
2225         !(isa<OMPCapturedExprDecl>(D) && !D->hasAttr<OMPCaptureNoInitAttr>() &&
2226           !cast<OMPCapturedExprDecl>(D)->getInit()->isGLValue()) &&
2227         // If the variable is implicitly firstprivate and scalar - capture by
2228         // copy
2229         !((DSAStack->getDefaultDSA() == DSA_firstprivate ||
2230            DSAStack->getDefaultDSA() == DSA_private) &&
2231           !DSAStack->hasExplicitDSA(
2232               D, [](OpenMPClauseKind K, bool) { return K != OMPC_unknown; },
2233               Level) &&
2234           !DSAStack->isLoopControlVariable(D, Level).first);
2235   }
2236 
2237   // When passing data by copy, we need to make sure it fits the uintptr size
2238   // and alignment, because the runtime library only deals with uintptr types.
2239   // If it does not fit the uintptr size, we need to pass the data by reference
2240   // instead.
2241   if (!IsByRef &&
2242       (Ctx.getTypeSizeInChars(Ty) >
2243            Ctx.getTypeSizeInChars(Ctx.getUIntPtrType()) ||
2244        Ctx.getDeclAlign(D) > Ctx.getTypeAlignInChars(Ctx.getUIntPtrType()))) {
2245     IsByRef = true;
2246   }
2247 
2248   return IsByRef;
2249 }
2250 
2251 unsigned Sema::getOpenMPNestingLevel() const {
2252   assert(getLangOpts().OpenMP);
2253   return DSAStack->getNestingLevel();
2254 }
2255 
2256 bool Sema::isInOpenMPTaskUntiedContext() const {
2257   return isOpenMPTaskingDirective(DSAStack->getCurrentDirective()) &&
2258          DSAStack->isUntiedRegion();
2259 }
2260 
2261 bool Sema::isInOpenMPTargetExecutionDirective() const {
2262   return (isOpenMPTargetExecutionDirective(DSAStack->getCurrentDirective()) &&
2263           !DSAStack->isClauseParsingMode()) ||
2264          DSAStack->hasDirective(
2265              [](OpenMPDirectiveKind K, const DeclarationNameInfo &,
2266                 SourceLocation) -> bool {
2267                return isOpenMPTargetExecutionDirective(K);
2268              },
2269              false);
2270 }
2271 
2272 bool Sema::isOpenMPRebuildMemberExpr(ValueDecl *D) {
2273   DSAStackTy::DSAVarData DVarPrivate = DSAStack->hasDSA(
2274       D,
2275       [](OpenMPClauseKind C, bool AppliedToPointee,
2276          DefaultDataSharingAttributes DefaultAttr) {
2277         return isOpenMPPrivate(C) && !AppliedToPointee &&
2278                (DefaultAttr == DSA_firstprivate || DefaultAttr == DSA_private);
2279       },
2280       [](OpenMPDirectiveKind) { return true; },
2281       DSAStack->isClauseParsingMode());
2282   if (DVarPrivate.CKind != OMPC_unknown)
2283     return true;
2284   return false;
2285 }
2286 
2287 static OMPCapturedExprDecl *buildCaptureDecl(Sema &S, IdentifierInfo *Id,
2288                                              Expr *CaptureExpr, bool WithInit,
2289                                              DeclContext *CurContext,
2290                                              bool AsExpression);
2291 
2292 VarDecl *Sema::isOpenMPCapturedDecl(ValueDecl *D, bool CheckScopeInfo,
2293                                     unsigned StopAt) {
2294   assert(LangOpts.OpenMP && "OpenMP is not allowed");
2295   D = getCanonicalDecl(D);
2296 
2297   auto *VD = dyn_cast<VarDecl>(D);
2298   // Do not capture constexpr variables.
2299   if (VD && VD->isConstexpr())
2300     return nullptr;
2301 
2302   // If we want to determine whether the variable should be captured from the
2303   // perspective of the current capturing scope, and we've already left all the
2304   // capturing scopes of the top directive on the stack, check from the
2305   // perspective of its parent directive (if any) instead.
2306   DSAStackTy::ParentDirectiveScope InParentDirectiveRAII(
2307       *DSAStack, CheckScopeInfo && DSAStack->isBodyComplete());
2308 
2309   // If we are attempting to capture a global variable in a directive with
2310   // 'target' we return true so that this global is also mapped to the device.
2311   //
2312   if (VD && !VD->hasLocalStorage() &&
2313       (getCurCapturedRegion() || getCurBlock() || getCurLambda())) {
2314     if (isInOpenMPTargetExecutionDirective()) {
2315       DSAStackTy::DSAVarData DVarTop =
2316           DSAStack->getTopDSA(D, DSAStack->isClauseParsingMode());
2317       if (DVarTop.CKind != OMPC_unknown && DVarTop.RefExpr)
2318         return VD;
2319       // If the declaration is enclosed in a 'declare target' directive,
2320       // then it should not be captured.
2321       //
2322       if (OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(VD))
2323         return nullptr;
2324       CapturedRegionScopeInfo *CSI = nullptr;
2325       for (FunctionScopeInfo *FSI : llvm::drop_begin(
2326                llvm::reverse(FunctionScopes),
2327                CheckScopeInfo ? (FunctionScopes.size() - (StopAt + 1)) : 0)) {
2328         if (!isa<CapturingScopeInfo>(FSI))
2329           return nullptr;
2330         if (auto *RSI = dyn_cast<CapturedRegionScopeInfo>(FSI))
2331           if (RSI->CapRegionKind == CR_OpenMP) {
2332             CSI = RSI;
2333             break;
2334           }
2335       }
2336       assert(CSI && "Failed to find CapturedRegionScopeInfo");
2337       SmallVector<OpenMPDirectiveKind, 4> Regions;
2338       getOpenMPCaptureRegions(Regions,
2339                               DSAStack->getDirective(CSI->OpenMPLevel));
2340       if (Regions[CSI->OpenMPCaptureLevel] != OMPD_task)
2341         return VD;
2342     }
2343     if (isInOpenMPDeclareTargetContext()) {
2344       // Try to mark variable as declare target if it is used in capturing
2345       // regions.
2346       if (LangOpts.OpenMP <= 45 &&
2347           !OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(VD))
2348         checkDeclIsAllowedInOpenMPTarget(nullptr, VD);
2349       return nullptr;
2350     }
2351   }
2352 
2353   if (CheckScopeInfo) {
2354     bool OpenMPFound = false;
2355     for (unsigned I = StopAt + 1; I > 0; --I) {
2356       FunctionScopeInfo *FSI = FunctionScopes[I - 1];
2357       if (!isa<CapturingScopeInfo>(FSI))
2358         return nullptr;
2359       if (auto *RSI = dyn_cast<CapturedRegionScopeInfo>(FSI))
2360         if (RSI->CapRegionKind == CR_OpenMP) {
2361           OpenMPFound = true;
2362           break;
2363         }
2364     }
2365     if (!OpenMPFound)
2366       return nullptr;
2367   }
2368 
2369   if (DSAStack->getCurrentDirective() != OMPD_unknown &&
2370       (!DSAStack->isClauseParsingMode() ||
2371        DSAStack->getParentDirective() != OMPD_unknown)) {
2372     auto &&Info = DSAStack->isLoopControlVariable(D);
2373     if (Info.first ||
2374         (VD && VD->hasLocalStorage() &&
2375          isImplicitOrExplicitTaskingRegion(DSAStack->getCurrentDirective())) ||
2376         (VD && DSAStack->isForceVarCapturing()))
2377       return VD ? VD : Info.second;
2378     DSAStackTy::DSAVarData DVarTop =
2379         DSAStack->getTopDSA(D, DSAStack->isClauseParsingMode());
2380     if (DVarTop.CKind != OMPC_unknown && isOpenMPPrivate(DVarTop.CKind) &&
2381         (!VD || VD->hasLocalStorage() || !DVarTop.AppliedToPointee))
2382       return VD ? VD : cast<VarDecl>(DVarTop.PrivateCopy->getDecl());
2383     // Threadprivate variables must not be captured.
2384     if (isOpenMPThreadPrivate(DVarTop.CKind))
2385       return nullptr;
2386     // The variable is not private or it is the variable in the directive with
2387     // default(none) clause and not used in any clause.
2388     DSAStackTy::DSAVarData DVarPrivate = DSAStack->hasDSA(
2389         D,
2390         [](OpenMPClauseKind C, bool AppliedToPointee, bool) {
2391           return isOpenMPPrivate(C) && !AppliedToPointee;
2392         },
2393         [](OpenMPDirectiveKind) { return true; },
2394         DSAStack->isClauseParsingMode());
2395     // Global shared must not be captured.
2396     if (VD && !VD->hasLocalStorage() && DVarPrivate.CKind == OMPC_unknown &&
2397         ((DSAStack->getDefaultDSA() != DSA_none &&
2398           DSAStack->getDefaultDSA() != DSA_private &&
2399           DSAStack->getDefaultDSA() != DSA_firstprivate) ||
2400          DVarTop.CKind == OMPC_shared))
2401       return nullptr;
2402     auto *FD = dyn_cast<FieldDecl>(D);
2403     if (DVarPrivate.CKind != OMPC_unknown && !VD && FD &&
2404         !DVarPrivate.PrivateCopy) {
2405       DSAStackTy::DSAVarData DVarPrivate = DSAStack->hasDSA(
2406           D,
2407           [](OpenMPClauseKind C, bool AppliedToPointee,
2408              DefaultDataSharingAttributes DefaultAttr) {
2409             return isOpenMPPrivate(C) && !AppliedToPointee &&
2410                    (DefaultAttr == DSA_firstprivate ||
2411                     DefaultAttr == DSA_private);
2412           },
2413           [](OpenMPDirectiveKind) { return true; },
2414           DSAStack->isClauseParsingMode());
2415       if (DVarPrivate.CKind == OMPC_unknown)
2416         return nullptr;
2417 
2418       VarDecl *VD = DSAStack->getImplicitFDCapExprDecl(FD);
2419       if (VD)
2420         return VD;
2421       if (getCurrentThisType().isNull())
2422         return nullptr;
2423       Expr *ThisExpr = BuildCXXThisExpr(SourceLocation(), getCurrentThisType(),
2424                                         /*IsImplicit=*/true);
2425       const CXXScopeSpec CS = CXXScopeSpec();
2426       Expr *ME = BuildMemberExpr(ThisExpr, /*IsArrow=*/true, SourceLocation(),
2427                                  NestedNameSpecifierLoc(), SourceLocation(), FD,
2428                                  DeclAccessPair::make(FD, FD->getAccess()),
2429                                  /*HadMultipleCandidates=*/false,
2430                                  DeclarationNameInfo(), FD->getType(),
2431                                  VK_LValue, OK_Ordinary);
2432       OMPCapturedExprDecl *CD = buildCaptureDecl(
2433           *this, FD->getIdentifier(), ME, DVarPrivate.CKind != OMPC_private,
2434           CurContext->getParent(), /*AsExpression=*/false);
2435       DeclRefExpr *VDPrivateRefExpr = buildDeclRefExpr(
2436           *this, CD, CD->getType().getNonReferenceType(), SourceLocation());
2437       VD = cast<VarDecl>(VDPrivateRefExpr->getDecl());
2438       DSAStack->addImplicitDefaultFirstprivateFD(FD, VD);
2439       return VD;
2440     }
2441     if (DVarPrivate.CKind != OMPC_unknown ||
2442         (VD && (DSAStack->getDefaultDSA() == DSA_none ||
2443                 DSAStack->getDefaultDSA() == DSA_private ||
2444                 DSAStack->getDefaultDSA() == DSA_firstprivate)))
2445       return VD ? VD : cast<VarDecl>(DVarPrivate.PrivateCopy->getDecl());
2446   }
2447   return nullptr;
2448 }
2449 
2450 void Sema::adjustOpenMPTargetScopeIndex(unsigned &FunctionScopesIndex,
2451                                         unsigned Level) const {
2452   FunctionScopesIndex -= getOpenMPCaptureLevels(DSAStack->getDirective(Level));
2453 }
2454 
2455 void Sema::startOpenMPLoop() {
2456   assert(LangOpts.OpenMP && "OpenMP must be enabled.");
2457   if (isOpenMPLoopDirective(DSAStack->getCurrentDirective()))
2458     DSAStack->loopInit();
2459 }
2460 
2461 void Sema::startOpenMPCXXRangeFor() {
2462   assert(LangOpts.OpenMP && "OpenMP must be enabled.");
2463   if (isOpenMPLoopDirective(DSAStack->getCurrentDirective())) {
2464     DSAStack->resetPossibleLoopCounter();
2465     DSAStack->loopStart();
2466   }
2467 }
2468 
2469 OpenMPClauseKind Sema::isOpenMPPrivateDecl(ValueDecl *D, unsigned Level,
2470                                            unsigned CapLevel) const {
2471   assert(LangOpts.OpenMP && "OpenMP is not allowed");
2472   if (DSAStack->getCurrentDirective() != OMPD_unknown &&
2473       (!DSAStack->isClauseParsingMode() ||
2474        DSAStack->getParentDirective() != OMPD_unknown)) {
2475     DSAStackTy::DSAVarData DVarPrivate = DSAStack->hasDSA(
2476         D,
2477         [](OpenMPClauseKind C, bool AppliedToPointee,
2478            DefaultDataSharingAttributes DefaultAttr) {
2479           return isOpenMPPrivate(C) && !AppliedToPointee &&
2480                  DefaultAttr == DSA_private;
2481         },
2482         [](OpenMPDirectiveKind) { return true; },
2483         DSAStack->isClauseParsingMode());
2484     if (DVarPrivate.CKind == OMPC_private && isa<OMPCapturedExprDecl>(D) &&
2485         DSAStack->isImplicitDefaultFirstprivateFD(cast<VarDecl>(D)) &&
2486         !DSAStack->isLoopControlVariable(D).first)
2487       return OMPC_private;
2488   }
2489   if (DSAStack->hasExplicitDirective(isOpenMPTaskingDirective, Level)) {
2490     bool IsTriviallyCopyable =
2491         D->getType().getNonReferenceType().isTriviallyCopyableType(Context) &&
2492         !D->getType()
2493              .getNonReferenceType()
2494              .getCanonicalType()
2495              ->getAsCXXRecordDecl();
2496     OpenMPDirectiveKind DKind = DSAStack->getDirective(Level);
2497     SmallVector<OpenMPDirectiveKind, 4> CaptureRegions;
2498     getOpenMPCaptureRegions(CaptureRegions, DKind);
2499     if (isOpenMPTaskingDirective(CaptureRegions[CapLevel]) &&
2500         (IsTriviallyCopyable ||
2501          !isOpenMPTaskLoopDirective(CaptureRegions[CapLevel]))) {
2502       if (DSAStack->hasExplicitDSA(
2503               D,
2504               [](OpenMPClauseKind K, bool) { return K == OMPC_firstprivate; },
2505               Level, /*NotLastprivate=*/true))
2506         return OMPC_firstprivate;
2507       DSAStackTy::DSAVarData DVar = DSAStack->getImplicitDSA(D, Level);
2508       if (DVar.CKind != OMPC_shared &&
2509           !DSAStack->isLoopControlVariable(D, Level).first && !DVar.RefExpr) {
2510         DSAStack->addImplicitTaskFirstprivate(Level, D);
2511         return OMPC_firstprivate;
2512       }
2513     }
2514   }
2515   if (isOpenMPLoopDirective(DSAStack->getCurrentDirective())) {
2516     if (DSAStack->getAssociatedLoops() > 0 && !DSAStack->isLoopStarted()) {
2517       DSAStack->resetPossibleLoopCounter(D);
2518       DSAStack->loopStart();
2519       return OMPC_private;
2520     }
2521     if ((DSAStack->getPossiblyLoopCunter() == D->getCanonicalDecl() ||
2522          DSAStack->isLoopControlVariable(D).first) &&
2523         !DSAStack->hasExplicitDSA(
2524             D, [](OpenMPClauseKind K, bool) { return K != OMPC_private; },
2525             Level) &&
2526         !isOpenMPSimdDirective(DSAStack->getCurrentDirective()))
2527       return OMPC_private;
2528   }
2529   if (const auto *VD = dyn_cast<VarDecl>(D)) {
2530     if (DSAStack->isThreadPrivate(const_cast<VarDecl *>(VD)) &&
2531         DSAStack->isForceVarCapturing() &&
2532         !DSAStack->hasExplicitDSA(
2533             D, [](OpenMPClauseKind K, bool) { return K == OMPC_copyin; },
2534             Level))
2535       return OMPC_private;
2536   }
2537   // User-defined allocators are private since they must be defined in the
2538   // context of target region.
2539   if (DSAStack->hasExplicitDirective(isOpenMPTargetExecutionDirective, Level) &&
2540       DSAStack->isUsesAllocatorsDecl(Level, D).value_or(
2541           DSAStackTy::UsesAllocatorsDeclKind::AllocatorTrait) ==
2542           DSAStackTy::UsesAllocatorsDeclKind::UserDefinedAllocator)
2543     return OMPC_private;
2544   return (DSAStack->hasExplicitDSA(
2545               D, [](OpenMPClauseKind K, bool) { return K == OMPC_private; },
2546               Level) ||
2547           (DSAStack->isClauseParsingMode() &&
2548            DSAStack->getClauseParsingMode() == OMPC_private) ||
2549           // Consider taskgroup reduction descriptor variable a private
2550           // to avoid possible capture in the region.
2551           (DSAStack->hasExplicitDirective(
2552                [](OpenMPDirectiveKind K) {
2553                  return K == OMPD_taskgroup ||
2554                         ((isOpenMPParallelDirective(K) ||
2555                           isOpenMPWorksharingDirective(K)) &&
2556                          !isOpenMPSimdDirective(K));
2557                },
2558                Level) &&
2559            DSAStack->isTaskgroupReductionRef(D, Level)))
2560              ? OMPC_private
2561              : OMPC_unknown;
2562 }
2563 
2564 void Sema::setOpenMPCaptureKind(FieldDecl *FD, const ValueDecl *D,
2565                                 unsigned Level) {
2566   assert(LangOpts.OpenMP && "OpenMP is not allowed");
2567   D = getCanonicalDecl(D);
2568   OpenMPClauseKind OMPC = OMPC_unknown;
2569   for (unsigned I = DSAStack->getNestingLevel() + 1; I > Level; --I) {
2570     const unsigned NewLevel = I - 1;
2571     if (DSAStack->hasExplicitDSA(
2572             D,
2573             [&OMPC](const OpenMPClauseKind K, bool AppliedToPointee) {
2574               if (isOpenMPPrivate(K) && !AppliedToPointee) {
2575                 OMPC = K;
2576                 return true;
2577               }
2578               return false;
2579             },
2580             NewLevel))
2581       break;
2582     if (DSAStack->checkMappableExprComponentListsForDeclAtLevel(
2583             D, NewLevel,
2584             [](OMPClauseMappableExprCommon::MappableExprComponentListRef,
2585                OpenMPClauseKind) { return true; })) {
2586       OMPC = OMPC_map;
2587       break;
2588     }
2589     if (DSAStack->hasExplicitDirective(isOpenMPTargetExecutionDirective,
2590                                        NewLevel)) {
2591       OMPC = OMPC_map;
2592       if (DSAStack->mustBeFirstprivateAtLevel(
2593               NewLevel, getVariableCategoryFromDecl(LangOpts, D)))
2594         OMPC = OMPC_firstprivate;
2595       break;
2596     }
2597   }
2598   if (OMPC != OMPC_unknown)
2599     FD->addAttr(OMPCaptureKindAttr::CreateImplicit(Context, unsigned(OMPC)));
2600 }
2601 
2602 bool Sema::isOpenMPTargetCapturedDecl(const ValueDecl *D, unsigned Level,
2603                                       unsigned CaptureLevel) const {
2604   assert(LangOpts.OpenMP && "OpenMP is not allowed");
2605   // Return true if the current level is no longer enclosed in a target region.
2606 
2607   SmallVector<OpenMPDirectiveKind, 4> Regions;
2608   getOpenMPCaptureRegions(Regions, DSAStack->getDirective(Level));
2609   const auto *VD = dyn_cast<VarDecl>(D);
2610   return VD && !VD->hasLocalStorage() &&
2611          DSAStack->hasExplicitDirective(isOpenMPTargetExecutionDirective,
2612                                         Level) &&
2613          Regions[CaptureLevel] != OMPD_task;
2614 }
2615 
2616 bool Sema::isOpenMPGlobalCapturedDecl(ValueDecl *D, unsigned Level,
2617                                       unsigned CaptureLevel) const {
2618   assert(LangOpts.OpenMP && "OpenMP is not allowed");
2619   // Return true if the current level is no longer enclosed in a target region.
2620 
2621   if (const auto *VD = dyn_cast<VarDecl>(D)) {
2622     if (!VD->hasLocalStorage()) {
2623       if (isInOpenMPTargetExecutionDirective())
2624         return true;
2625       DSAStackTy::DSAVarData TopDVar =
2626           DSAStack->getTopDSA(D, /*FromParent=*/false);
2627       unsigned NumLevels =
2628           getOpenMPCaptureLevels(DSAStack->getDirective(Level));
2629       if (Level == 0)
2630         // non-file scope static variale with default(firstprivate)
2631         // should be gloabal captured.
2632         return (NumLevels == CaptureLevel + 1 &&
2633                 (TopDVar.CKind != OMPC_shared ||
2634                  DSAStack->getDefaultDSA() == DSA_firstprivate));
2635       do {
2636         --Level;
2637         DSAStackTy::DSAVarData DVar = DSAStack->getImplicitDSA(D, Level);
2638         if (DVar.CKind != OMPC_shared)
2639           return true;
2640       } while (Level > 0);
2641     }
2642   }
2643   return true;
2644 }
2645 
2646 void Sema::DestroyDataSharingAttributesStack() { delete DSAStack; }
2647 
2648 void Sema::ActOnOpenMPBeginDeclareVariant(SourceLocation Loc,
2649                                           OMPTraitInfo &TI) {
2650   OMPDeclareVariantScopes.push_back(OMPDeclareVariantScope(TI));
2651 }
2652 
2653 void Sema::ActOnOpenMPEndDeclareVariant() {
2654   assert(isInOpenMPDeclareVariantScope() &&
2655          "Not in OpenMP declare variant scope!");
2656 
2657   OMPDeclareVariantScopes.pop_back();
2658 }
2659 
2660 void Sema::finalizeOpenMPDelayedAnalysis(const FunctionDecl *Caller,
2661                                          const FunctionDecl *Callee,
2662                                          SourceLocation Loc) {
2663   assert(LangOpts.OpenMP && "Expected OpenMP compilation mode.");
2664   Optional<OMPDeclareTargetDeclAttr::DevTypeTy> DevTy =
2665       OMPDeclareTargetDeclAttr::getDeviceType(Caller->getMostRecentDecl());
2666   // Ignore host functions during device analyzis.
2667   if (LangOpts.OpenMPIsDevice &&
2668       (!DevTy || *DevTy == OMPDeclareTargetDeclAttr::DT_Host))
2669     return;
2670   // Ignore nohost functions during host analyzis.
2671   if (!LangOpts.OpenMPIsDevice && DevTy &&
2672       *DevTy == OMPDeclareTargetDeclAttr::DT_NoHost)
2673     return;
2674   const FunctionDecl *FD = Callee->getMostRecentDecl();
2675   DevTy = OMPDeclareTargetDeclAttr::getDeviceType(FD);
2676   if (LangOpts.OpenMPIsDevice && DevTy &&
2677       *DevTy == OMPDeclareTargetDeclAttr::DT_Host) {
2678     // Diagnose host function called during device codegen.
2679     StringRef HostDevTy =
2680         getOpenMPSimpleClauseTypeName(OMPC_device_type, OMPC_DEVICE_TYPE_host);
2681     Diag(Loc, diag::err_omp_wrong_device_function_call) << HostDevTy << 0;
2682     Diag(*OMPDeclareTargetDeclAttr::getLocation(FD),
2683          diag::note_omp_marked_device_type_here)
2684         << HostDevTy;
2685     return;
2686   }
2687   if (!LangOpts.OpenMPIsDevice && !LangOpts.OpenMPOffloadMandatory && DevTy &&
2688       *DevTy == OMPDeclareTargetDeclAttr::DT_NoHost) {
2689     // Diagnose nohost function called during host codegen.
2690     StringRef NoHostDevTy = getOpenMPSimpleClauseTypeName(
2691         OMPC_device_type, OMPC_DEVICE_TYPE_nohost);
2692     Diag(Loc, diag::err_omp_wrong_device_function_call) << NoHostDevTy << 1;
2693     Diag(*OMPDeclareTargetDeclAttr::getLocation(FD),
2694          diag::note_omp_marked_device_type_here)
2695         << NoHostDevTy;
2696   }
2697 }
2698 
2699 void Sema::StartOpenMPDSABlock(OpenMPDirectiveKind DKind,
2700                                const DeclarationNameInfo &DirName,
2701                                Scope *CurScope, SourceLocation Loc) {
2702   DSAStack->push(DKind, DirName, CurScope, Loc);
2703   PushExpressionEvaluationContext(
2704       ExpressionEvaluationContext::PotentiallyEvaluated);
2705 }
2706 
2707 void Sema::StartOpenMPClause(OpenMPClauseKind K) {
2708   DSAStack->setClauseParsingMode(K);
2709 }
2710 
2711 void Sema::EndOpenMPClause() {
2712   DSAStack->setClauseParsingMode(/*K=*/OMPC_unknown);
2713   CleanupVarDeclMarking();
2714 }
2715 
2716 static std::pair<ValueDecl *, bool>
2717 getPrivateItem(Sema &S, Expr *&RefExpr, SourceLocation &ELoc,
2718                SourceRange &ERange, bool AllowArraySection = false);
2719 
2720 /// Check consistency of the reduction clauses.
2721 static void checkReductionClauses(Sema &S, DSAStackTy *Stack,
2722                                   ArrayRef<OMPClause *> Clauses) {
2723   bool InscanFound = false;
2724   SourceLocation InscanLoc;
2725   // OpenMP 5.0, 2.19.5.4 reduction Clause, Restrictions.
2726   // A reduction clause without the inscan reduction-modifier may not appear on
2727   // a construct on which a reduction clause with the inscan reduction-modifier
2728   // appears.
2729   for (OMPClause *C : Clauses) {
2730     if (C->getClauseKind() != OMPC_reduction)
2731       continue;
2732     auto *RC = cast<OMPReductionClause>(C);
2733     if (RC->getModifier() == OMPC_REDUCTION_inscan) {
2734       InscanFound = true;
2735       InscanLoc = RC->getModifierLoc();
2736       continue;
2737     }
2738     if (RC->getModifier() == OMPC_REDUCTION_task) {
2739       // OpenMP 5.0, 2.19.5.4 reduction Clause.
2740       // A reduction clause with the task reduction-modifier may only appear on
2741       // a parallel construct, a worksharing construct or a combined or
2742       // composite construct for which any of the aforementioned constructs is a
2743       // constituent construct and simd or loop are not constituent constructs.
2744       OpenMPDirectiveKind CurDir = Stack->getCurrentDirective();
2745       if (!(isOpenMPParallelDirective(CurDir) ||
2746             isOpenMPWorksharingDirective(CurDir)) ||
2747           isOpenMPSimdDirective(CurDir))
2748         S.Diag(RC->getModifierLoc(),
2749                diag::err_omp_reduction_task_not_parallel_or_worksharing);
2750       continue;
2751     }
2752   }
2753   if (InscanFound) {
2754     for (OMPClause *C : Clauses) {
2755       if (C->getClauseKind() != OMPC_reduction)
2756         continue;
2757       auto *RC = cast<OMPReductionClause>(C);
2758       if (RC->getModifier() != OMPC_REDUCTION_inscan) {
2759         S.Diag(RC->getModifier() == OMPC_REDUCTION_unknown
2760                    ? RC->getBeginLoc()
2761                    : RC->getModifierLoc(),
2762                diag::err_omp_inscan_reduction_expected);
2763         S.Diag(InscanLoc, diag::note_omp_previous_inscan_reduction);
2764         continue;
2765       }
2766       for (Expr *Ref : RC->varlists()) {
2767         assert(Ref && "NULL expr in OpenMP nontemporal clause.");
2768         SourceLocation ELoc;
2769         SourceRange ERange;
2770         Expr *SimpleRefExpr = Ref;
2771         auto Res = getPrivateItem(S, SimpleRefExpr, ELoc, ERange,
2772                                   /*AllowArraySection=*/true);
2773         ValueDecl *D = Res.first;
2774         if (!D)
2775           continue;
2776         if (!Stack->isUsedInScanDirective(getCanonicalDecl(D))) {
2777           S.Diag(Ref->getExprLoc(),
2778                  diag::err_omp_reduction_not_inclusive_exclusive)
2779               << Ref->getSourceRange();
2780         }
2781       }
2782     }
2783   }
2784 }
2785 
2786 static void checkAllocateClauses(Sema &S, DSAStackTy *Stack,
2787                                  ArrayRef<OMPClause *> Clauses);
2788 static DeclRefExpr *buildCapture(Sema &S, ValueDecl *D, Expr *CaptureExpr,
2789                                  bool WithInit);
2790 
2791 static void reportOriginalDsa(Sema &SemaRef, const DSAStackTy *Stack,
2792                               const ValueDecl *D,
2793                               const DSAStackTy::DSAVarData &DVar,
2794                               bool IsLoopIterVar = false);
2795 
2796 void Sema::EndOpenMPDSABlock(Stmt *CurDirective) {
2797   // OpenMP [2.14.3.5, Restrictions, C/C++, p.1]
2798   //  A variable of class type (or array thereof) that appears in a lastprivate
2799   //  clause requires an accessible, unambiguous default constructor for the
2800   //  class type, unless the list item is also specified in a firstprivate
2801   //  clause.
2802   if (const auto *D = dyn_cast_or_null<OMPExecutableDirective>(CurDirective)) {
2803     for (OMPClause *C : D->clauses()) {
2804       if (auto *Clause = dyn_cast<OMPLastprivateClause>(C)) {
2805         SmallVector<Expr *, 8> PrivateCopies;
2806         for (Expr *DE : Clause->varlists()) {
2807           if (DE->isValueDependent() || DE->isTypeDependent()) {
2808             PrivateCopies.push_back(nullptr);
2809             continue;
2810           }
2811           auto *DRE = cast<DeclRefExpr>(DE->IgnoreParens());
2812           auto *VD = cast<VarDecl>(DRE->getDecl());
2813           QualType Type = VD->getType().getNonReferenceType();
2814           const DSAStackTy::DSAVarData DVar =
2815               DSAStack->getTopDSA(VD, /*FromParent=*/false);
2816           if (DVar.CKind == OMPC_lastprivate) {
2817             // Generate helper private variable and initialize it with the
2818             // default value. The address of the original variable is replaced
2819             // by the address of the new private variable in CodeGen. This new
2820             // variable is not added to IdResolver, so the code in the OpenMP
2821             // region uses original variable for proper diagnostics.
2822             VarDecl *VDPrivate = buildVarDecl(
2823                 *this, DE->getExprLoc(), Type.getUnqualifiedType(),
2824                 VD->getName(), VD->hasAttrs() ? &VD->getAttrs() : nullptr, DRE);
2825             ActOnUninitializedDecl(VDPrivate);
2826             if (VDPrivate->isInvalidDecl()) {
2827               PrivateCopies.push_back(nullptr);
2828               continue;
2829             }
2830             PrivateCopies.push_back(buildDeclRefExpr(
2831                 *this, VDPrivate, DE->getType(), DE->getExprLoc()));
2832           } else {
2833             // The variable is also a firstprivate, so initialization sequence
2834             // for private copy is generated already.
2835             PrivateCopies.push_back(nullptr);
2836           }
2837         }
2838         Clause->setPrivateCopies(PrivateCopies);
2839         continue;
2840       }
2841       // Finalize nontemporal clause by handling private copies, if any.
2842       if (auto *Clause = dyn_cast<OMPNontemporalClause>(C)) {
2843         SmallVector<Expr *, 8> PrivateRefs;
2844         for (Expr *RefExpr : Clause->varlists()) {
2845           assert(RefExpr && "NULL expr in OpenMP nontemporal clause.");
2846           SourceLocation ELoc;
2847           SourceRange ERange;
2848           Expr *SimpleRefExpr = RefExpr;
2849           auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
2850           if (Res.second)
2851             // It will be analyzed later.
2852             PrivateRefs.push_back(RefExpr);
2853           ValueDecl *D = Res.first;
2854           if (!D)
2855             continue;
2856 
2857           const DSAStackTy::DSAVarData DVar =
2858               DSAStack->getTopDSA(D, /*FromParent=*/false);
2859           PrivateRefs.push_back(DVar.PrivateCopy ? DVar.PrivateCopy
2860                                                  : SimpleRefExpr);
2861         }
2862         Clause->setPrivateRefs(PrivateRefs);
2863         continue;
2864       }
2865       if (auto *Clause = dyn_cast<OMPUsesAllocatorsClause>(C)) {
2866         for (unsigned I = 0, E = Clause->getNumberOfAllocators(); I < E; ++I) {
2867           OMPUsesAllocatorsClause::Data D = Clause->getAllocatorData(I);
2868           auto *DRE = dyn_cast<DeclRefExpr>(D.Allocator->IgnoreParenImpCasts());
2869           if (!DRE)
2870             continue;
2871           ValueDecl *VD = DRE->getDecl();
2872           if (!VD || !isa<VarDecl>(VD))
2873             continue;
2874           DSAStackTy::DSAVarData DVar =
2875               DSAStack->getTopDSA(VD, /*FromParent=*/false);
2876           // OpenMP [2.12.5, target Construct]
2877           // Memory allocators that appear in a uses_allocators clause cannot
2878           // appear in other data-sharing attribute clauses or data-mapping
2879           // attribute clauses in the same construct.
2880           Expr *MapExpr = nullptr;
2881           if (DVar.RefExpr ||
2882               DSAStack->checkMappableExprComponentListsForDecl(
2883                   VD, /*CurrentRegionOnly=*/true,
2884                   [VD, &MapExpr](
2885                       OMPClauseMappableExprCommon::MappableExprComponentListRef
2886                           MapExprComponents,
2887                       OpenMPClauseKind C) {
2888                     auto MI = MapExprComponents.rbegin();
2889                     auto ME = MapExprComponents.rend();
2890                     if (MI != ME &&
2891                         MI->getAssociatedDeclaration()->getCanonicalDecl() ==
2892                             VD->getCanonicalDecl()) {
2893                       MapExpr = MI->getAssociatedExpression();
2894                       return true;
2895                     }
2896                     return false;
2897                   })) {
2898             Diag(D.Allocator->getExprLoc(),
2899                  diag::err_omp_allocator_used_in_clauses)
2900                 << D.Allocator->getSourceRange();
2901             if (DVar.RefExpr)
2902               reportOriginalDsa(*this, DSAStack, VD, DVar);
2903             else
2904               Diag(MapExpr->getExprLoc(), diag::note_used_here)
2905                   << MapExpr->getSourceRange();
2906           }
2907         }
2908         continue;
2909       }
2910     }
2911     // Check allocate clauses.
2912     if (!CurContext->isDependentContext())
2913       checkAllocateClauses(*this, DSAStack, D->clauses());
2914     checkReductionClauses(*this, DSAStack, D->clauses());
2915   }
2916 
2917   DSAStack->pop();
2918   DiscardCleanupsInEvaluationContext();
2919   PopExpressionEvaluationContext();
2920 }
2921 
2922 static bool FinishOpenMPLinearClause(OMPLinearClause &Clause, DeclRefExpr *IV,
2923                                      Expr *NumIterations, Sema &SemaRef,
2924                                      Scope *S, DSAStackTy *Stack);
2925 
2926 namespace {
2927 
2928 class VarDeclFilterCCC final : public CorrectionCandidateCallback {
2929 private:
2930   Sema &SemaRef;
2931 
2932 public:
2933   explicit VarDeclFilterCCC(Sema &S) : SemaRef(S) {}
2934   bool ValidateCandidate(const TypoCorrection &Candidate) override {
2935     NamedDecl *ND = Candidate.getCorrectionDecl();
2936     if (const auto *VD = dyn_cast_or_null<VarDecl>(ND)) {
2937       return VD->hasGlobalStorage() &&
2938              SemaRef.isDeclInScope(ND, SemaRef.getCurLexicalContext(),
2939                                    SemaRef.getCurScope());
2940     }
2941     return false;
2942   }
2943 
2944   std::unique_ptr<CorrectionCandidateCallback> clone() override {
2945     return std::make_unique<VarDeclFilterCCC>(*this);
2946   }
2947 };
2948 
2949 class VarOrFuncDeclFilterCCC final : public CorrectionCandidateCallback {
2950 private:
2951   Sema &SemaRef;
2952 
2953 public:
2954   explicit VarOrFuncDeclFilterCCC(Sema &S) : SemaRef(S) {}
2955   bool ValidateCandidate(const TypoCorrection &Candidate) override {
2956     NamedDecl *ND = Candidate.getCorrectionDecl();
2957     if (ND && ((isa<VarDecl>(ND) && ND->getKind() == Decl::Var) ||
2958                isa<FunctionDecl>(ND))) {
2959       return SemaRef.isDeclInScope(ND, SemaRef.getCurLexicalContext(),
2960                                    SemaRef.getCurScope());
2961     }
2962     return false;
2963   }
2964 
2965   std::unique_ptr<CorrectionCandidateCallback> clone() override {
2966     return std::make_unique<VarOrFuncDeclFilterCCC>(*this);
2967   }
2968 };
2969 
2970 } // namespace
2971 
2972 ExprResult Sema::ActOnOpenMPIdExpression(Scope *CurScope,
2973                                          CXXScopeSpec &ScopeSpec,
2974                                          const DeclarationNameInfo &Id,
2975                                          OpenMPDirectiveKind Kind) {
2976   LookupResult Lookup(*this, Id, LookupOrdinaryName);
2977   LookupParsedName(Lookup, CurScope, &ScopeSpec, true);
2978 
2979   if (Lookup.isAmbiguous())
2980     return ExprError();
2981 
2982   VarDecl *VD;
2983   if (!Lookup.isSingleResult()) {
2984     VarDeclFilterCCC CCC(*this);
2985     if (TypoCorrection Corrected =
2986             CorrectTypo(Id, LookupOrdinaryName, CurScope, nullptr, CCC,
2987                         CTK_ErrorRecovery)) {
2988       diagnoseTypo(Corrected,
2989                    PDiag(Lookup.empty()
2990                              ? diag::err_undeclared_var_use_suggest
2991                              : diag::err_omp_expected_var_arg_suggest)
2992                        << Id.getName());
2993       VD = Corrected.getCorrectionDeclAs<VarDecl>();
2994     } else {
2995       Diag(Id.getLoc(), Lookup.empty() ? diag::err_undeclared_var_use
2996                                        : diag::err_omp_expected_var_arg)
2997           << Id.getName();
2998       return ExprError();
2999     }
3000   } else if (!(VD = Lookup.getAsSingle<VarDecl>())) {
3001     Diag(Id.getLoc(), diag::err_omp_expected_var_arg) << Id.getName();
3002     Diag(Lookup.getFoundDecl()->getLocation(), diag::note_declared_at);
3003     return ExprError();
3004   }
3005   Lookup.suppressDiagnostics();
3006 
3007   // OpenMP [2.9.2, Syntax, C/C++]
3008   //   Variables must be file-scope, namespace-scope, or static block-scope.
3009   if (Kind == OMPD_threadprivate && !VD->hasGlobalStorage()) {
3010     Diag(Id.getLoc(), diag::err_omp_global_var_arg)
3011         << getOpenMPDirectiveName(Kind) << !VD->isStaticLocal();
3012     bool IsDecl =
3013         VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3014     Diag(VD->getLocation(),
3015          IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3016         << VD;
3017     return ExprError();
3018   }
3019 
3020   VarDecl *CanonicalVD = VD->getCanonicalDecl();
3021   NamedDecl *ND = CanonicalVD;
3022   // OpenMP [2.9.2, Restrictions, C/C++, p.2]
3023   //   A threadprivate directive for file-scope variables must appear outside
3024   //   any definition or declaration.
3025   if (CanonicalVD->getDeclContext()->isTranslationUnit() &&
3026       !getCurLexicalContext()->isTranslationUnit()) {
3027     Diag(Id.getLoc(), diag::err_omp_var_scope)
3028         << getOpenMPDirectiveName(Kind) << VD;
3029     bool IsDecl =
3030         VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3031     Diag(VD->getLocation(),
3032          IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3033         << VD;
3034     return ExprError();
3035   }
3036   // OpenMP [2.9.2, Restrictions, C/C++, p.3]
3037   //   A threadprivate directive for static class member variables must appear
3038   //   in the class definition, in the same scope in which the member
3039   //   variables are declared.
3040   if (CanonicalVD->isStaticDataMember() &&
3041       !CanonicalVD->getDeclContext()->Equals(getCurLexicalContext())) {
3042     Diag(Id.getLoc(), diag::err_omp_var_scope)
3043         << getOpenMPDirectiveName(Kind) << VD;
3044     bool IsDecl =
3045         VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3046     Diag(VD->getLocation(),
3047          IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3048         << VD;
3049     return ExprError();
3050   }
3051   // OpenMP [2.9.2, Restrictions, C/C++, p.4]
3052   //   A threadprivate directive for namespace-scope variables must appear
3053   //   outside any definition or declaration other than the namespace
3054   //   definition itself.
3055   if (CanonicalVD->getDeclContext()->isNamespace() &&
3056       (!getCurLexicalContext()->isFileContext() ||
3057        !getCurLexicalContext()->Encloses(CanonicalVD->getDeclContext()))) {
3058     Diag(Id.getLoc(), diag::err_omp_var_scope)
3059         << getOpenMPDirectiveName(Kind) << VD;
3060     bool IsDecl =
3061         VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3062     Diag(VD->getLocation(),
3063          IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3064         << VD;
3065     return ExprError();
3066   }
3067   // OpenMP [2.9.2, Restrictions, C/C++, p.6]
3068   //   A threadprivate directive for static block-scope variables must appear
3069   //   in the scope of the variable and not in a nested scope.
3070   if (CanonicalVD->isLocalVarDecl() && CurScope &&
3071       !isDeclInScope(ND, getCurLexicalContext(), CurScope)) {
3072     Diag(Id.getLoc(), diag::err_omp_var_scope)
3073         << getOpenMPDirectiveName(Kind) << VD;
3074     bool IsDecl =
3075         VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3076     Diag(VD->getLocation(),
3077          IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3078         << VD;
3079     return ExprError();
3080   }
3081 
3082   // OpenMP [2.9.2, Restrictions, C/C++, p.2-6]
3083   //   A threadprivate directive must lexically precede all references to any
3084   //   of the variables in its list.
3085   if (Kind == OMPD_threadprivate && VD->isUsed() &&
3086       !DSAStack->isThreadPrivate(VD)) {
3087     Diag(Id.getLoc(), diag::err_omp_var_used)
3088         << getOpenMPDirectiveName(Kind) << VD;
3089     return ExprError();
3090   }
3091 
3092   QualType ExprType = VD->getType().getNonReferenceType();
3093   return DeclRefExpr::Create(Context, NestedNameSpecifierLoc(),
3094                              SourceLocation(), VD,
3095                              /*RefersToEnclosingVariableOrCapture=*/false,
3096                              Id.getLoc(), ExprType, VK_LValue);
3097 }
3098 
3099 Sema::DeclGroupPtrTy
3100 Sema::ActOnOpenMPThreadprivateDirective(SourceLocation Loc,
3101                                         ArrayRef<Expr *> VarList) {
3102   if (OMPThreadPrivateDecl *D = CheckOMPThreadPrivateDecl(Loc, VarList)) {
3103     CurContext->addDecl(D);
3104     return DeclGroupPtrTy::make(DeclGroupRef(D));
3105   }
3106   return nullptr;
3107 }
3108 
3109 namespace {
3110 class LocalVarRefChecker final
3111     : public ConstStmtVisitor<LocalVarRefChecker, bool> {
3112   Sema &SemaRef;
3113 
3114 public:
3115   bool VisitDeclRefExpr(const DeclRefExpr *E) {
3116     if (const auto *VD = dyn_cast<VarDecl>(E->getDecl())) {
3117       if (VD->hasLocalStorage()) {
3118         SemaRef.Diag(E->getBeginLoc(),
3119                      diag::err_omp_local_var_in_threadprivate_init)
3120             << E->getSourceRange();
3121         SemaRef.Diag(VD->getLocation(), diag::note_defined_here)
3122             << VD << VD->getSourceRange();
3123         return true;
3124       }
3125     }
3126     return false;
3127   }
3128   bool VisitStmt(const Stmt *S) {
3129     for (const Stmt *Child : S->children()) {
3130       if (Child && Visit(Child))
3131         return true;
3132     }
3133     return false;
3134   }
3135   explicit LocalVarRefChecker(Sema &SemaRef) : SemaRef(SemaRef) {}
3136 };
3137 } // namespace
3138 
3139 OMPThreadPrivateDecl *
3140 Sema::CheckOMPThreadPrivateDecl(SourceLocation Loc, ArrayRef<Expr *> VarList) {
3141   SmallVector<Expr *, 8> Vars;
3142   for (Expr *RefExpr : VarList) {
3143     auto *DE = cast<DeclRefExpr>(RefExpr);
3144     auto *VD = cast<VarDecl>(DE->getDecl());
3145     SourceLocation ILoc = DE->getExprLoc();
3146 
3147     // Mark variable as used.
3148     VD->setReferenced();
3149     VD->markUsed(Context);
3150 
3151     QualType QType = VD->getType();
3152     if (QType->isDependentType() || QType->isInstantiationDependentType()) {
3153       // It will be analyzed later.
3154       Vars.push_back(DE);
3155       continue;
3156     }
3157 
3158     // OpenMP [2.9.2, Restrictions, C/C++, p.10]
3159     //   A threadprivate variable must not have an incomplete type.
3160     if (RequireCompleteType(ILoc, VD->getType(),
3161                             diag::err_omp_threadprivate_incomplete_type)) {
3162       continue;
3163     }
3164 
3165     // OpenMP [2.9.2, Restrictions, C/C++, p.10]
3166     //   A threadprivate variable must not have a reference type.
3167     if (VD->getType()->isReferenceType()) {
3168       Diag(ILoc, diag::err_omp_ref_type_arg)
3169           << getOpenMPDirectiveName(OMPD_threadprivate) << VD->getType();
3170       bool IsDecl =
3171           VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3172       Diag(VD->getLocation(),
3173            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3174           << VD;
3175       continue;
3176     }
3177 
3178     // Check if this is a TLS variable. If TLS is not being supported, produce
3179     // the corresponding diagnostic.
3180     if ((VD->getTLSKind() != VarDecl::TLS_None &&
3181          !(VD->hasAttr<OMPThreadPrivateDeclAttr>() &&
3182            getLangOpts().OpenMPUseTLS &&
3183            getASTContext().getTargetInfo().isTLSSupported())) ||
3184         (VD->getStorageClass() == SC_Register && VD->hasAttr<AsmLabelAttr>() &&
3185          !VD->isLocalVarDecl())) {
3186       Diag(ILoc, diag::err_omp_var_thread_local)
3187           << VD << ((VD->getTLSKind() != VarDecl::TLS_None) ? 0 : 1);
3188       bool IsDecl =
3189           VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3190       Diag(VD->getLocation(),
3191            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3192           << VD;
3193       continue;
3194     }
3195 
3196     // Check if initial value of threadprivate variable reference variable with
3197     // local storage (it is not supported by runtime).
3198     if (const Expr *Init = VD->getAnyInitializer()) {
3199       LocalVarRefChecker Checker(*this);
3200       if (Checker.Visit(Init))
3201         continue;
3202     }
3203 
3204     Vars.push_back(RefExpr);
3205     DSAStack->addDSA(VD, DE, OMPC_threadprivate);
3206     VD->addAttr(OMPThreadPrivateDeclAttr::CreateImplicit(
3207         Context, SourceRange(Loc, Loc)));
3208     if (ASTMutationListener *ML = Context.getASTMutationListener())
3209       ML->DeclarationMarkedOpenMPThreadPrivate(VD);
3210   }
3211   OMPThreadPrivateDecl *D = nullptr;
3212   if (!Vars.empty()) {
3213     D = OMPThreadPrivateDecl::Create(Context, getCurLexicalContext(), Loc,
3214                                      Vars);
3215     D->setAccess(AS_public);
3216   }
3217   return D;
3218 }
3219 
3220 static OMPAllocateDeclAttr::AllocatorTypeTy
3221 getAllocatorKind(Sema &S, DSAStackTy *Stack, Expr *Allocator) {
3222   if (!Allocator)
3223     return OMPAllocateDeclAttr::OMPNullMemAlloc;
3224   if (Allocator->isTypeDependent() || Allocator->isValueDependent() ||
3225       Allocator->isInstantiationDependent() ||
3226       Allocator->containsUnexpandedParameterPack())
3227     return OMPAllocateDeclAttr::OMPUserDefinedMemAlloc;
3228   auto AllocatorKindRes = OMPAllocateDeclAttr::OMPUserDefinedMemAlloc;
3229   const Expr *AE = Allocator->IgnoreParenImpCasts();
3230   for (int I = 0; I < OMPAllocateDeclAttr::OMPUserDefinedMemAlloc; ++I) {
3231     auto AllocatorKind = static_cast<OMPAllocateDeclAttr::AllocatorTypeTy>(I);
3232     const Expr *DefAllocator = Stack->getAllocator(AllocatorKind);
3233     llvm::FoldingSetNodeID AEId, DAEId;
3234     AE->Profile(AEId, S.getASTContext(), /*Canonical=*/true);
3235     DefAllocator->Profile(DAEId, S.getASTContext(), /*Canonical=*/true);
3236     if (AEId == DAEId) {
3237       AllocatorKindRes = AllocatorKind;
3238       break;
3239     }
3240   }
3241   return AllocatorKindRes;
3242 }
3243 
3244 static bool checkPreviousOMPAllocateAttribute(
3245     Sema &S, DSAStackTy *Stack, Expr *RefExpr, VarDecl *VD,
3246     OMPAllocateDeclAttr::AllocatorTypeTy AllocatorKind, Expr *Allocator) {
3247   if (!VD->hasAttr<OMPAllocateDeclAttr>())
3248     return false;
3249   const auto *A = VD->getAttr<OMPAllocateDeclAttr>();
3250   Expr *PrevAllocator = A->getAllocator();
3251   OMPAllocateDeclAttr::AllocatorTypeTy PrevAllocatorKind =
3252       getAllocatorKind(S, Stack, PrevAllocator);
3253   bool AllocatorsMatch = AllocatorKind == PrevAllocatorKind;
3254   if (AllocatorsMatch &&
3255       AllocatorKind == OMPAllocateDeclAttr::OMPUserDefinedMemAlloc &&
3256       Allocator && PrevAllocator) {
3257     const Expr *AE = Allocator->IgnoreParenImpCasts();
3258     const Expr *PAE = PrevAllocator->IgnoreParenImpCasts();
3259     llvm::FoldingSetNodeID AEId, PAEId;
3260     AE->Profile(AEId, S.Context, /*Canonical=*/true);
3261     PAE->Profile(PAEId, S.Context, /*Canonical=*/true);
3262     AllocatorsMatch = AEId == PAEId;
3263   }
3264   if (!AllocatorsMatch) {
3265     SmallString<256> AllocatorBuffer;
3266     llvm::raw_svector_ostream AllocatorStream(AllocatorBuffer);
3267     if (Allocator)
3268       Allocator->printPretty(AllocatorStream, nullptr, S.getPrintingPolicy());
3269     SmallString<256> PrevAllocatorBuffer;
3270     llvm::raw_svector_ostream PrevAllocatorStream(PrevAllocatorBuffer);
3271     if (PrevAllocator)
3272       PrevAllocator->printPretty(PrevAllocatorStream, nullptr,
3273                                  S.getPrintingPolicy());
3274 
3275     SourceLocation AllocatorLoc =
3276         Allocator ? Allocator->getExprLoc() : RefExpr->getExprLoc();
3277     SourceRange AllocatorRange =
3278         Allocator ? Allocator->getSourceRange() : RefExpr->getSourceRange();
3279     SourceLocation PrevAllocatorLoc =
3280         PrevAllocator ? PrevAllocator->getExprLoc() : A->getLocation();
3281     SourceRange PrevAllocatorRange =
3282         PrevAllocator ? PrevAllocator->getSourceRange() : A->getRange();
3283     S.Diag(AllocatorLoc, diag::warn_omp_used_different_allocator)
3284         << (Allocator ? 1 : 0) << AllocatorStream.str()
3285         << (PrevAllocator ? 1 : 0) << PrevAllocatorStream.str()
3286         << AllocatorRange;
3287     S.Diag(PrevAllocatorLoc, diag::note_omp_previous_allocator)
3288         << PrevAllocatorRange;
3289     return true;
3290   }
3291   return false;
3292 }
3293 
3294 static void
3295 applyOMPAllocateAttribute(Sema &S, VarDecl *VD,
3296                           OMPAllocateDeclAttr::AllocatorTypeTy AllocatorKind,
3297                           Expr *Allocator, Expr *Alignment, SourceRange SR) {
3298   if (VD->hasAttr<OMPAllocateDeclAttr>())
3299     return;
3300   if (Alignment &&
3301       (Alignment->isTypeDependent() || Alignment->isValueDependent() ||
3302        Alignment->isInstantiationDependent() ||
3303        Alignment->containsUnexpandedParameterPack()))
3304     // Apply later when we have a usable value.
3305     return;
3306   if (Allocator &&
3307       (Allocator->isTypeDependent() || Allocator->isValueDependent() ||
3308        Allocator->isInstantiationDependent() ||
3309        Allocator->containsUnexpandedParameterPack()))
3310     return;
3311   auto *A = OMPAllocateDeclAttr::CreateImplicit(S.Context, AllocatorKind,
3312                                                 Allocator, Alignment, SR);
3313   VD->addAttr(A);
3314   if (ASTMutationListener *ML = S.Context.getASTMutationListener())
3315     ML->DeclarationMarkedOpenMPAllocate(VD, A);
3316 }
3317 
3318 Sema::DeclGroupPtrTy
3319 Sema::ActOnOpenMPAllocateDirective(SourceLocation Loc, ArrayRef<Expr *> VarList,
3320                                    ArrayRef<OMPClause *> Clauses,
3321                                    DeclContext *Owner) {
3322   assert(Clauses.size() <= 2 && "Expected at most two clauses.");
3323   Expr *Alignment = nullptr;
3324   Expr *Allocator = nullptr;
3325   if (Clauses.empty()) {
3326     // OpenMP 5.0, 2.11.3 allocate Directive, Restrictions.
3327     // allocate directives that appear in a target region must specify an
3328     // allocator clause unless a requires directive with the dynamic_allocators
3329     // clause is present in the same compilation unit.
3330     if (LangOpts.OpenMPIsDevice &&
3331         !DSAStack->hasRequiresDeclWithClause<OMPDynamicAllocatorsClause>())
3332       targetDiag(Loc, diag::err_expected_allocator_clause);
3333   } else {
3334     for (const OMPClause *C : Clauses)
3335       if (const auto *AC = dyn_cast<OMPAllocatorClause>(C))
3336         Allocator = AC->getAllocator();
3337       else if (const auto *AC = dyn_cast<OMPAlignClause>(C))
3338         Alignment = AC->getAlignment();
3339       else
3340         llvm_unreachable("Unexpected clause on allocate directive");
3341   }
3342   OMPAllocateDeclAttr::AllocatorTypeTy AllocatorKind =
3343       getAllocatorKind(*this, DSAStack, Allocator);
3344   SmallVector<Expr *, 8> Vars;
3345   for (Expr *RefExpr : VarList) {
3346     auto *DE = cast<DeclRefExpr>(RefExpr);
3347     auto *VD = cast<VarDecl>(DE->getDecl());
3348 
3349     // Check if this is a TLS variable or global register.
3350     if (VD->getTLSKind() != VarDecl::TLS_None ||
3351         VD->hasAttr<OMPThreadPrivateDeclAttr>() ||
3352         (VD->getStorageClass() == SC_Register && VD->hasAttr<AsmLabelAttr>() &&
3353          !VD->isLocalVarDecl()))
3354       continue;
3355 
3356     // If the used several times in the allocate directive, the same allocator
3357     // must be used.
3358     if (checkPreviousOMPAllocateAttribute(*this, DSAStack, RefExpr, VD,
3359                                           AllocatorKind, Allocator))
3360       continue;
3361 
3362     // OpenMP, 2.11.3 allocate Directive, Restrictions, C / C++
3363     // If a list item has a static storage type, the allocator expression in the
3364     // allocator clause must be a constant expression that evaluates to one of
3365     // the predefined memory allocator values.
3366     if (Allocator && VD->hasGlobalStorage()) {
3367       if (AllocatorKind == OMPAllocateDeclAttr::OMPUserDefinedMemAlloc) {
3368         Diag(Allocator->getExprLoc(),
3369              diag::err_omp_expected_predefined_allocator)
3370             << Allocator->getSourceRange();
3371         bool IsDecl = VD->isThisDeclarationADefinition(Context) ==
3372                       VarDecl::DeclarationOnly;
3373         Diag(VD->getLocation(),
3374              IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3375             << VD;
3376         continue;
3377       }
3378     }
3379 
3380     Vars.push_back(RefExpr);
3381     applyOMPAllocateAttribute(*this, VD, AllocatorKind, Allocator, Alignment,
3382                               DE->getSourceRange());
3383   }
3384   if (Vars.empty())
3385     return nullptr;
3386   if (!Owner)
3387     Owner = getCurLexicalContext();
3388   auto *D = OMPAllocateDecl::Create(Context, Owner, Loc, Vars, Clauses);
3389   D->setAccess(AS_public);
3390   Owner->addDecl(D);
3391   return DeclGroupPtrTy::make(DeclGroupRef(D));
3392 }
3393 
3394 Sema::DeclGroupPtrTy
3395 Sema::ActOnOpenMPRequiresDirective(SourceLocation Loc,
3396                                    ArrayRef<OMPClause *> ClauseList) {
3397   OMPRequiresDecl *D = nullptr;
3398   if (!CurContext->isFileContext()) {
3399     Diag(Loc, diag::err_omp_invalid_scope) << "requires";
3400   } else {
3401     D = CheckOMPRequiresDecl(Loc, ClauseList);
3402     if (D) {
3403       CurContext->addDecl(D);
3404       DSAStack->addRequiresDecl(D);
3405     }
3406   }
3407   return DeclGroupPtrTy::make(DeclGroupRef(D));
3408 }
3409 
3410 void Sema::ActOnOpenMPAssumesDirective(SourceLocation Loc,
3411                                        OpenMPDirectiveKind DKind,
3412                                        ArrayRef<std::string> Assumptions,
3413                                        bool SkippedClauses) {
3414   if (!SkippedClauses && Assumptions.empty())
3415     Diag(Loc, diag::err_omp_no_clause_for_directive)
3416         << llvm::omp::getAllAssumeClauseOptions()
3417         << llvm::omp::getOpenMPDirectiveName(DKind);
3418 
3419   auto *AA = AssumptionAttr::Create(Context, llvm::join(Assumptions, ","), Loc);
3420   if (DKind == llvm::omp::Directive::OMPD_begin_assumes) {
3421     OMPAssumeScoped.push_back(AA);
3422     return;
3423   }
3424 
3425   // Global assumes without assumption clauses are ignored.
3426   if (Assumptions.empty())
3427     return;
3428 
3429   assert(DKind == llvm::omp::Directive::OMPD_assumes &&
3430          "Unexpected omp assumption directive!");
3431   OMPAssumeGlobal.push_back(AA);
3432 
3433   // The OMPAssumeGlobal scope above will take care of new declarations but
3434   // we also want to apply the assumption to existing ones, e.g., to
3435   // declarations in included headers. To this end, we traverse all existing
3436   // declaration contexts and annotate function declarations here.
3437   SmallVector<DeclContext *, 8> DeclContexts;
3438   auto *Ctx = CurContext;
3439   while (Ctx->getLexicalParent())
3440     Ctx = Ctx->getLexicalParent();
3441   DeclContexts.push_back(Ctx);
3442   while (!DeclContexts.empty()) {
3443     DeclContext *DC = DeclContexts.pop_back_val();
3444     for (auto *SubDC : DC->decls()) {
3445       if (SubDC->isInvalidDecl())
3446         continue;
3447       if (auto *CTD = dyn_cast<ClassTemplateDecl>(SubDC)) {
3448         DeclContexts.push_back(CTD->getTemplatedDecl());
3449         llvm::append_range(DeclContexts, CTD->specializations());
3450         continue;
3451       }
3452       if (auto *DC = dyn_cast<DeclContext>(SubDC))
3453         DeclContexts.push_back(DC);
3454       if (auto *F = dyn_cast<FunctionDecl>(SubDC)) {
3455         F->addAttr(AA);
3456         continue;
3457       }
3458     }
3459   }
3460 }
3461 
3462 void Sema::ActOnOpenMPEndAssumesDirective() {
3463   assert(isInOpenMPAssumeScope() && "Not in OpenMP assumes scope!");
3464   OMPAssumeScoped.pop_back();
3465 }
3466 
3467 OMPRequiresDecl *Sema::CheckOMPRequiresDecl(SourceLocation Loc,
3468                                             ArrayRef<OMPClause *> ClauseList) {
3469   /// For target specific clauses, the requires directive cannot be
3470   /// specified after the handling of any of the target regions in the
3471   /// current compilation unit.
3472   ArrayRef<SourceLocation> TargetLocations =
3473       DSAStack->getEncounteredTargetLocs();
3474   SourceLocation AtomicLoc = DSAStack->getAtomicDirectiveLoc();
3475   if (!TargetLocations.empty() || !AtomicLoc.isInvalid()) {
3476     for (const OMPClause *CNew : ClauseList) {
3477       // Check if any of the requires clauses affect target regions.
3478       if (isa<OMPUnifiedSharedMemoryClause>(CNew) ||
3479           isa<OMPUnifiedAddressClause>(CNew) ||
3480           isa<OMPReverseOffloadClause>(CNew) ||
3481           isa<OMPDynamicAllocatorsClause>(CNew)) {
3482         Diag(Loc, diag::err_omp_directive_before_requires)
3483             << "target" << getOpenMPClauseName(CNew->getClauseKind());
3484         for (SourceLocation TargetLoc : TargetLocations) {
3485           Diag(TargetLoc, diag::note_omp_requires_encountered_directive)
3486               << "target";
3487         }
3488       } else if (!AtomicLoc.isInvalid() &&
3489                  isa<OMPAtomicDefaultMemOrderClause>(CNew)) {
3490         Diag(Loc, diag::err_omp_directive_before_requires)
3491             << "atomic" << getOpenMPClauseName(CNew->getClauseKind());
3492         Diag(AtomicLoc, diag::note_omp_requires_encountered_directive)
3493             << "atomic";
3494       }
3495     }
3496   }
3497 
3498   if (!DSAStack->hasDuplicateRequiresClause(ClauseList))
3499     return OMPRequiresDecl::Create(Context, getCurLexicalContext(), Loc,
3500                                    ClauseList);
3501   return nullptr;
3502 }
3503 
3504 static void reportOriginalDsa(Sema &SemaRef, const DSAStackTy *Stack,
3505                               const ValueDecl *D,
3506                               const DSAStackTy::DSAVarData &DVar,
3507                               bool IsLoopIterVar) {
3508   if (DVar.RefExpr) {
3509     SemaRef.Diag(DVar.RefExpr->getExprLoc(), diag::note_omp_explicit_dsa)
3510         << getOpenMPClauseName(DVar.CKind);
3511     return;
3512   }
3513   enum {
3514     PDSA_StaticMemberShared,
3515     PDSA_StaticLocalVarShared,
3516     PDSA_LoopIterVarPrivate,
3517     PDSA_LoopIterVarLinear,
3518     PDSA_LoopIterVarLastprivate,
3519     PDSA_ConstVarShared,
3520     PDSA_GlobalVarShared,
3521     PDSA_TaskVarFirstprivate,
3522     PDSA_LocalVarPrivate,
3523     PDSA_Implicit
3524   } Reason = PDSA_Implicit;
3525   bool ReportHint = false;
3526   auto ReportLoc = D->getLocation();
3527   auto *VD = dyn_cast<VarDecl>(D);
3528   if (IsLoopIterVar) {
3529     if (DVar.CKind == OMPC_private)
3530       Reason = PDSA_LoopIterVarPrivate;
3531     else if (DVar.CKind == OMPC_lastprivate)
3532       Reason = PDSA_LoopIterVarLastprivate;
3533     else
3534       Reason = PDSA_LoopIterVarLinear;
3535   } else if (isOpenMPTaskingDirective(DVar.DKind) &&
3536              DVar.CKind == OMPC_firstprivate) {
3537     Reason = PDSA_TaskVarFirstprivate;
3538     ReportLoc = DVar.ImplicitDSALoc;
3539   } else if (VD && VD->isStaticLocal())
3540     Reason = PDSA_StaticLocalVarShared;
3541   else if (VD && VD->isStaticDataMember())
3542     Reason = PDSA_StaticMemberShared;
3543   else if (VD && VD->isFileVarDecl())
3544     Reason = PDSA_GlobalVarShared;
3545   else if (D->getType().isConstant(SemaRef.getASTContext()))
3546     Reason = PDSA_ConstVarShared;
3547   else if (VD && VD->isLocalVarDecl() && DVar.CKind == OMPC_private) {
3548     ReportHint = true;
3549     Reason = PDSA_LocalVarPrivate;
3550   }
3551   if (Reason != PDSA_Implicit) {
3552     SemaRef.Diag(ReportLoc, diag::note_omp_predetermined_dsa)
3553         << Reason << ReportHint
3554         << getOpenMPDirectiveName(Stack->getCurrentDirective());
3555   } else if (DVar.ImplicitDSALoc.isValid()) {
3556     SemaRef.Diag(DVar.ImplicitDSALoc, diag::note_omp_implicit_dsa)
3557         << getOpenMPClauseName(DVar.CKind);
3558   }
3559 }
3560 
3561 static OpenMPMapClauseKind
3562 getMapClauseKindFromModifier(OpenMPDefaultmapClauseModifier M,
3563                              bool IsAggregateOrDeclareTarget) {
3564   OpenMPMapClauseKind Kind = OMPC_MAP_unknown;
3565   switch (M) {
3566   case OMPC_DEFAULTMAP_MODIFIER_alloc:
3567     Kind = OMPC_MAP_alloc;
3568     break;
3569   case OMPC_DEFAULTMAP_MODIFIER_to:
3570     Kind = OMPC_MAP_to;
3571     break;
3572   case OMPC_DEFAULTMAP_MODIFIER_from:
3573     Kind = OMPC_MAP_from;
3574     break;
3575   case OMPC_DEFAULTMAP_MODIFIER_tofrom:
3576     Kind = OMPC_MAP_tofrom;
3577     break;
3578   case OMPC_DEFAULTMAP_MODIFIER_present:
3579     // OpenMP 5.1 [2.21.7.3] defaultmap clause, Description]
3580     // If implicit-behavior is present, each variable referenced in the
3581     // construct in the category specified by variable-category is treated as if
3582     // it had been listed in a map clause with the map-type of alloc and
3583     // map-type-modifier of present.
3584     Kind = OMPC_MAP_alloc;
3585     break;
3586   case OMPC_DEFAULTMAP_MODIFIER_firstprivate:
3587   case OMPC_DEFAULTMAP_MODIFIER_last:
3588     llvm_unreachable("Unexpected defaultmap implicit behavior");
3589   case OMPC_DEFAULTMAP_MODIFIER_none:
3590   case OMPC_DEFAULTMAP_MODIFIER_default:
3591   case OMPC_DEFAULTMAP_MODIFIER_unknown:
3592     // IsAggregateOrDeclareTarget could be true if:
3593     // 1. the implicit behavior for aggregate is tofrom
3594     // 2. it's a declare target link
3595     if (IsAggregateOrDeclareTarget) {
3596       Kind = OMPC_MAP_tofrom;
3597       break;
3598     }
3599     llvm_unreachable("Unexpected defaultmap implicit behavior");
3600   }
3601   assert(Kind != OMPC_MAP_unknown && "Expect map kind to be known");
3602   return Kind;
3603 }
3604 
3605 namespace {
3606 class DSAAttrChecker final : public StmtVisitor<DSAAttrChecker, void> {
3607   DSAStackTy *Stack;
3608   Sema &SemaRef;
3609   bool ErrorFound = false;
3610   bool TryCaptureCXXThisMembers = false;
3611   CapturedStmt *CS = nullptr;
3612   const static unsigned DefaultmapKindNum = OMPC_DEFAULTMAP_pointer + 1;
3613   llvm::SmallVector<Expr *, 4> ImplicitFirstprivate;
3614   llvm::SmallVector<Expr *, 4> ImplicitPrivate;
3615   llvm::SmallVector<Expr *, 4> ImplicitMap[DefaultmapKindNum][OMPC_MAP_delete];
3616   llvm::SmallVector<OpenMPMapModifierKind, NumberOfOMPMapClauseModifiers>
3617       ImplicitMapModifier[DefaultmapKindNum];
3618   Sema::VarsWithInheritedDSAType VarsWithInheritedDSA;
3619   llvm::SmallDenseSet<const ValueDecl *, 4> ImplicitDeclarations;
3620 
3621   void VisitSubCaptures(OMPExecutableDirective *S) {
3622     // Check implicitly captured variables.
3623     if (!S->hasAssociatedStmt() || !S->getAssociatedStmt())
3624       return;
3625     if (S->getDirectiveKind() == OMPD_atomic ||
3626         S->getDirectiveKind() == OMPD_critical ||
3627         S->getDirectiveKind() == OMPD_section ||
3628         S->getDirectiveKind() == OMPD_master ||
3629         S->getDirectiveKind() == OMPD_masked ||
3630         isOpenMPLoopTransformationDirective(S->getDirectiveKind())) {
3631       Visit(S->getAssociatedStmt());
3632       return;
3633     }
3634     visitSubCaptures(S->getInnermostCapturedStmt());
3635     // Try to capture inner this->member references to generate correct mappings
3636     // and diagnostics.
3637     if (TryCaptureCXXThisMembers ||
3638         (isOpenMPTargetExecutionDirective(Stack->getCurrentDirective()) &&
3639          llvm::any_of(S->getInnermostCapturedStmt()->captures(),
3640                       [](const CapturedStmt::Capture &C) {
3641                         return C.capturesThis();
3642                       }))) {
3643       bool SavedTryCaptureCXXThisMembers = TryCaptureCXXThisMembers;
3644       TryCaptureCXXThisMembers = true;
3645       Visit(S->getInnermostCapturedStmt()->getCapturedStmt());
3646       TryCaptureCXXThisMembers = SavedTryCaptureCXXThisMembers;
3647     }
3648     // In tasks firstprivates are not captured anymore, need to analyze them
3649     // explicitly.
3650     if (isOpenMPTaskingDirective(S->getDirectiveKind()) &&
3651         !isOpenMPTaskLoopDirective(S->getDirectiveKind())) {
3652       for (OMPClause *C : S->clauses())
3653         if (auto *FC = dyn_cast<OMPFirstprivateClause>(C)) {
3654           for (Expr *Ref : FC->varlists())
3655             Visit(Ref);
3656         }
3657     }
3658   }
3659 
3660 public:
3661   void VisitDeclRefExpr(DeclRefExpr *E) {
3662     if (TryCaptureCXXThisMembers || E->isTypeDependent() ||
3663         E->isValueDependent() || E->containsUnexpandedParameterPack() ||
3664         E->isInstantiationDependent())
3665       return;
3666     if (auto *VD = dyn_cast<VarDecl>(E->getDecl())) {
3667       // Check the datasharing rules for the expressions in the clauses.
3668       if (!CS || (isa<OMPCapturedExprDecl>(VD) && !CS->capturesVariable(VD) &&
3669                   !Stack->getTopDSA(VD, /*FromParent=*/false).RefExpr &&
3670                   !Stack->isImplicitDefaultFirstprivateFD(VD))) {
3671         if (auto *CED = dyn_cast<OMPCapturedExprDecl>(VD))
3672           if (!CED->hasAttr<OMPCaptureNoInitAttr>()) {
3673             Visit(CED->getInit());
3674             return;
3675           }
3676       } else if (VD->isImplicit() || isa<OMPCapturedExprDecl>(VD))
3677         // Do not analyze internal variables and do not enclose them into
3678         // implicit clauses.
3679         if (!Stack->isImplicitDefaultFirstprivateFD(VD))
3680           return;
3681       VD = VD->getCanonicalDecl();
3682       // Skip internally declared variables.
3683       if (VD->hasLocalStorage() && CS && !CS->capturesVariable(VD) &&
3684           !Stack->isImplicitDefaultFirstprivateFD(VD) &&
3685           !Stack->isImplicitTaskFirstprivate(VD))
3686         return;
3687       // Skip allocators in uses_allocators clauses.
3688       if (Stack->isUsesAllocatorsDecl(VD))
3689         return;
3690 
3691       DSAStackTy::DSAVarData DVar = Stack->getTopDSA(VD, /*FromParent=*/false);
3692       // Check if the variable has explicit DSA set and stop analysis if it so.
3693       if (DVar.RefExpr || !ImplicitDeclarations.insert(VD).second)
3694         return;
3695 
3696       // Skip internally declared static variables.
3697       llvm::Optional<OMPDeclareTargetDeclAttr::MapTypeTy> Res =
3698           OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(VD);
3699       if (VD->hasGlobalStorage() && CS && !CS->capturesVariable(VD) &&
3700           (Stack->hasRequiresDeclWithClause<OMPUnifiedSharedMemoryClause>() ||
3701            !Res || *Res != OMPDeclareTargetDeclAttr::MT_Link) &&
3702           !Stack->isImplicitDefaultFirstprivateFD(VD) &&
3703           !Stack->isImplicitTaskFirstprivate(VD))
3704         return;
3705 
3706       SourceLocation ELoc = E->getExprLoc();
3707       OpenMPDirectiveKind DKind = Stack->getCurrentDirective();
3708       // The default(none) clause requires that each variable that is referenced
3709       // in the construct, and does not have a predetermined data-sharing
3710       // attribute, must have its data-sharing attribute explicitly determined
3711       // by being listed in a data-sharing attribute clause.
3712       if (DVar.CKind == OMPC_unknown &&
3713           (Stack->getDefaultDSA() == DSA_none ||
3714            Stack->getDefaultDSA() == DSA_private ||
3715            Stack->getDefaultDSA() == DSA_firstprivate) &&
3716           isImplicitOrExplicitTaskingRegion(DKind) &&
3717           VarsWithInheritedDSA.count(VD) == 0) {
3718         bool InheritedDSA = Stack->getDefaultDSA() == DSA_none;
3719         if (!InheritedDSA && (Stack->getDefaultDSA() == DSA_firstprivate ||
3720                               Stack->getDefaultDSA() == DSA_private)) {
3721           DSAStackTy::DSAVarData DVar =
3722               Stack->getImplicitDSA(VD, /*FromParent=*/false);
3723           InheritedDSA = DVar.CKind == OMPC_unknown;
3724         }
3725         if (InheritedDSA)
3726           VarsWithInheritedDSA[VD] = E;
3727         if (Stack->getDefaultDSA() == DSA_none)
3728           return;
3729       }
3730 
3731       // OpenMP 5.0 [2.19.7.2, defaultmap clause, Description]
3732       // If implicit-behavior is none, each variable referenced in the
3733       // construct that does not have a predetermined data-sharing attribute
3734       // and does not appear in a to or link clause on a declare target
3735       // directive must be listed in a data-mapping attribute clause, a
3736       // data-sharing attribute clause (including a data-sharing attribute
3737       // clause on a combined construct where target. is one of the
3738       // constituent constructs), or an is_device_ptr clause.
3739       OpenMPDefaultmapClauseKind ClauseKind =
3740           getVariableCategoryFromDecl(SemaRef.getLangOpts(), VD);
3741       if (SemaRef.getLangOpts().OpenMP >= 50) {
3742         bool IsModifierNone = Stack->getDefaultmapModifier(ClauseKind) ==
3743                               OMPC_DEFAULTMAP_MODIFIER_none;
3744         if (DVar.CKind == OMPC_unknown && IsModifierNone &&
3745             VarsWithInheritedDSA.count(VD) == 0 && !Res) {
3746           // Only check for data-mapping attribute and is_device_ptr here
3747           // since we have already make sure that the declaration does not
3748           // have a data-sharing attribute above
3749           if (!Stack->checkMappableExprComponentListsForDecl(
3750                   VD, /*CurrentRegionOnly=*/true,
3751                   [VD](OMPClauseMappableExprCommon::MappableExprComponentListRef
3752                            MapExprComponents,
3753                        OpenMPClauseKind) {
3754                     auto MI = MapExprComponents.rbegin();
3755                     auto ME = MapExprComponents.rend();
3756                     return MI != ME && MI->getAssociatedDeclaration() == VD;
3757                   })) {
3758             VarsWithInheritedDSA[VD] = E;
3759             return;
3760           }
3761         }
3762       }
3763       if (SemaRef.getLangOpts().OpenMP > 50) {
3764         bool IsModifierPresent = Stack->getDefaultmapModifier(ClauseKind) ==
3765                                  OMPC_DEFAULTMAP_MODIFIER_present;
3766         if (IsModifierPresent) {
3767           if (llvm::find(ImplicitMapModifier[ClauseKind],
3768                          OMPC_MAP_MODIFIER_present) ==
3769               std::end(ImplicitMapModifier[ClauseKind])) {
3770             ImplicitMapModifier[ClauseKind].push_back(
3771                 OMPC_MAP_MODIFIER_present);
3772           }
3773         }
3774       }
3775 
3776       if (isOpenMPTargetExecutionDirective(DKind) &&
3777           !Stack->isLoopControlVariable(VD).first) {
3778         if (!Stack->checkMappableExprComponentListsForDecl(
3779                 VD, /*CurrentRegionOnly=*/true,
3780                 [this](OMPClauseMappableExprCommon::MappableExprComponentListRef
3781                            StackComponents,
3782                        OpenMPClauseKind) {
3783                   if (SemaRef.LangOpts.OpenMP >= 50)
3784                     return !StackComponents.empty();
3785                   // Variable is used if it has been marked as an array, array
3786                   // section, array shaping or the variable iself.
3787                   return StackComponents.size() == 1 ||
3788                          std::all_of(
3789                              std::next(StackComponents.rbegin()),
3790                              StackComponents.rend(),
3791                              [](const OMPClauseMappableExprCommon::
3792                                     MappableComponent &MC) {
3793                                return MC.getAssociatedDeclaration() ==
3794                                           nullptr &&
3795                                       (isa<OMPArraySectionExpr>(
3796                                            MC.getAssociatedExpression()) ||
3797                                        isa<OMPArrayShapingExpr>(
3798                                            MC.getAssociatedExpression()) ||
3799                                        isa<ArraySubscriptExpr>(
3800                                            MC.getAssociatedExpression()));
3801                              });
3802                 })) {
3803           bool IsFirstprivate = false;
3804           // By default lambdas are captured as firstprivates.
3805           if (const auto *RD =
3806                   VD->getType().getNonReferenceType()->getAsCXXRecordDecl())
3807             IsFirstprivate = RD->isLambda();
3808           IsFirstprivate =
3809               IsFirstprivate || (Stack->mustBeFirstprivate(ClauseKind) && !Res);
3810           if (IsFirstprivate) {
3811             ImplicitFirstprivate.emplace_back(E);
3812           } else {
3813             OpenMPDefaultmapClauseModifier M =
3814                 Stack->getDefaultmapModifier(ClauseKind);
3815             OpenMPMapClauseKind Kind = getMapClauseKindFromModifier(
3816                 M, ClauseKind == OMPC_DEFAULTMAP_aggregate || Res);
3817             ImplicitMap[ClauseKind][Kind].emplace_back(E);
3818           }
3819           return;
3820         }
3821       }
3822 
3823       // OpenMP [2.9.3.6, Restrictions, p.2]
3824       //  A list item that appears in a reduction clause of the innermost
3825       //  enclosing worksharing or parallel construct may not be accessed in an
3826       //  explicit task.
3827       DVar = Stack->hasInnermostDSA(
3828           VD,
3829           [](OpenMPClauseKind C, bool AppliedToPointee) {
3830             return C == OMPC_reduction && !AppliedToPointee;
3831           },
3832           [](OpenMPDirectiveKind K) {
3833             return isOpenMPParallelDirective(K) ||
3834                    isOpenMPWorksharingDirective(K) || isOpenMPTeamsDirective(K);
3835           },
3836           /*FromParent=*/true);
3837       if (isOpenMPTaskingDirective(DKind) && DVar.CKind == OMPC_reduction) {
3838         ErrorFound = true;
3839         SemaRef.Diag(ELoc, diag::err_omp_reduction_in_task);
3840         reportOriginalDsa(SemaRef, Stack, VD, DVar);
3841         return;
3842       }
3843 
3844       // Define implicit data-sharing attributes for task.
3845       DVar = Stack->getImplicitDSA(VD, /*FromParent=*/false);
3846       if (((isOpenMPTaskingDirective(DKind) && DVar.CKind != OMPC_shared) ||
3847            (((Stack->getDefaultDSA() == DSA_firstprivate &&
3848               DVar.CKind == OMPC_firstprivate) ||
3849              (Stack->getDefaultDSA() == DSA_private &&
3850               DVar.CKind == OMPC_private)) &&
3851             !DVar.RefExpr)) &&
3852           !Stack->isLoopControlVariable(VD).first) {
3853         if (Stack->getDefaultDSA() == DSA_private)
3854           ImplicitPrivate.push_back(E);
3855         else
3856           ImplicitFirstprivate.push_back(E);
3857         return;
3858       }
3859 
3860       // Store implicitly used globals with declare target link for parent
3861       // target.
3862       if (!isOpenMPTargetExecutionDirective(DKind) && Res &&
3863           *Res == OMPDeclareTargetDeclAttr::MT_Link) {
3864         Stack->addToParentTargetRegionLinkGlobals(E);
3865         return;
3866       }
3867     }
3868   }
3869   void VisitMemberExpr(MemberExpr *E) {
3870     if (E->isTypeDependent() || E->isValueDependent() ||
3871         E->containsUnexpandedParameterPack() || E->isInstantiationDependent())
3872       return;
3873     auto *FD = dyn_cast<FieldDecl>(E->getMemberDecl());
3874     OpenMPDirectiveKind DKind = Stack->getCurrentDirective();
3875     if (auto *TE = dyn_cast<CXXThisExpr>(E->getBase()->IgnoreParenCasts())) {
3876       if (!FD)
3877         return;
3878       DSAStackTy::DSAVarData DVar = Stack->getTopDSA(FD, /*FromParent=*/false);
3879       // Check if the variable has explicit DSA set and stop analysis if it
3880       // so.
3881       if (DVar.RefExpr || !ImplicitDeclarations.insert(FD).second)
3882         return;
3883 
3884       if (isOpenMPTargetExecutionDirective(DKind) &&
3885           !Stack->isLoopControlVariable(FD).first &&
3886           !Stack->checkMappableExprComponentListsForDecl(
3887               FD, /*CurrentRegionOnly=*/true,
3888               [](OMPClauseMappableExprCommon::MappableExprComponentListRef
3889                      StackComponents,
3890                  OpenMPClauseKind) {
3891                 return isa<CXXThisExpr>(
3892                     cast<MemberExpr>(
3893                         StackComponents.back().getAssociatedExpression())
3894                         ->getBase()
3895                         ->IgnoreParens());
3896               })) {
3897         // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C/C++, p.3]
3898         //  A bit-field cannot appear in a map clause.
3899         //
3900         if (FD->isBitField())
3901           return;
3902 
3903         // Check to see if the member expression is referencing a class that
3904         // has already been explicitly mapped
3905         if (Stack->isClassPreviouslyMapped(TE->getType()))
3906           return;
3907 
3908         OpenMPDefaultmapClauseModifier Modifier =
3909             Stack->getDefaultmapModifier(OMPC_DEFAULTMAP_aggregate);
3910         OpenMPDefaultmapClauseKind ClauseKind =
3911             getVariableCategoryFromDecl(SemaRef.getLangOpts(), FD);
3912         OpenMPMapClauseKind Kind = getMapClauseKindFromModifier(
3913             Modifier, /*IsAggregateOrDeclareTarget*/ true);
3914         ImplicitMap[ClauseKind][Kind].emplace_back(E);
3915         return;
3916       }
3917 
3918       SourceLocation ELoc = E->getExprLoc();
3919       // OpenMP [2.9.3.6, Restrictions, p.2]
3920       //  A list item that appears in a reduction clause of the innermost
3921       //  enclosing worksharing or parallel construct may not be accessed in
3922       //  an  explicit task.
3923       DVar = Stack->hasInnermostDSA(
3924           FD,
3925           [](OpenMPClauseKind C, bool AppliedToPointee) {
3926             return C == OMPC_reduction && !AppliedToPointee;
3927           },
3928           [](OpenMPDirectiveKind K) {
3929             return isOpenMPParallelDirective(K) ||
3930                    isOpenMPWorksharingDirective(K) || isOpenMPTeamsDirective(K);
3931           },
3932           /*FromParent=*/true);
3933       if (isOpenMPTaskingDirective(DKind) && DVar.CKind == OMPC_reduction) {
3934         ErrorFound = true;
3935         SemaRef.Diag(ELoc, diag::err_omp_reduction_in_task);
3936         reportOriginalDsa(SemaRef, Stack, FD, DVar);
3937         return;
3938       }
3939 
3940       // Define implicit data-sharing attributes for task.
3941       DVar = Stack->getImplicitDSA(FD, /*FromParent=*/false);
3942       if (isOpenMPTaskingDirective(DKind) && DVar.CKind != OMPC_shared &&
3943           !Stack->isLoopControlVariable(FD).first) {
3944         // Check if there is a captured expression for the current field in the
3945         // region. Do not mark it as firstprivate unless there is no captured
3946         // expression.
3947         // TODO: try to make it firstprivate.
3948         if (DVar.CKind != OMPC_unknown)
3949           ImplicitFirstprivate.push_back(E);
3950       }
3951       return;
3952     }
3953     if (isOpenMPTargetExecutionDirective(DKind)) {
3954       OMPClauseMappableExprCommon::MappableExprComponentList CurComponents;
3955       if (!checkMapClauseExpressionBase(SemaRef, E, CurComponents, OMPC_map,
3956                                         Stack->getCurrentDirective(),
3957                                         /*NoDiagnose=*/true))
3958         return;
3959       const auto *VD = cast<ValueDecl>(
3960           CurComponents.back().getAssociatedDeclaration()->getCanonicalDecl());
3961       if (!Stack->checkMappableExprComponentListsForDecl(
3962               VD, /*CurrentRegionOnly=*/true,
3963               [&CurComponents](
3964                   OMPClauseMappableExprCommon::MappableExprComponentListRef
3965                       StackComponents,
3966                   OpenMPClauseKind) {
3967                 auto CCI = CurComponents.rbegin();
3968                 auto CCE = CurComponents.rend();
3969                 for (const auto &SC : llvm::reverse(StackComponents)) {
3970                   // Do both expressions have the same kind?
3971                   if (CCI->getAssociatedExpression()->getStmtClass() !=
3972                       SC.getAssociatedExpression()->getStmtClass())
3973                     if (!((isa<OMPArraySectionExpr>(
3974                                SC.getAssociatedExpression()) ||
3975                            isa<OMPArrayShapingExpr>(
3976                                SC.getAssociatedExpression())) &&
3977                           isa<ArraySubscriptExpr>(
3978                               CCI->getAssociatedExpression())))
3979                       return false;
3980 
3981                   const Decl *CCD = CCI->getAssociatedDeclaration();
3982                   const Decl *SCD = SC.getAssociatedDeclaration();
3983                   CCD = CCD ? CCD->getCanonicalDecl() : nullptr;
3984                   SCD = SCD ? SCD->getCanonicalDecl() : nullptr;
3985                   if (SCD != CCD)
3986                     return false;
3987                   std::advance(CCI, 1);
3988                   if (CCI == CCE)
3989                     break;
3990                 }
3991                 return true;
3992               })) {
3993         Visit(E->getBase());
3994       }
3995     } else if (!TryCaptureCXXThisMembers) {
3996       Visit(E->getBase());
3997     }
3998   }
3999   void VisitOMPExecutableDirective(OMPExecutableDirective *S) {
4000     for (OMPClause *C : S->clauses()) {
4001       // Skip analysis of arguments of private clauses for task|target
4002       // directives.
4003       if (isa_and_nonnull<OMPPrivateClause>(C))
4004         continue;
4005       // Skip analysis of arguments of implicitly defined firstprivate clause
4006       // for task|target directives.
4007       // Skip analysis of arguments of implicitly defined map clause for target
4008       // directives.
4009       if (C && !((isa<OMPFirstprivateClause>(C) || isa<OMPMapClause>(C)) &&
4010                  C->isImplicit() &&
4011                  !isOpenMPTaskingDirective(Stack->getCurrentDirective()))) {
4012         for (Stmt *CC : C->children()) {
4013           if (CC)
4014             Visit(CC);
4015         }
4016       }
4017     }
4018     // Check implicitly captured variables.
4019     VisitSubCaptures(S);
4020   }
4021 
4022   void VisitOMPLoopTransformationDirective(OMPLoopTransformationDirective *S) {
4023     // Loop transformation directives do not introduce data sharing
4024     VisitStmt(S);
4025   }
4026 
4027   void VisitCallExpr(CallExpr *S) {
4028     for (Stmt *C : S->arguments()) {
4029       if (C) {
4030         // Check implicitly captured variables in the task-based directives to
4031         // check if they must be firstprivatized.
4032         Visit(C);
4033       }
4034     }
4035     if (Expr *Callee = S->getCallee())
4036       if (auto *CE = dyn_cast<MemberExpr>(Callee->IgnoreParenImpCasts()))
4037         Visit(CE->getBase());
4038   }
4039   void VisitStmt(Stmt *S) {
4040     for (Stmt *C : S->children()) {
4041       if (C) {
4042         // Check implicitly captured variables in the task-based directives to
4043         // check if they must be firstprivatized.
4044         Visit(C);
4045       }
4046     }
4047   }
4048 
4049   void visitSubCaptures(CapturedStmt *S) {
4050     for (const CapturedStmt::Capture &Cap : S->captures()) {
4051       if (!Cap.capturesVariable() && !Cap.capturesVariableByCopy())
4052         continue;
4053       VarDecl *VD = Cap.getCapturedVar();
4054       // Do not try to map the variable if it or its sub-component was mapped
4055       // already.
4056       if (isOpenMPTargetExecutionDirective(Stack->getCurrentDirective()) &&
4057           Stack->checkMappableExprComponentListsForDecl(
4058               VD, /*CurrentRegionOnly=*/true,
4059               [](OMPClauseMappableExprCommon::MappableExprComponentListRef,
4060                  OpenMPClauseKind) { return true; }))
4061         continue;
4062       DeclRefExpr *DRE = buildDeclRefExpr(
4063           SemaRef, VD, VD->getType().getNonLValueExprType(SemaRef.Context),
4064           Cap.getLocation(), /*RefersToCapture=*/true);
4065       Visit(DRE);
4066     }
4067   }
4068   bool isErrorFound() const { return ErrorFound; }
4069   ArrayRef<Expr *> getImplicitFirstprivate() const {
4070     return ImplicitFirstprivate;
4071   }
4072   ArrayRef<Expr *> getImplicitPrivate() const { return ImplicitPrivate; }
4073   ArrayRef<Expr *> getImplicitMap(OpenMPDefaultmapClauseKind DK,
4074                                   OpenMPMapClauseKind MK) const {
4075     return ImplicitMap[DK][MK];
4076   }
4077   ArrayRef<OpenMPMapModifierKind>
4078   getImplicitMapModifier(OpenMPDefaultmapClauseKind Kind) const {
4079     return ImplicitMapModifier[Kind];
4080   }
4081   const Sema::VarsWithInheritedDSAType &getVarsWithInheritedDSA() const {
4082     return VarsWithInheritedDSA;
4083   }
4084 
4085   DSAAttrChecker(DSAStackTy *S, Sema &SemaRef, CapturedStmt *CS)
4086       : Stack(S), SemaRef(SemaRef), ErrorFound(false), CS(CS) {
4087     // Process declare target link variables for the target directives.
4088     if (isOpenMPTargetExecutionDirective(S->getCurrentDirective())) {
4089       for (DeclRefExpr *E : Stack->getLinkGlobals())
4090         Visit(E);
4091     }
4092   }
4093 };
4094 } // namespace
4095 
4096 static void handleDeclareVariantConstructTrait(DSAStackTy *Stack,
4097                                                OpenMPDirectiveKind DKind,
4098                                                bool ScopeEntry) {
4099   SmallVector<llvm::omp::TraitProperty, 8> Traits;
4100   if (isOpenMPTargetExecutionDirective(DKind))
4101     Traits.emplace_back(llvm::omp::TraitProperty::construct_target_target);
4102   if (isOpenMPTeamsDirective(DKind))
4103     Traits.emplace_back(llvm::omp::TraitProperty::construct_teams_teams);
4104   if (isOpenMPParallelDirective(DKind))
4105     Traits.emplace_back(llvm::omp::TraitProperty::construct_parallel_parallel);
4106   if (isOpenMPWorksharingDirective(DKind))
4107     Traits.emplace_back(llvm::omp::TraitProperty::construct_for_for);
4108   if (isOpenMPSimdDirective(DKind))
4109     Traits.emplace_back(llvm::omp::TraitProperty::construct_simd_simd);
4110   Stack->handleConstructTrait(Traits, ScopeEntry);
4111 }
4112 
4113 void Sema::ActOnOpenMPRegionStart(OpenMPDirectiveKind DKind, Scope *CurScope) {
4114   switch (DKind) {
4115   case OMPD_parallel:
4116   case OMPD_parallel_for:
4117   case OMPD_parallel_for_simd:
4118   case OMPD_parallel_sections:
4119   case OMPD_parallel_master:
4120   case OMPD_parallel_masked:
4121   case OMPD_parallel_loop:
4122   case OMPD_teams:
4123   case OMPD_teams_distribute:
4124   case OMPD_teams_distribute_simd: {
4125     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4126     QualType KmpInt32PtrTy =
4127         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4128     Sema::CapturedParamNameType Params[] = {
4129         std::make_pair(".global_tid.", KmpInt32PtrTy),
4130         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4131         std::make_pair(StringRef(), QualType()) // __context with shared vars
4132     };
4133     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4134                              Params);
4135     break;
4136   }
4137   case OMPD_target_teams:
4138   case OMPD_target_parallel:
4139   case OMPD_target_parallel_for:
4140   case OMPD_target_parallel_for_simd:
4141   case OMPD_target_teams_loop:
4142   case OMPD_target_parallel_loop:
4143   case OMPD_target_teams_distribute:
4144   case OMPD_target_teams_distribute_simd: {
4145     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4146     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4147     QualType KmpInt32PtrTy =
4148         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4149     QualType Args[] = {VoidPtrTy};
4150     FunctionProtoType::ExtProtoInfo EPI;
4151     EPI.Variadic = true;
4152     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4153     Sema::CapturedParamNameType Params[] = {
4154         std::make_pair(".global_tid.", KmpInt32Ty),
4155         std::make_pair(".part_id.", KmpInt32PtrTy),
4156         std::make_pair(".privates.", VoidPtrTy),
4157         std::make_pair(
4158             ".copy_fn.",
4159             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4160         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4161         std::make_pair(StringRef(), QualType()) // __context with shared vars
4162     };
4163     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4164                              Params, /*OpenMPCaptureLevel=*/0);
4165     // Mark this captured region as inlined, because we don't use outlined
4166     // function directly.
4167     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4168         AlwaysInlineAttr::CreateImplicit(
4169             Context, {}, AttributeCommonInfo::AS_Keyword,
4170             AlwaysInlineAttr::Keyword_forceinline));
4171     Sema::CapturedParamNameType ParamsTarget[] = {
4172         std::make_pair(StringRef(), QualType()) // __context with shared vars
4173     };
4174     // Start a captured region for 'target' with no implicit parameters.
4175     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4176                              ParamsTarget, /*OpenMPCaptureLevel=*/1);
4177     Sema::CapturedParamNameType ParamsTeamsOrParallel[] = {
4178         std::make_pair(".global_tid.", KmpInt32PtrTy),
4179         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4180         std::make_pair(StringRef(), QualType()) // __context with shared vars
4181     };
4182     // Start a captured region for 'teams' or 'parallel'.  Both regions have
4183     // the same implicit parameters.
4184     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4185                              ParamsTeamsOrParallel, /*OpenMPCaptureLevel=*/2);
4186     break;
4187   }
4188   case OMPD_target:
4189   case OMPD_target_simd: {
4190     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4191     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4192     QualType KmpInt32PtrTy =
4193         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4194     QualType Args[] = {VoidPtrTy};
4195     FunctionProtoType::ExtProtoInfo EPI;
4196     EPI.Variadic = true;
4197     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4198     Sema::CapturedParamNameType Params[] = {
4199         std::make_pair(".global_tid.", KmpInt32Ty),
4200         std::make_pair(".part_id.", KmpInt32PtrTy),
4201         std::make_pair(".privates.", VoidPtrTy),
4202         std::make_pair(
4203             ".copy_fn.",
4204             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4205         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4206         std::make_pair(StringRef(), QualType()) // __context with shared vars
4207     };
4208     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4209                              Params, /*OpenMPCaptureLevel=*/0);
4210     // Mark this captured region as inlined, because we don't use outlined
4211     // function directly.
4212     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4213         AlwaysInlineAttr::CreateImplicit(
4214             Context, {}, AttributeCommonInfo::AS_Keyword,
4215             AlwaysInlineAttr::Keyword_forceinline));
4216     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4217                              std::make_pair(StringRef(), QualType()),
4218                              /*OpenMPCaptureLevel=*/1);
4219     break;
4220   }
4221   case OMPD_atomic:
4222   case OMPD_critical:
4223   case OMPD_section:
4224   case OMPD_master:
4225   case OMPD_masked:
4226   case OMPD_tile:
4227   case OMPD_unroll:
4228     break;
4229   case OMPD_loop:
4230     // TODO: 'loop' may require additional parameters depending on the binding.
4231     // Treat similar to OMPD_simd/OMPD_for for now.
4232   case OMPD_simd:
4233   case OMPD_for:
4234   case OMPD_for_simd:
4235   case OMPD_sections:
4236   case OMPD_single:
4237   case OMPD_taskgroup:
4238   case OMPD_distribute:
4239   case OMPD_distribute_simd:
4240   case OMPD_ordered:
4241   case OMPD_target_data:
4242   case OMPD_dispatch: {
4243     Sema::CapturedParamNameType Params[] = {
4244         std::make_pair(StringRef(), QualType()) // __context with shared vars
4245     };
4246     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4247                              Params);
4248     break;
4249   }
4250   case OMPD_task: {
4251     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4252     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4253     QualType KmpInt32PtrTy =
4254         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4255     QualType Args[] = {VoidPtrTy};
4256     FunctionProtoType::ExtProtoInfo EPI;
4257     EPI.Variadic = true;
4258     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4259     Sema::CapturedParamNameType Params[] = {
4260         std::make_pair(".global_tid.", KmpInt32Ty),
4261         std::make_pair(".part_id.", KmpInt32PtrTy),
4262         std::make_pair(".privates.", VoidPtrTy),
4263         std::make_pair(
4264             ".copy_fn.",
4265             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4266         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4267         std::make_pair(StringRef(), QualType()) // __context with shared vars
4268     };
4269     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4270                              Params);
4271     // Mark this captured region as inlined, because we don't use outlined
4272     // function directly.
4273     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4274         AlwaysInlineAttr::CreateImplicit(
4275             Context, {}, AttributeCommonInfo::AS_Keyword,
4276             AlwaysInlineAttr::Keyword_forceinline));
4277     break;
4278   }
4279   case OMPD_taskloop:
4280   case OMPD_taskloop_simd:
4281   case OMPD_master_taskloop:
4282   case OMPD_masked_taskloop:
4283   case OMPD_masked_taskloop_simd:
4284   case OMPD_master_taskloop_simd: {
4285     QualType KmpInt32Ty =
4286         Context.getIntTypeForBitwidth(/*DestWidth=*/32, /*Signed=*/1)
4287             .withConst();
4288     QualType KmpUInt64Ty =
4289         Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/0)
4290             .withConst();
4291     QualType KmpInt64Ty =
4292         Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/1)
4293             .withConst();
4294     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4295     QualType KmpInt32PtrTy =
4296         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4297     QualType Args[] = {VoidPtrTy};
4298     FunctionProtoType::ExtProtoInfo EPI;
4299     EPI.Variadic = true;
4300     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4301     Sema::CapturedParamNameType Params[] = {
4302         std::make_pair(".global_tid.", KmpInt32Ty),
4303         std::make_pair(".part_id.", KmpInt32PtrTy),
4304         std::make_pair(".privates.", VoidPtrTy),
4305         std::make_pair(
4306             ".copy_fn.",
4307             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4308         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4309         std::make_pair(".lb.", KmpUInt64Ty),
4310         std::make_pair(".ub.", KmpUInt64Ty),
4311         std::make_pair(".st.", KmpInt64Ty),
4312         std::make_pair(".liter.", KmpInt32Ty),
4313         std::make_pair(".reductions.", VoidPtrTy),
4314         std::make_pair(StringRef(), QualType()) // __context with shared vars
4315     };
4316     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4317                              Params);
4318     // Mark this captured region as inlined, because we don't use outlined
4319     // function directly.
4320     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4321         AlwaysInlineAttr::CreateImplicit(
4322             Context, {}, AttributeCommonInfo::AS_Keyword,
4323             AlwaysInlineAttr::Keyword_forceinline));
4324     break;
4325   }
4326   case OMPD_parallel_masked_taskloop:
4327   case OMPD_parallel_masked_taskloop_simd:
4328   case OMPD_parallel_master_taskloop:
4329   case OMPD_parallel_master_taskloop_simd: {
4330     QualType KmpInt32Ty =
4331         Context.getIntTypeForBitwidth(/*DestWidth=*/32, /*Signed=*/1)
4332             .withConst();
4333     QualType KmpUInt64Ty =
4334         Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/0)
4335             .withConst();
4336     QualType KmpInt64Ty =
4337         Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/1)
4338             .withConst();
4339     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4340     QualType KmpInt32PtrTy =
4341         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4342     Sema::CapturedParamNameType ParamsParallel[] = {
4343         std::make_pair(".global_tid.", KmpInt32PtrTy),
4344         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4345         std::make_pair(StringRef(), QualType()) // __context with shared vars
4346     };
4347     // Start a captured region for 'parallel'.
4348     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4349                              ParamsParallel, /*OpenMPCaptureLevel=*/0);
4350     QualType Args[] = {VoidPtrTy};
4351     FunctionProtoType::ExtProtoInfo EPI;
4352     EPI.Variadic = true;
4353     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4354     Sema::CapturedParamNameType Params[] = {
4355         std::make_pair(".global_tid.", KmpInt32Ty),
4356         std::make_pair(".part_id.", KmpInt32PtrTy),
4357         std::make_pair(".privates.", VoidPtrTy),
4358         std::make_pair(
4359             ".copy_fn.",
4360             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4361         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4362         std::make_pair(".lb.", KmpUInt64Ty),
4363         std::make_pair(".ub.", KmpUInt64Ty),
4364         std::make_pair(".st.", KmpInt64Ty),
4365         std::make_pair(".liter.", KmpInt32Ty),
4366         std::make_pair(".reductions.", VoidPtrTy),
4367         std::make_pair(StringRef(), QualType()) // __context with shared vars
4368     };
4369     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4370                              Params, /*OpenMPCaptureLevel=*/1);
4371     // Mark this captured region as inlined, because we don't use outlined
4372     // function directly.
4373     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4374         AlwaysInlineAttr::CreateImplicit(
4375             Context, {}, AttributeCommonInfo::AS_Keyword,
4376             AlwaysInlineAttr::Keyword_forceinline));
4377     break;
4378   }
4379   case OMPD_distribute_parallel_for_simd:
4380   case OMPD_distribute_parallel_for: {
4381     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4382     QualType KmpInt32PtrTy =
4383         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4384     Sema::CapturedParamNameType Params[] = {
4385         std::make_pair(".global_tid.", KmpInt32PtrTy),
4386         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4387         std::make_pair(".previous.lb.", Context.getSizeType().withConst()),
4388         std::make_pair(".previous.ub.", Context.getSizeType().withConst()),
4389         std::make_pair(StringRef(), QualType()) // __context with shared vars
4390     };
4391     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4392                              Params);
4393     break;
4394   }
4395   case OMPD_target_teams_distribute_parallel_for:
4396   case OMPD_target_teams_distribute_parallel_for_simd: {
4397     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4398     QualType KmpInt32PtrTy =
4399         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4400     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4401 
4402     QualType Args[] = {VoidPtrTy};
4403     FunctionProtoType::ExtProtoInfo EPI;
4404     EPI.Variadic = true;
4405     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4406     Sema::CapturedParamNameType Params[] = {
4407         std::make_pair(".global_tid.", KmpInt32Ty),
4408         std::make_pair(".part_id.", KmpInt32PtrTy),
4409         std::make_pair(".privates.", VoidPtrTy),
4410         std::make_pair(
4411             ".copy_fn.",
4412             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4413         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4414         std::make_pair(StringRef(), QualType()) // __context with shared vars
4415     };
4416     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4417                              Params, /*OpenMPCaptureLevel=*/0);
4418     // Mark this captured region as inlined, because we don't use outlined
4419     // function directly.
4420     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4421         AlwaysInlineAttr::CreateImplicit(
4422             Context, {}, AttributeCommonInfo::AS_Keyword,
4423             AlwaysInlineAttr::Keyword_forceinline));
4424     Sema::CapturedParamNameType ParamsTarget[] = {
4425         std::make_pair(StringRef(), QualType()) // __context with shared vars
4426     };
4427     // Start a captured region for 'target' with no implicit parameters.
4428     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4429                              ParamsTarget, /*OpenMPCaptureLevel=*/1);
4430 
4431     Sema::CapturedParamNameType ParamsTeams[] = {
4432         std::make_pair(".global_tid.", KmpInt32PtrTy),
4433         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4434         std::make_pair(StringRef(), QualType()) // __context with shared vars
4435     };
4436     // Start a captured region for 'target' with no implicit parameters.
4437     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4438                              ParamsTeams, /*OpenMPCaptureLevel=*/2);
4439 
4440     Sema::CapturedParamNameType ParamsParallel[] = {
4441         std::make_pair(".global_tid.", KmpInt32PtrTy),
4442         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4443         std::make_pair(".previous.lb.", Context.getSizeType().withConst()),
4444         std::make_pair(".previous.ub.", Context.getSizeType().withConst()),
4445         std::make_pair(StringRef(), QualType()) // __context with shared vars
4446     };
4447     // Start a captured region for 'teams' or 'parallel'.  Both regions have
4448     // the same implicit parameters.
4449     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4450                              ParamsParallel, /*OpenMPCaptureLevel=*/3);
4451     break;
4452   }
4453 
4454   case OMPD_teams_loop: {
4455     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4456     QualType KmpInt32PtrTy =
4457         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4458 
4459     Sema::CapturedParamNameType ParamsTeams[] = {
4460         std::make_pair(".global_tid.", KmpInt32PtrTy),
4461         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4462         std::make_pair(StringRef(), QualType()) // __context with shared vars
4463     };
4464     // Start a captured region for 'teams'.
4465     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4466                              ParamsTeams, /*OpenMPCaptureLevel=*/0);
4467     break;
4468   }
4469 
4470   case OMPD_teams_distribute_parallel_for:
4471   case OMPD_teams_distribute_parallel_for_simd: {
4472     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4473     QualType KmpInt32PtrTy =
4474         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4475 
4476     Sema::CapturedParamNameType ParamsTeams[] = {
4477         std::make_pair(".global_tid.", KmpInt32PtrTy),
4478         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4479         std::make_pair(StringRef(), QualType()) // __context with shared vars
4480     };
4481     // Start a captured region for 'target' with no implicit parameters.
4482     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4483                              ParamsTeams, /*OpenMPCaptureLevel=*/0);
4484 
4485     Sema::CapturedParamNameType ParamsParallel[] = {
4486         std::make_pair(".global_tid.", KmpInt32PtrTy),
4487         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4488         std::make_pair(".previous.lb.", Context.getSizeType().withConst()),
4489         std::make_pair(".previous.ub.", Context.getSizeType().withConst()),
4490         std::make_pair(StringRef(), QualType()) // __context with shared vars
4491     };
4492     // Start a captured region for 'teams' or 'parallel'.  Both regions have
4493     // the same implicit parameters.
4494     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4495                              ParamsParallel, /*OpenMPCaptureLevel=*/1);
4496     break;
4497   }
4498   case OMPD_target_update:
4499   case OMPD_target_enter_data:
4500   case OMPD_target_exit_data: {
4501     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4502     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4503     QualType KmpInt32PtrTy =
4504         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4505     QualType Args[] = {VoidPtrTy};
4506     FunctionProtoType::ExtProtoInfo EPI;
4507     EPI.Variadic = true;
4508     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4509     Sema::CapturedParamNameType Params[] = {
4510         std::make_pair(".global_tid.", KmpInt32Ty),
4511         std::make_pair(".part_id.", KmpInt32PtrTy),
4512         std::make_pair(".privates.", VoidPtrTy),
4513         std::make_pair(
4514             ".copy_fn.",
4515             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4516         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4517         std::make_pair(StringRef(), QualType()) // __context with shared vars
4518     };
4519     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4520                              Params);
4521     // Mark this captured region as inlined, because we don't use outlined
4522     // function directly.
4523     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4524         AlwaysInlineAttr::CreateImplicit(
4525             Context, {}, AttributeCommonInfo::AS_Keyword,
4526             AlwaysInlineAttr::Keyword_forceinline));
4527     break;
4528   }
4529   case OMPD_threadprivate:
4530   case OMPD_allocate:
4531   case OMPD_taskyield:
4532   case OMPD_barrier:
4533   case OMPD_taskwait:
4534   case OMPD_cancellation_point:
4535   case OMPD_cancel:
4536   case OMPD_flush:
4537   case OMPD_depobj:
4538   case OMPD_scan:
4539   case OMPD_declare_reduction:
4540   case OMPD_declare_mapper:
4541   case OMPD_declare_simd:
4542   case OMPD_declare_target:
4543   case OMPD_end_declare_target:
4544   case OMPD_requires:
4545   case OMPD_declare_variant:
4546   case OMPD_begin_declare_variant:
4547   case OMPD_end_declare_variant:
4548   case OMPD_metadirective:
4549     llvm_unreachable("OpenMP Directive is not allowed");
4550   case OMPD_unknown:
4551   default:
4552     llvm_unreachable("Unknown OpenMP directive");
4553   }
4554   DSAStack->setContext(CurContext);
4555   handleDeclareVariantConstructTrait(DSAStack, DKind, /* ScopeEntry */ true);
4556 }
4557 
4558 int Sema::getNumberOfConstructScopes(unsigned Level) const {
4559   return getOpenMPCaptureLevels(DSAStack->getDirective(Level));
4560 }
4561 
4562 int Sema::getOpenMPCaptureLevels(OpenMPDirectiveKind DKind) {
4563   SmallVector<OpenMPDirectiveKind, 4> CaptureRegions;
4564   getOpenMPCaptureRegions(CaptureRegions, DKind);
4565   return CaptureRegions.size();
4566 }
4567 
4568 static OMPCapturedExprDecl *buildCaptureDecl(Sema &S, IdentifierInfo *Id,
4569                                              Expr *CaptureExpr, bool WithInit,
4570                                              DeclContext *CurContext,
4571                                              bool AsExpression) {
4572   assert(CaptureExpr);
4573   ASTContext &C = S.getASTContext();
4574   Expr *Init = AsExpression ? CaptureExpr : CaptureExpr->IgnoreImpCasts();
4575   QualType Ty = Init->getType();
4576   if (CaptureExpr->getObjectKind() == OK_Ordinary && CaptureExpr->isGLValue()) {
4577     if (S.getLangOpts().CPlusPlus) {
4578       Ty = C.getLValueReferenceType(Ty);
4579     } else {
4580       Ty = C.getPointerType(Ty);
4581       ExprResult Res =
4582           S.CreateBuiltinUnaryOp(CaptureExpr->getExprLoc(), UO_AddrOf, Init);
4583       if (!Res.isUsable())
4584         return nullptr;
4585       Init = Res.get();
4586     }
4587     WithInit = true;
4588   }
4589   auto *CED = OMPCapturedExprDecl::Create(C, CurContext, Id, Ty,
4590                                           CaptureExpr->getBeginLoc());
4591   if (!WithInit)
4592     CED->addAttr(OMPCaptureNoInitAttr::CreateImplicit(C));
4593   CurContext->addHiddenDecl(CED);
4594   Sema::TentativeAnalysisScope Trap(S);
4595   S.AddInitializerToDecl(CED, Init, /*DirectInit=*/false);
4596   return CED;
4597 }
4598 
4599 static DeclRefExpr *buildCapture(Sema &S, ValueDecl *D, Expr *CaptureExpr,
4600                                  bool WithInit) {
4601   OMPCapturedExprDecl *CD;
4602   if (VarDecl *VD = S.isOpenMPCapturedDecl(D))
4603     CD = cast<OMPCapturedExprDecl>(VD);
4604   else
4605     CD = buildCaptureDecl(S, D->getIdentifier(), CaptureExpr, WithInit,
4606                           S.CurContext,
4607                           /*AsExpression=*/false);
4608   return buildDeclRefExpr(S, CD, CD->getType().getNonReferenceType(),
4609                           CaptureExpr->getExprLoc());
4610 }
4611 
4612 static ExprResult buildCapture(Sema &S, Expr *CaptureExpr, DeclRefExpr *&Ref) {
4613   CaptureExpr = S.DefaultLvalueConversion(CaptureExpr).get();
4614   if (!Ref) {
4615     OMPCapturedExprDecl *CD = buildCaptureDecl(
4616         S, &S.getASTContext().Idents.get(".capture_expr."), CaptureExpr,
4617         /*WithInit=*/true, S.CurContext, /*AsExpression=*/true);
4618     Ref = buildDeclRefExpr(S, CD, CD->getType().getNonReferenceType(),
4619                            CaptureExpr->getExprLoc());
4620   }
4621   ExprResult Res = Ref;
4622   if (!S.getLangOpts().CPlusPlus &&
4623       CaptureExpr->getObjectKind() == OK_Ordinary && CaptureExpr->isGLValue() &&
4624       Ref->getType()->isPointerType()) {
4625     Res = S.CreateBuiltinUnaryOp(CaptureExpr->getExprLoc(), UO_Deref, Ref);
4626     if (!Res.isUsable())
4627       return ExprError();
4628   }
4629   return S.DefaultLvalueConversion(Res.get());
4630 }
4631 
4632 namespace {
4633 // OpenMP directives parsed in this section are represented as a
4634 // CapturedStatement with an associated statement.  If a syntax error
4635 // is detected during the parsing of the associated statement, the
4636 // compiler must abort processing and close the CapturedStatement.
4637 //
4638 // Combined directives such as 'target parallel' have more than one
4639 // nested CapturedStatements.  This RAII ensures that we unwind out
4640 // of all the nested CapturedStatements when an error is found.
4641 class CaptureRegionUnwinderRAII {
4642 private:
4643   Sema &S;
4644   bool &ErrorFound;
4645   OpenMPDirectiveKind DKind = OMPD_unknown;
4646 
4647 public:
4648   CaptureRegionUnwinderRAII(Sema &S, bool &ErrorFound,
4649                             OpenMPDirectiveKind DKind)
4650       : S(S), ErrorFound(ErrorFound), DKind(DKind) {}
4651   ~CaptureRegionUnwinderRAII() {
4652     if (ErrorFound) {
4653       int ThisCaptureLevel = S.getOpenMPCaptureLevels(DKind);
4654       while (--ThisCaptureLevel >= 0)
4655         S.ActOnCapturedRegionError();
4656     }
4657   }
4658 };
4659 } // namespace
4660 
4661 void Sema::tryCaptureOpenMPLambdas(ValueDecl *V) {
4662   // Capture variables captured by reference in lambdas for target-based
4663   // directives.
4664   if (!CurContext->isDependentContext() &&
4665       (isOpenMPTargetExecutionDirective(DSAStack->getCurrentDirective()) ||
4666        isOpenMPTargetDataManagementDirective(
4667            DSAStack->getCurrentDirective()))) {
4668     QualType Type = V->getType();
4669     if (const auto *RD = Type.getCanonicalType()
4670                              .getNonReferenceType()
4671                              ->getAsCXXRecordDecl()) {
4672       bool SavedForceCaptureByReferenceInTargetExecutable =
4673           DSAStack->isForceCaptureByReferenceInTargetExecutable();
4674       DSAStack->setForceCaptureByReferenceInTargetExecutable(
4675           /*V=*/true);
4676       if (RD->isLambda()) {
4677         llvm::DenseMap<const VarDecl *, FieldDecl *> Captures;
4678         FieldDecl *ThisCapture;
4679         RD->getCaptureFields(Captures, ThisCapture);
4680         for (const LambdaCapture &LC : RD->captures()) {
4681           if (LC.getCaptureKind() == LCK_ByRef) {
4682             VarDecl *VD = LC.getCapturedVar();
4683             DeclContext *VDC = VD->getDeclContext();
4684             if (!VDC->Encloses(CurContext))
4685               continue;
4686             MarkVariableReferenced(LC.getLocation(), VD);
4687           } else if (LC.getCaptureKind() == LCK_This) {
4688             QualType ThisTy = getCurrentThisType();
4689             if (!ThisTy.isNull() &&
4690                 Context.typesAreCompatible(ThisTy, ThisCapture->getType()))
4691               CheckCXXThisCapture(LC.getLocation());
4692           }
4693         }
4694       }
4695       DSAStack->setForceCaptureByReferenceInTargetExecutable(
4696           SavedForceCaptureByReferenceInTargetExecutable);
4697     }
4698   }
4699 }
4700 
4701 static bool checkOrderedOrderSpecified(Sema &S,
4702                                        const ArrayRef<OMPClause *> Clauses) {
4703   const OMPOrderedClause *Ordered = nullptr;
4704   const OMPOrderClause *Order = nullptr;
4705 
4706   for (const OMPClause *Clause : Clauses) {
4707     if (Clause->getClauseKind() == OMPC_ordered)
4708       Ordered = cast<OMPOrderedClause>(Clause);
4709     else if (Clause->getClauseKind() == OMPC_order) {
4710       Order = cast<OMPOrderClause>(Clause);
4711       if (Order->getKind() != OMPC_ORDER_concurrent)
4712         Order = nullptr;
4713     }
4714     if (Ordered && Order)
4715       break;
4716   }
4717 
4718   if (Ordered && Order) {
4719     S.Diag(Order->getKindKwLoc(),
4720            diag::err_omp_simple_clause_incompatible_with_ordered)
4721         << getOpenMPClauseName(OMPC_order)
4722         << getOpenMPSimpleClauseTypeName(OMPC_order, OMPC_ORDER_concurrent)
4723         << SourceRange(Order->getBeginLoc(), Order->getEndLoc());
4724     S.Diag(Ordered->getBeginLoc(), diag::note_omp_ordered_param)
4725         << 0 << SourceRange(Ordered->getBeginLoc(), Ordered->getEndLoc());
4726     return true;
4727   }
4728   return false;
4729 }
4730 
4731 StmtResult Sema::ActOnOpenMPRegionEnd(StmtResult S,
4732                                       ArrayRef<OMPClause *> Clauses) {
4733   handleDeclareVariantConstructTrait(DSAStack, DSAStack->getCurrentDirective(),
4734                                      /* ScopeEntry */ false);
4735   if (DSAStack->getCurrentDirective() == OMPD_atomic ||
4736       DSAStack->getCurrentDirective() == OMPD_critical ||
4737       DSAStack->getCurrentDirective() == OMPD_section ||
4738       DSAStack->getCurrentDirective() == OMPD_master ||
4739       DSAStack->getCurrentDirective() == OMPD_masked)
4740     return S;
4741 
4742   bool ErrorFound = false;
4743   CaptureRegionUnwinderRAII CaptureRegionUnwinder(
4744       *this, ErrorFound, DSAStack->getCurrentDirective());
4745   if (!S.isUsable()) {
4746     ErrorFound = true;
4747     return StmtError();
4748   }
4749 
4750   SmallVector<OpenMPDirectiveKind, 4> CaptureRegions;
4751   getOpenMPCaptureRegions(CaptureRegions, DSAStack->getCurrentDirective());
4752   OMPOrderedClause *OC = nullptr;
4753   OMPScheduleClause *SC = nullptr;
4754   SmallVector<const OMPLinearClause *, 4> LCs;
4755   SmallVector<const OMPClauseWithPreInit *, 4> PICs;
4756   // This is required for proper codegen.
4757   for (OMPClause *Clause : Clauses) {
4758     if (!LangOpts.OpenMPSimd &&
4759         (isOpenMPTaskingDirective(DSAStack->getCurrentDirective()) ||
4760          DSAStack->getCurrentDirective() == OMPD_target) &&
4761         Clause->getClauseKind() == OMPC_in_reduction) {
4762       // Capture taskgroup task_reduction descriptors inside the tasking regions
4763       // with the corresponding in_reduction items.
4764       auto *IRC = cast<OMPInReductionClause>(Clause);
4765       for (Expr *E : IRC->taskgroup_descriptors())
4766         if (E)
4767           MarkDeclarationsReferencedInExpr(E);
4768     }
4769     if (isOpenMPPrivate(Clause->getClauseKind()) ||
4770         Clause->getClauseKind() == OMPC_copyprivate ||
4771         (getLangOpts().OpenMPUseTLS &&
4772          getASTContext().getTargetInfo().isTLSSupported() &&
4773          Clause->getClauseKind() == OMPC_copyin)) {
4774       DSAStack->setForceVarCapturing(Clause->getClauseKind() == OMPC_copyin);
4775       // Mark all variables in private list clauses as used in inner region.
4776       for (Stmt *VarRef : Clause->children()) {
4777         if (auto *E = cast_or_null<Expr>(VarRef)) {
4778           MarkDeclarationsReferencedInExpr(E);
4779         }
4780       }
4781       DSAStack->setForceVarCapturing(/*V=*/false);
4782     } else if (isOpenMPLoopTransformationDirective(
4783                    DSAStack->getCurrentDirective())) {
4784       assert(CaptureRegions.empty() &&
4785              "No captured regions in loop transformation directives.");
4786     } else if (CaptureRegions.size() > 1 ||
4787                CaptureRegions.back() != OMPD_unknown) {
4788       if (auto *C = OMPClauseWithPreInit::get(Clause))
4789         PICs.push_back(C);
4790       if (auto *C = OMPClauseWithPostUpdate::get(Clause)) {
4791         if (Expr *E = C->getPostUpdateExpr())
4792           MarkDeclarationsReferencedInExpr(E);
4793       }
4794     }
4795     if (Clause->getClauseKind() == OMPC_schedule)
4796       SC = cast<OMPScheduleClause>(Clause);
4797     else if (Clause->getClauseKind() == OMPC_ordered)
4798       OC = cast<OMPOrderedClause>(Clause);
4799     else if (Clause->getClauseKind() == OMPC_linear)
4800       LCs.push_back(cast<OMPLinearClause>(Clause));
4801   }
4802   // Capture allocator expressions if used.
4803   for (Expr *E : DSAStack->getInnerAllocators())
4804     MarkDeclarationsReferencedInExpr(E);
4805   // OpenMP, 2.7.1 Loop Construct, Restrictions
4806   // The nonmonotonic modifier cannot be specified if an ordered clause is
4807   // specified.
4808   if (SC &&
4809       (SC->getFirstScheduleModifier() == OMPC_SCHEDULE_MODIFIER_nonmonotonic ||
4810        SC->getSecondScheduleModifier() ==
4811            OMPC_SCHEDULE_MODIFIER_nonmonotonic) &&
4812       OC) {
4813     Diag(SC->getFirstScheduleModifier() == OMPC_SCHEDULE_MODIFIER_nonmonotonic
4814              ? SC->getFirstScheduleModifierLoc()
4815              : SC->getSecondScheduleModifierLoc(),
4816          diag::err_omp_simple_clause_incompatible_with_ordered)
4817         << getOpenMPClauseName(OMPC_schedule)
4818         << getOpenMPSimpleClauseTypeName(OMPC_schedule,
4819                                          OMPC_SCHEDULE_MODIFIER_nonmonotonic)
4820         << SourceRange(OC->getBeginLoc(), OC->getEndLoc());
4821     ErrorFound = true;
4822   }
4823   // OpenMP 5.0, 2.9.2 Worksharing-Loop Construct, Restrictions.
4824   // If an order(concurrent) clause is present, an ordered clause may not appear
4825   // on the same directive.
4826   if (checkOrderedOrderSpecified(*this, Clauses))
4827     ErrorFound = true;
4828   if (!LCs.empty() && OC && OC->getNumForLoops()) {
4829     for (const OMPLinearClause *C : LCs) {
4830       Diag(C->getBeginLoc(), diag::err_omp_linear_ordered)
4831           << SourceRange(OC->getBeginLoc(), OC->getEndLoc());
4832     }
4833     ErrorFound = true;
4834   }
4835   if (isOpenMPWorksharingDirective(DSAStack->getCurrentDirective()) &&
4836       isOpenMPSimdDirective(DSAStack->getCurrentDirective()) && OC &&
4837       OC->getNumForLoops()) {
4838     Diag(OC->getBeginLoc(), diag::err_omp_ordered_simd)
4839         << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
4840     ErrorFound = true;
4841   }
4842   if (ErrorFound) {
4843     return StmtError();
4844   }
4845   StmtResult SR = S;
4846   unsigned CompletedRegions = 0;
4847   for (OpenMPDirectiveKind ThisCaptureRegion : llvm::reverse(CaptureRegions)) {
4848     // Mark all variables in private list clauses as used in inner region.
4849     // Required for proper codegen of combined directives.
4850     // TODO: add processing for other clauses.
4851     if (ThisCaptureRegion != OMPD_unknown) {
4852       for (const clang::OMPClauseWithPreInit *C : PICs) {
4853         OpenMPDirectiveKind CaptureRegion = C->getCaptureRegion();
4854         // Find the particular capture region for the clause if the
4855         // directive is a combined one with multiple capture regions.
4856         // If the directive is not a combined one, the capture region
4857         // associated with the clause is OMPD_unknown and is generated
4858         // only once.
4859         if (CaptureRegion == ThisCaptureRegion ||
4860             CaptureRegion == OMPD_unknown) {
4861           if (auto *DS = cast_or_null<DeclStmt>(C->getPreInitStmt())) {
4862             for (Decl *D : DS->decls())
4863               MarkVariableReferenced(D->getLocation(), cast<VarDecl>(D));
4864           }
4865         }
4866       }
4867     }
4868     if (ThisCaptureRegion == OMPD_target) {
4869       // Capture allocator traits in the target region. They are used implicitly
4870       // and, thus, are not captured by default.
4871       for (OMPClause *C : Clauses) {
4872         if (const auto *UAC = dyn_cast<OMPUsesAllocatorsClause>(C)) {
4873           for (unsigned I = 0, End = UAC->getNumberOfAllocators(); I < End;
4874                ++I) {
4875             OMPUsesAllocatorsClause::Data D = UAC->getAllocatorData(I);
4876             if (Expr *E = D.AllocatorTraits)
4877               MarkDeclarationsReferencedInExpr(E);
4878           }
4879           continue;
4880         }
4881       }
4882     }
4883     if (ThisCaptureRegion == OMPD_parallel) {
4884       // Capture temp arrays for inscan reductions and locals in aligned
4885       // clauses.
4886       for (OMPClause *C : Clauses) {
4887         if (auto *RC = dyn_cast<OMPReductionClause>(C)) {
4888           if (RC->getModifier() != OMPC_REDUCTION_inscan)
4889             continue;
4890           for (Expr *E : RC->copy_array_temps())
4891             MarkDeclarationsReferencedInExpr(E);
4892         }
4893         if (auto *AC = dyn_cast<OMPAlignedClause>(C)) {
4894           for (Expr *E : AC->varlists())
4895             MarkDeclarationsReferencedInExpr(E);
4896         }
4897       }
4898     }
4899     if (++CompletedRegions == CaptureRegions.size())
4900       DSAStack->setBodyComplete();
4901     SR = ActOnCapturedRegionEnd(SR.get());
4902   }
4903   return SR;
4904 }
4905 
4906 static bool checkCancelRegion(Sema &SemaRef, OpenMPDirectiveKind CurrentRegion,
4907                               OpenMPDirectiveKind CancelRegion,
4908                               SourceLocation StartLoc) {
4909   // CancelRegion is only needed for cancel and cancellation_point.
4910   if (CurrentRegion != OMPD_cancel && CurrentRegion != OMPD_cancellation_point)
4911     return false;
4912 
4913   if (CancelRegion == OMPD_parallel || CancelRegion == OMPD_for ||
4914       CancelRegion == OMPD_sections || CancelRegion == OMPD_taskgroup)
4915     return false;
4916 
4917   SemaRef.Diag(StartLoc, diag::err_omp_wrong_cancel_region)
4918       << getOpenMPDirectiveName(CancelRegion);
4919   return true;
4920 }
4921 
4922 static bool checkNestingOfRegions(Sema &SemaRef, const DSAStackTy *Stack,
4923                                   OpenMPDirectiveKind CurrentRegion,
4924                                   const DeclarationNameInfo &CurrentName,
4925                                   OpenMPDirectiveKind CancelRegion,
4926                                   OpenMPBindClauseKind BindKind,
4927                                   SourceLocation StartLoc) {
4928   if (Stack->getCurScope()) {
4929     OpenMPDirectiveKind ParentRegion = Stack->getParentDirective();
4930     OpenMPDirectiveKind OffendingRegion = ParentRegion;
4931     bool NestingProhibited = false;
4932     bool CloseNesting = true;
4933     bool OrphanSeen = false;
4934     enum {
4935       NoRecommend,
4936       ShouldBeInParallelRegion,
4937       ShouldBeInOrderedRegion,
4938       ShouldBeInTargetRegion,
4939       ShouldBeInTeamsRegion,
4940       ShouldBeInLoopSimdRegion,
4941     } Recommend = NoRecommend;
4942     if (isOpenMPSimdDirective(ParentRegion) &&
4943         ((SemaRef.LangOpts.OpenMP <= 45 && CurrentRegion != OMPD_ordered) ||
4944          (SemaRef.LangOpts.OpenMP >= 50 && CurrentRegion != OMPD_ordered &&
4945           CurrentRegion != OMPD_simd && CurrentRegion != OMPD_atomic &&
4946           CurrentRegion != OMPD_scan))) {
4947       // OpenMP [2.16, Nesting of Regions]
4948       // OpenMP constructs may not be nested inside a simd region.
4949       // OpenMP [2.8.1,simd Construct, Restrictions]
4950       // An ordered construct with the simd clause is the only OpenMP
4951       // construct that can appear in the simd region.
4952       // Allowing a SIMD construct nested in another SIMD construct is an
4953       // extension. The OpenMP 4.5 spec does not allow it. Issue a warning
4954       // message.
4955       // OpenMP 5.0 [2.9.3.1, simd Construct, Restrictions]
4956       // The only OpenMP constructs that can be encountered during execution of
4957       // a simd region are the atomic construct, the loop construct, the simd
4958       // construct and the ordered construct with the simd clause.
4959       SemaRef.Diag(StartLoc, (CurrentRegion != OMPD_simd)
4960                                  ? diag::err_omp_prohibited_region_simd
4961                                  : diag::warn_omp_nesting_simd)
4962           << (SemaRef.LangOpts.OpenMP >= 50 ? 1 : 0);
4963       return CurrentRegion != OMPD_simd;
4964     }
4965     if (ParentRegion == OMPD_atomic) {
4966       // OpenMP [2.16, Nesting of Regions]
4967       // OpenMP constructs may not be nested inside an atomic region.
4968       SemaRef.Diag(StartLoc, diag::err_omp_prohibited_region_atomic);
4969       return true;
4970     }
4971     if (CurrentRegion == OMPD_section) {
4972       // OpenMP [2.7.2, sections Construct, Restrictions]
4973       // Orphaned section directives are prohibited. That is, the section
4974       // directives must appear within the sections construct and must not be
4975       // encountered elsewhere in the sections region.
4976       if (ParentRegion != OMPD_sections &&
4977           ParentRegion != OMPD_parallel_sections) {
4978         SemaRef.Diag(StartLoc, diag::err_omp_orphaned_section_directive)
4979             << (ParentRegion != OMPD_unknown)
4980             << getOpenMPDirectiveName(ParentRegion);
4981         return true;
4982       }
4983       return false;
4984     }
4985     // Allow some constructs (except teams and cancellation constructs) to be
4986     // orphaned (they could be used in functions, called from OpenMP regions
4987     // with the required preconditions).
4988     if (ParentRegion == OMPD_unknown &&
4989         !isOpenMPNestingTeamsDirective(CurrentRegion) &&
4990         CurrentRegion != OMPD_cancellation_point &&
4991         CurrentRegion != OMPD_cancel && CurrentRegion != OMPD_scan)
4992       return false;
4993     if (CurrentRegion == OMPD_cancellation_point ||
4994         CurrentRegion == OMPD_cancel) {
4995       // OpenMP [2.16, Nesting of Regions]
4996       // A cancellation point construct for which construct-type-clause is
4997       // taskgroup must be nested inside a task construct. A cancellation
4998       // point construct for which construct-type-clause is not taskgroup must
4999       // be closely nested inside an OpenMP construct that matches the type
5000       // specified in construct-type-clause.
5001       // A cancel construct for which construct-type-clause is taskgroup must be
5002       // nested inside a task construct. A cancel construct for which
5003       // construct-type-clause is not taskgroup must be closely nested inside an
5004       // OpenMP construct that matches the type specified in
5005       // construct-type-clause.
5006       NestingProhibited =
5007           !((CancelRegion == OMPD_parallel &&
5008              (ParentRegion == OMPD_parallel ||
5009               ParentRegion == OMPD_target_parallel)) ||
5010             (CancelRegion == OMPD_for &&
5011              (ParentRegion == OMPD_for || ParentRegion == OMPD_parallel_for ||
5012               ParentRegion == OMPD_target_parallel_for ||
5013               ParentRegion == OMPD_distribute_parallel_for ||
5014               ParentRegion == OMPD_teams_distribute_parallel_for ||
5015               ParentRegion == OMPD_target_teams_distribute_parallel_for)) ||
5016             (CancelRegion == OMPD_taskgroup &&
5017              (ParentRegion == OMPD_task ||
5018               (SemaRef.getLangOpts().OpenMP >= 50 &&
5019                (ParentRegion == OMPD_taskloop ||
5020                 ParentRegion == OMPD_master_taskloop ||
5021                 ParentRegion == OMPD_masked_taskloop ||
5022                 ParentRegion == OMPD_parallel_masked_taskloop ||
5023                 ParentRegion == OMPD_parallel_master_taskloop)))) ||
5024             (CancelRegion == OMPD_sections &&
5025              (ParentRegion == OMPD_section || ParentRegion == OMPD_sections ||
5026               ParentRegion == OMPD_parallel_sections)));
5027       OrphanSeen = ParentRegion == OMPD_unknown;
5028     } else if (CurrentRegion == OMPD_master || CurrentRegion == OMPD_masked) {
5029       // OpenMP 5.1 [2.22, Nesting of Regions]
5030       // A masked region may not be closely nested inside a worksharing, loop,
5031       // atomic, task, or taskloop region.
5032       NestingProhibited = isOpenMPWorksharingDirective(ParentRegion) ||
5033                           isOpenMPGenericLoopDirective(ParentRegion) ||
5034                           isOpenMPTaskingDirective(ParentRegion);
5035     } else if (CurrentRegion == OMPD_critical && CurrentName.getName()) {
5036       // OpenMP [2.16, Nesting of Regions]
5037       // A critical region may not be nested (closely or otherwise) inside a
5038       // critical region with the same name. Note that this restriction is not
5039       // sufficient to prevent deadlock.
5040       SourceLocation PreviousCriticalLoc;
5041       bool DeadLock = Stack->hasDirective(
5042           [CurrentName, &PreviousCriticalLoc](OpenMPDirectiveKind K,
5043                                               const DeclarationNameInfo &DNI,
5044                                               SourceLocation Loc) {
5045             if (K == OMPD_critical && DNI.getName() == CurrentName.getName()) {
5046               PreviousCriticalLoc = Loc;
5047               return true;
5048             }
5049             return false;
5050           },
5051           false /* skip top directive */);
5052       if (DeadLock) {
5053         SemaRef.Diag(StartLoc,
5054                      diag::err_omp_prohibited_region_critical_same_name)
5055             << CurrentName.getName();
5056         if (PreviousCriticalLoc.isValid())
5057           SemaRef.Diag(PreviousCriticalLoc,
5058                        diag::note_omp_previous_critical_region);
5059         return true;
5060       }
5061     } else if (CurrentRegion == OMPD_barrier) {
5062       // OpenMP 5.1 [2.22, Nesting of Regions]
5063       // A barrier region may not be closely nested inside a worksharing, loop,
5064       // task, taskloop, critical, ordered, atomic, or masked region.
5065       NestingProhibited =
5066           isOpenMPWorksharingDirective(ParentRegion) ||
5067           isOpenMPGenericLoopDirective(ParentRegion) ||
5068           isOpenMPTaskingDirective(ParentRegion) ||
5069           ParentRegion == OMPD_master || ParentRegion == OMPD_masked ||
5070           ParentRegion == OMPD_parallel_master ||
5071           ParentRegion == OMPD_parallel_masked ||
5072           ParentRegion == OMPD_critical || ParentRegion == OMPD_ordered;
5073     } else if (isOpenMPWorksharingDirective(CurrentRegion) &&
5074                !isOpenMPParallelDirective(CurrentRegion) &&
5075                !isOpenMPTeamsDirective(CurrentRegion)) {
5076       // OpenMP 5.1 [2.22, Nesting of Regions]
5077       // A loop region that binds to a parallel region or a worksharing region
5078       // may not be closely nested inside a worksharing, loop, task, taskloop,
5079       // critical, ordered, atomic, or masked region.
5080       NestingProhibited =
5081           isOpenMPWorksharingDirective(ParentRegion) ||
5082           isOpenMPGenericLoopDirective(ParentRegion) ||
5083           isOpenMPTaskingDirective(ParentRegion) ||
5084           ParentRegion == OMPD_master || ParentRegion == OMPD_masked ||
5085           ParentRegion == OMPD_parallel_master ||
5086           ParentRegion == OMPD_parallel_masked ||
5087           ParentRegion == OMPD_critical || ParentRegion == OMPD_ordered;
5088       Recommend = ShouldBeInParallelRegion;
5089     } else if (CurrentRegion == OMPD_ordered) {
5090       // OpenMP [2.16, Nesting of Regions]
5091       // An ordered region may not be closely nested inside a critical,
5092       // atomic, or explicit task region.
5093       // An ordered region must be closely nested inside a loop region (or
5094       // parallel loop region) with an ordered clause.
5095       // OpenMP [2.8.1,simd Construct, Restrictions]
5096       // An ordered construct with the simd clause is the only OpenMP construct
5097       // that can appear in the simd region.
5098       NestingProhibited = ParentRegion == OMPD_critical ||
5099                           isOpenMPTaskingDirective(ParentRegion) ||
5100                           !(isOpenMPSimdDirective(ParentRegion) ||
5101                             Stack->isParentOrderedRegion());
5102       Recommend = ShouldBeInOrderedRegion;
5103     } else if (isOpenMPNestingTeamsDirective(CurrentRegion)) {
5104       // OpenMP [2.16, Nesting of Regions]
5105       // If specified, a teams construct must be contained within a target
5106       // construct.
5107       NestingProhibited =
5108           (SemaRef.LangOpts.OpenMP <= 45 && ParentRegion != OMPD_target) ||
5109           (SemaRef.LangOpts.OpenMP >= 50 && ParentRegion != OMPD_unknown &&
5110            ParentRegion != OMPD_target);
5111       OrphanSeen = ParentRegion == OMPD_unknown;
5112       Recommend = ShouldBeInTargetRegion;
5113     } else if (CurrentRegion == OMPD_scan) {
5114       // OpenMP [2.16, Nesting of Regions]
5115       // If specified, a teams construct must be contained within a target
5116       // construct.
5117       NestingProhibited =
5118           SemaRef.LangOpts.OpenMP < 50 ||
5119           (ParentRegion != OMPD_simd && ParentRegion != OMPD_for &&
5120            ParentRegion != OMPD_for_simd && ParentRegion != OMPD_parallel_for &&
5121            ParentRegion != OMPD_parallel_for_simd);
5122       OrphanSeen = ParentRegion == OMPD_unknown;
5123       Recommend = ShouldBeInLoopSimdRegion;
5124     }
5125     if (!NestingProhibited &&
5126         !isOpenMPTargetExecutionDirective(CurrentRegion) &&
5127         !isOpenMPTargetDataManagementDirective(CurrentRegion) &&
5128         (ParentRegion == OMPD_teams || ParentRegion == OMPD_target_teams)) {
5129       // OpenMP [5.1, 2.22, Nesting of Regions]
5130       // distribute, distribute simd, distribute parallel worksharing-loop,
5131       // distribute parallel worksharing-loop SIMD, loop, parallel regions,
5132       // including any parallel regions arising from combined constructs,
5133       // omp_get_num_teams() regions, and omp_get_team_num() regions are the
5134       // only OpenMP regions that may be strictly nested inside the teams
5135       // region.
5136       //
5137       // As an extension, we permit atomic within teams as well.
5138       NestingProhibited = !isOpenMPParallelDirective(CurrentRegion) &&
5139                           !isOpenMPDistributeDirective(CurrentRegion) &&
5140                           CurrentRegion != OMPD_loop &&
5141                           !(SemaRef.getLangOpts().OpenMPExtensions &&
5142                             CurrentRegion == OMPD_atomic);
5143       Recommend = ShouldBeInParallelRegion;
5144     }
5145     if (!NestingProhibited && CurrentRegion == OMPD_loop) {
5146       // OpenMP [5.1, 2.11.7, loop Construct, Restrictions]
5147       // If the bind clause is present on the loop construct and binding is
5148       // teams then the corresponding loop region must be strictly nested inside
5149       // a teams region.
5150       NestingProhibited = BindKind == OMPC_BIND_teams &&
5151                           ParentRegion != OMPD_teams &&
5152                           ParentRegion != OMPD_target_teams;
5153       Recommend = ShouldBeInTeamsRegion;
5154     }
5155     if (!NestingProhibited &&
5156         isOpenMPNestingDistributeDirective(CurrentRegion)) {
5157       // OpenMP 4.5 [2.17 Nesting of Regions]
5158       // The region associated with the distribute construct must be strictly
5159       // nested inside a teams region
5160       NestingProhibited =
5161           (ParentRegion != OMPD_teams && ParentRegion != OMPD_target_teams);
5162       Recommend = ShouldBeInTeamsRegion;
5163     }
5164     if (!NestingProhibited &&
5165         (isOpenMPTargetExecutionDirective(CurrentRegion) ||
5166          isOpenMPTargetDataManagementDirective(CurrentRegion))) {
5167       // OpenMP 4.5 [2.17 Nesting of Regions]
5168       // If a target, target update, target data, target enter data, or
5169       // target exit data construct is encountered during execution of a
5170       // target region, the behavior is unspecified.
5171       NestingProhibited = Stack->hasDirective(
5172           [&OffendingRegion](OpenMPDirectiveKind K, const DeclarationNameInfo &,
5173                              SourceLocation) {
5174             if (isOpenMPTargetExecutionDirective(K)) {
5175               OffendingRegion = K;
5176               return true;
5177             }
5178             return false;
5179           },
5180           false /* don't skip top directive */);
5181       CloseNesting = false;
5182     }
5183     if (NestingProhibited) {
5184       if (OrphanSeen) {
5185         SemaRef.Diag(StartLoc, diag::err_omp_orphaned_device_directive)
5186             << getOpenMPDirectiveName(CurrentRegion) << Recommend;
5187       } else {
5188         SemaRef.Diag(StartLoc, diag::err_omp_prohibited_region)
5189             << CloseNesting << getOpenMPDirectiveName(OffendingRegion)
5190             << Recommend << getOpenMPDirectiveName(CurrentRegion);
5191       }
5192       return true;
5193     }
5194   }
5195   return false;
5196 }
5197 
5198 struct Kind2Unsigned {
5199   using argument_type = OpenMPDirectiveKind;
5200   unsigned operator()(argument_type DK) { return unsigned(DK); }
5201 };
5202 static bool checkIfClauses(Sema &S, OpenMPDirectiveKind Kind,
5203                            ArrayRef<OMPClause *> Clauses,
5204                            ArrayRef<OpenMPDirectiveKind> AllowedNameModifiers) {
5205   bool ErrorFound = false;
5206   unsigned NamedModifiersNumber = 0;
5207   llvm::IndexedMap<const OMPIfClause *, Kind2Unsigned> FoundNameModifiers;
5208   FoundNameModifiers.resize(llvm::omp::Directive_enumSize + 1);
5209   SmallVector<SourceLocation, 4> NameModifierLoc;
5210   for (const OMPClause *C : Clauses) {
5211     if (const auto *IC = dyn_cast_or_null<OMPIfClause>(C)) {
5212       // At most one if clause without a directive-name-modifier can appear on
5213       // the directive.
5214       OpenMPDirectiveKind CurNM = IC->getNameModifier();
5215       if (FoundNameModifiers[CurNM]) {
5216         S.Diag(C->getBeginLoc(), diag::err_omp_more_one_clause)
5217             << getOpenMPDirectiveName(Kind) << getOpenMPClauseName(OMPC_if)
5218             << (CurNM != OMPD_unknown) << getOpenMPDirectiveName(CurNM);
5219         ErrorFound = true;
5220       } else if (CurNM != OMPD_unknown) {
5221         NameModifierLoc.push_back(IC->getNameModifierLoc());
5222         ++NamedModifiersNumber;
5223       }
5224       FoundNameModifiers[CurNM] = IC;
5225       if (CurNM == OMPD_unknown)
5226         continue;
5227       // Check if the specified name modifier is allowed for the current
5228       // directive.
5229       // At most one if clause with the particular directive-name-modifier can
5230       // appear on the directive.
5231       if (!llvm::is_contained(AllowedNameModifiers, CurNM)) {
5232         S.Diag(IC->getNameModifierLoc(),
5233                diag::err_omp_wrong_if_directive_name_modifier)
5234             << getOpenMPDirectiveName(CurNM) << getOpenMPDirectiveName(Kind);
5235         ErrorFound = true;
5236       }
5237     }
5238   }
5239   // If any if clause on the directive includes a directive-name-modifier then
5240   // all if clauses on the directive must include a directive-name-modifier.
5241   if (FoundNameModifiers[OMPD_unknown] && NamedModifiersNumber > 0) {
5242     if (NamedModifiersNumber == AllowedNameModifiers.size()) {
5243       S.Diag(FoundNameModifiers[OMPD_unknown]->getBeginLoc(),
5244              diag::err_omp_no_more_if_clause);
5245     } else {
5246       std::string Values;
5247       std::string Sep(", ");
5248       unsigned AllowedCnt = 0;
5249       unsigned TotalAllowedNum =
5250           AllowedNameModifiers.size() - NamedModifiersNumber;
5251       for (unsigned Cnt = 0, End = AllowedNameModifiers.size(); Cnt < End;
5252            ++Cnt) {
5253         OpenMPDirectiveKind NM = AllowedNameModifiers[Cnt];
5254         if (!FoundNameModifiers[NM]) {
5255           Values += "'";
5256           Values += getOpenMPDirectiveName(NM);
5257           Values += "'";
5258           if (AllowedCnt + 2 == TotalAllowedNum)
5259             Values += " or ";
5260           else if (AllowedCnt + 1 != TotalAllowedNum)
5261             Values += Sep;
5262           ++AllowedCnt;
5263         }
5264       }
5265       S.Diag(FoundNameModifiers[OMPD_unknown]->getCondition()->getBeginLoc(),
5266              diag::err_omp_unnamed_if_clause)
5267           << (TotalAllowedNum > 1) << Values;
5268     }
5269     for (SourceLocation Loc : NameModifierLoc) {
5270       S.Diag(Loc, diag::note_omp_previous_named_if_clause);
5271     }
5272     ErrorFound = true;
5273   }
5274   return ErrorFound;
5275 }
5276 
5277 static std::pair<ValueDecl *, bool> getPrivateItem(Sema &S, Expr *&RefExpr,
5278                                                    SourceLocation &ELoc,
5279                                                    SourceRange &ERange,
5280                                                    bool AllowArraySection) {
5281   if (RefExpr->isTypeDependent() || RefExpr->isValueDependent() ||
5282       RefExpr->containsUnexpandedParameterPack())
5283     return std::make_pair(nullptr, true);
5284 
5285   // OpenMP [3.1, C/C++]
5286   //  A list item is a variable name.
5287   // OpenMP  [2.9.3.3, Restrictions, p.1]
5288   //  A variable that is part of another variable (as an array or
5289   //  structure element) cannot appear in a private clause.
5290   RefExpr = RefExpr->IgnoreParens();
5291   enum {
5292     NoArrayExpr = -1,
5293     ArraySubscript = 0,
5294     OMPArraySection = 1
5295   } IsArrayExpr = NoArrayExpr;
5296   if (AllowArraySection) {
5297     if (auto *ASE = dyn_cast_or_null<ArraySubscriptExpr>(RefExpr)) {
5298       Expr *Base = ASE->getBase()->IgnoreParenImpCasts();
5299       while (auto *TempASE = dyn_cast<ArraySubscriptExpr>(Base))
5300         Base = TempASE->getBase()->IgnoreParenImpCasts();
5301       RefExpr = Base;
5302       IsArrayExpr = ArraySubscript;
5303     } else if (auto *OASE = dyn_cast_or_null<OMPArraySectionExpr>(RefExpr)) {
5304       Expr *Base = OASE->getBase()->IgnoreParenImpCasts();
5305       while (auto *TempOASE = dyn_cast<OMPArraySectionExpr>(Base))
5306         Base = TempOASE->getBase()->IgnoreParenImpCasts();
5307       while (auto *TempASE = dyn_cast<ArraySubscriptExpr>(Base))
5308         Base = TempASE->getBase()->IgnoreParenImpCasts();
5309       RefExpr = Base;
5310       IsArrayExpr = OMPArraySection;
5311     }
5312   }
5313   ELoc = RefExpr->getExprLoc();
5314   ERange = RefExpr->getSourceRange();
5315   RefExpr = RefExpr->IgnoreParenImpCasts();
5316   auto *DE = dyn_cast_or_null<DeclRefExpr>(RefExpr);
5317   auto *ME = dyn_cast_or_null<MemberExpr>(RefExpr);
5318   if ((!DE || !isa<VarDecl>(DE->getDecl())) &&
5319       (S.getCurrentThisType().isNull() || !ME ||
5320        !isa<CXXThisExpr>(ME->getBase()->IgnoreParenImpCasts()) ||
5321        !isa<FieldDecl>(ME->getMemberDecl()))) {
5322     if (IsArrayExpr != NoArrayExpr) {
5323       S.Diag(ELoc, diag::err_omp_expected_base_var_name)
5324           << IsArrayExpr << ERange;
5325     } else {
5326       S.Diag(ELoc,
5327              AllowArraySection
5328                  ? diag::err_omp_expected_var_name_member_expr_or_array_item
5329                  : diag::err_omp_expected_var_name_member_expr)
5330           << (S.getCurrentThisType().isNull() ? 0 : 1) << ERange;
5331     }
5332     return std::make_pair(nullptr, false);
5333   }
5334   return std::make_pair(
5335       getCanonicalDecl(DE ? DE->getDecl() : ME->getMemberDecl()), false);
5336 }
5337 
5338 namespace {
5339 /// Checks if the allocator is used in uses_allocators clause to be allowed in
5340 /// target regions.
5341 class AllocatorChecker final : public ConstStmtVisitor<AllocatorChecker, bool> {
5342   DSAStackTy *S = nullptr;
5343 
5344 public:
5345   bool VisitDeclRefExpr(const DeclRefExpr *E) {
5346     return S->isUsesAllocatorsDecl(E->getDecl())
5347                .value_or(DSAStackTy::UsesAllocatorsDeclKind::AllocatorTrait) ==
5348            DSAStackTy::UsesAllocatorsDeclKind::AllocatorTrait;
5349   }
5350   bool VisitStmt(const Stmt *S) {
5351     for (const Stmt *Child : S->children()) {
5352       if (Child && Visit(Child))
5353         return true;
5354     }
5355     return false;
5356   }
5357   explicit AllocatorChecker(DSAStackTy *S) : S(S) {}
5358 };
5359 } // namespace
5360 
5361 static void checkAllocateClauses(Sema &S, DSAStackTy *Stack,
5362                                  ArrayRef<OMPClause *> Clauses) {
5363   assert(!S.CurContext->isDependentContext() &&
5364          "Expected non-dependent context.");
5365   auto AllocateRange =
5366       llvm::make_filter_range(Clauses, OMPAllocateClause::classof);
5367   llvm::DenseMap<CanonicalDeclPtr<Decl>, CanonicalDeclPtr<VarDecl>> DeclToCopy;
5368   auto PrivateRange = llvm::make_filter_range(Clauses, [](const OMPClause *C) {
5369     return isOpenMPPrivate(C->getClauseKind());
5370   });
5371   for (OMPClause *Cl : PrivateRange) {
5372     MutableArrayRef<Expr *>::iterator I, It, Et;
5373     if (Cl->getClauseKind() == OMPC_private) {
5374       auto *PC = cast<OMPPrivateClause>(Cl);
5375       I = PC->private_copies().begin();
5376       It = PC->varlist_begin();
5377       Et = PC->varlist_end();
5378     } else if (Cl->getClauseKind() == OMPC_firstprivate) {
5379       auto *PC = cast<OMPFirstprivateClause>(Cl);
5380       I = PC->private_copies().begin();
5381       It = PC->varlist_begin();
5382       Et = PC->varlist_end();
5383     } else if (Cl->getClauseKind() == OMPC_lastprivate) {
5384       auto *PC = cast<OMPLastprivateClause>(Cl);
5385       I = PC->private_copies().begin();
5386       It = PC->varlist_begin();
5387       Et = PC->varlist_end();
5388     } else if (Cl->getClauseKind() == OMPC_linear) {
5389       auto *PC = cast<OMPLinearClause>(Cl);
5390       I = PC->privates().begin();
5391       It = PC->varlist_begin();
5392       Et = PC->varlist_end();
5393     } else if (Cl->getClauseKind() == OMPC_reduction) {
5394       auto *PC = cast<OMPReductionClause>(Cl);
5395       I = PC->privates().begin();
5396       It = PC->varlist_begin();
5397       Et = PC->varlist_end();
5398     } else if (Cl->getClauseKind() == OMPC_task_reduction) {
5399       auto *PC = cast<OMPTaskReductionClause>(Cl);
5400       I = PC->privates().begin();
5401       It = PC->varlist_begin();
5402       Et = PC->varlist_end();
5403     } else if (Cl->getClauseKind() == OMPC_in_reduction) {
5404       auto *PC = cast<OMPInReductionClause>(Cl);
5405       I = PC->privates().begin();
5406       It = PC->varlist_begin();
5407       Et = PC->varlist_end();
5408     } else {
5409       llvm_unreachable("Expected private clause.");
5410     }
5411     for (Expr *E : llvm::make_range(It, Et)) {
5412       if (!*I) {
5413         ++I;
5414         continue;
5415       }
5416       SourceLocation ELoc;
5417       SourceRange ERange;
5418       Expr *SimpleRefExpr = E;
5419       auto Res = getPrivateItem(S, SimpleRefExpr, ELoc, ERange,
5420                                 /*AllowArraySection=*/true);
5421       DeclToCopy.try_emplace(Res.first,
5422                              cast<VarDecl>(cast<DeclRefExpr>(*I)->getDecl()));
5423       ++I;
5424     }
5425   }
5426   for (OMPClause *C : AllocateRange) {
5427     auto *AC = cast<OMPAllocateClause>(C);
5428     if (S.getLangOpts().OpenMP >= 50 &&
5429         !Stack->hasRequiresDeclWithClause<OMPDynamicAllocatorsClause>() &&
5430         isOpenMPTargetExecutionDirective(Stack->getCurrentDirective()) &&
5431         AC->getAllocator()) {
5432       Expr *Allocator = AC->getAllocator();
5433       // OpenMP, 2.12.5 target Construct
5434       // Memory allocators that do not appear in a uses_allocators clause cannot
5435       // appear as an allocator in an allocate clause or be used in the target
5436       // region unless a requires directive with the dynamic_allocators clause
5437       // is present in the same compilation unit.
5438       AllocatorChecker Checker(Stack);
5439       if (Checker.Visit(Allocator))
5440         S.Diag(Allocator->getExprLoc(),
5441                diag::err_omp_allocator_not_in_uses_allocators)
5442             << Allocator->getSourceRange();
5443     }
5444     OMPAllocateDeclAttr::AllocatorTypeTy AllocatorKind =
5445         getAllocatorKind(S, Stack, AC->getAllocator());
5446     // OpenMP, 2.11.4 allocate Clause, Restrictions.
5447     // For task, taskloop or target directives, allocation requests to memory
5448     // allocators with the trait access set to thread result in unspecified
5449     // behavior.
5450     if (AllocatorKind == OMPAllocateDeclAttr::OMPThreadMemAlloc &&
5451         (isOpenMPTaskingDirective(Stack->getCurrentDirective()) ||
5452          isOpenMPTargetExecutionDirective(Stack->getCurrentDirective()))) {
5453       S.Diag(AC->getAllocator()->getExprLoc(),
5454              diag::warn_omp_allocate_thread_on_task_target_directive)
5455           << getOpenMPDirectiveName(Stack->getCurrentDirective());
5456     }
5457     for (Expr *E : AC->varlists()) {
5458       SourceLocation ELoc;
5459       SourceRange ERange;
5460       Expr *SimpleRefExpr = E;
5461       auto Res = getPrivateItem(S, SimpleRefExpr, ELoc, ERange);
5462       ValueDecl *VD = Res.first;
5463       DSAStackTy::DSAVarData Data = Stack->getTopDSA(VD, /*FromParent=*/false);
5464       if (!isOpenMPPrivate(Data.CKind)) {
5465         S.Diag(E->getExprLoc(),
5466                diag::err_omp_expected_private_copy_for_allocate);
5467         continue;
5468       }
5469       VarDecl *PrivateVD = DeclToCopy[VD];
5470       if (checkPreviousOMPAllocateAttribute(S, Stack, E, PrivateVD,
5471                                             AllocatorKind, AC->getAllocator()))
5472         continue;
5473       // Placeholder until allocate clause supports align modifier.
5474       Expr *Alignment = nullptr;
5475       applyOMPAllocateAttribute(S, PrivateVD, AllocatorKind, AC->getAllocator(),
5476                                 Alignment, E->getSourceRange());
5477     }
5478   }
5479 }
5480 
5481 namespace {
5482 /// Rewrite statements and expressions for Sema \p Actions CurContext.
5483 ///
5484 /// Used to wrap already parsed statements/expressions into a new CapturedStmt
5485 /// context. DeclRefExpr used inside the new context are changed to refer to the
5486 /// captured variable instead.
5487 class CaptureVars : public TreeTransform<CaptureVars> {
5488   using BaseTransform = TreeTransform<CaptureVars>;
5489 
5490 public:
5491   CaptureVars(Sema &Actions) : BaseTransform(Actions) {}
5492 
5493   bool AlwaysRebuild() { return true; }
5494 };
5495 } // namespace
5496 
5497 static VarDecl *precomputeExpr(Sema &Actions,
5498                                SmallVectorImpl<Stmt *> &BodyStmts, Expr *E,
5499                                StringRef Name) {
5500   Expr *NewE = AssertSuccess(CaptureVars(Actions).TransformExpr(E));
5501   VarDecl *NewVar = buildVarDecl(Actions, {}, NewE->getType(), Name, nullptr,
5502                                  dyn_cast<DeclRefExpr>(E->IgnoreImplicit()));
5503   auto *NewDeclStmt = cast<DeclStmt>(AssertSuccess(
5504       Actions.ActOnDeclStmt(Actions.ConvertDeclToDeclGroup(NewVar), {}, {})));
5505   Actions.AddInitializerToDecl(NewDeclStmt->getSingleDecl(), NewE, false);
5506   BodyStmts.push_back(NewDeclStmt);
5507   return NewVar;
5508 }
5509 
5510 /// Create a closure that computes the number of iterations of a loop.
5511 ///
5512 /// \param Actions   The Sema object.
5513 /// \param LogicalTy Type for the logical iteration number.
5514 /// \param Rel       Comparison operator of the loop condition.
5515 /// \param StartExpr Value of the loop counter at the first iteration.
5516 /// \param StopExpr  Expression the loop counter is compared against in the loop
5517 /// condition. \param StepExpr      Amount of increment after each iteration.
5518 ///
5519 /// \return Closure (CapturedStmt) of the distance calculation.
5520 static CapturedStmt *buildDistanceFunc(Sema &Actions, QualType LogicalTy,
5521                                        BinaryOperator::Opcode Rel,
5522                                        Expr *StartExpr, Expr *StopExpr,
5523                                        Expr *StepExpr) {
5524   ASTContext &Ctx = Actions.getASTContext();
5525   TypeSourceInfo *LogicalTSI = Ctx.getTrivialTypeSourceInfo(LogicalTy);
5526 
5527   // Captured regions currently don't support return values, we use an
5528   // out-parameter instead. All inputs are implicit captures.
5529   // TODO: Instead of capturing each DeclRefExpr occurring in
5530   // StartExpr/StopExpr/Step, these could also be passed as a value capture.
5531   QualType ResultTy = Ctx.getLValueReferenceType(LogicalTy);
5532   Sema::CapturedParamNameType Params[] = {{"Distance", ResultTy},
5533                                           {StringRef(), QualType()}};
5534   Actions.ActOnCapturedRegionStart({}, nullptr, CR_Default, Params);
5535 
5536   Stmt *Body;
5537   {
5538     Sema::CompoundScopeRAII CompoundScope(Actions);
5539     CapturedDecl *CS = cast<CapturedDecl>(Actions.CurContext);
5540 
5541     // Get the LValue expression for the result.
5542     ImplicitParamDecl *DistParam = CS->getParam(0);
5543     DeclRefExpr *DistRef = Actions.BuildDeclRefExpr(
5544         DistParam, LogicalTy, VK_LValue, {}, nullptr, nullptr, {}, nullptr);
5545 
5546     SmallVector<Stmt *, 4> BodyStmts;
5547 
5548     // Capture all referenced variable references.
5549     // TODO: Instead of computing NewStart/NewStop/NewStep inside the
5550     // CapturedStmt, we could compute them before and capture the result, to be
5551     // used jointly with the LoopVar function.
5552     VarDecl *NewStart = precomputeExpr(Actions, BodyStmts, StartExpr, ".start");
5553     VarDecl *NewStop = precomputeExpr(Actions, BodyStmts, StopExpr, ".stop");
5554     VarDecl *NewStep = precomputeExpr(Actions, BodyStmts, StepExpr, ".step");
5555     auto BuildVarRef = [&](VarDecl *VD) {
5556       return buildDeclRefExpr(Actions, VD, VD->getType(), {});
5557     };
5558 
5559     IntegerLiteral *Zero = IntegerLiteral::Create(
5560         Ctx, llvm::APInt(Ctx.getIntWidth(LogicalTy), 0), LogicalTy, {});
5561     IntegerLiteral *One = IntegerLiteral::Create(
5562         Ctx, llvm::APInt(Ctx.getIntWidth(LogicalTy), 1), LogicalTy, {});
5563     Expr *Dist;
5564     if (Rel == BO_NE) {
5565       // When using a != comparison, the increment can be +1 or -1. This can be
5566       // dynamic at runtime, so we need to check for the direction.
5567       Expr *IsNegStep = AssertSuccess(
5568           Actions.BuildBinOp(nullptr, {}, BO_LT, BuildVarRef(NewStep), Zero));
5569 
5570       // Positive increment.
5571       Expr *ForwardRange = AssertSuccess(Actions.BuildBinOp(
5572           nullptr, {}, BO_Sub, BuildVarRef(NewStop), BuildVarRef(NewStart)));
5573       ForwardRange = AssertSuccess(
5574           Actions.BuildCStyleCastExpr({}, LogicalTSI, {}, ForwardRange));
5575       Expr *ForwardDist = AssertSuccess(Actions.BuildBinOp(
5576           nullptr, {}, BO_Div, ForwardRange, BuildVarRef(NewStep)));
5577 
5578       // Negative increment.
5579       Expr *BackwardRange = AssertSuccess(Actions.BuildBinOp(
5580           nullptr, {}, BO_Sub, BuildVarRef(NewStart), BuildVarRef(NewStop)));
5581       BackwardRange = AssertSuccess(
5582           Actions.BuildCStyleCastExpr({}, LogicalTSI, {}, BackwardRange));
5583       Expr *NegIncAmount = AssertSuccess(
5584           Actions.BuildUnaryOp(nullptr, {}, UO_Minus, BuildVarRef(NewStep)));
5585       Expr *BackwardDist = AssertSuccess(
5586           Actions.BuildBinOp(nullptr, {}, BO_Div, BackwardRange, NegIncAmount));
5587 
5588       // Use the appropriate case.
5589       Dist = AssertSuccess(Actions.ActOnConditionalOp(
5590           {}, {}, IsNegStep, BackwardDist, ForwardDist));
5591     } else {
5592       assert((Rel == BO_LT || Rel == BO_LE || Rel == BO_GE || Rel == BO_GT) &&
5593              "Expected one of these relational operators");
5594 
5595       // We can derive the direction from any other comparison operator. It is
5596       // non well-formed OpenMP if Step increments/decrements in the other
5597       // directions. Whether at least the first iteration passes the loop
5598       // condition.
5599       Expr *HasAnyIteration = AssertSuccess(Actions.BuildBinOp(
5600           nullptr, {}, Rel, BuildVarRef(NewStart), BuildVarRef(NewStop)));
5601 
5602       // Compute the range between first and last counter value.
5603       Expr *Range;
5604       if (Rel == BO_GE || Rel == BO_GT)
5605         Range = AssertSuccess(Actions.BuildBinOp(
5606             nullptr, {}, BO_Sub, BuildVarRef(NewStart), BuildVarRef(NewStop)));
5607       else
5608         Range = AssertSuccess(Actions.BuildBinOp(
5609             nullptr, {}, BO_Sub, BuildVarRef(NewStop), BuildVarRef(NewStart)));
5610 
5611       // Ensure unsigned range space.
5612       Range =
5613           AssertSuccess(Actions.BuildCStyleCastExpr({}, LogicalTSI, {}, Range));
5614 
5615       if (Rel == BO_LE || Rel == BO_GE) {
5616         // Add one to the range if the relational operator is inclusive.
5617         Range =
5618             AssertSuccess(Actions.BuildBinOp(nullptr, {}, BO_Add, Range, One));
5619       }
5620 
5621       // Divide by the absolute step amount. If the range is not a multiple of
5622       // the step size, rounding-up the effective upper bound ensures that the
5623       // last iteration is included.
5624       // Note that the rounding-up may cause an overflow in a temporry that
5625       // could be avoided, but would have occurred in a C-style for-loop as well.
5626       Expr *Divisor = BuildVarRef(NewStep);
5627       if (Rel == BO_GE || Rel == BO_GT)
5628         Divisor =
5629             AssertSuccess(Actions.BuildUnaryOp(nullptr, {}, UO_Minus, Divisor));
5630       Expr *DivisorMinusOne =
5631           AssertSuccess(Actions.BuildBinOp(nullptr, {}, BO_Sub, Divisor, One));
5632       Expr *RangeRoundUp = AssertSuccess(
5633           Actions.BuildBinOp(nullptr, {}, BO_Add, Range, DivisorMinusOne));
5634       Dist = AssertSuccess(
5635           Actions.BuildBinOp(nullptr, {}, BO_Div, RangeRoundUp, Divisor));
5636 
5637       // If there is not at least one iteration, the range contains garbage. Fix
5638       // to zero in this case.
5639       Dist = AssertSuccess(
5640           Actions.ActOnConditionalOp({}, {}, HasAnyIteration, Dist, Zero));
5641     }
5642 
5643     // Assign the result to the out-parameter.
5644     Stmt *ResultAssign = AssertSuccess(Actions.BuildBinOp(
5645         Actions.getCurScope(), {}, BO_Assign, DistRef, Dist));
5646     BodyStmts.push_back(ResultAssign);
5647 
5648     Body = AssertSuccess(Actions.ActOnCompoundStmt({}, {}, BodyStmts, false));
5649   }
5650 
5651   return cast<CapturedStmt>(
5652       AssertSuccess(Actions.ActOnCapturedRegionEnd(Body)));
5653 }
5654 
5655 /// Create a closure that computes the loop variable from the logical iteration
5656 /// number.
5657 ///
5658 /// \param Actions   The Sema object.
5659 /// \param LoopVarTy Type for the loop variable used for result value.
5660 /// \param LogicalTy Type for the logical iteration number.
5661 /// \param StartExpr Value of the loop counter at the first iteration.
5662 /// \param Step      Amount of increment after each iteration.
5663 /// \param Deref     Whether the loop variable is a dereference of the loop
5664 /// counter variable.
5665 ///
5666 /// \return Closure (CapturedStmt) of the loop value calculation.
5667 static CapturedStmt *buildLoopVarFunc(Sema &Actions, QualType LoopVarTy,
5668                                       QualType LogicalTy,
5669                                       DeclRefExpr *StartExpr, Expr *Step,
5670                                       bool Deref) {
5671   ASTContext &Ctx = Actions.getASTContext();
5672 
5673   // Pass the result as an out-parameter. Passing as return value would require
5674   // the OpenMPIRBuilder to know additional C/C++ semantics, such as how to
5675   // invoke a copy constructor.
5676   QualType TargetParamTy = Ctx.getLValueReferenceType(LoopVarTy);
5677   Sema::CapturedParamNameType Params[] = {{"LoopVar", TargetParamTy},
5678                                           {"Logical", LogicalTy},
5679                                           {StringRef(), QualType()}};
5680   Actions.ActOnCapturedRegionStart({}, nullptr, CR_Default, Params);
5681 
5682   // Capture the initial iterator which represents the LoopVar value at the
5683   // zero's logical iteration. Since the original ForStmt/CXXForRangeStmt update
5684   // it in every iteration, capture it by value before it is modified.
5685   VarDecl *StartVar = cast<VarDecl>(StartExpr->getDecl());
5686   bool Invalid = Actions.tryCaptureVariable(StartVar, {},
5687                                             Sema::TryCapture_ExplicitByVal, {});
5688   (void)Invalid;
5689   assert(!Invalid && "Expecting capture-by-value to work.");
5690 
5691   Expr *Body;
5692   {
5693     Sema::CompoundScopeRAII CompoundScope(Actions);
5694     auto *CS = cast<CapturedDecl>(Actions.CurContext);
5695 
5696     ImplicitParamDecl *TargetParam = CS->getParam(0);
5697     DeclRefExpr *TargetRef = Actions.BuildDeclRefExpr(
5698         TargetParam, LoopVarTy, VK_LValue, {}, nullptr, nullptr, {}, nullptr);
5699     ImplicitParamDecl *IndvarParam = CS->getParam(1);
5700     DeclRefExpr *LogicalRef = Actions.BuildDeclRefExpr(
5701         IndvarParam, LogicalTy, VK_LValue, {}, nullptr, nullptr, {}, nullptr);
5702 
5703     // Capture the Start expression.
5704     CaptureVars Recap(Actions);
5705     Expr *NewStart = AssertSuccess(Recap.TransformExpr(StartExpr));
5706     Expr *NewStep = AssertSuccess(Recap.TransformExpr(Step));
5707 
5708     Expr *Skip = AssertSuccess(
5709         Actions.BuildBinOp(nullptr, {}, BO_Mul, NewStep, LogicalRef));
5710     // TODO: Explicitly cast to the iterator's difference_type instead of
5711     // relying on implicit conversion.
5712     Expr *Advanced =
5713         AssertSuccess(Actions.BuildBinOp(nullptr, {}, BO_Add, NewStart, Skip));
5714 
5715     if (Deref) {
5716       // For range-based for-loops convert the loop counter value to a concrete
5717       // loop variable value by dereferencing the iterator.
5718       Advanced =
5719           AssertSuccess(Actions.BuildUnaryOp(nullptr, {}, UO_Deref, Advanced));
5720     }
5721 
5722     // Assign the result to the output parameter.
5723     Body = AssertSuccess(Actions.BuildBinOp(Actions.getCurScope(), {},
5724                                             BO_Assign, TargetRef, Advanced));
5725   }
5726   return cast<CapturedStmt>(
5727       AssertSuccess(Actions.ActOnCapturedRegionEnd(Body)));
5728 }
5729 
5730 StmtResult Sema::ActOnOpenMPCanonicalLoop(Stmt *AStmt) {
5731   ASTContext &Ctx = getASTContext();
5732 
5733   // Extract the common elements of ForStmt and CXXForRangeStmt:
5734   // Loop variable, repeat condition, increment
5735   Expr *Cond, *Inc;
5736   VarDecl *LIVDecl, *LUVDecl;
5737   if (auto *For = dyn_cast<ForStmt>(AStmt)) {
5738     Stmt *Init = For->getInit();
5739     if (auto *LCVarDeclStmt = dyn_cast<DeclStmt>(Init)) {
5740       // For statement declares loop variable.
5741       LIVDecl = cast<VarDecl>(LCVarDeclStmt->getSingleDecl());
5742     } else if (auto *LCAssign = dyn_cast<BinaryOperator>(Init)) {
5743       // For statement reuses variable.
5744       assert(LCAssign->getOpcode() == BO_Assign &&
5745              "init part must be a loop variable assignment");
5746       auto *CounterRef = cast<DeclRefExpr>(LCAssign->getLHS());
5747       LIVDecl = cast<VarDecl>(CounterRef->getDecl());
5748     } else
5749       llvm_unreachable("Cannot determine loop variable");
5750     LUVDecl = LIVDecl;
5751 
5752     Cond = For->getCond();
5753     Inc = For->getInc();
5754   } else if (auto *RangeFor = dyn_cast<CXXForRangeStmt>(AStmt)) {
5755     DeclStmt *BeginStmt = RangeFor->getBeginStmt();
5756     LIVDecl = cast<VarDecl>(BeginStmt->getSingleDecl());
5757     LUVDecl = RangeFor->getLoopVariable();
5758 
5759     Cond = RangeFor->getCond();
5760     Inc = RangeFor->getInc();
5761   } else
5762     llvm_unreachable("unhandled kind of loop");
5763 
5764   QualType CounterTy = LIVDecl->getType();
5765   QualType LVTy = LUVDecl->getType();
5766 
5767   // Analyze the loop condition.
5768   Expr *LHS, *RHS;
5769   BinaryOperator::Opcode CondRel;
5770   Cond = Cond->IgnoreImplicit();
5771   if (auto *CondBinExpr = dyn_cast<BinaryOperator>(Cond)) {
5772     LHS = CondBinExpr->getLHS();
5773     RHS = CondBinExpr->getRHS();
5774     CondRel = CondBinExpr->getOpcode();
5775   } else if (auto *CondCXXOp = dyn_cast<CXXOperatorCallExpr>(Cond)) {
5776     assert(CondCXXOp->getNumArgs() == 2 && "Comparison should have 2 operands");
5777     LHS = CondCXXOp->getArg(0);
5778     RHS = CondCXXOp->getArg(1);
5779     switch (CondCXXOp->getOperator()) {
5780     case OO_ExclaimEqual:
5781       CondRel = BO_NE;
5782       break;
5783     case OO_Less:
5784       CondRel = BO_LT;
5785       break;
5786     case OO_LessEqual:
5787       CondRel = BO_LE;
5788       break;
5789     case OO_Greater:
5790       CondRel = BO_GT;
5791       break;
5792     case OO_GreaterEqual:
5793       CondRel = BO_GE;
5794       break;
5795     default:
5796       llvm_unreachable("unexpected iterator operator");
5797     }
5798   } else
5799     llvm_unreachable("unexpected loop condition");
5800 
5801   // Normalize such that the loop counter is on the LHS.
5802   if (!isa<DeclRefExpr>(LHS->IgnoreImplicit()) ||
5803       cast<DeclRefExpr>(LHS->IgnoreImplicit())->getDecl() != LIVDecl) {
5804     std::swap(LHS, RHS);
5805     CondRel = BinaryOperator::reverseComparisonOp(CondRel);
5806   }
5807   auto *CounterRef = cast<DeclRefExpr>(LHS->IgnoreImplicit());
5808 
5809   // Decide the bit width for the logical iteration counter. By default use the
5810   // unsigned ptrdiff_t integer size (for iterators and pointers).
5811   // TODO: For iterators, use iterator::difference_type,
5812   // std::iterator_traits<>::difference_type or decltype(it - end).
5813   QualType LogicalTy = Ctx.getUnsignedPointerDiffType();
5814   if (CounterTy->isIntegerType()) {
5815     unsigned BitWidth = Ctx.getIntWidth(CounterTy);
5816     LogicalTy = Ctx.getIntTypeForBitwidth(BitWidth, false);
5817   }
5818 
5819   // Analyze the loop increment.
5820   Expr *Step;
5821   if (auto *IncUn = dyn_cast<UnaryOperator>(Inc)) {
5822     int Direction;
5823     switch (IncUn->getOpcode()) {
5824     case UO_PreInc:
5825     case UO_PostInc:
5826       Direction = 1;
5827       break;
5828     case UO_PreDec:
5829     case UO_PostDec:
5830       Direction = -1;
5831       break;
5832     default:
5833       llvm_unreachable("unhandled unary increment operator");
5834     }
5835     Step = IntegerLiteral::Create(
5836         Ctx, llvm::APInt(Ctx.getIntWidth(LogicalTy), Direction), LogicalTy, {});
5837   } else if (auto *IncBin = dyn_cast<BinaryOperator>(Inc)) {
5838     if (IncBin->getOpcode() == BO_AddAssign) {
5839       Step = IncBin->getRHS();
5840     } else if (IncBin->getOpcode() == BO_SubAssign) {
5841       Step =
5842           AssertSuccess(BuildUnaryOp(nullptr, {}, UO_Minus, IncBin->getRHS()));
5843     } else
5844       llvm_unreachable("unhandled binary increment operator");
5845   } else if (auto *CondCXXOp = dyn_cast<CXXOperatorCallExpr>(Inc)) {
5846     switch (CondCXXOp->getOperator()) {
5847     case OO_PlusPlus:
5848       Step = IntegerLiteral::Create(
5849           Ctx, llvm::APInt(Ctx.getIntWidth(LogicalTy), 1), LogicalTy, {});
5850       break;
5851     case OO_MinusMinus:
5852       Step = IntegerLiteral::Create(
5853           Ctx, llvm::APInt(Ctx.getIntWidth(LogicalTy), -1), LogicalTy, {});
5854       break;
5855     case OO_PlusEqual:
5856       Step = CondCXXOp->getArg(1);
5857       break;
5858     case OO_MinusEqual:
5859       Step = AssertSuccess(
5860           BuildUnaryOp(nullptr, {}, UO_Minus, CondCXXOp->getArg(1)));
5861       break;
5862     default:
5863       llvm_unreachable("unhandled overloaded increment operator");
5864     }
5865   } else
5866     llvm_unreachable("unknown increment expression");
5867 
5868   CapturedStmt *DistanceFunc =
5869       buildDistanceFunc(*this, LogicalTy, CondRel, LHS, RHS, Step);
5870   CapturedStmt *LoopVarFunc = buildLoopVarFunc(
5871       *this, LVTy, LogicalTy, CounterRef, Step, isa<CXXForRangeStmt>(AStmt));
5872   DeclRefExpr *LVRef = BuildDeclRefExpr(LUVDecl, LUVDecl->getType(), VK_LValue,
5873                                         {}, nullptr, nullptr, {}, nullptr);
5874   return OMPCanonicalLoop::create(getASTContext(), AStmt, DistanceFunc,
5875                                   LoopVarFunc, LVRef);
5876 }
5877 
5878 StmtResult Sema::ActOnOpenMPLoopnest(Stmt *AStmt) {
5879   // Handle a literal loop.
5880   if (isa<ForStmt>(AStmt) || isa<CXXForRangeStmt>(AStmt))
5881     return ActOnOpenMPCanonicalLoop(AStmt);
5882 
5883   // If not a literal loop, it must be the result of a loop transformation.
5884   OMPExecutableDirective *LoopTransform = cast<OMPExecutableDirective>(AStmt);
5885   assert(
5886       isOpenMPLoopTransformationDirective(LoopTransform->getDirectiveKind()) &&
5887       "Loop transformation directive expected");
5888   return LoopTransform;
5889 }
5890 
5891 static ExprResult buildUserDefinedMapperRef(Sema &SemaRef, Scope *S,
5892                                             CXXScopeSpec &MapperIdScopeSpec,
5893                                             const DeclarationNameInfo &MapperId,
5894                                             QualType Type,
5895                                             Expr *UnresolvedMapper);
5896 
5897 /// Perform DFS through the structure/class data members trying to find
5898 /// member(s) with user-defined 'default' mapper and generate implicit map
5899 /// clauses for such members with the found 'default' mapper.
5900 static void
5901 processImplicitMapsWithDefaultMappers(Sema &S, DSAStackTy *Stack,
5902                                       SmallVectorImpl<OMPClause *> &Clauses) {
5903   // Check for the deault mapper for data members.
5904   if (S.getLangOpts().OpenMP < 50)
5905     return;
5906   SmallVector<OMPClause *, 4> ImplicitMaps;
5907   for (int Cnt = 0, EndCnt = Clauses.size(); Cnt < EndCnt; ++Cnt) {
5908     auto *C = dyn_cast<OMPMapClause>(Clauses[Cnt]);
5909     if (!C)
5910       continue;
5911     SmallVector<Expr *, 4> SubExprs;
5912     auto *MI = C->mapperlist_begin();
5913     for (auto I = C->varlist_begin(), End = C->varlist_end(); I != End;
5914          ++I, ++MI) {
5915       // Expression is mapped using mapper - skip it.
5916       if (*MI)
5917         continue;
5918       Expr *E = *I;
5919       // Expression is dependent - skip it, build the mapper when it gets
5920       // instantiated.
5921       if (E->isTypeDependent() || E->isValueDependent() ||
5922           E->containsUnexpandedParameterPack())
5923         continue;
5924       // Array section - need to check for the mapping of the array section
5925       // element.
5926       QualType CanonType = E->getType().getCanonicalType();
5927       if (CanonType->isSpecificBuiltinType(BuiltinType::OMPArraySection)) {
5928         const auto *OASE = cast<OMPArraySectionExpr>(E->IgnoreParenImpCasts());
5929         QualType BaseType =
5930             OMPArraySectionExpr::getBaseOriginalType(OASE->getBase());
5931         QualType ElemType;
5932         if (const auto *ATy = BaseType->getAsArrayTypeUnsafe())
5933           ElemType = ATy->getElementType();
5934         else
5935           ElemType = BaseType->getPointeeType();
5936         CanonType = ElemType;
5937       }
5938 
5939       // DFS over data members in structures/classes.
5940       SmallVector<std::pair<QualType, FieldDecl *>, 4> Types(
5941           1, {CanonType, nullptr});
5942       llvm::DenseMap<const Type *, Expr *> Visited;
5943       SmallVector<std::pair<FieldDecl *, unsigned>, 4> ParentChain(
5944           1, {nullptr, 1});
5945       while (!Types.empty()) {
5946         QualType BaseType;
5947         FieldDecl *CurFD;
5948         std::tie(BaseType, CurFD) = Types.pop_back_val();
5949         while (ParentChain.back().second == 0)
5950           ParentChain.pop_back();
5951         --ParentChain.back().second;
5952         if (BaseType.isNull())
5953           continue;
5954         // Only structs/classes are allowed to have mappers.
5955         const RecordDecl *RD = BaseType.getCanonicalType()->getAsRecordDecl();
5956         if (!RD)
5957           continue;
5958         auto It = Visited.find(BaseType.getTypePtr());
5959         if (It == Visited.end()) {
5960           // Try to find the associated user-defined mapper.
5961           CXXScopeSpec MapperIdScopeSpec;
5962           DeclarationNameInfo DefaultMapperId;
5963           DefaultMapperId.setName(S.Context.DeclarationNames.getIdentifier(
5964               &S.Context.Idents.get("default")));
5965           DefaultMapperId.setLoc(E->getExprLoc());
5966           ExprResult ER = buildUserDefinedMapperRef(
5967               S, Stack->getCurScope(), MapperIdScopeSpec, DefaultMapperId,
5968               BaseType, /*UnresolvedMapper=*/nullptr);
5969           if (ER.isInvalid())
5970             continue;
5971           It = Visited.try_emplace(BaseType.getTypePtr(), ER.get()).first;
5972         }
5973         // Found default mapper.
5974         if (It->second) {
5975           auto *OE = new (S.Context) OpaqueValueExpr(E->getExprLoc(), CanonType,
5976                                                      VK_LValue, OK_Ordinary, E);
5977           OE->setIsUnique(/*V=*/true);
5978           Expr *BaseExpr = OE;
5979           for (const auto &P : ParentChain) {
5980             if (P.first) {
5981               BaseExpr = S.BuildMemberExpr(
5982                   BaseExpr, /*IsArrow=*/false, E->getExprLoc(),
5983                   NestedNameSpecifierLoc(), SourceLocation(), P.first,
5984                   DeclAccessPair::make(P.first, P.first->getAccess()),
5985                   /*HadMultipleCandidates=*/false, DeclarationNameInfo(),
5986                   P.first->getType(), VK_LValue, OK_Ordinary);
5987               BaseExpr = S.DefaultLvalueConversion(BaseExpr).get();
5988             }
5989           }
5990           if (CurFD)
5991             BaseExpr = S.BuildMemberExpr(
5992                 BaseExpr, /*IsArrow=*/false, E->getExprLoc(),
5993                 NestedNameSpecifierLoc(), SourceLocation(), CurFD,
5994                 DeclAccessPair::make(CurFD, CurFD->getAccess()),
5995                 /*HadMultipleCandidates=*/false, DeclarationNameInfo(),
5996                 CurFD->getType(), VK_LValue, OK_Ordinary);
5997           SubExprs.push_back(BaseExpr);
5998           continue;
5999         }
6000         // Check for the "default" mapper for data members.
6001         bool FirstIter = true;
6002         for (FieldDecl *FD : RD->fields()) {
6003           if (!FD)
6004             continue;
6005           QualType FieldTy = FD->getType();
6006           if (FieldTy.isNull() ||
6007               !(FieldTy->isStructureOrClassType() || FieldTy->isUnionType()))
6008             continue;
6009           if (FirstIter) {
6010             FirstIter = false;
6011             ParentChain.emplace_back(CurFD, 1);
6012           } else {
6013             ++ParentChain.back().second;
6014           }
6015           Types.emplace_back(FieldTy, FD);
6016         }
6017       }
6018     }
6019     if (SubExprs.empty())
6020       continue;
6021     CXXScopeSpec MapperIdScopeSpec;
6022     DeclarationNameInfo MapperId;
6023     if (OMPClause *NewClause = S.ActOnOpenMPMapClause(
6024             C->getMapTypeModifiers(), C->getMapTypeModifiersLoc(),
6025             MapperIdScopeSpec, MapperId, C->getMapType(),
6026             /*IsMapTypeImplicit=*/true, SourceLocation(), SourceLocation(),
6027             SubExprs, OMPVarListLocTy()))
6028       Clauses.push_back(NewClause);
6029   }
6030 }
6031 
6032 StmtResult Sema::ActOnOpenMPExecutableDirective(
6033     OpenMPDirectiveKind Kind, const DeclarationNameInfo &DirName,
6034     OpenMPDirectiveKind CancelRegion, ArrayRef<OMPClause *> Clauses,
6035     Stmt *AStmt, SourceLocation StartLoc, SourceLocation EndLoc) {
6036   StmtResult Res = StmtError();
6037   OpenMPBindClauseKind BindKind = OMPC_BIND_unknown;
6038   if (const OMPBindClause *BC =
6039           OMPExecutableDirective::getSingleClause<OMPBindClause>(Clauses))
6040     BindKind = BC->getBindKind();
6041   // First check CancelRegion which is then used in checkNestingOfRegions.
6042   if (checkCancelRegion(*this, Kind, CancelRegion, StartLoc) ||
6043       checkNestingOfRegions(*this, DSAStack, Kind, DirName, CancelRegion,
6044                             BindKind, StartLoc))
6045     return StmtError();
6046 
6047   llvm::SmallVector<OMPClause *, 8> ClausesWithImplicit;
6048   VarsWithInheritedDSAType VarsWithInheritedDSA;
6049   bool ErrorFound = false;
6050   ClausesWithImplicit.append(Clauses.begin(), Clauses.end());
6051   if (AStmt && !CurContext->isDependentContext() && Kind != OMPD_atomic &&
6052       Kind != OMPD_critical && Kind != OMPD_section && Kind != OMPD_master &&
6053       Kind != OMPD_masked && !isOpenMPLoopTransformationDirective(Kind)) {
6054     assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
6055 
6056     // Check default data sharing attributes for referenced variables.
6057     DSAAttrChecker DSAChecker(DSAStack, *this, cast<CapturedStmt>(AStmt));
6058     int ThisCaptureLevel = getOpenMPCaptureLevels(Kind);
6059     Stmt *S = AStmt;
6060     while (--ThisCaptureLevel >= 0)
6061       S = cast<CapturedStmt>(S)->getCapturedStmt();
6062     DSAChecker.Visit(S);
6063     if (!isOpenMPTargetDataManagementDirective(Kind) &&
6064         !isOpenMPTaskingDirective(Kind)) {
6065       // Visit subcaptures to generate implicit clauses for captured vars.
6066       auto *CS = cast<CapturedStmt>(AStmt);
6067       SmallVector<OpenMPDirectiveKind, 4> CaptureRegions;
6068       getOpenMPCaptureRegions(CaptureRegions, Kind);
6069       // Ignore outer tasking regions for target directives.
6070       if (CaptureRegions.size() > 1 && CaptureRegions.front() == OMPD_task)
6071         CS = cast<CapturedStmt>(CS->getCapturedStmt());
6072       DSAChecker.visitSubCaptures(CS);
6073     }
6074     if (DSAChecker.isErrorFound())
6075       return StmtError();
6076     // Generate list of implicitly defined firstprivate variables.
6077     VarsWithInheritedDSA = DSAChecker.getVarsWithInheritedDSA();
6078 
6079     SmallVector<Expr *, 4> ImplicitFirstprivates(
6080         DSAChecker.getImplicitFirstprivate().begin(),
6081         DSAChecker.getImplicitFirstprivate().end());
6082     SmallVector<Expr *, 4> ImplicitPrivates(
6083         DSAChecker.getImplicitPrivate().begin(),
6084         DSAChecker.getImplicitPrivate().end());
6085     const unsigned DefaultmapKindNum = OMPC_DEFAULTMAP_pointer + 1;
6086     SmallVector<Expr *, 4> ImplicitMaps[DefaultmapKindNum][OMPC_MAP_delete];
6087     SmallVector<OpenMPMapModifierKind, NumberOfOMPMapClauseModifiers>
6088         ImplicitMapModifiers[DefaultmapKindNum];
6089     SmallVector<SourceLocation, NumberOfOMPMapClauseModifiers>
6090         ImplicitMapModifiersLoc[DefaultmapKindNum];
6091     // Get the original location of present modifier from Defaultmap clause.
6092     SourceLocation PresentModifierLocs[DefaultmapKindNum];
6093     for (OMPClause *C : Clauses) {
6094       if (auto *DMC = dyn_cast<OMPDefaultmapClause>(C))
6095         if (DMC->getDefaultmapModifier() == OMPC_DEFAULTMAP_MODIFIER_present)
6096           PresentModifierLocs[DMC->getDefaultmapKind()] =
6097               DMC->getDefaultmapModifierLoc();
6098     }
6099     for (unsigned VC = 0; VC < DefaultmapKindNum; ++VC) {
6100       auto Kind = static_cast<OpenMPDefaultmapClauseKind>(VC);
6101       for (unsigned I = 0; I < OMPC_MAP_delete; ++I) {
6102         ArrayRef<Expr *> ImplicitMap = DSAChecker.getImplicitMap(
6103             Kind, static_cast<OpenMPMapClauseKind>(I));
6104         ImplicitMaps[VC][I].append(ImplicitMap.begin(), ImplicitMap.end());
6105       }
6106       ArrayRef<OpenMPMapModifierKind> ImplicitModifier =
6107           DSAChecker.getImplicitMapModifier(Kind);
6108       ImplicitMapModifiers[VC].append(ImplicitModifier.begin(),
6109                                       ImplicitModifier.end());
6110       std::fill_n(std::back_inserter(ImplicitMapModifiersLoc[VC]),
6111                   ImplicitModifier.size(), PresentModifierLocs[VC]);
6112     }
6113     // Mark taskgroup task_reduction descriptors as implicitly firstprivate.
6114     for (OMPClause *C : Clauses) {
6115       if (auto *IRC = dyn_cast<OMPInReductionClause>(C)) {
6116         for (Expr *E : IRC->taskgroup_descriptors())
6117           if (E)
6118             ImplicitFirstprivates.emplace_back(E);
6119       }
6120       // OpenMP 5.0, 2.10.1 task Construct
6121       // [detach clause]... The event-handle will be considered as if it was
6122       // specified on a firstprivate clause.
6123       if (auto *DC = dyn_cast<OMPDetachClause>(C))
6124         ImplicitFirstprivates.push_back(DC->getEventHandler());
6125     }
6126     if (!ImplicitFirstprivates.empty()) {
6127       if (OMPClause *Implicit = ActOnOpenMPFirstprivateClause(
6128               ImplicitFirstprivates, SourceLocation(), SourceLocation(),
6129               SourceLocation())) {
6130         ClausesWithImplicit.push_back(Implicit);
6131         ErrorFound = cast<OMPFirstprivateClause>(Implicit)->varlist_size() !=
6132                      ImplicitFirstprivates.size();
6133       } else {
6134         ErrorFound = true;
6135       }
6136     }
6137     if (!ImplicitPrivates.empty()) {
6138       if (OMPClause *Implicit =
6139               ActOnOpenMPPrivateClause(ImplicitPrivates, SourceLocation(),
6140                                        SourceLocation(), SourceLocation())) {
6141         ClausesWithImplicit.push_back(Implicit);
6142         ErrorFound = cast<OMPPrivateClause>(Implicit)->varlist_size() !=
6143                      ImplicitPrivates.size();
6144       } else {
6145         ErrorFound = true;
6146       }
6147     }
6148     // OpenMP 5.0 [2.19.7]
6149     // If a list item appears in a reduction, lastprivate or linear
6150     // clause on a combined target construct then it is treated as
6151     // if it also appears in a map clause with a map-type of tofrom
6152     if (getLangOpts().OpenMP >= 50 && Kind != OMPD_target &&
6153         isOpenMPTargetExecutionDirective(Kind)) {
6154       SmallVector<Expr *, 4> ImplicitExprs;
6155       for (OMPClause *C : Clauses) {
6156         if (auto *RC = dyn_cast<OMPReductionClause>(C))
6157           for (Expr *E : RC->varlists())
6158             if (!isa<DeclRefExpr>(E->IgnoreParenImpCasts()))
6159               ImplicitExprs.emplace_back(E);
6160       }
6161       if (!ImplicitExprs.empty()) {
6162         ArrayRef<Expr *> Exprs = ImplicitExprs;
6163         CXXScopeSpec MapperIdScopeSpec;
6164         DeclarationNameInfo MapperId;
6165         if (OMPClause *Implicit = ActOnOpenMPMapClause(
6166                 OMPC_MAP_MODIFIER_unknown, SourceLocation(), MapperIdScopeSpec,
6167                 MapperId, OMPC_MAP_tofrom,
6168                 /*IsMapTypeImplicit=*/true, SourceLocation(), SourceLocation(),
6169                 Exprs, OMPVarListLocTy(), /*NoDiagnose=*/true))
6170           ClausesWithImplicit.emplace_back(Implicit);
6171       }
6172     }
6173     for (unsigned I = 0, E = DefaultmapKindNum; I < E; ++I) {
6174       int ClauseKindCnt = -1;
6175       for (ArrayRef<Expr *> ImplicitMap : ImplicitMaps[I]) {
6176         ++ClauseKindCnt;
6177         if (ImplicitMap.empty())
6178           continue;
6179         CXXScopeSpec MapperIdScopeSpec;
6180         DeclarationNameInfo MapperId;
6181         auto Kind = static_cast<OpenMPMapClauseKind>(ClauseKindCnt);
6182         if (OMPClause *Implicit = ActOnOpenMPMapClause(
6183                 ImplicitMapModifiers[I], ImplicitMapModifiersLoc[I],
6184                 MapperIdScopeSpec, MapperId, Kind, /*IsMapTypeImplicit=*/true,
6185                 SourceLocation(), SourceLocation(), ImplicitMap,
6186                 OMPVarListLocTy())) {
6187           ClausesWithImplicit.emplace_back(Implicit);
6188           ErrorFound |= cast<OMPMapClause>(Implicit)->varlist_size() !=
6189                         ImplicitMap.size();
6190         } else {
6191           ErrorFound = true;
6192         }
6193       }
6194     }
6195     // Build expressions for implicit maps of data members with 'default'
6196     // mappers.
6197     if (LangOpts.OpenMP >= 50)
6198       processImplicitMapsWithDefaultMappers(*this, DSAStack,
6199                                             ClausesWithImplicit);
6200   }
6201 
6202   llvm::SmallVector<OpenMPDirectiveKind, 4> AllowedNameModifiers;
6203   switch (Kind) {
6204   case OMPD_parallel:
6205     Res = ActOnOpenMPParallelDirective(ClausesWithImplicit, AStmt, StartLoc,
6206                                        EndLoc);
6207     AllowedNameModifiers.push_back(OMPD_parallel);
6208     break;
6209   case OMPD_simd:
6210     Res = ActOnOpenMPSimdDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc,
6211                                    VarsWithInheritedDSA);
6212     if (LangOpts.OpenMP >= 50)
6213       AllowedNameModifiers.push_back(OMPD_simd);
6214     break;
6215   case OMPD_tile:
6216     Res =
6217         ActOnOpenMPTileDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc);
6218     break;
6219   case OMPD_unroll:
6220     Res = ActOnOpenMPUnrollDirective(ClausesWithImplicit, AStmt, StartLoc,
6221                                      EndLoc);
6222     break;
6223   case OMPD_for:
6224     Res = ActOnOpenMPForDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc,
6225                                   VarsWithInheritedDSA);
6226     break;
6227   case OMPD_for_simd:
6228     Res = ActOnOpenMPForSimdDirective(ClausesWithImplicit, AStmt, StartLoc,
6229                                       EndLoc, VarsWithInheritedDSA);
6230     if (LangOpts.OpenMP >= 50)
6231       AllowedNameModifiers.push_back(OMPD_simd);
6232     break;
6233   case OMPD_sections:
6234     Res = ActOnOpenMPSectionsDirective(ClausesWithImplicit, AStmt, StartLoc,
6235                                        EndLoc);
6236     break;
6237   case OMPD_section:
6238     assert(ClausesWithImplicit.empty() &&
6239            "No clauses are allowed for 'omp section' directive");
6240     Res = ActOnOpenMPSectionDirective(AStmt, StartLoc, EndLoc);
6241     break;
6242   case OMPD_single:
6243     Res = ActOnOpenMPSingleDirective(ClausesWithImplicit, AStmt, StartLoc,
6244                                      EndLoc);
6245     break;
6246   case OMPD_master:
6247     assert(ClausesWithImplicit.empty() &&
6248            "No clauses are allowed for 'omp master' directive");
6249     Res = ActOnOpenMPMasterDirective(AStmt, StartLoc, EndLoc);
6250     break;
6251   case OMPD_masked:
6252     Res = ActOnOpenMPMaskedDirective(ClausesWithImplicit, AStmt, StartLoc,
6253                                      EndLoc);
6254     break;
6255   case OMPD_critical:
6256     Res = ActOnOpenMPCriticalDirective(DirName, ClausesWithImplicit, AStmt,
6257                                        StartLoc, EndLoc);
6258     break;
6259   case OMPD_parallel_for:
6260     Res = ActOnOpenMPParallelForDirective(ClausesWithImplicit, AStmt, StartLoc,
6261                                           EndLoc, VarsWithInheritedDSA);
6262     AllowedNameModifiers.push_back(OMPD_parallel);
6263     break;
6264   case OMPD_parallel_for_simd:
6265     Res = ActOnOpenMPParallelForSimdDirective(
6266         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6267     AllowedNameModifiers.push_back(OMPD_parallel);
6268     if (LangOpts.OpenMP >= 50)
6269       AllowedNameModifiers.push_back(OMPD_simd);
6270     break;
6271   case OMPD_parallel_master:
6272     Res = ActOnOpenMPParallelMasterDirective(ClausesWithImplicit, AStmt,
6273                                              StartLoc, EndLoc);
6274     AllowedNameModifiers.push_back(OMPD_parallel);
6275     break;
6276   case OMPD_parallel_masked:
6277     Res = ActOnOpenMPParallelMaskedDirective(ClausesWithImplicit, AStmt,
6278                                              StartLoc, EndLoc);
6279     AllowedNameModifiers.push_back(OMPD_parallel);
6280     break;
6281   case OMPD_parallel_sections:
6282     Res = ActOnOpenMPParallelSectionsDirective(ClausesWithImplicit, AStmt,
6283                                                StartLoc, EndLoc);
6284     AllowedNameModifiers.push_back(OMPD_parallel);
6285     break;
6286   case OMPD_task:
6287     Res =
6288         ActOnOpenMPTaskDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc);
6289     AllowedNameModifiers.push_back(OMPD_task);
6290     break;
6291   case OMPD_taskyield:
6292     assert(ClausesWithImplicit.empty() &&
6293            "No clauses are allowed for 'omp taskyield' directive");
6294     assert(AStmt == nullptr &&
6295            "No associated statement allowed for 'omp taskyield' directive");
6296     Res = ActOnOpenMPTaskyieldDirective(StartLoc, EndLoc);
6297     break;
6298   case OMPD_barrier:
6299     assert(ClausesWithImplicit.empty() &&
6300            "No clauses are allowed for 'omp barrier' directive");
6301     assert(AStmt == nullptr &&
6302            "No associated statement allowed for 'omp barrier' directive");
6303     Res = ActOnOpenMPBarrierDirective(StartLoc, EndLoc);
6304     break;
6305   case OMPD_taskwait:
6306     assert(AStmt == nullptr &&
6307            "No associated statement allowed for 'omp taskwait' directive");
6308     Res = ActOnOpenMPTaskwaitDirective(ClausesWithImplicit, StartLoc, EndLoc);
6309     break;
6310   case OMPD_taskgroup:
6311     Res = ActOnOpenMPTaskgroupDirective(ClausesWithImplicit, AStmt, StartLoc,
6312                                         EndLoc);
6313     break;
6314   case OMPD_flush:
6315     assert(AStmt == nullptr &&
6316            "No associated statement allowed for 'omp flush' directive");
6317     Res = ActOnOpenMPFlushDirective(ClausesWithImplicit, StartLoc, EndLoc);
6318     break;
6319   case OMPD_depobj:
6320     assert(AStmt == nullptr &&
6321            "No associated statement allowed for 'omp depobj' directive");
6322     Res = ActOnOpenMPDepobjDirective(ClausesWithImplicit, StartLoc, EndLoc);
6323     break;
6324   case OMPD_scan:
6325     assert(AStmt == nullptr &&
6326            "No associated statement allowed for 'omp scan' directive");
6327     Res = ActOnOpenMPScanDirective(ClausesWithImplicit, StartLoc, EndLoc);
6328     break;
6329   case OMPD_ordered:
6330     Res = ActOnOpenMPOrderedDirective(ClausesWithImplicit, AStmt, StartLoc,
6331                                       EndLoc);
6332     break;
6333   case OMPD_atomic:
6334     Res = ActOnOpenMPAtomicDirective(ClausesWithImplicit, AStmt, StartLoc,
6335                                      EndLoc);
6336     break;
6337   case OMPD_teams:
6338     Res =
6339         ActOnOpenMPTeamsDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc);
6340     break;
6341   case OMPD_target:
6342     Res = ActOnOpenMPTargetDirective(ClausesWithImplicit, AStmt, StartLoc,
6343                                      EndLoc);
6344     AllowedNameModifiers.push_back(OMPD_target);
6345     break;
6346   case OMPD_target_parallel:
6347     Res = ActOnOpenMPTargetParallelDirective(ClausesWithImplicit, AStmt,
6348                                              StartLoc, EndLoc);
6349     AllowedNameModifiers.push_back(OMPD_target);
6350     AllowedNameModifiers.push_back(OMPD_parallel);
6351     break;
6352   case OMPD_target_parallel_for:
6353     Res = ActOnOpenMPTargetParallelForDirective(
6354         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6355     AllowedNameModifiers.push_back(OMPD_target);
6356     AllowedNameModifiers.push_back(OMPD_parallel);
6357     break;
6358   case OMPD_cancellation_point:
6359     assert(ClausesWithImplicit.empty() &&
6360            "No clauses are allowed for 'omp cancellation point' directive");
6361     assert(AStmt == nullptr && "No associated statement allowed for 'omp "
6362                                "cancellation point' directive");
6363     Res = ActOnOpenMPCancellationPointDirective(StartLoc, EndLoc, CancelRegion);
6364     break;
6365   case OMPD_cancel:
6366     assert(AStmt == nullptr &&
6367            "No associated statement allowed for 'omp cancel' directive");
6368     Res = ActOnOpenMPCancelDirective(ClausesWithImplicit, StartLoc, EndLoc,
6369                                      CancelRegion);
6370     AllowedNameModifiers.push_back(OMPD_cancel);
6371     break;
6372   case OMPD_target_data:
6373     Res = ActOnOpenMPTargetDataDirective(ClausesWithImplicit, AStmt, StartLoc,
6374                                          EndLoc);
6375     AllowedNameModifiers.push_back(OMPD_target_data);
6376     break;
6377   case OMPD_target_enter_data:
6378     Res = ActOnOpenMPTargetEnterDataDirective(ClausesWithImplicit, StartLoc,
6379                                               EndLoc, AStmt);
6380     AllowedNameModifiers.push_back(OMPD_target_enter_data);
6381     break;
6382   case OMPD_target_exit_data:
6383     Res = ActOnOpenMPTargetExitDataDirective(ClausesWithImplicit, StartLoc,
6384                                              EndLoc, AStmt);
6385     AllowedNameModifiers.push_back(OMPD_target_exit_data);
6386     break;
6387   case OMPD_taskloop:
6388     Res = ActOnOpenMPTaskLoopDirective(ClausesWithImplicit, AStmt, StartLoc,
6389                                        EndLoc, VarsWithInheritedDSA);
6390     AllowedNameModifiers.push_back(OMPD_taskloop);
6391     break;
6392   case OMPD_taskloop_simd:
6393     Res = ActOnOpenMPTaskLoopSimdDirective(ClausesWithImplicit, AStmt, StartLoc,
6394                                            EndLoc, VarsWithInheritedDSA);
6395     AllowedNameModifiers.push_back(OMPD_taskloop);
6396     if (LangOpts.OpenMP >= 50)
6397       AllowedNameModifiers.push_back(OMPD_simd);
6398     break;
6399   case OMPD_master_taskloop:
6400     Res = ActOnOpenMPMasterTaskLoopDirective(
6401         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6402     AllowedNameModifiers.push_back(OMPD_taskloop);
6403     break;
6404   case OMPD_masked_taskloop:
6405     Res = ActOnOpenMPMaskedTaskLoopDirective(
6406         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6407     AllowedNameModifiers.push_back(OMPD_taskloop);
6408     break;
6409   case OMPD_master_taskloop_simd:
6410     Res = ActOnOpenMPMasterTaskLoopSimdDirective(
6411         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6412     AllowedNameModifiers.push_back(OMPD_taskloop);
6413     if (LangOpts.OpenMP >= 50)
6414       AllowedNameModifiers.push_back(OMPD_simd);
6415     break;
6416   case OMPD_masked_taskloop_simd:
6417     Res = ActOnOpenMPMaskedTaskLoopSimdDirective(
6418         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6419     if (LangOpts.OpenMP >= 51) {
6420       AllowedNameModifiers.push_back(OMPD_taskloop);
6421       AllowedNameModifiers.push_back(OMPD_simd);
6422     }
6423     break;
6424   case OMPD_parallel_master_taskloop:
6425     Res = ActOnOpenMPParallelMasterTaskLoopDirective(
6426         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6427     AllowedNameModifiers.push_back(OMPD_taskloop);
6428     AllowedNameModifiers.push_back(OMPD_parallel);
6429     break;
6430   case OMPD_parallel_masked_taskloop:
6431     Res = ActOnOpenMPParallelMaskedTaskLoopDirective(
6432         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6433     if (LangOpts.OpenMP >= 51) {
6434       AllowedNameModifiers.push_back(OMPD_taskloop);
6435       AllowedNameModifiers.push_back(OMPD_parallel);
6436     }
6437     break;
6438   case OMPD_parallel_master_taskloop_simd:
6439     Res = ActOnOpenMPParallelMasterTaskLoopSimdDirective(
6440         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6441     AllowedNameModifiers.push_back(OMPD_taskloop);
6442     AllowedNameModifiers.push_back(OMPD_parallel);
6443     if (LangOpts.OpenMP >= 50)
6444       AllowedNameModifiers.push_back(OMPD_simd);
6445     break;
6446   case OMPD_parallel_masked_taskloop_simd:
6447     Res = ActOnOpenMPParallelMaskedTaskLoopSimdDirective(
6448         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6449     if (LangOpts.OpenMP >= 51) {
6450       AllowedNameModifiers.push_back(OMPD_taskloop);
6451       AllowedNameModifiers.push_back(OMPD_parallel);
6452       AllowedNameModifiers.push_back(OMPD_simd);
6453     }
6454     break;
6455   case OMPD_distribute:
6456     Res = ActOnOpenMPDistributeDirective(ClausesWithImplicit, AStmt, StartLoc,
6457                                          EndLoc, VarsWithInheritedDSA);
6458     break;
6459   case OMPD_target_update:
6460     Res = ActOnOpenMPTargetUpdateDirective(ClausesWithImplicit, StartLoc,
6461                                            EndLoc, AStmt);
6462     AllowedNameModifiers.push_back(OMPD_target_update);
6463     break;
6464   case OMPD_distribute_parallel_for:
6465     Res = ActOnOpenMPDistributeParallelForDirective(
6466         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6467     AllowedNameModifiers.push_back(OMPD_parallel);
6468     break;
6469   case OMPD_distribute_parallel_for_simd:
6470     Res = ActOnOpenMPDistributeParallelForSimdDirective(
6471         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6472     AllowedNameModifiers.push_back(OMPD_parallel);
6473     if (LangOpts.OpenMP >= 50)
6474       AllowedNameModifiers.push_back(OMPD_simd);
6475     break;
6476   case OMPD_distribute_simd:
6477     Res = ActOnOpenMPDistributeSimdDirective(
6478         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6479     if (LangOpts.OpenMP >= 50)
6480       AllowedNameModifiers.push_back(OMPD_simd);
6481     break;
6482   case OMPD_target_parallel_for_simd:
6483     Res = ActOnOpenMPTargetParallelForSimdDirective(
6484         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6485     AllowedNameModifiers.push_back(OMPD_target);
6486     AllowedNameModifiers.push_back(OMPD_parallel);
6487     if (LangOpts.OpenMP >= 50)
6488       AllowedNameModifiers.push_back(OMPD_simd);
6489     break;
6490   case OMPD_target_simd:
6491     Res = ActOnOpenMPTargetSimdDirective(ClausesWithImplicit, AStmt, StartLoc,
6492                                          EndLoc, VarsWithInheritedDSA);
6493     AllowedNameModifiers.push_back(OMPD_target);
6494     if (LangOpts.OpenMP >= 50)
6495       AllowedNameModifiers.push_back(OMPD_simd);
6496     break;
6497   case OMPD_teams_distribute:
6498     Res = ActOnOpenMPTeamsDistributeDirective(
6499         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6500     break;
6501   case OMPD_teams_distribute_simd:
6502     Res = ActOnOpenMPTeamsDistributeSimdDirective(
6503         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6504     if (LangOpts.OpenMP >= 50)
6505       AllowedNameModifiers.push_back(OMPD_simd);
6506     break;
6507   case OMPD_teams_distribute_parallel_for_simd:
6508     Res = ActOnOpenMPTeamsDistributeParallelForSimdDirective(
6509         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6510     AllowedNameModifiers.push_back(OMPD_parallel);
6511     if (LangOpts.OpenMP >= 50)
6512       AllowedNameModifiers.push_back(OMPD_simd);
6513     break;
6514   case OMPD_teams_distribute_parallel_for:
6515     Res = ActOnOpenMPTeamsDistributeParallelForDirective(
6516         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6517     AllowedNameModifiers.push_back(OMPD_parallel);
6518     break;
6519   case OMPD_target_teams:
6520     Res = ActOnOpenMPTargetTeamsDirective(ClausesWithImplicit, AStmt, StartLoc,
6521                                           EndLoc);
6522     AllowedNameModifiers.push_back(OMPD_target);
6523     break;
6524   case OMPD_target_teams_distribute:
6525     Res = ActOnOpenMPTargetTeamsDistributeDirective(
6526         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6527     AllowedNameModifiers.push_back(OMPD_target);
6528     break;
6529   case OMPD_target_teams_distribute_parallel_for:
6530     Res = ActOnOpenMPTargetTeamsDistributeParallelForDirective(
6531         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6532     AllowedNameModifiers.push_back(OMPD_target);
6533     AllowedNameModifiers.push_back(OMPD_parallel);
6534     break;
6535   case OMPD_target_teams_distribute_parallel_for_simd:
6536     Res = ActOnOpenMPTargetTeamsDistributeParallelForSimdDirective(
6537         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6538     AllowedNameModifiers.push_back(OMPD_target);
6539     AllowedNameModifiers.push_back(OMPD_parallel);
6540     if (LangOpts.OpenMP >= 50)
6541       AllowedNameModifiers.push_back(OMPD_simd);
6542     break;
6543   case OMPD_target_teams_distribute_simd:
6544     Res = ActOnOpenMPTargetTeamsDistributeSimdDirective(
6545         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6546     AllowedNameModifiers.push_back(OMPD_target);
6547     if (LangOpts.OpenMP >= 50)
6548       AllowedNameModifiers.push_back(OMPD_simd);
6549     break;
6550   case OMPD_interop:
6551     assert(AStmt == nullptr &&
6552            "No associated statement allowed for 'omp interop' directive");
6553     Res = ActOnOpenMPInteropDirective(ClausesWithImplicit, StartLoc, EndLoc);
6554     break;
6555   case OMPD_dispatch:
6556     Res = ActOnOpenMPDispatchDirective(ClausesWithImplicit, AStmt, StartLoc,
6557                                        EndLoc);
6558     break;
6559   case OMPD_loop:
6560     Res = ActOnOpenMPGenericLoopDirective(ClausesWithImplicit, AStmt, StartLoc,
6561                                           EndLoc, VarsWithInheritedDSA);
6562     break;
6563   case OMPD_teams_loop:
6564     Res = ActOnOpenMPTeamsGenericLoopDirective(
6565         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6566     break;
6567   case OMPD_target_teams_loop:
6568     Res = ActOnOpenMPTargetTeamsGenericLoopDirective(
6569         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6570     break;
6571   case OMPD_parallel_loop:
6572     Res = ActOnOpenMPParallelGenericLoopDirective(
6573         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6574     break;
6575   case OMPD_target_parallel_loop:
6576     Res = ActOnOpenMPTargetParallelGenericLoopDirective(
6577         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6578     break;
6579   case OMPD_declare_target:
6580   case OMPD_end_declare_target:
6581   case OMPD_threadprivate:
6582   case OMPD_allocate:
6583   case OMPD_declare_reduction:
6584   case OMPD_declare_mapper:
6585   case OMPD_declare_simd:
6586   case OMPD_requires:
6587   case OMPD_declare_variant:
6588   case OMPD_begin_declare_variant:
6589   case OMPD_end_declare_variant:
6590     llvm_unreachable("OpenMP Directive is not allowed");
6591   case OMPD_unknown:
6592   default:
6593     llvm_unreachable("Unknown OpenMP directive");
6594   }
6595 
6596   ErrorFound = Res.isInvalid() || ErrorFound;
6597 
6598   // Check variables in the clauses if default(none) or
6599   // default(firstprivate) was specified.
6600   if (DSAStack->getDefaultDSA() == DSA_none ||
6601       DSAStack->getDefaultDSA() == DSA_private ||
6602       DSAStack->getDefaultDSA() == DSA_firstprivate) {
6603     DSAAttrChecker DSAChecker(DSAStack, *this, nullptr);
6604     for (OMPClause *C : Clauses) {
6605       switch (C->getClauseKind()) {
6606       case OMPC_num_threads:
6607       case OMPC_dist_schedule:
6608         // Do not analyse if no parent teams directive.
6609         if (isOpenMPTeamsDirective(Kind))
6610           break;
6611         continue;
6612       case OMPC_if:
6613         if (isOpenMPTeamsDirective(Kind) &&
6614             cast<OMPIfClause>(C)->getNameModifier() != OMPD_target)
6615           break;
6616         if (isOpenMPParallelDirective(Kind) &&
6617             isOpenMPTaskLoopDirective(Kind) &&
6618             cast<OMPIfClause>(C)->getNameModifier() != OMPD_parallel)
6619           break;
6620         continue;
6621       case OMPC_schedule:
6622       case OMPC_detach:
6623         break;
6624       case OMPC_grainsize:
6625       case OMPC_num_tasks:
6626       case OMPC_final:
6627       case OMPC_priority:
6628       case OMPC_novariants:
6629       case OMPC_nocontext:
6630         // Do not analyze if no parent parallel directive.
6631         if (isOpenMPParallelDirective(Kind))
6632           break;
6633         continue;
6634       case OMPC_ordered:
6635       case OMPC_device:
6636       case OMPC_num_teams:
6637       case OMPC_thread_limit:
6638       case OMPC_hint:
6639       case OMPC_collapse:
6640       case OMPC_safelen:
6641       case OMPC_simdlen:
6642       case OMPC_sizes:
6643       case OMPC_default:
6644       case OMPC_proc_bind:
6645       case OMPC_private:
6646       case OMPC_firstprivate:
6647       case OMPC_lastprivate:
6648       case OMPC_shared:
6649       case OMPC_reduction:
6650       case OMPC_task_reduction:
6651       case OMPC_in_reduction:
6652       case OMPC_linear:
6653       case OMPC_aligned:
6654       case OMPC_copyin:
6655       case OMPC_copyprivate:
6656       case OMPC_nowait:
6657       case OMPC_untied:
6658       case OMPC_mergeable:
6659       case OMPC_allocate:
6660       case OMPC_read:
6661       case OMPC_write:
6662       case OMPC_update:
6663       case OMPC_capture:
6664       case OMPC_compare:
6665       case OMPC_seq_cst:
6666       case OMPC_acq_rel:
6667       case OMPC_acquire:
6668       case OMPC_release:
6669       case OMPC_relaxed:
6670       case OMPC_depend:
6671       case OMPC_threads:
6672       case OMPC_simd:
6673       case OMPC_map:
6674       case OMPC_nogroup:
6675       case OMPC_defaultmap:
6676       case OMPC_to:
6677       case OMPC_from:
6678       case OMPC_use_device_ptr:
6679       case OMPC_use_device_addr:
6680       case OMPC_is_device_ptr:
6681       case OMPC_has_device_addr:
6682       case OMPC_nontemporal:
6683       case OMPC_order:
6684       case OMPC_destroy:
6685       case OMPC_inclusive:
6686       case OMPC_exclusive:
6687       case OMPC_uses_allocators:
6688       case OMPC_affinity:
6689       case OMPC_bind:
6690       case OMPC_filter:
6691         continue;
6692       case OMPC_allocator:
6693       case OMPC_flush:
6694       case OMPC_depobj:
6695       case OMPC_threadprivate:
6696       case OMPC_uniform:
6697       case OMPC_unknown:
6698       case OMPC_unified_address:
6699       case OMPC_unified_shared_memory:
6700       case OMPC_reverse_offload:
6701       case OMPC_dynamic_allocators:
6702       case OMPC_atomic_default_mem_order:
6703       case OMPC_device_type:
6704       case OMPC_match:
6705       case OMPC_when:
6706       default:
6707         llvm_unreachable("Unexpected clause");
6708       }
6709       for (Stmt *CC : C->children()) {
6710         if (CC)
6711           DSAChecker.Visit(CC);
6712       }
6713     }
6714     for (const auto &P : DSAChecker.getVarsWithInheritedDSA())
6715       VarsWithInheritedDSA[P.getFirst()] = P.getSecond();
6716   }
6717   for (const auto &P : VarsWithInheritedDSA) {
6718     if (P.getFirst()->isImplicit() || isa<OMPCapturedExprDecl>(P.getFirst()))
6719       continue;
6720     ErrorFound = true;
6721     if (DSAStack->getDefaultDSA() == DSA_none ||
6722         DSAStack->getDefaultDSA() == DSA_private ||
6723         DSAStack->getDefaultDSA() == DSA_firstprivate) {
6724       Diag(P.second->getExprLoc(), diag::err_omp_no_dsa_for_variable)
6725           << P.first << P.second->getSourceRange();
6726       Diag(DSAStack->getDefaultDSALocation(), diag::note_omp_default_dsa_none);
6727     } else if (getLangOpts().OpenMP >= 50) {
6728       Diag(P.second->getExprLoc(),
6729            diag::err_omp_defaultmap_no_attr_for_variable)
6730           << P.first << P.second->getSourceRange();
6731       Diag(DSAStack->getDefaultDSALocation(),
6732            diag::note_omp_defaultmap_attr_none);
6733     }
6734   }
6735 
6736   if (!AllowedNameModifiers.empty())
6737     ErrorFound = checkIfClauses(*this, Kind, Clauses, AllowedNameModifiers) ||
6738                  ErrorFound;
6739 
6740   if (ErrorFound)
6741     return StmtError();
6742 
6743   if (!CurContext->isDependentContext() &&
6744       isOpenMPTargetExecutionDirective(Kind) &&
6745       !(DSAStack->hasRequiresDeclWithClause<OMPUnifiedSharedMemoryClause>() ||
6746         DSAStack->hasRequiresDeclWithClause<OMPUnifiedAddressClause>() ||
6747         DSAStack->hasRequiresDeclWithClause<OMPReverseOffloadClause>() ||
6748         DSAStack->hasRequiresDeclWithClause<OMPDynamicAllocatorsClause>())) {
6749     // Register target to DSA Stack.
6750     DSAStack->addTargetDirLocation(StartLoc);
6751   }
6752 
6753   return Res;
6754 }
6755 
6756 Sema::DeclGroupPtrTy Sema::ActOnOpenMPDeclareSimdDirective(
6757     DeclGroupPtrTy DG, OMPDeclareSimdDeclAttr::BranchStateTy BS, Expr *Simdlen,
6758     ArrayRef<Expr *> Uniforms, ArrayRef<Expr *> Aligneds,
6759     ArrayRef<Expr *> Alignments, ArrayRef<Expr *> Linears,
6760     ArrayRef<unsigned> LinModifiers, ArrayRef<Expr *> Steps, SourceRange SR) {
6761   assert(Aligneds.size() == Alignments.size());
6762   assert(Linears.size() == LinModifiers.size());
6763   assert(Linears.size() == Steps.size());
6764   if (!DG || DG.get().isNull())
6765     return DeclGroupPtrTy();
6766 
6767   const int SimdId = 0;
6768   if (!DG.get().isSingleDecl()) {
6769     Diag(SR.getBegin(), diag::err_omp_single_decl_in_declare_simd_variant)
6770         << SimdId;
6771     return DG;
6772   }
6773   Decl *ADecl = DG.get().getSingleDecl();
6774   if (auto *FTD = dyn_cast<FunctionTemplateDecl>(ADecl))
6775     ADecl = FTD->getTemplatedDecl();
6776 
6777   auto *FD = dyn_cast<FunctionDecl>(ADecl);
6778   if (!FD) {
6779     Diag(ADecl->getLocation(), diag::err_omp_function_expected) << SimdId;
6780     return DeclGroupPtrTy();
6781   }
6782 
6783   // OpenMP [2.8.2, declare simd construct, Description]
6784   // The parameter of the simdlen clause must be a constant positive integer
6785   // expression.
6786   ExprResult SL;
6787   if (Simdlen)
6788     SL = VerifyPositiveIntegerConstantInClause(Simdlen, OMPC_simdlen);
6789   // OpenMP [2.8.2, declare simd construct, Description]
6790   // The special this pointer can be used as if was one of the arguments to the
6791   // function in any of the linear, aligned, or uniform clauses.
6792   // The uniform clause declares one or more arguments to have an invariant
6793   // value for all concurrent invocations of the function in the execution of a
6794   // single SIMD loop.
6795   llvm::DenseMap<const Decl *, const Expr *> UniformedArgs;
6796   const Expr *UniformedLinearThis = nullptr;
6797   for (const Expr *E : Uniforms) {
6798     E = E->IgnoreParenImpCasts();
6799     if (const auto *DRE = dyn_cast<DeclRefExpr>(E))
6800       if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl()))
6801         if (FD->getNumParams() > PVD->getFunctionScopeIndex() &&
6802             FD->getParamDecl(PVD->getFunctionScopeIndex())
6803                     ->getCanonicalDecl() == PVD->getCanonicalDecl()) {
6804           UniformedArgs.try_emplace(PVD->getCanonicalDecl(), E);
6805           continue;
6806         }
6807     if (isa<CXXThisExpr>(E)) {
6808       UniformedLinearThis = E;
6809       continue;
6810     }
6811     Diag(E->getExprLoc(), diag::err_omp_param_or_this_in_clause)
6812         << FD->getDeclName() << (isa<CXXMethodDecl>(ADecl) ? 1 : 0);
6813   }
6814   // OpenMP [2.8.2, declare simd construct, Description]
6815   // The aligned clause declares that the object to which each list item points
6816   // is aligned to the number of bytes expressed in the optional parameter of
6817   // the aligned clause.
6818   // The special this pointer can be used as if was one of the arguments to the
6819   // function in any of the linear, aligned, or uniform clauses.
6820   // The type of list items appearing in the aligned clause must be array,
6821   // pointer, reference to array, or reference to pointer.
6822   llvm::DenseMap<const Decl *, const Expr *> AlignedArgs;
6823   const Expr *AlignedThis = nullptr;
6824   for (const Expr *E : Aligneds) {
6825     E = E->IgnoreParenImpCasts();
6826     if (const auto *DRE = dyn_cast<DeclRefExpr>(E))
6827       if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl())) {
6828         const VarDecl *CanonPVD = PVD->getCanonicalDecl();
6829         if (FD->getNumParams() > PVD->getFunctionScopeIndex() &&
6830             FD->getParamDecl(PVD->getFunctionScopeIndex())
6831                     ->getCanonicalDecl() == CanonPVD) {
6832           // OpenMP  [2.8.1, simd construct, Restrictions]
6833           // A list-item cannot appear in more than one aligned clause.
6834           if (AlignedArgs.count(CanonPVD) > 0) {
6835             Diag(E->getExprLoc(), diag::err_omp_used_in_clause_twice)
6836                 << 1 << getOpenMPClauseName(OMPC_aligned)
6837                 << E->getSourceRange();
6838             Diag(AlignedArgs[CanonPVD]->getExprLoc(),
6839                  diag::note_omp_explicit_dsa)
6840                 << getOpenMPClauseName(OMPC_aligned);
6841             continue;
6842           }
6843           AlignedArgs[CanonPVD] = E;
6844           QualType QTy = PVD->getType()
6845                              .getNonReferenceType()
6846                              .getUnqualifiedType()
6847                              .getCanonicalType();
6848           const Type *Ty = QTy.getTypePtrOrNull();
6849           if (!Ty || (!Ty->isArrayType() && !Ty->isPointerType())) {
6850             Diag(E->getExprLoc(), diag::err_omp_aligned_expected_array_or_ptr)
6851                 << QTy << getLangOpts().CPlusPlus << E->getSourceRange();
6852             Diag(PVD->getLocation(), diag::note_previous_decl) << PVD;
6853           }
6854           continue;
6855         }
6856       }
6857     if (isa<CXXThisExpr>(E)) {
6858       if (AlignedThis) {
6859         Diag(E->getExprLoc(), diag::err_omp_used_in_clause_twice)
6860             << 2 << getOpenMPClauseName(OMPC_aligned) << E->getSourceRange();
6861         Diag(AlignedThis->getExprLoc(), diag::note_omp_explicit_dsa)
6862             << getOpenMPClauseName(OMPC_aligned);
6863       }
6864       AlignedThis = E;
6865       continue;
6866     }
6867     Diag(E->getExprLoc(), diag::err_omp_param_or_this_in_clause)
6868         << FD->getDeclName() << (isa<CXXMethodDecl>(ADecl) ? 1 : 0);
6869   }
6870   // The optional parameter of the aligned clause, alignment, must be a constant
6871   // positive integer expression. If no optional parameter is specified,
6872   // implementation-defined default alignments for SIMD instructions on the
6873   // target platforms are assumed.
6874   SmallVector<const Expr *, 4> NewAligns;
6875   for (Expr *E : Alignments) {
6876     ExprResult Align;
6877     if (E)
6878       Align = VerifyPositiveIntegerConstantInClause(E, OMPC_aligned);
6879     NewAligns.push_back(Align.get());
6880   }
6881   // OpenMP [2.8.2, declare simd construct, Description]
6882   // The linear clause declares one or more list items to be private to a SIMD
6883   // lane and to have a linear relationship with respect to the iteration space
6884   // of a loop.
6885   // The special this pointer can be used as if was one of the arguments to the
6886   // function in any of the linear, aligned, or uniform clauses.
6887   // When a linear-step expression is specified in a linear clause it must be
6888   // either a constant integer expression or an integer-typed parameter that is
6889   // specified in a uniform clause on the directive.
6890   llvm::DenseMap<const Decl *, const Expr *> LinearArgs;
6891   const bool IsUniformedThis = UniformedLinearThis != nullptr;
6892   auto MI = LinModifiers.begin();
6893   for (const Expr *E : Linears) {
6894     auto LinKind = static_cast<OpenMPLinearClauseKind>(*MI);
6895     ++MI;
6896     E = E->IgnoreParenImpCasts();
6897     if (const auto *DRE = dyn_cast<DeclRefExpr>(E))
6898       if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl())) {
6899         const VarDecl *CanonPVD = PVD->getCanonicalDecl();
6900         if (FD->getNumParams() > PVD->getFunctionScopeIndex() &&
6901             FD->getParamDecl(PVD->getFunctionScopeIndex())
6902                     ->getCanonicalDecl() == CanonPVD) {
6903           // OpenMP  [2.15.3.7, linear Clause, Restrictions]
6904           // A list-item cannot appear in more than one linear clause.
6905           if (LinearArgs.count(CanonPVD) > 0) {
6906             Diag(E->getExprLoc(), diag::err_omp_wrong_dsa)
6907                 << getOpenMPClauseName(OMPC_linear)
6908                 << getOpenMPClauseName(OMPC_linear) << E->getSourceRange();
6909             Diag(LinearArgs[CanonPVD]->getExprLoc(),
6910                  diag::note_omp_explicit_dsa)
6911                 << getOpenMPClauseName(OMPC_linear);
6912             continue;
6913           }
6914           // Each argument can appear in at most one uniform or linear clause.
6915           if (UniformedArgs.count(CanonPVD) > 0) {
6916             Diag(E->getExprLoc(), diag::err_omp_wrong_dsa)
6917                 << getOpenMPClauseName(OMPC_linear)
6918                 << getOpenMPClauseName(OMPC_uniform) << E->getSourceRange();
6919             Diag(UniformedArgs[CanonPVD]->getExprLoc(),
6920                  diag::note_omp_explicit_dsa)
6921                 << getOpenMPClauseName(OMPC_uniform);
6922             continue;
6923           }
6924           LinearArgs[CanonPVD] = E;
6925           if (E->isValueDependent() || E->isTypeDependent() ||
6926               E->isInstantiationDependent() ||
6927               E->containsUnexpandedParameterPack())
6928             continue;
6929           (void)CheckOpenMPLinearDecl(CanonPVD, E->getExprLoc(), LinKind,
6930                                       PVD->getOriginalType(),
6931                                       /*IsDeclareSimd=*/true);
6932           continue;
6933         }
6934       }
6935     if (isa<CXXThisExpr>(E)) {
6936       if (UniformedLinearThis) {
6937         Diag(E->getExprLoc(), diag::err_omp_wrong_dsa)
6938             << getOpenMPClauseName(OMPC_linear)
6939             << getOpenMPClauseName(IsUniformedThis ? OMPC_uniform : OMPC_linear)
6940             << E->getSourceRange();
6941         Diag(UniformedLinearThis->getExprLoc(), diag::note_omp_explicit_dsa)
6942             << getOpenMPClauseName(IsUniformedThis ? OMPC_uniform
6943                                                    : OMPC_linear);
6944         continue;
6945       }
6946       UniformedLinearThis = E;
6947       if (E->isValueDependent() || E->isTypeDependent() ||
6948           E->isInstantiationDependent() || E->containsUnexpandedParameterPack())
6949         continue;
6950       (void)CheckOpenMPLinearDecl(/*D=*/nullptr, E->getExprLoc(), LinKind,
6951                                   E->getType(), /*IsDeclareSimd=*/true);
6952       continue;
6953     }
6954     Diag(E->getExprLoc(), diag::err_omp_param_or_this_in_clause)
6955         << FD->getDeclName() << (isa<CXXMethodDecl>(ADecl) ? 1 : 0);
6956   }
6957   Expr *Step = nullptr;
6958   Expr *NewStep = nullptr;
6959   SmallVector<Expr *, 4> NewSteps;
6960   for (Expr *E : Steps) {
6961     // Skip the same step expression, it was checked already.
6962     if (Step == E || !E) {
6963       NewSteps.push_back(E ? NewStep : nullptr);
6964       continue;
6965     }
6966     Step = E;
6967     if (const auto *DRE = dyn_cast<DeclRefExpr>(Step))
6968       if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl())) {
6969         const VarDecl *CanonPVD = PVD->getCanonicalDecl();
6970         if (UniformedArgs.count(CanonPVD) == 0) {
6971           Diag(Step->getExprLoc(), diag::err_omp_expected_uniform_param)
6972               << Step->getSourceRange();
6973         } else if (E->isValueDependent() || E->isTypeDependent() ||
6974                    E->isInstantiationDependent() ||
6975                    E->containsUnexpandedParameterPack() ||
6976                    CanonPVD->getType()->hasIntegerRepresentation()) {
6977           NewSteps.push_back(Step);
6978         } else {
6979           Diag(Step->getExprLoc(), diag::err_omp_expected_int_param)
6980               << Step->getSourceRange();
6981         }
6982         continue;
6983       }
6984     NewStep = Step;
6985     if (Step && !Step->isValueDependent() && !Step->isTypeDependent() &&
6986         !Step->isInstantiationDependent() &&
6987         !Step->containsUnexpandedParameterPack()) {
6988       NewStep = PerformOpenMPImplicitIntegerConversion(Step->getExprLoc(), Step)
6989                     .get();
6990       if (NewStep)
6991         NewStep =
6992             VerifyIntegerConstantExpression(NewStep, /*FIXME*/ AllowFold).get();
6993     }
6994     NewSteps.push_back(NewStep);
6995   }
6996   auto *NewAttr = OMPDeclareSimdDeclAttr::CreateImplicit(
6997       Context, BS, SL.get(), const_cast<Expr **>(Uniforms.data()),
6998       Uniforms.size(), const_cast<Expr **>(Aligneds.data()), Aligneds.size(),
6999       const_cast<Expr **>(NewAligns.data()), NewAligns.size(),
7000       const_cast<Expr **>(Linears.data()), Linears.size(),
7001       const_cast<unsigned *>(LinModifiers.data()), LinModifiers.size(),
7002       NewSteps.data(), NewSteps.size(), SR);
7003   ADecl->addAttr(NewAttr);
7004   return DG;
7005 }
7006 
7007 static void setPrototype(Sema &S, FunctionDecl *FD, FunctionDecl *FDWithProto,
7008                          QualType NewType) {
7009   assert(NewType->isFunctionProtoType() &&
7010          "Expected function type with prototype.");
7011   assert(FD->getType()->isFunctionNoProtoType() &&
7012          "Expected function with type with no prototype.");
7013   assert(FDWithProto->getType()->isFunctionProtoType() &&
7014          "Expected function with prototype.");
7015   // Synthesize parameters with the same types.
7016   FD->setType(NewType);
7017   SmallVector<ParmVarDecl *, 16> Params;
7018   for (const ParmVarDecl *P : FDWithProto->parameters()) {
7019     auto *Param = ParmVarDecl::Create(S.getASTContext(), FD, SourceLocation(),
7020                                       SourceLocation(), nullptr, P->getType(),
7021                                       /*TInfo=*/nullptr, SC_None, nullptr);
7022     Param->setScopeInfo(0, Params.size());
7023     Param->setImplicit();
7024     Params.push_back(Param);
7025   }
7026 
7027   FD->setParams(Params);
7028 }
7029 
7030 void Sema::ActOnFinishedFunctionDefinitionInOpenMPAssumeScope(Decl *D) {
7031   if (D->isInvalidDecl())
7032     return;
7033   FunctionDecl *FD = nullptr;
7034   if (auto *UTemplDecl = dyn_cast<FunctionTemplateDecl>(D))
7035     FD = UTemplDecl->getTemplatedDecl();
7036   else
7037     FD = cast<FunctionDecl>(D);
7038   assert(FD && "Expected a function declaration!");
7039 
7040   // If we are instantiating templates we do *not* apply scoped assumptions but
7041   // only global ones. We apply scoped assumption to the template definition
7042   // though.
7043   if (!inTemplateInstantiation()) {
7044     for (AssumptionAttr *AA : OMPAssumeScoped)
7045       FD->addAttr(AA);
7046   }
7047   for (AssumptionAttr *AA : OMPAssumeGlobal)
7048     FD->addAttr(AA);
7049 }
7050 
7051 Sema::OMPDeclareVariantScope::OMPDeclareVariantScope(OMPTraitInfo &TI)
7052     : TI(&TI), NameSuffix(TI.getMangledName()) {}
7053 
7054 void Sema::ActOnStartOfFunctionDefinitionInOpenMPDeclareVariantScope(
7055     Scope *S, Declarator &D, MultiTemplateParamsArg TemplateParamLists,
7056     SmallVectorImpl<FunctionDecl *> &Bases) {
7057   if (!D.getIdentifier())
7058     return;
7059 
7060   OMPDeclareVariantScope &DVScope = OMPDeclareVariantScopes.back();
7061 
7062   // Template specialization is an extension, check if we do it.
7063   bool IsTemplated = !TemplateParamLists.empty();
7064   if (IsTemplated &
7065       !DVScope.TI->isExtensionActive(
7066           llvm::omp::TraitProperty::implementation_extension_allow_templates))
7067     return;
7068 
7069   IdentifierInfo *BaseII = D.getIdentifier();
7070   LookupResult Lookup(*this, DeclarationName(BaseII), D.getIdentifierLoc(),
7071                       LookupOrdinaryName);
7072   LookupParsedName(Lookup, S, &D.getCXXScopeSpec());
7073 
7074   TypeSourceInfo *TInfo = GetTypeForDeclarator(D, S);
7075   QualType FType = TInfo->getType();
7076 
7077   bool IsConstexpr =
7078       D.getDeclSpec().getConstexprSpecifier() == ConstexprSpecKind::Constexpr;
7079   bool IsConsteval =
7080       D.getDeclSpec().getConstexprSpecifier() == ConstexprSpecKind::Consteval;
7081 
7082   for (auto *Candidate : Lookup) {
7083     auto *CandidateDecl = Candidate->getUnderlyingDecl();
7084     FunctionDecl *UDecl = nullptr;
7085     if (IsTemplated && isa<FunctionTemplateDecl>(CandidateDecl)) {
7086       auto *FTD = cast<FunctionTemplateDecl>(CandidateDecl);
7087       if (FTD->getTemplateParameters()->size() == TemplateParamLists.size())
7088         UDecl = FTD->getTemplatedDecl();
7089     } else if (!IsTemplated)
7090       UDecl = dyn_cast<FunctionDecl>(CandidateDecl);
7091     if (!UDecl)
7092       continue;
7093 
7094     // Don't specialize constexpr/consteval functions with
7095     // non-constexpr/consteval functions.
7096     if (UDecl->isConstexpr() && !IsConstexpr)
7097       continue;
7098     if (UDecl->isConsteval() && !IsConsteval)
7099       continue;
7100 
7101     QualType UDeclTy = UDecl->getType();
7102     if (!UDeclTy->isDependentType()) {
7103       QualType NewType = Context.mergeFunctionTypes(
7104           FType, UDeclTy, /* OfBlockPointer */ false,
7105           /* Unqualified */ false, /* AllowCXX */ true);
7106       if (NewType.isNull())
7107         continue;
7108     }
7109 
7110     // Found a base!
7111     Bases.push_back(UDecl);
7112   }
7113 
7114   bool UseImplicitBase = !DVScope.TI->isExtensionActive(
7115       llvm::omp::TraitProperty::implementation_extension_disable_implicit_base);
7116   // If no base was found we create a declaration that we use as base.
7117   if (Bases.empty() && UseImplicitBase) {
7118     D.setFunctionDefinitionKind(FunctionDefinitionKind::Declaration);
7119     Decl *BaseD = HandleDeclarator(S, D, TemplateParamLists);
7120     BaseD->setImplicit(true);
7121     if (auto *BaseTemplD = dyn_cast<FunctionTemplateDecl>(BaseD))
7122       Bases.push_back(BaseTemplD->getTemplatedDecl());
7123     else
7124       Bases.push_back(cast<FunctionDecl>(BaseD));
7125   }
7126 
7127   std::string MangledName;
7128   MangledName += D.getIdentifier()->getName();
7129   MangledName += getOpenMPVariantManglingSeparatorStr();
7130   MangledName += DVScope.NameSuffix;
7131   IdentifierInfo &VariantII = Context.Idents.get(MangledName);
7132 
7133   VariantII.setMangledOpenMPVariantName(true);
7134   D.SetIdentifier(&VariantII, D.getBeginLoc());
7135 }
7136 
7137 void Sema::ActOnFinishedFunctionDefinitionInOpenMPDeclareVariantScope(
7138     Decl *D, SmallVectorImpl<FunctionDecl *> &Bases) {
7139   // Do not mark function as is used to prevent its emission if this is the
7140   // only place where it is used.
7141   EnterExpressionEvaluationContext Unevaluated(
7142       *this, Sema::ExpressionEvaluationContext::Unevaluated);
7143 
7144   FunctionDecl *FD = nullptr;
7145   if (auto *UTemplDecl = dyn_cast<FunctionTemplateDecl>(D))
7146     FD = UTemplDecl->getTemplatedDecl();
7147   else
7148     FD = cast<FunctionDecl>(D);
7149   auto *VariantFuncRef = DeclRefExpr::Create(
7150       Context, NestedNameSpecifierLoc(), SourceLocation(), FD,
7151       /* RefersToEnclosingVariableOrCapture */ false,
7152       /* NameLoc */ FD->getLocation(), FD->getType(),
7153       ExprValueKind::VK_PRValue);
7154 
7155   OMPDeclareVariantScope &DVScope = OMPDeclareVariantScopes.back();
7156   auto *OMPDeclareVariantA = OMPDeclareVariantAttr::CreateImplicit(
7157       Context, VariantFuncRef, DVScope.TI,
7158       /*NothingArgs=*/nullptr, /*NothingArgsSize=*/0,
7159       /*NeedDevicePtrArgs=*/nullptr, /*NeedDevicePtrArgsSize=*/0,
7160       /*AppendArgs=*/nullptr, /*AppendArgsSize=*/0);
7161   for (FunctionDecl *BaseFD : Bases)
7162     BaseFD->addAttr(OMPDeclareVariantA);
7163 }
7164 
7165 ExprResult Sema::ActOnOpenMPCall(ExprResult Call, Scope *Scope,
7166                                  SourceLocation LParenLoc,
7167                                  MultiExprArg ArgExprs,
7168                                  SourceLocation RParenLoc, Expr *ExecConfig) {
7169   // The common case is a regular call we do not want to specialize at all. Try
7170   // to make that case fast by bailing early.
7171   CallExpr *CE = dyn_cast<CallExpr>(Call.get());
7172   if (!CE)
7173     return Call;
7174 
7175   FunctionDecl *CalleeFnDecl = CE->getDirectCallee();
7176   if (!CalleeFnDecl)
7177     return Call;
7178 
7179   if (!CalleeFnDecl->hasAttr<OMPDeclareVariantAttr>())
7180     return Call;
7181 
7182   ASTContext &Context = getASTContext();
7183   std::function<void(StringRef)> DiagUnknownTrait = [this,
7184                                                      CE](StringRef ISATrait) {
7185     // TODO Track the selector locations in a way that is accessible here to
7186     // improve the diagnostic location.
7187     Diag(CE->getBeginLoc(), diag::warn_unknown_declare_variant_isa_trait)
7188         << ISATrait;
7189   };
7190   TargetOMPContext OMPCtx(Context, std::move(DiagUnknownTrait),
7191                           getCurFunctionDecl(), DSAStack->getConstructTraits());
7192 
7193   QualType CalleeFnType = CalleeFnDecl->getType();
7194 
7195   SmallVector<Expr *, 4> Exprs;
7196   SmallVector<VariantMatchInfo, 4> VMIs;
7197   while (CalleeFnDecl) {
7198     for (OMPDeclareVariantAttr *A :
7199          CalleeFnDecl->specific_attrs<OMPDeclareVariantAttr>()) {
7200       Expr *VariantRef = A->getVariantFuncRef();
7201 
7202       VariantMatchInfo VMI;
7203       OMPTraitInfo &TI = A->getTraitInfo();
7204       TI.getAsVariantMatchInfo(Context, VMI);
7205       if (!isVariantApplicableInContext(VMI, OMPCtx,
7206                                         /* DeviceSetOnly */ false))
7207         continue;
7208 
7209       VMIs.push_back(VMI);
7210       Exprs.push_back(VariantRef);
7211     }
7212 
7213     CalleeFnDecl = CalleeFnDecl->getPreviousDecl();
7214   }
7215 
7216   ExprResult NewCall;
7217   do {
7218     int BestIdx = getBestVariantMatchForContext(VMIs, OMPCtx);
7219     if (BestIdx < 0)
7220       return Call;
7221     Expr *BestExpr = cast<DeclRefExpr>(Exprs[BestIdx]);
7222     Decl *BestDecl = cast<DeclRefExpr>(BestExpr)->getDecl();
7223 
7224     {
7225       // Try to build a (member) call expression for the current best applicable
7226       // variant expression. We allow this to fail in which case we continue
7227       // with the next best variant expression. The fail case is part of the
7228       // implementation defined behavior in the OpenMP standard when it talks
7229       // about what differences in the function prototypes: "Any differences
7230       // that the specific OpenMP context requires in the prototype of the
7231       // variant from the base function prototype are implementation defined."
7232       // This wording is there to allow the specialized variant to have a
7233       // different type than the base function. This is intended and OK but if
7234       // we cannot create a call the difference is not in the "implementation
7235       // defined range" we allow.
7236       Sema::TentativeAnalysisScope Trap(*this);
7237 
7238       if (auto *SpecializedMethod = dyn_cast<CXXMethodDecl>(BestDecl)) {
7239         auto *MemberCall = dyn_cast<CXXMemberCallExpr>(CE);
7240         BestExpr = MemberExpr::CreateImplicit(
7241             Context, MemberCall->getImplicitObjectArgument(),
7242             /* IsArrow */ false, SpecializedMethod, Context.BoundMemberTy,
7243             MemberCall->getValueKind(), MemberCall->getObjectKind());
7244       }
7245       NewCall = BuildCallExpr(Scope, BestExpr, LParenLoc, ArgExprs, RParenLoc,
7246                               ExecConfig);
7247       if (NewCall.isUsable()) {
7248         if (CallExpr *NCE = dyn_cast<CallExpr>(NewCall.get())) {
7249           FunctionDecl *NewCalleeFnDecl = NCE->getDirectCallee();
7250           QualType NewType = Context.mergeFunctionTypes(
7251               CalleeFnType, NewCalleeFnDecl->getType(),
7252               /* OfBlockPointer */ false,
7253               /* Unqualified */ false, /* AllowCXX */ true);
7254           if (!NewType.isNull())
7255             break;
7256           // Don't use the call if the function type was not compatible.
7257           NewCall = nullptr;
7258         }
7259       }
7260     }
7261 
7262     VMIs.erase(VMIs.begin() + BestIdx);
7263     Exprs.erase(Exprs.begin() + BestIdx);
7264   } while (!VMIs.empty());
7265 
7266   if (!NewCall.isUsable())
7267     return Call;
7268   return PseudoObjectExpr::Create(Context, CE, {NewCall.get()}, 0);
7269 }
7270 
7271 Optional<std::pair<FunctionDecl *, Expr *>>
7272 Sema::checkOpenMPDeclareVariantFunction(Sema::DeclGroupPtrTy DG,
7273                                         Expr *VariantRef, OMPTraitInfo &TI,
7274                                         unsigned NumAppendArgs,
7275                                         SourceRange SR) {
7276   if (!DG || DG.get().isNull())
7277     return None;
7278 
7279   const int VariantId = 1;
7280   // Must be applied only to single decl.
7281   if (!DG.get().isSingleDecl()) {
7282     Diag(SR.getBegin(), diag::err_omp_single_decl_in_declare_simd_variant)
7283         << VariantId << SR;
7284     return None;
7285   }
7286   Decl *ADecl = DG.get().getSingleDecl();
7287   if (auto *FTD = dyn_cast<FunctionTemplateDecl>(ADecl))
7288     ADecl = FTD->getTemplatedDecl();
7289 
7290   // Decl must be a function.
7291   auto *FD = dyn_cast<FunctionDecl>(ADecl);
7292   if (!FD) {
7293     Diag(ADecl->getLocation(), diag::err_omp_function_expected)
7294         << VariantId << SR;
7295     return None;
7296   }
7297 
7298   auto &&HasMultiVersionAttributes = [](const FunctionDecl *FD) {
7299     // The 'target' attribute needs to be separately checked because it does
7300     // not always signify a multiversion function declaration.
7301     return FD->isMultiVersion() || FD->hasAttr<TargetAttr>();
7302   };
7303   // OpenMP is not compatible with multiversion function attributes.
7304   if (HasMultiVersionAttributes(FD)) {
7305     Diag(FD->getLocation(), diag::err_omp_declare_variant_incompat_attributes)
7306         << SR;
7307     return None;
7308   }
7309 
7310   // Allow #pragma omp declare variant only if the function is not used.
7311   if (FD->isUsed(false))
7312     Diag(SR.getBegin(), diag::warn_omp_declare_variant_after_used)
7313         << FD->getLocation();
7314 
7315   // Check if the function was emitted already.
7316   const FunctionDecl *Definition;
7317   if (!FD->isThisDeclarationADefinition() && FD->isDefined(Definition) &&
7318       (LangOpts.EmitAllDecls || Context.DeclMustBeEmitted(Definition)))
7319     Diag(SR.getBegin(), diag::warn_omp_declare_variant_after_emitted)
7320         << FD->getLocation();
7321 
7322   // The VariantRef must point to function.
7323   if (!VariantRef) {
7324     Diag(SR.getBegin(), diag::err_omp_function_expected) << VariantId;
7325     return None;
7326   }
7327 
7328   auto ShouldDelayChecks = [](Expr *&E, bool) {
7329     return E && (E->isTypeDependent() || E->isValueDependent() ||
7330                  E->containsUnexpandedParameterPack() ||
7331                  E->isInstantiationDependent());
7332   };
7333   // Do not check templates, wait until instantiation.
7334   if (FD->isDependentContext() || ShouldDelayChecks(VariantRef, false) ||
7335       TI.anyScoreOrCondition(ShouldDelayChecks))
7336     return std::make_pair(FD, VariantRef);
7337 
7338   // Deal with non-constant score and user condition expressions.
7339   auto HandleNonConstantScoresAndConditions = [this](Expr *&E,
7340                                                      bool IsScore) -> bool {
7341     if (!E || E->isIntegerConstantExpr(Context))
7342       return false;
7343 
7344     if (IsScore) {
7345       // We warn on non-constant scores and pretend they were not present.
7346       Diag(E->getExprLoc(), diag::warn_omp_declare_variant_score_not_constant)
7347           << E;
7348       E = nullptr;
7349     } else {
7350       // We could replace a non-constant user condition with "false" but we
7351       // will soon need to handle these anyway for the dynamic version of
7352       // OpenMP context selectors.
7353       Diag(E->getExprLoc(),
7354            diag::err_omp_declare_variant_user_condition_not_constant)
7355           << E;
7356     }
7357     return true;
7358   };
7359   if (TI.anyScoreOrCondition(HandleNonConstantScoresAndConditions))
7360     return None;
7361 
7362   QualType AdjustedFnType = FD->getType();
7363   if (NumAppendArgs) {
7364     const auto *PTy = AdjustedFnType->getAsAdjusted<FunctionProtoType>();
7365     if (!PTy) {
7366       Diag(FD->getLocation(), diag::err_omp_declare_variant_prototype_required)
7367           << SR;
7368       return None;
7369     }
7370     // Adjust the function type to account for an extra omp_interop_t for each
7371     // specified in the append_args clause.
7372     const TypeDecl *TD = nullptr;
7373     LookupResult Result(*this, &Context.Idents.get("omp_interop_t"),
7374                         SR.getBegin(), Sema::LookupOrdinaryName);
7375     if (LookupName(Result, getCurScope())) {
7376       NamedDecl *ND = Result.getFoundDecl();
7377       TD = dyn_cast_or_null<TypeDecl>(ND);
7378     }
7379     if (!TD) {
7380       Diag(SR.getBegin(), diag::err_omp_interop_type_not_found) << SR;
7381       return None;
7382     }
7383     QualType InteropType = Context.getTypeDeclType(TD);
7384     if (PTy->isVariadic()) {
7385       Diag(FD->getLocation(), diag::err_omp_append_args_with_varargs) << SR;
7386       return None;
7387     }
7388     llvm::SmallVector<QualType, 8> Params;
7389     Params.append(PTy->param_type_begin(), PTy->param_type_end());
7390     Params.insert(Params.end(), NumAppendArgs, InteropType);
7391     AdjustedFnType = Context.getFunctionType(PTy->getReturnType(), Params,
7392                                              PTy->getExtProtoInfo());
7393   }
7394 
7395   // Convert VariantRef expression to the type of the original function to
7396   // resolve possible conflicts.
7397   ExprResult VariantRefCast = VariantRef;
7398   if (LangOpts.CPlusPlus) {
7399     QualType FnPtrType;
7400     auto *Method = dyn_cast<CXXMethodDecl>(FD);
7401     if (Method && !Method->isStatic()) {
7402       const Type *ClassType =
7403           Context.getTypeDeclType(Method->getParent()).getTypePtr();
7404       FnPtrType = Context.getMemberPointerType(AdjustedFnType, ClassType);
7405       ExprResult ER;
7406       {
7407         // Build adrr_of unary op to correctly handle type checks for member
7408         // functions.
7409         Sema::TentativeAnalysisScope Trap(*this);
7410         ER = CreateBuiltinUnaryOp(VariantRef->getBeginLoc(), UO_AddrOf,
7411                                   VariantRef);
7412       }
7413       if (!ER.isUsable()) {
7414         Diag(VariantRef->getExprLoc(), diag::err_omp_function_expected)
7415             << VariantId << VariantRef->getSourceRange();
7416         return None;
7417       }
7418       VariantRef = ER.get();
7419     } else {
7420       FnPtrType = Context.getPointerType(AdjustedFnType);
7421     }
7422     QualType VarianPtrType = Context.getPointerType(VariantRef->getType());
7423     if (VarianPtrType.getUnqualifiedType() != FnPtrType.getUnqualifiedType()) {
7424       ImplicitConversionSequence ICS = TryImplicitConversion(
7425           VariantRef, FnPtrType.getUnqualifiedType(),
7426           /*SuppressUserConversions=*/false, AllowedExplicit::None,
7427           /*InOverloadResolution=*/false,
7428           /*CStyle=*/false,
7429           /*AllowObjCWritebackConversion=*/false);
7430       if (ICS.isFailure()) {
7431         Diag(VariantRef->getExprLoc(),
7432              diag::err_omp_declare_variant_incompat_types)
7433             << VariantRef->getType()
7434             << ((Method && !Method->isStatic()) ? FnPtrType : FD->getType())
7435             << (NumAppendArgs ? 1 : 0) << VariantRef->getSourceRange();
7436         return None;
7437       }
7438       VariantRefCast = PerformImplicitConversion(
7439           VariantRef, FnPtrType.getUnqualifiedType(), AA_Converting);
7440       if (!VariantRefCast.isUsable())
7441         return None;
7442     }
7443     // Drop previously built artificial addr_of unary op for member functions.
7444     if (Method && !Method->isStatic()) {
7445       Expr *PossibleAddrOfVariantRef = VariantRefCast.get();
7446       if (auto *UO = dyn_cast<UnaryOperator>(
7447               PossibleAddrOfVariantRef->IgnoreImplicit()))
7448         VariantRefCast = UO->getSubExpr();
7449     }
7450   }
7451 
7452   ExprResult ER = CheckPlaceholderExpr(VariantRefCast.get());
7453   if (!ER.isUsable() ||
7454       !ER.get()->IgnoreParenImpCasts()->getType()->isFunctionType()) {
7455     Diag(VariantRef->getExprLoc(), diag::err_omp_function_expected)
7456         << VariantId << VariantRef->getSourceRange();
7457     return None;
7458   }
7459 
7460   // The VariantRef must point to function.
7461   auto *DRE = dyn_cast<DeclRefExpr>(ER.get()->IgnoreParenImpCasts());
7462   if (!DRE) {
7463     Diag(VariantRef->getExprLoc(), diag::err_omp_function_expected)
7464         << VariantId << VariantRef->getSourceRange();
7465     return None;
7466   }
7467   auto *NewFD = dyn_cast_or_null<FunctionDecl>(DRE->getDecl());
7468   if (!NewFD) {
7469     Diag(VariantRef->getExprLoc(), diag::err_omp_function_expected)
7470         << VariantId << VariantRef->getSourceRange();
7471     return None;
7472   }
7473 
7474   if (FD->getCanonicalDecl() == NewFD->getCanonicalDecl()) {
7475     Diag(VariantRef->getExprLoc(),
7476          diag::err_omp_declare_variant_same_base_function)
7477         << VariantRef->getSourceRange();
7478     return None;
7479   }
7480 
7481   // Check if function types are compatible in C.
7482   if (!LangOpts.CPlusPlus) {
7483     QualType NewType =
7484         Context.mergeFunctionTypes(AdjustedFnType, NewFD->getType());
7485     if (NewType.isNull()) {
7486       Diag(VariantRef->getExprLoc(),
7487            diag::err_omp_declare_variant_incompat_types)
7488           << NewFD->getType() << FD->getType() << (NumAppendArgs ? 1 : 0)
7489           << VariantRef->getSourceRange();
7490       return None;
7491     }
7492     if (NewType->isFunctionProtoType()) {
7493       if (FD->getType()->isFunctionNoProtoType())
7494         setPrototype(*this, FD, NewFD, NewType);
7495       else if (NewFD->getType()->isFunctionNoProtoType())
7496         setPrototype(*this, NewFD, FD, NewType);
7497     }
7498   }
7499 
7500   // Check if variant function is not marked with declare variant directive.
7501   if (NewFD->hasAttrs() && NewFD->hasAttr<OMPDeclareVariantAttr>()) {
7502     Diag(VariantRef->getExprLoc(),
7503          diag::warn_omp_declare_variant_marked_as_declare_variant)
7504         << VariantRef->getSourceRange();
7505     SourceRange SR =
7506         NewFD->specific_attr_begin<OMPDeclareVariantAttr>()->getRange();
7507     Diag(SR.getBegin(), diag::note_omp_marked_declare_variant_here) << SR;
7508     return None;
7509   }
7510 
7511   enum DoesntSupport {
7512     VirtFuncs = 1,
7513     Constructors = 3,
7514     Destructors = 4,
7515     DeletedFuncs = 5,
7516     DefaultedFuncs = 6,
7517     ConstexprFuncs = 7,
7518     ConstevalFuncs = 8,
7519   };
7520   if (const auto *CXXFD = dyn_cast<CXXMethodDecl>(FD)) {
7521     if (CXXFD->isVirtual()) {
7522       Diag(FD->getLocation(), diag::err_omp_declare_variant_doesnt_support)
7523           << VirtFuncs;
7524       return None;
7525     }
7526 
7527     if (isa<CXXConstructorDecl>(FD)) {
7528       Diag(FD->getLocation(), diag::err_omp_declare_variant_doesnt_support)
7529           << Constructors;
7530       return None;
7531     }
7532 
7533     if (isa<CXXDestructorDecl>(FD)) {
7534       Diag(FD->getLocation(), diag::err_omp_declare_variant_doesnt_support)
7535           << Destructors;
7536       return None;
7537     }
7538   }
7539 
7540   if (FD->isDeleted()) {
7541     Diag(FD->getLocation(), diag::err_omp_declare_variant_doesnt_support)
7542         << DeletedFuncs;
7543     return None;
7544   }
7545 
7546   if (FD->isDefaulted()) {
7547     Diag(FD->getLocation(), diag::err_omp_declare_variant_doesnt_support)
7548         << DefaultedFuncs;
7549     return None;
7550   }
7551 
7552   if (FD->isConstexpr()) {
7553     Diag(FD->getLocation(), diag::err_omp_declare_variant_doesnt_support)
7554         << (NewFD->isConsteval() ? ConstevalFuncs : ConstexprFuncs);
7555     return None;
7556   }
7557 
7558   // Check general compatibility.
7559   if (areMultiversionVariantFunctionsCompatible(
7560           FD, NewFD, PartialDiagnostic::NullDiagnostic(),
7561           PartialDiagnosticAt(SourceLocation(),
7562                               PartialDiagnostic::NullDiagnostic()),
7563           PartialDiagnosticAt(
7564               VariantRef->getExprLoc(),
7565               PDiag(diag::err_omp_declare_variant_doesnt_support)),
7566           PartialDiagnosticAt(VariantRef->getExprLoc(),
7567                               PDiag(diag::err_omp_declare_variant_diff)
7568                                   << FD->getLocation()),
7569           /*TemplatesSupported=*/true, /*ConstexprSupported=*/false,
7570           /*CLinkageMayDiffer=*/true))
7571     return None;
7572   return std::make_pair(FD, cast<Expr>(DRE));
7573 }
7574 
7575 void Sema::ActOnOpenMPDeclareVariantDirective(
7576     FunctionDecl *FD, Expr *VariantRef, OMPTraitInfo &TI,
7577     ArrayRef<Expr *> AdjustArgsNothing,
7578     ArrayRef<Expr *> AdjustArgsNeedDevicePtr,
7579     ArrayRef<OMPDeclareVariantAttr::InteropType> AppendArgs,
7580     SourceLocation AdjustArgsLoc, SourceLocation AppendArgsLoc,
7581     SourceRange SR) {
7582 
7583   // OpenMP 5.1 [2.3.5, declare variant directive, Restrictions]
7584   // An adjust_args clause or append_args clause can only be specified if the
7585   // dispatch selector of the construct selector set appears in the match
7586   // clause.
7587 
7588   SmallVector<Expr *, 8> AllAdjustArgs;
7589   llvm::append_range(AllAdjustArgs, AdjustArgsNothing);
7590   llvm::append_range(AllAdjustArgs, AdjustArgsNeedDevicePtr);
7591 
7592   if (!AllAdjustArgs.empty() || !AppendArgs.empty()) {
7593     VariantMatchInfo VMI;
7594     TI.getAsVariantMatchInfo(Context, VMI);
7595     if (!llvm::is_contained(
7596             VMI.ConstructTraits,
7597             llvm::omp::TraitProperty::construct_dispatch_dispatch)) {
7598       if (!AllAdjustArgs.empty())
7599         Diag(AdjustArgsLoc, diag::err_omp_clause_requires_dispatch_construct)
7600             << getOpenMPClauseName(OMPC_adjust_args);
7601       if (!AppendArgs.empty())
7602         Diag(AppendArgsLoc, diag::err_omp_clause_requires_dispatch_construct)
7603             << getOpenMPClauseName(OMPC_append_args);
7604       return;
7605     }
7606   }
7607 
7608   // OpenMP 5.1 [2.3.5, declare variant directive, Restrictions]
7609   // Each argument can only appear in a single adjust_args clause for each
7610   // declare variant directive.
7611   llvm::SmallPtrSet<const VarDecl *, 4> AdjustVars;
7612 
7613   for (Expr *E : AllAdjustArgs) {
7614     E = E->IgnoreParenImpCasts();
7615     if (const auto *DRE = dyn_cast<DeclRefExpr>(E)) {
7616       if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl())) {
7617         const VarDecl *CanonPVD = PVD->getCanonicalDecl();
7618         if (FD->getNumParams() > PVD->getFunctionScopeIndex() &&
7619             FD->getParamDecl(PVD->getFunctionScopeIndex())
7620                     ->getCanonicalDecl() == CanonPVD) {
7621           // It's a parameter of the function, check duplicates.
7622           if (!AdjustVars.insert(CanonPVD).second) {
7623             Diag(DRE->getLocation(), diag::err_omp_adjust_arg_multiple_clauses)
7624                 << PVD;
7625             return;
7626           }
7627           continue;
7628         }
7629       }
7630     }
7631     // Anything that is not a function parameter is an error.
7632     Diag(E->getExprLoc(), diag::err_omp_param_or_this_in_clause) << FD << 0;
7633     return;
7634   }
7635 
7636   auto *NewAttr = OMPDeclareVariantAttr::CreateImplicit(
7637       Context, VariantRef, &TI, const_cast<Expr **>(AdjustArgsNothing.data()),
7638       AdjustArgsNothing.size(),
7639       const_cast<Expr **>(AdjustArgsNeedDevicePtr.data()),
7640       AdjustArgsNeedDevicePtr.size(),
7641       const_cast<OMPDeclareVariantAttr::InteropType *>(AppendArgs.data()),
7642       AppendArgs.size(), SR);
7643   FD->addAttr(NewAttr);
7644 }
7645 
7646 StmtResult Sema::ActOnOpenMPParallelDirective(ArrayRef<OMPClause *> Clauses,
7647                                               Stmt *AStmt,
7648                                               SourceLocation StartLoc,
7649                                               SourceLocation EndLoc) {
7650   if (!AStmt)
7651     return StmtError();
7652 
7653   auto *CS = cast<CapturedStmt>(AStmt);
7654   // 1.2.2 OpenMP Language Terminology
7655   // Structured block - An executable statement with a single entry at the
7656   // top and a single exit at the bottom.
7657   // The point of exit cannot be a branch out of the structured block.
7658   // longjmp() and throw() must not violate the entry/exit criteria.
7659   CS->getCapturedDecl()->setNothrow();
7660 
7661   setFunctionHasBranchProtectedScope();
7662 
7663   return OMPParallelDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
7664                                       DSAStack->getTaskgroupReductionRef(),
7665                                       DSAStack->isCancelRegion());
7666 }
7667 
7668 namespace {
7669 /// Iteration space of a single for loop.
7670 struct LoopIterationSpace final {
7671   /// True if the condition operator is the strict compare operator (<, > or
7672   /// !=).
7673   bool IsStrictCompare = false;
7674   /// Condition of the loop.
7675   Expr *PreCond = nullptr;
7676   /// This expression calculates the number of iterations in the loop.
7677   /// It is always possible to calculate it before starting the loop.
7678   Expr *NumIterations = nullptr;
7679   /// The loop counter variable.
7680   Expr *CounterVar = nullptr;
7681   /// Private loop counter variable.
7682   Expr *PrivateCounterVar = nullptr;
7683   /// This is initializer for the initial value of #CounterVar.
7684   Expr *CounterInit = nullptr;
7685   /// This is step for the #CounterVar used to generate its update:
7686   /// #CounterVar = #CounterInit + #CounterStep * CurrentIteration.
7687   Expr *CounterStep = nullptr;
7688   /// Should step be subtracted?
7689   bool Subtract = false;
7690   /// Source range of the loop init.
7691   SourceRange InitSrcRange;
7692   /// Source range of the loop condition.
7693   SourceRange CondSrcRange;
7694   /// Source range of the loop increment.
7695   SourceRange IncSrcRange;
7696   /// Minimum value that can have the loop control variable. Used to support
7697   /// non-rectangular loops. Applied only for LCV with the non-iterator types,
7698   /// since only such variables can be used in non-loop invariant expressions.
7699   Expr *MinValue = nullptr;
7700   /// Maximum value that can have the loop control variable. Used to support
7701   /// non-rectangular loops. Applied only for LCV with the non-iterator type,
7702   /// since only such variables can be used in non-loop invariant expressions.
7703   Expr *MaxValue = nullptr;
7704   /// true, if the lower bound depends on the outer loop control var.
7705   bool IsNonRectangularLB = false;
7706   /// true, if the upper bound depends on the outer loop control var.
7707   bool IsNonRectangularUB = false;
7708   /// Index of the loop this loop depends on and forms non-rectangular loop
7709   /// nest.
7710   unsigned LoopDependentIdx = 0;
7711   /// Final condition for the non-rectangular loop nest support. It is used to
7712   /// check that the number of iterations for this particular counter must be
7713   /// finished.
7714   Expr *FinalCondition = nullptr;
7715 };
7716 
7717 /// Helper class for checking canonical form of the OpenMP loops and
7718 /// extracting iteration space of each loop in the loop nest, that will be used
7719 /// for IR generation.
7720 class OpenMPIterationSpaceChecker {
7721   /// Reference to Sema.
7722   Sema &SemaRef;
7723   /// Does the loop associated directive support non-rectangular loops?
7724   bool SupportsNonRectangular;
7725   /// Data-sharing stack.
7726   DSAStackTy &Stack;
7727   /// A location for diagnostics (when there is no some better location).
7728   SourceLocation DefaultLoc;
7729   /// A location for diagnostics (when increment is not compatible).
7730   SourceLocation ConditionLoc;
7731   /// A source location for referring to loop init later.
7732   SourceRange InitSrcRange;
7733   /// A source location for referring to condition later.
7734   SourceRange ConditionSrcRange;
7735   /// A source location for referring to increment later.
7736   SourceRange IncrementSrcRange;
7737   /// Loop variable.
7738   ValueDecl *LCDecl = nullptr;
7739   /// Reference to loop variable.
7740   Expr *LCRef = nullptr;
7741   /// Lower bound (initializer for the var).
7742   Expr *LB = nullptr;
7743   /// Upper bound.
7744   Expr *UB = nullptr;
7745   /// Loop step (increment).
7746   Expr *Step = nullptr;
7747   /// This flag is true when condition is one of:
7748   ///   Var <  UB
7749   ///   Var <= UB
7750   ///   UB  >  Var
7751   ///   UB  >= Var
7752   /// This will have no value when the condition is !=
7753   llvm::Optional<bool> TestIsLessOp;
7754   /// This flag is true when condition is strict ( < or > ).
7755   bool TestIsStrictOp = false;
7756   /// This flag is true when step is subtracted on each iteration.
7757   bool SubtractStep = false;
7758   /// The outer loop counter this loop depends on (if any).
7759   const ValueDecl *DepDecl = nullptr;
7760   /// Contains number of loop (starts from 1) on which loop counter init
7761   /// expression of this loop depends on.
7762   Optional<unsigned> InitDependOnLC;
7763   /// Contains number of loop (starts from 1) on which loop counter condition
7764   /// expression of this loop depends on.
7765   Optional<unsigned> CondDependOnLC;
7766   /// Checks if the provide statement depends on the loop counter.
7767   Optional<unsigned> doesDependOnLoopCounter(const Stmt *S, bool IsInitializer);
7768   /// Original condition required for checking of the exit condition for
7769   /// non-rectangular loop.
7770   Expr *Condition = nullptr;
7771 
7772 public:
7773   OpenMPIterationSpaceChecker(Sema &SemaRef, bool SupportsNonRectangular,
7774                               DSAStackTy &Stack, SourceLocation DefaultLoc)
7775       : SemaRef(SemaRef), SupportsNonRectangular(SupportsNonRectangular),
7776         Stack(Stack), DefaultLoc(DefaultLoc), ConditionLoc(DefaultLoc) {}
7777   /// Check init-expr for canonical loop form and save loop counter
7778   /// variable - #Var and its initialization value - #LB.
7779   bool checkAndSetInit(Stmt *S, bool EmitDiags = true);
7780   /// Check test-expr for canonical form, save upper-bound (#UB), flags
7781   /// for less/greater and for strict/non-strict comparison.
7782   bool checkAndSetCond(Expr *S);
7783   /// Check incr-expr for canonical loop form and return true if it
7784   /// does not conform, otherwise save loop step (#Step).
7785   bool checkAndSetInc(Expr *S);
7786   /// Return the loop counter variable.
7787   ValueDecl *getLoopDecl() const { return LCDecl; }
7788   /// Return the reference expression to loop counter variable.
7789   Expr *getLoopDeclRefExpr() const { return LCRef; }
7790   /// Source range of the loop init.
7791   SourceRange getInitSrcRange() const { return InitSrcRange; }
7792   /// Source range of the loop condition.
7793   SourceRange getConditionSrcRange() const { return ConditionSrcRange; }
7794   /// Source range of the loop increment.
7795   SourceRange getIncrementSrcRange() const { return IncrementSrcRange; }
7796   /// True if the step should be subtracted.
7797   bool shouldSubtractStep() const { return SubtractStep; }
7798   /// True, if the compare operator is strict (<, > or !=).
7799   bool isStrictTestOp() const { return TestIsStrictOp; }
7800   /// Build the expression to calculate the number of iterations.
7801   Expr *buildNumIterations(
7802       Scope *S, ArrayRef<LoopIterationSpace> ResultIterSpaces, bool LimitedType,
7803       llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const;
7804   /// Build the precondition expression for the loops.
7805   Expr *
7806   buildPreCond(Scope *S, Expr *Cond,
7807                llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const;
7808   /// Build reference expression to the counter be used for codegen.
7809   DeclRefExpr *
7810   buildCounterVar(llvm::MapVector<const Expr *, DeclRefExpr *> &Captures,
7811                   DSAStackTy &DSA) const;
7812   /// Build reference expression to the private counter be used for
7813   /// codegen.
7814   Expr *buildPrivateCounterVar() const;
7815   /// Build initialization of the counter be used for codegen.
7816   Expr *buildCounterInit() const;
7817   /// Build step of the counter be used for codegen.
7818   Expr *buildCounterStep() const;
7819   /// Build loop data with counter value for depend clauses in ordered
7820   /// directives.
7821   Expr *
7822   buildOrderedLoopData(Scope *S, Expr *Counter,
7823                        llvm::MapVector<const Expr *, DeclRefExpr *> &Captures,
7824                        SourceLocation Loc, Expr *Inc = nullptr,
7825                        OverloadedOperatorKind OOK = OO_Amp);
7826   /// Builds the minimum value for the loop counter.
7827   std::pair<Expr *, Expr *> buildMinMaxValues(
7828       Scope *S, llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const;
7829   /// Builds final condition for the non-rectangular loops.
7830   Expr *buildFinalCondition(Scope *S) const;
7831   /// Return true if any expression is dependent.
7832   bool dependent() const;
7833   /// Returns true if the initializer forms non-rectangular loop.
7834   bool doesInitDependOnLC() const { return InitDependOnLC.hasValue(); }
7835   /// Returns true if the condition forms non-rectangular loop.
7836   bool doesCondDependOnLC() const { return CondDependOnLC.hasValue(); }
7837   /// Returns index of the loop we depend on (starting from 1), or 0 otherwise.
7838   unsigned getLoopDependentIdx() const {
7839     return InitDependOnLC.value_or(CondDependOnLC.value_or(0));
7840   }
7841 
7842 private:
7843   /// Check the right-hand side of an assignment in the increment
7844   /// expression.
7845   bool checkAndSetIncRHS(Expr *RHS);
7846   /// Helper to set loop counter variable and its initializer.
7847   bool setLCDeclAndLB(ValueDecl *NewLCDecl, Expr *NewDeclRefExpr, Expr *NewLB,
7848                       bool EmitDiags);
7849   /// Helper to set upper bound.
7850   bool setUB(Expr *NewUB, llvm::Optional<bool> LessOp, bool StrictOp,
7851              SourceRange SR, SourceLocation SL);
7852   /// Helper to set loop increment.
7853   bool setStep(Expr *NewStep, bool Subtract);
7854 };
7855 
7856 bool OpenMPIterationSpaceChecker::dependent() const {
7857   if (!LCDecl) {
7858     assert(!LB && !UB && !Step);
7859     return false;
7860   }
7861   return LCDecl->getType()->isDependentType() ||
7862          (LB && LB->isValueDependent()) || (UB && UB->isValueDependent()) ||
7863          (Step && Step->isValueDependent());
7864 }
7865 
7866 bool OpenMPIterationSpaceChecker::setLCDeclAndLB(ValueDecl *NewLCDecl,
7867                                                  Expr *NewLCRefExpr,
7868                                                  Expr *NewLB, bool EmitDiags) {
7869   // State consistency checking to ensure correct usage.
7870   assert(LCDecl == nullptr && LB == nullptr && LCRef == nullptr &&
7871          UB == nullptr && Step == nullptr && !TestIsLessOp && !TestIsStrictOp);
7872   if (!NewLCDecl || !NewLB || NewLB->containsErrors())
7873     return true;
7874   LCDecl = getCanonicalDecl(NewLCDecl);
7875   LCRef = NewLCRefExpr;
7876   if (auto *CE = dyn_cast_or_null<CXXConstructExpr>(NewLB))
7877     if (const CXXConstructorDecl *Ctor = CE->getConstructor())
7878       if ((Ctor->isCopyOrMoveConstructor() ||
7879            Ctor->isConvertingConstructor(/*AllowExplicit=*/false)) &&
7880           CE->getNumArgs() > 0 && CE->getArg(0) != nullptr)
7881         NewLB = CE->getArg(0)->IgnoreParenImpCasts();
7882   LB = NewLB;
7883   if (EmitDiags)
7884     InitDependOnLC = doesDependOnLoopCounter(LB, /*IsInitializer=*/true);
7885   return false;
7886 }
7887 
7888 bool OpenMPIterationSpaceChecker::setUB(Expr *NewUB,
7889                                         llvm::Optional<bool> LessOp,
7890                                         bool StrictOp, SourceRange SR,
7891                                         SourceLocation SL) {
7892   // State consistency checking to ensure correct usage.
7893   assert(LCDecl != nullptr && LB != nullptr && UB == nullptr &&
7894          Step == nullptr && !TestIsLessOp && !TestIsStrictOp);
7895   if (!NewUB || NewUB->containsErrors())
7896     return true;
7897   UB = NewUB;
7898   if (LessOp)
7899     TestIsLessOp = LessOp;
7900   TestIsStrictOp = StrictOp;
7901   ConditionSrcRange = SR;
7902   ConditionLoc = SL;
7903   CondDependOnLC = doesDependOnLoopCounter(UB, /*IsInitializer=*/false);
7904   return false;
7905 }
7906 
7907 bool OpenMPIterationSpaceChecker::setStep(Expr *NewStep, bool Subtract) {
7908   // State consistency checking to ensure correct usage.
7909   assert(LCDecl != nullptr && LB != nullptr && Step == nullptr);
7910   if (!NewStep || NewStep->containsErrors())
7911     return true;
7912   if (!NewStep->isValueDependent()) {
7913     // Check that the step is integer expression.
7914     SourceLocation StepLoc = NewStep->getBeginLoc();
7915     ExprResult Val = SemaRef.PerformOpenMPImplicitIntegerConversion(
7916         StepLoc, getExprAsWritten(NewStep));
7917     if (Val.isInvalid())
7918       return true;
7919     NewStep = Val.get();
7920 
7921     // OpenMP [2.6, Canonical Loop Form, Restrictions]
7922     //  If test-expr is of form var relational-op b and relational-op is < or
7923     //  <= then incr-expr must cause var to increase on each iteration of the
7924     //  loop. If test-expr is of form var relational-op b and relational-op is
7925     //  > or >= then incr-expr must cause var to decrease on each iteration of
7926     //  the loop.
7927     //  If test-expr is of form b relational-op var and relational-op is < or
7928     //  <= then incr-expr must cause var to decrease on each iteration of the
7929     //  loop. If test-expr is of form b relational-op var and relational-op is
7930     //  > or >= then incr-expr must cause var to increase on each iteration of
7931     //  the loop.
7932     Optional<llvm::APSInt> Result =
7933         NewStep->getIntegerConstantExpr(SemaRef.Context);
7934     bool IsUnsigned = !NewStep->getType()->hasSignedIntegerRepresentation();
7935     bool IsConstNeg =
7936         Result && Result->isSigned() && (Subtract != Result->isNegative());
7937     bool IsConstPos =
7938         Result && Result->isSigned() && (Subtract == Result->isNegative());
7939     bool IsConstZero = Result && !Result->getBoolValue();
7940 
7941     // != with increment is treated as <; != with decrement is treated as >
7942     if (!TestIsLessOp)
7943       TestIsLessOp = IsConstPos || (IsUnsigned && !Subtract);
7944     if (UB &&
7945         (IsConstZero || (TestIsLessOp.getValue()
7946                              ? (IsConstNeg || (IsUnsigned && Subtract))
7947                              : (IsConstPos || (IsUnsigned && !Subtract))))) {
7948       SemaRef.Diag(NewStep->getExprLoc(),
7949                    diag::err_omp_loop_incr_not_compatible)
7950           << LCDecl << TestIsLessOp.getValue() << NewStep->getSourceRange();
7951       SemaRef.Diag(ConditionLoc,
7952                    diag::note_omp_loop_cond_requres_compatible_incr)
7953           << TestIsLessOp.getValue() << ConditionSrcRange;
7954       return true;
7955     }
7956     if (TestIsLessOp.getValue() == Subtract) {
7957       NewStep =
7958           SemaRef.CreateBuiltinUnaryOp(NewStep->getExprLoc(), UO_Minus, NewStep)
7959               .get();
7960       Subtract = !Subtract;
7961     }
7962   }
7963 
7964   Step = NewStep;
7965   SubtractStep = Subtract;
7966   return false;
7967 }
7968 
7969 namespace {
7970 /// Checker for the non-rectangular loops. Checks if the initializer or
7971 /// condition expression references loop counter variable.
7972 class LoopCounterRefChecker final
7973     : public ConstStmtVisitor<LoopCounterRefChecker, bool> {
7974   Sema &SemaRef;
7975   DSAStackTy &Stack;
7976   const ValueDecl *CurLCDecl = nullptr;
7977   const ValueDecl *DepDecl = nullptr;
7978   const ValueDecl *PrevDepDecl = nullptr;
7979   bool IsInitializer = true;
7980   bool SupportsNonRectangular;
7981   unsigned BaseLoopId = 0;
7982   bool checkDecl(const Expr *E, const ValueDecl *VD) {
7983     if (getCanonicalDecl(VD) == getCanonicalDecl(CurLCDecl)) {
7984       SemaRef.Diag(E->getExprLoc(), diag::err_omp_stmt_depends_on_loop_counter)
7985           << (IsInitializer ? 0 : 1);
7986       return false;
7987     }
7988     const auto &&Data = Stack.isLoopControlVariable(VD);
7989     // OpenMP, 2.9.1 Canonical Loop Form, Restrictions.
7990     // The type of the loop iterator on which we depend may not have a random
7991     // access iterator type.
7992     if (Data.first && VD->getType()->isRecordType()) {
7993       SmallString<128> Name;
7994       llvm::raw_svector_ostream OS(Name);
7995       VD->getNameForDiagnostic(OS, SemaRef.getPrintingPolicy(),
7996                                /*Qualified=*/true);
7997       SemaRef.Diag(E->getExprLoc(),
7998                    diag::err_omp_wrong_dependency_iterator_type)
7999           << OS.str();
8000       SemaRef.Diag(VD->getLocation(), diag::note_previous_decl) << VD;
8001       return false;
8002     }
8003     if (Data.first && !SupportsNonRectangular) {
8004       SemaRef.Diag(E->getExprLoc(), diag::err_omp_invariant_dependency);
8005       return false;
8006     }
8007     if (Data.first &&
8008         (DepDecl || (PrevDepDecl &&
8009                      getCanonicalDecl(VD) != getCanonicalDecl(PrevDepDecl)))) {
8010       if (!DepDecl && PrevDepDecl)
8011         DepDecl = PrevDepDecl;
8012       SmallString<128> Name;
8013       llvm::raw_svector_ostream OS(Name);
8014       DepDecl->getNameForDiagnostic(OS, SemaRef.getPrintingPolicy(),
8015                                     /*Qualified=*/true);
8016       SemaRef.Diag(E->getExprLoc(),
8017                    diag::err_omp_invariant_or_linear_dependency)
8018           << OS.str();
8019       return false;
8020     }
8021     if (Data.first) {
8022       DepDecl = VD;
8023       BaseLoopId = Data.first;
8024     }
8025     return Data.first;
8026   }
8027 
8028 public:
8029   bool VisitDeclRefExpr(const DeclRefExpr *E) {
8030     const ValueDecl *VD = E->getDecl();
8031     if (isa<VarDecl>(VD))
8032       return checkDecl(E, VD);
8033     return false;
8034   }
8035   bool VisitMemberExpr(const MemberExpr *E) {
8036     if (isa<CXXThisExpr>(E->getBase()->IgnoreParens())) {
8037       const ValueDecl *VD = E->getMemberDecl();
8038       if (isa<VarDecl>(VD) || isa<FieldDecl>(VD))
8039         return checkDecl(E, VD);
8040     }
8041     return false;
8042   }
8043   bool VisitStmt(const Stmt *S) {
8044     bool Res = false;
8045     for (const Stmt *Child : S->children())
8046       Res = (Child && Visit(Child)) || Res;
8047     return Res;
8048   }
8049   explicit LoopCounterRefChecker(Sema &SemaRef, DSAStackTy &Stack,
8050                                  const ValueDecl *CurLCDecl, bool IsInitializer,
8051                                  const ValueDecl *PrevDepDecl = nullptr,
8052                                  bool SupportsNonRectangular = true)
8053       : SemaRef(SemaRef), Stack(Stack), CurLCDecl(CurLCDecl),
8054         PrevDepDecl(PrevDepDecl), IsInitializer(IsInitializer),
8055         SupportsNonRectangular(SupportsNonRectangular) {}
8056   unsigned getBaseLoopId() const {
8057     assert(CurLCDecl && "Expected loop dependency.");
8058     return BaseLoopId;
8059   }
8060   const ValueDecl *getDepDecl() const {
8061     assert(CurLCDecl && "Expected loop dependency.");
8062     return DepDecl;
8063   }
8064 };
8065 } // namespace
8066 
8067 Optional<unsigned>
8068 OpenMPIterationSpaceChecker::doesDependOnLoopCounter(const Stmt *S,
8069                                                      bool IsInitializer) {
8070   // Check for the non-rectangular loops.
8071   LoopCounterRefChecker LoopStmtChecker(SemaRef, Stack, LCDecl, IsInitializer,
8072                                         DepDecl, SupportsNonRectangular);
8073   if (LoopStmtChecker.Visit(S)) {
8074     DepDecl = LoopStmtChecker.getDepDecl();
8075     return LoopStmtChecker.getBaseLoopId();
8076   }
8077   return llvm::None;
8078 }
8079 
8080 bool OpenMPIterationSpaceChecker::checkAndSetInit(Stmt *S, bool EmitDiags) {
8081   // Check init-expr for canonical loop form and save loop counter
8082   // variable - #Var and its initialization value - #LB.
8083   // OpenMP [2.6] Canonical loop form. init-expr may be one of the following:
8084   //   var = lb
8085   //   integer-type var = lb
8086   //   random-access-iterator-type var = lb
8087   //   pointer-type var = lb
8088   //
8089   if (!S) {
8090     if (EmitDiags) {
8091       SemaRef.Diag(DefaultLoc, diag::err_omp_loop_not_canonical_init);
8092     }
8093     return true;
8094   }
8095   if (auto *ExprTemp = dyn_cast<ExprWithCleanups>(S))
8096     if (!ExprTemp->cleanupsHaveSideEffects())
8097       S = ExprTemp->getSubExpr();
8098 
8099   InitSrcRange = S->getSourceRange();
8100   if (Expr *E = dyn_cast<Expr>(S))
8101     S = E->IgnoreParens();
8102   if (auto *BO = dyn_cast<BinaryOperator>(S)) {
8103     if (BO->getOpcode() == BO_Assign) {
8104       Expr *LHS = BO->getLHS()->IgnoreParens();
8105       if (auto *DRE = dyn_cast<DeclRefExpr>(LHS)) {
8106         if (auto *CED = dyn_cast<OMPCapturedExprDecl>(DRE->getDecl()))
8107           if (auto *ME = dyn_cast<MemberExpr>(getExprAsWritten(CED->getInit())))
8108             return setLCDeclAndLB(ME->getMemberDecl(), ME, BO->getRHS(),
8109                                   EmitDiags);
8110         return setLCDeclAndLB(DRE->getDecl(), DRE, BO->getRHS(), EmitDiags);
8111       }
8112       if (auto *ME = dyn_cast<MemberExpr>(LHS)) {
8113         if (ME->isArrow() &&
8114             isa<CXXThisExpr>(ME->getBase()->IgnoreParenImpCasts()))
8115           return setLCDeclAndLB(ME->getMemberDecl(), ME, BO->getRHS(),
8116                                 EmitDiags);
8117       }
8118     }
8119   } else if (auto *DS = dyn_cast<DeclStmt>(S)) {
8120     if (DS->isSingleDecl()) {
8121       if (auto *Var = dyn_cast_or_null<VarDecl>(DS->getSingleDecl())) {
8122         if (Var->hasInit() && !Var->getType()->isReferenceType()) {
8123           // Accept non-canonical init form here but emit ext. warning.
8124           if (Var->getInitStyle() != VarDecl::CInit && EmitDiags)
8125             SemaRef.Diag(S->getBeginLoc(),
8126                          diag::ext_omp_loop_not_canonical_init)
8127                 << S->getSourceRange();
8128           return setLCDeclAndLB(
8129               Var,
8130               buildDeclRefExpr(SemaRef, Var,
8131                                Var->getType().getNonReferenceType(),
8132                                DS->getBeginLoc()),
8133               Var->getInit(), EmitDiags);
8134         }
8135       }
8136     }
8137   } else if (auto *CE = dyn_cast<CXXOperatorCallExpr>(S)) {
8138     if (CE->getOperator() == OO_Equal) {
8139       Expr *LHS = CE->getArg(0);
8140       if (auto *DRE = dyn_cast<DeclRefExpr>(LHS)) {
8141         if (auto *CED = dyn_cast<OMPCapturedExprDecl>(DRE->getDecl()))
8142           if (auto *ME = dyn_cast<MemberExpr>(getExprAsWritten(CED->getInit())))
8143             return setLCDeclAndLB(ME->getMemberDecl(), ME, BO->getRHS(),
8144                                   EmitDiags);
8145         return setLCDeclAndLB(DRE->getDecl(), DRE, CE->getArg(1), EmitDiags);
8146       }
8147       if (auto *ME = dyn_cast<MemberExpr>(LHS)) {
8148         if (ME->isArrow() &&
8149             isa<CXXThisExpr>(ME->getBase()->IgnoreParenImpCasts()))
8150           return setLCDeclAndLB(ME->getMemberDecl(), ME, BO->getRHS(),
8151                                 EmitDiags);
8152       }
8153     }
8154   }
8155 
8156   if (dependent() || SemaRef.CurContext->isDependentContext())
8157     return false;
8158   if (EmitDiags) {
8159     SemaRef.Diag(S->getBeginLoc(), diag::err_omp_loop_not_canonical_init)
8160         << S->getSourceRange();
8161   }
8162   return true;
8163 }
8164 
8165 /// Ignore parenthesizes, implicit casts, copy constructor and return the
8166 /// variable (which may be the loop variable) if possible.
8167 static const ValueDecl *getInitLCDecl(const Expr *E) {
8168   if (!E)
8169     return nullptr;
8170   E = getExprAsWritten(E);
8171   if (const auto *CE = dyn_cast_or_null<CXXConstructExpr>(E))
8172     if (const CXXConstructorDecl *Ctor = CE->getConstructor())
8173       if ((Ctor->isCopyOrMoveConstructor() ||
8174            Ctor->isConvertingConstructor(/*AllowExplicit=*/false)) &&
8175           CE->getNumArgs() > 0 && CE->getArg(0) != nullptr)
8176         E = CE->getArg(0)->IgnoreParenImpCasts();
8177   if (const auto *DRE = dyn_cast_or_null<DeclRefExpr>(E)) {
8178     if (const auto *VD = dyn_cast<VarDecl>(DRE->getDecl()))
8179       return getCanonicalDecl(VD);
8180   }
8181   if (const auto *ME = dyn_cast_or_null<MemberExpr>(E))
8182     if (ME->isArrow() && isa<CXXThisExpr>(ME->getBase()->IgnoreParenImpCasts()))
8183       return getCanonicalDecl(ME->getMemberDecl());
8184   return nullptr;
8185 }
8186 
8187 bool OpenMPIterationSpaceChecker::checkAndSetCond(Expr *S) {
8188   // Check test-expr for canonical form, save upper-bound UB, flags for
8189   // less/greater and for strict/non-strict comparison.
8190   // OpenMP [2.9] Canonical loop form. Test-expr may be one of the following:
8191   //   var relational-op b
8192   //   b relational-op var
8193   //
8194   bool IneqCondIsCanonical = SemaRef.getLangOpts().OpenMP >= 50;
8195   if (!S) {
8196     SemaRef.Diag(DefaultLoc, diag::err_omp_loop_not_canonical_cond)
8197         << (IneqCondIsCanonical ? 1 : 0) << LCDecl;
8198     return true;
8199   }
8200   Condition = S;
8201   S = getExprAsWritten(S);
8202   SourceLocation CondLoc = S->getBeginLoc();
8203   auto &&CheckAndSetCond = [this, IneqCondIsCanonical](
8204                                BinaryOperatorKind Opcode, const Expr *LHS,
8205                                const Expr *RHS, SourceRange SR,
8206                                SourceLocation OpLoc) -> llvm::Optional<bool> {
8207     if (BinaryOperator::isRelationalOp(Opcode)) {
8208       if (getInitLCDecl(LHS) == LCDecl)
8209         return setUB(const_cast<Expr *>(RHS),
8210                      (Opcode == BO_LT || Opcode == BO_LE),
8211                      (Opcode == BO_LT || Opcode == BO_GT), SR, OpLoc);
8212       if (getInitLCDecl(RHS) == LCDecl)
8213         return setUB(const_cast<Expr *>(LHS),
8214                      (Opcode == BO_GT || Opcode == BO_GE),
8215                      (Opcode == BO_LT || Opcode == BO_GT), SR, OpLoc);
8216     } else if (IneqCondIsCanonical && Opcode == BO_NE) {
8217       return setUB(const_cast<Expr *>(getInitLCDecl(LHS) == LCDecl ? RHS : LHS),
8218                    /*LessOp=*/llvm::None,
8219                    /*StrictOp=*/true, SR, OpLoc);
8220     }
8221     return llvm::None;
8222   };
8223   llvm::Optional<bool> Res;
8224   if (auto *RBO = dyn_cast<CXXRewrittenBinaryOperator>(S)) {
8225     CXXRewrittenBinaryOperator::DecomposedForm DF = RBO->getDecomposedForm();
8226     Res = CheckAndSetCond(DF.Opcode, DF.LHS, DF.RHS, RBO->getSourceRange(),
8227                           RBO->getOperatorLoc());
8228   } else if (auto *BO = dyn_cast<BinaryOperator>(S)) {
8229     Res = CheckAndSetCond(BO->getOpcode(), BO->getLHS(), BO->getRHS(),
8230                           BO->getSourceRange(), BO->getOperatorLoc());
8231   } else if (auto *CE = dyn_cast<CXXOperatorCallExpr>(S)) {
8232     if (CE->getNumArgs() == 2) {
8233       Res = CheckAndSetCond(
8234           BinaryOperator::getOverloadedOpcode(CE->getOperator()), CE->getArg(0),
8235           CE->getArg(1), CE->getSourceRange(), CE->getOperatorLoc());
8236     }
8237   }
8238   if (Res)
8239     return *Res;
8240   if (dependent() || SemaRef.CurContext->isDependentContext())
8241     return false;
8242   SemaRef.Diag(CondLoc, diag::err_omp_loop_not_canonical_cond)
8243       << (IneqCondIsCanonical ? 1 : 0) << S->getSourceRange() << LCDecl;
8244   return true;
8245 }
8246 
8247 bool OpenMPIterationSpaceChecker::checkAndSetIncRHS(Expr *RHS) {
8248   // RHS of canonical loop form increment can be:
8249   //   var + incr
8250   //   incr + var
8251   //   var - incr
8252   //
8253   RHS = RHS->IgnoreParenImpCasts();
8254   if (auto *BO = dyn_cast<BinaryOperator>(RHS)) {
8255     if (BO->isAdditiveOp()) {
8256       bool IsAdd = BO->getOpcode() == BO_Add;
8257       if (getInitLCDecl(BO->getLHS()) == LCDecl)
8258         return setStep(BO->getRHS(), !IsAdd);
8259       if (IsAdd && getInitLCDecl(BO->getRHS()) == LCDecl)
8260         return setStep(BO->getLHS(), /*Subtract=*/false);
8261     }
8262   } else if (auto *CE = dyn_cast<CXXOperatorCallExpr>(RHS)) {
8263     bool IsAdd = CE->getOperator() == OO_Plus;
8264     if ((IsAdd || CE->getOperator() == OO_Minus) && CE->getNumArgs() == 2) {
8265       if (getInitLCDecl(CE->getArg(0)) == LCDecl)
8266         return setStep(CE->getArg(1), !IsAdd);
8267       if (IsAdd && getInitLCDecl(CE->getArg(1)) == LCDecl)
8268         return setStep(CE->getArg(0), /*Subtract=*/false);
8269     }
8270   }
8271   if (dependent() || SemaRef.CurContext->isDependentContext())
8272     return false;
8273   SemaRef.Diag(RHS->getBeginLoc(), diag::err_omp_loop_not_canonical_incr)
8274       << RHS->getSourceRange() << LCDecl;
8275   return true;
8276 }
8277 
8278 bool OpenMPIterationSpaceChecker::checkAndSetInc(Expr *S) {
8279   // Check incr-expr for canonical loop form and return true if it
8280   // does not conform.
8281   // OpenMP [2.6] Canonical loop form. Test-expr may be one of the following:
8282   //   ++var
8283   //   var++
8284   //   --var
8285   //   var--
8286   //   var += incr
8287   //   var -= incr
8288   //   var = var + incr
8289   //   var = incr + var
8290   //   var = var - incr
8291   //
8292   if (!S) {
8293     SemaRef.Diag(DefaultLoc, diag::err_omp_loop_not_canonical_incr) << LCDecl;
8294     return true;
8295   }
8296   if (auto *ExprTemp = dyn_cast<ExprWithCleanups>(S))
8297     if (!ExprTemp->cleanupsHaveSideEffects())
8298       S = ExprTemp->getSubExpr();
8299 
8300   IncrementSrcRange = S->getSourceRange();
8301   S = S->IgnoreParens();
8302   if (auto *UO = dyn_cast<UnaryOperator>(S)) {
8303     if (UO->isIncrementDecrementOp() &&
8304         getInitLCDecl(UO->getSubExpr()) == LCDecl)
8305       return setStep(SemaRef
8306                          .ActOnIntegerConstant(UO->getBeginLoc(),
8307                                                (UO->isDecrementOp() ? -1 : 1))
8308                          .get(),
8309                      /*Subtract=*/false);
8310   } else if (auto *BO = dyn_cast<BinaryOperator>(S)) {
8311     switch (BO->getOpcode()) {
8312     case BO_AddAssign:
8313     case BO_SubAssign:
8314       if (getInitLCDecl(BO->getLHS()) == LCDecl)
8315         return setStep(BO->getRHS(), BO->getOpcode() == BO_SubAssign);
8316       break;
8317     case BO_Assign:
8318       if (getInitLCDecl(BO->getLHS()) == LCDecl)
8319         return checkAndSetIncRHS(BO->getRHS());
8320       break;
8321     default:
8322       break;
8323     }
8324   } else if (auto *CE = dyn_cast<CXXOperatorCallExpr>(S)) {
8325     switch (CE->getOperator()) {
8326     case OO_PlusPlus:
8327     case OO_MinusMinus:
8328       if (getInitLCDecl(CE->getArg(0)) == LCDecl)
8329         return setStep(SemaRef
8330                            .ActOnIntegerConstant(
8331                                CE->getBeginLoc(),
8332                                ((CE->getOperator() == OO_MinusMinus) ? -1 : 1))
8333                            .get(),
8334                        /*Subtract=*/false);
8335       break;
8336     case OO_PlusEqual:
8337     case OO_MinusEqual:
8338       if (getInitLCDecl(CE->getArg(0)) == LCDecl)
8339         return setStep(CE->getArg(1), CE->getOperator() == OO_MinusEqual);
8340       break;
8341     case OO_Equal:
8342       if (getInitLCDecl(CE->getArg(0)) == LCDecl)
8343         return checkAndSetIncRHS(CE->getArg(1));
8344       break;
8345     default:
8346       break;
8347     }
8348   }
8349   if (dependent() || SemaRef.CurContext->isDependentContext())
8350     return false;
8351   SemaRef.Diag(S->getBeginLoc(), diag::err_omp_loop_not_canonical_incr)
8352       << S->getSourceRange() << LCDecl;
8353   return true;
8354 }
8355 
8356 static ExprResult
8357 tryBuildCapture(Sema &SemaRef, Expr *Capture,
8358                 llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
8359   if (SemaRef.CurContext->isDependentContext() || Capture->containsErrors())
8360     return Capture;
8361   if (Capture->isEvaluatable(SemaRef.Context, Expr::SE_AllowSideEffects))
8362     return SemaRef.PerformImplicitConversion(
8363         Capture->IgnoreImpCasts(), Capture->getType(), Sema::AA_Converting,
8364         /*AllowExplicit=*/true);
8365   auto I = Captures.find(Capture);
8366   if (I != Captures.end())
8367     return buildCapture(SemaRef, Capture, I->second);
8368   DeclRefExpr *Ref = nullptr;
8369   ExprResult Res = buildCapture(SemaRef, Capture, Ref);
8370   Captures[Capture] = Ref;
8371   return Res;
8372 }
8373 
8374 /// Calculate number of iterations, transforming to unsigned, if number of
8375 /// iterations may be larger than the original type.
8376 static Expr *
8377 calculateNumIters(Sema &SemaRef, Scope *S, SourceLocation DefaultLoc,
8378                   Expr *Lower, Expr *Upper, Expr *Step, QualType LCTy,
8379                   bool TestIsStrictOp, bool RoundToStep,
8380                   llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
8381   ExprResult NewStep = tryBuildCapture(SemaRef, Step, Captures);
8382   if (!NewStep.isUsable())
8383     return nullptr;
8384   llvm::APSInt LRes, SRes;
8385   bool IsLowerConst = false, IsStepConst = false;
8386   if (Optional<llvm::APSInt> Res =
8387           Lower->getIntegerConstantExpr(SemaRef.Context)) {
8388     LRes = *Res;
8389     IsLowerConst = true;
8390   }
8391   if (Optional<llvm::APSInt> Res =
8392           Step->getIntegerConstantExpr(SemaRef.Context)) {
8393     SRes = *Res;
8394     IsStepConst = true;
8395   }
8396   bool NoNeedToConvert = IsLowerConst && !RoundToStep &&
8397                          ((!TestIsStrictOp && LRes.isNonNegative()) ||
8398                           (TestIsStrictOp && LRes.isStrictlyPositive()));
8399   bool NeedToReorganize = false;
8400   // Check if any subexpressions in Lower -Step [+ 1] lead to overflow.
8401   if (!NoNeedToConvert && IsLowerConst &&
8402       (TestIsStrictOp || (RoundToStep && IsStepConst))) {
8403     NoNeedToConvert = true;
8404     if (RoundToStep) {
8405       unsigned BW = LRes.getBitWidth() > SRes.getBitWidth()
8406                         ? LRes.getBitWidth()
8407                         : SRes.getBitWidth();
8408       LRes = LRes.extend(BW + 1);
8409       LRes.setIsSigned(true);
8410       SRes = SRes.extend(BW + 1);
8411       SRes.setIsSigned(true);
8412       LRes -= SRes;
8413       NoNeedToConvert = LRes.trunc(BW).extend(BW + 1) == LRes;
8414       LRes = LRes.trunc(BW);
8415     }
8416     if (TestIsStrictOp) {
8417       unsigned BW = LRes.getBitWidth();
8418       LRes = LRes.extend(BW + 1);
8419       LRes.setIsSigned(true);
8420       ++LRes;
8421       NoNeedToConvert =
8422           NoNeedToConvert && LRes.trunc(BW).extend(BW + 1) == LRes;
8423       // truncate to the original bitwidth.
8424       LRes = LRes.trunc(BW);
8425     }
8426     NeedToReorganize = NoNeedToConvert;
8427   }
8428   llvm::APSInt URes;
8429   bool IsUpperConst = false;
8430   if (Optional<llvm::APSInt> Res =
8431           Upper->getIntegerConstantExpr(SemaRef.Context)) {
8432     URes = *Res;
8433     IsUpperConst = true;
8434   }
8435   if (NoNeedToConvert && IsLowerConst && IsUpperConst &&
8436       (!RoundToStep || IsStepConst)) {
8437     unsigned BW = LRes.getBitWidth() > URes.getBitWidth() ? LRes.getBitWidth()
8438                                                           : URes.getBitWidth();
8439     LRes = LRes.extend(BW + 1);
8440     LRes.setIsSigned(true);
8441     URes = URes.extend(BW + 1);
8442     URes.setIsSigned(true);
8443     URes -= LRes;
8444     NoNeedToConvert = URes.trunc(BW).extend(BW + 1) == URes;
8445     NeedToReorganize = NoNeedToConvert;
8446   }
8447   // If the boundaries are not constant or (Lower - Step [+ 1]) is not constant
8448   // or less than zero (Upper - (Lower - Step [+ 1]) may overflow) - promote to
8449   // unsigned.
8450   if ((!NoNeedToConvert || (LRes.isNegative() && !IsUpperConst)) &&
8451       !LCTy->isDependentType() && LCTy->isIntegerType()) {
8452     QualType LowerTy = Lower->getType();
8453     QualType UpperTy = Upper->getType();
8454     uint64_t LowerSize = SemaRef.Context.getTypeSize(LowerTy);
8455     uint64_t UpperSize = SemaRef.Context.getTypeSize(UpperTy);
8456     if ((LowerSize <= UpperSize && UpperTy->hasSignedIntegerRepresentation()) ||
8457         (LowerSize > UpperSize && LowerTy->hasSignedIntegerRepresentation())) {
8458       QualType CastType = SemaRef.Context.getIntTypeForBitwidth(
8459           LowerSize > UpperSize ? LowerSize : UpperSize, /*Signed=*/0);
8460       Upper =
8461           SemaRef
8462               .PerformImplicitConversion(
8463                   SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Upper).get(),
8464                   CastType, Sema::AA_Converting)
8465               .get();
8466       Lower = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Lower).get();
8467       NewStep = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, NewStep.get());
8468     }
8469   }
8470   if (!Lower || !Upper || NewStep.isInvalid())
8471     return nullptr;
8472 
8473   ExprResult Diff;
8474   // If need to reorganize, then calculate the form as Upper - (Lower - Step [+
8475   // 1]).
8476   if (NeedToReorganize) {
8477     Diff = Lower;
8478 
8479     if (RoundToStep) {
8480       // Lower - Step
8481       Diff =
8482           SemaRef.BuildBinOp(S, DefaultLoc, BO_Sub, Diff.get(), NewStep.get());
8483       if (!Diff.isUsable())
8484         return nullptr;
8485     }
8486 
8487     // Lower - Step [+ 1]
8488     if (TestIsStrictOp)
8489       Diff = SemaRef.BuildBinOp(
8490           S, DefaultLoc, BO_Add, Diff.get(),
8491           SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get());
8492     if (!Diff.isUsable())
8493       return nullptr;
8494 
8495     Diff = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Diff.get());
8496     if (!Diff.isUsable())
8497       return nullptr;
8498 
8499     // Upper - (Lower - Step [+ 1]).
8500     Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Sub, Upper, Diff.get());
8501     if (!Diff.isUsable())
8502       return nullptr;
8503   } else {
8504     Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Sub, Upper, Lower);
8505 
8506     if (!Diff.isUsable() && LCTy->getAsCXXRecordDecl()) {
8507       // BuildBinOp already emitted error, this one is to point user to upper
8508       // and lower bound, and to tell what is passed to 'operator-'.
8509       SemaRef.Diag(Upper->getBeginLoc(), diag::err_omp_loop_diff_cxx)
8510           << Upper->getSourceRange() << Lower->getSourceRange();
8511       return nullptr;
8512     }
8513 
8514     if (!Diff.isUsable())
8515       return nullptr;
8516 
8517     // Upper - Lower [- 1]
8518     if (TestIsStrictOp)
8519       Diff = SemaRef.BuildBinOp(
8520           S, DefaultLoc, BO_Sub, Diff.get(),
8521           SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get());
8522     if (!Diff.isUsable())
8523       return nullptr;
8524 
8525     if (RoundToStep) {
8526       // Upper - Lower [- 1] + Step
8527       Diff =
8528           SemaRef.BuildBinOp(S, DefaultLoc, BO_Add, Diff.get(), NewStep.get());
8529       if (!Diff.isUsable())
8530         return nullptr;
8531     }
8532   }
8533 
8534   // Parentheses (for dumping/debugging purposes only).
8535   Diff = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Diff.get());
8536   if (!Diff.isUsable())
8537     return nullptr;
8538 
8539   // (Upper - Lower [- 1] + Step) / Step or (Upper - Lower) / Step
8540   Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Div, Diff.get(), NewStep.get());
8541   if (!Diff.isUsable())
8542     return nullptr;
8543 
8544   return Diff.get();
8545 }
8546 
8547 /// Build the expression to calculate the number of iterations.
8548 Expr *OpenMPIterationSpaceChecker::buildNumIterations(
8549     Scope *S, ArrayRef<LoopIterationSpace> ResultIterSpaces, bool LimitedType,
8550     llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const {
8551   QualType VarType = LCDecl->getType().getNonReferenceType();
8552   if (!VarType->isIntegerType() && !VarType->isPointerType() &&
8553       !SemaRef.getLangOpts().CPlusPlus)
8554     return nullptr;
8555   Expr *LBVal = LB;
8556   Expr *UBVal = UB;
8557   // LB = TestIsLessOp.getValue() ? min(LB(MinVal), LB(MaxVal)) :
8558   // max(LB(MinVal), LB(MaxVal))
8559   if (InitDependOnLC) {
8560     const LoopIterationSpace &IS = ResultIterSpaces[*InitDependOnLC - 1];
8561     if (!IS.MinValue || !IS.MaxValue)
8562       return nullptr;
8563     // OuterVar = Min
8564     ExprResult MinValue =
8565         SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, IS.MinValue);
8566     if (!MinValue.isUsable())
8567       return nullptr;
8568 
8569     ExprResult LBMinVal = SemaRef.BuildBinOp(S, DefaultLoc, BO_Assign,
8570                                              IS.CounterVar, MinValue.get());
8571     if (!LBMinVal.isUsable())
8572       return nullptr;
8573     // OuterVar = Min, LBVal
8574     LBMinVal =
8575         SemaRef.BuildBinOp(S, DefaultLoc, BO_Comma, LBMinVal.get(), LBVal);
8576     if (!LBMinVal.isUsable())
8577       return nullptr;
8578     // (OuterVar = Min, LBVal)
8579     LBMinVal = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, LBMinVal.get());
8580     if (!LBMinVal.isUsable())
8581       return nullptr;
8582 
8583     // OuterVar = Max
8584     ExprResult MaxValue =
8585         SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, IS.MaxValue);
8586     if (!MaxValue.isUsable())
8587       return nullptr;
8588 
8589     ExprResult LBMaxVal = SemaRef.BuildBinOp(S, DefaultLoc, BO_Assign,
8590                                              IS.CounterVar, MaxValue.get());
8591     if (!LBMaxVal.isUsable())
8592       return nullptr;
8593     // OuterVar = Max, LBVal
8594     LBMaxVal =
8595         SemaRef.BuildBinOp(S, DefaultLoc, BO_Comma, LBMaxVal.get(), LBVal);
8596     if (!LBMaxVal.isUsable())
8597       return nullptr;
8598     // (OuterVar = Max, LBVal)
8599     LBMaxVal = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, LBMaxVal.get());
8600     if (!LBMaxVal.isUsable())
8601       return nullptr;
8602 
8603     Expr *LBMin = tryBuildCapture(SemaRef, LBMinVal.get(), Captures).get();
8604     Expr *LBMax = tryBuildCapture(SemaRef, LBMaxVal.get(), Captures).get();
8605     if (!LBMin || !LBMax)
8606       return nullptr;
8607     // LB(MinVal) < LB(MaxVal)
8608     ExprResult MinLessMaxRes =
8609         SemaRef.BuildBinOp(S, DefaultLoc, BO_LT, LBMin, LBMax);
8610     if (!MinLessMaxRes.isUsable())
8611       return nullptr;
8612     Expr *MinLessMax =
8613         tryBuildCapture(SemaRef, MinLessMaxRes.get(), Captures).get();
8614     if (!MinLessMax)
8615       return nullptr;
8616     if (*TestIsLessOp) {
8617       // LB(MinVal) < LB(MaxVal) ? LB(MinVal) : LB(MaxVal) - min(LB(MinVal),
8618       // LB(MaxVal))
8619       ExprResult MinLB = SemaRef.ActOnConditionalOp(DefaultLoc, DefaultLoc,
8620                                                     MinLessMax, LBMin, LBMax);
8621       if (!MinLB.isUsable())
8622         return nullptr;
8623       LBVal = MinLB.get();
8624     } else {
8625       // LB(MinVal) < LB(MaxVal) ? LB(MaxVal) : LB(MinVal) - max(LB(MinVal),
8626       // LB(MaxVal))
8627       ExprResult MaxLB = SemaRef.ActOnConditionalOp(DefaultLoc, DefaultLoc,
8628                                                     MinLessMax, LBMax, LBMin);
8629       if (!MaxLB.isUsable())
8630         return nullptr;
8631       LBVal = MaxLB.get();
8632     }
8633   }
8634   // UB = TestIsLessOp.getValue() ? max(UB(MinVal), UB(MaxVal)) :
8635   // min(UB(MinVal), UB(MaxVal))
8636   if (CondDependOnLC) {
8637     const LoopIterationSpace &IS = ResultIterSpaces[*CondDependOnLC - 1];
8638     if (!IS.MinValue || !IS.MaxValue)
8639       return nullptr;
8640     // OuterVar = Min
8641     ExprResult MinValue =
8642         SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, IS.MinValue);
8643     if (!MinValue.isUsable())
8644       return nullptr;
8645 
8646     ExprResult UBMinVal = SemaRef.BuildBinOp(S, DefaultLoc, BO_Assign,
8647                                              IS.CounterVar, MinValue.get());
8648     if (!UBMinVal.isUsable())
8649       return nullptr;
8650     // OuterVar = Min, UBVal
8651     UBMinVal =
8652         SemaRef.BuildBinOp(S, DefaultLoc, BO_Comma, UBMinVal.get(), UBVal);
8653     if (!UBMinVal.isUsable())
8654       return nullptr;
8655     // (OuterVar = Min, UBVal)
8656     UBMinVal = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, UBMinVal.get());
8657     if (!UBMinVal.isUsable())
8658       return nullptr;
8659 
8660     // OuterVar = Max
8661     ExprResult MaxValue =
8662         SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, IS.MaxValue);
8663     if (!MaxValue.isUsable())
8664       return nullptr;
8665 
8666     ExprResult UBMaxVal = SemaRef.BuildBinOp(S, DefaultLoc, BO_Assign,
8667                                              IS.CounterVar, MaxValue.get());
8668     if (!UBMaxVal.isUsable())
8669       return nullptr;
8670     // OuterVar = Max, UBVal
8671     UBMaxVal =
8672         SemaRef.BuildBinOp(S, DefaultLoc, BO_Comma, UBMaxVal.get(), UBVal);
8673     if (!UBMaxVal.isUsable())
8674       return nullptr;
8675     // (OuterVar = Max, UBVal)
8676     UBMaxVal = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, UBMaxVal.get());
8677     if (!UBMaxVal.isUsable())
8678       return nullptr;
8679 
8680     Expr *UBMin = tryBuildCapture(SemaRef, UBMinVal.get(), Captures).get();
8681     Expr *UBMax = tryBuildCapture(SemaRef, UBMaxVal.get(), Captures).get();
8682     if (!UBMin || !UBMax)
8683       return nullptr;
8684     // UB(MinVal) > UB(MaxVal)
8685     ExprResult MinGreaterMaxRes =
8686         SemaRef.BuildBinOp(S, DefaultLoc, BO_GT, UBMin, UBMax);
8687     if (!MinGreaterMaxRes.isUsable())
8688       return nullptr;
8689     Expr *MinGreaterMax =
8690         tryBuildCapture(SemaRef, MinGreaterMaxRes.get(), Captures).get();
8691     if (!MinGreaterMax)
8692       return nullptr;
8693     if (*TestIsLessOp) {
8694       // UB(MinVal) > UB(MaxVal) ? UB(MinVal) : UB(MaxVal) - max(UB(MinVal),
8695       // UB(MaxVal))
8696       ExprResult MaxUB = SemaRef.ActOnConditionalOp(
8697           DefaultLoc, DefaultLoc, MinGreaterMax, UBMin, UBMax);
8698       if (!MaxUB.isUsable())
8699         return nullptr;
8700       UBVal = MaxUB.get();
8701     } else {
8702       // UB(MinVal) > UB(MaxVal) ? UB(MaxVal) : UB(MinVal) - min(UB(MinVal),
8703       // UB(MaxVal))
8704       ExprResult MinUB = SemaRef.ActOnConditionalOp(
8705           DefaultLoc, DefaultLoc, MinGreaterMax, UBMax, UBMin);
8706       if (!MinUB.isUsable())
8707         return nullptr;
8708       UBVal = MinUB.get();
8709     }
8710   }
8711   Expr *UBExpr = TestIsLessOp.getValue() ? UBVal : LBVal;
8712   Expr *LBExpr = TestIsLessOp.getValue() ? LBVal : UBVal;
8713   Expr *Upper = tryBuildCapture(SemaRef, UBExpr, Captures).get();
8714   Expr *Lower = tryBuildCapture(SemaRef, LBExpr, Captures).get();
8715   if (!Upper || !Lower)
8716     return nullptr;
8717 
8718   ExprResult Diff = calculateNumIters(SemaRef, S, DefaultLoc, Lower, Upper,
8719                                       Step, VarType, TestIsStrictOp,
8720                                       /*RoundToStep=*/true, Captures);
8721   if (!Diff.isUsable())
8722     return nullptr;
8723 
8724   // OpenMP runtime requires 32-bit or 64-bit loop variables.
8725   QualType Type = Diff.get()->getType();
8726   ASTContext &C = SemaRef.Context;
8727   bool UseVarType = VarType->hasIntegerRepresentation() &&
8728                     C.getTypeSize(Type) > C.getTypeSize(VarType);
8729   if (!Type->isIntegerType() || UseVarType) {
8730     unsigned NewSize =
8731         UseVarType ? C.getTypeSize(VarType) : C.getTypeSize(Type);
8732     bool IsSigned = UseVarType ? VarType->hasSignedIntegerRepresentation()
8733                                : Type->hasSignedIntegerRepresentation();
8734     Type = C.getIntTypeForBitwidth(NewSize, IsSigned);
8735     if (!SemaRef.Context.hasSameType(Diff.get()->getType(), Type)) {
8736       Diff = SemaRef.PerformImplicitConversion(
8737           Diff.get(), Type, Sema::AA_Converting, /*AllowExplicit=*/true);
8738       if (!Diff.isUsable())
8739         return nullptr;
8740     }
8741   }
8742   if (LimitedType) {
8743     unsigned NewSize = (C.getTypeSize(Type) > 32) ? 64 : 32;
8744     if (NewSize != C.getTypeSize(Type)) {
8745       if (NewSize < C.getTypeSize(Type)) {
8746         assert(NewSize == 64 && "incorrect loop var size");
8747         SemaRef.Diag(DefaultLoc, diag::warn_omp_loop_64_bit_var)
8748             << InitSrcRange << ConditionSrcRange;
8749       }
8750       QualType NewType = C.getIntTypeForBitwidth(
8751           NewSize, Type->hasSignedIntegerRepresentation() ||
8752                        C.getTypeSize(Type) < NewSize);
8753       if (!SemaRef.Context.hasSameType(Diff.get()->getType(), NewType)) {
8754         Diff = SemaRef.PerformImplicitConversion(Diff.get(), NewType,
8755                                                  Sema::AA_Converting, true);
8756         if (!Diff.isUsable())
8757           return nullptr;
8758       }
8759     }
8760   }
8761 
8762   return Diff.get();
8763 }
8764 
8765 std::pair<Expr *, Expr *> OpenMPIterationSpaceChecker::buildMinMaxValues(
8766     Scope *S, llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const {
8767   // Do not build for iterators, they cannot be used in non-rectangular loop
8768   // nests.
8769   if (LCDecl->getType()->isRecordType())
8770     return std::make_pair(nullptr, nullptr);
8771   // If we subtract, the min is in the condition, otherwise the min is in the
8772   // init value.
8773   Expr *MinExpr = nullptr;
8774   Expr *MaxExpr = nullptr;
8775   Expr *LBExpr = TestIsLessOp.getValue() ? LB : UB;
8776   Expr *UBExpr = TestIsLessOp.getValue() ? UB : LB;
8777   bool LBNonRect = TestIsLessOp.getValue() ? InitDependOnLC.hasValue()
8778                                            : CondDependOnLC.hasValue();
8779   bool UBNonRect = TestIsLessOp.getValue() ? CondDependOnLC.hasValue()
8780                                            : InitDependOnLC.hasValue();
8781   Expr *Lower =
8782       LBNonRect ? LBExpr : tryBuildCapture(SemaRef, LBExpr, Captures).get();
8783   Expr *Upper =
8784       UBNonRect ? UBExpr : tryBuildCapture(SemaRef, UBExpr, Captures).get();
8785   if (!Upper || !Lower)
8786     return std::make_pair(nullptr, nullptr);
8787 
8788   if (*TestIsLessOp)
8789     MinExpr = Lower;
8790   else
8791     MaxExpr = Upper;
8792 
8793   // Build minimum/maximum value based on number of iterations.
8794   QualType VarType = LCDecl->getType().getNonReferenceType();
8795 
8796   ExprResult Diff = calculateNumIters(SemaRef, S, DefaultLoc, Lower, Upper,
8797                                       Step, VarType, TestIsStrictOp,
8798                                       /*RoundToStep=*/false, Captures);
8799   if (!Diff.isUsable())
8800     return std::make_pair(nullptr, nullptr);
8801 
8802   // ((Upper - Lower [- 1]) / Step) * Step
8803   // Parentheses (for dumping/debugging purposes only).
8804   Diff = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Diff.get());
8805   if (!Diff.isUsable())
8806     return std::make_pair(nullptr, nullptr);
8807 
8808   ExprResult NewStep = tryBuildCapture(SemaRef, Step, Captures);
8809   if (!NewStep.isUsable())
8810     return std::make_pair(nullptr, nullptr);
8811   Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Mul, Diff.get(), NewStep.get());
8812   if (!Diff.isUsable())
8813     return std::make_pair(nullptr, nullptr);
8814 
8815   // Parentheses (for dumping/debugging purposes only).
8816   Diff = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Diff.get());
8817   if (!Diff.isUsable())
8818     return std::make_pair(nullptr, nullptr);
8819 
8820   // Convert to the ptrdiff_t, if original type is pointer.
8821   if (VarType->isAnyPointerType() &&
8822       !SemaRef.Context.hasSameType(
8823           Diff.get()->getType(),
8824           SemaRef.Context.getUnsignedPointerDiffType())) {
8825     Diff = SemaRef.PerformImplicitConversion(
8826         Diff.get(), SemaRef.Context.getUnsignedPointerDiffType(),
8827         Sema::AA_Converting, /*AllowExplicit=*/true);
8828   }
8829   if (!Diff.isUsable())
8830     return std::make_pair(nullptr, nullptr);
8831 
8832   if (*TestIsLessOp) {
8833     // MinExpr = Lower;
8834     // MaxExpr = Lower + (((Upper - Lower [- 1]) / Step) * Step)
8835     Diff = SemaRef.BuildBinOp(
8836         S, DefaultLoc, BO_Add,
8837         SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Lower).get(),
8838         Diff.get());
8839     if (!Diff.isUsable())
8840       return std::make_pair(nullptr, nullptr);
8841   } else {
8842     // MaxExpr = Upper;
8843     // MinExpr = Upper - (((Upper - Lower [- 1]) / Step) * Step)
8844     Diff = SemaRef.BuildBinOp(
8845         S, DefaultLoc, BO_Sub,
8846         SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Upper).get(),
8847         Diff.get());
8848     if (!Diff.isUsable())
8849       return std::make_pair(nullptr, nullptr);
8850   }
8851 
8852   // Convert to the original type.
8853   if (SemaRef.Context.hasSameType(Diff.get()->getType(), VarType))
8854     Diff = SemaRef.PerformImplicitConversion(Diff.get(), VarType,
8855                                              Sema::AA_Converting,
8856                                              /*AllowExplicit=*/true);
8857   if (!Diff.isUsable())
8858     return std::make_pair(nullptr, nullptr);
8859 
8860   Sema::TentativeAnalysisScope Trap(SemaRef);
8861   Diff = SemaRef.ActOnFinishFullExpr(Diff.get(), /*DiscardedValue=*/false);
8862   if (!Diff.isUsable())
8863     return std::make_pair(nullptr, nullptr);
8864 
8865   if (*TestIsLessOp)
8866     MaxExpr = Diff.get();
8867   else
8868     MinExpr = Diff.get();
8869 
8870   return std::make_pair(MinExpr, MaxExpr);
8871 }
8872 
8873 Expr *OpenMPIterationSpaceChecker::buildFinalCondition(Scope *S) const {
8874   if (InitDependOnLC || CondDependOnLC)
8875     return Condition;
8876   return nullptr;
8877 }
8878 
8879 Expr *OpenMPIterationSpaceChecker::buildPreCond(
8880     Scope *S, Expr *Cond,
8881     llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const {
8882   // Do not build a precondition when the condition/initialization is dependent
8883   // to prevent pessimistic early loop exit.
8884   // TODO: this can be improved by calculating min/max values but not sure that
8885   // it will be very effective.
8886   if (CondDependOnLC || InitDependOnLC)
8887     return SemaRef
8888         .PerformImplicitConversion(
8889             SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get(),
8890             SemaRef.Context.BoolTy, /*Action=*/Sema::AA_Casting,
8891             /*AllowExplicit=*/true)
8892         .get();
8893 
8894   // Try to build LB <op> UB, where <op> is <, >, <=, or >=.
8895   Sema::TentativeAnalysisScope Trap(SemaRef);
8896 
8897   ExprResult NewLB = tryBuildCapture(SemaRef, LB, Captures);
8898   ExprResult NewUB = tryBuildCapture(SemaRef, UB, Captures);
8899   if (!NewLB.isUsable() || !NewUB.isUsable())
8900     return nullptr;
8901 
8902   ExprResult CondExpr = SemaRef.BuildBinOp(
8903       S, DefaultLoc,
8904       TestIsLessOp.getValue() ? (TestIsStrictOp ? BO_LT : BO_LE)
8905                               : (TestIsStrictOp ? BO_GT : BO_GE),
8906       NewLB.get(), NewUB.get());
8907   if (CondExpr.isUsable()) {
8908     if (!SemaRef.Context.hasSameUnqualifiedType(CondExpr.get()->getType(),
8909                                                 SemaRef.Context.BoolTy))
8910       CondExpr = SemaRef.PerformImplicitConversion(
8911           CondExpr.get(), SemaRef.Context.BoolTy, /*Action=*/Sema::AA_Casting,
8912           /*AllowExplicit=*/true);
8913   }
8914 
8915   // Otherwise use original loop condition and evaluate it in runtime.
8916   return CondExpr.isUsable() ? CondExpr.get() : Cond;
8917 }
8918 
8919 /// Build reference expression to the counter be used for codegen.
8920 DeclRefExpr *OpenMPIterationSpaceChecker::buildCounterVar(
8921     llvm::MapVector<const Expr *, DeclRefExpr *> &Captures,
8922     DSAStackTy &DSA) const {
8923   auto *VD = dyn_cast<VarDecl>(LCDecl);
8924   if (!VD) {
8925     VD = SemaRef.isOpenMPCapturedDecl(LCDecl);
8926     DeclRefExpr *Ref = buildDeclRefExpr(
8927         SemaRef, VD, VD->getType().getNonReferenceType(), DefaultLoc);
8928     const DSAStackTy::DSAVarData Data =
8929         DSA.getTopDSA(LCDecl, /*FromParent=*/false);
8930     // If the loop control decl is explicitly marked as private, do not mark it
8931     // as captured again.
8932     if (!isOpenMPPrivate(Data.CKind) || !Data.RefExpr)
8933       Captures.insert(std::make_pair(LCRef, Ref));
8934     return Ref;
8935   }
8936   return cast<DeclRefExpr>(LCRef);
8937 }
8938 
8939 Expr *OpenMPIterationSpaceChecker::buildPrivateCounterVar() const {
8940   if (LCDecl && !LCDecl->isInvalidDecl()) {
8941     QualType Type = LCDecl->getType().getNonReferenceType();
8942     VarDecl *PrivateVar = buildVarDecl(
8943         SemaRef, DefaultLoc, Type, LCDecl->getName(),
8944         LCDecl->hasAttrs() ? &LCDecl->getAttrs() : nullptr,
8945         isa<VarDecl>(LCDecl)
8946             ? buildDeclRefExpr(SemaRef, cast<VarDecl>(LCDecl), Type, DefaultLoc)
8947             : nullptr);
8948     if (PrivateVar->isInvalidDecl())
8949       return nullptr;
8950     return buildDeclRefExpr(SemaRef, PrivateVar, Type, DefaultLoc);
8951   }
8952   return nullptr;
8953 }
8954 
8955 /// Build initialization of the counter to be used for codegen.
8956 Expr *OpenMPIterationSpaceChecker::buildCounterInit() const { return LB; }
8957 
8958 /// Build step of the counter be used for codegen.
8959 Expr *OpenMPIterationSpaceChecker::buildCounterStep() const { return Step; }
8960 
8961 Expr *OpenMPIterationSpaceChecker::buildOrderedLoopData(
8962     Scope *S, Expr *Counter,
8963     llvm::MapVector<const Expr *, DeclRefExpr *> &Captures, SourceLocation Loc,
8964     Expr *Inc, OverloadedOperatorKind OOK) {
8965   Expr *Cnt = SemaRef.DefaultLvalueConversion(Counter).get();
8966   if (!Cnt)
8967     return nullptr;
8968   if (Inc) {
8969     assert((OOK == OO_Plus || OOK == OO_Minus) &&
8970            "Expected only + or - operations for depend clauses.");
8971     BinaryOperatorKind BOK = (OOK == OO_Plus) ? BO_Add : BO_Sub;
8972     Cnt = SemaRef.BuildBinOp(S, Loc, BOK, Cnt, Inc).get();
8973     if (!Cnt)
8974       return nullptr;
8975   }
8976   QualType VarType = LCDecl->getType().getNonReferenceType();
8977   if (!VarType->isIntegerType() && !VarType->isPointerType() &&
8978       !SemaRef.getLangOpts().CPlusPlus)
8979     return nullptr;
8980   // Upper - Lower
8981   Expr *Upper = TestIsLessOp.getValue()
8982                     ? Cnt
8983                     : tryBuildCapture(SemaRef, LB, Captures).get();
8984   Expr *Lower = TestIsLessOp.getValue()
8985                     ? tryBuildCapture(SemaRef, LB, Captures).get()
8986                     : Cnt;
8987   if (!Upper || !Lower)
8988     return nullptr;
8989 
8990   ExprResult Diff = calculateNumIters(
8991       SemaRef, S, DefaultLoc, Lower, Upper, Step, VarType,
8992       /*TestIsStrictOp=*/false, /*RoundToStep=*/false, Captures);
8993   if (!Diff.isUsable())
8994     return nullptr;
8995 
8996   return Diff.get();
8997 }
8998 } // namespace
8999 
9000 void Sema::ActOnOpenMPLoopInitialization(SourceLocation ForLoc, Stmt *Init) {
9001   assert(getLangOpts().OpenMP && "OpenMP is not active.");
9002   assert(Init && "Expected loop in canonical form.");
9003   unsigned AssociatedLoops = DSAStack->getAssociatedLoops();
9004   if (AssociatedLoops > 0 &&
9005       isOpenMPLoopDirective(DSAStack->getCurrentDirective())) {
9006     DSAStack->loopStart();
9007     OpenMPIterationSpaceChecker ISC(*this, /*SupportsNonRectangular=*/true,
9008                                     *DSAStack, ForLoc);
9009     if (!ISC.checkAndSetInit(Init, /*EmitDiags=*/false)) {
9010       if (ValueDecl *D = ISC.getLoopDecl()) {
9011         auto *VD = dyn_cast<VarDecl>(D);
9012         DeclRefExpr *PrivateRef = nullptr;
9013         if (!VD) {
9014           if (VarDecl *Private = isOpenMPCapturedDecl(D)) {
9015             VD = Private;
9016           } else {
9017             PrivateRef = buildCapture(*this, D, ISC.getLoopDeclRefExpr(),
9018                                       /*WithInit=*/false);
9019             VD = cast<VarDecl>(PrivateRef->getDecl());
9020           }
9021         }
9022         DSAStack->addLoopControlVariable(D, VD);
9023         const Decl *LD = DSAStack->getPossiblyLoopCunter();
9024         if (LD != D->getCanonicalDecl()) {
9025           DSAStack->resetPossibleLoopCounter();
9026           if (auto *Var = dyn_cast_or_null<VarDecl>(LD))
9027             MarkDeclarationsReferencedInExpr(
9028                 buildDeclRefExpr(*this, const_cast<VarDecl *>(Var),
9029                                  Var->getType().getNonLValueExprType(Context),
9030                                  ForLoc, /*RefersToCapture=*/true));
9031         }
9032         OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
9033         // OpenMP [2.14.1.1, Data-sharing Attribute Rules for Variables
9034         // Referenced in a Construct, C/C++]. The loop iteration variable in the
9035         // associated for-loop of a simd construct with just one associated
9036         // for-loop may be listed in a linear clause with a constant-linear-step
9037         // that is the increment of the associated for-loop. The loop iteration
9038         // variable(s) in the associated for-loop(s) of a for or parallel for
9039         // construct may be listed in a private or lastprivate clause.
9040         DSAStackTy::DSAVarData DVar =
9041             DSAStack->getTopDSA(D, /*FromParent=*/false);
9042         // If LoopVarRefExpr is nullptr it means the corresponding loop variable
9043         // is declared in the loop and it is predetermined as a private.
9044         Expr *LoopDeclRefExpr = ISC.getLoopDeclRefExpr();
9045         OpenMPClauseKind PredeterminedCKind =
9046             isOpenMPSimdDirective(DKind)
9047                 ? (DSAStack->hasMutipleLoops() ? OMPC_lastprivate : OMPC_linear)
9048                 : OMPC_private;
9049         if (((isOpenMPSimdDirective(DKind) && DVar.CKind != OMPC_unknown &&
9050               DVar.CKind != PredeterminedCKind && DVar.RefExpr &&
9051               (LangOpts.OpenMP <= 45 || (DVar.CKind != OMPC_lastprivate &&
9052                                          DVar.CKind != OMPC_private))) ||
9053              ((isOpenMPWorksharingDirective(DKind) || DKind == OMPD_taskloop ||
9054                DKind == OMPD_master_taskloop || DKind == OMPD_masked_taskloop ||
9055                DKind == OMPD_parallel_master_taskloop ||
9056                DKind == OMPD_parallel_masked_taskloop ||
9057                isOpenMPDistributeDirective(DKind)) &&
9058               !isOpenMPSimdDirective(DKind) && DVar.CKind != OMPC_unknown &&
9059               DVar.CKind != OMPC_private && DVar.CKind != OMPC_lastprivate)) &&
9060             (DVar.CKind != OMPC_private || DVar.RefExpr)) {
9061           Diag(Init->getBeginLoc(), diag::err_omp_loop_var_dsa)
9062               << getOpenMPClauseName(DVar.CKind)
9063               << getOpenMPDirectiveName(DKind)
9064               << getOpenMPClauseName(PredeterminedCKind);
9065           if (DVar.RefExpr == nullptr)
9066             DVar.CKind = PredeterminedCKind;
9067           reportOriginalDsa(*this, DSAStack, D, DVar,
9068                             /*IsLoopIterVar=*/true);
9069         } else if (LoopDeclRefExpr) {
9070           // Make the loop iteration variable private (for worksharing
9071           // constructs), linear (for simd directives with the only one
9072           // associated loop) or lastprivate (for simd directives with several
9073           // collapsed or ordered loops).
9074           if (DVar.CKind == OMPC_unknown)
9075             DSAStack->addDSA(D, LoopDeclRefExpr, PredeterminedCKind,
9076                              PrivateRef);
9077         }
9078       }
9079     }
9080     DSAStack->setAssociatedLoops(AssociatedLoops - 1);
9081   }
9082 }
9083 
9084 /// Called on a for stmt to check and extract its iteration space
9085 /// for further processing (such as collapsing).
9086 static bool checkOpenMPIterationSpace(
9087     OpenMPDirectiveKind DKind, Stmt *S, Sema &SemaRef, DSAStackTy &DSA,
9088     unsigned CurrentNestedLoopCount, unsigned NestedLoopCount,
9089     unsigned TotalNestedLoopCount, Expr *CollapseLoopCountExpr,
9090     Expr *OrderedLoopCountExpr,
9091     Sema::VarsWithInheritedDSAType &VarsWithImplicitDSA,
9092     llvm::MutableArrayRef<LoopIterationSpace> ResultIterSpaces,
9093     llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
9094   bool SupportsNonRectangular = !isOpenMPLoopTransformationDirective(DKind);
9095   // OpenMP [2.9.1, Canonical Loop Form]
9096   //   for (init-expr; test-expr; incr-expr) structured-block
9097   //   for (range-decl: range-expr) structured-block
9098   if (auto *CanonLoop = dyn_cast_or_null<OMPCanonicalLoop>(S))
9099     S = CanonLoop->getLoopStmt();
9100   auto *For = dyn_cast_or_null<ForStmt>(S);
9101   auto *CXXFor = dyn_cast_or_null<CXXForRangeStmt>(S);
9102   // Ranged for is supported only in OpenMP 5.0.
9103   if (!For && (SemaRef.LangOpts.OpenMP <= 45 || !CXXFor)) {
9104     SemaRef.Diag(S->getBeginLoc(), diag::err_omp_not_for)
9105         << (CollapseLoopCountExpr != nullptr || OrderedLoopCountExpr != nullptr)
9106         << getOpenMPDirectiveName(DKind) << TotalNestedLoopCount
9107         << (CurrentNestedLoopCount > 0) << CurrentNestedLoopCount;
9108     if (TotalNestedLoopCount > 1) {
9109       if (CollapseLoopCountExpr && OrderedLoopCountExpr)
9110         SemaRef.Diag(DSA.getConstructLoc(),
9111                      diag::note_omp_collapse_ordered_expr)
9112             << 2 << CollapseLoopCountExpr->getSourceRange()
9113             << OrderedLoopCountExpr->getSourceRange();
9114       else if (CollapseLoopCountExpr)
9115         SemaRef.Diag(CollapseLoopCountExpr->getExprLoc(),
9116                      diag::note_omp_collapse_ordered_expr)
9117             << 0 << CollapseLoopCountExpr->getSourceRange();
9118       else
9119         SemaRef.Diag(OrderedLoopCountExpr->getExprLoc(),
9120                      diag::note_omp_collapse_ordered_expr)
9121             << 1 << OrderedLoopCountExpr->getSourceRange();
9122     }
9123     return true;
9124   }
9125   assert(((For && For->getBody()) || (CXXFor && CXXFor->getBody())) &&
9126          "No loop body.");
9127   // Postpone analysis in dependent contexts for ranged for loops.
9128   if (CXXFor && SemaRef.CurContext->isDependentContext())
9129     return false;
9130 
9131   OpenMPIterationSpaceChecker ISC(SemaRef, SupportsNonRectangular, DSA,
9132                                   For ? For->getForLoc() : CXXFor->getForLoc());
9133 
9134   // Check init.
9135   Stmt *Init = For ? For->getInit() : CXXFor->getBeginStmt();
9136   if (ISC.checkAndSetInit(Init))
9137     return true;
9138 
9139   bool HasErrors = false;
9140 
9141   // Check loop variable's type.
9142   if (ValueDecl *LCDecl = ISC.getLoopDecl()) {
9143     // OpenMP [2.6, Canonical Loop Form]
9144     // Var is one of the following:
9145     //   A variable of signed or unsigned integer type.
9146     //   For C++, a variable of a random access iterator type.
9147     //   For C, a variable of a pointer type.
9148     QualType VarType = LCDecl->getType().getNonReferenceType();
9149     if (!VarType->isDependentType() && !VarType->isIntegerType() &&
9150         !VarType->isPointerType() &&
9151         !(SemaRef.getLangOpts().CPlusPlus && VarType->isOverloadableType())) {
9152       SemaRef.Diag(Init->getBeginLoc(), diag::err_omp_loop_variable_type)
9153           << SemaRef.getLangOpts().CPlusPlus;
9154       HasErrors = true;
9155     }
9156 
9157     // OpenMP, 2.14.1.1 Data-sharing Attribute Rules for Variables Referenced in
9158     // a Construct
9159     // The loop iteration variable(s) in the associated for-loop(s) of a for or
9160     // parallel for construct is (are) private.
9161     // The loop iteration variable in the associated for-loop of a simd
9162     // construct with just one associated for-loop is linear with a
9163     // constant-linear-step that is the increment of the associated for-loop.
9164     // Exclude loop var from the list of variables with implicitly defined data
9165     // sharing attributes.
9166     VarsWithImplicitDSA.erase(LCDecl);
9167 
9168     assert(isOpenMPLoopDirective(DKind) && "DSA for non-loop vars");
9169 
9170     // Check test-expr.
9171     HasErrors |= ISC.checkAndSetCond(For ? For->getCond() : CXXFor->getCond());
9172 
9173     // Check incr-expr.
9174     HasErrors |= ISC.checkAndSetInc(For ? For->getInc() : CXXFor->getInc());
9175   }
9176 
9177   if (ISC.dependent() || SemaRef.CurContext->isDependentContext() || HasErrors)
9178     return HasErrors;
9179 
9180   // Build the loop's iteration space representation.
9181   ResultIterSpaces[CurrentNestedLoopCount].PreCond = ISC.buildPreCond(
9182       DSA.getCurScope(), For ? For->getCond() : CXXFor->getCond(), Captures);
9183   ResultIterSpaces[CurrentNestedLoopCount].NumIterations =
9184       ISC.buildNumIterations(DSA.getCurScope(), ResultIterSpaces,
9185                              (isOpenMPWorksharingDirective(DKind) ||
9186                               isOpenMPGenericLoopDirective(DKind) ||
9187                               isOpenMPTaskLoopDirective(DKind) ||
9188                               isOpenMPDistributeDirective(DKind) ||
9189                               isOpenMPLoopTransformationDirective(DKind)),
9190                              Captures);
9191   ResultIterSpaces[CurrentNestedLoopCount].CounterVar =
9192       ISC.buildCounterVar(Captures, DSA);
9193   ResultIterSpaces[CurrentNestedLoopCount].PrivateCounterVar =
9194       ISC.buildPrivateCounterVar();
9195   ResultIterSpaces[CurrentNestedLoopCount].CounterInit = ISC.buildCounterInit();
9196   ResultIterSpaces[CurrentNestedLoopCount].CounterStep = ISC.buildCounterStep();
9197   ResultIterSpaces[CurrentNestedLoopCount].InitSrcRange = ISC.getInitSrcRange();
9198   ResultIterSpaces[CurrentNestedLoopCount].CondSrcRange =
9199       ISC.getConditionSrcRange();
9200   ResultIterSpaces[CurrentNestedLoopCount].IncSrcRange =
9201       ISC.getIncrementSrcRange();
9202   ResultIterSpaces[CurrentNestedLoopCount].Subtract = ISC.shouldSubtractStep();
9203   ResultIterSpaces[CurrentNestedLoopCount].IsStrictCompare =
9204       ISC.isStrictTestOp();
9205   std::tie(ResultIterSpaces[CurrentNestedLoopCount].MinValue,
9206            ResultIterSpaces[CurrentNestedLoopCount].MaxValue) =
9207       ISC.buildMinMaxValues(DSA.getCurScope(), Captures);
9208   ResultIterSpaces[CurrentNestedLoopCount].FinalCondition =
9209       ISC.buildFinalCondition(DSA.getCurScope());
9210   ResultIterSpaces[CurrentNestedLoopCount].IsNonRectangularLB =
9211       ISC.doesInitDependOnLC();
9212   ResultIterSpaces[CurrentNestedLoopCount].IsNonRectangularUB =
9213       ISC.doesCondDependOnLC();
9214   ResultIterSpaces[CurrentNestedLoopCount].LoopDependentIdx =
9215       ISC.getLoopDependentIdx();
9216 
9217   HasErrors |=
9218       (ResultIterSpaces[CurrentNestedLoopCount].PreCond == nullptr ||
9219        ResultIterSpaces[CurrentNestedLoopCount].NumIterations == nullptr ||
9220        ResultIterSpaces[CurrentNestedLoopCount].CounterVar == nullptr ||
9221        ResultIterSpaces[CurrentNestedLoopCount].PrivateCounterVar == nullptr ||
9222        ResultIterSpaces[CurrentNestedLoopCount].CounterInit == nullptr ||
9223        ResultIterSpaces[CurrentNestedLoopCount].CounterStep == nullptr);
9224   if (!HasErrors && DSA.isOrderedRegion()) {
9225     if (DSA.getOrderedRegionParam().second->getNumForLoops()) {
9226       if (CurrentNestedLoopCount <
9227           DSA.getOrderedRegionParam().second->getLoopNumIterations().size()) {
9228         DSA.getOrderedRegionParam().second->setLoopNumIterations(
9229             CurrentNestedLoopCount,
9230             ResultIterSpaces[CurrentNestedLoopCount].NumIterations);
9231         DSA.getOrderedRegionParam().second->setLoopCounter(
9232             CurrentNestedLoopCount,
9233             ResultIterSpaces[CurrentNestedLoopCount].CounterVar);
9234       }
9235     }
9236     for (auto &Pair : DSA.getDoacrossDependClauses()) {
9237       if (CurrentNestedLoopCount >= Pair.first->getNumLoops()) {
9238         // Erroneous case - clause has some problems.
9239         continue;
9240       }
9241       if (Pair.first->getDependencyKind() == OMPC_DEPEND_sink &&
9242           Pair.second.size() <= CurrentNestedLoopCount) {
9243         // Erroneous case - clause has some problems.
9244         Pair.first->setLoopData(CurrentNestedLoopCount, nullptr);
9245         continue;
9246       }
9247       Expr *CntValue;
9248       if (Pair.first->getDependencyKind() == OMPC_DEPEND_source)
9249         CntValue = ISC.buildOrderedLoopData(
9250             DSA.getCurScope(),
9251             ResultIterSpaces[CurrentNestedLoopCount].CounterVar, Captures,
9252             Pair.first->getDependencyLoc());
9253       else
9254         CntValue = ISC.buildOrderedLoopData(
9255             DSA.getCurScope(),
9256             ResultIterSpaces[CurrentNestedLoopCount].CounterVar, Captures,
9257             Pair.first->getDependencyLoc(),
9258             Pair.second[CurrentNestedLoopCount].first,
9259             Pair.second[CurrentNestedLoopCount].second);
9260       Pair.first->setLoopData(CurrentNestedLoopCount, CntValue);
9261     }
9262   }
9263 
9264   return HasErrors;
9265 }
9266 
9267 /// Build 'VarRef = Start.
9268 static ExprResult
9269 buildCounterInit(Sema &SemaRef, Scope *S, SourceLocation Loc, ExprResult VarRef,
9270                  ExprResult Start, bool IsNonRectangularLB,
9271                  llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
9272   // Build 'VarRef = Start.
9273   ExprResult NewStart = IsNonRectangularLB
9274                             ? Start.get()
9275                             : tryBuildCapture(SemaRef, Start.get(), Captures);
9276   if (!NewStart.isUsable())
9277     return ExprError();
9278   if (!SemaRef.Context.hasSameType(NewStart.get()->getType(),
9279                                    VarRef.get()->getType())) {
9280     NewStart = SemaRef.PerformImplicitConversion(
9281         NewStart.get(), VarRef.get()->getType(), Sema::AA_Converting,
9282         /*AllowExplicit=*/true);
9283     if (!NewStart.isUsable())
9284       return ExprError();
9285   }
9286 
9287   ExprResult Init =
9288       SemaRef.BuildBinOp(S, Loc, BO_Assign, VarRef.get(), NewStart.get());
9289   return Init;
9290 }
9291 
9292 /// Build 'VarRef = Start + Iter * Step'.
9293 static ExprResult buildCounterUpdate(
9294     Sema &SemaRef, Scope *S, SourceLocation Loc, ExprResult VarRef,
9295     ExprResult Start, ExprResult Iter, ExprResult Step, bool Subtract,
9296     bool IsNonRectangularLB,
9297     llvm::MapVector<const Expr *, DeclRefExpr *> *Captures = nullptr) {
9298   // Add parentheses (for debugging purposes only).
9299   Iter = SemaRef.ActOnParenExpr(Loc, Loc, Iter.get());
9300   if (!VarRef.isUsable() || !Start.isUsable() || !Iter.isUsable() ||
9301       !Step.isUsable())
9302     return ExprError();
9303 
9304   ExprResult NewStep = Step;
9305   if (Captures)
9306     NewStep = tryBuildCapture(SemaRef, Step.get(), *Captures);
9307   if (NewStep.isInvalid())
9308     return ExprError();
9309   ExprResult Update =
9310       SemaRef.BuildBinOp(S, Loc, BO_Mul, Iter.get(), NewStep.get());
9311   if (!Update.isUsable())
9312     return ExprError();
9313 
9314   // Try to build 'VarRef = Start, VarRef (+|-)= Iter * Step' or
9315   // 'VarRef = Start (+|-) Iter * Step'.
9316   if (!Start.isUsable())
9317     return ExprError();
9318   ExprResult NewStart = SemaRef.ActOnParenExpr(Loc, Loc, Start.get());
9319   if (!NewStart.isUsable())
9320     return ExprError();
9321   if (Captures && !IsNonRectangularLB)
9322     NewStart = tryBuildCapture(SemaRef, Start.get(), *Captures);
9323   if (NewStart.isInvalid())
9324     return ExprError();
9325 
9326   // First attempt: try to build 'VarRef = Start, VarRef += Iter * Step'.
9327   ExprResult SavedUpdate = Update;
9328   ExprResult UpdateVal;
9329   if (VarRef.get()->getType()->isOverloadableType() ||
9330       NewStart.get()->getType()->isOverloadableType() ||
9331       Update.get()->getType()->isOverloadableType()) {
9332     Sema::TentativeAnalysisScope Trap(SemaRef);
9333 
9334     Update =
9335         SemaRef.BuildBinOp(S, Loc, BO_Assign, VarRef.get(), NewStart.get());
9336     if (Update.isUsable()) {
9337       UpdateVal =
9338           SemaRef.BuildBinOp(S, Loc, Subtract ? BO_SubAssign : BO_AddAssign,
9339                              VarRef.get(), SavedUpdate.get());
9340       if (UpdateVal.isUsable()) {
9341         Update = SemaRef.CreateBuiltinBinOp(Loc, BO_Comma, Update.get(),
9342                                             UpdateVal.get());
9343       }
9344     }
9345   }
9346 
9347   // Second attempt: try to build 'VarRef = Start (+|-) Iter * Step'.
9348   if (!Update.isUsable() || !UpdateVal.isUsable()) {
9349     Update = SemaRef.BuildBinOp(S, Loc, Subtract ? BO_Sub : BO_Add,
9350                                 NewStart.get(), SavedUpdate.get());
9351     if (!Update.isUsable())
9352       return ExprError();
9353 
9354     if (!SemaRef.Context.hasSameType(Update.get()->getType(),
9355                                      VarRef.get()->getType())) {
9356       Update = SemaRef.PerformImplicitConversion(
9357           Update.get(), VarRef.get()->getType(), Sema::AA_Converting, true);
9358       if (!Update.isUsable())
9359         return ExprError();
9360     }
9361 
9362     Update = SemaRef.BuildBinOp(S, Loc, BO_Assign, VarRef.get(), Update.get());
9363   }
9364   return Update;
9365 }
9366 
9367 /// Convert integer expression \a E to make it have at least \a Bits
9368 /// bits.
9369 static ExprResult widenIterationCount(unsigned Bits, Expr *E, Sema &SemaRef) {
9370   if (E == nullptr)
9371     return ExprError();
9372   ASTContext &C = SemaRef.Context;
9373   QualType OldType = E->getType();
9374   unsigned HasBits = C.getTypeSize(OldType);
9375   if (HasBits >= Bits)
9376     return ExprResult(E);
9377   // OK to convert to signed, because new type has more bits than old.
9378   QualType NewType = C.getIntTypeForBitwidth(Bits, /* Signed */ true);
9379   return SemaRef.PerformImplicitConversion(E, NewType, Sema::AA_Converting,
9380                                            true);
9381 }
9382 
9383 /// Check if the given expression \a E is a constant integer that fits
9384 /// into \a Bits bits.
9385 static bool fitsInto(unsigned Bits, bool Signed, const Expr *E, Sema &SemaRef) {
9386   if (E == nullptr)
9387     return false;
9388   if (Optional<llvm::APSInt> Result =
9389           E->getIntegerConstantExpr(SemaRef.Context))
9390     return Signed ? Result->isSignedIntN(Bits) : Result->isIntN(Bits);
9391   return false;
9392 }
9393 
9394 /// Build preinits statement for the given declarations.
9395 static Stmt *buildPreInits(ASTContext &Context,
9396                            MutableArrayRef<Decl *> PreInits) {
9397   if (!PreInits.empty()) {
9398     return new (Context) DeclStmt(
9399         DeclGroupRef::Create(Context, PreInits.begin(), PreInits.size()),
9400         SourceLocation(), SourceLocation());
9401   }
9402   return nullptr;
9403 }
9404 
9405 /// Build preinits statement for the given declarations.
9406 static Stmt *
9407 buildPreInits(ASTContext &Context,
9408               const llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
9409   if (!Captures.empty()) {
9410     SmallVector<Decl *, 16> PreInits;
9411     for (const auto &Pair : Captures)
9412       PreInits.push_back(Pair.second->getDecl());
9413     return buildPreInits(Context, PreInits);
9414   }
9415   return nullptr;
9416 }
9417 
9418 /// Build postupdate expression for the given list of postupdates expressions.
9419 static Expr *buildPostUpdate(Sema &S, ArrayRef<Expr *> PostUpdates) {
9420   Expr *PostUpdate = nullptr;
9421   if (!PostUpdates.empty()) {
9422     for (Expr *E : PostUpdates) {
9423       Expr *ConvE = S.BuildCStyleCastExpr(
9424                          E->getExprLoc(),
9425                          S.Context.getTrivialTypeSourceInfo(S.Context.VoidTy),
9426                          E->getExprLoc(), E)
9427                         .get();
9428       PostUpdate = PostUpdate
9429                        ? S.CreateBuiltinBinOp(ConvE->getExprLoc(), BO_Comma,
9430                                               PostUpdate, ConvE)
9431                              .get()
9432                        : ConvE;
9433     }
9434   }
9435   return PostUpdate;
9436 }
9437 
9438 /// Called on a for stmt to check itself and nested loops (if any).
9439 /// \return Returns 0 if one of the collapsed stmts is not canonical for loop,
9440 /// number of collapsed loops otherwise.
9441 static unsigned
9442 checkOpenMPLoop(OpenMPDirectiveKind DKind, Expr *CollapseLoopCountExpr,
9443                 Expr *OrderedLoopCountExpr, Stmt *AStmt, Sema &SemaRef,
9444                 DSAStackTy &DSA,
9445                 Sema::VarsWithInheritedDSAType &VarsWithImplicitDSA,
9446                 OMPLoopBasedDirective::HelperExprs &Built) {
9447   unsigned NestedLoopCount = 1;
9448   bool SupportsNonPerfectlyNested = (SemaRef.LangOpts.OpenMP >= 50) &&
9449                                     !isOpenMPLoopTransformationDirective(DKind);
9450 
9451   if (CollapseLoopCountExpr) {
9452     // Found 'collapse' clause - calculate collapse number.
9453     Expr::EvalResult Result;
9454     if (!CollapseLoopCountExpr->isValueDependent() &&
9455         CollapseLoopCountExpr->EvaluateAsInt(Result, SemaRef.getASTContext())) {
9456       NestedLoopCount = Result.Val.getInt().getLimitedValue();
9457     } else {
9458       Built.clear(/*Size=*/1);
9459       return 1;
9460     }
9461   }
9462   unsigned OrderedLoopCount = 1;
9463   if (OrderedLoopCountExpr) {
9464     // Found 'ordered' clause - calculate collapse number.
9465     Expr::EvalResult EVResult;
9466     if (!OrderedLoopCountExpr->isValueDependent() &&
9467         OrderedLoopCountExpr->EvaluateAsInt(EVResult,
9468                                             SemaRef.getASTContext())) {
9469       llvm::APSInt Result = EVResult.Val.getInt();
9470       if (Result.getLimitedValue() < NestedLoopCount) {
9471         SemaRef.Diag(OrderedLoopCountExpr->getExprLoc(),
9472                      diag::err_omp_wrong_ordered_loop_count)
9473             << OrderedLoopCountExpr->getSourceRange();
9474         SemaRef.Diag(CollapseLoopCountExpr->getExprLoc(),
9475                      diag::note_collapse_loop_count)
9476             << CollapseLoopCountExpr->getSourceRange();
9477       }
9478       OrderedLoopCount = Result.getLimitedValue();
9479     } else {
9480       Built.clear(/*Size=*/1);
9481       return 1;
9482     }
9483   }
9484   // This is helper routine for loop directives (e.g., 'for', 'simd',
9485   // 'for simd', etc.).
9486   llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
9487   unsigned NumLoops = std::max(OrderedLoopCount, NestedLoopCount);
9488   SmallVector<LoopIterationSpace, 4> IterSpaces(NumLoops);
9489   if (!OMPLoopBasedDirective::doForAllLoops(
9490           AStmt->IgnoreContainers(!isOpenMPLoopTransformationDirective(DKind)),
9491           SupportsNonPerfectlyNested, NumLoops,
9492           [DKind, &SemaRef, &DSA, NumLoops, NestedLoopCount,
9493            CollapseLoopCountExpr, OrderedLoopCountExpr, &VarsWithImplicitDSA,
9494            &IterSpaces, &Captures](unsigned Cnt, Stmt *CurStmt) {
9495             if (checkOpenMPIterationSpace(
9496                     DKind, CurStmt, SemaRef, DSA, Cnt, NestedLoopCount,
9497                     NumLoops, CollapseLoopCountExpr, OrderedLoopCountExpr,
9498                     VarsWithImplicitDSA, IterSpaces, Captures))
9499               return true;
9500             if (Cnt > 0 && Cnt >= NestedLoopCount &&
9501                 IterSpaces[Cnt].CounterVar) {
9502               // Handle initialization of captured loop iterator variables.
9503               auto *DRE = cast<DeclRefExpr>(IterSpaces[Cnt].CounterVar);
9504               if (isa<OMPCapturedExprDecl>(DRE->getDecl())) {
9505                 Captures[DRE] = DRE;
9506               }
9507             }
9508             return false;
9509           },
9510           [&SemaRef, &Captures](OMPLoopTransformationDirective *Transform) {
9511             Stmt *DependentPreInits = Transform->getPreInits();
9512             if (!DependentPreInits)
9513               return;
9514             for (Decl *C : cast<DeclStmt>(DependentPreInits)->getDeclGroup()) {
9515               auto *D = cast<VarDecl>(C);
9516               DeclRefExpr *Ref = buildDeclRefExpr(SemaRef, D, D->getType(),
9517                                                   Transform->getBeginLoc());
9518               Captures[Ref] = Ref;
9519             }
9520           }))
9521     return 0;
9522 
9523   Built.clear(/* size */ NestedLoopCount);
9524 
9525   if (SemaRef.CurContext->isDependentContext())
9526     return NestedLoopCount;
9527 
9528   // An example of what is generated for the following code:
9529   //
9530   //   #pragma omp simd collapse(2) ordered(2)
9531   //   for (i = 0; i < NI; ++i)
9532   //     for (k = 0; k < NK; ++k)
9533   //       for (j = J0; j < NJ; j+=2) {
9534   //         <loop body>
9535   //       }
9536   //
9537   // We generate the code below.
9538   // Note: the loop body may be outlined in CodeGen.
9539   // Note: some counters may be C++ classes, operator- is used to find number of
9540   // iterations and operator+= to calculate counter value.
9541   // Note: decltype(NumIterations) must be integer type (in 'omp for', only i32
9542   // or i64 is currently supported).
9543   //
9544   //   #define NumIterations (NI * ((NJ - J0 - 1 + 2) / 2))
9545   //   for (int[32|64]_t IV = 0; IV < NumIterations; ++IV ) {
9546   //     .local.i = IV / ((NJ - J0 - 1 + 2) / 2);
9547   //     .local.j = J0 + (IV % ((NJ - J0 - 1 + 2) / 2)) * 2;
9548   //     // similar updates for vars in clauses (e.g. 'linear')
9549   //     <loop body (using local i and j)>
9550   //   }
9551   //   i = NI; // assign final values of counters
9552   //   j = NJ;
9553   //
9554 
9555   // Last iteration number is (I1 * I2 * ... In) - 1, where I1, I2 ... In are
9556   // the iteration counts of the collapsed for loops.
9557   // Precondition tests if there is at least one iteration (all conditions are
9558   // true).
9559   auto PreCond = ExprResult(IterSpaces[0].PreCond);
9560   Expr *N0 = IterSpaces[0].NumIterations;
9561   ExprResult LastIteration32 =
9562       widenIterationCount(/*Bits=*/32,
9563                           SemaRef
9564                               .PerformImplicitConversion(
9565                                   N0->IgnoreImpCasts(), N0->getType(),
9566                                   Sema::AA_Converting, /*AllowExplicit=*/true)
9567                               .get(),
9568                           SemaRef);
9569   ExprResult LastIteration64 = widenIterationCount(
9570       /*Bits=*/64,
9571       SemaRef
9572           .PerformImplicitConversion(N0->IgnoreImpCasts(), N0->getType(),
9573                                      Sema::AA_Converting,
9574                                      /*AllowExplicit=*/true)
9575           .get(),
9576       SemaRef);
9577 
9578   if (!LastIteration32.isUsable() || !LastIteration64.isUsable())
9579     return NestedLoopCount;
9580 
9581   ASTContext &C = SemaRef.Context;
9582   bool AllCountsNeedLessThan32Bits = C.getTypeSize(N0->getType()) < 32;
9583 
9584   Scope *CurScope = DSA.getCurScope();
9585   for (unsigned Cnt = 1; Cnt < NestedLoopCount; ++Cnt) {
9586     if (PreCond.isUsable()) {
9587       PreCond =
9588           SemaRef.BuildBinOp(CurScope, PreCond.get()->getExprLoc(), BO_LAnd,
9589                              PreCond.get(), IterSpaces[Cnt].PreCond);
9590     }
9591     Expr *N = IterSpaces[Cnt].NumIterations;
9592     SourceLocation Loc = N->getExprLoc();
9593     AllCountsNeedLessThan32Bits &= C.getTypeSize(N->getType()) < 32;
9594     if (LastIteration32.isUsable())
9595       LastIteration32 = SemaRef.BuildBinOp(
9596           CurScope, Loc, BO_Mul, LastIteration32.get(),
9597           SemaRef
9598               .PerformImplicitConversion(N->IgnoreImpCasts(), N->getType(),
9599                                          Sema::AA_Converting,
9600                                          /*AllowExplicit=*/true)
9601               .get());
9602     if (LastIteration64.isUsable())
9603       LastIteration64 = SemaRef.BuildBinOp(
9604           CurScope, Loc, BO_Mul, LastIteration64.get(),
9605           SemaRef
9606               .PerformImplicitConversion(N->IgnoreImpCasts(), N->getType(),
9607                                          Sema::AA_Converting,
9608                                          /*AllowExplicit=*/true)
9609               .get());
9610   }
9611 
9612   // Choose either the 32-bit or 64-bit version.
9613   ExprResult LastIteration = LastIteration64;
9614   if (SemaRef.getLangOpts().OpenMPOptimisticCollapse ||
9615       (LastIteration32.isUsable() &&
9616        C.getTypeSize(LastIteration32.get()->getType()) == 32 &&
9617        (AllCountsNeedLessThan32Bits || NestedLoopCount == 1 ||
9618         fitsInto(
9619             /*Bits=*/32,
9620             LastIteration32.get()->getType()->hasSignedIntegerRepresentation(),
9621             LastIteration64.get(), SemaRef))))
9622     LastIteration = LastIteration32;
9623   QualType VType = LastIteration.get()->getType();
9624   QualType RealVType = VType;
9625   QualType StrideVType = VType;
9626   if (isOpenMPTaskLoopDirective(DKind)) {
9627     VType =
9628         SemaRef.Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/0);
9629     StrideVType =
9630         SemaRef.Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/1);
9631   }
9632 
9633   if (!LastIteration.isUsable())
9634     return 0;
9635 
9636   // Save the number of iterations.
9637   ExprResult NumIterations = LastIteration;
9638   {
9639     LastIteration = SemaRef.BuildBinOp(
9640         CurScope, LastIteration.get()->getExprLoc(), BO_Sub,
9641         LastIteration.get(),
9642         SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get());
9643     if (!LastIteration.isUsable())
9644       return 0;
9645   }
9646 
9647   // Calculate the last iteration number beforehand instead of doing this on
9648   // each iteration. Do not do this if the number of iterations may be kfold-ed.
9649   bool IsConstant = LastIteration.get()->isIntegerConstantExpr(SemaRef.Context);
9650   ExprResult CalcLastIteration;
9651   if (!IsConstant) {
9652     ExprResult SaveRef =
9653         tryBuildCapture(SemaRef, LastIteration.get(), Captures);
9654     LastIteration = SaveRef;
9655 
9656     // Prepare SaveRef + 1.
9657     NumIterations = SemaRef.BuildBinOp(
9658         CurScope, SaveRef.get()->getExprLoc(), BO_Add, SaveRef.get(),
9659         SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get());
9660     if (!NumIterations.isUsable())
9661       return 0;
9662   }
9663 
9664   SourceLocation InitLoc = IterSpaces[0].InitSrcRange.getBegin();
9665 
9666   // Build variables passed into runtime, necessary for worksharing directives.
9667   ExprResult LB, UB, IL, ST, EUB, CombLB, CombUB, PrevLB, PrevUB, CombEUB;
9668   if (isOpenMPWorksharingDirective(DKind) || isOpenMPTaskLoopDirective(DKind) ||
9669       isOpenMPDistributeDirective(DKind) ||
9670       isOpenMPGenericLoopDirective(DKind) ||
9671       isOpenMPLoopTransformationDirective(DKind)) {
9672     // Lower bound variable, initialized with zero.
9673     VarDecl *LBDecl = buildVarDecl(SemaRef, InitLoc, VType, ".omp.lb");
9674     LB = buildDeclRefExpr(SemaRef, LBDecl, VType, InitLoc);
9675     SemaRef.AddInitializerToDecl(LBDecl,
9676                                  SemaRef.ActOnIntegerConstant(InitLoc, 0).get(),
9677                                  /*DirectInit*/ false);
9678 
9679     // Upper bound variable, initialized with last iteration number.
9680     VarDecl *UBDecl = buildVarDecl(SemaRef, InitLoc, VType, ".omp.ub");
9681     UB = buildDeclRefExpr(SemaRef, UBDecl, VType, InitLoc);
9682     SemaRef.AddInitializerToDecl(UBDecl, LastIteration.get(),
9683                                  /*DirectInit*/ false);
9684 
9685     // A 32-bit variable-flag where runtime returns 1 for the last iteration.
9686     // This will be used to implement clause 'lastprivate'.
9687     QualType Int32Ty = SemaRef.Context.getIntTypeForBitwidth(32, true);
9688     VarDecl *ILDecl = buildVarDecl(SemaRef, InitLoc, Int32Ty, ".omp.is_last");
9689     IL = buildDeclRefExpr(SemaRef, ILDecl, Int32Ty, InitLoc);
9690     SemaRef.AddInitializerToDecl(ILDecl,
9691                                  SemaRef.ActOnIntegerConstant(InitLoc, 0).get(),
9692                                  /*DirectInit*/ false);
9693 
9694     // Stride variable returned by runtime (we initialize it to 1 by default).
9695     VarDecl *STDecl =
9696         buildVarDecl(SemaRef, InitLoc, StrideVType, ".omp.stride");
9697     ST = buildDeclRefExpr(SemaRef, STDecl, StrideVType, InitLoc);
9698     SemaRef.AddInitializerToDecl(STDecl,
9699                                  SemaRef.ActOnIntegerConstant(InitLoc, 1).get(),
9700                                  /*DirectInit*/ false);
9701 
9702     // Build expression: UB = min(UB, LastIteration)
9703     // It is necessary for CodeGen of directives with static scheduling.
9704     ExprResult IsUBGreater = SemaRef.BuildBinOp(CurScope, InitLoc, BO_GT,
9705                                                 UB.get(), LastIteration.get());
9706     ExprResult CondOp = SemaRef.ActOnConditionalOp(
9707         LastIteration.get()->getExprLoc(), InitLoc, IsUBGreater.get(),
9708         LastIteration.get(), UB.get());
9709     EUB = SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, UB.get(),
9710                              CondOp.get());
9711     EUB = SemaRef.ActOnFinishFullExpr(EUB.get(), /*DiscardedValue*/ false);
9712 
9713     // If we have a combined directive that combines 'distribute', 'for' or
9714     // 'simd' we need to be able to access the bounds of the schedule of the
9715     // enclosing region. E.g. in 'distribute parallel for' the bounds obtained
9716     // by scheduling 'distribute' have to be passed to the schedule of 'for'.
9717     if (isOpenMPLoopBoundSharingDirective(DKind)) {
9718       // Lower bound variable, initialized with zero.
9719       VarDecl *CombLBDecl =
9720           buildVarDecl(SemaRef, InitLoc, VType, ".omp.comb.lb");
9721       CombLB = buildDeclRefExpr(SemaRef, CombLBDecl, VType, InitLoc);
9722       SemaRef.AddInitializerToDecl(
9723           CombLBDecl, SemaRef.ActOnIntegerConstant(InitLoc, 0).get(),
9724           /*DirectInit*/ false);
9725 
9726       // Upper bound variable, initialized with last iteration number.
9727       VarDecl *CombUBDecl =
9728           buildVarDecl(SemaRef, InitLoc, VType, ".omp.comb.ub");
9729       CombUB = buildDeclRefExpr(SemaRef, CombUBDecl, VType, InitLoc);
9730       SemaRef.AddInitializerToDecl(CombUBDecl, LastIteration.get(),
9731                                    /*DirectInit*/ false);
9732 
9733       ExprResult CombIsUBGreater = SemaRef.BuildBinOp(
9734           CurScope, InitLoc, BO_GT, CombUB.get(), LastIteration.get());
9735       ExprResult CombCondOp =
9736           SemaRef.ActOnConditionalOp(InitLoc, InitLoc, CombIsUBGreater.get(),
9737                                      LastIteration.get(), CombUB.get());
9738       CombEUB = SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, CombUB.get(),
9739                                    CombCondOp.get());
9740       CombEUB =
9741           SemaRef.ActOnFinishFullExpr(CombEUB.get(), /*DiscardedValue*/ false);
9742 
9743       const CapturedDecl *CD = cast<CapturedStmt>(AStmt)->getCapturedDecl();
9744       // We expect to have at least 2 more parameters than the 'parallel'
9745       // directive does - the lower and upper bounds of the previous schedule.
9746       assert(CD->getNumParams() >= 4 &&
9747              "Unexpected number of parameters in loop combined directive");
9748 
9749       // Set the proper type for the bounds given what we learned from the
9750       // enclosed loops.
9751       ImplicitParamDecl *PrevLBDecl = CD->getParam(/*PrevLB=*/2);
9752       ImplicitParamDecl *PrevUBDecl = CD->getParam(/*PrevUB=*/3);
9753 
9754       // Previous lower and upper bounds are obtained from the region
9755       // parameters.
9756       PrevLB =
9757           buildDeclRefExpr(SemaRef, PrevLBDecl, PrevLBDecl->getType(), InitLoc);
9758       PrevUB =
9759           buildDeclRefExpr(SemaRef, PrevUBDecl, PrevUBDecl->getType(), InitLoc);
9760     }
9761   }
9762 
9763   // Build the iteration variable and its initialization before loop.
9764   ExprResult IV;
9765   ExprResult Init, CombInit;
9766   {
9767     VarDecl *IVDecl = buildVarDecl(SemaRef, InitLoc, RealVType, ".omp.iv");
9768     IV = buildDeclRefExpr(SemaRef, IVDecl, RealVType, InitLoc);
9769     Expr *RHS = (isOpenMPWorksharingDirective(DKind) ||
9770                  isOpenMPGenericLoopDirective(DKind) ||
9771                  isOpenMPTaskLoopDirective(DKind) ||
9772                  isOpenMPDistributeDirective(DKind) ||
9773                  isOpenMPLoopTransformationDirective(DKind))
9774                     ? LB.get()
9775                     : SemaRef.ActOnIntegerConstant(SourceLocation(), 0).get();
9776     Init = SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, IV.get(), RHS);
9777     Init = SemaRef.ActOnFinishFullExpr(Init.get(), /*DiscardedValue*/ false);
9778 
9779     if (isOpenMPLoopBoundSharingDirective(DKind)) {
9780       Expr *CombRHS =
9781           (isOpenMPWorksharingDirective(DKind) ||
9782            isOpenMPGenericLoopDirective(DKind) ||
9783            isOpenMPTaskLoopDirective(DKind) ||
9784            isOpenMPDistributeDirective(DKind))
9785               ? CombLB.get()
9786               : SemaRef.ActOnIntegerConstant(SourceLocation(), 0).get();
9787       CombInit =
9788           SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, IV.get(), CombRHS);
9789       CombInit =
9790           SemaRef.ActOnFinishFullExpr(CombInit.get(), /*DiscardedValue*/ false);
9791     }
9792   }
9793 
9794   bool UseStrictCompare =
9795       RealVType->hasUnsignedIntegerRepresentation() &&
9796       llvm::all_of(IterSpaces, [](const LoopIterationSpace &LIS) {
9797         return LIS.IsStrictCompare;
9798       });
9799   // Loop condition (IV < NumIterations) or (IV <= UB or IV < UB + 1 (for
9800   // unsigned IV)) for worksharing loops.
9801   SourceLocation CondLoc = AStmt->getBeginLoc();
9802   Expr *BoundUB = UB.get();
9803   if (UseStrictCompare) {
9804     BoundUB =
9805         SemaRef
9806             .BuildBinOp(CurScope, CondLoc, BO_Add, BoundUB,
9807                         SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get())
9808             .get();
9809     BoundUB =
9810         SemaRef.ActOnFinishFullExpr(BoundUB, /*DiscardedValue*/ false).get();
9811   }
9812   ExprResult Cond =
9813       (isOpenMPWorksharingDirective(DKind) ||
9814        isOpenMPGenericLoopDirective(DKind) ||
9815        isOpenMPTaskLoopDirective(DKind) || isOpenMPDistributeDirective(DKind) ||
9816        isOpenMPLoopTransformationDirective(DKind))
9817           ? SemaRef.BuildBinOp(CurScope, CondLoc,
9818                                UseStrictCompare ? BO_LT : BO_LE, IV.get(),
9819                                BoundUB)
9820           : SemaRef.BuildBinOp(CurScope, CondLoc, BO_LT, IV.get(),
9821                                NumIterations.get());
9822   ExprResult CombDistCond;
9823   if (isOpenMPLoopBoundSharingDirective(DKind)) {
9824     CombDistCond = SemaRef.BuildBinOp(CurScope, CondLoc, BO_LT, IV.get(),
9825                                       NumIterations.get());
9826   }
9827 
9828   ExprResult CombCond;
9829   if (isOpenMPLoopBoundSharingDirective(DKind)) {
9830     Expr *BoundCombUB = CombUB.get();
9831     if (UseStrictCompare) {
9832       BoundCombUB =
9833           SemaRef
9834               .BuildBinOp(
9835                   CurScope, CondLoc, BO_Add, BoundCombUB,
9836                   SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get())
9837               .get();
9838       BoundCombUB =
9839           SemaRef.ActOnFinishFullExpr(BoundCombUB, /*DiscardedValue*/ false)
9840               .get();
9841     }
9842     CombCond =
9843         SemaRef.BuildBinOp(CurScope, CondLoc, UseStrictCompare ? BO_LT : BO_LE,
9844                            IV.get(), BoundCombUB);
9845   }
9846   // Loop increment (IV = IV + 1)
9847   SourceLocation IncLoc = AStmt->getBeginLoc();
9848   ExprResult Inc =
9849       SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, IV.get(),
9850                          SemaRef.ActOnIntegerConstant(IncLoc, 1).get());
9851   if (!Inc.isUsable())
9852     return 0;
9853   Inc = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, IV.get(), Inc.get());
9854   Inc = SemaRef.ActOnFinishFullExpr(Inc.get(), /*DiscardedValue*/ false);
9855   if (!Inc.isUsable())
9856     return 0;
9857 
9858   // Increments for worksharing loops (LB = LB + ST; UB = UB + ST).
9859   // Used for directives with static scheduling.
9860   // In combined construct, add combined version that use CombLB and CombUB
9861   // base variables for the update
9862   ExprResult NextLB, NextUB, CombNextLB, CombNextUB;
9863   if (isOpenMPWorksharingDirective(DKind) || isOpenMPTaskLoopDirective(DKind) ||
9864       isOpenMPGenericLoopDirective(DKind) ||
9865       isOpenMPDistributeDirective(DKind) ||
9866       isOpenMPLoopTransformationDirective(DKind)) {
9867     // LB + ST
9868     NextLB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, LB.get(), ST.get());
9869     if (!NextLB.isUsable())
9870       return 0;
9871     // LB = LB + ST
9872     NextLB =
9873         SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, LB.get(), NextLB.get());
9874     NextLB =
9875         SemaRef.ActOnFinishFullExpr(NextLB.get(), /*DiscardedValue*/ false);
9876     if (!NextLB.isUsable())
9877       return 0;
9878     // UB + ST
9879     NextUB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, UB.get(), ST.get());
9880     if (!NextUB.isUsable())
9881       return 0;
9882     // UB = UB + ST
9883     NextUB =
9884         SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, UB.get(), NextUB.get());
9885     NextUB =
9886         SemaRef.ActOnFinishFullExpr(NextUB.get(), /*DiscardedValue*/ false);
9887     if (!NextUB.isUsable())
9888       return 0;
9889     if (isOpenMPLoopBoundSharingDirective(DKind)) {
9890       CombNextLB =
9891           SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, CombLB.get(), ST.get());
9892       if (!NextLB.isUsable())
9893         return 0;
9894       // LB = LB + ST
9895       CombNextLB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, CombLB.get(),
9896                                       CombNextLB.get());
9897       CombNextLB = SemaRef.ActOnFinishFullExpr(CombNextLB.get(),
9898                                                /*DiscardedValue*/ false);
9899       if (!CombNextLB.isUsable())
9900         return 0;
9901       // UB + ST
9902       CombNextUB =
9903           SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, CombUB.get(), ST.get());
9904       if (!CombNextUB.isUsable())
9905         return 0;
9906       // UB = UB + ST
9907       CombNextUB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, CombUB.get(),
9908                                       CombNextUB.get());
9909       CombNextUB = SemaRef.ActOnFinishFullExpr(CombNextUB.get(),
9910                                                /*DiscardedValue*/ false);
9911       if (!CombNextUB.isUsable())
9912         return 0;
9913     }
9914   }
9915 
9916   // Create increment expression for distribute loop when combined in a same
9917   // directive with for as IV = IV + ST; ensure upper bound expression based
9918   // on PrevUB instead of NumIterations - used to implement 'for' when found
9919   // in combination with 'distribute', like in 'distribute parallel for'
9920   SourceLocation DistIncLoc = AStmt->getBeginLoc();
9921   ExprResult DistCond, DistInc, PrevEUB, ParForInDistCond;
9922   if (isOpenMPLoopBoundSharingDirective(DKind)) {
9923     DistCond = SemaRef.BuildBinOp(
9924         CurScope, CondLoc, UseStrictCompare ? BO_LT : BO_LE, IV.get(), BoundUB);
9925     assert(DistCond.isUsable() && "distribute cond expr was not built");
9926 
9927     DistInc =
9928         SemaRef.BuildBinOp(CurScope, DistIncLoc, BO_Add, IV.get(), ST.get());
9929     assert(DistInc.isUsable() && "distribute inc expr was not built");
9930     DistInc = SemaRef.BuildBinOp(CurScope, DistIncLoc, BO_Assign, IV.get(),
9931                                  DistInc.get());
9932     DistInc =
9933         SemaRef.ActOnFinishFullExpr(DistInc.get(), /*DiscardedValue*/ false);
9934     assert(DistInc.isUsable() && "distribute inc expr was not built");
9935 
9936     // Build expression: UB = min(UB, prevUB) for #for in composite or combined
9937     // construct
9938     ExprResult NewPrevUB = PrevUB;
9939     SourceLocation DistEUBLoc = AStmt->getBeginLoc();
9940     if (!SemaRef.Context.hasSameType(UB.get()->getType(),
9941                                      PrevUB.get()->getType())) {
9942       NewPrevUB = SemaRef.BuildCStyleCastExpr(
9943           DistEUBLoc,
9944           SemaRef.Context.getTrivialTypeSourceInfo(UB.get()->getType()),
9945           DistEUBLoc, NewPrevUB.get());
9946       if (!NewPrevUB.isUsable())
9947         return 0;
9948     }
9949     ExprResult IsUBGreater = SemaRef.BuildBinOp(CurScope, DistEUBLoc, BO_GT,
9950                                                 UB.get(), NewPrevUB.get());
9951     ExprResult CondOp = SemaRef.ActOnConditionalOp(
9952         DistEUBLoc, DistEUBLoc, IsUBGreater.get(), NewPrevUB.get(), UB.get());
9953     PrevEUB = SemaRef.BuildBinOp(CurScope, DistIncLoc, BO_Assign, UB.get(),
9954                                  CondOp.get());
9955     PrevEUB =
9956         SemaRef.ActOnFinishFullExpr(PrevEUB.get(), /*DiscardedValue*/ false);
9957 
9958     // Build IV <= PrevUB or IV < PrevUB + 1 for unsigned IV to be used in
9959     // parallel for is in combination with a distribute directive with
9960     // schedule(static, 1)
9961     Expr *BoundPrevUB = PrevUB.get();
9962     if (UseStrictCompare) {
9963       BoundPrevUB =
9964           SemaRef
9965               .BuildBinOp(
9966                   CurScope, CondLoc, BO_Add, BoundPrevUB,
9967                   SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get())
9968               .get();
9969       BoundPrevUB =
9970           SemaRef.ActOnFinishFullExpr(BoundPrevUB, /*DiscardedValue*/ false)
9971               .get();
9972     }
9973     ParForInDistCond =
9974         SemaRef.BuildBinOp(CurScope, CondLoc, UseStrictCompare ? BO_LT : BO_LE,
9975                            IV.get(), BoundPrevUB);
9976   }
9977 
9978   // Build updates and final values of the loop counters.
9979   bool HasErrors = false;
9980   Built.Counters.resize(NestedLoopCount);
9981   Built.Inits.resize(NestedLoopCount);
9982   Built.Updates.resize(NestedLoopCount);
9983   Built.Finals.resize(NestedLoopCount);
9984   Built.DependentCounters.resize(NestedLoopCount);
9985   Built.DependentInits.resize(NestedLoopCount);
9986   Built.FinalsConditions.resize(NestedLoopCount);
9987   {
9988     // We implement the following algorithm for obtaining the
9989     // original loop iteration variable values based on the
9990     // value of the collapsed loop iteration variable IV.
9991     //
9992     // Let n+1 be the number of collapsed loops in the nest.
9993     // Iteration variables (I0, I1, .... In)
9994     // Iteration counts (N0, N1, ... Nn)
9995     //
9996     // Acc = IV;
9997     //
9998     // To compute Ik for loop k, 0 <= k <= n, generate:
9999     //    Prod = N(k+1) * N(k+2) * ... * Nn;
10000     //    Ik = Acc / Prod;
10001     //    Acc -= Ik * Prod;
10002     //
10003     ExprResult Acc = IV;
10004     for (unsigned int Cnt = 0; Cnt < NestedLoopCount; ++Cnt) {
10005       LoopIterationSpace &IS = IterSpaces[Cnt];
10006       SourceLocation UpdLoc = IS.IncSrcRange.getBegin();
10007       ExprResult Iter;
10008 
10009       // Compute prod
10010       ExprResult Prod = SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get();
10011       for (unsigned int K = Cnt + 1; K < NestedLoopCount; ++K)
10012         Prod = SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Mul, Prod.get(),
10013                                   IterSpaces[K].NumIterations);
10014 
10015       // Iter = Acc / Prod
10016       // If there is at least one more inner loop to avoid
10017       // multiplication by 1.
10018       if (Cnt + 1 < NestedLoopCount)
10019         Iter =
10020             SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Div, Acc.get(), Prod.get());
10021       else
10022         Iter = Acc;
10023       if (!Iter.isUsable()) {
10024         HasErrors = true;
10025         break;
10026       }
10027 
10028       // Update Acc:
10029       // Acc -= Iter * Prod
10030       // Check if there is at least one more inner loop to avoid
10031       // multiplication by 1.
10032       if (Cnt + 1 < NestedLoopCount)
10033         Prod = SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Mul, Iter.get(),
10034                                   Prod.get());
10035       else
10036         Prod = Iter;
10037       Acc = SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Sub, Acc.get(), Prod.get());
10038 
10039       // Build update: IS.CounterVar(Private) = IS.Start + Iter * IS.Step
10040       auto *VD = cast<VarDecl>(cast<DeclRefExpr>(IS.CounterVar)->getDecl());
10041       DeclRefExpr *CounterVar = buildDeclRefExpr(
10042           SemaRef, VD, IS.CounterVar->getType(), IS.CounterVar->getExprLoc(),
10043           /*RefersToCapture=*/true);
10044       ExprResult Init =
10045           buildCounterInit(SemaRef, CurScope, UpdLoc, CounterVar,
10046                            IS.CounterInit, IS.IsNonRectangularLB, Captures);
10047       if (!Init.isUsable()) {
10048         HasErrors = true;
10049         break;
10050       }
10051       ExprResult Update = buildCounterUpdate(
10052           SemaRef, CurScope, UpdLoc, CounterVar, IS.CounterInit, Iter,
10053           IS.CounterStep, IS.Subtract, IS.IsNonRectangularLB, &Captures);
10054       if (!Update.isUsable()) {
10055         HasErrors = true;
10056         break;
10057       }
10058 
10059       // Build final: IS.CounterVar = IS.Start + IS.NumIters * IS.Step
10060       ExprResult Final =
10061           buildCounterUpdate(SemaRef, CurScope, UpdLoc, CounterVar,
10062                              IS.CounterInit, IS.NumIterations, IS.CounterStep,
10063                              IS.Subtract, IS.IsNonRectangularLB, &Captures);
10064       if (!Final.isUsable()) {
10065         HasErrors = true;
10066         break;
10067       }
10068 
10069       if (!Update.isUsable() || !Final.isUsable()) {
10070         HasErrors = true;
10071         break;
10072       }
10073       // Save results
10074       Built.Counters[Cnt] = IS.CounterVar;
10075       Built.PrivateCounters[Cnt] = IS.PrivateCounterVar;
10076       Built.Inits[Cnt] = Init.get();
10077       Built.Updates[Cnt] = Update.get();
10078       Built.Finals[Cnt] = Final.get();
10079       Built.DependentCounters[Cnt] = nullptr;
10080       Built.DependentInits[Cnt] = nullptr;
10081       Built.FinalsConditions[Cnt] = nullptr;
10082       if (IS.IsNonRectangularLB || IS.IsNonRectangularUB) {
10083         Built.DependentCounters[Cnt] =
10084             Built.Counters[NestedLoopCount - 1 - IS.LoopDependentIdx];
10085         Built.DependentInits[Cnt] =
10086             Built.Inits[NestedLoopCount - 1 - IS.LoopDependentIdx];
10087         Built.FinalsConditions[Cnt] = IS.FinalCondition;
10088       }
10089     }
10090   }
10091 
10092   if (HasErrors)
10093     return 0;
10094 
10095   // Save results
10096   Built.IterationVarRef = IV.get();
10097   Built.LastIteration = LastIteration.get();
10098   Built.NumIterations = NumIterations.get();
10099   Built.CalcLastIteration = SemaRef
10100                                 .ActOnFinishFullExpr(CalcLastIteration.get(),
10101                                                      /*DiscardedValue=*/false)
10102                                 .get();
10103   Built.PreCond = PreCond.get();
10104   Built.PreInits = buildPreInits(C, Captures);
10105   Built.Cond = Cond.get();
10106   Built.Init = Init.get();
10107   Built.Inc = Inc.get();
10108   Built.LB = LB.get();
10109   Built.UB = UB.get();
10110   Built.IL = IL.get();
10111   Built.ST = ST.get();
10112   Built.EUB = EUB.get();
10113   Built.NLB = NextLB.get();
10114   Built.NUB = NextUB.get();
10115   Built.PrevLB = PrevLB.get();
10116   Built.PrevUB = PrevUB.get();
10117   Built.DistInc = DistInc.get();
10118   Built.PrevEUB = PrevEUB.get();
10119   Built.DistCombinedFields.LB = CombLB.get();
10120   Built.DistCombinedFields.UB = CombUB.get();
10121   Built.DistCombinedFields.EUB = CombEUB.get();
10122   Built.DistCombinedFields.Init = CombInit.get();
10123   Built.DistCombinedFields.Cond = CombCond.get();
10124   Built.DistCombinedFields.NLB = CombNextLB.get();
10125   Built.DistCombinedFields.NUB = CombNextUB.get();
10126   Built.DistCombinedFields.DistCond = CombDistCond.get();
10127   Built.DistCombinedFields.ParForInDistCond = ParForInDistCond.get();
10128 
10129   return NestedLoopCount;
10130 }
10131 
10132 static Expr *getCollapseNumberExpr(ArrayRef<OMPClause *> Clauses) {
10133   auto CollapseClauses =
10134       OMPExecutableDirective::getClausesOfKind<OMPCollapseClause>(Clauses);
10135   if (CollapseClauses.begin() != CollapseClauses.end())
10136     return (*CollapseClauses.begin())->getNumForLoops();
10137   return nullptr;
10138 }
10139 
10140 static Expr *getOrderedNumberExpr(ArrayRef<OMPClause *> Clauses) {
10141   auto OrderedClauses =
10142       OMPExecutableDirective::getClausesOfKind<OMPOrderedClause>(Clauses);
10143   if (OrderedClauses.begin() != OrderedClauses.end())
10144     return (*OrderedClauses.begin())->getNumForLoops();
10145   return nullptr;
10146 }
10147 
10148 static bool checkSimdlenSafelenSpecified(Sema &S,
10149                                          const ArrayRef<OMPClause *> Clauses) {
10150   const OMPSafelenClause *Safelen = nullptr;
10151   const OMPSimdlenClause *Simdlen = nullptr;
10152 
10153   for (const OMPClause *Clause : Clauses) {
10154     if (Clause->getClauseKind() == OMPC_safelen)
10155       Safelen = cast<OMPSafelenClause>(Clause);
10156     else if (Clause->getClauseKind() == OMPC_simdlen)
10157       Simdlen = cast<OMPSimdlenClause>(Clause);
10158     if (Safelen && Simdlen)
10159       break;
10160   }
10161 
10162   if (Simdlen && Safelen) {
10163     const Expr *SimdlenLength = Simdlen->getSimdlen();
10164     const Expr *SafelenLength = Safelen->getSafelen();
10165     if (SimdlenLength->isValueDependent() || SimdlenLength->isTypeDependent() ||
10166         SimdlenLength->isInstantiationDependent() ||
10167         SimdlenLength->containsUnexpandedParameterPack())
10168       return false;
10169     if (SafelenLength->isValueDependent() || SafelenLength->isTypeDependent() ||
10170         SafelenLength->isInstantiationDependent() ||
10171         SafelenLength->containsUnexpandedParameterPack())
10172       return false;
10173     Expr::EvalResult SimdlenResult, SafelenResult;
10174     SimdlenLength->EvaluateAsInt(SimdlenResult, S.Context);
10175     SafelenLength->EvaluateAsInt(SafelenResult, S.Context);
10176     llvm::APSInt SimdlenRes = SimdlenResult.Val.getInt();
10177     llvm::APSInt SafelenRes = SafelenResult.Val.getInt();
10178     // OpenMP 4.5 [2.8.1, simd Construct, Restrictions]
10179     // If both simdlen and safelen clauses are specified, the value of the
10180     // simdlen parameter must be less than or equal to the value of the safelen
10181     // parameter.
10182     if (SimdlenRes > SafelenRes) {
10183       S.Diag(SimdlenLength->getExprLoc(),
10184              diag::err_omp_wrong_simdlen_safelen_values)
10185           << SimdlenLength->getSourceRange() << SafelenLength->getSourceRange();
10186       return true;
10187     }
10188   }
10189   return false;
10190 }
10191 
10192 StmtResult
10193 Sema::ActOnOpenMPSimdDirective(ArrayRef<OMPClause *> Clauses, Stmt *AStmt,
10194                                SourceLocation StartLoc, SourceLocation EndLoc,
10195                                VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10196   if (!AStmt)
10197     return StmtError();
10198 
10199   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10200   OMPLoopBasedDirective::HelperExprs B;
10201   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
10202   // define the nested loops number.
10203   unsigned NestedLoopCount = checkOpenMPLoop(
10204       OMPD_simd, getCollapseNumberExpr(Clauses), getOrderedNumberExpr(Clauses),
10205       AStmt, *this, *DSAStack, VarsWithImplicitDSA, B);
10206   if (NestedLoopCount == 0)
10207     return StmtError();
10208 
10209   assert((CurContext->isDependentContext() || B.builtAll()) &&
10210          "omp simd loop exprs were not built");
10211 
10212   if (!CurContext->isDependentContext()) {
10213     // Finalize the clauses that need pre-built expressions for CodeGen.
10214     for (OMPClause *C : Clauses) {
10215       if (auto *LC = dyn_cast<OMPLinearClause>(C))
10216         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
10217                                      B.NumIterations, *this, CurScope,
10218                                      DSAStack))
10219           return StmtError();
10220     }
10221   }
10222 
10223   if (checkSimdlenSafelenSpecified(*this, Clauses))
10224     return StmtError();
10225 
10226   setFunctionHasBranchProtectedScope();
10227   return OMPSimdDirective::Create(Context, StartLoc, EndLoc, NestedLoopCount,
10228                                   Clauses, AStmt, B);
10229 }
10230 
10231 StmtResult
10232 Sema::ActOnOpenMPForDirective(ArrayRef<OMPClause *> Clauses, Stmt *AStmt,
10233                               SourceLocation StartLoc, SourceLocation EndLoc,
10234                               VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10235   if (!AStmt)
10236     return StmtError();
10237 
10238   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10239   OMPLoopBasedDirective::HelperExprs B;
10240   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
10241   // define the nested loops number.
10242   unsigned NestedLoopCount = checkOpenMPLoop(
10243       OMPD_for, getCollapseNumberExpr(Clauses), getOrderedNumberExpr(Clauses),
10244       AStmt, *this, *DSAStack, VarsWithImplicitDSA, B);
10245   if (NestedLoopCount == 0)
10246     return StmtError();
10247 
10248   assert((CurContext->isDependentContext() || B.builtAll()) &&
10249          "omp for loop exprs were not built");
10250 
10251   if (!CurContext->isDependentContext()) {
10252     // Finalize the clauses that need pre-built expressions for CodeGen.
10253     for (OMPClause *C : Clauses) {
10254       if (auto *LC = dyn_cast<OMPLinearClause>(C))
10255         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
10256                                      B.NumIterations, *this, CurScope,
10257                                      DSAStack))
10258           return StmtError();
10259     }
10260   }
10261 
10262   setFunctionHasBranchProtectedScope();
10263   return OMPForDirective::Create(
10264       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
10265       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
10266 }
10267 
10268 StmtResult Sema::ActOnOpenMPForSimdDirective(
10269     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10270     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10271   if (!AStmt)
10272     return StmtError();
10273 
10274   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10275   OMPLoopBasedDirective::HelperExprs B;
10276   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
10277   // define the nested loops number.
10278   unsigned NestedLoopCount =
10279       checkOpenMPLoop(OMPD_for_simd, getCollapseNumberExpr(Clauses),
10280                       getOrderedNumberExpr(Clauses), AStmt, *this, *DSAStack,
10281                       VarsWithImplicitDSA, B);
10282   if (NestedLoopCount == 0)
10283     return StmtError();
10284 
10285   assert((CurContext->isDependentContext() || B.builtAll()) &&
10286          "omp for simd loop exprs were not built");
10287 
10288   if (!CurContext->isDependentContext()) {
10289     // Finalize the clauses that need pre-built expressions for CodeGen.
10290     for (OMPClause *C : Clauses) {
10291       if (auto *LC = dyn_cast<OMPLinearClause>(C))
10292         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
10293                                      B.NumIterations, *this, CurScope,
10294                                      DSAStack))
10295           return StmtError();
10296     }
10297   }
10298 
10299   if (checkSimdlenSafelenSpecified(*this, Clauses))
10300     return StmtError();
10301 
10302   setFunctionHasBranchProtectedScope();
10303   return OMPForSimdDirective::Create(Context, StartLoc, EndLoc, NestedLoopCount,
10304                                      Clauses, AStmt, B);
10305 }
10306 
10307 StmtResult Sema::ActOnOpenMPSectionsDirective(ArrayRef<OMPClause *> Clauses,
10308                                               Stmt *AStmt,
10309                                               SourceLocation StartLoc,
10310                                               SourceLocation EndLoc) {
10311   if (!AStmt)
10312     return StmtError();
10313 
10314   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10315   auto BaseStmt = AStmt;
10316   while (auto *CS = dyn_cast_or_null<CapturedStmt>(BaseStmt))
10317     BaseStmt = CS->getCapturedStmt();
10318   if (auto *C = dyn_cast_or_null<CompoundStmt>(BaseStmt)) {
10319     auto S = C->children();
10320     if (S.begin() == S.end())
10321       return StmtError();
10322     // All associated statements must be '#pragma omp section' except for
10323     // the first one.
10324     for (Stmt *SectionStmt : llvm::drop_begin(S)) {
10325       if (!SectionStmt || !isa<OMPSectionDirective>(SectionStmt)) {
10326         if (SectionStmt)
10327           Diag(SectionStmt->getBeginLoc(),
10328                diag::err_omp_sections_substmt_not_section);
10329         return StmtError();
10330       }
10331       cast<OMPSectionDirective>(SectionStmt)
10332           ->setHasCancel(DSAStack->isCancelRegion());
10333     }
10334   } else {
10335     Diag(AStmt->getBeginLoc(), diag::err_omp_sections_not_compound_stmt);
10336     return StmtError();
10337   }
10338 
10339   setFunctionHasBranchProtectedScope();
10340 
10341   return OMPSectionsDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
10342                                       DSAStack->getTaskgroupReductionRef(),
10343                                       DSAStack->isCancelRegion());
10344 }
10345 
10346 StmtResult Sema::ActOnOpenMPSectionDirective(Stmt *AStmt,
10347                                              SourceLocation StartLoc,
10348                                              SourceLocation EndLoc) {
10349   if (!AStmt)
10350     return StmtError();
10351 
10352   setFunctionHasBranchProtectedScope();
10353   DSAStack->setParentCancelRegion(DSAStack->isCancelRegion());
10354 
10355   return OMPSectionDirective::Create(Context, StartLoc, EndLoc, AStmt,
10356                                      DSAStack->isCancelRegion());
10357 }
10358 
10359 static Expr *getDirectCallExpr(Expr *E) {
10360   E = E->IgnoreParenCasts()->IgnoreImplicit();
10361   if (auto *CE = dyn_cast<CallExpr>(E))
10362     if (CE->getDirectCallee())
10363       return E;
10364   return nullptr;
10365 }
10366 
10367 StmtResult Sema::ActOnOpenMPDispatchDirective(ArrayRef<OMPClause *> Clauses,
10368                                               Stmt *AStmt,
10369                                               SourceLocation StartLoc,
10370                                               SourceLocation EndLoc) {
10371   if (!AStmt)
10372     return StmtError();
10373 
10374   Stmt *S = cast<CapturedStmt>(AStmt)->getCapturedStmt();
10375 
10376   // 5.1 OpenMP
10377   // expression-stmt : an expression statement with one of the following forms:
10378   //   expression = target-call ( [expression-list] );
10379   //   target-call ( [expression-list] );
10380 
10381   SourceLocation TargetCallLoc;
10382 
10383   if (!CurContext->isDependentContext()) {
10384     Expr *TargetCall = nullptr;
10385 
10386     auto *E = dyn_cast<Expr>(S);
10387     if (!E) {
10388       Diag(S->getBeginLoc(), diag::err_omp_dispatch_statement_call);
10389       return StmtError();
10390     }
10391 
10392     E = E->IgnoreParenCasts()->IgnoreImplicit();
10393 
10394     if (auto *BO = dyn_cast<BinaryOperator>(E)) {
10395       if (BO->getOpcode() == BO_Assign)
10396         TargetCall = getDirectCallExpr(BO->getRHS());
10397     } else {
10398       if (auto *COCE = dyn_cast<CXXOperatorCallExpr>(E))
10399         if (COCE->getOperator() == OO_Equal)
10400           TargetCall = getDirectCallExpr(COCE->getArg(1));
10401       if (!TargetCall)
10402         TargetCall = getDirectCallExpr(E);
10403     }
10404     if (!TargetCall) {
10405       Diag(E->getBeginLoc(), diag::err_omp_dispatch_statement_call);
10406       return StmtError();
10407     }
10408     TargetCallLoc = TargetCall->getExprLoc();
10409   }
10410 
10411   setFunctionHasBranchProtectedScope();
10412 
10413   return OMPDispatchDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
10414                                       TargetCallLoc);
10415 }
10416 
10417 static bool checkGenericLoopLastprivate(Sema &S, ArrayRef<OMPClause *> Clauses,
10418                                         OpenMPDirectiveKind K,
10419                                         DSAStackTy *Stack) {
10420   bool ErrorFound = false;
10421   for (OMPClause *C : Clauses) {
10422     if (auto *LPC = dyn_cast<OMPLastprivateClause>(C)) {
10423       for (Expr *RefExpr : LPC->varlists()) {
10424         SourceLocation ELoc;
10425         SourceRange ERange;
10426         Expr *SimpleRefExpr = RefExpr;
10427         auto Res = getPrivateItem(S, SimpleRefExpr, ELoc, ERange);
10428         if (ValueDecl *D = Res.first) {
10429           auto &&Info = Stack->isLoopControlVariable(D);
10430           if (!Info.first) {
10431             S.Diag(ELoc, diag::err_omp_lastprivate_loop_var_non_loop_iteration)
10432                 << getOpenMPDirectiveName(K);
10433             ErrorFound = true;
10434           }
10435         }
10436       }
10437     }
10438   }
10439   return ErrorFound;
10440 }
10441 
10442 StmtResult Sema::ActOnOpenMPGenericLoopDirective(
10443     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10444     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10445   if (!AStmt)
10446     return StmtError();
10447 
10448   // OpenMP 5.1 [2.11.7, loop construct, Restrictions]
10449   // A list item may not appear in a lastprivate clause unless it is the
10450   // loop iteration variable of a loop that is associated with the construct.
10451   if (checkGenericLoopLastprivate(*this, Clauses, OMPD_loop, DSAStack))
10452     return StmtError();
10453 
10454   auto *CS = cast<CapturedStmt>(AStmt);
10455   // 1.2.2 OpenMP Language Terminology
10456   // Structured block - An executable statement with a single entry at the
10457   // top and a single exit at the bottom.
10458   // The point of exit cannot be a branch out of the structured block.
10459   // longjmp() and throw() must not violate the entry/exit criteria.
10460   CS->getCapturedDecl()->setNothrow();
10461 
10462   OMPLoopDirective::HelperExprs B;
10463   // In presence of clause 'collapse', it will define the nested loops number.
10464   unsigned NestedLoopCount = checkOpenMPLoop(
10465       OMPD_loop, getCollapseNumberExpr(Clauses), getOrderedNumberExpr(Clauses),
10466       AStmt, *this, *DSAStack, VarsWithImplicitDSA, B);
10467   if (NestedLoopCount == 0)
10468     return StmtError();
10469 
10470   assert((CurContext->isDependentContext() || B.builtAll()) &&
10471          "omp loop exprs were not built");
10472 
10473   setFunctionHasBranchProtectedScope();
10474   return OMPGenericLoopDirective::Create(Context, StartLoc, EndLoc,
10475                                          NestedLoopCount, Clauses, AStmt, B);
10476 }
10477 
10478 StmtResult Sema::ActOnOpenMPTeamsGenericLoopDirective(
10479     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10480     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10481   if (!AStmt)
10482     return StmtError();
10483 
10484   // OpenMP 5.1 [2.11.7, loop construct, Restrictions]
10485   // A list item may not appear in a lastprivate clause unless it is the
10486   // loop iteration variable of a loop that is associated with the construct.
10487   if (checkGenericLoopLastprivate(*this, Clauses, OMPD_teams_loop, DSAStack))
10488     return StmtError();
10489 
10490   auto *CS = cast<CapturedStmt>(AStmt);
10491   // 1.2.2 OpenMP Language Terminology
10492   // Structured block - An executable statement with a single entry at the
10493   // top and a single exit at the bottom.
10494   // The point of exit cannot be a branch out of the structured block.
10495   // longjmp() and throw() must not violate the entry/exit criteria.
10496   CS->getCapturedDecl()->setNothrow();
10497   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_teams_loop);
10498        ThisCaptureLevel > 1; --ThisCaptureLevel) {
10499     CS = cast<CapturedStmt>(CS->getCapturedStmt());
10500     // 1.2.2 OpenMP Language Terminology
10501     // Structured block - An executable statement with a single entry at the
10502     // top and a single exit at the bottom.
10503     // The point of exit cannot be a branch out of the structured block.
10504     // longjmp() and throw() must not violate the entry/exit criteria.
10505     CS->getCapturedDecl()->setNothrow();
10506   }
10507 
10508   OMPLoopDirective::HelperExprs B;
10509   // In presence of clause 'collapse', it will define the nested loops number.
10510   unsigned NestedLoopCount =
10511       checkOpenMPLoop(OMPD_teams_loop, getCollapseNumberExpr(Clauses),
10512                       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
10513                       VarsWithImplicitDSA, B);
10514   if (NestedLoopCount == 0)
10515     return StmtError();
10516 
10517   assert((CurContext->isDependentContext() || B.builtAll()) &&
10518          "omp loop exprs were not built");
10519 
10520   setFunctionHasBranchProtectedScope();
10521   DSAStack->setParentTeamsRegionLoc(StartLoc);
10522 
10523   return OMPTeamsGenericLoopDirective::Create(
10524       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
10525 }
10526 
10527 StmtResult Sema::ActOnOpenMPTargetTeamsGenericLoopDirective(
10528     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10529     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10530   if (!AStmt)
10531     return StmtError();
10532 
10533   // OpenMP 5.1 [2.11.7, loop construct, Restrictions]
10534   // A list item may not appear in a lastprivate clause unless it is the
10535   // loop iteration variable of a loop that is associated with the construct.
10536   if (checkGenericLoopLastprivate(*this, Clauses, OMPD_target_teams_loop,
10537                                   DSAStack))
10538     return StmtError();
10539 
10540   auto *CS = cast<CapturedStmt>(AStmt);
10541   // 1.2.2 OpenMP Language Terminology
10542   // Structured block - An executable statement with a single entry at the
10543   // top and a single exit at the bottom.
10544   // The point of exit cannot be a branch out of the structured block.
10545   // longjmp() and throw() must not violate the entry/exit criteria.
10546   CS->getCapturedDecl()->setNothrow();
10547   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_teams_loop);
10548        ThisCaptureLevel > 1; --ThisCaptureLevel) {
10549     CS = cast<CapturedStmt>(CS->getCapturedStmt());
10550     // 1.2.2 OpenMP Language Terminology
10551     // Structured block - An executable statement with a single entry at the
10552     // top and a single exit at the bottom.
10553     // The point of exit cannot be a branch out of the structured block.
10554     // longjmp() and throw() must not violate the entry/exit criteria.
10555     CS->getCapturedDecl()->setNothrow();
10556   }
10557 
10558   OMPLoopDirective::HelperExprs B;
10559   // In presence of clause 'collapse', it will define the nested loops number.
10560   unsigned NestedLoopCount =
10561       checkOpenMPLoop(OMPD_target_teams_loop, getCollapseNumberExpr(Clauses),
10562                       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
10563                       VarsWithImplicitDSA, B);
10564   if (NestedLoopCount == 0)
10565     return StmtError();
10566 
10567   assert((CurContext->isDependentContext() || B.builtAll()) &&
10568          "omp loop exprs were not built");
10569 
10570   setFunctionHasBranchProtectedScope();
10571 
10572   return OMPTargetTeamsGenericLoopDirective::Create(
10573       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
10574 }
10575 
10576 StmtResult Sema::ActOnOpenMPParallelGenericLoopDirective(
10577     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10578     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10579   if (!AStmt)
10580     return StmtError();
10581 
10582   // OpenMP 5.1 [2.11.7, loop construct, Restrictions]
10583   // A list item may not appear in a lastprivate clause unless it is the
10584   // loop iteration variable of a loop that is associated with the construct.
10585   if (checkGenericLoopLastprivate(*this, Clauses, OMPD_parallel_loop, DSAStack))
10586     return StmtError();
10587 
10588   auto *CS = cast<CapturedStmt>(AStmt);
10589   // 1.2.2 OpenMP Language Terminology
10590   // Structured block - An executable statement with a single entry at the
10591   // top and a single exit at the bottom.
10592   // The point of exit cannot be a branch out of the structured block.
10593   // longjmp() and throw() must not violate the entry/exit criteria.
10594   CS->getCapturedDecl()->setNothrow();
10595   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_parallel_loop);
10596        ThisCaptureLevel > 1; --ThisCaptureLevel) {
10597     CS = cast<CapturedStmt>(CS->getCapturedStmt());
10598     // 1.2.2 OpenMP Language Terminology
10599     // Structured block - An executable statement with a single entry at the
10600     // top and a single exit at the bottom.
10601     // The point of exit cannot be a branch out of the structured block.
10602     // longjmp() and throw() must not violate the entry/exit criteria.
10603     CS->getCapturedDecl()->setNothrow();
10604   }
10605 
10606   OMPLoopDirective::HelperExprs B;
10607   // In presence of clause 'collapse', it will define the nested loops number.
10608   unsigned NestedLoopCount =
10609       checkOpenMPLoop(OMPD_parallel_loop, getCollapseNumberExpr(Clauses),
10610                       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
10611                       VarsWithImplicitDSA, B);
10612   if (NestedLoopCount == 0)
10613     return StmtError();
10614 
10615   assert((CurContext->isDependentContext() || B.builtAll()) &&
10616          "omp loop exprs were not built");
10617 
10618   setFunctionHasBranchProtectedScope();
10619 
10620   return OMPParallelGenericLoopDirective::Create(
10621       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
10622 }
10623 
10624 StmtResult Sema::ActOnOpenMPTargetParallelGenericLoopDirective(
10625     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10626     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10627   if (!AStmt)
10628     return StmtError();
10629 
10630   // OpenMP 5.1 [2.11.7, loop construct, Restrictions]
10631   // A list item may not appear in a lastprivate clause unless it is the
10632   // loop iteration variable of a loop that is associated with the construct.
10633   if (checkGenericLoopLastprivate(*this, Clauses, OMPD_target_parallel_loop,
10634                                   DSAStack))
10635     return StmtError();
10636 
10637   auto *CS = cast<CapturedStmt>(AStmt);
10638   // 1.2.2 OpenMP Language Terminology
10639   // Structured block - An executable statement with a single entry at the
10640   // top and a single exit at the bottom.
10641   // The point of exit cannot be a branch out of the structured block.
10642   // longjmp() and throw() must not violate the entry/exit criteria.
10643   CS->getCapturedDecl()->setNothrow();
10644   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_parallel_loop);
10645        ThisCaptureLevel > 1; --ThisCaptureLevel) {
10646     CS = cast<CapturedStmt>(CS->getCapturedStmt());
10647     // 1.2.2 OpenMP Language Terminology
10648     // Structured block - An executable statement with a single entry at the
10649     // top and a single exit at the bottom.
10650     // The point of exit cannot be a branch out of the structured block.
10651     // longjmp() and throw() must not violate the entry/exit criteria.
10652     CS->getCapturedDecl()->setNothrow();
10653   }
10654 
10655   OMPLoopDirective::HelperExprs B;
10656   // In presence of clause 'collapse', it will define the nested loops number.
10657   unsigned NestedLoopCount =
10658       checkOpenMPLoop(OMPD_target_parallel_loop, getCollapseNumberExpr(Clauses),
10659                       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
10660                       VarsWithImplicitDSA, B);
10661   if (NestedLoopCount == 0)
10662     return StmtError();
10663 
10664   assert((CurContext->isDependentContext() || B.builtAll()) &&
10665          "omp loop exprs were not built");
10666 
10667   setFunctionHasBranchProtectedScope();
10668 
10669   return OMPTargetParallelGenericLoopDirective::Create(
10670       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
10671 }
10672 
10673 StmtResult Sema::ActOnOpenMPSingleDirective(ArrayRef<OMPClause *> Clauses,
10674                                             Stmt *AStmt,
10675                                             SourceLocation StartLoc,
10676                                             SourceLocation EndLoc) {
10677   if (!AStmt)
10678     return StmtError();
10679 
10680   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10681 
10682   setFunctionHasBranchProtectedScope();
10683 
10684   // OpenMP [2.7.3, single Construct, Restrictions]
10685   // The copyprivate clause must not be used with the nowait clause.
10686   const OMPClause *Nowait = nullptr;
10687   const OMPClause *Copyprivate = nullptr;
10688   for (const OMPClause *Clause : Clauses) {
10689     if (Clause->getClauseKind() == OMPC_nowait)
10690       Nowait = Clause;
10691     else if (Clause->getClauseKind() == OMPC_copyprivate)
10692       Copyprivate = Clause;
10693     if (Copyprivate && Nowait) {
10694       Diag(Copyprivate->getBeginLoc(),
10695            diag::err_omp_single_copyprivate_with_nowait);
10696       Diag(Nowait->getBeginLoc(), diag::note_omp_nowait_clause_here);
10697       return StmtError();
10698     }
10699   }
10700 
10701   return OMPSingleDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt);
10702 }
10703 
10704 StmtResult Sema::ActOnOpenMPMasterDirective(Stmt *AStmt,
10705                                             SourceLocation StartLoc,
10706                                             SourceLocation EndLoc) {
10707   if (!AStmt)
10708     return StmtError();
10709 
10710   setFunctionHasBranchProtectedScope();
10711 
10712   return OMPMasterDirective::Create(Context, StartLoc, EndLoc, AStmt);
10713 }
10714 
10715 StmtResult Sema::ActOnOpenMPMaskedDirective(ArrayRef<OMPClause *> Clauses,
10716                                             Stmt *AStmt,
10717                                             SourceLocation StartLoc,
10718                                             SourceLocation EndLoc) {
10719   if (!AStmt)
10720     return StmtError();
10721 
10722   setFunctionHasBranchProtectedScope();
10723 
10724   return OMPMaskedDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt);
10725 }
10726 
10727 StmtResult Sema::ActOnOpenMPCriticalDirective(
10728     const DeclarationNameInfo &DirName, ArrayRef<OMPClause *> Clauses,
10729     Stmt *AStmt, SourceLocation StartLoc, SourceLocation EndLoc) {
10730   if (!AStmt)
10731     return StmtError();
10732 
10733   bool ErrorFound = false;
10734   llvm::APSInt Hint;
10735   SourceLocation HintLoc;
10736   bool DependentHint = false;
10737   for (const OMPClause *C : Clauses) {
10738     if (C->getClauseKind() == OMPC_hint) {
10739       if (!DirName.getName()) {
10740         Diag(C->getBeginLoc(), diag::err_omp_hint_clause_no_name);
10741         ErrorFound = true;
10742       }
10743       Expr *E = cast<OMPHintClause>(C)->getHint();
10744       if (E->isTypeDependent() || E->isValueDependent() ||
10745           E->isInstantiationDependent()) {
10746         DependentHint = true;
10747       } else {
10748         Hint = E->EvaluateKnownConstInt(Context);
10749         HintLoc = C->getBeginLoc();
10750       }
10751     }
10752   }
10753   if (ErrorFound)
10754     return StmtError();
10755   const auto Pair = DSAStack->getCriticalWithHint(DirName);
10756   if (Pair.first && DirName.getName() && !DependentHint) {
10757     if (llvm::APSInt::compareValues(Hint, Pair.second) != 0) {
10758       Diag(StartLoc, diag::err_omp_critical_with_hint);
10759       if (HintLoc.isValid())
10760         Diag(HintLoc, diag::note_omp_critical_hint_here)
10761             << 0 << toString(Hint, /*Radix=*/10, /*Signed=*/false);
10762       else
10763         Diag(StartLoc, diag::note_omp_critical_no_hint) << 0;
10764       if (const auto *C = Pair.first->getSingleClause<OMPHintClause>()) {
10765         Diag(C->getBeginLoc(), diag::note_omp_critical_hint_here)
10766             << 1
10767             << toString(C->getHint()->EvaluateKnownConstInt(Context),
10768                         /*Radix=*/10, /*Signed=*/false);
10769       } else {
10770         Diag(Pair.first->getBeginLoc(), diag::note_omp_critical_no_hint) << 1;
10771       }
10772     }
10773   }
10774 
10775   setFunctionHasBranchProtectedScope();
10776 
10777   auto *Dir = OMPCriticalDirective::Create(Context, DirName, StartLoc, EndLoc,
10778                                            Clauses, AStmt);
10779   if (!Pair.first && DirName.getName() && !DependentHint)
10780     DSAStack->addCriticalWithHint(Dir, Hint);
10781   return Dir;
10782 }
10783 
10784 StmtResult Sema::ActOnOpenMPParallelForDirective(
10785     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10786     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10787   if (!AStmt)
10788     return StmtError();
10789 
10790   auto *CS = cast<CapturedStmt>(AStmt);
10791   // 1.2.2 OpenMP Language Terminology
10792   // Structured block - An executable statement with a single entry at the
10793   // top and a single exit at the bottom.
10794   // The point of exit cannot be a branch out of the structured block.
10795   // longjmp() and throw() must not violate the entry/exit criteria.
10796   CS->getCapturedDecl()->setNothrow();
10797 
10798   OMPLoopBasedDirective::HelperExprs B;
10799   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
10800   // define the nested loops number.
10801   unsigned NestedLoopCount =
10802       checkOpenMPLoop(OMPD_parallel_for, getCollapseNumberExpr(Clauses),
10803                       getOrderedNumberExpr(Clauses), AStmt, *this, *DSAStack,
10804                       VarsWithImplicitDSA, B);
10805   if (NestedLoopCount == 0)
10806     return StmtError();
10807 
10808   assert((CurContext->isDependentContext() || B.builtAll()) &&
10809          "omp parallel for loop exprs were not built");
10810 
10811   if (!CurContext->isDependentContext()) {
10812     // Finalize the clauses that need pre-built expressions for CodeGen.
10813     for (OMPClause *C : Clauses) {
10814       if (auto *LC = dyn_cast<OMPLinearClause>(C))
10815         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
10816                                      B.NumIterations, *this, CurScope,
10817                                      DSAStack))
10818           return StmtError();
10819     }
10820   }
10821 
10822   setFunctionHasBranchProtectedScope();
10823   return OMPParallelForDirective::Create(
10824       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
10825       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
10826 }
10827 
10828 StmtResult Sema::ActOnOpenMPParallelForSimdDirective(
10829     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10830     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10831   if (!AStmt)
10832     return StmtError();
10833 
10834   auto *CS = cast<CapturedStmt>(AStmt);
10835   // 1.2.2 OpenMP Language Terminology
10836   // Structured block - An executable statement with a single entry at the
10837   // top and a single exit at the bottom.
10838   // The point of exit cannot be a branch out of the structured block.
10839   // longjmp() and throw() must not violate the entry/exit criteria.
10840   CS->getCapturedDecl()->setNothrow();
10841 
10842   OMPLoopBasedDirective::HelperExprs B;
10843   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
10844   // define the nested loops number.
10845   unsigned NestedLoopCount =
10846       checkOpenMPLoop(OMPD_parallel_for_simd, getCollapseNumberExpr(Clauses),
10847                       getOrderedNumberExpr(Clauses), AStmt, *this, *DSAStack,
10848                       VarsWithImplicitDSA, B);
10849   if (NestedLoopCount == 0)
10850     return StmtError();
10851 
10852   if (!CurContext->isDependentContext()) {
10853     // Finalize the clauses that need pre-built expressions for CodeGen.
10854     for (OMPClause *C : Clauses) {
10855       if (auto *LC = dyn_cast<OMPLinearClause>(C))
10856         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
10857                                      B.NumIterations, *this, CurScope,
10858                                      DSAStack))
10859           return StmtError();
10860     }
10861   }
10862 
10863   if (checkSimdlenSafelenSpecified(*this, Clauses))
10864     return StmtError();
10865 
10866   setFunctionHasBranchProtectedScope();
10867   return OMPParallelForSimdDirective::Create(
10868       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
10869 }
10870 
10871 StmtResult
10872 Sema::ActOnOpenMPParallelMasterDirective(ArrayRef<OMPClause *> Clauses,
10873                                          Stmt *AStmt, SourceLocation StartLoc,
10874                                          SourceLocation EndLoc) {
10875   if (!AStmt)
10876     return StmtError();
10877 
10878   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10879   auto *CS = cast<CapturedStmt>(AStmt);
10880   // 1.2.2 OpenMP Language Terminology
10881   // Structured block - An executable statement with a single entry at the
10882   // top and a single exit at the bottom.
10883   // The point of exit cannot be a branch out of the structured block.
10884   // longjmp() and throw() must not violate the entry/exit criteria.
10885   CS->getCapturedDecl()->setNothrow();
10886 
10887   setFunctionHasBranchProtectedScope();
10888 
10889   return OMPParallelMasterDirective::Create(
10890       Context, StartLoc, EndLoc, Clauses, AStmt,
10891       DSAStack->getTaskgroupReductionRef());
10892 }
10893 
10894 StmtResult
10895 Sema::ActOnOpenMPParallelMaskedDirective(ArrayRef<OMPClause *> Clauses,
10896                                          Stmt *AStmt, SourceLocation StartLoc,
10897                                          SourceLocation EndLoc) {
10898   if (!AStmt)
10899     return StmtError();
10900 
10901   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10902   auto *CS = cast<CapturedStmt>(AStmt);
10903   // 1.2.2 OpenMP Language Terminology
10904   // Structured block - An executable statement with a single entry at the
10905   // top and a single exit at the bottom.
10906   // The point of exit cannot be a branch out of the structured block.
10907   // longjmp() and throw() must not violate the entry/exit criteria.
10908   CS->getCapturedDecl()->setNothrow();
10909 
10910   setFunctionHasBranchProtectedScope();
10911 
10912   return OMPParallelMaskedDirective::Create(
10913       Context, StartLoc, EndLoc, Clauses, AStmt,
10914       DSAStack->getTaskgroupReductionRef());
10915 }
10916 
10917 StmtResult
10918 Sema::ActOnOpenMPParallelSectionsDirective(ArrayRef<OMPClause *> Clauses,
10919                                            Stmt *AStmt, SourceLocation StartLoc,
10920                                            SourceLocation EndLoc) {
10921   if (!AStmt)
10922     return StmtError();
10923 
10924   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10925   auto BaseStmt = AStmt;
10926   while (auto *CS = dyn_cast_or_null<CapturedStmt>(BaseStmt))
10927     BaseStmt = CS->getCapturedStmt();
10928   if (auto *C = dyn_cast_or_null<CompoundStmt>(BaseStmt)) {
10929     auto S = C->children();
10930     if (S.begin() == S.end())
10931       return StmtError();
10932     // All associated statements must be '#pragma omp section' except for
10933     // the first one.
10934     for (Stmt *SectionStmt : llvm::drop_begin(S)) {
10935       if (!SectionStmt || !isa<OMPSectionDirective>(SectionStmt)) {
10936         if (SectionStmt)
10937           Diag(SectionStmt->getBeginLoc(),
10938                diag::err_omp_parallel_sections_substmt_not_section);
10939         return StmtError();
10940       }
10941       cast<OMPSectionDirective>(SectionStmt)
10942           ->setHasCancel(DSAStack->isCancelRegion());
10943     }
10944   } else {
10945     Diag(AStmt->getBeginLoc(),
10946          diag::err_omp_parallel_sections_not_compound_stmt);
10947     return StmtError();
10948   }
10949 
10950   setFunctionHasBranchProtectedScope();
10951 
10952   return OMPParallelSectionsDirective::Create(
10953       Context, StartLoc, EndLoc, Clauses, AStmt,
10954       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
10955 }
10956 
10957 /// Find and diagnose mutually exclusive clause kinds.
10958 static bool checkMutuallyExclusiveClauses(
10959     Sema &S, ArrayRef<OMPClause *> Clauses,
10960     ArrayRef<OpenMPClauseKind> MutuallyExclusiveClauses) {
10961   const OMPClause *PrevClause = nullptr;
10962   bool ErrorFound = false;
10963   for (const OMPClause *C : Clauses) {
10964     if (llvm::is_contained(MutuallyExclusiveClauses, C->getClauseKind())) {
10965       if (!PrevClause) {
10966         PrevClause = C;
10967       } else if (PrevClause->getClauseKind() != C->getClauseKind()) {
10968         S.Diag(C->getBeginLoc(), diag::err_omp_clauses_mutually_exclusive)
10969             << getOpenMPClauseName(C->getClauseKind())
10970             << getOpenMPClauseName(PrevClause->getClauseKind());
10971         S.Diag(PrevClause->getBeginLoc(), diag::note_omp_previous_clause)
10972             << getOpenMPClauseName(PrevClause->getClauseKind());
10973         ErrorFound = true;
10974       }
10975     }
10976   }
10977   return ErrorFound;
10978 }
10979 
10980 StmtResult Sema::ActOnOpenMPTaskDirective(ArrayRef<OMPClause *> Clauses,
10981                                           Stmt *AStmt, SourceLocation StartLoc,
10982                                           SourceLocation EndLoc) {
10983   if (!AStmt)
10984     return StmtError();
10985 
10986   // OpenMP 5.0, 2.10.1 task Construct
10987   // If a detach clause appears on the directive, then a mergeable clause cannot
10988   // appear on the same directive.
10989   if (checkMutuallyExclusiveClauses(*this, Clauses,
10990                                     {OMPC_detach, OMPC_mergeable}))
10991     return StmtError();
10992 
10993   auto *CS = cast<CapturedStmt>(AStmt);
10994   // 1.2.2 OpenMP Language Terminology
10995   // Structured block - An executable statement with a single entry at the
10996   // top and a single exit at the bottom.
10997   // The point of exit cannot be a branch out of the structured block.
10998   // longjmp() and throw() must not violate the entry/exit criteria.
10999   CS->getCapturedDecl()->setNothrow();
11000 
11001   setFunctionHasBranchProtectedScope();
11002 
11003   return OMPTaskDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
11004                                   DSAStack->isCancelRegion());
11005 }
11006 
11007 StmtResult Sema::ActOnOpenMPTaskyieldDirective(SourceLocation StartLoc,
11008                                                SourceLocation EndLoc) {
11009   return OMPTaskyieldDirective::Create(Context, StartLoc, EndLoc);
11010 }
11011 
11012 StmtResult Sema::ActOnOpenMPBarrierDirective(SourceLocation StartLoc,
11013                                              SourceLocation EndLoc) {
11014   return OMPBarrierDirective::Create(Context, StartLoc, EndLoc);
11015 }
11016 
11017 StmtResult Sema::ActOnOpenMPTaskwaitDirective(ArrayRef<OMPClause *> Clauses,
11018                                               SourceLocation StartLoc,
11019                                               SourceLocation EndLoc) {
11020   return OMPTaskwaitDirective::Create(Context, StartLoc, EndLoc, Clauses);
11021 }
11022 
11023 StmtResult Sema::ActOnOpenMPTaskgroupDirective(ArrayRef<OMPClause *> Clauses,
11024                                                Stmt *AStmt,
11025                                                SourceLocation StartLoc,
11026                                                SourceLocation EndLoc) {
11027   if (!AStmt)
11028     return StmtError();
11029 
11030   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
11031 
11032   setFunctionHasBranchProtectedScope();
11033 
11034   return OMPTaskgroupDirective::Create(Context, StartLoc, EndLoc, Clauses,
11035                                        AStmt,
11036                                        DSAStack->getTaskgroupReductionRef());
11037 }
11038 
11039 StmtResult Sema::ActOnOpenMPFlushDirective(ArrayRef<OMPClause *> Clauses,
11040                                            SourceLocation StartLoc,
11041                                            SourceLocation EndLoc) {
11042   OMPFlushClause *FC = nullptr;
11043   OMPClause *OrderClause = nullptr;
11044   for (OMPClause *C : Clauses) {
11045     if (C->getClauseKind() == OMPC_flush)
11046       FC = cast<OMPFlushClause>(C);
11047     else
11048       OrderClause = C;
11049   }
11050   OpenMPClauseKind MemOrderKind = OMPC_unknown;
11051   SourceLocation MemOrderLoc;
11052   for (const OMPClause *C : Clauses) {
11053     if (C->getClauseKind() == OMPC_acq_rel ||
11054         C->getClauseKind() == OMPC_acquire ||
11055         C->getClauseKind() == OMPC_release) {
11056       if (MemOrderKind != OMPC_unknown) {
11057         Diag(C->getBeginLoc(), diag::err_omp_several_mem_order_clauses)
11058             << getOpenMPDirectiveName(OMPD_flush) << 1
11059             << SourceRange(C->getBeginLoc(), C->getEndLoc());
11060         Diag(MemOrderLoc, diag::note_omp_previous_mem_order_clause)
11061             << getOpenMPClauseName(MemOrderKind);
11062       } else {
11063         MemOrderKind = C->getClauseKind();
11064         MemOrderLoc = C->getBeginLoc();
11065       }
11066     }
11067   }
11068   if (FC && OrderClause) {
11069     Diag(FC->getLParenLoc(), diag::err_omp_flush_order_clause_and_list)
11070         << getOpenMPClauseName(OrderClause->getClauseKind());
11071     Diag(OrderClause->getBeginLoc(), diag::note_omp_flush_order_clause_here)
11072         << getOpenMPClauseName(OrderClause->getClauseKind());
11073     return StmtError();
11074   }
11075   return OMPFlushDirective::Create(Context, StartLoc, EndLoc, Clauses);
11076 }
11077 
11078 StmtResult Sema::ActOnOpenMPDepobjDirective(ArrayRef<OMPClause *> Clauses,
11079                                             SourceLocation StartLoc,
11080                                             SourceLocation EndLoc) {
11081   if (Clauses.empty()) {
11082     Diag(StartLoc, diag::err_omp_depobj_expected);
11083     return StmtError();
11084   } else if (Clauses[0]->getClauseKind() != OMPC_depobj) {
11085     Diag(Clauses[0]->getBeginLoc(), diag::err_omp_depobj_expected);
11086     return StmtError();
11087   }
11088   // Only depobj expression and another single clause is allowed.
11089   if (Clauses.size() > 2) {
11090     Diag(Clauses[2]->getBeginLoc(),
11091          diag::err_omp_depobj_single_clause_expected);
11092     return StmtError();
11093   } else if (Clauses.size() < 1) {
11094     Diag(Clauses[0]->getEndLoc(), diag::err_omp_depobj_single_clause_expected);
11095     return StmtError();
11096   }
11097   return OMPDepobjDirective::Create(Context, StartLoc, EndLoc, Clauses);
11098 }
11099 
11100 StmtResult Sema::ActOnOpenMPScanDirective(ArrayRef<OMPClause *> Clauses,
11101                                           SourceLocation StartLoc,
11102                                           SourceLocation EndLoc) {
11103   // Check that exactly one clause is specified.
11104   if (Clauses.size() != 1) {
11105     Diag(Clauses.empty() ? EndLoc : Clauses[1]->getBeginLoc(),
11106          diag::err_omp_scan_single_clause_expected);
11107     return StmtError();
11108   }
11109   // Check that scan directive is used in the scopeof the OpenMP loop body.
11110   if (Scope *S = DSAStack->getCurScope()) {
11111     Scope *ParentS = S->getParent();
11112     if (!ParentS || ParentS->getParent() != ParentS->getBreakParent() ||
11113         !ParentS->getBreakParent()->isOpenMPLoopScope())
11114       return StmtError(Diag(StartLoc, diag::err_omp_orphaned_device_directive)
11115                        << getOpenMPDirectiveName(OMPD_scan) << 5);
11116   }
11117   // Check that only one instance of scan directives is used in the same outer
11118   // region.
11119   if (DSAStack->doesParentHasScanDirective()) {
11120     Diag(StartLoc, diag::err_omp_several_directives_in_region) << "scan";
11121     Diag(DSAStack->getParentScanDirectiveLoc(),
11122          diag::note_omp_previous_directive)
11123         << "scan";
11124     return StmtError();
11125   }
11126   DSAStack->setParentHasScanDirective(StartLoc);
11127   return OMPScanDirective::Create(Context, StartLoc, EndLoc, Clauses);
11128 }
11129 
11130 StmtResult Sema::ActOnOpenMPOrderedDirective(ArrayRef<OMPClause *> Clauses,
11131                                              Stmt *AStmt,
11132                                              SourceLocation StartLoc,
11133                                              SourceLocation EndLoc) {
11134   const OMPClause *DependFound = nullptr;
11135   const OMPClause *DependSourceClause = nullptr;
11136   const OMPClause *DependSinkClause = nullptr;
11137   bool ErrorFound = false;
11138   const OMPThreadsClause *TC = nullptr;
11139   const OMPSIMDClause *SC = nullptr;
11140   for (const OMPClause *C : Clauses) {
11141     if (auto *DC = dyn_cast<OMPDependClause>(C)) {
11142       DependFound = C;
11143       if (DC->getDependencyKind() == OMPC_DEPEND_source) {
11144         if (DependSourceClause) {
11145           Diag(C->getBeginLoc(), diag::err_omp_more_one_clause)
11146               << getOpenMPDirectiveName(OMPD_ordered)
11147               << getOpenMPClauseName(OMPC_depend) << 2;
11148           ErrorFound = true;
11149         } else {
11150           DependSourceClause = C;
11151         }
11152         if (DependSinkClause) {
11153           Diag(C->getBeginLoc(), diag::err_omp_depend_sink_source_not_allowed)
11154               << 0;
11155           ErrorFound = true;
11156         }
11157       } else if (DC->getDependencyKind() == OMPC_DEPEND_sink) {
11158         if (DependSourceClause) {
11159           Diag(C->getBeginLoc(), diag::err_omp_depend_sink_source_not_allowed)
11160               << 1;
11161           ErrorFound = true;
11162         }
11163         DependSinkClause = C;
11164       }
11165     } else if (C->getClauseKind() == OMPC_threads) {
11166       TC = cast<OMPThreadsClause>(C);
11167     } else if (C->getClauseKind() == OMPC_simd) {
11168       SC = cast<OMPSIMDClause>(C);
11169     }
11170   }
11171   if (!ErrorFound && !SC &&
11172       isOpenMPSimdDirective(DSAStack->getParentDirective())) {
11173     // OpenMP [2.8.1,simd Construct, Restrictions]
11174     // An ordered construct with the simd clause is the only OpenMP construct
11175     // that can appear in the simd region.
11176     Diag(StartLoc, diag::err_omp_prohibited_region_simd)
11177         << (LangOpts.OpenMP >= 50 ? 1 : 0);
11178     ErrorFound = true;
11179   } else if (DependFound && (TC || SC)) {
11180     Diag(DependFound->getBeginLoc(), diag::err_omp_depend_clause_thread_simd)
11181         << getOpenMPClauseName(TC ? TC->getClauseKind() : SC->getClauseKind());
11182     ErrorFound = true;
11183   } else if (DependFound && !DSAStack->getParentOrderedRegionParam().first) {
11184     Diag(DependFound->getBeginLoc(),
11185          diag::err_omp_ordered_directive_without_param);
11186     ErrorFound = true;
11187   } else if (TC || Clauses.empty()) {
11188     if (const Expr *Param = DSAStack->getParentOrderedRegionParam().first) {
11189       SourceLocation ErrLoc = TC ? TC->getBeginLoc() : StartLoc;
11190       Diag(ErrLoc, diag::err_omp_ordered_directive_with_param)
11191           << (TC != nullptr);
11192       Diag(Param->getBeginLoc(), diag::note_omp_ordered_param) << 1;
11193       ErrorFound = true;
11194     }
11195   }
11196   if ((!AStmt && !DependFound) || ErrorFound)
11197     return StmtError();
11198 
11199   // OpenMP 5.0, 2.17.9, ordered Construct, Restrictions.
11200   // During execution of an iteration of a worksharing-loop or a loop nest
11201   // within a worksharing-loop, simd, or worksharing-loop SIMD region, a thread
11202   // must not execute more than one ordered region corresponding to an ordered
11203   // construct without a depend clause.
11204   if (!DependFound) {
11205     if (DSAStack->doesParentHasOrderedDirective()) {
11206       Diag(StartLoc, diag::err_omp_several_directives_in_region) << "ordered";
11207       Diag(DSAStack->getParentOrderedDirectiveLoc(),
11208            diag::note_omp_previous_directive)
11209           << "ordered";
11210       return StmtError();
11211     }
11212     DSAStack->setParentHasOrderedDirective(StartLoc);
11213   }
11214 
11215   if (AStmt) {
11216     assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
11217 
11218     setFunctionHasBranchProtectedScope();
11219   }
11220 
11221   return OMPOrderedDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt);
11222 }
11223 
11224 namespace {
11225 /// Helper class for checking expression in 'omp atomic [update]'
11226 /// construct.
11227 class OpenMPAtomicUpdateChecker {
11228   /// Error results for atomic update expressions.
11229   enum ExprAnalysisErrorCode {
11230     /// A statement is not an expression statement.
11231     NotAnExpression,
11232     /// Expression is not builtin binary or unary operation.
11233     NotABinaryOrUnaryExpression,
11234     /// Unary operation is not post-/pre- increment/decrement operation.
11235     NotAnUnaryIncDecExpression,
11236     /// An expression is not of scalar type.
11237     NotAScalarType,
11238     /// A binary operation is not an assignment operation.
11239     NotAnAssignmentOp,
11240     /// RHS part of the binary operation is not a binary expression.
11241     NotABinaryExpression,
11242     /// RHS part is not additive/multiplicative/shift/biwise binary
11243     /// expression.
11244     NotABinaryOperator,
11245     /// RHS binary operation does not have reference to the updated LHS
11246     /// part.
11247     NotAnUpdateExpression,
11248     /// No errors is found.
11249     NoError
11250   };
11251   /// Reference to Sema.
11252   Sema &SemaRef;
11253   /// A location for note diagnostics (when error is found).
11254   SourceLocation NoteLoc;
11255   /// 'x' lvalue part of the source atomic expression.
11256   Expr *X;
11257   /// 'expr' rvalue part of the source atomic expression.
11258   Expr *E;
11259   /// Helper expression of the form
11260   /// 'OpaqueValueExpr(x) binop OpaqueValueExpr(expr)' or
11261   /// 'OpaqueValueExpr(expr) binop OpaqueValueExpr(x)'.
11262   Expr *UpdateExpr;
11263   /// Is 'x' a LHS in a RHS part of full update expression. It is
11264   /// important for non-associative operations.
11265   bool IsXLHSInRHSPart;
11266   BinaryOperatorKind Op;
11267   SourceLocation OpLoc;
11268   /// true if the source expression is a postfix unary operation, false
11269   /// if it is a prefix unary operation.
11270   bool IsPostfixUpdate;
11271 
11272 public:
11273   OpenMPAtomicUpdateChecker(Sema &SemaRef)
11274       : SemaRef(SemaRef), X(nullptr), E(nullptr), UpdateExpr(nullptr),
11275         IsXLHSInRHSPart(false), Op(BO_PtrMemD), IsPostfixUpdate(false) {}
11276   /// Check specified statement that it is suitable for 'atomic update'
11277   /// constructs and extract 'x', 'expr' and Operation from the original
11278   /// expression. If DiagId and NoteId == 0, then only check is performed
11279   /// without error notification.
11280   /// \param DiagId Diagnostic which should be emitted if error is found.
11281   /// \param NoteId Diagnostic note for the main error message.
11282   /// \return true if statement is not an update expression, false otherwise.
11283   bool checkStatement(Stmt *S, unsigned DiagId = 0, unsigned NoteId = 0);
11284   /// Return the 'x' lvalue part of the source atomic expression.
11285   Expr *getX() const { return X; }
11286   /// Return the 'expr' rvalue part of the source atomic expression.
11287   Expr *getExpr() const { return E; }
11288   /// Return the update expression used in calculation of the updated
11289   /// value. Always has form 'OpaqueValueExpr(x) binop OpaqueValueExpr(expr)' or
11290   /// 'OpaqueValueExpr(expr) binop OpaqueValueExpr(x)'.
11291   Expr *getUpdateExpr() const { return UpdateExpr; }
11292   /// Return true if 'x' is LHS in RHS part of full update expression,
11293   /// false otherwise.
11294   bool isXLHSInRHSPart() const { return IsXLHSInRHSPart; }
11295 
11296   /// true if the source expression is a postfix unary operation, false
11297   /// if it is a prefix unary operation.
11298   bool isPostfixUpdate() const { return IsPostfixUpdate; }
11299 
11300 private:
11301   bool checkBinaryOperation(BinaryOperator *AtomicBinOp, unsigned DiagId = 0,
11302                             unsigned NoteId = 0);
11303 };
11304 
11305 bool OpenMPAtomicUpdateChecker::checkBinaryOperation(
11306     BinaryOperator *AtomicBinOp, unsigned DiagId, unsigned NoteId) {
11307   ExprAnalysisErrorCode ErrorFound = NoError;
11308   SourceLocation ErrorLoc, NoteLoc;
11309   SourceRange ErrorRange, NoteRange;
11310   // Allowed constructs are:
11311   //  x = x binop expr;
11312   //  x = expr binop x;
11313   if (AtomicBinOp->getOpcode() == BO_Assign) {
11314     X = AtomicBinOp->getLHS();
11315     if (const auto *AtomicInnerBinOp = dyn_cast<BinaryOperator>(
11316             AtomicBinOp->getRHS()->IgnoreParenImpCasts())) {
11317       if (AtomicInnerBinOp->isMultiplicativeOp() ||
11318           AtomicInnerBinOp->isAdditiveOp() || AtomicInnerBinOp->isShiftOp() ||
11319           AtomicInnerBinOp->isBitwiseOp()) {
11320         Op = AtomicInnerBinOp->getOpcode();
11321         OpLoc = AtomicInnerBinOp->getOperatorLoc();
11322         Expr *LHS = AtomicInnerBinOp->getLHS();
11323         Expr *RHS = AtomicInnerBinOp->getRHS();
11324         llvm::FoldingSetNodeID XId, LHSId, RHSId;
11325         X->IgnoreParenImpCasts()->Profile(XId, SemaRef.getASTContext(),
11326                                           /*Canonical=*/true);
11327         LHS->IgnoreParenImpCasts()->Profile(LHSId, SemaRef.getASTContext(),
11328                                             /*Canonical=*/true);
11329         RHS->IgnoreParenImpCasts()->Profile(RHSId, SemaRef.getASTContext(),
11330                                             /*Canonical=*/true);
11331         if (XId == LHSId) {
11332           E = RHS;
11333           IsXLHSInRHSPart = true;
11334         } else if (XId == RHSId) {
11335           E = LHS;
11336           IsXLHSInRHSPart = false;
11337         } else {
11338           ErrorLoc = AtomicInnerBinOp->getExprLoc();
11339           ErrorRange = AtomicInnerBinOp->getSourceRange();
11340           NoteLoc = X->getExprLoc();
11341           NoteRange = X->getSourceRange();
11342           ErrorFound = NotAnUpdateExpression;
11343         }
11344       } else {
11345         ErrorLoc = AtomicInnerBinOp->getExprLoc();
11346         ErrorRange = AtomicInnerBinOp->getSourceRange();
11347         NoteLoc = AtomicInnerBinOp->getOperatorLoc();
11348         NoteRange = SourceRange(NoteLoc, NoteLoc);
11349         ErrorFound = NotABinaryOperator;
11350       }
11351     } else {
11352       NoteLoc = ErrorLoc = AtomicBinOp->getRHS()->getExprLoc();
11353       NoteRange = ErrorRange = AtomicBinOp->getRHS()->getSourceRange();
11354       ErrorFound = NotABinaryExpression;
11355     }
11356   } else {
11357     ErrorLoc = AtomicBinOp->getExprLoc();
11358     ErrorRange = AtomicBinOp->getSourceRange();
11359     NoteLoc = AtomicBinOp->getOperatorLoc();
11360     NoteRange = SourceRange(NoteLoc, NoteLoc);
11361     ErrorFound = NotAnAssignmentOp;
11362   }
11363   if (ErrorFound != NoError && DiagId != 0 && NoteId != 0) {
11364     SemaRef.Diag(ErrorLoc, DiagId) << ErrorRange;
11365     SemaRef.Diag(NoteLoc, NoteId) << ErrorFound << NoteRange;
11366     return true;
11367   }
11368   if (SemaRef.CurContext->isDependentContext())
11369     E = X = UpdateExpr = nullptr;
11370   return ErrorFound != NoError;
11371 }
11372 
11373 bool OpenMPAtomicUpdateChecker::checkStatement(Stmt *S, unsigned DiagId,
11374                                                unsigned NoteId) {
11375   ExprAnalysisErrorCode ErrorFound = NoError;
11376   SourceLocation ErrorLoc, NoteLoc;
11377   SourceRange ErrorRange, NoteRange;
11378   // Allowed constructs are:
11379   //  x++;
11380   //  x--;
11381   //  ++x;
11382   //  --x;
11383   //  x binop= expr;
11384   //  x = x binop expr;
11385   //  x = expr binop x;
11386   if (auto *AtomicBody = dyn_cast<Expr>(S)) {
11387     AtomicBody = AtomicBody->IgnoreParenImpCasts();
11388     if (AtomicBody->getType()->isScalarType() ||
11389         AtomicBody->isInstantiationDependent()) {
11390       if (const auto *AtomicCompAssignOp = dyn_cast<CompoundAssignOperator>(
11391               AtomicBody->IgnoreParenImpCasts())) {
11392         // Check for Compound Assignment Operation
11393         Op = BinaryOperator::getOpForCompoundAssignment(
11394             AtomicCompAssignOp->getOpcode());
11395         OpLoc = AtomicCompAssignOp->getOperatorLoc();
11396         E = AtomicCompAssignOp->getRHS();
11397         X = AtomicCompAssignOp->getLHS()->IgnoreParens();
11398         IsXLHSInRHSPart = true;
11399       } else if (auto *AtomicBinOp = dyn_cast<BinaryOperator>(
11400                      AtomicBody->IgnoreParenImpCasts())) {
11401         // Check for Binary Operation
11402         if (checkBinaryOperation(AtomicBinOp, DiagId, NoteId))
11403           return true;
11404       } else if (const auto *AtomicUnaryOp = dyn_cast<UnaryOperator>(
11405                      AtomicBody->IgnoreParenImpCasts())) {
11406         // Check for Unary Operation
11407         if (AtomicUnaryOp->isIncrementDecrementOp()) {
11408           IsPostfixUpdate = AtomicUnaryOp->isPostfix();
11409           Op = AtomicUnaryOp->isIncrementOp() ? BO_Add : BO_Sub;
11410           OpLoc = AtomicUnaryOp->getOperatorLoc();
11411           X = AtomicUnaryOp->getSubExpr()->IgnoreParens();
11412           E = SemaRef.ActOnIntegerConstant(OpLoc, /*uint64_t Val=*/1).get();
11413           IsXLHSInRHSPart = true;
11414         } else {
11415           ErrorFound = NotAnUnaryIncDecExpression;
11416           ErrorLoc = AtomicUnaryOp->getExprLoc();
11417           ErrorRange = AtomicUnaryOp->getSourceRange();
11418           NoteLoc = AtomicUnaryOp->getOperatorLoc();
11419           NoteRange = SourceRange(NoteLoc, NoteLoc);
11420         }
11421       } else if (!AtomicBody->isInstantiationDependent()) {
11422         ErrorFound = NotABinaryOrUnaryExpression;
11423         NoteLoc = ErrorLoc = AtomicBody->getExprLoc();
11424         NoteRange = ErrorRange = AtomicBody->getSourceRange();
11425       }
11426     } else {
11427       ErrorFound = NotAScalarType;
11428       NoteLoc = ErrorLoc = AtomicBody->getBeginLoc();
11429       NoteRange = ErrorRange = SourceRange(NoteLoc, NoteLoc);
11430     }
11431   } else {
11432     ErrorFound = NotAnExpression;
11433     NoteLoc = ErrorLoc = S->getBeginLoc();
11434     NoteRange = ErrorRange = SourceRange(NoteLoc, NoteLoc);
11435   }
11436   if (ErrorFound != NoError && DiagId != 0 && NoteId != 0) {
11437     SemaRef.Diag(ErrorLoc, DiagId) << ErrorRange;
11438     SemaRef.Diag(NoteLoc, NoteId) << ErrorFound << NoteRange;
11439     return true;
11440   }
11441   if (SemaRef.CurContext->isDependentContext())
11442     E = X = UpdateExpr = nullptr;
11443   if (ErrorFound == NoError && E && X) {
11444     // Build an update expression of form 'OpaqueValueExpr(x) binop
11445     // OpaqueValueExpr(expr)' or 'OpaqueValueExpr(expr) binop
11446     // OpaqueValueExpr(x)' and then cast it to the type of the 'x' expression.
11447     auto *OVEX = new (SemaRef.getASTContext())
11448         OpaqueValueExpr(X->getExprLoc(), X->getType(), VK_PRValue);
11449     auto *OVEExpr = new (SemaRef.getASTContext())
11450         OpaqueValueExpr(E->getExprLoc(), E->getType(), VK_PRValue);
11451     ExprResult Update =
11452         SemaRef.CreateBuiltinBinOp(OpLoc, Op, IsXLHSInRHSPart ? OVEX : OVEExpr,
11453                                    IsXLHSInRHSPart ? OVEExpr : OVEX);
11454     if (Update.isInvalid())
11455       return true;
11456     Update = SemaRef.PerformImplicitConversion(Update.get(), X->getType(),
11457                                                Sema::AA_Casting);
11458     if (Update.isInvalid())
11459       return true;
11460     UpdateExpr = Update.get();
11461   }
11462   return ErrorFound != NoError;
11463 }
11464 
11465 /// Get the node id of the fixed point of an expression \a S.
11466 llvm::FoldingSetNodeID getNodeId(ASTContext &Context, const Expr *S) {
11467   llvm::FoldingSetNodeID Id;
11468   S->IgnoreParenImpCasts()->Profile(Id, Context, true);
11469   return Id;
11470 }
11471 
11472 /// Check if two expressions are same.
11473 bool checkIfTwoExprsAreSame(ASTContext &Context, const Expr *LHS,
11474                             const Expr *RHS) {
11475   return getNodeId(Context, LHS) == getNodeId(Context, RHS);
11476 }
11477 
11478 class OpenMPAtomicCompareChecker {
11479 public:
11480   /// All kinds of errors that can occur in `atomic compare`
11481   enum ErrorTy {
11482     /// Empty compound statement.
11483     NoStmt = 0,
11484     /// More than one statement in a compound statement.
11485     MoreThanOneStmt,
11486     /// Not an assignment binary operator.
11487     NotAnAssignment,
11488     /// Not a conditional operator.
11489     NotCondOp,
11490     /// Wrong false expr. According to the spec, 'x' should be at the false
11491     /// expression of a conditional expression.
11492     WrongFalseExpr,
11493     /// The condition of a conditional expression is not a binary operator.
11494     NotABinaryOp,
11495     /// Invalid binary operator (not <, >, or ==).
11496     InvalidBinaryOp,
11497     /// Invalid comparison (not x == e, e == x, x ordop expr, or expr ordop x).
11498     InvalidComparison,
11499     /// X is not a lvalue.
11500     XNotLValue,
11501     /// Not a scalar.
11502     NotScalar,
11503     /// Not an integer.
11504     NotInteger,
11505     /// 'else' statement is not expected.
11506     UnexpectedElse,
11507     /// Not an equality operator.
11508     NotEQ,
11509     /// Invalid assignment (not v == x).
11510     InvalidAssignment,
11511     /// Not if statement
11512     NotIfStmt,
11513     /// More than two statements in a compund statement.
11514     MoreThanTwoStmts,
11515     /// Not a compound statement.
11516     NotCompoundStmt,
11517     /// No else statement.
11518     NoElse,
11519     /// Not 'if (r)'.
11520     InvalidCondition,
11521     /// No error.
11522     NoError,
11523   };
11524 
11525   struct ErrorInfoTy {
11526     ErrorTy Error;
11527     SourceLocation ErrorLoc;
11528     SourceRange ErrorRange;
11529     SourceLocation NoteLoc;
11530     SourceRange NoteRange;
11531   };
11532 
11533   OpenMPAtomicCompareChecker(Sema &S) : ContextRef(S.getASTContext()) {}
11534 
11535   /// Check if statement \a S is valid for <tt>atomic compare</tt>.
11536   bool checkStmt(Stmt *S, ErrorInfoTy &ErrorInfo);
11537 
11538   Expr *getX() const { return X; }
11539   Expr *getE() const { return E; }
11540   Expr *getD() const { return D; }
11541   Expr *getCond() const { return C; }
11542   bool isXBinopExpr() const { return IsXBinopExpr; }
11543 
11544 protected:
11545   /// Reference to ASTContext
11546   ASTContext &ContextRef;
11547   /// 'x' lvalue part of the source atomic expression.
11548   Expr *X = nullptr;
11549   /// 'expr' or 'e' rvalue part of the source atomic expression.
11550   Expr *E = nullptr;
11551   /// 'd' rvalue part of the source atomic expression.
11552   Expr *D = nullptr;
11553   /// 'cond' part of the source atomic expression. It is in one of the following
11554   /// forms:
11555   /// expr ordop x
11556   /// x ordop expr
11557   /// x == e
11558   /// e == x
11559   Expr *C = nullptr;
11560   /// True if the cond expr is in the form of 'x ordop expr'.
11561   bool IsXBinopExpr = true;
11562 
11563   /// Check if it is a valid conditional update statement (cond-update-stmt).
11564   bool checkCondUpdateStmt(IfStmt *S, ErrorInfoTy &ErrorInfo);
11565 
11566   /// Check if it is a valid conditional expression statement (cond-expr-stmt).
11567   bool checkCondExprStmt(Stmt *S, ErrorInfoTy &ErrorInfo);
11568 
11569   /// Check if all captured values have right type.
11570   bool checkType(ErrorInfoTy &ErrorInfo) const;
11571 
11572   static bool CheckValue(const Expr *E, ErrorInfoTy &ErrorInfo,
11573                          bool ShouldBeLValue, bool ShouldBeInteger = false) {
11574     if (ShouldBeLValue && !E->isLValue()) {
11575       ErrorInfo.Error = ErrorTy::XNotLValue;
11576       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = E->getExprLoc();
11577       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = E->getSourceRange();
11578       return false;
11579     }
11580 
11581     if (!E->isInstantiationDependent()) {
11582       QualType QTy = E->getType();
11583       if (!QTy->isScalarType()) {
11584         ErrorInfo.Error = ErrorTy::NotScalar;
11585         ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = E->getExprLoc();
11586         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = E->getSourceRange();
11587         return false;
11588       }
11589       if (ShouldBeInteger && !QTy->isIntegerType()) {
11590         ErrorInfo.Error = ErrorTy::NotInteger;
11591         ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = E->getExprLoc();
11592         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = E->getSourceRange();
11593         return false;
11594       }
11595     }
11596 
11597     return true;
11598   }
11599 };
11600 
11601 bool OpenMPAtomicCompareChecker::checkCondUpdateStmt(IfStmt *S,
11602                                                      ErrorInfoTy &ErrorInfo) {
11603   auto *Then = S->getThen();
11604   if (auto *CS = dyn_cast<CompoundStmt>(Then)) {
11605     if (CS->body_empty()) {
11606       ErrorInfo.Error = ErrorTy::NoStmt;
11607       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11608       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
11609       return false;
11610     }
11611     if (CS->size() > 1) {
11612       ErrorInfo.Error = ErrorTy::MoreThanOneStmt;
11613       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11614       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getSourceRange();
11615       return false;
11616     }
11617     Then = CS->body_front();
11618   }
11619 
11620   auto *BO = dyn_cast<BinaryOperator>(Then);
11621   if (!BO) {
11622     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11623     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Then->getBeginLoc();
11624     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Then->getSourceRange();
11625     return false;
11626   }
11627   if (BO->getOpcode() != BO_Assign) {
11628     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11629     ErrorInfo.ErrorLoc = BO->getExprLoc();
11630     ErrorInfo.NoteLoc = BO->getOperatorLoc();
11631     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getSourceRange();
11632     return false;
11633   }
11634 
11635   X = BO->getLHS();
11636 
11637   auto *Cond = dyn_cast<BinaryOperator>(S->getCond());
11638   if (!Cond) {
11639     ErrorInfo.Error = ErrorTy::NotABinaryOp;
11640     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S->getCond()->getExprLoc();
11641     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getCond()->getSourceRange();
11642     return false;
11643   }
11644 
11645   switch (Cond->getOpcode()) {
11646   case BO_EQ: {
11647     C = Cond;
11648     D = BO->getRHS();
11649     if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getLHS())) {
11650       E = Cond->getRHS();
11651     } else if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getRHS())) {
11652       E = Cond->getLHS();
11653     } else {
11654       ErrorInfo.Error = ErrorTy::InvalidComparison;
11655       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11656       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11657       return false;
11658     }
11659     break;
11660   }
11661   case BO_LT:
11662   case BO_GT: {
11663     E = BO->getRHS();
11664     if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getLHS()) &&
11665         checkIfTwoExprsAreSame(ContextRef, E, Cond->getRHS())) {
11666       C = Cond;
11667     } else if (checkIfTwoExprsAreSame(ContextRef, E, Cond->getLHS()) &&
11668                checkIfTwoExprsAreSame(ContextRef, X, Cond->getRHS())) {
11669       C = Cond;
11670       IsXBinopExpr = false;
11671     } else {
11672       ErrorInfo.Error = ErrorTy::InvalidComparison;
11673       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11674       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11675       return false;
11676     }
11677     break;
11678   }
11679   default:
11680     ErrorInfo.Error = ErrorTy::InvalidBinaryOp;
11681     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11682     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11683     return false;
11684   }
11685 
11686   if (S->getElse()) {
11687     ErrorInfo.Error = ErrorTy::UnexpectedElse;
11688     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S->getElse()->getBeginLoc();
11689     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getElse()->getSourceRange();
11690     return false;
11691   }
11692 
11693   return true;
11694 }
11695 
11696 bool OpenMPAtomicCompareChecker::checkCondExprStmt(Stmt *S,
11697                                                    ErrorInfoTy &ErrorInfo) {
11698   auto *BO = dyn_cast<BinaryOperator>(S);
11699   if (!BO) {
11700     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11701     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S->getBeginLoc();
11702     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getSourceRange();
11703     return false;
11704   }
11705   if (BO->getOpcode() != BO_Assign) {
11706     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11707     ErrorInfo.ErrorLoc = BO->getExprLoc();
11708     ErrorInfo.NoteLoc = BO->getOperatorLoc();
11709     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getSourceRange();
11710     return false;
11711   }
11712 
11713   X = BO->getLHS();
11714 
11715   auto *CO = dyn_cast<ConditionalOperator>(BO->getRHS()->IgnoreParenImpCasts());
11716   if (!CO) {
11717     ErrorInfo.Error = ErrorTy::NotCondOp;
11718     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = BO->getRHS()->getExprLoc();
11719     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getRHS()->getSourceRange();
11720     return false;
11721   }
11722 
11723   if (!checkIfTwoExprsAreSame(ContextRef, X, CO->getFalseExpr())) {
11724     ErrorInfo.Error = ErrorTy::WrongFalseExpr;
11725     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CO->getFalseExpr()->getExprLoc();
11726     ErrorInfo.ErrorRange = ErrorInfo.NoteRange =
11727         CO->getFalseExpr()->getSourceRange();
11728     return false;
11729   }
11730 
11731   auto *Cond = dyn_cast<BinaryOperator>(CO->getCond());
11732   if (!Cond) {
11733     ErrorInfo.Error = ErrorTy::NotABinaryOp;
11734     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CO->getCond()->getExprLoc();
11735     ErrorInfo.ErrorRange = ErrorInfo.NoteRange =
11736         CO->getCond()->getSourceRange();
11737     return false;
11738   }
11739 
11740   switch (Cond->getOpcode()) {
11741   case BO_EQ: {
11742     C = Cond;
11743     D = CO->getTrueExpr();
11744     if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getLHS())) {
11745       E = Cond->getRHS();
11746     } else if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getRHS())) {
11747       E = Cond->getLHS();
11748     } else {
11749       ErrorInfo.Error = ErrorTy::InvalidComparison;
11750       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11751       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11752       return false;
11753     }
11754     break;
11755   }
11756   case BO_LT:
11757   case BO_GT: {
11758     E = CO->getTrueExpr();
11759     if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getLHS()) &&
11760         checkIfTwoExprsAreSame(ContextRef, E, Cond->getRHS())) {
11761       C = Cond;
11762     } else if (checkIfTwoExprsAreSame(ContextRef, E, Cond->getLHS()) &&
11763                checkIfTwoExprsAreSame(ContextRef, X, Cond->getRHS())) {
11764       C = Cond;
11765       IsXBinopExpr = false;
11766     } else {
11767       ErrorInfo.Error = ErrorTy::InvalidComparison;
11768       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11769       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11770       return false;
11771     }
11772     break;
11773   }
11774   default:
11775     ErrorInfo.Error = ErrorTy::InvalidBinaryOp;
11776     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11777     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11778     return false;
11779   }
11780 
11781   return true;
11782 }
11783 
11784 bool OpenMPAtomicCompareChecker::checkType(ErrorInfoTy &ErrorInfo) const {
11785   // 'x' and 'e' cannot be nullptr
11786   assert(X && E && "X and E cannot be nullptr");
11787 
11788   if (!CheckValue(X, ErrorInfo, true))
11789     return false;
11790 
11791   if (!CheckValue(E, ErrorInfo, false))
11792     return false;
11793 
11794   if (D && !CheckValue(D, ErrorInfo, false))
11795     return false;
11796 
11797   return true;
11798 }
11799 
11800 bool OpenMPAtomicCompareChecker::checkStmt(
11801     Stmt *S, OpenMPAtomicCompareChecker::ErrorInfoTy &ErrorInfo) {
11802   auto *CS = dyn_cast<CompoundStmt>(S);
11803   if (CS) {
11804     if (CS->body_empty()) {
11805       ErrorInfo.Error = ErrorTy::NoStmt;
11806       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11807       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
11808       return false;
11809     }
11810 
11811     if (CS->size() != 1) {
11812       ErrorInfo.Error = ErrorTy::MoreThanOneStmt;
11813       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11814       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
11815       return false;
11816     }
11817     S = CS->body_front();
11818   }
11819 
11820   auto Res = false;
11821 
11822   if (auto *IS = dyn_cast<IfStmt>(S)) {
11823     // Check if the statement is in one of the following forms
11824     // (cond-update-stmt):
11825     // if (expr ordop x) { x = expr; }
11826     // if (x ordop expr) { x = expr; }
11827     // if (x == e) { x = d; }
11828     Res = checkCondUpdateStmt(IS, ErrorInfo);
11829   } else {
11830     // Check if the statement is in one of the following forms (cond-expr-stmt):
11831     // x = expr ordop x ? expr : x;
11832     // x = x ordop expr ? expr : x;
11833     // x = x == e ? d : x;
11834     Res = checkCondExprStmt(S, ErrorInfo);
11835   }
11836 
11837   if (!Res)
11838     return false;
11839 
11840   return checkType(ErrorInfo);
11841 }
11842 
11843 class OpenMPAtomicCompareCaptureChecker final
11844     : public OpenMPAtomicCompareChecker {
11845 public:
11846   OpenMPAtomicCompareCaptureChecker(Sema &S) : OpenMPAtomicCompareChecker(S) {}
11847 
11848   Expr *getV() const { return V; }
11849   Expr *getR() const { return R; }
11850   bool isFailOnly() const { return IsFailOnly; }
11851   bool isPostfixUpdate() const { return IsPostfixUpdate; }
11852 
11853   /// Check if statement \a S is valid for <tt>atomic compare capture</tt>.
11854   bool checkStmt(Stmt *S, ErrorInfoTy &ErrorInfo);
11855 
11856 private:
11857   bool checkType(ErrorInfoTy &ErrorInfo);
11858 
11859   // NOTE: Form 3, 4, 5 in the following comments mean the 3rd, 4th, and 5th
11860   // form of 'conditional-update-capture-atomic' structured block on the v5.2
11861   // spec p.p. 82:
11862   // (1) { v = x; cond-update-stmt }
11863   // (2) { cond-update-stmt v = x; }
11864   // (3) if(x == e) { x = d; } else { v = x; }
11865   // (4) { r = x == e; if(r) { x = d; } }
11866   // (5) { r = x == e; if(r) { x = d; } else { v = x; } }
11867 
11868   /// Check if it is valid 'if(x == e) { x = d; } else { v = x; }' (form 3)
11869   bool checkForm3(IfStmt *S, ErrorInfoTy &ErrorInfo);
11870 
11871   /// Check if it is valid '{ r = x == e; if(r) { x = d; } }',
11872   /// or '{ r = x == e; if(r) { x = d; } else { v = x; } }' (form 4 and 5)
11873   bool checkForm45(Stmt *S, ErrorInfoTy &ErrorInfo);
11874 
11875   /// 'v' lvalue part of the source atomic expression.
11876   Expr *V = nullptr;
11877   /// 'r' lvalue part of the source atomic expression.
11878   Expr *R = nullptr;
11879   /// If 'v' is only updated when the comparison fails.
11880   bool IsFailOnly = false;
11881   /// If original value of 'x' must be stored in 'v', not an updated one.
11882   bool IsPostfixUpdate = false;
11883 };
11884 
11885 bool OpenMPAtomicCompareCaptureChecker::checkType(ErrorInfoTy &ErrorInfo) {
11886   if (!OpenMPAtomicCompareChecker::checkType(ErrorInfo))
11887     return false;
11888 
11889   if (V && !CheckValue(V, ErrorInfo, true))
11890     return false;
11891 
11892   if (R && !CheckValue(R, ErrorInfo, true, true))
11893     return false;
11894 
11895   return true;
11896 }
11897 
11898 bool OpenMPAtomicCompareCaptureChecker::checkForm3(IfStmt *S,
11899                                                    ErrorInfoTy &ErrorInfo) {
11900   IsFailOnly = true;
11901 
11902   auto *Then = S->getThen();
11903   if (auto *CS = dyn_cast<CompoundStmt>(Then)) {
11904     if (CS->body_empty()) {
11905       ErrorInfo.Error = ErrorTy::NoStmt;
11906       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11907       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
11908       return false;
11909     }
11910     if (CS->size() > 1) {
11911       ErrorInfo.Error = ErrorTy::MoreThanOneStmt;
11912       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11913       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
11914       return false;
11915     }
11916     Then = CS->body_front();
11917   }
11918 
11919   auto *BO = dyn_cast<BinaryOperator>(Then);
11920   if (!BO) {
11921     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11922     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Then->getBeginLoc();
11923     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Then->getSourceRange();
11924     return false;
11925   }
11926   if (BO->getOpcode() != BO_Assign) {
11927     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11928     ErrorInfo.ErrorLoc = BO->getExprLoc();
11929     ErrorInfo.NoteLoc = BO->getOperatorLoc();
11930     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getSourceRange();
11931     return false;
11932   }
11933 
11934   X = BO->getLHS();
11935   D = BO->getRHS();
11936 
11937   auto *Cond = dyn_cast<BinaryOperator>(S->getCond());
11938   if (!Cond) {
11939     ErrorInfo.Error = ErrorTy::NotABinaryOp;
11940     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S->getCond()->getExprLoc();
11941     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getCond()->getSourceRange();
11942     return false;
11943   }
11944   if (Cond->getOpcode() != BO_EQ) {
11945     ErrorInfo.Error = ErrorTy::NotEQ;
11946     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11947     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11948     return false;
11949   }
11950 
11951   if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getLHS())) {
11952     E = Cond->getRHS();
11953   } else if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getRHS())) {
11954     E = Cond->getLHS();
11955   } else {
11956     ErrorInfo.Error = ErrorTy::InvalidComparison;
11957     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11958     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11959     return false;
11960   }
11961 
11962   C = Cond;
11963 
11964   if (!S->getElse()) {
11965     ErrorInfo.Error = ErrorTy::NoElse;
11966     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S->getBeginLoc();
11967     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getSourceRange();
11968     return false;
11969   }
11970 
11971   auto *Else = S->getElse();
11972   if (auto *CS = dyn_cast<CompoundStmt>(Else)) {
11973     if (CS->body_empty()) {
11974       ErrorInfo.Error = ErrorTy::NoStmt;
11975       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11976       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
11977       return false;
11978     }
11979     if (CS->size() > 1) {
11980       ErrorInfo.Error = ErrorTy::MoreThanOneStmt;
11981       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11982       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getSourceRange();
11983       return false;
11984     }
11985     Else = CS->body_front();
11986   }
11987 
11988   auto *ElseBO = dyn_cast<BinaryOperator>(Else);
11989   if (!ElseBO) {
11990     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11991     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Else->getBeginLoc();
11992     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Else->getSourceRange();
11993     return false;
11994   }
11995   if (ElseBO->getOpcode() != BO_Assign) {
11996     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11997     ErrorInfo.ErrorLoc = ElseBO->getExprLoc();
11998     ErrorInfo.NoteLoc = ElseBO->getOperatorLoc();
11999     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ElseBO->getSourceRange();
12000     return false;
12001   }
12002 
12003   if (!checkIfTwoExprsAreSame(ContextRef, X, ElseBO->getRHS())) {
12004     ErrorInfo.Error = ErrorTy::InvalidAssignment;
12005     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = ElseBO->getRHS()->getExprLoc();
12006     ErrorInfo.ErrorRange = ErrorInfo.NoteRange =
12007         ElseBO->getRHS()->getSourceRange();
12008     return false;
12009   }
12010 
12011   V = ElseBO->getLHS();
12012 
12013   return checkType(ErrorInfo);
12014 }
12015 
12016 bool OpenMPAtomicCompareCaptureChecker::checkForm45(Stmt *S,
12017                                                     ErrorInfoTy &ErrorInfo) {
12018   // We don't check here as they should be already done before call this
12019   // function.
12020   auto *CS = cast<CompoundStmt>(S);
12021   assert(CS->size() == 2 && "CompoundStmt size is not expected");
12022   auto *S1 = cast<BinaryOperator>(CS->body_front());
12023   auto *S2 = cast<IfStmt>(CS->body_back());
12024   assert(S1->getOpcode() == BO_Assign && "unexpected binary operator");
12025 
12026   if (!checkIfTwoExprsAreSame(ContextRef, S1->getLHS(), S2->getCond())) {
12027     ErrorInfo.Error = ErrorTy::InvalidCondition;
12028     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S2->getCond()->getExprLoc();
12029     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S1->getLHS()->getSourceRange();
12030     return false;
12031   }
12032 
12033   R = S1->getLHS();
12034 
12035   auto *Then = S2->getThen();
12036   if (auto *ThenCS = dyn_cast<CompoundStmt>(Then)) {
12037     if (ThenCS->body_empty()) {
12038       ErrorInfo.Error = ErrorTy::NoStmt;
12039       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = ThenCS->getBeginLoc();
12040       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ThenCS->getSourceRange();
12041       return false;
12042     }
12043     if (ThenCS->size() > 1) {
12044       ErrorInfo.Error = ErrorTy::MoreThanOneStmt;
12045       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = ThenCS->getBeginLoc();
12046       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ThenCS->getSourceRange();
12047       return false;
12048     }
12049     Then = ThenCS->body_front();
12050   }
12051 
12052   auto *ThenBO = dyn_cast<BinaryOperator>(Then);
12053   if (!ThenBO) {
12054     ErrorInfo.Error = ErrorTy::NotAnAssignment;
12055     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S2->getBeginLoc();
12056     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S2->getSourceRange();
12057     return false;
12058   }
12059   if (ThenBO->getOpcode() != BO_Assign) {
12060     ErrorInfo.Error = ErrorTy::NotAnAssignment;
12061     ErrorInfo.ErrorLoc = ThenBO->getExprLoc();
12062     ErrorInfo.NoteLoc = ThenBO->getOperatorLoc();
12063     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ThenBO->getSourceRange();
12064     return false;
12065   }
12066 
12067   X = ThenBO->getLHS();
12068   D = ThenBO->getRHS();
12069 
12070   auto *BO = cast<BinaryOperator>(S1->getRHS()->IgnoreImpCasts());
12071   if (BO->getOpcode() != BO_EQ) {
12072     ErrorInfo.Error = ErrorTy::NotEQ;
12073     ErrorInfo.ErrorLoc = BO->getExprLoc();
12074     ErrorInfo.NoteLoc = BO->getOperatorLoc();
12075     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getSourceRange();
12076     return false;
12077   }
12078 
12079   C = BO;
12080 
12081   if (checkIfTwoExprsAreSame(ContextRef, X, BO->getLHS())) {
12082     E = BO->getRHS();
12083   } else if (checkIfTwoExprsAreSame(ContextRef, X, BO->getRHS())) {
12084     E = BO->getLHS();
12085   } else {
12086     ErrorInfo.Error = ErrorTy::InvalidComparison;
12087     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = BO->getExprLoc();
12088     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getSourceRange();
12089     return false;
12090   }
12091 
12092   if (S2->getElse()) {
12093     IsFailOnly = true;
12094 
12095     auto *Else = S2->getElse();
12096     if (auto *ElseCS = dyn_cast<CompoundStmt>(Else)) {
12097       if (ElseCS->body_empty()) {
12098         ErrorInfo.Error = ErrorTy::NoStmt;
12099         ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = ElseCS->getBeginLoc();
12100         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ElseCS->getSourceRange();
12101         return false;
12102       }
12103       if (ElseCS->size() > 1) {
12104         ErrorInfo.Error = ErrorTy::MoreThanOneStmt;
12105         ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = ElseCS->getBeginLoc();
12106         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ElseCS->getSourceRange();
12107         return false;
12108       }
12109       Else = ElseCS->body_front();
12110     }
12111 
12112     auto *ElseBO = dyn_cast<BinaryOperator>(Else);
12113     if (!ElseBO) {
12114       ErrorInfo.Error = ErrorTy::NotAnAssignment;
12115       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Else->getBeginLoc();
12116       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Else->getSourceRange();
12117       return false;
12118     }
12119     if (ElseBO->getOpcode() != BO_Assign) {
12120       ErrorInfo.Error = ErrorTy::NotAnAssignment;
12121       ErrorInfo.ErrorLoc = ElseBO->getExprLoc();
12122       ErrorInfo.NoteLoc = ElseBO->getOperatorLoc();
12123       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ElseBO->getSourceRange();
12124       return false;
12125     }
12126     if (!checkIfTwoExprsAreSame(ContextRef, X, ElseBO->getRHS())) {
12127       ErrorInfo.Error = ErrorTy::InvalidAssignment;
12128       ErrorInfo.ErrorLoc = ElseBO->getRHS()->getExprLoc();
12129       ErrorInfo.NoteLoc = X->getExprLoc();
12130       ErrorInfo.ErrorRange = ElseBO->getRHS()->getSourceRange();
12131       ErrorInfo.NoteRange = X->getSourceRange();
12132       return false;
12133     }
12134 
12135     V = ElseBO->getLHS();
12136   }
12137 
12138   return checkType(ErrorInfo);
12139 }
12140 
12141 bool OpenMPAtomicCompareCaptureChecker::checkStmt(Stmt *S,
12142                                                   ErrorInfoTy &ErrorInfo) {
12143   // if(x == e) { x = d; } else { v = x; }
12144   if (auto *IS = dyn_cast<IfStmt>(S))
12145     return checkForm3(IS, ErrorInfo);
12146 
12147   auto *CS = dyn_cast<CompoundStmt>(S);
12148   if (!CS) {
12149     ErrorInfo.Error = ErrorTy::NotCompoundStmt;
12150     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S->getBeginLoc();
12151     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getSourceRange();
12152     return false;
12153   }
12154   if (CS->body_empty()) {
12155     ErrorInfo.Error = ErrorTy::NoStmt;
12156     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
12157     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
12158     return false;
12159   }
12160 
12161   // { if(x == e) { x = d; } else { v = x; } }
12162   if (CS->size() == 1) {
12163     auto *IS = dyn_cast<IfStmt>(CS->body_front());
12164     if (!IS) {
12165       ErrorInfo.Error = ErrorTy::NotIfStmt;
12166       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->body_front()->getBeginLoc();
12167       ErrorInfo.ErrorRange = ErrorInfo.NoteRange =
12168           CS->body_front()->getSourceRange();
12169       return false;
12170     }
12171 
12172     return checkForm3(IS, ErrorInfo);
12173   } else if (CS->size() == 2) {
12174     auto *S1 = CS->body_front();
12175     auto *S2 = CS->body_back();
12176 
12177     Stmt *UpdateStmt = nullptr;
12178     Stmt *CondUpdateStmt = nullptr;
12179 
12180     if (auto *BO = dyn_cast<BinaryOperator>(S1)) {
12181       // { v = x; cond-update-stmt } or form 45.
12182       UpdateStmt = S1;
12183       CondUpdateStmt = S2;
12184       // Check if form 45.
12185       if (isa<BinaryOperator>(BO->getRHS()->IgnoreImpCasts()) &&
12186           isa<IfStmt>(S2))
12187         return checkForm45(CS, ErrorInfo);
12188       // It cannot be set before we the check for form45.
12189       IsPostfixUpdate = true;
12190     } else {
12191       // { cond-update-stmt v = x; }
12192       UpdateStmt = S2;
12193       CondUpdateStmt = S1;
12194     }
12195 
12196     auto CheckCondUpdateStmt = [this, &ErrorInfo](Stmt *CUS) {
12197       auto *IS = dyn_cast<IfStmt>(CUS);
12198       if (!IS) {
12199         ErrorInfo.Error = ErrorTy::NotIfStmt;
12200         ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CUS->getBeginLoc();
12201         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CUS->getSourceRange();
12202         return false;
12203       }
12204 
12205       if (!checkCondUpdateStmt(IS, ErrorInfo))
12206         return false;
12207 
12208       return true;
12209     };
12210 
12211     // CheckUpdateStmt has to be called *after* CheckCondUpdateStmt.
12212     auto CheckUpdateStmt = [this, &ErrorInfo](Stmt *US) {
12213       auto *BO = dyn_cast<BinaryOperator>(US);
12214       if (!BO) {
12215         ErrorInfo.Error = ErrorTy::NotAnAssignment;
12216         ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = US->getBeginLoc();
12217         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = US->getSourceRange();
12218         return false;
12219       }
12220       if (BO->getOpcode() != BO_Assign) {
12221         ErrorInfo.Error = ErrorTy::NotAnAssignment;
12222         ErrorInfo.ErrorLoc = BO->getExprLoc();
12223         ErrorInfo.NoteLoc = BO->getOperatorLoc();
12224         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getSourceRange();
12225         return false;
12226       }
12227       if (!checkIfTwoExprsAreSame(ContextRef, this->X, BO->getRHS())) {
12228         ErrorInfo.Error = ErrorTy::InvalidAssignment;
12229         ErrorInfo.ErrorLoc = BO->getRHS()->getExprLoc();
12230         ErrorInfo.NoteLoc = this->X->getExprLoc();
12231         ErrorInfo.ErrorRange = BO->getRHS()->getSourceRange();
12232         ErrorInfo.NoteRange = this->X->getSourceRange();
12233         return false;
12234       }
12235 
12236       this->V = BO->getLHS();
12237 
12238       return true;
12239     };
12240 
12241     if (!CheckCondUpdateStmt(CondUpdateStmt))
12242       return false;
12243     if (!CheckUpdateStmt(UpdateStmt))
12244       return false;
12245   } else {
12246     ErrorInfo.Error = ErrorTy::MoreThanTwoStmts;
12247     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
12248     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
12249     return false;
12250   }
12251 
12252   return checkType(ErrorInfo);
12253 }
12254 } // namespace
12255 
12256 StmtResult Sema::ActOnOpenMPAtomicDirective(ArrayRef<OMPClause *> Clauses,
12257                                             Stmt *AStmt,
12258                                             SourceLocation StartLoc,
12259                                             SourceLocation EndLoc) {
12260   // Register location of the first atomic directive.
12261   DSAStack->addAtomicDirectiveLoc(StartLoc);
12262   if (!AStmt)
12263     return StmtError();
12264 
12265   // 1.2.2 OpenMP Language Terminology
12266   // Structured block - An executable statement with a single entry at the
12267   // top and a single exit at the bottom.
12268   // The point of exit cannot be a branch out of the structured block.
12269   // longjmp() and throw() must not violate the entry/exit criteria.
12270   OpenMPClauseKind AtomicKind = OMPC_unknown;
12271   SourceLocation AtomicKindLoc;
12272   OpenMPClauseKind MemOrderKind = OMPC_unknown;
12273   SourceLocation MemOrderLoc;
12274   bool MutexClauseEncountered = false;
12275   llvm::SmallSet<OpenMPClauseKind, 2> EncounteredAtomicKinds;
12276   for (const OMPClause *C : Clauses) {
12277     switch (C->getClauseKind()) {
12278     case OMPC_read:
12279     case OMPC_write:
12280     case OMPC_update:
12281       MutexClauseEncountered = true;
12282       LLVM_FALLTHROUGH;
12283     case OMPC_capture:
12284     case OMPC_compare: {
12285       if (AtomicKind != OMPC_unknown && MutexClauseEncountered) {
12286         Diag(C->getBeginLoc(), diag::err_omp_atomic_several_clauses)
12287             << SourceRange(C->getBeginLoc(), C->getEndLoc());
12288         Diag(AtomicKindLoc, diag::note_omp_previous_mem_order_clause)
12289             << getOpenMPClauseName(AtomicKind);
12290       } else {
12291         AtomicKind = C->getClauseKind();
12292         AtomicKindLoc = C->getBeginLoc();
12293         if (!EncounteredAtomicKinds.insert(C->getClauseKind()).second) {
12294           Diag(C->getBeginLoc(), diag::err_omp_atomic_several_clauses)
12295               << SourceRange(C->getBeginLoc(), C->getEndLoc());
12296           Diag(AtomicKindLoc, diag::note_omp_previous_mem_order_clause)
12297               << getOpenMPClauseName(AtomicKind);
12298         }
12299       }
12300       break;
12301     }
12302     case OMPC_seq_cst:
12303     case OMPC_acq_rel:
12304     case OMPC_acquire:
12305     case OMPC_release:
12306     case OMPC_relaxed: {
12307       if (MemOrderKind != OMPC_unknown) {
12308         Diag(C->getBeginLoc(), diag::err_omp_several_mem_order_clauses)
12309             << getOpenMPDirectiveName(OMPD_atomic) << 0
12310             << SourceRange(C->getBeginLoc(), C->getEndLoc());
12311         Diag(MemOrderLoc, diag::note_omp_previous_mem_order_clause)
12312             << getOpenMPClauseName(MemOrderKind);
12313       } else {
12314         MemOrderKind = C->getClauseKind();
12315         MemOrderLoc = C->getBeginLoc();
12316       }
12317       break;
12318     }
12319     // The following clauses are allowed, but we don't need to do anything here.
12320     case OMPC_hint:
12321       break;
12322     default:
12323       llvm_unreachable("unknown clause is encountered");
12324     }
12325   }
12326   bool IsCompareCapture = false;
12327   if (EncounteredAtomicKinds.contains(OMPC_compare) &&
12328       EncounteredAtomicKinds.contains(OMPC_capture)) {
12329     IsCompareCapture = true;
12330     AtomicKind = OMPC_compare;
12331   }
12332   // OpenMP 5.0, 2.17.7 atomic Construct, Restrictions
12333   // If atomic-clause is read then memory-order-clause must not be acq_rel or
12334   // release.
12335   // If atomic-clause is write then memory-order-clause must not be acq_rel or
12336   // acquire.
12337   // If atomic-clause is update or not present then memory-order-clause must not
12338   // be acq_rel or acquire.
12339   if ((AtomicKind == OMPC_read &&
12340        (MemOrderKind == OMPC_acq_rel || MemOrderKind == OMPC_release)) ||
12341       ((AtomicKind == OMPC_write || AtomicKind == OMPC_update ||
12342         AtomicKind == OMPC_unknown) &&
12343        (MemOrderKind == OMPC_acq_rel || MemOrderKind == OMPC_acquire))) {
12344     SourceLocation Loc = AtomicKindLoc;
12345     if (AtomicKind == OMPC_unknown)
12346       Loc = StartLoc;
12347     Diag(Loc, diag::err_omp_atomic_incompatible_mem_order_clause)
12348         << getOpenMPClauseName(AtomicKind)
12349         << (AtomicKind == OMPC_unknown ? 1 : 0)
12350         << getOpenMPClauseName(MemOrderKind);
12351     Diag(MemOrderLoc, diag::note_omp_previous_mem_order_clause)
12352         << getOpenMPClauseName(MemOrderKind);
12353   }
12354 
12355   Stmt *Body = AStmt;
12356   if (auto *EWC = dyn_cast<ExprWithCleanups>(Body))
12357     Body = EWC->getSubExpr();
12358 
12359   Expr *X = nullptr;
12360   Expr *V = nullptr;
12361   Expr *E = nullptr;
12362   Expr *UE = nullptr;
12363   Expr *D = nullptr;
12364   Expr *CE = nullptr;
12365   Expr *R = nullptr;
12366   bool IsXLHSInRHSPart = false;
12367   bool IsPostfixUpdate = false;
12368   bool IsFailOnly = false;
12369   // OpenMP [2.12.6, atomic Construct]
12370   // In the next expressions:
12371   // * x and v (as applicable) are both l-value expressions with scalar type.
12372   // * During the execution of an atomic region, multiple syntactic
12373   // occurrences of x must designate the same storage location.
12374   // * Neither of v and expr (as applicable) may access the storage location
12375   // designated by x.
12376   // * Neither of x and expr (as applicable) may access the storage location
12377   // designated by v.
12378   // * expr is an expression with scalar type.
12379   // * binop is one of +, *, -, /, &, ^, |, <<, or >>.
12380   // * binop, binop=, ++, and -- are not overloaded operators.
12381   // * The expression x binop expr must be numerically equivalent to x binop
12382   // (expr). This requirement is satisfied if the operators in expr have
12383   // precedence greater than binop, or by using parentheses around expr or
12384   // subexpressions of expr.
12385   // * The expression expr binop x must be numerically equivalent to (expr)
12386   // binop x. This requirement is satisfied if the operators in expr have
12387   // precedence equal to or greater than binop, or by using parentheses around
12388   // expr or subexpressions of expr.
12389   // * For forms that allow multiple occurrences of x, the number of times
12390   // that x is evaluated is unspecified.
12391   if (AtomicKind == OMPC_read) {
12392     enum {
12393       NotAnExpression,
12394       NotAnAssignmentOp,
12395       NotAScalarType,
12396       NotAnLValue,
12397       NoError
12398     } ErrorFound = NoError;
12399     SourceLocation ErrorLoc, NoteLoc;
12400     SourceRange ErrorRange, NoteRange;
12401     // If clause is read:
12402     //  v = x;
12403     if (const auto *AtomicBody = dyn_cast<Expr>(Body)) {
12404       const auto *AtomicBinOp =
12405           dyn_cast<BinaryOperator>(AtomicBody->IgnoreParenImpCasts());
12406       if (AtomicBinOp && AtomicBinOp->getOpcode() == BO_Assign) {
12407         X = AtomicBinOp->getRHS()->IgnoreParenImpCasts();
12408         V = AtomicBinOp->getLHS()->IgnoreParenImpCasts();
12409         if ((X->isInstantiationDependent() || X->getType()->isScalarType()) &&
12410             (V->isInstantiationDependent() || V->getType()->isScalarType())) {
12411           if (!X->isLValue() || !V->isLValue()) {
12412             const Expr *NotLValueExpr = X->isLValue() ? V : X;
12413             ErrorFound = NotAnLValue;
12414             ErrorLoc = AtomicBinOp->getExprLoc();
12415             ErrorRange = AtomicBinOp->getSourceRange();
12416             NoteLoc = NotLValueExpr->getExprLoc();
12417             NoteRange = NotLValueExpr->getSourceRange();
12418           }
12419         } else if (!X->isInstantiationDependent() ||
12420                    !V->isInstantiationDependent()) {
12421           const Expr *NotScalarExpr =
12422               (X->isInstantiationDependent() || X->getType()->isScalarType())
12423                   ? V
12424                   : X;
12425           ErrorFound = NotAScalarType;
12426           ErrorLoc = AtomicBinOp->getExprLoc();
12427           ErrorRange = AtomicBinOp->getSourceRange();
12428           NoteLoc = NotScalarExpr->getExprLoc();
12429           NoteRange = NotScalarExpr->getSourceRange();
12430         }
12431       } else if (!AtomicBody->isInstantiationDependent()) {
12432         ErrorFound = NotAnAssignmentOp;
12433         ErrorLoc = AtomicBody->getExprLoc();
12434         ErrorRange = AtomicBody->getSourceRange();
12435         NoteLoc = AtomicBinOp ? AtomicBinOp->getOperatorLoc()
12436                               : AtomicBody->getExprLoc();
12437         NoteRange = AtomicBinOp ? AtomicBinOp->getSourceRange()
12438                                 : AtomicBody->getSourceRange();
12439       }
12440     } else {
12441       ErrorFound = NotAnExpression;
12442       NoteLoc = ErrorLoc = Body->getBeginLoc();
12443       NoteRange = ErrorRange = SourceRange(NoteLoc, NoteLoc);
12444     }
12445     if (ErrorFound != NoError) {
12446       Diag(ErrorLoc, diag::err_omp_atomic_read_not_expression_statement)
12447           << ErrorRange;
12448       Diag(NoteLoc, diag::note_omp_atomic_read_write)
12449           << ErrorFound << NoteRange;
12450       return StmtError();
12451     }
12452     if (CurContext->isDependentContext())
12453       V = X = nullptr;
12454   } else if (AtomicKind == OMPC_write) {
12455     enum {
12456       NotAnExpression,
12457       NotAnAssignmentOp,
12458       NotAScalarType,
12459       NotAnLValue,
12460       NoError
12461     } ErrorFound = NoError;
12462     SourceLocation ErrorLoc, NoteLoc;
12463     SourceRange ErrorRange, NoteRange;
12464     // If clause is write:
12465     //  x = expr;
12466     if (const auto *AtomicBody = dyn_cast<Expr>(Body)) {
12467       const auto *AtomicBinOp =
12468           dyn_cast<BinaryOperator>(AtomicBody->IgnoreParenImpCasts());
12469       if (AtomicBinOp && AtomicBinOp->getOpcode() == BO_Assign) {
12470         X = AtomicBinOp->getLHS();
12471         E = AtomicBinOp->getRHS();
12472         if ((X->isInstantiationDependent() || X->getType()->isScalarType()) &&
12473             (E->isInstantiationDependent() || E->getType()->isScalarType())) {
12474           if (!X->isLValue()) {
12475             ErrorFound = NotAnLValue;
12476             ErrorLoc = AtomicBinOp->getExprLoc();
12477             ErrorRange = AtomicBinOp->getSourceRange();
12478             NoteLoc = X->getExprLoc();
12479             NoteRange = X->getSourceRange();
12480           }
12481         } else if (!X->isInstantiationDependent() ||
12482                    !E->isInstantiationDependent()) {
12483           const Expr *NotScalarExpr =
12484               (X->isInstantiationDependent() || X->getType()->isScalarType())
12485                   ? E
12486                   : X;
12487           ErrorFound = NotAScalarType;
12488           ErrorLoc = AtomicBinOp->getExprLoc();
12489           ErrorRange = AtomicBinOp->getSourceRange();
12490           NoteLoc = NotScalarExpr->getExprLoc();
12491           NoteRange = NotScalarExpr->getSourceRange();
12492         }
12493       } else if (!AtomicBody->isInstantiationDependent()) {
12494         ErrorFound = NotAnAssignmentOp;
12495         ErrorLoc = AtomicBody->getExprLoc();
12496         ErrorRange = AtomicBody->getSourceRange();
12497         NoteLoc = AtomicBinOp ? AtomicBinOp->getOperatorLoc()
12498                               : AtomicBody->getExprLoc();
12499         NoteRange = AtomicBinOp ? AtomicBinOp->getSourceRange()
12500                                 : AtomicBody->getSourceRange();
12501       }
12502     } else {
12503       ErrorFound = NotAnExpression;
12504       NoteLoc = ErrorLoc = Body->getBeginLoc();
12505       NoteRange = ErrorRange = SourceRange(NoteLoc, NoteLoc);
12506     }
12507     if (ErrorFound != NoError) {
12508       Diag(ErrorLoc, diag::err_omp_atomic_write_not_expression_statement)
12509           << ErrorRange;
12510       Diag(NoteLoc, diag::note_omp_atomic_read_write)
12511           << ErrorFound << NoteRange;
12512       return StmtError();
12513     }
12514     if (CurContext->isDependentContext())
12515       E = X = nullptr;
12516   } else if (AtomicKind == OMPC_update || AtomicKind == OMPC_unknown) {
12517     // If clause is update:
12518     //  x++;
12519     //  x--;
12520     //  ++x;
12521     //  --x;
12522     //  x binop= expr;
12523     //  x = x binop expr;
12524     //  x = expr binop x;
12525     OpenMPAtomicUpdateChecker Checker(*this);
12526     if (Checker.checkStatement(
12527             Body,
12528             (AtomicKind == OMPC_update)
12529                 ? diag::err_omp_atomic_update_not_expression_statement
12530                 : diag::err_omp_atomic_not_expression_statement,
12531             diag::note_omp_atomic_update))
12532       return StmtError();
12533     if (!CurContext->isDependentContext()) {
12534       E = Checker.getExpr();
12535       X = Checker.getX();
12536       UE = Checker.getUpdateExpr();
12537       IsXLHSInRHSPart = Checker.isXLHSInRHSPart();
12538     }
12539   } else if (AtomicKind == OMPC_capture) {
12540     enum {
12541       NotAnAssignmentOp,
12542       NotACompoundStatement,
12543       NotTwoSubstatements,
12544       NotASpecificExpression,
12545       NoError
12546     } ErrorFound = NoError;
12547     SourceLocation ErrorLoc, NoteLoc;
12548     SourceRange ErrorRange, NoteRange;
12549     if (const auto *AtomicBody = dyn_cast<Expr>(Body)) {
12550       // If clause is a capture:
12551       //  v = x++;
12552       //  v = x--;
12553       //  v = ++x;
12554       //  v = --x;
12555       //  v = x binop= expr;
12556       //  v = x = x binop expr;
12557       //  v = x = expr binop x;
12558       const auto *AtomicBinOp =
12559           dyn_cast<BinaryOperator>(AtomicBody->IgnoreParenImpCasts());
12560       if (AtomicBinOp && AtomicBinOp->getOpcode() == BO_Assign) {
12561         V = AtomicBinOp->getLHS();
12562         Body = AtomicBinOp->getRHS()->IgnoreParenImpCasts();
12563         OpenMPAtomicUpdateChecker Checker(*this);
12564         if (Checker.checkStatement(
12565                 Body, diag::err_omp_atomic_capture_not_expression_statement,
12566                 diag::note_omp_atomic_update))
12567           return StmtError();
12568         E = Checker.getExpr();
12569         X = Checker.getX();
12570         UE = Checker.getUpdateExpr();
12571         IsXLHSInRHSPart = Checker.isXLHSInRHSPart();
12572         IsPostfixUpdate = Checker.isPostfixUpdate();
12573       } else if (!AtomicBody->isInstantiationDependent()) {
12574         ErrorLoc = AtomicBody->getExprLoc();
12575         ErrorRange = AtomicBody->getSourceRange();
12576         NoteLoc = AtomicBinOp ? AtomicBinOp->getOperatorLoc()
12577                               : AtomicBody->getExprLoc();
12578         NoteRange = AtomicBinOp ? AtomicBinOp->getSourceRange()
12579                                 : AtomicBody->getSourceRange();
12580         ErrorFound = NotAnAssignmentOp;
12581       }
12582       if (ErrorFound != NoError) {
12583         Diag(ErrorLoc, diag::err_omp_atomic_capture_not_expression_statement)
12584             << ErrorRange;
12585         Diag(NoteLoc, diag::note_omp_atomic_capture) << ErrorFound << NoteRange;
12586         return StmtError();
12587       }
12588       if (CurContext->isDependentContext())
12589         UE = V = E = X = nullptr;
12590     } else {
12591       // If clause is a capture:
12592       //  { v = x; x = expr; }
12593       //  { v = x; x++; }
12594       //  { v = x; x--; }
12595       //  { v = x; ++x; }
12596       //  { v = x; --x; }
12597       //  { v = x; x binop= expr; }
12598       //  { v = x; x = x binop expr; }
12599       //  { v = x; x = expr binop x; }
12600       //  { x++; v = x; }
12601       //  { x--; v = x; }
12602       //  { ++x; v = x; }
12603       //  { --x; v = x; }
12604       //  { x binop= expr; v = x; }
12605       //  { x = x binop expr; v = x; }
12606       //  { x = expr binop x; v = x; }
12607       if (auto *CS = dyn_cast<CompoundStmt>(Body)) {
12608         // Check that this is { expr1; expr2; }
12609         if (CS->size() == 2) {
12610           Stmt *First = CS->body_front();
12611           Stmt *Second = CS->body_back();
12612           if (auto *EWC = dyn_cast<ExprWithCleanups>(First))
12613             First = EWC->getSubExpr()->IgnoreParenImpCasts();
12614           if (auto *EWC = dyn_cast<ExprWithCleanups>(Second))
12615             Second = EWC->getSubExpr()->IgnoreParenImpCasts();
12616           // Need to find what subexpression is 'v' and what is 'x'.
12617           OpenMPAtomicUpdateChecker Checker(*this);
12618           bool IsUpdateExprFound = !Checker.checkStatement(Second);
12619           BinaryOperator *BinOp = nullptr;
12620           if (IsUpdateExprFound) {
12621             BinOp = dyn_cast<BinaryOperator>(First);
12622             IsUpdateExprFound = BinOp && BinOp->getOpcode() == BO_Assign;
12623           }
12624           if (IsUpdateExprFound && !CurContext->isDependentContext()) {
12625             //  { v = x; x++; }
12626             //  { v = x; x--; }
12627             //  { v = x; ++x; }
12628             //  { v = x; --x; }
12629             //  { v = x; x binop= expr; }
12630             //  { v = x; x = x binop expr; }
12631             //  { v = x; x = expr binop x; }
12632             // Check that the first expression has form v = x.
12633             Expr *PossibleX = BinOp->getRHS()->IgnoreParenImpCasts();
12634             llvm::FoldingSetNodeID XId, PossibleXId;
12635             Checker.getX()->Profile(XId, Context, /*Canonical=*/true);
12636             PossibleX->Profile(PossibleXId, Context, /*Canonical=*/true);
12637             IsUpdateExprFound = XId == PossibleXId;
12638             if (IsUpdateExprFound) {
12639               V = BinOp->getLHS();
12640               X = Checker.getX();
12641               E = Checker.getExpr();
12642               UE = Checker.getUpdateExpr();
12643               IsXLHSInRHSPart = Checker.isXLHSInRHSPart();
12644               IsPostfixUpdate = true;
12645             }
12646           }
12647           if (!IsUpdateExprFound) {
12648             IsUpdateExprFound = !Checker.checkStatement(First);
12649             BinOp = nullptr;
12650             if (IsUpdateExprFound) {
12651               BinOp = dyn_cast<BinaryOperator>(Second);
12652               IsUpdateExprFound = BinOp && BinOp->getOpcode() == BO_Assign;
12653             }
12654             if (IsUpdateExprFound && !CurContext->isDependentContext()) {
12655               //  { x++; v = x; }
12656               //  { x--; v = x; }
12657               //  { ++x; v = x; }
12658               //  { --x; v = x; }
12659               //  { x binop= expr; v = x; }
12660               //  { x = x binop expr; v = x; }
12661               //  { x = expr binop x; v = x; }
12662               // Check that the second expression has form v = x.
12663               Expr *PossibleX = BinOp->getRHS()->IgnoreParenImpCasts();
12664               llvm::FoldingSetNodeID XId, PossibleXId;
12665               Checker.getX()->Profile(XId, Context, /*Canonical=*/true);
12666               PossibleX->Profile(PossibleXId, Context, /*Canonical=*/true);
12667               IsUpdateExprFound = XId == PossibleXId;
12668               if (IsUpdateExprFound) {
12669                 V = BinOp->getLHS();
12670                 X = Checker.getX();
12671                 E = Checker.getExpr();
12672                 UE = Checker.getUpdateExpr();
12673                 IsXLHSInRHSPart = Checker.isXLHSInRHSPart();
12674                 IsPostfixUpdate = false;
12675               }
12676             }
12677           }
12678           if (!IsUpdateExprFound) {
12679             //  { v = x; x = expr; }
12680             auto *FirstExpr = dyn_cast<Expr>(First);
12681             auto *SecondExpr = dyn_cast<Expr>(Second);
12682             if (!FirstExpr || !SecondExpr ||
12683                 !(FirstExpr->isInstantiationDependent() ||
12684                   SecondExpr->isInstantiationDependent())) {
12685               auto *FirstBinOp = dyn_cast<BinaryOperator>(First);
12686               if (!FirstBinOp || FirstBinOp->getOpcode() != BO_Assign) {
12687                 ErrorFound = NotAnAssignmentOp;
12688                 NoteLoc = ErrorLoc = FirstBinOp ? FirstBinOp->getOperatorLoc()
12689                                                 : First->getBeginLoc();
12690                 NoteRange = ErrorRange = FirstBinOp
12691                                              ? FirstBinOp->getSourceRange()
12692                                              : SourceRange(ErrorLoc, ErrorLoc);
12693               } else {
12694                 auto *SecondBinOp = dyn_cast<BinaryOperator>(Second);
12695                 if (!SecondBinOp || SecondBinOp->getOpcode() != BO_Assign) {
12696                   ErrorFound = NotAnAssignmentOp;
12697                   NoteLoc = ErrorLoc = SecondBinOp
12698                                            ? SecondBinOp->getOperatorLoc()
12699                                            : Second->getBeginLoc();
12700                   NoteRange = ErrorRange =
12701                       SecondBinOp ? SecondBinOp->getSourceRange()
12702                                   : SourceRange(ErrorLoc, ErrorLoc);
12703                 } else {
12704                   Expr *PossibleXRHSInFirst =
12705                       FirstBinOp->getRHS()->IgnoreParenImpCasts();
12706                   Expr *PossibleXLHSInSecond =
12707                       SecondBinOp->getLHS()->IgnoreParenImpCasts();
12708                   llvm::FoldingSetNodeID X1Id, X2Id;
12709                   PossibleXRHSInFirst->Profile(X1Id, Context,
12710                                                /*Canonical=*/true);
12711                   PossibleXLHSInSecond->Profile(X2Id, Context,
12712                                                 /*Canonical=*/true);
12713                   IsUpdateExprFound = X1Id == X2Id;
12714                   if (IsUpdateExprFound) {
12715                     V = FirstBinOp->getLHS();
12716                     X = SecondBinOp->getLHS();
12717                     E = SecondBinOp->getRHS();
12718                     UE = nullptr;
12719                     IsXLHSInRHSPart = false;
12720                     IsPostfixUpdate = true;
12721                   } else {
12722                     ErrorFound = NotASpecificExpression;
12723                     ErrorLoc = FirstBinOp->getExprLoc();
12724                     ErrorRange = FirstBinOp->getSourceRange();
12725                     NoteLoc = SecondBinOp->getLHS()->getExprLoc();
12726                     NoteRange = SecondBinOp->getRHS()->getSourceRange();
12727                   }
12728                 }
12729               }
12730             }
12731           }
12732         } else {
12733           NoteLoc = ErrorLoc = Body->getBeginLoc();
12734           NoteRange = ErrorRange =
12735               SourceRange(Body->getBeginLoc(), Body->getBeginLoc());
12736           ErrorFound = NotTwoSubstatements;
12737         }
12738       } else {
12739         NoteLoc = ErrorLoc = Body->getBeginLoc();
12740         NoteRange = ErrorRange =
12741             SourceRange(Body->getBeginLoc(), Body->getBeginLoc());
12742         ErrorFound = NotACompoundStatement;
12743       }
12744     }
12745     if (ErrorFound != NoError) {
12746       Diag(ErrorLoc, diag::err_omp_atomic_capture_not_compound_statement)
12747           << ErrorRange;
12748       Diag(NoteLoc, diag::note_omp_atomic_capture) << ErrorFound << NoteRange;
12749       return StmtError();
12750     }
12751     if (CurContext->isDependentContext())
12752       UE = V = E = X = nullptr;
12753   } else if (AtomicKind == OMPC_compare) {
12754     if (IsCompareCapture) {
12755       OpenMPAtomicCompareCaptureChecker::ErrorInfoTy ErrorInfo;
12756       OpenMPAtomicCompareCaptureChecker Checker(*this);
12757       if (!Checker.checkStmt(Body, ErrorInfo)) {
12758         Diag(ErrorInfo.ErrorLoc, diag::err_omp_atomic_compare_capture)
12759             << ErrorInfo.ErrorRange;
12760         Diag(ErrorInfo.NoteLoc, diag::note_omp_atomic_compare)
12761             << ErrorInfo.Error << ErrorInfo.NoteRange;
12762         return StmtError();
12763       }
12764       X = Checker.getX();
12765       E = Checker.getE();
12766       D = Checker.getD();
12767       CE = Checker.getCond();
12768       V = Checker.getV();
12769       R = Checker.getR();
12770       // We reuse IsXLHSInRHSPart to tell if it is in the form 'x ordop expr'.
12771       IsXLHSInRHSPart = Checker.isXBinopExpr();
12772       IsFailOnly = Checker.isFailOnly();
12773       IsPostfixUpdate = Checker.isPostfixUpdate();
12774     } else {
12775       OpenMPAtomicCompareChecker::ErrorInfoTy ErrorInfo;
12776       OpenMPAtomicCompareChecker Checker(*this);
12777       if (!Checker.checkStmt(Body, ErrorInfo)) {
12778         Diag(ErrorInfo.ErrorLoc, diag::err_omp_atomic_compare)
12779             << ErrorInfo.ErrorRange;
12780         Diag(ErrorInfo.NoteLoc, diag::note_omp_atomic_compare)
12781           << ErrorInfo.Error << ErrorInfo.NoteRange;
12782         return StmtError();
12783       }
12784       X = Checker.getX();
12785       E = Checker.getE();
12786       D = Checker.getD();
12787       CE = Checker.getCond();
12788       // We reuse IsXLHSInRHSPart to tell if it is in the form 'x ordop expr'.
12789       IsXLHSInRHSPart = Checker.isXBinopExpr();
12790     }
12791   }
12792 
12793   setFunctionHasBranchProtectedScope();
12794 
12795   return OMPAtomicDirective::Create(
12796       Context, StartLoc, EndLoc, Clauses, AStmt,
12797       {X, V, R, E, UE, D, CE, IsXLHSInRHSPart, IsPostfixUpdate, IsFailOnly});
12798 }
12799 
12800 StmtResult Sema::ActOnOpenMPTargetDirective(ArrayRef<OMPClause *> Clauses,
12801                                             Stmt *AStmt,
12802                                             SourceLocation StartLoc,
12803                                             SourceLocation EndLoc) {
12804   if (!AStmt)
12805     return StmtError();
12806 
12807   auto *CS = cast<CapturedStmt>(AStmt);
12808   // 1.2.2 OpenMP Language Terminology
12809   // Structured block - An executable statement with a single entry at the
12810   // top and a single exit at the bottom.
12811   // The point of exit cannot be a branch out of the structured block.
12812   // longjmp() and throw() must not violate the entry/exit criteria.
12813   CS->getCapturedDecl()->setNothrow();
12814   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target);
12815        ThisCaptureLevel > 1; --ThisCaptureLevel) {
12816     CS = cast<CapturedStmt>(CS->getCapturedStmt());
12817     // 1.2.2 OpenMP Language Terminology
12818     // Structured block - An executable statement with a single entry at the
12819     // top and a single exit at the bottom.
12820     // The point of exit cannot be a branch out of the structured block.
12821     // longjmp() and throw() must not violate the entry/exit criteria.
12822     CS->getCapturedDecl()->setNothrow();
12823   }
12824 
12825   // OpenMP [2.16, Nesting of Regions]
12826   // If specified, a teams construct must be contained within a target
12827   // construct. That target construct must contain no statements or directives
12828   // outside of the teams construct.
12829   if (DSAStack->hasInnerTeamsRegion()) {
12830     const Stmt *S = CS->IgnoreContainers(/*IgnoreCaptured=*/true);
12831     bool OMPTeamsFound = true;
12832     if (const auto *CS = dyn_cast<CompoundStmt>(S)) {
12833       auto I = CS->body_begin();
12834       while (I != CS->body_end()) {
12835         const auto *OED = dyn_cast<OMPExecutableDirective>(*I);
12836         if (!OED || !isOpenMPTeamsDirective(OED->getDirectiveKind()) ||
12837             OMPTeamsFound) {
12838 
12839           OMPTeamsFound = false;
12840           break;
12841         }
12842         ++I;
12843       }
12844       assert(I != CS->body_end() && "Not found statement");
12845       S = *I;
12846     } else {
12847       const auto *OED = dyn_cast<OMPExecutableDirective>(S);
12848       OMPTeamsFound = OED && isOpenMPTeamsDirective(OED->getDirectiveKind());
12849     }
12850     if (!OMPTeamsFound) {
12851       Diag(StartLoc, diag::err_omp_target_contains_not_only_teams);
12852       Diag(DSAStack->getInnerTeamsRegionLoc(),
12853            diag::note_omp_nested_teams_construct_here);
12854       Diag(S->getBeginLoc(), diag::note_omp_nested_statement_here)
12855           << isa<OMPExecutableDirective>(S);
12856       return StmtError();
12857     }
12858   }
12859 
12860   setFunctionHasBranchProtectedScope();
12861 
12862   return OMPTargetDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt);
12863 }
12864 
12865 StmtResult
12866 Sema::ActOnOpenMPTargetParallelDirective(ArrayRef<OMPClause *> Clauses,
12867                                          Stmt *AStmt, SourceLocation StartLoc,
12868                                          SourceLocation EndLoc) {
12869   if (!AStmt)
12870     return StmtError();
12871 
12872   auto *CS = cast<CapturedStmt>(AStmt);
12873   // 1.2.2 OpenMP Language Terminology
12874   // Structured block - An executable statement with a single entry at the
12875   // top and a single exit at the bottom.
12876   // The point of exit cannot be a branch out of the structured block.
12877   // longjmp() and throw() must not violate the entry/exit criteria.
12878   CS->getCapturedDecl()->setNothrow();
12879   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_parallel);
12880        ThisCaptureLevel > 1; --ThisCaptureLevel) {
12881     CS = cast<CapturedStmt>(CS->getCapturedStmt());
12882     // 1.2.2 OpenMP Language Terminology
12883     // Structured block - An executable statement with a single entry at the
12884     // top and a single exit at the bottom.
12885     // The point of exit cannot be a branch out of the structured block.
12886     // longjmp() and throw() must not violate the entry/exit criteria.
12887     CS->getCapturedDecl()->setNothrow();
12888   }
12889 
12890   setFunctionHasBranchProtectedScope();
12891 
12892   return OMPTargetParallelDirective::Create(
12893       Context, StartLoc, EndLoc, Clauses, AStmt,
12894       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
12895 }
12896 
12897 StmtResult Sema::ActOnOpenMPTargetParallelForDirective(
12898     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
12899     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
12900   if (!AStmt)
12901     return StmtError();
12902 
12903   auto *CS = cast<CapturedStmt>(AStmt);
12904   // 1.2.2 OpenMP Language Terminology
12905   // Structured block - An executable statement with a single entry at the
12906   // top and a single exit at the bottom.
12907   // The point of exit cannot be a branch out of the structured block.
12908   // longjmp() and throw() must not violate the entry/exit criteria.
12909   CS->getCapturedDecl()->setNothrow();
12910   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_parallel_for);
12911        ThisCaptureLevel > 1; --ThisCaptureLevel) {
12912     CS = cast<CapturedStmt>(CS->getCapturedStmt());
12913     // 1.2.2 OpenMP Language Terminology
12914     // Structured block - An executable statement with a single entry at the
12915     // top and a single exit at the bottom.
12916     // The point of exit cannot be a branch out of the structured block.
12917     // longjmp() and throw() must not violate the entry/exit criteria.
12918     CS->getCapturedDecl()->setNothrow();
12919   }
12920 
12921   OMPLoopBasedDirective::HelperExprs B;
12922   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
12923   // define the nested loops number.
12924   unsigned NestedLoopCount =
12925       checkOpenMPLoop(OMPD_target_parallel_for, getCollapseNumberExpr(Clauses),
12926                       getOrderedNumberExpr(Clauses), CS, *this, *DSAStack,
12927                       VarsWithImplicitDSA, B);
12928   if (NestedLoopCount == 0)
12929     return StmtError();
12930 
12931   assert((CurContext->isDependentContext() || B.builtAll()) &&
12932          "omp target parallel for loop exprs were not built");
12933 
12934   if (!CurContext->isDependentContext()) {
12935     // Finalize the clauses that need pre-built expressions for CodeGen.
12936     for (OMPClause *C : Clauses) {
12937       if (auto *LC = dyn_cast<OMPLinearClause>(C))
12938         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
12939                                      B.NumIterations, *this, CurScope,
12940                                      DSAStack))
12941           return StmtError();
12942     }
12943   }
12944 
12945   setFunctionHasBranchProtectedScope();
12946   return OMPTargetParallelForDirective::Create(
12947       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
12948       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
12949 }
12950 
12951 /// Check for existence of a map clause in the list of clauses.
12952 static bool hasClauses(ArrayRef<OMPClause *> Clauses,
12953                        const OpenMPClauseKind K) {
12954   return llvm::any_of(
12955       Clauses, [K](const OMPClause *C) { return C->getClauseKind() == K; });
12956 }
12957 
12958 template <typename... Params>
12959 static bool hasClauses(ArrayRef<OMPClause *> Clauses, const OpenMPClauseKind K,
12960                        const Params... ClauseTypes) {
12961   return hasClauses(Clauses, K) || hasClauses(Clauses, ClauseTypes...);
12962 }
12963 
12964 /// Check if the variables in the mapping clause are externally visible.
12965 static bool isClauseMappable(ArrayRef<OMPClause *> Clauses) {
12966   for (const OMPClause *C : Clauses) {
12967     if (auto *TC = dyn_cast<OMPToClause>(C))
12968       return llvm::all_of(TC->all_decls(), [](ValueDecl *VD) {
12969         return !VD || !VD->hasAttr<OMPDeclareTargetDeclAttr>() ||
12970                (VD->isExternallyVisible() &&
12971                 VD->getVisibility() != HiddenVisibility);
12972       });
12973     else if (auto *FC = dyn_cast<OMPFromClause>(C))
12974       return llvm::all_of(FC->all_decls(), [](ValueDecl *VD) {
12975         return !VD || !VD->hasAttr<OMPDeclareTargetDeclAttr>() ||
12976                (VD->isExternallyVisible() &&
12977                 VD->getVisibility() != HiddenVisibility);
12978       });
12979   }
12980 
12981   return true;
12982 }
12983 
12984 StmtResult Sema::ActOnOpenMPTargetDataDirective(ArrayRef<OMPClause *> Clauses,
12985                                                 Stmt *AStmt,
12986                                                 SourceLocation StartLoc,
12987                                                 SourceLocation EndLoc) {
12988   if (!AStmt)
12989     return StmtError();
12990 
12991   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
12992 
12993   // OpenMP [2.12.2, target data Construct, Restrictions]
12994   // At least one map, use_device_addr or use_device_ptr clause must appear on
12995   // the directive.
12996   if (!hasClauses(Clauses, OMPC_map, OMPC_use_device_ptr) &&
12997       (LangOpts.OpenMP < 50 || !hasClauses(Clauses, OMPC_use_device_addr))) {
12998     StringRef Expected;
12999     if (LangOpts.OpenMP < 50)
13000       Expected = "'map' or 'use_device_ptr'";
13001     else
13002       Expected = "'map', 'use_device_ptr', or 'use_device_addr'";
13003     Diag(StartLoc, diag::err_omp_no_clause_for_directive)
13004         << Expected << getOpenMPDirectiveName(OMPD_target_data);
13005     return StmtError();
13006   }
13007 
13008   setFunctionHasBranchProtectedScope();
13009 
13010   return OMPTargetDataDirective::Create(Context, StartLoc, EndLoc, Clauses,
13011                                         AStmt);
13012 }
13013 
13014 StmtResult
13015 Sema::ActOnOpenMPTargetEnterDataDirective(ArrayRef<OMPClause *> Clauses,
13016                                           SourceLocation StartLoc,
13017                                           SourceLocation EndLoc, Stmt *AStmt) {
13018   if (!AStmt)
13019     return StmtError();
13020 
13021   auto *CS = cast<CapturedStmt>(AStmt);
13022   // 1.2.2 OpenMP Language Terminology
13023   // Structured block - An executable statement with a single entry at the
13024   // top and a single exit at the bottom.
13025   // The point of exit cannot be a branch out of the structured block.
13026   // longjmp() and throw() must not violate the entry/exit criteria.
13027   CS->getCapturedDecl()->setNothrow();
13028   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_enter_data);
13029        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13030     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13031     // 1.2.2 OpenMP Language Terminology
13032     // Structured block - An executable statement with a single entry at the
13033     // top and a single exit at the bottom.
13034     // The point of exit cannot be a branch out of the structured block.
13035     // longjmp() and throw() must not violate the entry/exit criteria.
13036     CS->getCapturedDecl()->setNothrow();
13037   }
13038 
13039   // OpenMP [2.10.2, Restrictions, p. 99]
13040   // At least one map clause must appear on the directive.
13041   if (!hasClauses(Clauses, OMPC_map)) {
13042     Diag(StartLoc, diag::err_omp_no_clause_for_directive)
13043         << "'map'" << getOpenMPDirectiveName(OMPD_target_enter_data);
13044     return StmtError();
13045   }
13046 
13047   return OMPTargetEnterDataDirective::Create(Context, StartLoc, EndLoc, Clauses,
13048                                              AStmt);
13049 }
13050 
13051 StmtResult
13052 Sema::ActOnOpenMPTargetExitDataDirective(ArrayRef<OMPClause *> Clauses,
13053                                          SourceLocation StartLoc,
13054                                          SourceLocation EndLoc, Stmt *AStmt) {
13055   if (!AStmt)
13056     return StmtError();
13057 
13058   auto *CS = cast<CapturedStmt>(AStmt);
13059   // 1.2.2 OpenMP Language Terminology
13060   // Structured block - An executable statement with a single entry at the
13061   // top and a single exit at the bottom.
13062   // The point of exit cannot be a branch out of the structured block.
13063   // longjmp() and throw() must not violate the entry/exit criteria.
13064   CS->getCapturedDecl()->setNothrow();
13065   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_exit_data);
13066        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13067     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13068     // 1.2.2 OpenMP Language Terminology
13069     // Structured block - An executable statement with a single entry at the
13070     // top and a single exit at the bottom.
13071     // The point of exit cannot be a branch out of the structured block.
13072     // longjmp() and throw() must not violate the entry/exit criteria.
13073     CS->getCapturedDecl()->setNothrow();
13074   }
13075 
13076   // OpenMP [2.10.3, Restrictions, p. 102]
13077   // At least one map clause must appear on the directive.
13078   if (!hasClauses(Clauses, OMPC_map)) {
13079     Diag(StartLoc, diag::err_omp_no_clause_for_directive)
13080         << "'map'" << getOpenMPDirectiveName(OMPD_target_exit_data);
13081     return StmtError();
13082   }
13083 
13084   return OMPTargetExitDataDirective::Create(Context, StartLoc, EndLoc, Clauses,
13085                                             AStmt);
13086 }
13087 
13088 StmtResult Sema::ActOnOpenMPTargetUpdateDirective(ArrayRef<OMPClause *> Clauses,
13089                                                   SourceLocation StartLoc,
13090                                                   SourceLocation EndLoc,
13091                                                   Stmt *AStmt) {
13092   if (!AStmt)
13093     return StmtError();
13094 
13095   auto *CS = cast<CapturedStmt>(AStmt);
13096   // 1.2.2 OpenMP Language Terminology
13097   // Structured block - An executable statement with a single entry at the
13098   // top and a single exit at the bottom.
13099   // The point of exit cannot be a branch out of the structured block.
13100   // longjmp() and throw() must not violate the entry/exit criteria.
13101   CS->getCapturedDecl()->setNothrow();
13102   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_update);
13103        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13104     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13105     // 1.2.2 OpenMP Language Terminology
13106     // Structured block - An executable statement with a single entry at the
13107     // top and a single exit at the bottom.
13108     // The point of exit cannot be a branch out of the structured block.
13109     // longjmp() and throw() must not violate the entry/exit criteria.
13110     CS->getCapturedDecl()->setNothrow();
13111   }
13112 
13113   if (!hasClauses(Clauses, OMPC_to, OMPC_from)) {
13114     Diag(StartLoc, diag::err_omp_at_least_one_motion_clause_required);
13115     return StmtError();
13116   }
13117 
13118   if (!isClauseMappable(Clauses)) {
13119     Diag(StartLoc, diag::err_omp_cannot_update_with_internal_linkage);
13120     return StmtError();
13121   }
13122 
13123   return OMPTargetUpdateDirective::Create(Context, StartLoc, EndLoc, Clauses,
13124                                           AStmt);
13125 }
13126 
13127 StmtResult Sema::ActOnOpenMPTeamsDirective(ArrayRef<OMPClause *> Clauses,
13128                                            Stmt *AStmt, SourceLocation StartLoc,
13129                                            SourceLocation EndLoc) {
13130   if (!AStmt)
13131     return StmtError();
13132 
13133   auto *CS = cast<CapturedStmt>(AStmt);
13134   // 1.2.2 OpenMP Language Terminology
13135   // Structured block - An executable statement with a single entry at the
13136   // top and a single exit at the bottom.
13137   // The point of exit cannot be a branch out of the structured block.
13138   // longjmp() and throw() must not violate the entry/exit criteria.
13139   CS->getCapturedDecl()->setNothrow();
13140 
13141   setFunctionHasBranchProtectedScope();
13142 
13143   DSAStack->setParentTeamsRegionLoc(StartLoc);
13144 
13145   return OMPTeamsDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt);
13146 }
13147 
13148 StmtResult
13149 Sema::ActOnOpenMPCancellationPointDirective(SourceLocation StartLoc,
13150                                             SourceLocation EndLoc,
13151                                             OpenMPDirectiveKind CancelRegion) {
13152   if (DSAStack->isParentNowaitRegion()) {
13153     Diag(StartLoc, diag::err_omp_parent_cancel_region_nowait) << 0;
13154     return StmtError();
13155   }
13156   if (DSAStack->isParentOrderedRegion()) {
13157     Diag(StartLoc, diag::err_omp_parent_cancel_region_ordered) << 0;
13158     return StmtError();
13159   }
13160   return OMPCancellationPointDirective::Create(Context, StartLoc, EndLoc,
13161                                                CancelRegion);
13162 }
13163 
13164 StmtResult Sema::ActOnOpenMPCancelDirective(ArrayRef<OMPClause *> Clauses,
13165                                             SourceLocation StartLoc,
13166                                             SourceLocation EndLoc,
13167                                             OpenMPDirectiveKind CancelRegion) {
13168   if (DSAStack->isParentNowaitRegion()) {
13169     Diag(StartLoc, diag::err_omp_parent_cancel_region_nowait) << 1;
13170     return StmtError();
13171   }
13172   if (DSAStack->isParentOrderedRegion()) {
13173     Diag(StartLoc, diag::err_omp_parent_cancel_region_ordered) << 1;
13174     return StmtError();
13175   }
13176   DSAStack->setParentCancelRegion(/*Cancel=*/true);
13177   return OMPCancelDirective::Create(Context, StartLoc, EndLoc, Clauses,
13178                                     CancelRegion);
13179 }
13180 
13181 static bool checkReductionClauseWithNogroup(Sema &S,
13182                                             ArrayRef<OMPClause *> Clauses) {
13183   const OMPClause *ReductionClause = nullptr;
13184   const OMPClause *NogroupClause = nullptr;
13185   for (const OMPClause *C : Clauses) {
13186     if (C->getClauseKind() == OMPC_reduction) {
13187       ReductionClause = C;
13188       if (NogroupClause)
13189         break;
13190       continue;
13191     }
13192     if (C->getClauseKind() == OMPC_nogroup) {
13193       NogroupClause = C;
13194       if (ReductionClause)
13195         break;
13196       continue;
13197     }
13198   }
13199   if (ReductionClause && NogroupClause) {
13200     S.Diag(ReductionClause->getBeginLoc(), diag::err_omp_reduction_with_nogroup)
13201         << SourceRange(NogroupClause->getBeginLoc(),
13202                        NogroupClause->getEndLoc());
13203     return true;
13204   }
13205   return false;
13206 }
13207 
13208 StmtResult Sema::ActOnOpenMPTaskLoopDirective(
13209     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13210     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13211   if (!AStmt)
13212     return StmtError();
13213 
13214   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13215   OMPLoopBasedDirective::HelperExprs B;
13216   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13217   // define the nested loops number.
13218   unsigned NestedLoopCount =
13219       checkOpenMPLoop(OMPD_taskloop, getCollapseNumberExpr(Clauses),
13220                       /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack,
13221                       VarsWithImplicitDSA, B);
13222   if (NestedLoopCount == 0)
13223     return StmtError();
13224 
13225   assert((CurContext->isDependentContext() || B.builtAll()) &&
13226          "omp for loop exprs were not built");
13227 
13228   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13229   // The grainsize clause and num_tasks clause are mutually exclusive and may
13230   // not appear on the same taskloop directive.
13231   if (checkMutuallyExclusiveClauses(*this, Clauses,
13232                                     {OMPC_grainsize, OMPC_num_tasks}))
13233     return StmtError();
13234   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13235   // If a reduction clause is present on the taskloop directive, the nogroup
13236   // clause must not be specified.
13237   if (checkReductionClauseWithNogroup(*this, Clauses))
13238     return StmtError();
13239 
13240   setFunctionHasBranchProtectedScope();
13241   return OMPTaskLoopDirective::Create(Context, StartLoc, EndLoc,
13242                                       NestedLoopCount, Clauses, AStmt, B,
13243                                       DSAStack->isCancelRegion());
13244 }
13245 
13246 StmtResult Sema::ActOnOpenMPTaskLoopSimdDirective(
13247     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13248     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13249   if (!AStmt)
13250     return StmtError();
13251 
13252   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13253   OMPLoopBasedDirective::HelperExprs B;
13254   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13255   // define the nested loops number.
13256   unsigned NestedLoopCount =
13257       checkOpenMPLoop(OMPD_taskloop_simd, getCollapseNumberExpr(Clauses),
13258                       /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack,
13259                       VarsWithImplicitDSA, B);
13260   if (NestedLoopCount == 0)
13261     return StmtError();
13262 
13263   assert((CurContext->isDependentContext() || B.builtAll()) &&
13264          "omp for loop exprs were not built");
13265 
13266   if (!CurContext->isDependentContext()) {
13267     // Finalize the clauses that need pre-built expressions for CodeGen.
13268     for (OMPClause *C : Clauses) {
13269       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13270         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13271                                      B.NumIterations, *this, CurScope,
13272                                      DSAStack))
13273           return StmtError();
13274     }
13275   }
13276 
13277   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13278   // The grainsize clause and num_tasks clause are mutually exclusive and may
13279   // not appear on the same taskloop directive.
13280   if (checkMutuallyExclusiveClauses(*this, Clauses,
13281                                     {OMPC_grainsize, OMPC_num_tasks}))
13282     return StmtError();
13283   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13284   // If a reduction clause is present on the taskloop directive, the nogroup
13285   // clause must not be specified.
13286   if (checkReductionClauseWithNogroup(*this, Clauses))
13287     return StmtError();
13288   if (checkSimdlenSafelenSpecified(*this, Clauses))
13289     return StmtError();
13290 
13291   setFunctionHasBranchProtectedScope();
13292   return OMPTaskLoopSimdDirective::Create(Context, StartLoc, EndLoc,
13293                                           NestedLoopCount, Clauses, AStmt, B);
13294 }
13295 
13296 StmtResult Sema::ActOnOpenMPMasterTaskLoopDirective(
13297     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13298     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13299   if (!AStmt)
13300     return StmtError();
13301 
13302   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13303   OMPLoopBasedDirective::HelperExprs B;
13304   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13305   // define the nested loops number.
13306   unsigned NestedLoopCount =
13307       checkOpenMPLoop(OMPD_master_taskloop, getCollapseNumberExpr(Clauses),
13308                       /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack,
13309                       VarsWithImplicitDSA, B);
13310   if (NestedLoopCount == 0)
13311     return StmtError();
13312 
13313   assert((CurContext->isDependentContext() || B.builtAll()) &&
13314          "omp for loop exprs were not built");
13315 
13316   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13317   // The grainsize clause and num_tasks clause are mutually exclusive and may
13318   // not appear on the same taskloop directive.
13319   if (checkMutuallyExclusiveClauses(*this, Clauses,
13320                                     {OMPC_grainsize, OMPC_num_tasks}))
13321     return StmtError();
13322   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13323   // If a reduction clause is present on the taskloop directive, the nogroup
13324   // clause must not be specified.
13325   if (checkReductionClauseWithNogroup(*this, Clauses))
13326     return StmtError();
13327 
13328   setFunctionHasBranchProtectedScope();
13329   return OMPMasterTaskLoopDirective::Create(Context, StartLoc, EndLoc,
13330                                             NestedLoopCount, Clauses, AStmt, B,
13331                                             DSAStack->isCancelRegion());
13332 }
13333 
13334 StmtResult Sema::ActOnOpenMPMaskedTaskLoopDirective(
13335     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13336     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13337   if (!AStmt)
13338     return StmtError();
13339 
13340   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13341   OMPLoopBasedDirective::HelperExprs B;
13342   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13343   // define the nested loops number.
13344   unsigned NestedLoopCount =
13345       checkOpenMPLoop(OMPD_masked_taskloop, getCollapseNumberExpr(Clauses),
13346                       /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack,
13347                       VarsWithImplicitDSA, B);
13348   if (NestedLoopCount == 0)
13349     return StmtError();
13350 
13351   assert((CurContext->isDependentContext() || B.builtAll()) &&
13352          "omp for loop exprs were not built");
13353 
13354   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13355   // The grainsize clause and num_tasks clause are mutually exclusive and may
13356   // not appear on the same taskloop directive.
13357   if (checkMutuallyExclusiveClauses(*this, Clauses,
13358                                     {OMPC_grainsize, OMPC_num_tasks}))
13359     return StmtError();
13360   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13361   // If a reduction clause is present on the taskloop directive, the nogroup
13362   // clause must not be specified.
13363   if (checkReductionClauseWithNogroup(*this, Clauses))
13364     return StmtError();
13365 
13366   setFunctionHasBranchProtectedScope();
13367   return OMPMaskedTaskLoopDirective::Create(Context, StartLoc, EndLoc,
13368                                             NestedLoopCount, Clauses, AStmt, B,
13369                                             DSAStack->isCancelRegion());
13370 }
13371 
13372 StmtResult Sema::ActOnOpenMPMasterTaskLoopSimdDirective(
13373     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13374     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13375   if (!AStmt)
13376     return StmtError();
13377 
13378   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13379   OMPLoopBasedDirective::HelperExprs B;
13380   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13381   // define the nested loops number.
13382   unsigned NestedLoopCount =
13383       checkOpenMPLoop(OMPD_master_taskloop_simd, getCollapseNumberExpr(Clauses),
13384                       /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack,
13385                       VarsWithImplicitDSA, B);
13386   if (NestedLoopCount == 0)
13387     return StmtError();
13388 
13389   assert((CurContext->isDependentContext() || B.builtAll()) &&
13390          "omp for loop exprs were not built");
13391 
13392   if (!CurContext->isDependentContext()) {
13393     // Finalize the clauses that need pre-built expressions for CodeGen.
13394     for (OMPClause *C : Clauses) {
13395       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13396         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13397                                      B.NumIterations, *this, CurScope,
13398                                      DSAStack))
13399           return StmtError();
13400     }
13401   }
13402 
13403   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13404   // The grainsize clause and num_tasks clause are mutually exclusive and may
13405   // not appear on the same taskloop directive.
13406   if (checkMutuallyExclusiveClauses(*this, Clauses,
13407                                     {OMPC_grainsize, OMPC_num_tasks}))
13408     return StmtError();
13409   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13410   // If a reduction clause is present on the taskloop directive, the nogroup
13411   // clause must not be specified.
13412   if (checkReductionClauseWithNogroup(*this, Clauses))
13413     return StmtError();
13414   if (checkSimdlenSafelenSpecified(*this, Clauses))
13415     return StmtError();
13416 
13417   setFunctionHasBranchProtectedScope();
13418   return OMPMasterTaskLoopSimdDirective::Create(
13419       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
13420 }
13421 
13422 StmtResult Sema::ActOnOpenMPMaskedTaskLoopSimdDirective(
13423     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13424     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13425   if (!AStmt)
13426     return StmtError();
13427 
13428   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13429   OMPLoopBasedDirective::HelperExprs B;
13430   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13431   // define the nested loops number.
13432   unsigned NestedLoopCount =
13433       checkOpenMPLoop(OMPD_masked_taskloop_simd, getCollapseNumberExpr(Clauses),
13434                       /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack,
13435                       VarsWithImplicitDSA, B);
13436   if (NestedLoopCount == 0)
13437     return StmtError();
13438 
13439   assert((CurContext->isDependentContext() || B.builtAll()) &&
13440          "omp for loop exprs were not built");
13441 
13442   if (!CurContext->isDependentContext()) {
13443     // Finalize the clauses that need pre-built expressions for CodeGen.
13444     for (OMPClause *C : Clauses) {
13445       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13446         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13447                                      B.NumIterations, *this, CurScope,
13448                                      DSAStack))
13449           return StmtError();
13450     }
13451   }
13452 
13453   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13454   // The grainsize clause and num_tasks clause are mutually exclusive and may
13455   // not appear on the same taskloop directive.
13456   if (checkMutuallyExclusiveClauses(*this, Clauses,
13457                                     {OMPC_grainsize, OMPC_num_tasks}))
13458     return StmtError();
13459   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13460   // If a reduction clause is present on the taskloop directive, the nogroup
13461   // clause must not be specified.
13462   if (checkReductionClauseWithNogroup(*this, Clauses))
13463     return StmtError();
13464   if (checkSimdlenSafelenSpecified(*this, Clauses))
13465     return StmtError();
13466 
13467   setFunctionHasBranchProtectedScope();
13468   return OMPMaskedTaskLoopSimdDirective::Create(
13469       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
13470 }
13471 
13472 StmtResult Sema::ActOnOpenMPParallelMasterTaskLoopDirective(
13473     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13474     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13475   if (!AStmt)
13476     return StmtError();
13477 
13478   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13479   auto *CS = cast<CapturedStmt>(AStmt);
13480   // 1.2.2 OpenMP Language Terminology
13481   // Structured block - An executable statement with a single entry at the
13482   // top and a single exit at the bottom.
13483   // The point of exit cannot be a branch out of the structured block.
13484   // longjmp() and throw() must not violate the entry/exit criteria.
13485   CS->getCapturedDecl()->setNothrow();
13486   for (int ThisCaptureLevel =
13487            getOpenMPCaptureLevels(OMPD_parallel_master_taskloop);
13488        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13489     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13490     // 1.2.2 OpenMP Language Terminology
13491     // Structured block - An executable statement with a single entry at the
13492     // top and a single exit at the bottom.
13493     // The point of exit cannot be a branch out of the structured block.
13494     // longjmp() and throw() must not violate the entry/exit criteria.
13495     CS->getCapturedDecl()->setNothrow();
13496   }
13497 
13498   OMPLoopBasedDirective::HelperExprs B;
13499   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13500   // define the nested loops number.
13501   unsigned NestedLoopCount = checkOpenMPLoop(
13502       OMPD_parallel_master_taskloop, getCollapseNumberExpr(Clauses),
13503       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
13504       VarsWithImplicitDSA, B);
13505   if (NestedLoopCount == 0)
13506     return StmtError();
13507 
13508   assert((CurContext->isDependentContext() || B.builtAll()) &&
13509          "omp for loop exprs were not built");
13510 
13511   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13512   // The grainsize clause and num_tasks clause are mutually exclusive and may
13513   // not appear on the same taskloop directive.
13514   if (checkMutuallyExclusiveClauses(*this, Clauses,
13515                                     {OMPC_grainsize, OMPC_num_tasks}))
13516     return StmtError();
13517   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13518   // If a reduction clause is present on the taskloop directive, the nogroup
13519   // clause must not be specified.
13520   if (checkReductionClauseWithNogroup(*this, Clauses))
13521     return StmtError();
13522 
13523   setFunctionHasBranchProtectedScope();
13524   return OMPParallelMasterTaskLoopDirective::Create(
13525       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
13526       DSAStack->isCancelRegion());
13527 }
13528 
13529 StmtResult Sema::ActOnOpenMPParallelMaskedTaskLoopDirective(
13530     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13531     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13532   if (!AStmt)
13533     return StmtError();
13534 
13535   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13536   auto *CS = cast<CapturedStmt>(AStmt);
13537   // 1.2.2 OpenMP Language Terminology
13538   // Structured block - An executable statement with a single entry at the
13539   // top and a single exit at the bottom.
13540   // The point of exit cannot be a branch out of the structured block.
13541   // longjmp() and throw() must not violate the entry/exit criteria.
13542   CS->getCapturedDecl()->setNothrow();
13543   for (int ThisCaptureLevel =
13544            getOpenMPCaptureLevels(OMPD_parallel_masked_taskloop);
13545        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13546     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13547     // 1.2.2 OpenMP Language Terminology
13548     // Structured block - An executable statement with a single entry at the
13549     // top and a single exit at the bottom.
13550     // The point of exit cannot be a branch out of the structured block.
13551     // longjmp() and throw() must not violate the entry/exit criteria.
13552     CS->getCapturedDecl()->setNothrow();
13553   }
13554 
13555   OMPLoopBasedDirective::HelperExprs B;
13556   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13557   // define the nested loops number.
13558   unsigned NestedLoopCount = checkOpenMPLoop(
13559       OMPD_parallel_masked_taskloop, getCollapseNumberExpr(Clauses),
13560       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
13561       VarsWithImplicitDSA, B);
13562   if (NestedLoopCount == 0)
13563     return StmtError();
13564 
13565   assert((CurContext->isDependentContext() || B.builtAll()) &&
13566          "omp for loop exprs were not built");
13567 
13568   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13569   // The grainsize clause and num_tasks clause are mutually exclusive and may
13570   // not appear on the same taskloop directive.
13571   if (checkMutuallyExclusiveClauses(*this, Clauses,
13572                                     {OMPC_grainsize, OMPC_num_tasks}))
13573     return StmtError();
13574   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13575   // If a reduction clause is present on the taskloop directive, the nogroup
13576   // clause must not be specified.
13577   if (checkReductionClauseWithNogroup(*this, Clauses))
13578     return StmtError();
13579 
13580   setFunctionHasBranchProtectedScope();
13581   return OMPParallelMaskedTaskLoopDirective::Create(
13582       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
13583       DSAStack->isCancelRegion());
13584 }
13585 
13586 StmtResult Sema::ActOnOpenMPParallelMasterTaskLoopSimdDirective(
13587     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13588     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13589   if (!AStmt)
13590     return StmtError();
13591 
13592   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13593   auto *CS = cast<CapturedStmt>(AStmt);
13594   // 1.2.2 OpenMP Language Terminology
13595   // Structured block - An executable statement with a single entry at the
13596   // top and a single exit at the bottom.
13597   // The point of exit cannot be a branch out of the structured block.
13598   // longjmp() and throw() must not violate the entry/exit criteria.
13599   CS->getCapturedDecl()->setNothrow();
13600   for (int ThisCaptureLevel =
13601            getOpenMPCaptureLevels(OMPD_parallel_master_taskloop_simd);
13602        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13603     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13604     // 1.2.2 OpenMP Language Terminology
13605     // Structured block - An executable statement with a single entry at the
13606     // top and a single exit at the bottom.
13607     // The point of exit cannot be a branch out of the structured block.
13608     // longjmp() and throw() must not violate the entry/exit criteria.
13609     CS->getCapturedDecl()->setNothrow();
13610   }
13611 
13612   OMPLoopBasedDirective::HelperExprs B;
13613   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13614   // define the nested loops number.
13615   unsigned NestedLoopCount = checkOpenMPLoop(
13616       OMPD_parallel_master_taskloop_simd, getCollapseNumberExpr(Clauses),
13617       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
13618       VarsWithImplicitDSA, B);
13619   if (NestedLoopCount == 0)
13620     return StmtError();
13621 
13622   assert((CurContext->isDependentContext() || B.builtAll()) &&
13623          "omp for loop exprs were not built");
13624 
13625   if (!CurContext->isDependentContext()) {
13626     // Finalize the clauses that need pre-built expressions for CodeGen.
13627     for (OMPClause *C : Clauses) {
13628       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13629         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13630                                      B.NumIterations, *this, CurScope,
13631                                      DSAStack))
13632           return StmtError();
13633     }
13634   }
13635 
13636   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13637   // The grainsize clause and num_tasks clause are mutually exclusive and may
13638   // not appear on the same taskloop directive.
13639   if (checkMutuallyExclusiveClauses(*this, Clauses,
13640                                     {OMPC_grainsize, OMPC_num_tasks}))
13641     return StmtError();
13642   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13643   // If a reduction clause is present on the taskloop directive, the nogroup
13644   // clause must not be specified.
13645   if (checkReductionClauseWithNogroup(*this, Clauses))
13646     return StmtError();
13647   if (checkSimdlenSafelenSpecified(*this, Clauses))
13648     return StmtError();
13649 
13650   setFunctionHasBranchProtectedScope();
13651   return OMPParallelMasterTaskLoopSimdDirective::Create(
13652       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
13653 }
13654 
13655 StmtResult Sema::ActOnOpenMPParallelMaskedTaskLoopSimdDirective(
13656     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13657     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13658   if (!AStmt)
13659     return StmtError();
13660 
13661   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13662   auto *CS = cast<CapturedStmt>(AStmt);
13663   // 1.2.2 OpenMP Language Terminology
13664   // Structured block - An executable statement with a single entry at the
13665   // top and a single exit at the bottom.
13666   // The point of exit cannot be a branch out of the structured block.
13667   // longjmp() and throw() must not violate the entry/exit criteria.
13668   CS->getCapturedDecl()->setNothrow();
13669   for (int ThisCaptureLevel =
13670            getOpenMPCaptureLevels(OMPD_parallel_masked_taskloop_simd);
13671        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13672     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13673     // 1.2.2 OpenMP Language Terminology
13674     // Structured block - An executable statement with a single entry at the
13675     // top and a single exit at the bottom.
13676     // The point of exit cannot be a branch out of the structured block.
13677     // longjmp() and throw() must not violate the entry/exit criteria.
13678     CS->getCapturedDecl()->setNothrow();
13679   }
13680 
13681   OMPLoopBasedDirective::HelperExprs B;
13682   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13683   // define the nested loops number.
13684   unsigned NestedLoopCount = checkOpenMPLoop(
13685       OMPD_parallel_masked_taskloop_simd, getCollapseNumberExpr(Clauses),
13686       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
13687       VarsWithImplicitDSA, B);
13688   if (NestedLoopCount == 0)
13689     return StmtError();
13690 
13691   assert((CurContext->isDependentContext() || B.builtAll()) &&
13692          "omp for loop exprs were not built");
13693 
13694   if (!CurContext->isDependentContext()) {
13695     // Finalize the clauses that need pre-built expressions for CodeGen.
13696     for (OMPClause *C : Clauses) {
13697       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13698         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13699                                      B.NumIterations, *this, CurScope,
13700                                      DSAStack))
13701           return StmtError();
13702     }
13703   }
13704 
13705   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13706   // The grainsize clause and num_tasks clause are mutually exclusive and may
13707   // not appear on the same taskloop directive.
13708   if (checkMutuallyExclusiveClauses(*this, Clauses,
13709                                     {OMPC_grainsize, OMPC_num_tasks}))
13710     return StmtError();
13711   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13712   // If a reduction clause is present on the taskloop directive, the nogroup
13713   // clause must not be specified.
13714   if (checkReductionClauseWithNogroup(*this, Clauses))
13715     return StmtError();
13716   if (checkSimdlenSafelenSpecified(*this, Clauses))
13717     return StmtError();
13718 
13719   setFunctionHasBranchProtectedScope();
13720   return OMPParallelMaskedTaskLoopSimdDirective::Create(
13721       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
13722 }
13723 
13724 StmtResult Sema::ActOnOpenMPDistributeDirective(
13725     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13726     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13727   if (!AStmt)
13728     return StmtError();
13729 
13730   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13731   OMPLoopBasedDirective::HelperExprs B;
13732   // In presence of clause 'collapse' with number of loops, it will
13733   // define the nested loops number.
13734   unsigned NestedLoopCount =
13735       checkOpenMPLoop(OMPD_distribute, getCollapseNumberExpr(Clauses),
13736                       nullptr /*ordered not a clause on distribute*/, AStmt,
13737                       *this, *DSAStack, VarsWithImplicitDSA, B);
13738   if (NestedLoopCount == 0)
13739     return StmtError();
13740 
13741   assert((CurContext->isDependentContext() || B.builtAll()) &&
13742          "omp for loop exprs were not built");
13743 
13744   setFunctionHasBranchProtectedScope();
13745   return OMPDistributeDirective::Create(Context, StartLoc, EndLoc,
13746                                         NestedLoopCount, Clauses, AStmt, B);
13747 }
13748 
13749 StmtResult Sema::ActOnOpenMPDistributeParallelForDirective(
13750     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13751     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13752   if (!AStmt)
13753     return StmtError();
13754 
13755   auto *CS = cast<CapturedStmt>(AStmt);
13756   // 1.2.2 OpenMP Language Terminology
13757   // Structured block - An executable statement with a single entry at the
13758   // top and a single exit at the bottom.
13759   // The point of exit cannot be a branch out of the structured block.
13760   // longjmp() and throw() must not violate the entry/exit criteria.
13761   CS->getCapturedDecl()->setNothrow();
13762   for (int ThisCaptureLevel =
13763            getOpenMPCaptureLevels(OMPD_distribute_parallel_for);
13764        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13765     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13766     // 1.2.2 OpenMP Language Terminology
13767     // Structured block - An executable statement with a single entry at the
13768     // top and a single exit at the bottom.
13769     // The point of exit cannot be a branch out of the structured block.
13770     // longjmp() and throw() must not violate the entry/exit criteria.
13771     CS->getCapturedDecl()->setNothrow();
13772   }
13773 
13774   OMPLoopBasedDirective::HelperExprs B;
13775   // In presence of clause 'collapse' with number of loops, it will
13776   // define the nested loops number.
13777   unsigned NestedLoopCount = checkOpenMPLoop(
13778       OMPD_distribute_parallel_for, getCollapseNumberExpr(Clauses),
13779       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
13780       VarsWithImplicitDSA, B);
13781   if (NestedLoopCount == 0)
13782     return StmtError();
13783 
13784   assert((CurContext->isDependentContext() || B.builtAll()) &&
13785          "omp for loop exprs were not built");
13786 
13787   setFunctionHasBranchProtectedScope();
13788   return OMPDistributeParallelForDirective::Create(
13789       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
13790       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
13791 }
13792 
13793 StmtResult Sema::ActOnOpenMPDistributeParallelForSimdDirective(
13794     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13795     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13796   if (!AStmt)
13797     return StmtError();
13798 
13799   auto *CS = cast<CapturedStmt>(AStmt);
13800   // 1.2.2 OpenMP Language Terminology
13801   // Structured block - An executable statement with a single entry at the
13802   // top and a single exit at the bottom.
13803   // The point of exit cannot be a branch out of the structured block.
13804   // longjmp() and throw() must not violate the entry/exit criteria.
13805   CS->getCapturedDecl()->setNothrow();
13806   for (int ThisCaptureLevel =
13807            getOpenMPCaptureLevels(OMPD_distribute_parallel_for_simd);
13808        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13809     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13810     // 1.2.2 OpenMP Language Terminology
13811     // Structured block - An executable statement with a single entry at the
13812     // top and a single exit at the bottom.
13813     // The point of exit cannot be a branch out of the structured block.
13814     // longjmp() and throw() must not violate the entry/exit criteria.
13815     CS->getCapturedDecl()->setNothrow();
13816   }
13817 
13818   OMPLoopBasedDirective::HelperExprs B;
13819   // In presence of clause 'collapse' with number of loops, it will
13820   // define the nested loops number.
13821   unsigned NestedLoopCount = checkOpenMPLoop(
13822       OMPD_distribute_parallel_for_simd, getCollapseNumberExpr(Clauses),
13823       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
13824       VarsWithImplicitDSA, B);
13825   if (NestedLoopCount == 0)
13826     return StmtError();
13827 
13828   assert((CurContext->isDependentContext() || B.builtAll()) &&
13829          "omp for loop exprs were not built");
13830 
13831   if (!CurContext->isDependentContext()) {
13832     // Finalize the clauses that need pre-built expressions for CodeGen.
13833     for (OMPClause *C : Clauses) {
13834       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13835         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13836                                      B.NumIterations, *this, CurScope,
13837                                      DSAStack))
13838           return StmtError();
13839     }
13840   }
13841 
13842   if (checkSimdlenSafelenSpecified(*this, Clauses))
13843     return StmtError();
13844 
13845   setFunctionHasBranchProtectedScope();
13846   return OMPDistributeParallelForSimdDirective::Create(
13847       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
13848 }
13849 
13850 StmtResult Sema::ActOnOpenMPDistributeSimdDirective(
13851     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13852     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13853   if (!AStmt)
13854     return StmtError();
13855 
13856   auto *CS = cast<CapturedStmt>(AStmt);
13857   // 1.2.2 OpenMP Language Terminology
13858   // Structured block - An executable statement with a single entry at the
13859   // top and a single exit at the bottom.
13860   // The point of exit cannot be a branch out of the structured block.
13861   // longjmp() and throw() must not violate the entry/exit criteria.
13862   CS->getCapturedDecl()->setNothrow();
13863   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_distribute_simd);
13864        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13865     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13866     // 1.2.2 OpenMP Language Terminology
13867     // Structured block - An executable statement with a single entry at the
13868     // top and a single exit at the bottom.
13869     // The point of exit cannot be a branch out of the structured block.
13870     // longjmp() and throw() must not violate the entry/exit criteria.
13871     CS->getCapturedDecl()->setNothrow();
13872   }
13873 
13874   OMPLoopBasedDirective::HelperExprs B;
13875   // In presence of clause 'collapse' with number of loops, it will
13876   // define the nested loops number.
13877   unsigned NestedLoopCount =
13878       checkOpenMPLoop(OMPD_distribute_simd, getCollapseNumberExpr(Clauses),
13879                       nullptr /*ordered not a clause on distribute*/, CS, *this,
13880                       *DSAStack, VarsWithImplicitDSA, B);
13881   if (NestedLoopCount == 0)
13882     return StmtError();
13883 
13884   assert((CurContext->isDependentContext() || B.builtAll()) &&
13885          "omp for loop exprs were not built");
13886 
13887   if (!CurContext->isDependentContext()) {
13888     // Finalize the clauses that need pre-built expressions for CodeGen.
13889     for (OMPClause *C : Clauses) {
13890       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13891         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13892                                      B.NumIterations, *this, CurScope,
13893                                      DSAStack))
13894           return StmtError();
13895     }
13896   }
13897 
13898   if (checkSimdlenSafelenSpecified(*this, Clauses))
13899     return StmtError();
13900 
13901   setFunctionHasBranchProtectedScope();
13902   return OMPDistributeSimdDirective::Create(Context, StartLoc, EndLoc,
13903                                             NestedLoopCount, Clauses, AStmt, B);
13904 }
13905 
13906 StmtResult Sema::ActOnOpenMPTargetParallelForSimdDirective(
13907     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13908     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13909   if (!AStmt)
13910     return StmtError();
13911 
13912   auto *CS = cast<CapturedStmt>(AStmt);
13913   // 1.2.2 OpenMP Language Terminology
13914   // Structured block - An executable statement with a single entry at the
13915   // top and a single exit at the bottom.
13916   // The point of exit cannot be a branch out of the structured block.
13917   // longjmp() and throw() must not violate the entry/exit criteria.
13918   CS->getCapturedDecl()->setNothrow();
13919   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_parallel_for);
13920        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13921     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13922     // 1.2.2 OpenMP Language Terminology
13923     // Structured block - An executable statement with a single entry at the
13924     // top and a single exit at the bottom.
13925     // The point of exit cannot be a branch out of the structured block.
13926     // longjmp() and throw() must not violate the entry/exit criteria.
13927     CS->getCapturedDecl()->setNothrow();
13928   }
13929 
13930   OMPLoopBasedDirective::HelperExprs B;
13931   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13932   // define the nested loops number.
13933   unsigned NestedLoopCount = checkOpenMPLoop(
13934       OMPD_target_parallel_for_simd, getCollapseNumberExpr(Clauses),
13935       getOrderedNumberExpr(Clauses), CS, *this, *DSAStack, VarsWithImplicitDSA,
13936       B);
13937   if (NestedLoopCount == 0)
13938     return StmtError();
13939 
13940   assert((CurContext->isDependentContext() || B.builtAll()) &&
13941          "omp target parallel for simd loop exprs were not built");
13942 
13943   if (!CurContext->isDependentContext()) {
13944     // Finalize the clauses that need pre-built expressions for CodeGen.
13945     for (OMPClause *C : Clauses) {
13946       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13947         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13948                                      B.NumIterations, *this, CurScope,
13949                                      DSAStack))
13950           return StmtError();
13951     }
13952   }
13953   if (checkSimdlenSafelenSpecified(*this, Clauses))
13954     return StmtError();
13955 
13956   setFunctionHasBranchProtectedScope();
13957   return OMPTargetParallelForSimdDirective::Create(
13958       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
13959 }
13960 
13961 StmtResult Sema::ActOnOpenMPTargetSimdDirective(
13962     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13963     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13964   if (!AStmt)
13965     return StmtError();
13966 
13967   auto *CS = cast<CapturedStmt>(AStmt);
13968   // 1.2.2 OpenMP Language Terminology
13969   // Structured block - An executable statement with a single entry at the
13970   // top and a single exit at the bottom.
13971   // The point of exit cannot be a branch out of the structured block.
13972   // longjmp() and throw() must not violate the entry/exit criteria.
13973   CS->getCapturedDecl()->setNothrow();
13974   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_simd);
13975        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13976     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13977     // 1.2.2 OpenMP Language Terminology
13978     // Structured block - An executable statement with a single entry at the
13979     // top and a single exit at the bottom.
13980     // The point of exit cannot be a branch out of the structured block.
13981     // longjmp() and throw() must not violate the entry/exit criteria.
13982     CS->getCapturedDecl()->setNothrow();
13983   }
13984 
13985   OMPLoopBasedDirective::HelperExprs B;
13986   // In presence of clause 'collapse' with number of loops, it will define the
13987   // nested loops number.
13988   unsigned NestedLoopCount =
13989       checkOpenMPLoop(OMPD_target_simd, getCollapseNumberExpr(Clauses),
13990                       getOrderedNumberExpr(Clauses), CS, *this, *DSAStack,
13991                       VarsWithImplicitDSA, B);
13992   if (NestedLoopCount == 0)
13993     return StmtError();
13994 
13995   assert((CurContext->isDependentContext() || B.builtAll()) &&
13996          "omp target simd loop exprs were not built");
13997 
13998   if (!CurContext->isDependentContext()) {
13999     // Finalize the clauses that need pre-built expressions for CodeGen.
14000     for (OMPClause *C : Clauses) {
14001       if (auto *LC = dyn_cast<OMPLinearClause>(C))
14002         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
14003                                      B.NumIterations, *this, CurScope,
14004                                      DSAStack))
14005           return StmtError();
14006     }
14007   }
14008 
14009   if (checkSimdlenSafelenSpecified(*this, Clauses))
14010     return StmtError();
14011 
14012   setFunctionHasBranchProtectedScope();
14013   return OMPTargetSimdDirective::Create(Context, StartLoc, EndLoc,
14014                                         NestedLoopCount, Clauses, AStmt, B);
14015 }
14016 
14017 StmtResult Sema::ActOnOpenMPTeamsDistributeDirective(
14018     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14019     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14020   if (!AStmt)
14021     return StmtError();
14022 
14023   auto *CS = cast<CapturedStmt>(AStmt);
14024   // 1.2.2 OpenMP Language Terminology
14025   // Structured block - An executable statement with a single entry at the
14026   // top and a single exit at the bottom.
14027   // The point of exit cannot be a branch out of the structured block.
14028   // longjmp() and throw() must not violate the entry/exit criteria.
14029   CS->getCapturedDecl()->setNothrow();
14030   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_teams_distribute);
14031        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14032     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14033     // 1.2.2 OpenMP Language Terminology
14034     // Structured block - An executable statement with a single entry at the
14035     // top and a single exit at the bottom.
14036     // The point of exit cannot be a branch out of the structured block.
14037     // longjmp() and throw() must not violate the entry/exit criteria.
14038     CS->getCapturedDecl()->setNothrow();
14039   }
14040 
14041   OMPLoopBasedDirective::HelperExprs B;
14042   // In presence of clause 'collapse' with number of loops, it will
14043   // define the nested loops number.
14044   unsigned NestedLoopCount =
14045       checkOpenMPLoop(OMPD_teams_distribute, getCollapseNumberExpr(Clauses),
14046                       nullptr /*ordered not a clause on distribute*/, CS, *this,
14047                       *DSAStack, VarsWithImplicitDSA, B);
14048   if (NestedLoopCount == 0)
14049     return StmtError();
14050 
14051   assert((CurContext->isDependentContext() || B.builtAll()) &&
14052          "omp teams distribute loop exprs were not built");
14053 
14054   setFunctionHasBranchProtectedScope();
14055 
14056   DSAStack->setParentTeamsRegionLoc(StartLoc);
14057 
14058   return OMPTeamsDistributeDirective::Create(
14059       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
14060 }
14061 
14062 StmtResult Sema::ActOnOpenMPTeamsDistributeSimdDirective(
14063     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14064     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14065   if (!AStmt)
14066     return StmtError();
14067 
14068   auto *CS = cast<CapturedStmt>(AStmt);
14069   // 1.2.2 OpenMP Language Terminology
14070   // Structured block - An executable statement with a single entry at the
14071   // top and a single exit at the bottom.
14072   // The point of exit cannot be a branch out of the structured block.
14073   // longjmp() and throw() must not violate the entry/exit criteria.
14074   CS->getCapturedDecl()->setNothrow();
14075   for (int ThisCaptureLevel =
14076            getOpenMPCaptureLevels(OMPD_teams_distribute_simd);
14077        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14078     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14079     // 1.2.2 OpenMP Language Terminology
14080     // Structured block - An executable statement with a single entry at the
14081     // top and a single exit at the bottom.
14082     // The point of exit cannot be a branch out of the structured block.
14083     // longjmp() and throw() must not violate the entry/exit criteria.
14084     CS->getCapturedDecl()->setNothrow();
14085   }
14086 
14087   OMPLoopBasedDirective::HelperExprs B;
14088   // In presence of clause 'collapse' with number of loops, it will
14089   // define the nested loops number.
14090   unsigned NestedLoopCount = checkOpenMPLoop(
14091       OMPD_teams_distribute_simd, getCollapseNumberExpr(Clauses),
14092       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
14093       VarsWithImplicitDSA, B);
14094 
14095   if (NestedLoopCount == 0)
14096     return StmtError();
14097 
14098   assert((CurContext->isDependentContext() || B.builtAll()) &&
14099          "omp teams distribute simd loop exprs were not built");
14100 
14101   if (!CurContext->isDependentContext()) {
14102     // Finalize the clauses that need pre-built expressions for CodeGen.
14103     for (OMPClause *C : Clauses) {
14104       if (auto *LC = dyn_cast<OMPLinearClause>(C))
14105         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
14106                                      B.NumIterations, *this, CurScope,
14107                                      DSAStack))
14108           return StmtError();
14109     }
14110   }
14111 
14112   if (checkSimdlenSafelenSpecified(*this, Clauses))
14113     return StmtError();
14114 
14115   setFunctionHasBranchProtectedScope();
14116 
14117   DSAStack->setParentTeamsRegionLoc(StartLoc);
14118 
14119   return OMPTeamsDistributeSimdDirective::Create(
14120       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
14121 }
14122 
14123 StmtResult Sema::ActOnOpenMPTeamsDistributeParallelForSimdDirective(
14124     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14125     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14126   if (!AStmt)
14127     return StmtError();
14128 
14129   auto *CS = cast<CapturedStmt>(AStmt);
14130   // 1.2.2 OpenMP Language Terminology
14131   // Structured block - An executable statement with a single entry at the
14132   // top and a single exit at the bottom.
14133   // The point of exit cannot be a branch out of the structured block.
14134   // longjmp() and throw() must not violate the entry/exit criteria.
14135   CS->getCapturedDecl()->setNothrow();
14136 
14137   for (int ThisCaptureLevel =
14138            getOpenMPCaptureLevels(OMPD_teams_distribute_parallel_for_simd);
14139        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14140     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14141     // 1.2.2 OpenMP Language Terminology
14142     // Structured block - An executable statement with a single entry at the
14143     // top and a single exit at the bottom.
14144     // The point of exit cannot be a branch out of the structured block.
14145     // longjmp() and throw() must not violate the entry/exit criteria.
14146     CS->getCapturedDecl()->setNothrow();
14147   }
14148 
14149   OMPLoopBasedDirective::HelperExprs B;
14150   // In presence of clause 'collapse' with number of loops, it will
14151   // define the nested loops number.
14152   unsigned NestedLoopCount = checkOpenMPLoop(
14153       OMPD_teams_distribute_parallel_for_simd, getCollapseNumberExpr(Clauses),
14154       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
14155       VarsWithImplicitDSA, B);
14156 
14157   if (NestedLoopCount == 0)
14158     return StmtError();
14159 
14160   assert((CurContext->isDependentContext() || B.builtAll()) &&
14161          "omp for loop exprs were not built");
14162 
14163   if (!CurContext->isDependentContext()) {
14164     // Finalize the clauses that need pre-built expressions for CodeGen.
14165     for (OMPClause *C : Clauses) {
14166       if (auto *LC = dyn_cast<OMPLinearClause>(C))
14167         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
14168                                      B.NumIterations, *this, CurScope,
14169                                      DSAStack))
14170           return StmtError();
14171     }
14172   }
14173 
14174   if (checkSimdlenSafelenSpecified(*this, Clauses))
14175     return StmtError();
14176 
14177   setFunctionHasBranchProtectedScope();
14178 
14179   DSAStack->setParentTeamsRegionLoc(StartLoc);
14180 
14181   return OMPTeamsDistributeParallelForSimdDirective::Create(
14182       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
14183 }
14184 
14185 StmtResult Sema::ActOnOpenMPTeamsDistributeParallelForDirective(
14186     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14187     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14188   if (!AStmt)
14189     return StmtError();
14190 
14191   auto *CS = cast<CapturedStmt>(AStmt);
14192   // 1.2.2 OpenMP Language Terminology
14193   // Structured block - An executable statement with a single entry at the
14194   // top and a single exit at the bottom.
14195   // The point of exit cannot be a branch out of the structured block.
14196   // longjmp() and throw() must not violate the entry/exit criteria.
14197   CS->getCapturedDecl()->setNothrow();
14198 
14199   for (int ThisCaptureLevel =
14200            getOpenMPCaptureLevels(OMPD_teams_distribute_parallel_for);
14201        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14202     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14203     // 1.2.2 OpenMP Language Terminology
14204     // Structured block - An executable statement with a single entry at the
14205     // top and a single exit at the bottom.
14206     // The point of exit cannot be a branch out of the structured block.
14207     // longjmp() and throw() must not violate the entry/exit criteria.
14208     CS->getCapturedDecl()->setNothrow();
14209   }
14210 
14211   OMPLoopBasedDirective::HelperExprs B;
14212   // In presence of clause 'collapse' with number of loops, it will
14213   // define the nested loops number.
14214   unsigned NestedLoopCount = checkOpenMPLoop(
14215       OMPD_teams_distribute_parallel_for, getCollapseNumberExpr(Clauses),
14216       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
14217       VarsWithImplicitDSA, B);
14218 
14219   if (NestedLoopCount == 0)
14220     return StmtError();
14221 
14222   assert((CurContext->isDependentContext() || B.builtAll()) &&
14223          "omp for loop exprs were not built");
14224 
14225   setFunctionHasBranchProtectedScope();
14226 
14227   DSAStack->setParentTeamsRegionLoc(StartLoc);
14228 
14229   return OMPTeamsDistributeParallelForDirective::Create(
14230       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
14231       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
14232 }
14233 
14234 StmtResult Sema::ActOnOpenMPTargetTeamsDirective(ArrayRef<OMPClause *> Clauses,
14235                                                  Stmt *AStmt,
14236                                                  SourceLocation StartLoc,
14237                                                  SourceLocation EndLoc) {
14238   if (!AStmt)
14239     return StmtError();
14240 
14241   auto *CS = cast<CapturedStmt>(AStmt);
14242   // 1.2.2 OpenMP Language Terminology
14243   // Structured block - An executable statement with a single entry at the
14244   // top and a single exit at the bottom.
14245   // The point of exit cannot be a branch out of the structured block.
14246   // longjmp() and throw() must not violate the entry/exit criteria.
14247   CS->getCapturedDecl()->setNothrow();
14248 
14249   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_teams);
14250        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14251     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14252     // 1.2.2 OpenMP Language Terminology
14253     // Structured block - An executable statement with a single entry at the
14254     // top and a single exit at the bottom.
14255     // The point of exit cannot be a branch out of the structured block.
14256     // longjmp() and throw() must not violate the entry/exit criteria.
14257     CS->getCapturedDecl()->setNothrow();
14258   }
14259   setFunctionHasBranchProtectedScope();
14260 
14261   return OMPTargetTeamsDirective::Create(Context, StartLoc, EndLoc, Clauses,
14262                                          AStmt);
14263 }
14264 
14265 StmtResult Sema::ActOnOpenMPTargetTeamsDistributeDirective(
14266     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14267     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14268   if (!AStmt)
14269     return StmtError();
14270 
14271   auto *CS = cast<CapturedStmt>(AStmt);
14272   // 1.2.2 OpenMP Language Terminology
14273   // Structured block - An executable statement with a single entry at the
14274   // top and a single exit at the bottom.
14275   // The point of exit cannot be a branch out of the structured block.
14276   // longjmp() and throw() must not violate the entry/exit criteria.
14277   CS->getCapturedDecl()->setNothrow();
14278   for (int ThisCaptureLevel =
14279            getOpenMPCaptureLevels(OMPD_target_teams_distribute);
14280        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14281     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14282     // 1.2.2 OpenMP Language Terminology
14283     // Structured block - An executable statement with a single entry at the
14284     // top and a single exit at the bottom.
14285     // The point of exit cannot be a branch out of the structured block.
14286     // longjmp() and throw() must not violate the entry/exit criteria.
14287     CS->getCapturedDecl()->setNothrow();
14288   }
14289 
14290   OMPLoopBasedDirective::HelperExprs B;
14291   // In presence of clause 'collapse' with number of loops, it will
14292   // define the nested loops number.
14293   unsigned NestedLoopCount = checkOpenMPLoop(
14294       OMPD_target_teams_distribute, getCollapseNumberExpr(Clauses),
14295       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
14296       VarsWithImplicitDSA, B);
14297   if (NestedLoopCount == 0)
14298     return StmtError();
14299 
14300   assert((CurContext->isDependentContext() || B.builtAll()) &&
14301          "omp target teams distribute loop exprs were not built");
14302 
14303   setFunctionHasBranchProtectedScope();
14304   return OMPTargetTeamsDistributeDirective::Create(
14305       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
14306 }
14307 
14308 StmtResult Sema::ActOnOpenMPTargetTeamsDistributeParallelForDirective(
14309     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14310     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14311   if (!AStmt)
14312     return StmtError();
14313 
14314   auto *CS = cast<CapturedStmt>(AStmt);
14315   // 1.2.2 OpenMP Language Terminology
14316   // Structured block - An executable statement with a single entry at the
14317   // top and a single exit at the bottom.
14318   // The point of exit cannot be a branch out of the structured block.
14319   // longjmp() and throw() must not violate the entry/exit criteria.
14320   CS->getCapturedDecl()->setNothrow();
14321   for (int ThisCaptureLevel =
14322            getOpenMPCaptureLevels(OMPD_target_teams_distribute_parallel_for);
14323        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14324     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14325     // 1.2.2 OpenMP Language Terminology
14326     // Structured block - An executable statement with a single entry at the
14327     // top and a single exit at the bottom.
14328     // The point of exit cannot be a branch out of the structured block.
14329     // longjmp() and throw() must not violate the entry/exit criteria.
14330     CS->getCapturedDecl()->setNothrow();
14331   }
14332 
14333   OMPLoopBasedDirective::HelperExprs B;
14334   // In presence of clause 'collapse' with number of loops, it will
14335   // define the nested loops number.
14336   unsigned NestedLoopCount = checkOpenMPLoop(
14337       OMPD_target_teams_distribute_parallel_for, getCollapseNumberExpr(Clauses),
14338       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
14339       VarsWithImplicitDSA, B);
14340   if (NestedLoopCount == 0)
14341     return StmtError();
14342 
14343   assert((CurContext->isDependentContext() || B.builtAll()) &&
14344          "omp target teams distribute parallel for loop exprs were not built");
14345 
14346   if (!CurContext->isDependentContext()) {
14347     // Finalize the clauses that need pre-built expressions for CodeGen.
14348     for (OMPClause *C : Clauses) {
14349       if (auto *LC = dyn_cast<OMPLinearClause>(C))
14350         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
14351                                      B.NumIterations, *this, CurScope,
14352                                      DSAStack))
14353           return StmtError();
14354     }
14355   }
14356 
14357   setFunctionHasBranchProtectedScope();
14358   return OMPTargetTeamsDistributeParallelForDirective::Create(
14359       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
14360       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
14361 }
14362 
14363 StmtResult Sema::ActOnOpenMPTargetTeamsDistributeParallelForSimdDirective(
14364     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14365     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14366   if (!AStmt)
14367     return StmtError();
14368 
14369   auto *CS = cast<CapturedStmt>(AStmt);
14370   // 1.2.2 OpenMP Language Terminology
14371   // Structured block - An executable statement with a single entry at the
14372   // top and a single exit at the bottom.
14373   // The point of exit cannot be a branch out of the structured block.
14374   // longjmp() and throw() must not violate the entry/exit criteria.
14375   CS->getCapturedDecl()->setNothrow();
14376   for (int ThisCaptureLevel = getOpenMPCaptureLevels(
14377            OMPD_target_teams_distribute_parallel_for_simd);
14378        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14379     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14380     // 1.2.2 OpenMP Language Terminology
14381     // Structured block - An executable statement with a single entry at the
14382     // top and a single exit at the bottom.
14383     // The point of exit cannot be a branch out of the structured block.
14384     // longjmp() and throw() must not violate the entry/exit criteria.
14385     CS->getCapturedDecl()->setNothrow();
14386   }
14387 
14388   OMPLoopBasedDirective::HelperExprs B;
14389   // In presence of clause 'collapse' with number of loops, it will
14390   // define the nested loops number.
14391   unsigned NestedLoopCount =
14392       checkOpenMPLoop(OMPD_target_teams_distribute_parallel_for_simd,
14393                       getCollapseNumberExpr(Clauses),
14394                       nullptr /*ordered not a clause on distribute*/, CS, *this,
14395                       *DSAStack, VarsWithImplicitDSA, B);
14396   if (NestedLoopCount == 0)
14397     return StmtError();
14398 
14399   assert((CurContext->isDependentContext() || B.builtAll()) &&
14400          "omp target teams distribute parallel for simd loop exprs were not "
14401          "built");
14402 
14403   if (!CurContext->isDependentContext()) {
14404     // Finalize the clauses that need pre-built expressions for CodeGen.
14405     for (OMPClause *C : Clauses) {
14406       if (auto *LC = dyn_cast<OMPLinearClause>(C))
14407         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
14408                                      B.NumIterations, *this, CurScope,
14409                                      DSAStack))
14410           return StmtError();
14411     }
14412   }
14413 
14414   if (checkSimdlenSafelenSpecified(*this, Clauses))
14415     return StmtError();
14416 
14417   setFunctionHasBranchProtectedScope();
14418   return OMPTargetTeamsDistributeParallelForSimdDirective::Create(
14419       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
14420 }
14421 
14422 StmtResult Sema::ActOnOpenMPTargetTeamsDistributeSimdDirective(
14423     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14424     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14425   if (!AStmt)
14426     return StmtError();
14427 
14428   auto *CS = cast<CapturedStmt>(AStmt);
14429   // 1.2.2 OpenMP Language Terminology
14430   // Structured block - An executable statement with a single entry at the
14431   // top and a single exit at the bottom.
14432   // The point of exit cannot be a branch out of the structured block.
14433   // longjmp() and throw() must not violate the entry/exit criteria.
14434   CS->getCapturedDecl()->setNothrow();
14435   for (int ThisCaptureLevel =
14436            getOpenMPCaptureLevels(OMPD_target_teams_distribute_simd);
14437        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14438     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14439     // 1.2.2 OpenMP Language Terminology
14440     // Structured block - An executable statement with a single entry at the
14441     // top and a single exit at the bottom.
14442     // The point of exit cannot be a branch out of the structured block.
14443     // longjmp() and throw() must not violate the entry/exit criteria.
14444     CS->getCapturedDecl()->setNothrow();
14445   }
14446 
14447   OMPLoopBasedDirective::HelperExprs B;
14448   // In presence of clause 'collapse' with number of loops, it will
14449   // define the nested loops number.
14450   unsigned NestedLoopCount = checkOpenMPLoop(
14451       OMPD_target_teams_distribute_simd, getCollapseNumberExpr(Clauses),
14452       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
14453       VarsWithImplicitDSA, B);
14454   if (NestedLoopCount == 0)
14455     return StmtError();
14456 
14457   assert((CurContext->isDependentContext() || B.builtAll()) &&
14458          "omp target teams distribute simd loop exprs were not built");
14459 
14460   if (!CurContext->isDependentContext()) {
14461     // Finalize the clauses that need pre-built expressions for CodeGen.
14462     for (OMPClause *C : Clauses) {
14463       if (auto *LC = dyn_cast<OMPLinearClause>(C))
14464         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
14465                                      B.NumIterations, *this, CurScope,
14466                                      DSAStack))
14467           return StmtError();
14468     }
14469   }
14470 
14471   if (checkSimdlenSafelenSpecified(*this, Clauses))
14472     return StmtError();
14473 
14474   setFunctionHasBranchProtectedScope();
14475   return OMPTargetTeamsDistributeSimdDirective::Create(
14476       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
14477 }
14478 
14479 bool Sema::checkTransformableLoopNest(
14480     OpenMPDirectiveKind Kind, Stmt *AStmt, int NumLoops,
14481     SmallVectorImpl<OMPLoopBasedDirective::HelperExprs> &LoopHelpers,
14482     Stmt *&Body,
14483     SmallVectorImpl<SmallVector<llvm::PointerUnion<Stmt *, Decl *>, 0>>
14484         &OriginalInits) {
14485   OriginalInits.emplace_back();
14486   bool Result = OMPLoopBasedDirective::doForAllLoops(
14487       AStmt->IgnoreContainers(), /*TryImperfectlyNestedLoops=*/false, NumLoops,
14488       [this, &LoopHelpers, &Body, &OriginalInits, Kind](unsigned Cnt,
14489                                                         Stmt *CurStmt) {
14490         VarsWithInheritedDSAType TmpDSA;
14491         unsigned SingleNumLoops =
14492             checkOpenMPLoop(Kind, nullptr, nullptr, CurStmt, *this, *DSAStack,
14493                             TmpDSA, LoopHelpers[Cnt]);
14494         if (SingleNumLoops == 0)
14495           return true;
14496         assert(SingleNumLoops == 1 && "Expect single loop iteration space");
14497         if (auto *For = dyn_cast<ForStmt>(CurStmt)) {
14498           OriginalInits.back().push_back(For->getInit());
14499           Body = For->getBody();
14500         } else {
14501           assert(isa<CXXForRangeStmt>(CurStmt) &&
14502                  "Expected canonical for or range-based for loops.");
14503           auto *CXXFor = cast<CXXForRangeStmt>(CurStmt);
14504           OriginalInits.back().push_back(CXXFor->getBeginStmt());
14505           Body = CXXFor->getBody();
14506         }
14507         OriginalInits.emplace_back();
14508         return false;
14509       },
14510       [&OriginalInits](OMPLoopBasedDirective *Transform) {
14511         Stmt *DependentPreInits;
14512         if (auto *Dir = dyn_cast<OMPTileDirective>(Transform))
14513           DependentPreInits = Dir->getPreInits();
14514         else if (auto *Dir = dyn_cast<OMPUnrollDirective>(Transform))
14515           DependentPreInits = Dir->getPreInits();
14516         else
14517           llvm_unreachable("Unhandled loop transformation");
14518         if (!DependentPreInits)
14519           return;
14520         llvm::append_range(OriginalInits.back(),
14521                            cast<DeclStmt>(DependentPreInits)->getDeclGroup());
14522       });
14523   assert(OriginalInits.back().empty() && "No preinit after innermost loop");
14524   OriginalInits.pop_back();
14525   return Result;
14526 }
14527 
14528 StmtResult Sema::ActOnOpenMPTileDirective(ArrayRef<OMPClause *> Clauses,
14529                                           Stmt *AStmt, SourceLocation StartLoc,
14530                                           SourceLocation EndLoc) {
14531   auto SizesClauses =
14532       OMPExecutableDirective::getClausesOfKind<OMPSizesClause>(Clauses);
14533   if (SizesClauses.empty()) {
14534     // A missing 'sizes' clause is already reported by the parser.
14535     return StmtError();
14536   }
14537   const OMPSizesClause *SizesClause = *SizesClauses.begin();
14538   unsigned NumLoops = SizesClause->getNumSizes();
14539 
14540   // Empty statement should only be possible if there already was an error.
14541   if (!AStmt)
14542     return StmtError();
14543 
14544   // Verify and diagnose loop nest.
14545   SmallVector<OMPLoopBasedDirective::HelperExprs, 4> LoopHelpers(NumLoops);
14546   Stmt *Body = nullptr;
14547   SmallVector<SmallVector<llvm::PointerUnion<Stmt *, Decl *>, 0>, 4>
14548       OriginalInits;
14549   if (!checkTransformableLoopNest(OMPD_tile, AStmt, NumLoops, LoopHelpers, Body,
14550                                   OriginalInits))
14551     return StmtError();
14552 
14553   // Delay tiling to when template is completely instantiated.
14554   if (CurContext->isDependentContext())
14555     return OMPTileDirective::Create(Context, StartLoc, EndLoc, Clauses,
14556                                     NumLoops, AStmt, nullptr, nullptr);
14557 
14558   SmallVector<Decl *, 4> PreInits;
14559 
14560   // Create iteration variables for the generated loops.
14561   SmallVector<VarDecl *, 4> FloorIndVars;
14562   SmallVector<VarDecl *, 4> TileIndVars;
14563   FloorIndVars.resize(NumLoops);
14564   TileIndVars.resize(NumLoops);
14565   for (unsigned I = 0; I < NumLoops; ++I) {
14566     OMPLoopBasedDirective::HelperExprs &LoopHelper = LoopHelpers[I];
14567 
14568     assert(LoopHelper.Counters.size() == 1 &&
14569            "Expect single-dimensional loop iteration space");
14570     auto *OrigCntVar = cast<DeclRefExpr>(LoopHelper.Counters.front());
14571     std::string OrigVarName = OrigCntVar->getNameInfo().getAsString();
14572     DeclRefExpr *IterVarRef = cast<DeclRefExpr>(LoopHelper.IterationVarRef);
14573     QualType CntTy = IterVarRef->getType();
14574 
14575     // Iteration variable for the floor (i.e. outer) loop.
14576     {
14577       std::string FloorCntName =
14578           (Twine(".floor_") + llvm::utostr(I) + ".iv." + OrigVarName).str();
14579       VarDecl *FloorCntDecl =
14580           buildVarDecl(*this, {}, CntTy, FloorCntName, nullptr, OrigCntVar);
14581       FloorIndVars[I] = FloorCntDecl;
14582     }
14583 
14584     // Iteration variable for the tile (i.e. inner) loop.
14585     {
14586       std::string TileCntName =
14587           (Twine(".tile_") + llvm::utostr(I) + ".iv." + OrigVarName).str();
14588 
14589       // Reuse the iteration variable created by checkOpenMPLoop. It is also
14590       // used by the expressions to derive the original iteration variable's
14591       // value from the logical iteration number.
14592       auto *TileCntDecl = cast<VarDecl>(IterVarRef->getDecl());
14593       TileCntDecl->setDeclName(&PP.getIdentifierTable().get(TileCntName));
14594       TileIndVars[I] = TileCntDecl;
14595     }
14596     for (auto &P : OriginalInits[I]) {
14597       if (auto *D = P.dyn_cast<Decl *>())
14598         PreInits.push_back(D);
14599       else if (auto *PI = dyn_cast_or_null<DeclStmt>(P.dyn_cast<Stmt *>()))
14600         PreInits.append(PI->decl_begin(), PI->decl_end());
14601     }
14602     if (auto *PI = cast_or_null<DeclStmt>(LoopHelper.PreInits))
14603       PreInits.append(PI->decl_begin(), PI->decl_end());
14604     // Gather declarations for the data members used as counters.
14605     for (Expr *CounterRef : LoopHelper.Counters) {
14606       auto *CounterDecl = cast<DeclRefExpr>(CounterRef)->getDecl();
14607       if (isa<OMPCapturedExprDecl>(CounterDecl))
14608         PreInits.push_back(CounterDecl);
14609     }
14610   }
14611 
14612   // Once the original iteration values are set, append the innermost body.
14613   Stmt *Inner = Body;
14614 
14615   // Create tile loops from the inside to the outside.
14616   for (int I = NumLoops - 1; I >= 0; --I) {
14617     OMPLoopBasedDirective::HelperExprs &LoopHelper = LoopHelpers[I];
14618     Expr *NumIterations = LoopHelper.NumIterations;
14619     auto *OrigCntVar = cast<DeclRefExpr>(LoopHelper.Counters[0]);
14620     QualType CntTy = OrigCntVar->getType();
14621     Expr *DimTileSize = SizesClause->getSizesRefs()[I];
14622     Scope *CurScope = getCurScope();
14623 
14624     // Commonly used variables.
14625     DeclRefExpr *TileIV = buildDeclRefExpr(*this, TileIndVars[I], CntTy,
14626                                            OrigCntVar->getExprLoc());
14627     DeclRefExpr *FloorIV = buildDeclRefExpr(*this, FloorIndVars[I], CntTy,
14628                                             OrigCntVar->getExprLoc());
14629 
14630     // For init-statement: auto .tile.iv = .floor.iv
14631     AddInitializerToDecl(TileIndVars[I], DefaultLvalueConversion(FloorIV).get(),
14632                          /*DirectInit=*/false);
14633     Decl *CounterDecl = TileIndVars[I];
14634     StmtResult InitStmt = new (Context)
14635         DeclStmt(DeclGroupRef::Create(Context, &CounterDecl, 1),
14636                  OrigCntVar->getBeginLoc(), OrigCntVar->getEndLoc());
14637     if (!InitStmt.isUsable())
14638       return StmtError();
14639 
14640     // For cond-expression: .tile.iv < min(.floor.iv + DimTileSize,
14641     // NumIterations)
14642     ExprResult EndOfTile = BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(),
14643                                       BO_Add, FloorIV, DimTileSize);
14644     if (!EndOfTile.isUsable())
14645       return StmtError();
14646     ExprResult IsPartialTile =
14647         BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(), BO_LT,
14648                    NumIterations, EndOfTile.get());
14649     if (!IsPartialTile.isUsable())
14650       return StmtError();
14651     ExprResult MinTileAndIterSpace = ActOnConditionalOp(
14652         LoopHelper.Cond->getBeginLoc(), LoopHelper.Cond->getEndLoc(),
14653         IsPartialTile.get(), NumIterations, EndOfTile.get());
14654     if (!MinTileAndIterSpace.isUsable())
14655       return StmtError();
14656     ExprResult CondExpr = BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(),
14657                                      BO_LT, TileIV, MinTileAndIterSpace.get());
14658     if (!CondExpr.isUsable())
14659       return StmtError();
14660 
14661     // For incr-statement: ++.tile.iv
14662     ExprResult IncrStmt =
14663         BuildUnaryOp(CurScope, LoopHelper.Inc->getExprLoc(), UO_PreInc, TileIV);
14664     if (!IncrStmt.isUsable())
14665       return StmtError();
14666 
14667     // Statements to set the original iteration variable's value from the
14668     // logical iteration number.
14669     // Generated for loop is:
14670     // Original_for_init;
14671     // for (auto .tile.iv = .floor.iv; .tile.iv < min(.floor.iv + DimTileSize,
14672     // NumIterations); ++.tile.iv) {
14673     //   Original_Body;
14674     //   Original_counter_update;
14675     // }
14676     // FIXME: If the innermost body is an loop itself, inserting these
14677     // statements stops it being recognized  as a perfectly nested loop (e.g.
14678     // for applying tiling again). If this is the case, sink the expressions
14679     // further into the inner loop.
14680     SmallVector<Stmt *, 4> BodyParts;
14681     BodyParts.append(LoopHelper.Updates.begin(), LoopHelper.Updates.end());
14682     BodyParts.push_back(Inner);
14683     Inner = CompoundStmt::Create(Context, BodyParts, FPOptionsOverride(),
14684                                  Inner->getBeginLoc(), Inner->getEndLoc());
14685     Inner = new (Context)
14686         ForStmt(Context, InitStmt.get(), CondExpr.get(), nullptr,
14687                 IncrStmt.get(), Inner, LoopHelper.Init->getBeginLoc(),
14688                 LoopHelper.Init->getBeginLoc(), LoopHelper.Inc->getEndLoc());
14689   }
14690 
14691   // Create floor loops from the inside to the outside.
14692   for (int I = NumLoops - 1; I >= 0; --I) {
14693     auto &LoopHelper = LoopHelpers[I];
14694     Expr *NumIterations = LoopHelper.NumIterations;
14695     DeclRefExpr *OrigCntVar = cast<DeclRefExpr>(LoopHelper.Counters[0]);
14696     QualType CntTy = OrigCntVar->getType();
14697     Expr *DimTileSize = SizesClause->getSizesRefs()[I];
14698     Scope *CurScope = getCurScope();
14699 
14700     // Commonly used variables.
14701     DeclRefExpr *FloorIV = buildDeclRefExpr(*this, FloorIndVars[I], CntTy,
14702                                             OrigCntVar->getExprLoc());
14703 
14704     // For init-statement: auto .floor.iv = 0
14705     AddInitializerToDecl(
14706         FloorIndVars[I],
14707         ActOnIntegerConstant(LoopHelper.Init->getExprLoc(), 0).get(),
14708         /*DirectInit=*/false);
14709     Decl *CounterDecl = FloorIndVars[I];
14710     StmtResult InitStmt = new (Context)
14711         DeclStmt(DeclGroupRef::Create(Context, &CounterDecl, 1),
14712                  OrigCntVar->getBeginLoc(), OrigCntVar->getEndLoc());
14713     if (!InitStmt.isUsable())
14714       return StmtError();
14715 
14716     // For cond-expression: .floor.iv < NumIterations
14717     ExprResult CondExpr = BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(),
14718                                      BO_LT, FloorIV, NumIterations);
14719     if (!CondExpr.isUsable())
14720       return StmtError();
14721 
14722     // For incr-statement: .floor.iv += DimTileSize
14723     ExprResult IncrStmt = BuildBinOp(CurScope, LoopHelper.Inc->getExprLoc(),
14724                                      BO_AddAssign, FloorIV, DimTileSize);
14725     if (!IncrStmt.isUsable())
14726       return StmtError();
14727 
14728     Inner = new (Context)
14729         ForStmt(Context, InitStmt.get(), CondExpr.get(), nullptr,
14730                 IncrStmt.get(), Inner, LoopHelper.Init->getBeginLoc(),
14731                 LoopHelper.Init->getBeginLoc(), LoopHelper.Inc->getEndLoc());
14732   }
14733 
14734   return OMPTileDirective::Create(Context, StartLoc, EndLoc, Clauses, NumLoops,
14735                                   AStmt, Inner,
14736                                   buildPreInits(Context, PreInits));
14737 }
14738 
14739 StmtResult Sema::ActOnOpenMPUnrollDirective(ArrayRef<OMPClause *> Clauses,
14740                                             Stmt *AStmt,
14741                                             SourceLocation StartLoc,
14742                                             SourceLocation EndLoc) {
14743   // Empty statement should only be possible if there already was an error.
14744   if (!AStmt)
14745     return StmtError();
14746 
14747   if (checkMutuallyExclusiveClauses(*this, Clauses, {OMPC_partial, OMPC_full}))
14748     return StmtError();
14749 
14750   const OMPFullClause *FullClause =
14751       OMPExecutableDirective::getSingleClause<OMPFullClause>(Clauses);
14752   const OMPPartialClause *PartialClause =
14753       OMPExecutableDirective::getSingleClause<OMPPartialClause>(Clauses);
14754   assert(!(FullClause && PartialClause) &&
14755          "mutual exclusivity must have been checked before");
14756 
14757   constexpr unsigned NumLoops = 1;
14758   Stmt *Body = nullptr;
14759   SmallVector<OMPLoopBasedDirective::HelperExprs, NumLoops> LoopHelpers(
14760       NumLoops);
14761   SmallVector<SmallVector<llvm::PointerUnion<Stmt *, Decl *>, 0>, NumLoops + 1>
14762       OriginalInits;
14763   if (!checkTransformableLoopNest(OMPD_unroll, AStmt, NumLoops, LoopHelpers,
14764                                   Body, OriginalInits))
14765     return StmtError();
14766 
14767   unsigned NumGeneratedLoops = PartialClause ? 1 : 0;
14768 
14769   // Delay unrolling to when template is completely instantiated.
14770   if (CurContext->isDependentContext())
14771     return OMPUnrollDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
14772                                       NumGeneratedLoops, nullptr, nullptr);
14773 
14774   OMPLoopBasedDirective::HelperExprs &LoopHelper = LoopHelpers.front();
14775 
14776   if (FullClause) {
14777     if (!VerifyPositiveIntegerConstantInClause(
14778              LoopHelper.NumIterations, OMPC_full, /*StrictlyPositive=*/false,
14779              /*SuppressExprDiags=*/true)
14780              .isUsable()) {
14781       Diag(AStmt->getBeginLoc(), diag::err_omp_unroll_full_variable_trip_count);
14782       Diag(FullClause->getBeginLoc(), diag::note_omp_directive_here)
14783           << "#pragma omp unroll full";
14784       return StmtError();
14785     }
14786   }
14787 
14788   // The generated loop may only be passed to other loop-associated directive
14789   // when a partial clause is specified. Without the requirement it is
14790   // sufficient to generate loop unroll metadata at code-generation.
14791   if (NumGeneratedLoops == 0)
14792     return OMPUnrollDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
14793                                       NumGeneratedLoops, nullptr, nullptr);
14794 
14795   // Otherwise, we need to provide a de-sugared/transformed AST that can be
14796   // associated with another loop directive.
14797   //
14798   // The canonical loop analysis return by checkTransformableLoopNest assumes
14799   // the following structure to be the same loop without transformations or
14800   // directives applied: \code OriginalInits; LoopHelper.PreInits;
14801   // LoopHelper.Counters;
14802   // for (; IV < LoopHelper.NumIterations; ++IV) {
14803   //   LoopHelper.Updates;
14804   //   Body;
14805   // }
14806   // \endcode
14807   // where IV is a variable declared and initialized to 0 in LoopHelper.PreInits
14808   // and referenced by LoopHelper.IterationVarRef.
14809   //
14810   // The unrolling directive transforms this into the following loop:
14811   // \code
14812   // OriginalInits;         \
14813   // LoopHelper.PreInits;    > NewPreInits
14814   // LoopHelper.Counters;   /
14815   // for (auto UIV = 0; UIV < LoopHelper.NumIterations; UIV+=Factor) {
14816   //   #pragma clang loop unroll_count(Factor)
14817   //   for (IV = UIV; IV < UIV + Factor && UIV < LoopHelper.NumIterations; ++IV)
14818   //   {
14819   //     LoopHelper.Updates;
14820   //     Body;
14821   //   }
14822   // }
14823   // \endcode
14824   // where UIV is a new logical iteration counter. IV must be the same VarDecl
14825   // as the original LoopHelper.IterationVarRef because LoopHelper.Updates
14826   // references it. If the partially unrolled loop is associated with another
14827   // loop directive (like an OMPForDirective), it will use checkOpenMPLoop to
14828   // analyze this loop, i.e. the outer loop must fulfill the constraints of an
14829   // OpenMP canonical loop. The inner loop is not an associable canonical loop
14830   // and only exists to defer its unrolling to LLVM's LoopUnroll instead of
14831   // doing it in the frontend (by adding loop metadata). NewPreInits becomes a
14832   // property of the OMPLoopBasedDirective instead of statements in
14833   // CompoundStatement. This is to allow the loop to become a non-outermost loop
14834   // of a canonical loop nest where these PreInits are emitted before the
14835   // outermost directive.
14836 
14837   // Determine the PreInit declarations.
14838   SmallVector<Decl *, 4> PreInits;
14839   assert(OriginalInits.size() == 1 &&
14840          "Expecting a single-dimensional loop iteration space");
14841   for (auto &P : OriginalInits[0]) {
14842     if (auto *D = P.dyn_cast<Decl *>())
14843       PreInits.push_back(D);
14844     else if (auto *PI = dyn_cast_or_null<DeclStmt>(P.dyn_cast<Stmt *>()))
14845       PreInits.append(PI->decl_begin(), PI->decl_end());
14846   }
14847   if (auto *PI = cast_or_null<DeclStmt>(LoopHelper.PreInits))
14848     PreInits.append(PI->decl_begin(), PI->decl_end());
14849   // Gather declarations for the data members used as counters.
14850   for (Expr *CounterRef : LoopHelper.Counters) {
14851     auto *CounterDecl = cast<DeclRefExpr>(CounterRef)->getDecl();
14852     if (isa<OMPCapturedExprDecl>(CounterDecl))
14853       PreInits.push_back(CounterDecl);
14854   }
14855 
14856   auto *IterationVarRef = cast<DeclRefExpr>(LoopHelper.IterationVarRef);
14857   QualType IVTy = IterationVarRef->getType();
14858   assert(LoopHelper.Counters.size() == 1 &&
14859          "Expecting a single-dimensional loop iteration space");
14860   auto *OrigVar = cast<DeclRefExpr>(LoopHelper.Counters.front());
14861 
14862   // Determine the unroll factor.
14863   uint64_t Factor;
14864   SourceLocation FactorLoc;
14865   if (Expr *FactorVal = PartialClause->getFactor()) {
14866     Factor = FactorVal->getIntegerConstantExpr(Context)->getZExtValue();
14867     FactorLoc = FactorVal->getExprLoc();
14868   } else {
14869     // TODO: Use a better profitability model.
14870     Factor = 2;
14871   }
14872   assert(Factor > 0 && "Expected positive unroll factor");
14873   auto MakeFactorExpr = [this, Factor, IVTy, FactorLoc]() {
14874     return IntegerLiteral::Create(
14875         Context, llvm::APInt(Context.getIntWidth(IVTy), Factor), IVTy,
14876         FactorLoc);
14877   };
14878 
14879   // Iteration variable SourceLocations.
14880   SourceLocation OrigVarLoc = OrigVar->getExprLoc();
14881   SourceLocation OrigVarLocBegin = OrigVar->getBeginLoc();
14882   SourceLocation OrigVarLocEnd = OrigVar->getEndLoc();
14883 
14884   // Internal variable names.
14885   std::string OrigVarName = OrigVar->getNameInfo().getAsString();
14886   std::string OuterIVName = (Twine(".unrolled.iv.") + OrigVarName).str();
14887   std::string InnerIVName = (Twine(".unroll_inner.iv.") + OrigVarName).str();
14888   std::string InnerTripCountName =
14889       (Twine(".unroll_inner.tripcount.") + OrigVarName).str();
14890 
14891   // Create the iteration variable for the unrolled loop.
14892   VarDecl *OuterIVDecl =
14893       buildVarDecl(*this, {}, IVTy, OuterIVName, nullptr, OrigVar);
14894   auto MakeOuterRef = [this, OuterIVDecl, IVTy, OrigVarLoc]() {
14895     return buildDeclRefExpr(*this, OuterIVDecl, IVTy, OrigVarLoc);
14896   };
14897 
14898   // Iteration variable for the inner loop: Reuse the iteration variable created
14899   // by checkOpenMPLoop.
14900   auto *InnerIVDecl = cast<VarDecl>(IterationVarRef->getDecl());
14901   InnerIVDecl->setDeclName(&PP.getIdentifierTable().get(InnerIVName));
14902   auto MakeInnerRef = [this, InnerIVDecl, IVTy, OrigVarLoc]() {
14903     return buildDeclRefExpr(*this, InnerIVDecl, IVTy, OrigVarLoc);
14904   };
14905 
14906   // Make a copy of the NumIterations expression for each use: By the AST
14907   // constraints, every expression object in a DeclContext must be unique.
14908   CaptureVars CopyTransformer(*this);
14909   auto MakeNumIterations = [&CopyTransformer, &LoopHelper]() -> Expr * {
14910     return AssertSuccess(
14911         CopyTransformer.TransformExpr(LoopHelper.NumIterations));
14912   };
14913 
14914   // Inner For init-statement: auto .unroll_inner.iv = .unrolled.iv
14915   ExprResult LValueConv = DefaultLvalueConversion(MakeOuterRef());
14916   AddInitializerToDecl(InnerIVDecl, LValueConv.get(), /*DirectInit=*/false);
14917   StmtResult InnerInit = new (Context)
14918       DeclStmt(DeclGroupRef(InnerIVDecl), OrigVarLocBegin, OrigVarLocEnd);
14919   if (!InnerInit.isUsable())
14920     return StmtError();
14921 
14922   // Inner For cond-expression:
14923   // \code
14924   //   .unroll_inner.iv < .unrolled.iv + Factor &&
14925   //   .unroll_inner.iv < NumIterations
14926   // \endcode
14927   // This conjunction of two conditions allows ScalarEvolution to derive the
14928   // maximum trip count of the inner loop.
14929   ExprResult EndOfTile = BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(),
14930                                     BO_Add, MakeOuterRef(), MakeFactorExpr());
14931   if (!EndOfTile.isUsable())
14932     return StmtError();
14933   ExprResult InnerCond1 = BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(),
14934                                      BO_LT, MakeInnerRef(), EndOfTile.get());
14935   if (!InnerCond1.isUsable())
14936     return StmtError();
14937   ExprResult InnerCond2 =
14938       BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(), BO_LT, MakeInnerRef(),
14939                  MakeNumIterations());
14940   if (!InnerCond2.isUsable())
14941     return StmtError();
14942   ExprResult InnerCond =
14943       BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(), BO_LAnd,
14944                  InnerCond1.get(), InnerCond2.get());
14945   if (!InnerCond.isUsable())
14946     return StmtError();
14947 
14948   // Inner For incr-statement: ++.unroll_inner.iv
14949   ExprResult InnerIncr = BuildUnaryOp(CurScope, LoopHelper.Inc->getExprLoc(),
14950                                       UO_PreInc, MakeInnerRef());
14951   if (!InnerIncr.isUsable())
14952     return StmtError();
14953 
14954   // Inner For statement.
14955   SmallVector<Stmt *> InnerBodyStmts;
14956   InnerBodyStmts.append(LoopHelper.Updates.begin(), LoopHelper.Updates.end());
14957   InnerBodyStmts.push_back(Body);
14958   CompoundStmt *InnerBody =
14959       CompoundStmt::Create(Context, InnerBodyStmts, FPOptionsOverride(),
14960                            Body->getBeginLoc(), Body->getEndLoc());
14961   ForStmt *InnerFor = new (Context)
14962       ForStmt(Context, InnerInit.get(), InnerCond.get(), nullptr,
14963               InnerIncr.get(), InnerBody, LoopHelper.Init->getBeginLoc(),
14964               LoopHelper.Init->getBeginLoc(), LoopHelper.Inc->getEndLoc());
14965 
14966   // Unroll metadata for the inner loop.
14967   // This needs to take into account the remainder portion of the unrolled loop,
14968   // hence `unroll(full)` does not apply here, even though the LoopUnroll pass
14969   // supports multiple loop exits. Instead, unroll using a factor equivalent to
14970   // the maximum trip count, which will also generate a remainder loop. Just
14971   // `unroll(enable)` (which could have been useful if the user has not
14972   // specified a concrete factor; even though the outer loop cannot be
14973   // influenced anymore, would avoid more code bloat than necessary) will refuse
14974   // the loop because "Won't unroll; remainder loop could not be generated when
14975   // assuming runtime trip count". Even if it did work, it must not choose a
14976   // larger unroll factor than the maximum loop length, or it would always just
14977   // execute the remainder loop.
14978   LoopHintAttr *UnrollHintAttr =
14979       LoopHintAttr::CreateImplicit(Context, LoopHintAttr::UnrollCount,
14980                                    LoopHintAttr::Numeric, MakeFactorExpr());
14981   AttributedStmt *InnerUnrolled =
14982       AttributedStmt::Create(Context, StartLoc, {UnrollHintAttr}, InnerFor);
14983 
14984   // Outer For init-statement: auto .unrolled.iv = 0
14985   AddInitializerToDecl(
14986       OuterIVDecl, ActOnIntegerConstant(LoopHelper.Init->getExprLoc(), 0).get(),
14987       /*DirectInit=*/false);
14988   StmtResult OuterInit = new (Context)
14989       DeclStmt(DeclGroupRef(OuterIVDecl), OrigVarLocBegin, OrigVarLocEnd);
14990   if (!OuterInit.isUsable())
14991     return StmtError();
14992 
14993   // Outer For cond-expression: .unrolled.iv < NumIterations
14994   ExprResult OuterConde =
14995       BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(), BO_LT, MakeOuterRef(),
14996                  MakeNumIterations());
14997   if (!OuterConde.isUsable())
14998     return StmtError();
14999 
15000   // Outer For incr-statement: .unrolled.iv += Factor
15001   ExprResult OuterIncr =
15002       BuildBinOp(CurScope, LoopHelper.Inc->getExprLoc(), BO_AddAssign,
15003                  MakeOuterRef(), MakeFactorExpr());
15004   if (!OuterIncr.isUsable())
15005     return StmtError();
15006 
15007   // Outer For statement.
15008   ForStmt *OuterFor = new (Context)
15009       ForStmt(Context, OuterInit.get(), OuterConde.get(), nullptr,
15010               OuterIncr.get(), InnerUnrolled, LoopHelper.Init->getBeginLoc(),
15011               LoopHelper.Init->getBeginLoc(), LoopHelper.Inc->getEndLoc());
15012 
15013   return OMPUnrollDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
15014                                     NumGeneratedLoops, OuterFor,
15015                                     buildPreInits(Context, PreInits));
15016 }
15017 
15018 OMPClause *Sema::ActOnOpenMPSingleExprClause(OpenMPClauseKind Kind, Expr *Expr,
15019                                              SourceLocation StartLoc,
15020                                              SourceLocation LParenLoc,
15021                                              SourceLocation EndLoc) {
15022   OMPClause *Res = nullptr;
15023   switch (Kind) {
15024   case OMPC_final:
15025     Res = ActOnOpenMPFinalClause(Expr, StartLoc, LParenLoc, EndLoc);
15026     break;
15027   case OMPC_num_threads:
15028     Res = ActOnOpenMPNumThreadsClause(Expr, StartLoc, LParenLoc, EndLoc);
15029     break;
15030   case OMPC_safelen:
15031     Res = ActOnOpenMPSafelenClause(Expr, StartLoc, LParenLoc, EndLoc);
15032     break;
15033   case OMPC_simdlen:
15034     Res = ActOnOpenMPSimdlenClause(Expr, StartLoc, LParenLoc, EndLoc);
15035     break;
15036   case OMPC_allocator:
15037     Res = ActOnOpenMPAllocatorClause(Expr, StartLoc, LParenLoc, EndLoc);
15038     break;
15039   case OMPC_collapse:
15040     Res = ActOnOpenMPCollapseClause(Expr, StartLoc, LParenLoc, EndLoc);
15041     break;
15042   case OMPC_ordered:
15043     Res = ActOnOpenMPOrderedClause(StartLoc, EndLoc, LParenLoc, Expr);
15044     break;
15045   case OMPC_num_teams:
15046     Res = ActOnOpenMPNumTeamsClause(Expr, StartLoc, LParenLoc, EndLoc);
15047     break;
15048   case OMPC_thread_limit:
15049     Res = ActOnOpenMPThreadLimitClause(Expr, StartLoc, LParenLoc, EndLoc);
15050     break;
15051   case OMPC_priority:
15052     Res = ActOnOpenMPPriorityClause(Expr, StartLoc, LParenLoc, EndLoc);
15053     break;
15054   case OMPC_grainsize:
15055     Res = ActOnOpenMPGrainsizeClause(Expr, StartLoc, LParenLoc, EndLoc);
15056     break;
15057   case OMPC_num_tasks:
15058     Res = ActOnOpenMPNumTasksClause(Expr, StartLoc, LParenLoc, EndLoc);
15059     break;
15060   case OMPC_hint:
15061     Res = ActOnOpenMPHintClause(Expr, StartLoc, LParenLoc, EndLoc);
15062     break;
15063   case OMPC_depobj:
15064     Res = ActOnOpenMPDepobjClause(Expr, StartLoc, LParenLoc, EndLoc);
15065     break;
15066   case OMPC_detach:
15067     Res = ActOnOpenMPDetachClause(Expr, StartLoc, LParenLoc, EndLoc);
15068     break;
15069   case OMPC_novariants:
15070     Res = ActOnOpenMPNovariantsClause(Expr, StartLoc, LParenLoc, EndLoc);
15071     break;
15072   case OMPC_nocontext:
15073     Res = ActOnOpenMPNocontextClause(Expr, StartLoc, LParenLoc, EndLoc);
15074     break;
15075   case OMPC_filter:
15076     Res = ActOnOpenMPFilterClause(Expr, StartLoc, LParenLoc, EndLoc);
15077     break;
15078   case OMPC_partial:
15079     Res = ActOnOpenMPPartialClause(Expr, StartLoc, LParenLoc, EndLoc);
15080     break;
15081   case OMPC_align:
15082     Res = ActOnOpenMPAlignClause(Expr, StartLoc, LParenLoc, EndLoc);
15083     break;
15084   case OMPC_device:
15085   case OMPC_if:
15086   case OMPC_default:
15087   case OMPC_proc_bind:
15088   case OMPC_schedule:
15089   case OMPC_private:
15090   case OMPC_firstprivate:
15091   case OMPC_lastprivate:
15092   case OMPC_shared:
15093   case OMPC_reduction:
15094   case OMPC_task_reduction:
15095   case OMPC_in_reduction:
15096   case OMPC_linear:
15097   case OMPC_aligned:
15098   case OMPC_copyin:
15099   case OMPC_copyprivate:
15100   case OMPC_nowait:
15101   case OMPC_untied:
15102   case OMPC_mergeable:
15103   case OMPC_threadprivate:
15104   case OMPC_sizes:
15105   case OMPC_allocate:
15106   case OMPC_flush:
15107   case OMPC_read:
15108   case OMPC_write:
15109   case OMPC_update:
15110   case OMPC_capture:
15111   case OMPC_compare:
15112   case OMPC_seq_cst:
15113   case OMPC_acq_rel:
15114   case OMPC_acquire:
15115   case OMPC_release:
15116   case OMPC_relaxed:
15117   case OMPC_depend:
15118   case OMPC_threads:
15119   case OMPC_simd:
15120   case OMPC_map:
15121   case OMPC_nogroup:
15122   case OMPC_dist_schedule:
15123   case OMPC_defaultmap:
15124   case OMPC_unknown:
15125   case OMPC_uniform:
15126   case OMPC_to:
15127   case OMPC_from:
15128   case OMPC_use_device_ptr:
15129   case OMPC_use_device_addr:
15130   case OMPC_is_device_ptr:
15131   case OMPC_unified_address:
15132   case OMPC_unified_shared_memory:
15133   case OMPC_reverse_offload:
15134   case OMPC_dynamic_allocators:
15135   case OMPC_atomic_default_mem_order:
15136   case OMPC_device_type:
15137   case OMPC_match:
15138   case OMPC_nontemporal:
15139   case OMPC_order:
15140   case OMPC_destroy:
15141   case OMPC_inclusive:
15142   case OMPC_exclusive:
15143   case OMPC_uses_allocators:
15144   case OMPC_affinity:
15145   case OMPC_when:
15146   case OMPC_bind:
15147   default:
15148     llvm_unreachable("Clause is not allowed.");
15149   }
15150   return Res;
15151 }
15152 
15153 // An OpenMP directive such as 'target parallel' has two captured regions:
15154 // for the 'target' and 'parallel' respectively.  This function returns
15155 // the region in which to capture expressions associated with a clause.
15156 // A return value of OMPD_unknown signifies that the expression should not
15157 // be captured.
15158 static OpenMPDirectiveKind getOpenMPCaptureRegionForClause(
15159     OpenMPDirectiveKind DKind, OpenMPClauseKind CKind, unsigned OpenMPVersion,
15160     OpenMPDirectiveKind NameModifier = OMPD_unknown) {
15161   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
15162   switch (CKind) {
15163   case OMPC_if:
15164     switch (DKind) {
15165     case OMPD_target_parallel_for_simd:
15166       if (OpenMPVersion >= 50 &&
15167           (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)) {
15168         CaptureRegion = OMPD_parallel;
15169         break;
15170       }
15171       LLVM_FALLTHROUGH;
15172     case OMPD_target_parallel:
15173     case OMPD_target_parallel_for:
15174     case OMPD_target_parallel_loop:
15175       // If this clause applies to the nested 'parallel' region, capture within
15176       // the 'target' region, otherwise do not capture.
15177       if (NameModifier == OMPD_unknown || NameModifier == OMPD_parallel)
15178         CaptureRegion = OMPD_target;
15179       break;
15180     case OMPD_target_teams_distribute_parallel_for_simd:
15181       if (OpenMPVersion >= 50 &&
15182           (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)) {
15183         CaptureRegion = OMPD_parallel;
15184         break;
15185       }
15186       LLVM_FALLTHROUGH;
15187     case OMPD_target_teams_distribute_parallel_for:
15188       // If this clause applies to the nested 'parallel' region, capture within
15189       // the 'teams' region, otherwise do not capture.
15190       if (NameModifier == OMPD_unknown || NameModifier == OMPD_parallel)
15191         CaptureRegion = OMPD_teams;
15192       break;
15193     case OMPD_teams_distribute_parallel_for_simd:
15194       if (OpenMPVersion >= 50 &&
15195           (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)) {
15196         CaptureRegion = OMPD_parallel;
15197         break;
15198       }
15199       LLVM_FALLTHROUGH;
15200     case OMPD_teams_distribute_parallel_for:
15201       CaptureRegion = OMPD_teams;
15202       break;
15203     case OMPD_target_update:
15204     case OMPD_target_enter_data:
15205     case OMPD_target_exit_data:
15206       CaptureRegion = OMPD_task;
15207       break;
15208     case OMPD_parallel_masked_taskloop:
15209       if (NameModifier == OMPD_unknown || NameModifier == OMPD_taskloop)
15210         CaptureRegion = OMPD_parallel;
15211       break;
15212     case OMPD_parallel_master_taskloop:
15213       if (NameModifier == OMPD_unknown || NameModifier == OMPD_taskloop)
15214         CaptureRegion = OMPD_parallel;
15215       break;
15216     case OMPD_parallel_masked_taskloop_simd:
15217       if ((OpenMPVersion <= 45 && NameModifier == OMPD_unknown) ||
15218           NameModifier == OMPD_taskloop) {
15219         CaptureRegion = OMPD_parallel;
15220         break;
15221       }
15222       if (OpenMPVersion <= 45)
15223         break;
15224       if (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)
15225         CaptureRegion = OMPD_taskloop;
15226       break;
15227     case OMPD_parallel_master_taskloop_simd:
15228       if ((OpenMPVersion <= 45 && NameModifier == OMPD_unknown) ||
15229           NameModifier == OMPD_taskloop) {
15230         CaptureRegion = OMPD_parallel;
15231         break;
15232       }
15233       if (OpenMPVersion <= 45)
15234         break;
15235       if (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)
15236         CaptureRegion = OMPD_taskloop;
15237       break;
15238     case OMPD_parallel_for_simd:
15239       if (OpenMPVersion <= 45)
15240         break;
15241       if (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)
15242         CaptureRegion = OMPD_parallel;
15243       break;
15244     case OMPD_taskloop_simd:
15245     case OMPD_master_taskloop_simd:
15246     case OMPD_masked_taskloop_simd:
15247       if (OpenMPVersion <= 45)
15248         break;
15249       if (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)
15250         CaptureRegion = OMPD_taskloop;
15251       break;
15252     case OMPD_distribute_parallel_for_simd:
15253       if (OpenMPVersion <= 45)
15254         break;
15255       if (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)
15256         CaptureRegion = OMPD_parallel;
15257       break;
15258     case OMPD_target_simd:
15259       if (OpenMPVersion >= 50 &&
15260           (NameModifier == OMPD_unknown || NameModifier == OMPD_simd))
15261         CaptureRegion = OMPD_target;
15262       break;
15263     case OMPD_teams_distribute_simd:
15264     case OMPD_target_teams_distribute_simd:
15265       if (OpenMPVersion >= 50 &&
15266           (NameModifier == OMPD_unknown || NameModifier == OMPD_simd))
15267         CaptureRegion = OMPD_teams;
15268       break;
15269     case OMPD_cancel:
15270     case OMPD_parallel:
15271     case OMPD_parallel_master:
15272     case OMPD_parallel_masked:
15273     case OMPD_parallel_sections:
15274     case OMPD_parallel_for:
15275     case OMPD_parallel_loop:
15276     case OMPD_target:
15277     case OMPD_target_teams:
15278     case OMPD_target_teams_distribute:
15279     case OMPD_target_teams_loop:
15280     case OMPD_distribute_parallel_for:
15281     case OMPD_task:
15282     case OMPD_taskloop:
15283     case OMPD_master_taskloop:
15284     case OMPD_masked_taskloop:
15285     case OMPD_target_data:
15286     case OMPD_simd:
15287     case OMPD_for_simd:
15288     case OMPD_distribute_simd:
15289       // Do not capture if-clause expressions.
15290       break;
15291     case OMPD_threadprivate:
15292     case OMPD_allocate:
15293     case OMPD_taskyield:
15294     case OMPD_barrier:
15295     case OMPD_taskwait:
15296     case OMPD_cancellation_point:
15297     case OMPD_flush:
15298     case OMPD_depobj:
15299     case OMPD_scan:
15300     case OMPD_declare_reduction:
15301     case OMPD_declare_mapper:
15302     case OMPD_declare_simd:
15303     case OMPD_declare_variant:
15304     case OMPD_begin_declare_variant:
15305     case OMPD_end_declare_variant:
15306     case OMPD_declare_target:
15307     case OMPD_end_declare_target:
15308     case OMPD_loop:
15309     case OMPD_teams_loop:
15310     case OMPD_teams:
15311     case OMPD_tile:
15312     case OMPD_unroll:
15313     case OMPD_for:
15314     case OMPD_sections:
15315     case OMPD_section:
15316     case OMPD_single:
15317     case OMPD_master:
15318     case OMPD_masked:
15319     case OMPD_critical:
15320     case OMPD_taskgroup:
15321     case OMPD_distribute:
15322     case OMPD_ordered:
15323     case OMPD_atomic:
15324     case OMPD_teams_distribute:
15325     case OMPD_requires:
15326     case OMPD_metadirective:
15327       llvm_unreachable("Unexpected OpenMP directive with if-clause");
15328     case OMPD_unknown:
15329     default:
15330       llvm_unreachable("Unknown OpenMP directive");
15331     }
15332     break;
15333   case OMPC_num_threads:
15334     switch (DKind) {
15335     case OMPD_target_parallel:
15336     case OMPD_target_parallel_for:
15337     case OMPD_target_parallel_for_simd:
15338     case OMPD_target_parallel_loop:
15339       CaptureRegion = OMPD_target;
15340       break;
15341     case OMPD_teams_distribute_parallel_for:
15342     case OMPD_teams_distribute_parallel_for_simd:
15343     case OMPD_target_teams_distribute_parallel_for:
15344     case OMPD_target_teams_distribute_parallel_for_simd:
15345       CaptureRegion = OMPD_teams;
15346       break;
15347     case OMPD_parallel:
15348     case OMPD_parallel_master:
15349     case OMPD_parallel_masked:
15350     case OMPD_parallel_sections:
15351     case OMPD_parallel_for:
15352     case OMPD_parallel_for_simd:
15353     case OMPD_parallel_loop:
15354     case OMPD_distribute_parallel_for:
15355     case OMPD_distribute_parallel_for_simd:
15356     case OMPD_parallel_master_taskloop:
15357     case OMPD_parallel_masked_taskloop:
15358     case OMPD_parallel_master_taskloop_simd:
15359     case OMPD_parallel_masked_taskloop_simd:
15360       // Do not capture num_threads-clause expressions.
15361       break;
15362     case OMPD_target_data:
15363     case OMPD_target_enter_data:
15364     case OMPD_target_exit_data:
15365     case OMPD_target_update:
15366     case OMPD_target:
15367     case OMPD_target_simd:
15368     case OMPD_target_teams:
15369     case OMPD_target_teams_distribute:
15370     case OMPD_target_teams_distribute_simd:
15371     case OMPD_cancel:
15372     case OMPD_task:
15373     case OMPD_taskloop:
15374     case OMPD_taskloop_simd:
15375     case OMPD_master_taskloop:
15376     case OMPD_masked_taskloop:
15377     case OMPD_master_taskloop_simd:
15378     case OMPD_masked_taskloop_simd:
15379     case OMPD_threadprivate:
15380     case OMPD_allocate:
15381     case OMPD_taskyield:
15382     case OMPD_barrier:
15383     case OMPD_taskwait:
15384     case OMPD_cancellation_point:
15385     case OMPD_flush:
15386     case OMPD_depobj:
15387     case OMPD_scan:
15388     case OMPD_declare_reduction:
15389     case OMPD_declare_mapper:
15390     case OMPD_declare_simd:
15391     case OMPD_declare_variant:
15392     case OMPD_begin_declare_variant:
15393     case OMPD_end_declare_variant:
15394     case OMPD_declare_target:
15395     case OMPD_end_declare_target:
15396     case OMPD_loop:
15397     case OMPD_teams_loop:
15398     case OMPD_target_teams_loop:
15399     case OMPD_teams:
15400     case OMPD_simd:
15401     case OMPD_tile:
15402     case OMPD_unroll:
15403     case OMPD_for:
15404     case OMPD_for_simd:
15405     case OMPD_sections:
15406     case OMPD_section:
15407     case OMPD_single:
15408     case OMPD_master:
15409     case OMPD_masked:
15410     case OMPD_critical:
15411     case OMPD_taskgroup:
15412     case OMPD_distribute:
15413     case OMPD_ordered:
15414     case OMPD_atomic:
15415     case OMPD_distribute_simd:
15416     case OMPD_teams_distribute:
15417     case OMPD_teams_distribute_simd:
15418     case OMPD_requires:
15419     case OMPD_metadirective:
15420       llvm_unreachable("Unexpected OpenMP directive with num_threads-clause");
15421     case OMPD_unknown:
15422     default:
15423       llvm_unreachable("Unknown OpenMP directive");
15424     }
15425     break;
15426   case OMPC_num_teams:
15427     switch (DKind) {
15428     case OMPD_target_teams:
15429     case OMPD_target_teams_distribute:
15430     case OMPD_target_teams_distribute_simd:
15431     case OMPD_target_teams_distribute_parallel_for:
15432     case OMPD_target_teams_distribute_parallel_for_simd:
15433     case OMPD_target_teams_loop:
15434       CaptureRegion = OMPD_target;
15435       break;
15436     case OMPD_teams_distribute_parallel_for:
15437     case OMPD_teams_distribute_parallel_for_simd:
15438     case OMPD_teams:
15439     case OMPD_teams_distribute:
15440     case OMPD_teams_distribute_simd:
15441     case OMPD_teams_loop:
15442       // Do not capture num_teams-clause expressions.
15443       break;
15444     case OMPD_distribute_parallel_for:
15445     case OMPD_distribute_parallel_for_simd:
15446     case OMPD_task:
15447     case OMPD_taskloop:
15448     case OMPD_taskloop_simd:
15449     case OMPD_master_taskloop:
15450     case OMPD_masked_taskloop:
15451     case OMPD_master_taskloop_simd:
15452     case OMPD_masked_taskloop_simd:
15453     case OMPD_parallel_master_taskloop:
15454     case OMPD_parallel_masked_taskloop:
15455     case OMPD_parallel_master_taskloop_simd:
15456     case OMPD_parallel_masked_taskloop_simd:
15457     case OMPD_target_data:
15458     case OMPD_target_enter_data:
15459     case OMPD_target_exit_data:
15460     case OMPD_target_update:
15461     case OMPD_cancel:
15462     case OMPD_parallel:
15463     case OMPD_parallel_master:
15464     case OMPD_parallel_masked:
15465     case OMPD_parallel_sections:
15466     case OMPD_parallel_for:
15467     case OMPD_parallel_for_simd:
15468     case OMPD_parallel_loop:
15469     case OMPD_target:
15470     case OMPD_target_simd:
15471     case OMPD_target_parallel:
15472     case OMPD_target_parallel_for:
15473     case OMPD_target_parallel_for_simd:
15474     case OMPD_target_parallel_loop:
15475     case OMPD_threadprivate:
15476     case OMPD_allocate:
15477     case OMPD_taskyield:
15478     case OMPD_barrier:
15479     case OMPD_taskwait:
15480     case OMPD_cancellation_point:
15481     case OMPD_flush:
15482     case OMPD_depobj:
15483     case OMPD_scan:
15484     case OMPD_declare_reduction:
15485     case OMPD_declare_mapper:
15486     case OMPD_declare_simd:
15487     case OMPD_declare_variant:
15488     case OMPD_begin_declare_variant:
15489     case OMPD_end_declare_variant:
15490     case OMPD_declare_target:
15491     case OMPD_end_declare_target:
15492     case OMPD_loop:
15493     case OMPD_simd:
15494     case OMPD_tile:
15495     case OMPD_unroll:
15496     case OMPD_for:
15497     case OMPD_for_simd:
15498     case OMPD_sections:
15499     case OMPD_section:
15500     case OMPD_single:
15501     case OMPD_master:
15502     case OMPD_masked:
15503     case OMPD_critical:
15504     case OMPD_taskgroup:
15505     case OMPD_distribute:
15506     case OMPD_ordered:
15507     case OMPD_atomic:
15508     case OMPD_distribute_simd:
15509     case OMPD_requires:
15510     case OMPD_metadirective:
15511       llvm_unreachable("Unexpected OpenMP directive with num_teams-clause");
15512     case OMPD_unknown:
15513     default:
15514       llvm_unreachable("Unknown OpenMP directive");
15515     }
15516     break;
15517   case OMPC_thread_limit:
15518     switch (DKind) {
15519     case OMPD_target_teams:
15520     case OMPD_target_teams_distribute:
15521     case OMPD_target_teams_distribute_simd:
15522     case OMPD_target_teams_distribute_parallel_for:
15523     case OMPD_target_teams_distribute_parallel_for_simd:
15524     case OMPD_target_teams_loop:
15525       CaptureRegion = OMPD_target;
15526       break;
15527     case OMPD_teams_distribute_parallel_for:
15528     case OMPD_teams_distribute_parallel_for_simd:
15529     case OMPD_teams:
15530     case OMPD_teams_distribute:
15531     case OMPD_teams_distribute_simd:
15532     case OMPD_teams_loop:
15533       // Do not capture thread_limit-clause expressions.
15534       break;
15535     case OMPD_distribute_parallel_for:
15536     case OMPD_distribute_parallel_for_simd:
15537     case OMPD_task:
15538     case OMPD_taskloop:
15539     case OMPD_taskloop_simd:
15540     case OMPD_master_taskloop:
15541     case OMPD_masked_taskloop:
15542     case OMPD_master_taskloop_simd:
15543     case OMPD_masked_taskloop_simd:
15544     case OMPD_parallel_master_taskloop:
15545     case OMPD_parallel_masked_taskloop:
15546     case OMPD_parallel_master_taskloop_simd:
15547     case OMPD_parallel_masked_taskloop_simd:
15548     case OMPD_target_data:
15549     case OMPD_target_enter_data:
15550     case OMPD_target_exit_data:
15551     case OMPD_target_update:
15552     case OMPD_cancel:
15553     case OMPD_parallel:
15554     case OMPD_parallel_master:
15555     case OMPD_parallel_masked:
15556     case OMPD_parallel_sections:
15557     case OMPD_parallel_for:
15558     case OMPD_parallel_for_simd:
15559     case OMPD_parallel_loop:
15560     case OMPD_target:
15561     case OMPD_target_simd:
15562     case OMPD_target_parallel:
15563     case OMPD_target_parallel_for:
15564     case OMPD_target_parallel_for_simd:
15565     case OMPD_target_parallel_loop:
15566     case OMPD_threadprivate:
15567     case OMPD_allocate:
15568     case OMPD_taskyield:
15569     case OMPD_barrier:
15570     case OMPD_taskwait:
15571     case OMPD_cancellation_point:
15572     case OMPD_flush:
15573     case OMPD_depobj:
15574     case OMPD_scan:
15575     case OMPD_declare_reduction:
15576     case OMPD_declare_mapper:
15577     case OMPD_declare_simd:
15578     case OMPD_declare_variant:
15579     case OMPD_begin_declare_variant:
15580     case OMPD_end_declare_variant:
15581     case OMPD_declare_target:
15582     case OMPD_end_declare_target:
15583     case OMPD_loop:
15584     case OMPD_simd:
15585     case OMPD_tile:
15586     case OMPD_unroll:
15587     case OMPD_for:
15588     case OMPD_for_simd:
15589     case OMPD_sections:
15590     case OMPD_section:
15591     case OMPD_single:
15592     case OMPD_master:
15593     case OMPD_masked:
15594     case OMPD_critical:
15595     case OMPD_taskgroup:
15596     case OMPD_distribute:
15597     case OMPD_ordered:
15598     case OMPD_atomic:
15599     case OMPD_distribute_simd:
15600     case OMPD_requires:
15601     case OMPD_metadirective:
15602       llvm_unreachable("Unexpected OpenMP directive with thread_limit-clause");
15603     case OMPD_unknown:
15604     default:
15605       llvm_unreachable("Unknown OpenMP directive");
15606     }
15607     break;
15608   case OMPC_schedule:
15609     switch (DKind) {
15610     case OMPD_parallel_for:
15611     case OMPD_parallel_for_simd:
15612     case OMPD_distribute_parallel_for:
15613     case OMPD_distribute_parallel_for_simd:
15614     case OMPD_teams_distribute_parallel_for:
15615     case OMPD_teams_distribute_parallel_for_simd:
15616     case OMPD_target_parallel_for:
15617     case OMPD_target_parallel_for_simd:
15618     case OMPD_target_teams_distribute_parallel_for:
15619     case OMPD_target_teams_distribute_parallel_for_simd:
15620       CaptureRegion = OMPD_parallel;
15621       break;
15622     case OMPD_for:
15623     case OMPD_for_simd:
15624       // Do not capture schedule-clause expressions.
15625       break;
15626     case OMPD_task:
15627     case OMPD_taskloop:
15628     case OMPD_taskloop_simd:
15629     case OMPD_master_taskloop:
15630     case OMPD_masked_taskloop:
15631     case OMPD_master_taskloop_simd:
15632     case OMPD_masked_taskloop_simd:
15633     case OMPD_parallel_master_taskloop:
15634     case OMPD_parallel_masked_taskloop:
15635     case OMPD_parallel_master_taskloop_simd:
15636     case OMPD_parallel_masked_taskloop_simd:
15637     case OMPD_target_data:
15638     case OMPD_target_enter_data:
15639     case OMPD_target_exit_data:
15640     case OMPD_target_update:
15641     case OMPD_teams:
15642     case OMPD_teams_distribute:
15643     case OMPD_teams_distribute_simd:
15644     case OMPD_target_teams_distribute:
15645     case OMPD_target_teams_distribute_simd:
15646     case OMPD_target:
15647     case OMPD_target_simd:
15648     case OMPD_target_parallel:
15649     case OMPD_cancel:
15650     case OMPD_parallel:
15651     case OMPD_parallel_master:
15652     case OMPD_parallel_masked:
15653     case OMPD_parallel_sections:
15654     case OMPD_threadprivate:
15655     case OMPD_allocate:
15656     case OMPD_taskyield:
15657     case OMPD_barrier:
15658     case OMPD_taskwait:
15659     case OMPD_cancellation_point:
15660     case OMPD_flush:
15661     case OMPD_depobj:
15662     case OMPD_scan:
15663     case OMPD_declare_reduction:
15664     case OMPD_declare_mapper:
15665     case OMPD_declare_simd:
15666     case OMPD_declare_variant:
15667     case OMPD_begin_declare_variant:
15668     case OMPD_end_declare_variant:
15669     case OMPD_declare_target:
15670     case OMPD_end_declare_target:
15671     case OMPD_loop:
15672     case OMPD_teams_loop:
15673     case OMPD_target_teams_loop:
15674     case OMPD_parallel_loop:
15675     case OMPD_target_parallel_loop:
15676     case OMPD_simd:
15677     case OMPD_tile:
15678     case OMPD_unroll:
15679     case OMPD_sections:
15680     case OMPD_section:
15681     case OMPD_single:
15682     case OMPD_master:
15683     case OMPD_masked:
15684     case OMPD_critical:
15685     case OMPD_taskgroup:
15686     case OMPD_distribute:
15687     case OMPD_ordered:
15688     case OMPD_atomic:
15689     case OMPD_distribute_simd:
15690     case OMPD_target_teams:
15691     case OMPD_requires:
15692     case OMPD_metadirective:
15693       llvm_unreachable("Unexpected OpenMP directive with schedule clause");
15694     case OMPD_unknown:
15695     default:
15696       llvm_unreachable("Unknown OpenMP directive");
15697     }
15698     break;
15699   case OMPC_dist_schedule:
15700     switch (DKind) {
15701     case OMPD_teams_distribute_parallel_for:
15702     case OMPD_teams_distribute_parallel_for_simd:
15703     case OMPD_teams_distribute:
15704     case OMPD_teams_distribute_simd:
15705     case OMPD_target_teams_distribute_parallel_for:
15706     case OMPD_target_teams_distribute_parallel_for_simd:
15707     case OMPD_target_teams_distribute:
15708     case OMPD_target_teams_distribute_simd:
15709       CaptureRegion = OMPD_teams;
15710       break;
15711     case OMPD_distribute_parallel_for:
15712     case OMPD_distribute_parallel_for_simd:
15713     case OMPD_distribute:
15714     case OMPD_distribute_simd:
15715       // Do not capture dist_schedule-clause expressions.
15716       break;
15717     case OMPD_parallel_for:
15718     case OMPD_parallel_for_simd:
15719     case OMPD_target_parallel_for_simd:
15720     case OMPD_target_parallel_for:
15721     case OMPD_task:
15722     case OMPD_taskloop:
15723     case OMPD_taskloop_simd:
15724     case OMPD_master_taskloop:
15725     case OMPD_masked_taskloop:
15726     case OMPD_master_taskloop_simd:
15727     case OMPD_masked_taskloop_simd:
15728     case OMPD_parallel_master_taskloop:
15729     case OMPD_parallel_masked_taskloop:
15730     case OMPD_parallel_master_taskloop_simd:
15731     case OMPD_parallel_masked_taskloop_simd:
15732     case OMPD_target_data:
15733     case OMPD_target_enter_data:
15734     case OMPD_target_exit_data:
15735     case OMPD_target_update:
15736     case OMPD_teams:
15737     case OMPD_target:
15738     case OMPD_target_simd:
15739     case OMPD_target_parallel:
15740     case OMPD_cancel:
15741     case OMPD_parallel:
15742     case OMPD_parallel_master:
15743     case OMPD_parallel_masked:
15744     case OMPD_parallel_sections:
15745     case OMPD_threadprivate:
15746     case OMPD_allocate:
15747     case OMPD_taskyield:
15748     case OMPD_barrier:
15749     case OMPD_taskwait:
15750     case OMPD_cancellation_point:
15751     case OMPD_flush:
15752     case OMPD_depobj:
15753     case OMPD_scan:
15754     case OMPD_declare_reduction:
15755     case OMPD_declare_mapper:
15756     case OMPD_declare_simd:
15757     case OMPD_declare_variant:
15758     case OMPD_begin_declare_variant:
15759     case OMPD_end_declare_variant:
15760     case OMPD_declare_target:
15761     case OMPD_end_declare_target:
15762     case OMPD_loop:
15763     case OMPD_teams_loop:
15764     case OMPD_target_teams_loop:
15765     case OMPD_parallel_loop:
15766     case OMPD_target_parallel_loop:
15767     case OMPD_simd:
15768     case OMPD_tile:
15769     case OMPD_unroll:
15770     case OMPD_for:
15771     case OMPD_for_simd:
15772     case OMPD_sections:
15773     case OMPD_section:
15774     case OMPD_single:
15775     case OMPD_master:
15776     case OMPD_masked:
15777     case OMPD_critical:
15778     case OMPD_taskgroup:
15779     case OMPD_ordered:
15780     case OMPD_atomic:
15781     case OMPD_target_teams:
15782     case OMPD_requires:
15783     case OMPD_metadirective:
15784       llvm_unreachable("Unexpected OpenMP directive with dist_schedule clause");
15785     case OMPD_unknown:
15786     default:
15787       llvm_unreachable("Unknown OpenMP directive");
15788     }
15789     break;
15790   case OMPC_device:
15791     switch (DKind) {
15792     case OMPD_target_update:
15793     case OMPD_target_enter_data:
15794     case OMPD_target_exit_data:
15795     case OMPD_target:
15796     case OMPD_target_simd:
15797     case OMPD_target_teams:
15798     case OMPD_target_parallel:
15799     case OMPD_target_teams_distribute:
15800     case OMPD_target_teams_distribute_simd:
15801     case OMPD_target_parallel_for:
15802     case OMPD_target_parallel_for_simd:
15803     case OMPD_target_parallel_loop:
15804     case OMPD_target_teams_distribute_parallel_for:
15805     case OMPD_target_teams_distribute_parallel_for_simd:
15806     case OMPD_target_teams_loop:
15807     case OMPD_dispatch:
15808       CaptureRegion = OMPD_task;
15809       break;
15810     case OMPD_target_data:
15811     case OMPD_interop:
15812       // Do not capture device-clause expressions.
15813       break;
15814     case OMPD_teams_distribute_parallel_for:
15815     case OMPD_teams_distribute_parallel_for_simd:
15816     case OMPD_teams:
15817     case OMPD_teams_distribute:
15818     case OMPD_teams_distribute_simd:
15819     case OMPD_distribute_parallel_for:
15820     case OMPD_distribute_parallel_for_simd:
15821     case OMPD_task:
15822     case OMPD_taskloop:
15823     case OMPD_taskloop_simd:
15824     case OMPD_master_taskloop:
15825     case OMPD_masked_taskloop:
15826     case OMPD_master_taskloop_simd:
15827     case OMPD_masked_taskloop_simd:
15828     case OMPD_parallel_master_taskloop:
15829     case OMPD_parallel_masked_taskloop:
15830     case OMPD_parallel_master_taskloop_simd:
15831     case OMPD_parallel_masked_taskloop_simd:
15832     case OMPD_cancel:
15833     case OMPD_parallel:
15834     case OMPD_parallel_master:
15835     case OMPD_parallel_masked:
15836     case OMPD_parallel_sections:
15837     case OMPD_parallel_for:
15838     case OMPD_parallel_for_simd:
15839     case OMPD_threadprivate:
15840     case OMPD_allocate:
15841     case OMPD_taskyield:
15842     case OMPD_barrier:
15843     case OMPD_taskwait:
15844     case OMPD_cancellation_point:
15845     case OMPD_flush:
15846     case OMPD_depobj:
15847     case OMPD_scan:
15848     case OMPD_declare_reduction:
15849     case OMPD_declare_mapper:
15850     case OMPD_declare_simd:
15851     case OMPD_declare_variant:
15852     case OMPD_begin_declare_variant:
15853     case OMPD_end_declare_variant:
15854     case OMPD_declare_target:
15855     case OMPD_end_declare_target:
15856     case OMPD_loop:
15857     case OMPD_teams_loop:
15858     case OMPD_parallel_loop:
15859     case OMPD_simd:
15860     case OMPD_tile:
15861     case OMPD_unroll:
15862     case OMPD_for:
15863     case OMPD_for_simd:
15864     case OMPD_sections:
15865     case OMPD_section:
15866     case OMPD_single:
15867     case OMPD_master:
15868     case OMPD_masked:
15869     case OMPD_critical:
15870     case OMPD_taskgroup:
15871     case OMPD_distribute:
15872     case OMPD_ordered:
15873     case OMPD_atomic:
15874     case OMPD_distribute_simd:
15875     case OMPD_requires:
15876     case OMPD_metadirective:
15877       llvm_unreachable("Unexpected OpenMP directive with device-clause");
15878     case OMPD_unknown:
15879     default:
15880       llvm_unreachable("Unknown OpenMP directive");
15881     }
15882     break;
15883   case OMPC_grainsize:
15884   case OMPC_num_tasks:
15885   case OMPC_final:
15886   case OMPC_priority:
15887     switch (DKind) {
15888     case OMPD_task:
15889     case OMPD_taskloop:
15890     case OMPD_taskloop_simd:
15891     case OMPD_master_taskloop:
15892     case OMPD_masked_taskloop:
15893     case OMPD_master_taskloop_simd:
15894     case OMPD_masked_taskloop_simd:
15895       break;
15896     case OMPD_parallel_masked_taskloop:
15897     case OMPD_parallel_masked_taskloop_simd:
15898     case OMPD_parallel_master_taskloop:
15899     case OMPD_parallel_master_taskloop_simd:
15900       CaptureRegion = OMPD_parallel;
15901       break;
15902     case OMPD_target_update:
15903     case OMPD_target_enter_data:
15904     case OMPD_target_exit_data:
15905     case OMPD_target:
15906     case OMPD_target_simd:
15907     case OMPD_target_teams:
15908     case OMPD_target_parallel:
15909     case OMPD_target_teams_distribute:
15910     case OMPD_target_teams_distribute_simd:
15911     case OMPD_target_parallel_for:
15912     case OMPD_target_parallel_for_simd:
15913     case OMPD_target_teams_distribute_parallel_for:
15914     case OMPD_target_teams_distribute_parallel_for_simd:
15915     case OMPD_target_data:
15916     case OMPD_teams_distribute_parallel_for:
15917     case OMPD_teams_distribute_parallel_for_simd:
15918     case OMPD_teams:
15919     case OMPD_teams_distribute:
15920     case OMPD_teams_distribute_simd:
15921     case OMPD_distribute_parallel_for:
15922     case OMPD_distribute_parallel_for_simd:
15923     case OMPD_cancel:
15924     case OMPD_parallel:
15925     case OMPD_parallel_master:
15926     case OMPD_parallel_masked:
15927     case OMPD_parallel_sections:
15928     case OMPD_parallel_for:
15929     case OMPD_parallel_for_simd:
15930     case OMPD_threadprivate:
15931     case OMPD_allocate:
15932     case OMPD_taskyield:
15933     case OMPD_barrier:
15934     case OMPD_taskwait:
15935     case OMPD_cancellation_point:
15936     case OMPD_flush:
15937     case OMPD_depobj:
15938     case OMPD_scan:
15939     case OMPD_declare_reduction:
15940     case OMPD_declare_mapper:
15941     case OMPD_declare_simd:
15942     case OMPD_declare_variant:
15943     case OMPD_begin_declare_variant:
15944     case OMPD_end_declare_variant:
15945     case OMPD_declare_target:
15946     case OMPD_end_declare_target:
15947     case OMPD_loop:
15948     case OMPD_teams_loop:
15949     case OMPD_target_teams_loop:
15950     case OMPD_parallel_loop:
15951     case OMPD_target_parallel_loop:
15952     case OMPD_simd:
15953     case OMPD_tile:
15954     case OMPD_unroll:
15955     case OMPD_for:
15956     case OMPD_for_simd:
15957     case OMPD_sections:
15958     case OMPD_section:
15959     case OMPD_single:
15960     case OMPD_master:
15961     case OMPD_masked:
15962     case OMPD_critical:
15963     case OMPD_taskgroup:
15964     case OMPD_distribute:
15965     case OMPD_ordered:
15966     case OMPD_atomic:
15967     case OMPD_distribute_simd:
15968     case OMPD_requires:
15969     case OMPD_metadirective:
15970       llvm_unreachable("Unexpected OpenMP directive with grainsize-clause");
15971     case OMPD_unknown:
15972     default:
15973       llvm_unreachable("Unknown OpenMP directive");
15974     }
15975     break;
15976   case OMPC_novariants:
15977   case OMPC_nocontext:
15978     switch (DKind) {
15979     case OMPD_dispatch:
15980       CaptureRegion = OMPD_task;
15981       break;
15982     default:
15983       llvm_unreachable("Unexpected OpenMP directive");
15984     }
15985     break;
15986   case OMPC_filter:
15987     // Do not capture filter-clause expressions.
15988     break;
15989   case OMPC_when:
15990     if (DKind == OMPD_metadirective) {
15991       CaptureRegion = OMPD_metadirective;
15992     } else if (DKind == OMPD_unknown) {
15993       llvm_unreachable("Unknown OpenMP directive");
15994     } else {
15995       llvm_unreachable("Unexpected OpenMP directive with when clause");
15996     }
15997     break;
15998   case OMPC_firstprivate:
15999   case OMPC_lastprivate:
16000   case OMPC_reduction:
16001   case OMPC_task_reduction:
16002   case OMPC_in_reduction:
16003   case OMPC_linear:
16004   case OMPC_default:
16005   case OMPC_proc_bind:
16006   case OMPC_safelen:
16007   case OMPC_simdlen:
16008   case OMPC_sizes:
16009   case OMPC_allocator:
16010   case OMPC_collapse:
16011   case OMPC_private:
16012   case OMPC_shared:
16013   case OMPC_aligned:
16014   case OMPC_copyin:
16015   case OMPC_copyprivate:
16016   case OMPC_ordered:
16017   case OMPC_nowait:
16018   case OMPC_untied:
16019   case OMPC_mergeable:
16020   case OMPC_threadprivate:
16021   case OMPC_allocate:
16022   case OMPC_flush:
16023   case OMPC_depobj:
16024   case OMPC_read:
16025   case OMPC_write:
16026   case OMPC_update:
16027   case OMPC_capture:
16028   case OMPC_compare:
16029   case OMPC_seq_cst:
16030   case OMPC_acq_rel:
16031   case OMPC_acquire:
16032   case OMPC_release:
16033   case OMPC_relaxed:
16034   case OMPC_depend:
16035   case OMPC_threads:
16036   case OMPC_simd:
16037   case OMPC_map:
16038   case OMPC_nogroup:
16039   case OMPC_hint:
16040   case OMPC_defaultmap:
16041   case OMPC_unknown:
16042   case OMPC_uniform:
16043   case OMPC_to:
16044   case OMPC_from:
16045   case OMPC_use_device_ptr:
16046   case OMPC_use_device_addr:
16047   case OMPC_is_device_ptr:
16048   case OMPC_unified_address:
16049   case OMPC_unified_shared_memory:
16050   case OMPC_reverse_offload:
16051   case OMPC_dynamic_allocators:
16052   case OMPC_atomic_default_mem_order:
16053   case OMPC_device_type:
16054   case OMPC_match:
16055   case OMPC_nontemporal:
16056   case OMPC_order:
16057   case OMPC_destroy:
16058   case OMPC_detach:
16059   case OMPC_inclusive:
16060   case OMPC_exclusive:
16061   case OMPC_uses_allocators:
16062   case OMPC_affinity:
16063   case OMPC_bind:
16064   default:
16065     llvm_unreachable("Unexpected OpenMP clause.");
16066   }
16067   return CaptureRegion;
16068 }
16069 
16070 OMPClause *Sema::ActOnOpenMPIfClause(OpenMPDirectiveKind NameModifier,
16071                                      Expr *Condition, SourceLocation StartLoc,
16072                                      SourceLocation LParenLoc,
16073                                      SourceLocation NameModifierLoc,
16074                                      SourceLocation ColonLoc,
16075                                      SourceLocation EndLoc) {
16076   Expr *ValExpr = Condition;
16077   Stmt *HelperValStmt = nullptr;
16078   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
16079   if (!Condition->isValueDependent() && !Condition->isTypeDependent() &&
16080       !Condition->isInstantiationDependent() &&
16081       !Condition->containsUnexpandedParameterPack()) {
16082     ExprResult Val = CheckBooleanCondition(StartLoc, Condition);
16083     if (Val.isInvalid())
16084       return nullptr;
16085 
16086     ValExpr = Val.get();
16087 
16088     OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
16089     CaptureRegion = getOpenMPCaptureRegionForClause(
16090         DKind, OMPC_if, LangOpts.OpenMP, NameModifier);
16091     if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
16092       ValExpr = MakeFullExpr(ValExpr).get();
16093       llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
16094       ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
16095       HelperValStmt = buildPreInits(Context, Captures);
16096     }
16097   }
16098 
16099   return new (Context)
16100       OMPIfClause(NameModifier, ValExpr, HelperValStmt, CaptureRegion, StartLoc,
16101                   LParenLoc, NameModifierLoc, ColonLoc, EndLoc);
16102 }
16103 
16104 OMPClause *Sema::ActOnOpenMPFinalClause(Expr *Condition,
16105                                         SourceLocation StartLoc,
16106                                         SourceLocation LParenLoc,
16107                                         SourceLocation EndLoc) {
16108   Expr *ValExpr = Condition;
16109   Stmt *HelperValStmt = nullptr;
16110   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
16111   if (!Condition->isValueDependent() && !Condition->isTypeDependent() &&
16112       !Condition->isInstantiationDependent() &&
16113       !Condition->containsUnexpandedParameterPack()) {
16114     ExprResult Val = CheckBooleanCondition(StartLoc, Condition);
16115     if (Val.isInvalid())
16116       return nullptr;
16117 
16118     ValExpr = MakeFullExpr(Val.get()).get();
16119 
16120     OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
16121     CaptureRegion =
16122         getOpenMPCaptureRegionForClause(DKind, OMPC_final, LangOpts.OpenMP);
16123     if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
16124       ValExpr = MakeFullExpr(ValExpr).get();
16125       llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
16126       ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
16127       HelperValStmt = buildPreInits(Context, Captures);
16128     }
16129   }
16130 
16131   return new (Context) OMPFinalClause(ValExpr, HelperValStmt, CaptureRegion,
16132                                       StartLoc, LParenLoc, EndLoc);
16133 }
16134 
16135 ExprResult Sema::PerformOpenMPImplicitIntegerConversion(SourceLocation Loc,
16136                                                         Expr *Op) {
16137   if (!Op)
16138     return ExprError();
16139 
16140   class IntConvertDiagnoser : public ICEConvertDiagnoser {
16141   public:
16142     IntConvertDiagnoser()
16143         : ICEConvertDiagnoser(/*AllowScopedEnumerations*/ false, false, true) {}
16144     SemaDiagnosticBuilder diagnoseNotInt(Sema &S, SourceLocation Loc,
16145                                          QualType T) override {
16146       return S.Diag(Loc, diag::err_omp_not_integral) << T;
16147     }
16148     SemaDiagnosticBuilder diagnoseIncomplete(Sema &S, SourceLocation Loc,
16149                                              QualType T) override {
16150       return S.Diag(Loc, diag::err_omp_incomplete_type) << T;
16151     }
16152     SemaDiagnosticBuilder diagnoseExplicitConv(Sema &S, SourceLocation Loc,
16153                                                QualType T,
16154                                                QualType ConvTy) override {
16155       return S.Diag(Loc, diag::err_omp_explicit_conversion) << T << ConvTy;
16156     }
16157     SemaDiagnosticBuilder noteExplicitConv(Sema &S, CXXConversionDecl *Conv,
16158                                            QualType ConvTy) override {
16159       return S.Diag(Conv->getLocation(), diag::note_omp_conversion_here)
16160              << ConvTy->isEnumeralType() << ConvTy;
16161     }
16162     SemaDiagnosticBuilder diagnoseAmbiguous(Sema &S, SourceLocation Loc,
16163                                             QualType T) override {
16164       return S.Diag(Loc, diag::err_omp_ambiguous_conversion) << T;
16165     }
16166     SemaDiagnosticBuilder noteAmbiguous(Sema &S, CXXConversionDecl *Conv,
16167                                         QualType ConvTy) override {
16168       return S.Diag(Conv->getLocation(), diag::note_omp_conversion_here)
16169              << ConvTy->isEnumeralType() << ConvTy;
16170     }
16171     SemaDiagnosticBuilder diagnoseConversion(Sema &, SourceLocation, QualType,
16172                                              QualType) override {
16173       llvm_unreachable("conversion functions are permitted");
16174     }
16175   } ConvertDiagnoser;
16176   return PerformContextualImplicitConversion(Loc, Op, ConvertDiagnoser);
16177 }
16178 
16179 static bool
16180 isNonNegativeIntegerValue(Expr *&ValExpr, Sema &SemaRef, OpenMPClauseKind CKind,
16181                           bool StrictlyPositive, bool BuildCapture = false,
16182                           OpenMPDirectiveKind DKind = OMPD_unknown,
16183                           OpenMPDirectiveKind *CaptureRegion = nullptr,
16184                           Stmt **HelperValStmt = nullptr) {
16185   if (!ValExpr->isTypeDependent() && !ValExpr->isValueDependent() &&
16186       !ValExpr->isInstantiationDependent()) {
16187     SourceLocation Loc = ValExpr->getExprLoc();
16188     ExprResult Value =
16189         SemaRef.PerformOpenMPImplicitIntegerConversion(Loc, ValExpr);
16190     if (Value.isInvalid())
16191       return false;
16192 
16193     ValExpr = Value.get();
16194     // The expression must evaluate to a non-negative integer value.
16195     if (Optional<llvm::APSInt> Result =
16196             ValExpr->getIntegerConstantExpr(SemaRef.Context)) {
16197       if (Result->isSigned() &&
16198           !((!StrictlyPositive && Result->isNonNegative()) ||
16199             (StrictlyPositive && Result->isStrictlyPositive()))) {
16200         SemaRef.Diag(Loc, diag::err_omp_negative_expression_in_clause)
16201             << getOpenMPClauseName(CKind) << (StrictlyPositive ? 1 : 0)
16202             << ValExpr->getSourceRange();
16203         return false;
16204       }
16205     }
16206     if (!BuildCapture)
16207       return true;
16208     *CaptureRegion =
16209         getOpenMPCaptureRegionForClause(DKind, CKind, SemaRef.LangOpts.OpenMP);
16210     if (*CaptureRegion != OMPD_unknown &&
16211         !SemaRef.CurContext->isDependentContext()) {
16212       ValExpr = SemaRef.MakeFullExpr(ValExpr).get();
16213       llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
16214       ValExpr = tryBuildCapture(SemaRef, ValExpr, Captures).get();
16215       *HelperValStmt = buildPreInits(SemaRef.Context, Captures);
16216     }
16217   }
16218   return true;
16219 }
16220 
16221 OMPClause *Sema::ActOnOpenMPNumThreadsClause(Expr *NumThreads,
16222                                              SourceLocation StartLoc,
16223                                              SourceLocation LParenLoc,
16224                                              SourceLocation EndLoc) {
16225   Expr *ValExpr = NumThreads;
16226   Stmt *HelperValStmt = nullptr;
16227 
16228   // OpenMP [2.5, Restrictions]
16229   //  The num_threads expression must evaluate to a positive integer value.
16230   if (!isNonNegativeIntegerValue(ValExpr, *this, OMPC_num_threads,
16231                                  /*StrictlyPositive=*/true))
16232     return nullptr;
16233 
16234   OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
16235   OpenMPDirectiveKind CaptureRegion =
16236       getOpenMPCaptureRegionForClause(DKind, OMPC_num_threads, LangOpts.OpenMP);
16237   if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
16238     ValExpr = MakeFullExpr(ValExpr).get();
16239     llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
16240     ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
16241     HelperValStmt = buildPreInits(Context, Captures);
16242   }
16243 
16244   return new (Context) OMPNumThreadsClause(
16245       ValExpr, HelperValStmt, CaptureRegion, StartLoc, LParenLoc, EndLoc);
16246 }
16247 
16248 ExprResult Sema::VerifyPositiveIntegerConstantInClause(Expr *E,
16249                                                        OpenMPClauseKind CKind,
16250                                                        bool StrictlyPositive,
16251                                                        bool SuppressExprDiags) {
16252   if (!E)
16253     return ExprError();
16254   if (E->isValueDependent() || E->isTypeDependent() ||
16255       E->isInstantiationDependent() || E->containsUnexpandedParameterPack())
16256     return E;
16257 
16258   llvm::APSInt Result;
16259   ExprResult ICE;
16260   if (SuppressExprDiags) {
16261     // Use a custom diagnoser that suppresses 'note' diagnostics about the
16262     // expression.
16263     struct SuppressedDiagnoser : public Sema::VerifyICEDiagnoser {
16264       SuppressedDiagnoser() : VerifyICEDiagnoser(/*Suppress=*/true) {}
16265       Sema::SemaDiagnosticBuilder diagnoseNotICE(Sema &S,
16266                                                  SourceLocation Loc) override {
16267         llvm_unreachable("Diagnostic suppressed");
16268       }
16269     } Diagnoser;
16270     ICE = VerifyIntegerConstantExpression(E, &Result, Diagnoser, AllowFold);
16271   } else {
16272     ICE = VerifyIntegerConstantExpression(E, &Result, /*FIXME*/ AllowFold);
16273   }
16274   if (ICE.isInvalid())
16275     return ExprError();
16276 
16277   if ((StrictlyPositive && !Result.isStrictlyPositive()) ||
16278       (!StrictlyPositive && !Result.isNonNegative())) {
16279     Diag(E->getExprLoc(), diag::err_omp_negative_expression_in_clause)
16280         << getOpenMPClauseName(CKind) << (StrictlyPositive ? 1 : 0)
16281         << E->getSourceRange();
16282     return ExprError();
16283   }
16284   if ((CKind == OMPC_aligned || CKind == OMPC_align) && !Result.isPowerOf2()) {
16285     Diag(E->getExprLoc(), diag::warn_omp_alignment_not_power_of_two)
16286         << E->getSourceRange();
16287     return ExprError();
16288   }
16289   if (CKind == OMPC_collapse && DSAStack->getAssociatedLoops() == 1)
16290     DSAStack->setAssociatedLoops(Result.getExtValue());
16291   else if (CKind == OMPC_ordered)
16292     DSAStack->setAssociatedLoops(Result.getExtValue());
16293   return ICE;
16294 }
16295 
16296 OMPClause *Sema::ActOnOpenMPSafelenClause(Expr *Len, SourceLocation StartLoc,
16297                                           SourceLocation LParenLoc,
16298                                           SourceLocation EndLoc) {
16299   // OpenMP [2.8.1, simd construct, Description]
16300   // The parameter of the safelen clause must be a constant
16301   // positive integer expression.
16302   ExprResult Safelen = VerifyPositiveIntegerConstantInClause(Len, OMPC_safelen);
16303   if (Safelen.isInvalid())
16304     return nullptr;
16305   return new (Context)
16306       OMPSafelenClause(Safelen.get(), StartLoc, LParenLoc, EndLoc);
16307 }
16308 
16309 OMPClause *Sema::ActOnOpenMPSimdlenClause(Expr *Len, SourceLocation StartLoc,
16310                                           SourceLocation LParenLoc,
16311                                           SourceLocation EndLoc) {
16312   // OpenMP [2.8.1, simd construct, Description]
16313   // The parameter of the simdlen clause must be a constant
16314   // positive integer expression.
16315   ExprResult Simdlen = VerifyPositiveIntegerConstantInClause(Len, OMPC_simdlen);
16316   if (Simdlen.isInvalid())
16317     return nullptr;
16318   return new (Context)
16319       OMPSimdlenClause(Simdlen.get(), StartLoc, LParenLoc, EndLoc);
16320 }
16321 
16322 /// Tries to find omp_allocator_handle_t type.
16323 static bool findOMPAllocatorHandleT(Sema &S, SourceLocation Loc,
16324                                     DSAStackTy *Stack) {
16325   QualType OMPAllocatorHandleT = Stack->getOMPAllocatorHandleT();
16326   if (!OMPAllocatorHandleT.isNull())
16327     return true;
16328   // Build the predefined allocator expressions.
16329   bool ErrorFound = false;
16330   for (int I = 0; I < OMPAllocateDeclAttr::OMPUserDefinedMemAlloc; ++I) {
16331     auto AllocatorKind = static_cast<OMPAllocateDeclAttr::AllocatorTypeTy>(I);
16332     StringRef Allocator =
16333         OMPAllocateDeclAttr::ConvertAllocatorTypeTyToStr(AllocatorKind);
16334     DeclarationName AllocatorName = &S.getASTContext().Idents.get(Allocator);
16335     auto *VD = dyn_cast_or_null<ValueDecl>(
16336         S.LookupSingleName(S.TUScope, AllocatorName, Loc, Sema::LookupAnyName));
16337     if (!VD) {
16338       ErrorFound = true;
16339       break;
16340     }
16341     QualType AllocatorType =
16342         VD->getType().getNonLValueExprType(S.getASTContext());
16343     ExprResult Res = S.BuildDeclRefExpr(VD, AllocatorType, VK_LValue, Loc);
16344     if (!Res.isUsable()) {
16345       ErrorFound = true;
16346       break;
16347     }
16348     if (OMPAllocatorHandleT.isNull())
16349       OMPAllocatorHandleT = AllocatorType;
16350     if (!S.getASTContext().hasSameType(OMPAllocatorHandleT, AllocatorType)) {
16351       ErrorFound = true;
16352       break;
16353     }
16354     Stack->setAllocator(AllocatorKind, Res.get());
16355   }
16356   if (ErrorFound) {
16357     S.Diag(Loc, diag::err_omp_implied_type_not_found)
16358         << "omp_allocator_handle_t";
16359     return false;
16360   }
16361   OMPAllocatorHandleT.addConst();
16362   Stack->setOMPAllocatorHandleT(OMPAllocatorHandleT);
16363   return true;
16364 }
16365 
16366 OMPClause *Sema::ActOnOpenMPAllocatorClause(Expr *A, SourceLocation StartLoc,
16367                                             SourceLocation LParenLoc,
16368                                             SourceLocation EndLoc) {
16369   // OpenMP [2.11.3, allocate Directive, Description]
16370   // allocator is an expression of omp_allocator_handle_t type.
16371   if (!findOMPAllocatorHandleT(*this, A->getExprLoc(), DSAStack))
16372     return nullptr;
16373 
16374   ExprResult Allocator = DefaultLvalueConversion(A);
16375   if (Allocator.isInvalid())
16376     return nullptr;
16377   Allocator = PerformImplicitConversion(Allocator.get(),
16378                                         DSAStack->getOMPAllocatorHandleT(),
16379                                         Sema::AA_Initializing,
16380                                         /*AllowExplicit=*/true);
16381   if (Allocator.isInvalid())
16382     return nullptr;
16383   return new (Context)
16384       OMPAllocatorClause(Allocator.get(), StartLoc, LParenLoc, EndLoc);
16385 }
16386 
16387 OMPClause *Sema::ActOnOpenMPCollapseClause(Expr *NumForLoops,
16388                                            SourceLocation StartLoc,
16389                                            SourceLocation LParenLoc,
16390                                            SourceLocation EndLoc) {
16391   // OpenMP [2.7.1, loop construct, Description]
16392   // OpenMP [2.8.1, simd construct, Description]
16393   // OpenMP [2.9.6, distribute construct, Description]
16394   // The parameter of the collapse clause must be a constant
16395   // positive integer expression.
16396   ExprResult NumForLoopsResult =
16397       VerifyPositiveIntegerConstantInClause(NumForLoops, OMPC_collapse);
16398   if (NumForLoopsResult.isInvalid())
16399     return nullptr;
16400   return new (Context)
16401       OMPCollapseClause(NumForLoopsResult.get(), StartLoc, LParenLoc, EndLoc);
16402 }
16403 
16404 OMPClause *Sema::ActOnOpenMPOrderedClause(SourceLocation StartLoc,
16405                                           SourceLocation EndLoc,
16406                                           SourceLocation LParenLoc,
16407                                           Expr *NumForLoops) {
16408   // OpenMP [2.7.1, loop construct, Description]
16409   // OpenMP [2.8.1, simd construct, Description]
16410   // OpenMP [2.9.6, distribute construct, Description]
16411   // The parameter of the ordered clause must be a constant
16412   // positive integer expression if any.
16413   if (NumForLoops && LParenLoc.isValid()) {
16414     ExprResult NumForLoopsResult =
16415         VerifyPositiveIntegerConstantInClause(NumForLoops, OMPC_ordered);
16416     if (NumForLoopsResult.isInvalid())
16417       return nullptr;
16418     NumForLoops = NumForLoopsResult.get();
16419   } else {
16420     NumForLoops = nullptr;
16421   }
16422   auto *Clause = OMPOrderedClause::Create(
16423       Context, NumForLoops, NumForLoops ? DSAStack->getAssociatedLoops() : 0,
16424       StartLoc, LParenLoc, EndLoc);
16425   DSAStack->setOrderedRegion(/*IsOrdered=*/true, NumForLoops, Clause);
16426   return Clause;
16427 }
16428 
16429 OMPClause *Sema::ActOnOpenMPSimpleClause(
16430     OpenMPClauseKind Kind, unsigned Argument, SourceLocation ArgumentLoc,
16431     SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc) {
16432   OMPClause *Res = nullptr;
16433   switch (Kind) {
16434   case OMPC_default:
16435     Res = ActOnOpenMPDefaultClause(static_cast<DefaultKind>(Argument),
16436                                    ArgumentLoc, StartLoc, LParenLoc, EndLoc);
16437     break;
16438   case OMPC_proc_bind:
16439     Res = ActOnOpenMPProcBindClause(static_cast<ProcBindKind>(Argument),
16440                                     ArgumentLoc, StartLoc, LParenLoc, EndLoc);
16441     break;
16442   case OMPC_atomic_default_mem_order:
16443     Res = ActOnOpenMPAtomicDefaultMemOrderClause(
16444         static_cast<OpenMPAtomicDefaultMemOrderClauseKind>(Argument),
16445         ArgumentLoc, StartLoc, LParenLoc, EndLoc);
16446     break;
16447   case OMPC_order:
16448     Res = ActOnOpenMPOrderClause(static_cast<OpenMPOrderClauseKind>(Argument),
16449                                  ArgumentLoc, StartLoc, LParenLoc, EndLoc);
16450     break;
16451   case OMPC_update:
16452     Res = ActOnOpenMPUpdateClause(static_cast<OpenMPDependClauseKind>(Argument),
16453                                   ArgumentLoc, StartLoc, LParenLoc, EndLoc);
16454     break;
16455   case OMPC_bind:
16456     Res = ActOnOpenMPBindClause(static_cast<OpenMPBindClauseKind>(Argument),
16457                                 ArgumentLoc, StartLoc, LParenLoc, EndLoc);
16458     break;
16459   case OMPC_if:
16460   case OMPC_final:
16461   case OMPC_num_threads:
16462   case OMPC_safelen:
16463   case OMPC_simdlen:
16464   case OMPC_sizes:
16465   case OMPC_allocator:
16466   case OMPC_collapse:
16467   case OMPC_schedule:
16468   case OMPC_private:
16469   case OMPC_firstprivate:
16470   case OMPC_lastprivate:
16471   case OMPC_shared:
16472   case OMPC_reduction:
16473   case OMPC_task_reduction:
16474   case OMPC_in_reduction:
16475   case OMPC_linear:
16476   case OMPC_aligned:
16477   case OMPC_copyin:
16478   case OMPC_copyprivate:
16479   case OMPC_ordered:
16480   case OMPC_nowait:
16481   case OMPC_untied:
16482   case OMPC_mergeable:
16483   case OMPC_threadprivate:
16484   case OMPC_allocate:
16485   case OMPC_flush:
16486   case OMPC_depobj:
16487   case OMPC_read:
16488   case OMPC_write:
16489   case OMPC_capture:
16490   case OMPC_compare:
16491   case OMPC_seq_cst:
16492   case OMPC_acq_rel:
16493   case OMPC_acquire:
16494   case OMPC_release:
16495   case OMPC_relaxed:
16496   case OMPC_depend:
16497   case OMPC_device:
16498   case OMPC_threads:
16499   case OMPC_simd:
16500   case OMPC_map:
16501   case OMPC_num_teams:
16502   case OMPC_thread_limit:
16503   case OMPC_priority:
16504   case OMPC_grainsize:
16505   case OMPC_nogroup:
16506   case OMPC_num_tasks:
16507   case OMPC_hint:
16508   case OMPC_dist_schedule:
16509   case OMPC_defaultmap:
16510   case OMPC_unknown:
16511   case OMPC_uniform:
16512   case OMPC_to:
16513   case OMPC_from:
16514   case OMPC_use_device_ptr:
16515   case OMPC_use_device_addr:
16516   case OMPC_is_device_ptr:
16517   case OMPC_has_device_addr:
16518   case OMPC_unified_address:
16519   case OMPC_unified_shared_memory:
16520   case OMPC_reverse_offload:
16521   case OMPC_dynamic_allocators:
16522   case OMPC_device_type:
16523   case OMPC_match:
16524   case OMPC_nontemporal:
16525   case OMPC_destroy:
16526   case OMPC_novariants:
16527   case OMPC_nocontext:
16528   case OMPC_detach:
16529   case OMPC_inclusive:
16530   case OMPC_exclusive:
16531   case OMPC_uses_allocators:
16532   case OMPC_affinity:
16533   case OMPC_when:
16534   default:
16535     llvm_unreachable("Clause is not allowed.");
16536   }
16537   return Res;
16538 }
16539 
16540 static std::string
16541 getListOfPossibleValues(OpenMPClauseKind K, unsigned First, unsigned Last,
16542                         ArrayRef<unsigned> Exclude = llvm::None) {
16543   SmallString<256> Buffer;
16544   llvm::raw_svector_ostream Out(Buffer);
16545   unsigned Skipped = Exclude.size();
16546   auto S = Exclude.begin(), E = Exclude.end();
16547   for (unsigned I = First; I < Last; ++I) {
16548     if (std::find(S, E, I) != E) {
16549       --Skipped;
16550       continue;
16551     }
16552     Out << "'" << getOpenMPSimpleClauseTypeName(K, I) << "'";
16553     if (I + Skipped + 2 == Last)
16554       Out << " or ";
16555     else if (I + Skipped + 1 != Last)
16556       Out << ", ";
16557   }
16558   return std::string(Out.str());
16559 }
16560 
16561 OMPClause *Sema::ActOnOpenMPDefaultClause(DefaultKind Kind,
16562                                           SourceLocation KindKwLoc,
16563                                           SourceLocation StartLoc,
16564                                           SourceLocation LParenLoc,
16565                                           SourceLocation EndLoc) {
16566   if (Kind == OMP_DEFAULT_unknown) {
16567     Diag(KindKwLoc, diag::err_omp_unexpected_clause_value)
16568         << getListOfPossibleValues(OMPC_default, /*First=*/0,
16569                                    /*Last=*/unsigned(OMP_DEFAULT_unknown))
16570         << getOpenMPClauseName(OMPC_default);
16571     return nullptr;
16572   }
16573 
16574   switch (Kind) {
16575   case OMP_DEFAULT_none:
16576     DSAStack->setDefaultDSANone(KindKwLoc);
16577     break;
16578   case OMP_DEFAULT_shared:
16579     DSAStack->setDefaultDSAShared(KindKwLoc);
16580     break;
16581   case OMP_DEFAULT_firstprivate:
16582     DSAStack->setDefaultDSAFirstPrivate(KindKwLoc);
16583     break;
16584   case OMP_DEFAULT_private:
16585     DSAStack->setDefaultDSAPrivate(KindKwLoc);
16586     break;
16587   default:
16588     llvm_unreachable("DSA unexpected in OpenMP default clause");
16589   }
16590 
16591   return new (Context)
16592       OMPDefaultClause(Kind, KindKwLoc, StartLoc, LParenLoc, EndLoc);
16593 }
16594 
16595 OMPClause *Sema::ActOnOpenMPProcBindClause(ProcBindKind Kind,
16596                                            SourceLocation KindKwLoc,
16597                                            SourceLocation StartLoc,
16598                                            SourceLocation LParenLoc,
16599                                            SourceLocation EndLoc) {
16600   if (Kind == OMP_PROC_BIND_unknown) {
16601     Diag(KindKwLoc, diag::err_omp_unexpected_clause_value)
16602         << getListOfPossibleValues(OMPC_proc_bind,
16603                                    /*First=*/unsigned(OMP_PROC_BIND_master),
16604                                    /*Last=*/
16605                                    unsigned(LangOpts.OpenMP > 50
16606                                                 ? OMP_PROC_BIND_primary
16607                                                 : OMP_PROC_BIND_spread) +
16608                                        1)
16609         << getOpenMPClauseName(OMPC_proc_bind);
16610     return nullptr;
16611   }
16612   if (Kind == OMP_PROC_BIND_primary && LangOpts.OpenMP < 51)
16613     Diag(KindKwLoc, diag::err_omp_unexpected_clause_value)
16614         << getListOfPossibleValues(OMPC_proc_bind,
16615                                    /*First=*/unsigned(OMP_PROC_BIND_master),
16616                                    /*Last=*/
16617                                    unsigned(OMP_PROC_BIND_spread) + 1)
16618         << getOpenMPClauseName(OMPC_proc_bind);
16619   return new (Context)
16620       OMPProcBindClause(Kind, KindKwLoc, StartLoc, LParenLoc, EndLoc);
16621 }
16622 
16623 OMPClause *Sema::ActOnOpenMPAtomicDefaultMemOrderClause(
16624     OpenMPAtomicDefaultMemOrderClauseKind Kind, SourceLocation KindKwLoc,
16625     SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc) {
16626   if (Kind == OMPC_ATOMIC_DEFAULT_MEM_ORDER_unknown) {
16627     Diag(KindKwLoc, diag::err_omp_unexpected_clause_value)
16628         << getListOfPossibleValues(
16629                OMPC_atomic_default_mem_order, /*First=*/0,
16630                /*Last=*/OMPC_ATOMIC_DEFAULT_MEM_ORDER_unknown)
16631         << getOpenMPClauseName(OMPC_atomic_default_mem_order);
16632     return nullptr;
16633   }
16634   return new (Context) OMPAtomicDefaultMemOrderClause(Kind, KindKwLoc, StartLoc,
16635                                                       LParenLoc, EndLoc);
16636 }
16637 
16638 OMPClause *Sema::ActOnOpenMPOrderClause(OpenMPOrderClauseKind Kind,
16639                                         SourceLocation KindKwLoc,
16640                                         SourceLocation StartLoc,
16641                                         SourceLocation LParenLoc,
16642                                         SourceLocation EndLoc) {
16643   if (Kind == OMPC_ORDER_unknown) {
16644     static_assert(OMPC_ORDER_unknown > 0,
16645                   "OMPC_ORDER_unknown not greater than 0");
16646     Diag(KindKwLoc, diag::err_omp_unexpected_clause_value)
16647         << getListOfPossibleValues(OMPC_order, /*First=*/0,
16648                                    /*Last=*/OMPC_ORDER_unknown)
16649         << getOpenMPClauseName(OMPC_order);
16650     return nullptr;
16651   }
16652   return new (Context)
16653       OMPOrderClause(Kind, KindKwLoc, StartLoc, LParenLoc, EndLoc);
16654 }
16655 
16656 OMPClause *Sema::ActOnOpenMPUpdateClause(OpenMPDependClauseKind Kind,
16657                                          SourceLocation KindKwLoc,
16658                                          SourceLocation StartLoc,
16659                                          SourceLocation LParenLoc,
16660                                          SourceLocation EndLoc) {
16661   if (Kind == OMPC_DEPEND_unknown || Kind == OMPC_DEPEND_source ||
16662       Kind == OMPC_DEPEND_sink || Kind == OMPC_DEPEND_depobj) {
16663     SmallVector<unsigned> Except = {
16664         OMPC_DEPEND_source, OMPC_DEPEND_sink, OMPC_DEPEND_depobj,
16665         OMPC_DEPEND_outallmemory, OMPC_DEPEND_inoutallmemory};
16666     if (LangOpts.OpenMP < 51)
16667       Except.push_back(OMPC_DEPEND_inoutset);
16668     Diag(KindKwLoc, diag::err_omp_unexpected_clause_value)
16669         << getListOfPossibleValues(OMPC_depend, /*First=*/0,
16670                                    /*Last=*/OMPC_DEPEND_unknown, Except)
16671         << getOpenMPClauseName(OMPC_update);
16672     return nullptr;
16673   }
16674   return OMPUpdateClause::Create(Context, StartLoc, LParenLoc, KindKwLoc, Kind,
16675                                  EndLoc);
16676 }
16677 
16678 OMPClause *Sema::ActOnOpenMPSizesClause(ArrayRef<Expr *> SizeExprs,
16679                                         SourceLocation StartLoc,
16680                                         SourceLocation LParenLoc,
16681                                         SourceLocation EndLoc) {
16682   for (Expr *SizeExpr : SizeExprs) {
16683     ExprResult NumForLoopsResult = VerifyPositiveIntegerConstantInClause(
16684         SizeExpr, OMPC_sizes, /*StrictlyPositive=*/true);
16685     if (!NumForLoopsResult.isUsable())
16686       return nullptr;
16687   }
16688 
16689   DSAStack->setAssociatedLoops(SizeExprs.size());
16690   return OMPSizesClause::Create(Context, StartLoc, LParenLoc, EndLoc,
16691                                 SizeExprs);
16692 }
16693 
16694 OMPClause *Sema::ActOnOpenMPFullClause(SourceLocation StartLoc,
16695                                        SourceLocation EndLoc) {
16696   return OMPFullClause::Create(Context, StartLoc, EndLoc);
16697 }
16698 
16699 OMPClause *Sema::ActOnOpenMPPartialClause(Expr *FactorExpr,
16700                                           SourceLocation StartLoc,
16701                                           SourceLocation LParenLoc,
16702                                           SourceLocation EndLoc) {
16703   if (FactorExpr) {
16704     // If an argument is specified, it must be a constant (or an unevaluated
16705     // template expression).
16706     ExprResult FactorResult = VerifyPositiveIntegerConstantInClause(
16707         FactorExpr, OMPC_partial, /*StrictlyPositive=*/true);
16708     if (FactorResult.isInvalid())
16709       return nullptr;
16710     FactorExpr = FactorResult.get();
16711   }
16712 
16713   return OMPPartialClause::Create(Context, StartLoc, LParenLoc, EndLoc,
16714                                   FactorExpr);
16715 }
16716 
16717 OMPClause *Sema::ActOnOpenMPAlignClause(Expr *A, SourceLocation StartLoc,
16718                                         SourceLocation LParenLoc,
16719                                         SourceLocation EndLoc) {
16720   ExprResult AlignVal;
16721   AlignVal = VerifyPositiveIntegerConstantInClause(A, OMPC_align);
16722   if (AlignVal.isInvalid())
16723     return nullptr;
16724   return OMPAlignClause::Create(Context, AlignVal.get(), StartLoc, LParenLoc,
16725                                 EndLoc);
16726 }
16727 
16728 OMPClause *Sema::ActOnOpenMPSingleExprWithArgClause(
16729     OpenMPClauseKind Kind, ArrayRef<unsigned> Argument, Expr *Expr,
16730     SourceLocation StartLoc, SourceLocation LParenLoc,
16731     ArrayRef<SourceLocation> ArgumentLoc, SourceLocation DelimLoc,
16732     SourceLocation EndLoc) {
16733   OMPClause *Res = nullptr;
16734   switch (Kind) {
16735   case OMPC_schedule:
16736     enum { Modifier1, Modifier2, ScheduleKind, NumberOfElements };
16737     assert(Argument.size() == NumberOfElements &&
16738            ArgumentLoc.size() == NumberOfElements);
16739     Res = ActOnOpenMPScheduleClause(
16740         static_cast<OpenMPScheduleClauseModifier>(Argument[Modifier1]),
16741         static_cast<OpenMPScheduleClauseModifier>(Argument[Modifier2]),
16742         static_cast<OpenMPScheduleClauseKind>(Argument[ScheduleKind]), Expr,
16743         StartLoc, LParenLoc, ArgumentLoc[Modifier1], ArgumentLoc[Modifier2],
16744         ArgumentLoc[ScheduleKind], DelimLoc, EndLoc);
16745     break;
16746   case OMPC_if:
16747     assert(Argument.size() == 1 && ArgumentLoc.size() == 1);
16748     Res = ActOnOpenMPIfClause(static_cast<OpenMPDirectiveKind>(Argument.back()),
16749                               Expr, StartLoc, LParenLoc, ArgumentLoc.back(),
16750                               DelimLoc, EndLoc);
16751     break;
16752   case OMPC_dist_schedule:
16753     Res = ActOnOpenMPDistScheduleClause(
16754         static_cast<OpenMPDistScheduleClauseKind>(Argument.back()), Expr,
16755         StartLoc, LParenLoc, ArgumentLoc.back(), DelimLoc, EndLoc);
16756     break;
16757   case OMPC_defaultmap:
16758     enum { Modifier, DefaultmapKind };
16759     Res = ActOnOpenMPDefaultmapClause(
16760         static_cast<OpenMPDefaultmapClauseModifier>(Argument[Modifier]),
16761         static_cast<OpenMPDefaultmapClauseKind>(Argument[DefaultmapKind]),
16762         StartLoc, LParenLoc, ArgumentLoc[Modifier], ArgumentLoc[DefaultmapKind],
16763         EndLoc);
16764     break;
16765   case OMPC_device:
16766     assert(Argument.size() == 1 && ArgumentLoc.size() == 1);
16767     Res = ActOnOpenMPDeviceClause(
16768         static_cast<OpenMPDeviceClauseModifier>(Argument.back()), Expr,
16769         StartLoc, LParenLoc, ArgumentLoc.back(), EndLoc);
16770     break;
16771   case OMPC_final:
16772   case OMPC_num_threads:
16773   case OMPC_safelen:
16774   case OMPC_simdlen:
16775   case OMPC_sizes:
16776   case OMPC_allocator:
16777   case OMPC_collapse:
16778   case OMPC_default:
16779   case OMPC_proc_bind:
16780   case OMPC_private:
16781   case OMPC_firstprivate:
16782   case OMPC_lastprivate:
16783   case OMPC_shared:
16784   case OMPC_reduction:
16785   case OMPC_task_reduction:
16786   case OMPC_in_reduction:
16787   case OMPC_linear:
16788   case OMPC_aligned:
16789   case OMPC_copyin:
16790   case OMPC_copyprivate:
16791   case OMPC_ordered:
16792   case OMPC_nowait:
16793   case OMPC_untied:
16794   case OMPC_mergeable:
16795   case OMPC_threadprivate:
16796   case OMPC_allocate:
16797   case OMPC_flush:
16798   case OMPC_depobj:
16799   case OMPC_read:
16800   case OMPC_write:
16801   case OMPC_update:
16802   case OMPC_capture:
16803   case OMPC_compare:
16804   case OMPC_seq_cst:
16805   case OMPC_acq_rel:
16806   case OMPC_acquire:
16807   case OMPC_release:
16808   case OMPC_relaxed:
16809   case OMPC_depend:
16810   case OMPC_threads:
16811   case OMPC_simd:
16812   case OMPC_map:
16813   case OMPC_num_teams:
16814   case OMPC_thread_limit:
16815   case OMPC_priority:
16816   case OMPC_grainsize:
16817   case OMPC_nogroup:
16818   case OMPC_num_tasks:
16819   case OMPC_hint:
16820   case OMPC_unknown:
16821   case OMPC_uniform:
16822   case OMPC_to:
16823   case OMPC_from:
16824   case OMPC_use_device_ptr:
16825   case OMPC_use_device_addr:
16826   case OMPC_is_device_ptr:
16827   case OMPC_has_device_addr:
16828   case OMPC_unified_address:
16829   case OMPC_unified_shared_memory:
16830   case OMPC_reverse_offload:
16831   case OMPC_dynamic_allocators:
16832   case OMPC_atomic_default_mem_order:
16833   case OMPC_device_type:
16834   case OMPC_match:
16835   case OMPC_nontemporal:
16836   case OMPC_order:
16837   case OMPC_destroy:
16838   case OMPC_novariants:
16839   case OMPC_nocontext:
16840   case OMPC_detach:
16841   case OMPC_inclusive:
16842   case OMPC_exclusive:
16843   case OMPC_uses_allocators:
16844   case OMPC_affinity:
16845   case OMPC_when:
16846   case OMPC_bind:
16847   default:
16848     llvm_unreachable("Clause is not allowed.");
16849   }
16850   return Res;
16851 }
16852 
16853 static bool checkScheduleModifiers(Sema &S, OpenMPScheduleClauseModifier M1,
16854                                    OpenMPScheduleClauseModifier M2,
16855                                    SourceLocation M1Loc, SourceLocation M2Loc) {
16856   if (M1 == OMPC_SCHEDULE_MODIFIER_unknown && M1Loc.isValid()) {
16857     SmallVector<unsigned, 2> Excluded;
16858     if (M2 != OMPC_SCHEDULE_MODIFIER_unknown)
16859       Excluded.push_back(M2);
16860     if (M2 == OMPC_SCHEDULE_MODIFIER_nonmonotonic)
16861       Excluded.push_back(OMPC_SCHEDULE_MODIFIER_monotonic);
16862     if (M2 == OMPC_SCHEDULE_MODIFIER_monotonic)
16863       Excluded.push_back(OMPC_SCHEDULE_MODIFIER_nonmonotonic);
16864     S.Diag(M1Loc, diag::err_omp_unexpected_clause_value)
16865         << getListOfPossibleValues(OMPC_schedule,
16866                                    /*First=*/OMPC_SCHEDULE_MODIFIER_unknown + 1,
16867                                    /*Last=*/OMPC_SCHEDULE_MODIFIER_last,
16868                                    Excluded)
16869         << getOpenMPClauseName(OMPC_schedule);
16870     return true;
16871   }
16872   return false;
16873 }
16874 
16875 OMPClause *Sema::ActOnOpenMPScheduleClause(
16876     OpenMPScheduleClauseModifier M1, OpenMPScheduleClauseModifier M2,
16877     OpenMPScheduleClauseKind Kind, Expr *ChunkSize, SourceLocation StartLoc,
16878     SourceLocation LParenLoc, SourceLocation M1Loc, SourceLocation M2Loc,
16879     SourceLocation KindLoc, SourceLocation CommaLoc, SourceLocation EndLoc) {
16880   if (checkScheduleModifiers(*this, M1, M2, M1Loc, M2Loc) ||
16881       checkScheduleModifiers(*this, M2, M1, M2Loc, M1Loc))
16882     return nullptr;
16883   // OpenMP, 2.7.1, Loop Construct, Restrictions
16884   // Either the monotonic modifier or the nonmonotonic modifier can be specified
16885   // but not both.
16886   if ((M1 == M2 && M1 != OMPC_SCHEDULE_MODIFIER_unknown) ||
16887       (M1 == OMPC_SCHEDULE_MODIFIER_monotonic &&
16888        M2 == OMPC_SCHEDULE_MODIFIER_nonmonotonic) ||
16889       (M1 == OMPC_SCHEDULE_MODIFIER_nonmonotonic &&
16890        M2 == OMPC_SCHEDULE_MODIFIER_monotonic)) {
16891     Diag(M2Loc, diag::err_omp_unexpected_schedule_modifier)
16892         << getOpenMPSimpleClauseTypeName(OMPC_schedule, M2)
16893         << getOpenMPSimpleClauseTypeName(OMPC_schedule, M1);
16894     return nullptr;
16895   }
16896   if (Kind == OMPC_SCHEDULE_unknown) {
16897     std::string Values;
16898     if (M1Loc.isInvalid() && M2Loc.isInvalid()) {
16899       unsigned Exclude[] = {OMPC_SCHEDULE_unknown};
16900       Values = getListOfPossibleValues(OMPC_schedule, /*First=*/0,
16901                                        /*Last=*/OMPC_SCHEDULE_MODIFIER_last,
16902                                        Exclude);
16903     } else {
16904       Values = getListOfPossibleValues(OMPC_schedule, /*First=*/0,
16905                                        /*Last=*/OMPC_SCHEDULE_unknown);
16906     }
16907     Diag(KindLoc, diag::err_omp_unexpected_clause_value)
16908         << Values << getOpenMPClauseName(OMPC_schedule);
16909     return nullptr;
16910   }
16911   // OpenMP, 2.7.1, Loop Construct, Restrictions
16912   // The nonmonotonic modifier can only be specified with schedule(dynamic) or
16913   // schedule(guided).
16914   // OpenMP 5.0 does not have this restriction.
16915   if (LangOpts.OpenMP < 50 &&
16916       (M1 == OMPC_SCHEDULE_MODIFIER_nonmonotonic ||
16917        M2 == OMPC_SCHEDULE_MODIFIER_nonmonotonic) &&
16918       Kind != OMPC_SCHEDULE_dynamic && Kind != OMPC_SCHEDULE_guided) {
16919     Diag(M1 == OMPC_SCHEDULE_MODIFIER_nonmonotonic ? M1Loc : M2Loc,
16920          diag::err_omp_schedule_nonmonotonic_static);
16921     return nullptr;
16922   }
16923   Expr *ValExpr = ChunkSize;
16924   Stmt *HelperValStmt = nullptr;
16925   if (ChunkSize) {
16926     if (!ChunkSize->isValueDependent() && !ChunkSize->isTypeDependent() &&
16927         !ChunkSize->isInstantiationDependent() &&
16928         !ChunkSize->containsUnexpandedParameterPack()) {
16929       SourceLocation ChunkSizeLoc = ChunkSize->getBeginLoc();
16930       ExprResult Val =
16931           PerformOpenMPImplicitIntegerConversion(ChunkSizeLoc, ChunkSize);
16932       if (Val.isInvalid())
16933         return nullptr;
16934 
16935       ValExpr = Val.get();
16936 
16937       // OpenMP [2.7.1, Restrictions]
16938       //  chunk_size must be a loop invariant integer expression with a positive
16939       //  value.
16940       if (Optional<llvm::APSInt> Result =
16941               ValExpr->getIntegerConstantExpr(Context)) {
16942         if (Result->isSigned() && !Result->isStrictlyPositive()) {
16943           Diag(ChunkSizeLoc, diag::err_omp_negative_expression_in_clause)
16944               << "schedule" << 1 << ChunkSize->getSourceRange();
16945           return nullptr;
16946         }
16947       } else if (getOpenMPCaptureRegionForClause(
16948                      DSAStack->getCurrentDirective(), OMPC_schedule,
16949                      LangOpts.OpenMP) != OMPD_unknown &&
16950                  !CurContext->isDependentContext()) {
16951         ValExpr = MakeFullExpr(ValExpr).get();
16952         llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
16953         ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
16954         HelperValStmt = buildPreInits(Context, Captures);
16955       }
16956     }
16957   }
16958 
16959   return new (Context)
16960       OMPScheduleClause(StartLoc, LParenLoc, KindLoc, CommaLoc, EndLoc, Kind,
16961                         ValExpr, HelperValStmt, M1, M1Loc, M2, M2Loc);
16962 }
16963 
16964 OMPClause *Sema::ActOnOpenMPClause(OpenMPClauseKind Kind,
16965                                    SourceLocation StartLoc,
16966                                    SourceLocation EndLoc) {
16967   OMPClause *Res = nullptr;
16968   switch (Kind) {
16969   case OMPC_ordered:
16970     Res = ActOnOpenMPOrderedClause(StartLoc, EndLoc);
16971     break;
16972   case OMPC_nowait:
16973     Res = ActOnOpenMPNowaitClause(StartLoc, EndLoc);
16974     break;
16975   case OMPC_untied:
16976     Res = ActOnOpenMPUntiedClause(StartLoc, EndLoc);
16977     break;
16978   case OMPC_mergeable:
16979     Res = ActOnOpenMPMergeableClause(StartLoc, EndLoc);
16980     break;
16981   case OMPC_read:
16982     Res = ActOnOpenMPReadClause(StartLoc, EndLoc);
16983     break;
16984   case OMPC_write:
16985     Res = ActOnOpenMPWriteClause(StartLoc, EndLoc);
16986     break;
16987   case OMPC_update:
16988     Res = ActOnOpenMPUpdateClause(StartLoc, EndLoc);
16989     break;
16990   case OMPC_capture:
16991     Res = ActOnOpenMPCaptureClause(StartLoc, EndLoc);
16992     break;
16993   case OMPC_compare:
16994     Res = ActOnOpenMPCompareClause(StartLoc, EndLoc);
16995     break;
16996   case OMPC_seq_cst:
16997     Res = ActOnOpenMPSeqCstClause(StartLoc, EndLoc);
16998     break;
16999   case OMPC_acq_rel:
17000     Res = ActOnOpenMPAcqRelClause(StartLoc, EndLoc);
17001     break;
17002   case OMPC_acquire:
17003     Res = ActOnOpenMPAcquireClause(StartLoc, EndLoc);
17004     break;
17005   case OMPC_release:
17006     Res = ActOnOpenMPReleaseClause(StartLoc, EndLoc);
17007     break;
17008   case OMPC_relaxed:
17009     Res = ActOnOpenMPRelaxedClause(StartLoc, EndLoc);
17010     break;
17011   case OMPC_threads:
17012     Res = ActOnOpenMPThreadsClause(StartLoc, EndLoc);
17013     break;
17014   case OMPC_simd:
17015     Res = ActOnOpenMPSIMDClause(StartLoc, EndLoc);
17016     break;
17017   case OMPC_nogroup:
17018     Res = ActOnOpenMPNogroupClause(StartLoc, EndLoc);
17019     break;
17020   case OMPC_unified_address:
17021     Res = ActOnOpenMPUnifiedAddressClause(StartLoc, EndLoc);
17022     break;
17023   case OMPC_unified_shared_memory:
17024     Res = ActOnOpenMPUnifiedSharedMemoryClause(StartLoc, EndLoc);
17025     break;
17026   case OMPC_reverse_offload:
17027     Res = ActOnOpenMPReverseOffloadClause(StartLoc, EndLoc);
17028     break;
17029   case OMPC_dynamic_allocators:
17030     Res = ActOnOpenMPDynamicAllocatorsClause(StartLoc, EndLoc);
17031     break;
17032   case OMPC_destroy:
17033     Res = ActOnOpenMPDestroyClause(/*InteropVar=*/nullptr, StartLoc,
17034                                    /*LParenLoc=*/SourceLocation(),
17035                                    /*VarLoc=*/SourceLocation(), EndLoc);
17036     break;
17037   case OMPC_full:
17038     Res = ActOnOpenMPFullClause(StartLoc, EndLoc);
17039     break;
17040   case OMPC_partial:
17041     Res = ActOnOpenMPPartialClause(nullptr, StartLoc, /*LParenLoc=*/{}, EndLoc);
17042     break;
17043   case OMPC_if:
17044   case OMPC_final:
17045   case OMPC_num_threads:
17046   case OMPC_safelen:
17047   case OMPC_simdlen:
17048   case OMPC_sizes:
17049   case OMPC_allocator:
17050   case OMPC_collapse:
17051   case OMPC_schedule:
17052   case OMPC_private:
17053   case OMPC_firstprivate:
17054   case OMPC_lastprivate:
17055   case OMPC_shared:
17056   case OMPC_reduction:
17057   case OMPC_task_reduction:
17058   case OMPC_in_reduction:
17059   case OMPC_linear:
17060   case OMPC_aligned:
17061   case OMPC_copyin:
17062   case OMPC_copyprivate:
17063   case OMPC_default:
17064   case OMPC_proc_bind:
17065   case OMPC_threadprivate:
17066   case OMPC_allocate:
17067   case OMPC_flush:
17068   case OMPC_depobj:
17069   case OMPC_depend:
17070   case OMPC_device:
17071   case OMPC_map:
17072   case OMPC_num_teams:
17073   case OMPC_thread_limit:
17074   case OMPC_priority:
17075   case OMPC_grainsize:
17076   case OMPC_num_tasks:
17077   case OMPC_hint:
17078   case OMPC_dist_schedule:
17079   case OMPC_defaultmap:
17080   case OMPC_unknown:
17081   case OMPC_uniform:
17082   case OMPC_to:
17083   case OMPC_from:
17084   case OMPC_use_device_ptr:
17085   case OMPC_use_device_addr:
17086   case OMPC_is_device_ptr:
17087   case OMPC_has_device_addr:
17088   case OMPC_atomic_default_mem_order:
17089   case OMPC_device_type:
17090   case OMPC_match:
17091   case OMPC_nontemporal:
17092   case OMPC_order:
17093   case OMPC_novariants:
17094   case OMPC_nocontext:
17095   case OMPC_detach:
17096   case OMPC_inclusive:
17097   case OMPC_exclusive:
17098   case OMPC_uses_allocators:
17099   case OMPC_affinity:
17100   case OMPC_when:
17101   default:
17102     llvm_unreachable("Clause is not allowed.");
17103   }
17104   return Res;
17105 }
17106 
17107 OMPClause *Sema::ActOnOpenMPNowaitClause(SourceLocation StartLoc,
17108                                          SourceLocation EndLoc) {
17109   DSAStack->setNowaitRegion();
17110   return new (Context) OMPNowaitClause(StartLoc, EndLoc);
17111 }
17112 
17113 OMPClause *Sema::ActOnOpenMPUntiedClause(SourceLocation StartLoc,
17114                                          SourceLocation EndLoc) {
17115   DSAStack->setUntiedRegion();
17116   return new (Context) OMPUntiedClause(StartLoc, EndLoc);
17117 }
17118 
17119 OMPClause *Sema::ActOnOpenMPMergeableClause(SourceLocation StartLoc,
17120                                             SourceLocation EndLoc) {
17121   return new (Context) OMPMergeableClause(StartLoc, EndLoc);
17122 }
17123 
17124 OMPClause *Sema::ActOnOpenMPReadClause(SourceLocation StartLoc,
17125                                        SourceLocation EndLoc) {
17126   return new (Context) OMPReadClause(StartLoc, EndLoc);
17127 }
17128 
17129 OMPClause *Sema::ActOnOpenMPWriteClause(SourceLocation StartLoc,
17130                                         SourceLocation EndLoc) {
17131   return new (Context) OMPWriteClause(StartLoc, EndLoc);
17132 }
17133 
17134 OMPClause *Sema::ActOnOpenMPUpdateClause(SourceLocation StartLoc,
17135                                          SourceLocation EndLoc) {
17136   return OMPUpdateClause::Create(Context, StartLoc, EndLoc);
17137 }
17138 
17139 OMPClause *Sema::ActOnOpenMPCaptureClause(SourceLocation StartLoc,
17140                                           SourceLocation EndLoc) {
17141   return new (Context) OMPCaptureClause(StartLoc, EndLoc);
17142 }
17143 
17144 OMPClause *Sema::ActOnOpenMPCompareClause(SourceLocation StartLoc,
17145                                           SourceLocation EndLoc) {
17146   return new (Context) OMPCompareClause(StartLoc, EndLoc);
17147 }
17148 
17149 OMPClause *Sema::ActOnOpenMPSeqCstClause(SourceLocation StartLoc,
17150                                          SourceLocation EndLoc) {
17151   return new (Context) OMPSeqCstClause(StartLoc, EndLoc);
17152 }
17153 
17154 OMPClause *Sema::ActOnOpenMPAcqRelClause(SourceLocation StartLoc,
17155                                          SourceLocation EndLoc) {
17156   return new (Context) OMPAcqRelClause(StartLoc, EndLoc);
17157 }
17158 
17159 OMPClause *Sema::ActOnOpenMPAcquireClause(SourceLocation StartLoc,
17160                                           SourceLocation EndLoc) {
17161   return new (Context) OMPAcquireClause(StartLoc, EndLoc);
17162 }
17163 
17164 OMPClause *Sema::ActOnOpenMPReleaseClause(SourceLocation StartLoc,
17165                                           SourceLocation EndLoc) {
17166   return new (Context) OMPReleaseClause(StartLoc, EndLoc);
17167 }
17168 
17169 OMPClause *Sema::ActOnOpenMPRelaxedClause(SourceLocation StartLoc,
17170                                           SourceLocation EndLoc) {
17171   return new (Context) OMPRelaxedClause(StartLoc, EndLoc);
17172 }
17173 
17174 OMPClause *Sema::ActOnOpenMPThreadsClause(SourceLocation StartLoc,
17175                                           SourceLocation EndLoc) {
17176   return new (Context) OMPThreadsClause(StartLoc, EndLoc);
17177 }
17178 
17179 OMPClause *Sema::ActOnOpenMPSIMDClause(SourceLocation StartLoc,
17180                                        SourceLocation EndLoc) {
17181   return new (Context) OMPSIMDClause(StartLoc, EndLoc);
17182 }
17183 
17184 OMPClause *Sema::ActOnOpenMPNogroupClause(SourceLocation StartLoc,
17185                                           SourceLocation EndLoc) {
17186   return new (Context) OMPNogroupClause(StartLoc, EndLoc);
17187 }
17188 
17189 OMPClause *Sema::ActOnOpenMPUnifiedAddressClause(SourceLocation StartLoc,
17190                                                  SourceLocation EndLoc) {
17191   return new (Context) OMPUnifiedAddressClause(StartLoc, EndLoc);
17192 }
17193 
17194 OMPClause *Sema::ActOnOpenMPUnifiedSharedMemoryClause(SourceLocation StartLoc,
17195                                                       SourceLocation EndLoc) {
17196   return new (Context) OMPUnifiedSharedMemoryClause(StartLoc, EndLoc);
17197 }
17198 
17199 OMPClause *Sema::ActOnOpenMPReverseOffloadClause(SourceLocation StartLoc,
17200                                                  SourceLocation EndLoc) {
17201   return new (Context) OMPReverseOffloadClause(StartLoc, EndLoc);
17202 }
17203 
17204 OMPClause *Sema::ActOnOpenMPDynamicAllocatorsClause(SourceLocation StartLoc,
17205                                                     SourceLocation EndLoc) {
17206   return new (Context) OMPDynamicAllocatorsClause(StartLoc, EndLoc);
17207 }
17208 
17209 StmtResult Sema::ActOnOpenMPInteropDirective(ArrayRef<OMPClause *> Clauses,
17210                                              SourceLocation StartLoc,
17211                                              SourceLocation EndLoc) {
17212 
17213   // OpenMP 5.1 [2.15.1, interop Construct, Restrictions]
17214   // At least one action-clause must appear on a directive.
17215   if (!hasClauses(Clauses, OMPC_init, OMPC_use, OMPC_destroy, OMPC_nowait)) {
17216     StringRef Expected = "'init', 'use', 'destroy', or 'nowait'";
17217     Diag(StartLoc, diag::err_omp_no_clause_for_directive)
17218         << Expected << getOpenMPDirectiveName(OMPD_interop);
17219     return StmtError();
17220   }
17221 
17222   // OpenMP 5.1 [2.15.1, interop Construct, Restrictions]
17223   // A depend clause can only appear on the directive if a targetsync
17224   // interop-type is present or the interop-var was initialized with
17225   // the targetsync interop-type.
17226 
17227   // If there is any 'init' clause diagnose if there is no 'init' clause with
17228   // interop-type of 'targetsync'. Cases involving other directives cannot be
17229   // diagnosed.
17230   const OMPDependClause *DependClause = nullptr;
17231   bool HasInitClause = false;
17232   bool IsTargetSync = false;
17233   for (const OMPClause *C : Clauses) {
17234     if (IsTargetSync)
17235       break;
17236     if (const auto *InitClause = dyn_cast<OMPInitClause>(C)) {
17237       HasInitClause = true;
17238       if (InitClause->getIsTargetSync())
17239         IsTargetSync = true;
17240     } else if (const auto *DC = dyn_cast<OMPDependClause>(C)) {
17241       DependClause = DC;
17242     }
17243   }
17244   if (DependClause && HasInitClause && !IsTargetSync) {
17245     Diag(DependClause->getBeginLoc(), diag::err_omp_interop_bad_depend_clause);
17246     return StmtError();
17247   }
17248 
17249   // OpenMP 5.1 [2.15.1, interop Construct, Restrictions]
17250   // Each interop-var may be specified for at most one action-clause of each
17251   // interop construct.
17252   llvm::SmallPtrSet<const VarDecl *, 4> InteropVars;
17253   for (const OMPClause *C : Clauses) {
17254     OpenMPClauseKind ClauseKind = C->getClauseKind();
17255     const DeclRefExpr *DRE = nullptr;
17256     SourceLocation VarLoc;
17257 
17258     if (ClauseKind == OMPC_init) {
17259       const auto *IC = cast<OMPInitClause>(C);
17260       VarLoc = IC->getVarLoc();
17261       DRE = dyn_cast_or_null<DeclRefExpr>(IC->getInteropVar());
17262     } else if (ClauseKind == OMPC_use) {
17263       const auto *UC = cast<OMPUseClause>(C);
17264       VarLoc = UC->getVarLoc();
17265       DRE = dyn_cast_or_null<DeclRefExpr>(UC->getInteropVar());
17266     } else if (ClauseKind == OMPC_destroy) {
17267       const auto *DC = cast<OMPDestroyClause>(C);
17268       VarLoc = DC->getVarLoc();
17269       DRE = dyn_cast_or_null<DeclRefExpr>(DC->getInteropVar());
17270     }
17271 
17272     if (!DRE)
17273       continue;
17274 
17275     if (const auto *VD = dyn_cast<VarDecl>(DRE->getDecl())) {
17276       if (!InteropVars.insert(VD->getCanonicalDecl()).second) {
17277         Diag(VarLoc, diag::err_omp_interop_var_multiple_actions) << VD;
17278         return StmtError();
17279       }
17280     }
17281   }
17282 
17283   return OMPInteropDirective::Create(Context, StartLoc, EndLoc, Clauses);
17284 }
17285 
17286 static bool isValidInteropVariable(Sema &SemaRef, Expr *InteropVarExpr,
17287                                    SourceLocation VarLoc,
17288                                    OpenMPClauseKind Kind) {
17289   if (InteropVarExpr->isValueDependent() || InteropVarExpr->isTypeDependent() ||
17290       InteropVarExpr->isInstantiationDependent() ||
17291       InteropVarExpr->containsUnexpandedParameterPack())
17292     return true;
17293 
17294   const auto *DRE = dyn_cast<DeclRefExpr>(InteropVarExpr);
17295   if (!DRE || !isa<VarDecl>(DRE->getDecl())) {
17296     SemaRef.Diag(VarLoc, diag::err_omp_interop_variable_expected) << 0;
17297     return false;
17298   }
17299 
17300   // Interop variable should be of type omp_interop_t.
17301   bool HasError = false;
17302   QualType InteropType;
17303   LookupResult Result(SemaRef, &SemaRef.Context.Idents.get("omp_interop_t"),
17304                       VarLoc, Sema::LookupOrdinaryName);
17305   if (SemaRef.LookupName(Result, SemaRef.getCurScope())) {
17306     NamedDecl *ND = Result.getFoundDecl();
17307     if (const auto *TD = dyn_cast<TypeDecl>(ND)) {
17308       InteropType = QualType(TD->getTypeForDecl(), 0);
17309     } else {
17310       HasError = true;
17311     }
17312   } else {
17313     HasError = true;
17314   }
17315 
17316   if (HasError) {
17317     SemaRef.Diag(VarLoc, diag::err_omp_implied_type_not_found)
17318         << "omp_interop_t";
17319     return false;
17320   }
17321 
17322   QualType VarType = InteropVarExpr->getType().getUnqualifiedType();
17323   if (!SemaRef.Context.hasSameType(InteropType, VarType)) {
17324     SemaRef.Diag(VarLoc, diag::err_omp_interop_variable_wrong_type);
17325     return false;
17326   }
17327 
17328   // OpenMP 5.1 [2.15.1, interop Construct, Restrictions]
17329   // The interop-var passed to init or destroy must be non-const.
17330   if ((Kind == OMPC_init || Kind == OMPC_destroy) &&
17331       isConstNotMutableType(SemaRef, InteropVarExpr->getType())) {
17332     SemaRef.Diag(VarLoc, diag::err_omp_interop_variable_expected)
17333         << /*non-const*/ 1;
17334     return false;
17335   }
17336   return true;
17337 }
17338 
17339 OMPClause *
17340 Sema::ActOnOpenMPInitClause(Expr *InteropVar, ArrayRef<Expr *> PrefExprs,
17341                             bool IsTarget, bool IsTargetSync,
17342                             SourceLocation StartLoc, SourceLocation LParenLoc,
17343                             SourceLocation VarLoc, SourceLocation EndLoc) {
17344 
17345   if (!isValidInteropVariable(*this, InteropVar, VarLoc, OMPC_init))
17346     return nullptr;
17347 
17348   // Check prefer_type values.  These foreign-runtime-id values are either
17349   // string literals or constant integral expressions.
17350   for (const Expr *E : PrefExprs) {
17351     if (E->isValueDependent() || E->isTypeDependent() ||
17352         E->isInstantiationDependent() || E->containsUnexpandedParameterPack())
17353       continue;
17354     if (E->isIntegerConstantExpr(Context))
17355       continue;
17356     if (isa<StringLiteral>(E))
17357       continue;
17358     Diag(E->getExprLoc(), diag::err_omp_interop_prefer_type);
17359     return nullptr;
17360   }
17361 
17362   return OMPInitClause::Create(Context, InteropVar, PrefExprs, IsTarget,
17363                                IsTargetSync, StartLoc, LParenLoc, VarLoc,
17364                                EndLoc);
17365 }
17366 
17367 OMPClause *Sema::ActOnOpenMPUseClause(Expr *InteropVar, SourceLocation StartLoc,
17368                                       SourceLocation LParenLoc,
17369                                       SourceLocation VarLoc,
17370                                       SourceLocation EndLoc) {
17371 
17372   if (!isValidInteropVariable(*this, InteropVar, VarLoc, OMPC_use))
17373     return nullptr;
17374 
17375   return new (Context)
17376       OMPUseClause(InteropVar, StartLoc, LParenLoc, VarLoc, EndLoc);
17377 }
17378 
17379 OMPClause *Sema::ActOnOpenMPDestroyClause(Expr *InteropVar,
17380                                           SourceLocation StartLoc,
17381                                           SourceLocation LParenLoc,
17382                                           SourceLocation VarLoc,
17383                                           SourceLocation EndLoc) {
17384   if (InteropVar &&
17385       !isValidInteropVariable(*this, InteropVar, VarLoc, OMPC_destroy))
17386     return nullptr;
17387 
17388   return new (Context)
17389       OMPDestroyClause(InteropVar, StartLoc, LParenLoc, VarLoc, EndLoc);
17390 }
17391 
17392 OMPClause *Sema::ActOnOpenMPNovariantsClause(Expr *Condition,
17393                                              SourceLocation StartLoc,
17394                                              SourceLocation LParenLoc,
17395                                              SourceLocation EndLoc) {
17396   Expr *ValExpr = Condition;
17397   Stmt *HelperValStmt = nullptr;
17398   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
17399   if (!Condition->isValueDependent() && !Condition->isTypeDependent() &&
17400       !Condition->isInstantiationDependent() &&
17401       !Condition->containsUnexpandedParameterPack()) {
17402     ExprResult Val = CheckBooleanCondition(StartLoc, Condition);
17403     if (Val.isInvalid())
17404       return nullptr;
17405 
17406     ValExpr = MakeFullExpr(Val.get()).get();
17407 
17408     OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
17409     CaptureRegion = getOpenMPCaptureRegionForClause(DKind, OMPC_novariants,
17410                                                     LangOpts.OpenMP);
17411     if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
17412       ValExpr = MakeFullExpr(ValExpr).get();
17413       llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
17414       ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
17415       HelperValStmt = buildPreInits(Context, Captures);
17416     }
17417   }
17418 
17419   return new (Context) OMPNovariantsClause(
17420       ValExpr, HelperValStmt, CaptureRegion, StartLoc, LParenLoc, EndLoc);
17421 }
17422 
17423 OMPClause *Sema::ActOnOpenMPNocontextClause(Expr *Condition,
17424                                             SourceLocation StartLoc,
17425                                             SourceLocation LParenLoc,
17426                                             SourceLocation EndLoc) {
17427   Expr *ValExpr = Condition;
17428   Stmt *HelperValStmt = nullptr;
17429   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
17430   if (!Condition->isValueDependent() && !Condition->isTypeDependent() &&
17431       !Condition->isInstantiationDependent() &&
17432       !Condition->containsUnexpandedParameterPack()) {
17433     ExprResult Val = CheckBooleanCondition(StartLoc, Condition);
17434     if (Val.isInvalid())
17435       return nullptr;
17436 
17437     ValExpr = MakeFullExpr(Val.get()).get();
17438 
17439     OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
17440     CaptureRegion =
17441         getOpenMPCaptureRegionForClause(DKind, OMPC_nocontext, LangOpts.OpenMP);
17442     if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
17443       ValExpr = MakeFullExpr(ValExpr).get();
17444       llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
17445       ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
17446       HelperValStmt = buildPreInits(Context, Captures);
17447     }
17448   }
17449 
17450   return new (Context) OMPNocontextClause(ValExpr, HelperValStmt, CaptureRegion,
17451                                           StartLoc, LParenLoc, EndLoc);
17452 }
17453 
17454 OMPClause *Sema::ActOnOpenMPFilterClause(Expr *ThreadID,
17455                                          SourceLocation StartLoc,
17456                                          SourceLocation LParenLoc,
17457                                          SourceLocation EndLoc) {
17458   Expr *ValExpr = ThreadID;
17459   Stmt *HelperValStmt = nullptr;
17460 
17461   OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
17462   OpenMPDirectiveKind CaptureRegion =
17463       getOpenMPCaptureRegionForClause(DKind, OMPC_filter, LangOpts.OpenMP);
17464   if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
17465     ValExpr = MakeFullExpr(ValExpr).get();
17466     llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
17467     ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
17468     HelperValStmt = buildPreInits(Context, Captures);
17469   }
17470 
17471   return new (Context) OMPFilterClause(ValExpr, HelperValStmt, CaptureRegion,
17472                                        StartLoc, LParenLoc, EndLoc);
17473 }
17474 
17475 OMPClause *Sema::ActOnOpenMPVarListClause(OpenMPClauseKind Kind,
17476                                           ArrayRef<Expr *> VarList,
17477                                           const OMPVarListLocTy &Locs,
17478                                           OpenMPVarListDataTy &Data) {
17479   SourceLocation StartLoc = Locs.StartLoc;
17480   SourceLocation LParenLoc = Locs.LParenLoc;
17481   SourceLocation EndLoc = Locs.EndLoc;
17482   OMPClause *Res = nullptr;
17483   int ExtraModifier = Data.ExtraModifier;
17484   SourceLocation ExtraModifierLoc = Data.ExtraModifierLoc;
17485   SourceLocation ColonLoc = Data.ColonLoc;
17486   switch (Kind) {
17487   case OMPC_private:
17488     Res = ActOnOpenMPPrivateClause(VarList, StartLoc, LParenLoc, EndLoc);
17489     break;
17490   case OMPC_firstprivate:
17491     Res = ActOnOpenMPFirstprivateClause(VarList, StartLoc, LParenLoc, EndLoc);
17492     break;
17493   case OMPC_lastprivate:
17494     assert(0 <= ExtraModifier && ExtraModifier <= OMPC_LASTPRIVATE_unknown &&
17495            "Unexpected lastprivate modifier.");
17496     Res = ActOnOpenMPLastprivateClause(
17497         VarList, static_cast<OpenMPLastprivateModifier>(ExtraModifier),
17498         ExtraModifierLoc, ColonLoc, StartLoc, LParenLoc, EndLoc);
17499     break;
17500   case OMPC_shared:
17501     Res = ActOnOpenMPSharedClause(VarList, StartLoc, LParenLoc, EndLoc);
17502     break;
17503   case OMPC_reduction:
17504     assert(0 <= ExtraModifier && ExtraModifier <= OMPC_REDUCTION_unknown &&
17505            "Unexpected lastprivate modifier.");
17506     Res = ActOnOpenMPReductionClause(
17507         VarList, static_cast<OpenMPReductionClauseModifier>(ExtraModifier),
17508         StartLoc, LParenLoc, ExtraModifierLoc, ColonLoc, EndLoc,
17509         Data.ReductionOrMapperIdScopeSpec, Data.ReductionOrMapperId);
17510     break;
17511   case OMPC_task_reduction:
17512     Res = ActOnOpenMPTaskReductionClause(
17513         VarList, StartLoc, LParenLoc, ColonLoc, EndLoc,
17514         Data.ReductionOrMapperIdScopeSpec, Data.ReductionOrMapperId);
17515     break;
17516   case OMPC_in_reduction:
17517     Res = ActOnOpenMPInReductionClause(
17518         VarList, StartLoc, LParenLoc, ColonLoc, EndLoc,
17519         Data.ReductionOrMapperIdScopeSpec, Data.ReductionOrMapperId);
17520     break;
17521   case OMPC_linear:
17522     assert(0 <= ExtraModifier && ExtraModifier <= OMPC_LINEAR_unknown &&
17523            "Unexpected linear modifier.");
17524     Res = ActOnOpenMPLinearClause(
17525         VarList, Data.DepModOrTailExpr, StartLoc, LParenLoc,
17526         static_cast<OpenMPLinearClauseKind>(ExtraModifier), ExtraModifierLoc,
17527         ColonLoc, EndLoc);
17528     break;
17529   case OMPC_aligned:
17530     Res = ActOnOpenMPAlignedClause(VarList, Data.DepModOrTailExpr, StartLoc,
17531                                    LParenLoc, ColonLoc, EndLoc);
17532     break;
17533   case OMPC_copyin:
17534     Res = ActOnOpenMPCopyinClause(VarList, StartLoc, LParenLoc, EndLoc);
17535     break;
17536   case OMPC_copyprivate:
17537     Res = ActOnOpenMPCopyprivateClause(VarList, StartLoc, LParenLoc, EndLoc);
17538     break;
17539   case OMPC_flush:
17540     Res = ActOnOpenMPFlushClause(VarList, StartLoc, LParenLoc, EndLoc);
17541     break;
17542   case OMPC_depend:
17543     assert(0 <= ExtraModifier && ExtraModifier <= OMPC_DEPEND_unknown &&
17544            "Unexpected depend modifier.");
17545     Res = ActOnOpenMPDependClause(
17546         {static_cast<OpenMPDependClauseKind>(ExtraModifier), ExtraModifierLoc,
17547          ColonLoc, Data.OmpAllMemoryLoc},
17548         Data.DepModOrTailExpr, VarList, StartLoc, LParenLoc, EndLoc);
17549     break;
17550   case OMPC_map:
17551     assert(0 <= ExtraModifier && ExtraModifier <= OMPC_MAP_unknown &&
17552            "Unexpected map modifier.");
17553     Res = ActOnOpenMPMapClause(
17554         Data.MapTypeModifiers, Data.MapTypeModifiersLoc,
17555         Data.ReductionOrMapperIdScopeSpec, Data.ReductionOrMapperId,
17556         static_cast<OpenMPMapClauseKind>(ExtraModifier), Data.IsMapTypeImplicit,
17557         ExtraModifierLoc, ColonLoc, VarList, Locs);
17558     break;
17559   case OMPC_to:
17560     Res =
17561         ActOnOpenMPToClause(Data.MotionModifiers, Data.MotionModifiersLoc,
17562                             Data.ReductionOrMapperIdScopeSpec,
17563                             Data.ReductionOrMapperId, ColonLoc, VarList, Locs);
17564     break;
17565   case OMPC_from:
17566     Res = ActOnOpenMPFromClause(Data.MotionModifiers, Data.MotionModifiersLoc,
17567                                 Data.ReductionOrMapperIdScopeSpec,
17568                                 Data.ReductionOrMapperId, ColonLoc, VarList,
17569                                 Locs);
17570     break;
17571   case OMPC_use_device_ptr:
17572     Res = ActOnOpenMPUseDevicePtrClause(VarList, Locs);
17573     break;
17574   case OMPC_use_device_addr:
17575     Res = ActOnOpenMPUseDeviceAddrClause(VarList, Locs);
17576     break;
17577   case OMPC_is_device_ptr:
17578     Res = ActOnOpenMPIsDevicePtrClause(VarList, Locs);
17579     break;
17580   case OMPC_has_device_addr:
17581     Res = ActOnOpenMPHasDeviceAddrClause(VarList, Locs);
17582     break;
17583   case OMPC_allocate:
17584     Res = ActOnOpenMPAllocateClause(Data.DepModOrTailExpr, VarList, StartLoc,
17585                                     LParenLoc, ColonLoc, EndLoc);
17586     break;
17587   case OMPC_nontemporal:
17588     Res = ActOnOpenMPNontemporalClause(VarList, StartLoc, LParenLoc, EndLoc);
17589     break;
17590   case OMPC_inclusive:
17591     Res = ActOnOpenMPInclusiveClause(VarList, StartLoc, LParenLoc, EndLoc);
17592     break;
17593   case OMPC_exclusive:
17594     Res = ActOnOpenMPExclusiveClause(VarList, StartLoc, LParenLoc, EndLoc);
17595     break;
17596   case OMPC_affinity:
17597     Res = ActOnOpenMPAffinityClause(StartLoc, LParenLoc, ColonLoc, EndLoc,
17598                                     Data.DepModOrTailExpr, VarList);
17599     break;
17600   case OMPC_if:
17601   case OMPC_depobj:
17602   case OMPC_final:
17603   case OMPC_num_threads:
17604   case OMPC_safelen:
17605   case OMPC_simdlen:
17606   case OMPC_sizes:
17607   case OMPC_allocator:
17608   case OMPC_collapse:
17609   case OMPC_default:
17610   case OMPC_proc_bind:
17611   case OMPC_schedule:
17612   case OMPC_ordered:
17613   case OMPC_nowait:
17614   case OMPC_untied:
17615   case OMPC_mergeable:
17616   case OMPC_threadprivate:
17617   case OMPC_read:
17618   case OMPC_write:
17619   case OMPC_update:
17620   case OMPC_capture:
17621   case OMPC_compare:
17622   case OMPC_seq_cst:
17623   case OMPC_acq_rel:
17624   case OMPC_acquire:
17625   case OMPC_release:
17626   case OMPC_relaxed:
17627   case OMPC_device:
17628   case OMPC_threads:
17629   case OMPC_simd:
17630   case OMPC_num_teams:
17631   case OMPC_thread_limit:
17632   case OMPC_priority:
17633   case OMPC_grainsize:
17634   case OMPC_nogroup:
17635   case OMPC_num_tasks:
17636   case OMPC_hint:
17637   case OMPC_dist_schedule:
17638   case OMPC_defaultmap:
17639   case OMPC_unknown:
17640   case OMPC_uniform:
17641   case OMPC_unified_address:
17642   case OMPC_unified_shared_memory:
17643   case OMPC_reverse_offload:
17644   case OMPC_dynamic_allocators:
17645   case OMPC_atomic_default_mem_order:
17646   case OMPC_device_type:
17647   case OMPC_match:
17648   case OMPC_order:
17649   case OMPC_destroy:
17650   case OMPC_novariants:
17651   case OMPC_nocontext:
17652   case OMPC_detach:
17653   case OMPC_uses_allocators:
17654   case OMPC_when:
17655   case OMPC_bind:
17656   default:
17657     llvm_unreachable("Clause is not allowed.");
17658   }
17659   return Res;
17660 }
17661 
17662 ExprResult Sema::getOpenMPCapturedExpr(VarDecl *Capture, ExprValueKind VK,
17663                                        ExprObjectKind OK, SourceLocation Loc) {
17664   ExprResult Res = BuildDeclRefExpr(
17665       Capture, Capture->getType().getNonReferenceType(), VK_LValue, Loc);
17666   if (!Res.isUsable())
17667     return ExprError();
17668   if (OK == OK_Ordinary && !getLangOpts().CPlusPlus) {
17669     Res = CreateBuiltinUnaryOp(Loc, UO_Deref, Res.get());
17670     if (!Res.isUsable())
17671       return ExprError();
17672   }
17673   if (VK != VK_LValue && Res.get()->isGLValue()) {
17674     Res = DefaultLvalueConversion(Res.get());
17675     if (!Res.isUsable())
17676       return ExprError();
17677   }
17678   return Res;
17679 }
17680 
17681 OMPClause *Sema::ActOnOpenMPPrivateClause(ArrayRef<Expr *> VarList,
17682                                           SourceLocation StartLoc,
17683                                           SourceLocation LParenLoc,
17684                                           SourceLocation EndLoc) {
17685   SmallVector<Expr *, 8> Vars;
17686   SmallVector<Expr *, 8> PrivateCopies;
17687   bool IsImplicitClause =
17688       StartLoc.isInvalid() && LParenLoc.isInvalid() && EndLoc.isInvalid();
17689   for (Expr *RefExpr : VarList) {
17690     assert(RefExpr && "NULL expr in OpenMP private clause.");
17691     SourceLocation ELoc;
17692     SourceRange ERange;
17693     Expr *SimpleRefExpr = RefExpr;
17694     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
17695     if (Res.second) {
17696       // It will be analyzed later.
17697       Vars.push_back(RefExpr);
17698       PrivateCopies.push_back(nullptr);
17699     }
17700     ValueDecl *D = Res.first;
17701     if (!D)
17702       continue;
17703 
17704     QualType Type = D->getType();
17705     auto *VD = dyn_cast<VarDecl>(D);
17706 
17707     // OpenMP [2.9.3.3, Restrictions, C/C++, p.3]
17708     //  A variable that appears in a private clause must not have an incomplete
17709     //  type or a reference type.
17710     if (RequireCompleteType(ELoc, Type, diag::err_omp_private_incomplete_type))
17711       continue;
17712     Type = Type.getNonReferenceType();
17713 
17714     // OpenMP 5.0 [2.19.3, List Item Privatization, Restrictions]
17715     // A variable that is privatized must not have a const-qualified type
17716     // unless it is of class type with a mutable member. This restriction does
17717     // not apply to the firstprivate clause.
17718     //
17719     // OpenMP 3.1 [2.9.3.3, private clause, Restrictions]
17720     // A variable that appears in a private clause must not have a
17721     // const-qualified type unless it is of class type with a mutable member.
17722     if (rejectConstNotMutableType(*this, D, Type, OMPC_private, ELoc))
17723       continue;
17724 
17725     // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
17726     // in a Construct]
17727     //  Variables with the predetermined data-sharing attributes may not be
17728     //  listed in data-sharing attributes clauses, except for the cases
17729     //  listed below. For these exceptions only, listing a predetermined
17730     //  variable in a data-sharing attribute clause is allowed and overrides
17731     //  the variable's predetermined data-sharing attributes.
17732     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(D, /*FromParent=*/false);
17733     if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_private) {
17734       Diag(ELoc, diag::err_omp_wrong_dsa) << getOpenMPClauseName(DVar.CKind)
17735                                           << getOpenMPClauseName(OMPC_private);
17736       reportOriginalDsa(*this, DSAStack, D, DVar);
17737       continue;
17738     }
17739 
17740     OpenMPDirectiveKind CurrDir = DSAStack->getCurrentDirective();
17741     // Variably modified types are not supported for tasks.
17742     if (!Type->isAnyPointerType() && Type->isVariablyModifiedType() &&
17743         isOpenMPTaskingDirective(CurrDir)) {
17744       Diag(ELoc, diag::err_omp_variably_modified_type_not_supported)
17745           << getOpenMPClauseName(OMPC_private) << Type
17746           << getOpenMPDirectiveName(CurrDir);
17747       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
17748                                VarDecl::DeclarationOnly;
17749       Diag(D->getLocation(),
17750            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
17751           << D;
17752       continue;
17753     }
17754 
17755     // OpenMP 4.5 [2.15.5.1, Restrictions, p.3]
17756     // A list item cannot appear in both a map clause and a data-sharing
17757     // attribute clause on the same construct
17758     //
17759     // OpenMP 5.0 [2.19.7.1, Restrictions, p.7]
17760     // A list item cannot appear in both a map clause and a data-sharing
17761     // attribute clause on the same construct unless the construct is a
17762     // combined construct.
17763     if ((LangOpts.OpenMP <= 45 && isOpenMPTargetExecutionDirective(CurrDir)) ||
17764         CurrDir == OMPD_target) {
17765       OpenMPClauseKind ConflictKind;
17766       if (DSAStack->checkMappableExprComponentListsForDecl(
17767               VD, /*CurrentRegionOnly=*/true,
17768               [&](OMPClauseMappableExprCommon::MappableExprComponentListRef,
17769                   OpenMPClauseKind WhereFoundClauseKind) -> bool {
17770                 ConflictKind = WhereFoundClauseKind;
17771                 return true;
17772               })) {
17773         Diag(ELoc, diag::err_omp_variable_in_given_clause_and_dsa)
17774             << getOpenMPClauseName(OMPC_private)
17775             << getOpenMPClauseName(ConflictKind)
17776             << getOpenMPDirectiveName(CurrDir);
17777         reportOriginalDsa(*this, DSAStack, D, DVar);
17778         continue;
17779       }
17780     }
17781 
17782     // OpenMP [2.9.3.3, Restrictions, C/C++, p.1]
17783     //  A variable of class type (or array thereof) that appears in a private
17784     //  clause requires an accessible, unambiguous default constructor for the
17785     //  class type.
17786     // Generate helper private variable and initialize it with the default
17787     // value. The address of the original variable is replaced by the address of
17788     // the new private variable in CodeGen. This new variable is not added to
17789     // IdResolver, so the code in the OpenMP region uses original variable for
17790     // proper diagnostics.
17791     Type = Type.getUnqualifiedType();
17792     VarDecl *VDPrivate =
17793         buildVarDecl(*this, ELoc, Type, D->getName(),
17794                      D->hasAttrs() ? &D->getAttrs() : nullptr,
17795                      VD ? cast<DeclRefExpr>(SimpleRefExpr) : nullptr);
17796     ActOnUninitializedDecl(VDPrivate);
17797     if (VDPrivate->isInvalidDecl())
17798       continue;
17799     DeclRefExpr *VDPrivateRefExpr = buildDeclRefExpr(
17800         *this, VDPrivate, RefExpr->getType().getUnqualifiedType(), ELoc);
17801 
17802     DeclRefExpr *Ref = nullptr;
17803     if (!VD && !CurContext->isDependentContext()) {
17804       auto *FD = dyn_cast<FieldDecl>(D);
17805       VarDecl *VD = FD ? DSAStack->getImplicitFDCapExprDecl(FD) : nullptr;
17806       if (VD)
17807         Ref = buildDeclRefExpr(*this, VD, VD->getType().getNonReferenceType(),
17808                                RefExpr->getExprLoc());
17809       else
17810         Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/false);
17811     }
17812     if (!IsImplicitClause)
17813       DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_private, Ref);
17814     Vars.push_back((VD || CurContext->isDependentContext())
17815                        ? RefExpr->IgnoreParens()
17816                        : Ref);
17817     PrivateCopies.push_back(VDPrivateRefExpr);
17818   }
17819 
17820   if (Vars.empty())
17821     return nullptr;
17822 
17823   return OMPPrivateClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars,
17824                                   PrivateCopies);
17825 }
17826 
17827 OMPClause *Sema::ActOnOpenMPFirstprivateClause(ArrayRef<Expr *> VarList,
17828                                                SourceLocation StartLoc,
17829                                                SourceLocation LParenLoc,
17830                                                SourceLocation EndLoc) {
17831   SmallVector<Expr *, 8> Vars;
17832   SmallVector<Expr *, 8> PrivateCopies;
17833   SmallVector<Expr *, 8> Inits;
17834   SmallVector<Decl *, 4> ExprCaptures;
17835   bool IsImplicitClause =
17836       StartLoc.isInvalid() && LParenLoc.isInvalid() && EndLoc.isInvalid();
17837   SourceLocation ImplicitClauseLoc = DSAStack->getConstructLoc();
17838 
17839   for (Expr *RefExpr : VarList) {
17840     assert(RefExpr && "NULL expr in OpenMP firstprivate clause.");
17841     SourceLocation ELoc;
17842     SourceRange ERange;
17843     Expr *SimpleRefExpr = RefExpr;
17844     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
17845     if (Res.second) {
17846       // It will be analyzed later.
17847       Vars.push_back(RefExpr);
17848       PrivateCopies.push_back(nullptr);
17849       Inits.push_back(nullptr);
17850     }
17851     ValueDecl *D = Res.first;
17852     if (!D)
17853       continue;
17854 
17855     ELoc = IsImplicitClause ? ImplicitClauseLoc : ELoc;
17856     QualType Type = D->getType();
17857     auto *VD = dyn_cast<VarDecl>(D);
17858 
17859     // OpenMP [2.9.3.3, Restrictions, C/C++, p.3]
17860     //  A variable that appears in a private clause must not have an incomplete
17861     //  type or a reference type.
17862     if (RequireCompleteType(ELoc, Type,
17863                             diag::err_omp_firstprivate_incomplete_type))
17864       continue;
17865     Type = Type.getNonReferenceType();
17866 
17867     // OpenMP [2.9.3.4, Restrictions, C/C++, p.1]
17868     //  A variable of class type (or array thereof) that appears in a private
17869     //  clause requires an accessible, unambiguous copy constructor for the
17870     //  class type.
17871     QualType ElemType = Context.getBaseElementType(Type).getNonReferenceType();
17872 
17873     // If an implicit firstprivate variable found it was checked already.
17874     DSAStackTy::DSAVarData TopDVar;
17875     if (!IsImplicitClause) {
17876       DSAStackTy::DSAVarData DVar =
17877           DSAStack->getTopDSA(D, /*FromParent=*/false);
17878       TopDVar = DVar;
17879       OpenMPDirectiveKind CurrDir = DSAStack->getCurrentDirective();
17880       bool IsConstant = ElemType.isConstant(Context);
17881       // OpenMP [2.4.13, Data-sharing Attribute Clauses]
17882       //  A list item that specifies a given variable may not appear in more
17883       // than one clause on the same directive, except that a variable may be
17884       //  specified in both firstprivate and lastprivate clauses.
17885       // OpenMP 4.5 [2.10.8, Distribute Construct, p.3]
17886       // A list item may appear in a firstprivate or lastprivate clause but not
17887       // both.
17888       if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_firstprivate &&
17889           (isOpenMPDistributeDirective(CurrDir) ||
17890            DVar.CKind != OMPC_lastprivate) &&
17891           DVar.RefExpr) {
17892         Diag(ELoc, diag::err_omp_wrong_dsa)
17893             << getOpenMPClauseName(DVar.CKind)
17894             << getOpenMPClauseName(OMPC_firstprivate);
17895         reportOriginalDsa(*this, DSAStack, D, DVar);
17896         continue;
17897       }
17898 
17899       // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
17900       // in a Construct]
17901       //  Variables with the predetermined data-sharing attributes may not be
17902       //  listed in data-sharing attributes clauses, except for the cases
17903       //  listed below. For these exceptions only, listing a predetermined
17904       //  variable in a data-sharing attribute clause is allowed and overrides
17905       //  the variable's predetermined data-sharing attributes.
17906       // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
17907       // in a Construct, C/C++, p.2]
17908       //  Variables with const-qualified type having no mutable member may be
17909       //  listed in a firstprivate clause, even if they are static data members.
17910       if (!(IsConstant || (VD && VD->isStaticDataMember())) && !DVar.RefExpr &&
17911           DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_shared) {
17912         Diag(ELoc, diag::err_omp_wrong_dsa)
17913             << getOpenMPClauseName(DVar.CKind)
17914             << getOpenMPClauseName(OMPC_firstprivate);
17915         reportOriginalDsa(*this, DSAStack, D, DVar);
17916         continue;
17917       }
17918 
17919       // OpenMP [2.9.3.4, Restrictions, p.2]
17920       //  A list item that is private within a parallel region must not appear
17921       //  in a firstprivate clause on a worksharing construct if any of the
17922       //  worksharing regions arising from the worksharing construct ever bind
17923       //  to any of the parallel regions arising from the parallel construct.
17924       // OpenMP 4.5 [2.15.3.4, Restrictions, p.3]
17925       // A list item that is private within a teams region must not appear in a
17926       // firstprivate clause on a distribute construct if any of the distribute
17927       // regions arising from the distribute construct ever bind to any of the
17928       // teams regions arising from the teams construct.
17929       // OpenMP 4.5 [2.15.3.4, Restrictions, p.3]
17930       // A list item that appears in a reduction clause of a teams construct
17931       // must not appear in a firstprivate clause on a distribute construct if
17932       // any of the distribute regions arising from the distribute construct
17933       // ever bind to any of the teams regions arising from the teams construct.
17934       if ((isOpenMPWorksharingDirective(CurrDir) ||
17935            isOpenMPDistributeDirective(CurrDir)) &&
17936           !isOpenMPParallelDirective(CurrDir) &&
17937           !isOpenMPTeamsDirective(CurrDir)) {
17938         DVar = DSAStack->getImplicitDSA(D, true);
17939         if (DVar.CKind != OMPC_shared &&
17940             (isOpenMPParallelDirective(DVar.DKind) ||
17941              isOpenMPTeamsDirective(DVar.DKind) ||
17942              DVar.DKind == OMPD_unknown)) {
17943           Diag(ELoc, diag::err_omp_required_access)
17944               << getOpenMPClauseName(OMPC_firstprivate)
17945               << getOpenMPClauseName(OMPC_shared);
17946           reportOriginalDsa(*this, DSAStack, D, DVar);
17947           continue;
17948         }
17949       }
17950       // OpenMP [2.9.3.4, Restrictions, p.3]
17951       //  A list item that appears in a reduction clause of a parallel construct
17952       //  must not appear in a firstprivate clause on a worksharing or task
17953       //  construct if any of the worksharing or task regions arising from the
17954       //  worksharing or task construct ever bind to any of the parallel regions
17955       //  arising from the parallel construct.
17956       // OpenMP [2.9.3.4, Restrictions, p.4]
17957       //  A list item that appears in a reduction clause in worksharing
17958       //  construct must not appear in a firstprivate clause in a task construct
17959       //  encountered during execution of any of the worksharing regions arising
17960       //  from the worksharing construct.
17961       if (isOpenMPTaskingDirective(CurrDir)) {
17962         DVar = DSAStack->hasInnermostDSA(
17963             D,
17964             [](OpenMPClauseKind C, bool AppliedToPointee) {
17965               return C == OMPC_reduction && !AppliedToPointee;
17966             },
17967             [](OpenMPDirectiveKind K) {
17968               return isOpenMPParallelDirective(K) ||
17969                      isOpenMPWorksharingDirective(K) ||
17970                      isOpenMPTeamsDirective(K);
17971             },
17972             /*FromParent=*/true);
17973         if (DVar.CKind == OMPC_reduction &&
17974             (isOpenMPParallelDirective(DVar.DKind) ||
17975              isOpenMPWorksharingDirective(DVar.DKind) ||
17976              isOpenMPTeamsDirective(DVar.DKind))) {
17977           Diag(ELoc, diag::err_omp_parallel_reduction_in_task_firstprivate)
17978               << getOpenMPDirectiveName(DVar.DKind);
17979           reportOriginalDsa(*this, DSAStack, D, DVar);
17980           continue;
17981         }
17982       }
17983 
17984       // OpenMP 4.5 [2.15.5.1, Restrictions, p.3]
17985       // A list item cannot appear in both a map clause and a data-sharing
17986       // attribute clause on the same construct
17987       //
17988       // OpenMP 5.0 [2.19.7.1, Restrictions, p.7]
17989       // A list item cannot appear in both a map clause and a data-sharing
17990       // attribute clause on the same construct unless the construct is a
17991       // combined construct.
17992       if ((LangOpts.OpenMP <= 45 &&
17993            isOpenMPTargetExecutionDirective(CurrDir)) ||
17994           CurrDir == OMPD_target) {
17995         OpenMPClauseKind ConflictKind;
17996         if (DSAStack->checkMappableExprComponentListsForDecl(
17997                 VD, /*CurrentRegionOnly=*/true,
17998                 [&ConflictKind](
17999                     OMPClauseMappableExprCommon::MappableExprComponentListRef,
18000                     OpenMPClauseKind WhereFoundClauseKind) {
18001                   ConflictKind = WhereFoundClauseKind;
18002                   return true;
18003                 })) {
18004           Diag(ELoc, diag::err_omp_variable_in_given_clause_and_dsa)
18005               << getOpenMPClauseName(OMPC_firstprivate)
18006               << getOpenMPClauseName(ConflictKind)
18007               << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
18008           reportOriginalDsa(*this, DSAStack, D, DVar);
18009           continue;
18010         }
18011       }
18012     }
18013 
18014     // Variably modified types are not supported for tasks.
18015     if (!Type->isAnyPointerType() && Type->isVariablyModifiedType() &&
18016         isOpenMPTaskingDirective(DSAStack->getCurrentDirective())) {
18017       Diag(ELoc, diag::err_omp_variably_modified_type_not_supported)
18018           << getOpenMPClauseName(OMPC_firstprivate) << Type
18019           << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
18020       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
18021                                VarDecl::DeclarationOnly;
18022       Diag(D->getLocation(),
18023            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
18024           << D;
18025       continue;
18026     }
18027 
18028     Type = Type.getUnqualifiedType();
18029     VarDecl *VDPrivate =
18030         buildVarDecl(*this, ELoc, Type, D->getName(),
18031                      D->hasAttrs() ? &D->getAttrs() : nullptr,
18032                      VD ? cast<DeclRefExpr>(SimpleRefExpr) : nullptr);
18033     // Generate helper private variable and initialize it with the value of the
18034     // original variable. The address of the original variable is replaced by
18035     // the address of the new private variable in the CodeGen. This new variable
18036     // is not added to IdResolver, so the code in the OpenMP region uses
18037     // original variable for proper diagnostics and variable capturing.
18038     Expr *VDInitRefExpr = nullptr;
18039     // For arrays generate initializer for single element and replace it by the
18040     // original array element in CodeGen.
18041     if (Type->isArrayType()) {
18042       VarDecl *VDInit =
18043           buildVarDecl(*this, RefExpr->getExprLoc(), ElemType, D->getName());
18044       VDInitRefExpr = buildDeclRefExpr(*this, VDInit, ElemType, ELoc);
18045       Expr *Init = DefaultLvalueConversion(VDInitRefExpr).get();
18046       ElemType = ElemType.getUnqualifiedType();
18047       VarDecl *VDInitTemp = buildVarDecl(*this, RefExpr->getExprLoc(), ElemType,
18048                                          ".firstprivate.temp");
18049       InitializedEntity Entity =
18050           InitializedEntity::InitializeVariable(VDInitTemp);
18051       InitializationKind Kind = InitializationKind::CreateCopy(ELoc, ELoc);
18052 
18053       InitializationSequence InitSeq(*this, Entity, Kind, Init);
18054       ExprResult Result = InitSeq.Perform(*this, Entity, Kind, Init);
18055       if (Result.isInvalid())
18056         VDPrivate->setInvalidDecl();
18057       else
18058         VDPrivate->setInit(Result.getAs<Expr>());
18059       // Remove temp variable declaration.
18060       Context.Deallocate(VDInitTemp);
18061     } else {
18062       VarDecl *VDInit = buildVarDecl(*this, RefExpr->getExprLoc(), Type,
18063                                      ".firstprivate.temp");
18064       VDInitRefExpr = buildDeclRefExpr(*this, VDInit, RefExpr->getType(),
18065                                        RefExpr->getExprLoc());
18066       AddInitializerToDecl(VDPrivate,
18067                            DefaultLvalueConversion(VDInitRefExpr).get(),
18068                            /*DirectInit=*/false);
18069     }
18070     if (VDPrivate->isInvalidDecl()) {
18071       if (IsImplicitClause) {
18072         Diag(RefExpr->getExprLoc(),
18073              diag::note_omp_task_predetermined_firstprivate_here);
18074       }
18075       continue;
18076     }
18077     CurContext->addDecl(VDPrivate);
18078     DeclRefExpr *VDPrivateRefExpr = buildDeclRefExpr(
18079         *this, VDPrivate, RefExpr->getType().getUnqualifiedType(),
18080         RefExpr->getExprLoc());
18081     DeclRefExpr *Ref = nullptr;
18082     if (!VD && !CurContext->isDependentContext()) {
18083       if (TopDVar.CKind == OMPC_lastprivate) {
18084         Ref = TopDVar.PrivateCopy;
18085       } else {
18086         auto *FD = dyn_cast<FieldDecl>(D);
18087         VarDecl *VD = FD ? DSAStack->getImplicitFDCapExprDecl(FD) : nullptr;
18088         if (VD)
18089           Ref = buildDeclRefExpr(*this, VD, VD->getType().getNonReferenceType(),
18090                                  RefExpr->getExprLoc());
18091         else
18092           Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/true);
18093         if (VD || !isOpenMPCapturedDecl(D))
18094           ExprCaptures.push_back(Ref->getDecl());
18095       }
18096     }
18097     if (!IsImplicitClause)
18098       DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_firstprivate, Ref);
18099     Vars.push_back((VD || CurContext->isDependentContext())
18100                        ? RefExpr->IgnoreParens()
18101                        : Ref);
18102     PrivateCopies.push_back(VDPrivateRefExpr);
18103     Inits.push_back(VDInitRefExpr);
18104   }
18105 
18106   if (Vars.empty())
18107     return nullptr;
18108 
18109   return OMPFirstprivateClause::Create(Context, StartLoc, LParenLoc, EndLoc,
18110                                        Vars, PrivateCopies, Inits,
18111                                        buildPreInits(Context, ExprCaptures));
18112 }
18113 
18114 OMPClause *Sema::ActOnOpenMPLastprivateClause(
18115     ArrayRef<Expr *> VarList, OpenMPLastprivateModifier LPKind,
18116     SourceLocation LPKindLoc, SourceLocation ColonLoc, SourceLocation StartLoc,
18117     SourceLocation LParenLoc, SourceLocation EndLoc) {
18118   if (LPKind == OMPC_LASTPRIVATE_unknown && LPKindLoc.isValid()) {
18119     assert(ColonLoc.isValid() && "Colon location must be valid.");
18120     Diag(LPKindLoc, diag::err_omp_unexpected_clause_value)
18121         << getListOfPossibleValues(OMPC_lastprivate, /*First=*/0,
18122                                    /*Last=*/OMPC_LASTPRIVATE_unknown)
18123         << getOpenMPClauseName(OMPC_lastprivate);
18124     return nullptr;
18125   }
18126 
18127   SmallVector<Expr *, 8> Vars;
18128   SmallVector<Expr *, 8> SrcExprs;
18129   SmallVector<Expr *, 8> DstExprs;
18130   SmallVector<Expr *, 8> AssignmentOps;
18131   SmallVector<Decl *, 4> ExprCaptures;
18132   SmallVector<Expr *, 4> ExprPostUpdates;
18133   for (Expr *RefExpr : VarList) {
18134     assert(RefExpr && "NULL expr in OpenMP lastprivate clause.");
18135     SourceLocation ELoc;
18136     SourceRange ERange;
18137     Expr *SimpleRefExpr = RefExpr;
18138     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
18139     if (Res.second) {
18140       // It will be analyzed later.
18141       Vars.push_back(RefExpr);
18142       SrcExprs.push_back(nullptr);
18143       DstExprs.push_back(nullptr);
18144       AssignmentOps.push_back(nullptr);
18145     }
18146     ValueDecl *D = Res.first;
18147     if (!D)
18148       continue;
18149 
18150     QualType Type = D->getType();
18151     auto *VD = dyn_cast<VarDecl>(D);
18152 
18153     // OpenMP [2.14.3.5, Restrictions, C/C++, p.2]
18154     //  A variable that appears in a lastprivate clause must not have an
18155     //  incomplete type or a reference type.
18156     if (RequireCompleteType(ELoc, Type,
18157                             diag::err_omp_lastprivate_incomplete_type))
18158       continue;
18159     Type = Type.getNonReferenceType();
18160 
18161     // OpenMP 5.0 [2.19.3, List Item Privatization, Restrictions]
18162     // A variable that is privatized must not have a const-qualified type
18163     // unless it is of class type with a mutable member. This restriction does
18164     // not apply to the firstprivate clause.
18165     //
18166     // OpenMP 3.1 [2.9.3.5, lastprivate clause, Restrictions]
18167     // A variable that appears in a lastprivate clause must not have a
18168     // const-qualified type unless it is of class type with a mutable member.
18169     if (rejectConstNotMutableType(*this, D, Type, OMPC_lastprivate, ELoc))
18170       continue;
18171 
18172     // OpenMP 5.0 [2.19.4.5 lastprivate Clause, Restrictions]
18173     // A list item that appears in a lastprivate clause with the conditional
18174     // modifier must be a scalar variable.
18175     if (LPKind == OMPC_LASTPRIVATE_conditional && !Type->isScalarType()) {
18176       Diag(ELoc, diag::err_omp_lastprivate_conditional_non_scalar);
18177       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
18178                                VarDecl::DeclarationOnly;
18179       Diag(D->getLocation(),
18180            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
18181           << D;
18182       continue;
18183     }
18184 
18185     OpenMPDirectiveKind CurrDir = DSAStack->getCurrentDirective();
18186     // OpenMP [2.14.1.1, Data-sharing Attribute Rules for Variables Referenced
18187     // in a Construct]
18188     //  Variables with the predetermined data-sharing attributes may not be
18189     //  listed in data-sharing attributes clauses, except for the cases
18190     //  listed below.
18191     // OpenMP 4.5 [2.10.8, Distribute Construct, p.3]
18192     // A list item may appear in a firstprivate or lastprivate clause but not
18193     // both.
18194     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(D, /*FromParent=*/false);
18195     if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_lastprivate &&
18196         (isOpenMPDistributeDirective(CurrDir) ||
18197          DVar.CKind != OMPC_firstprivate) &&
18198         (DVar.CKind != OMPC_private || DVar.RefExpr != nullptr)) {
18199       Diag(ELoc, diag::err_omp_wrong_dsa)
18200           << getOpenMPClauseName(DVar.CKind)
18201           << getOpenMPClauseName(OMPC_lastprivate);
18202       reportOriginalDsa(*this, DSAStack, D, DVar);
18203       continue;
18204     }
18205 
18206     // OpenMP [2.14.3.5, Restrictions, p.2]
18207     // A list item that is private within a parallel region, or that appears in
18208     // the reduction clause of a parallel construct, must not appear in a
18209     // lastprivate clause on a worksharing construct if any of the corresponding
18210     // worksharing regions ever binds to any of the corresponding parallel
18211     // regions.
18212     DSAStackTy::DSAVarData TopDVar = DVar;
18213     if (isOpenMPWorksharingDirective(CurrDir) &&
18214         !isOpenMPParallelDirective(CurrDir) &&
18215         !isOpenMPTeamsDirective(CurrDir)) {
18216       DVar = DSAStack->getImplicitDSA(D, true);
18217       if (DVar.CKind != OMPC_shared) {
18218         Diag(ELoc, diag::err_omp_required_access)
18219             << getOpenMPClauseName(OMPC_lastprivate)
18220             << getOpenMPClauseName(OMPC_shared);
18221         reportOriginalDsa(*this, DSAStack, D, DVar);
18222         continue;
18223       }
18224     }
18225 
18226     // OpenMP [2.14.3.5, Restrictions, C++, p.1,2]
18227     //  A variable of class type (or array thereof) that appears in a
18228     //  lastprivate clause requires an accessible, unambiguous default
18229     //  constructor for the class type, unless the list item is also specified
18230     //  in a firstprivate clause.
18231     //  A variable of class type (or array thereof) that appears in a
18232     //  lastprivate clause requires an accessible, unambiguous copy assignment
18233     //  operator for the class type.
18234     Type = Context.getBaseElementType(Type).getNonReferenceType();
18235     VarDecl *SrcVD = buildVarDecl(*this, ERange.getBegin(),
18236                                   Type.getUnqualifiedType(), ".lastprivate.src",
18237                                   D->hasAttrs() ? &D->getAttrs() : nullptr);
18238     DeclRefExpr *PseudoSrcExpr =
18239         buildDeclRefExpr(*this, SrcVD, Type.getUnqualifiedType(), ELoc);
18240     VarDecl *DstVD =
18241         buildVarDecl(*this, ERange.getBegin(), Type, ".lastprivate.dst",
18242                      D->hasAttrs() ? &D->getAttrs() : nullptr);
18243     DeclRefExpr *PseudoDstExpr = buildDeclRefExpr(*this, DstVD, Type, ELoc);
18244     // For arrays generate assignment operation for single element and replace
18245     // it by the original array element in CodeGen.
18246     ExprResult AssignmentOp = BuildBinOp(/*S=*/nullptr, ELoc, BO_Assign,
18247                                          PseudoDstExpr, PseudoSrcExpr);
18248     if (AssignmentOp.isInvalid())
18249       continue;
18250     AssignmentOp =
18251         ActOnFinishFullExpr(AssignmentOp.get(), ELoc, /*DiscardedValue*/ false);
18252     if (AssignmentOp.isInvalid())
18253       continue;
18254 
18255     DeclRefExpr *Ref = nullptr;
18256     if (!VD && !CurContext->isDependentContext()) {
18257       if (TopDVar.CKind == OMPC_firstprivate) {
18258         Ref = TopDVar.PrivateCopy;
18259       } else {
18260         Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/false);
18261         if (!isOpenMPCapturedDecl(D))
18262           ExprCaptures.push_back(Ref->getDecl());
18263       }
18264       if ((TopDVar.CKind == OMPC_firstprivate && !TopDVar.PrivateCopy) ||
18265           (!isOpenMPCapturedDecl(D) &&
18266            Ref->getDecl()->hasAttr<OMPCaptureNoInitAttr>())) {
18267         ExprResult RefRes = DefaultLvalueConversion(Ref);
18268         if (!RefRes.isUsable())
18269           continue;
18270         ExprResult PostUpdateRes =
18271             BuildBinOp(DSAStack->getCurScope(), ELoc, BO_Assign, SimpleRefExpr,
18272                        RefRes.get());
18273         if (!PostUpdateRes.isUsable())
18274           continue;
18275         ExprPostUpdates.push_back(
18276             IgnoredValueConversions(PostUpdateRes.get()).get());
18277       }
18278     }
18279     DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_lastprivate, Ref);
18280     Vars.push_back((VD || CurContext->isDependentContext())
18281                        ? RefExpr->IgnoreParens()
18282                        : Ref);
18283     SrcExprs.push_back(PseudoSrcExpr);
18284     DstExprs.push_back(PseudoDstExpr);
18285     AssignmentOps.push_back(AssignmentOp.get());
18286   }
18287 
18288   if (Vars.empty())
18289     return nullptr;
18290 
18291   return OMPLastprivateClause::Create(Context, StartLoc, LParenLoc, EndLoc,
18292                                       Vars, SrcExprs, DstExprs, AssignmentOps,
18293                                       LPKind, LPKindLoc, ColonLoc,
18294                                       buildPreInits(Context, ExprCaptures),
18295                                       buildPostUpdate(*this, ExprPostUpdates));
18296 }
18297 
18298 OMPClause *Sema::ActOnOpenMPSharedClause(ArrayRef<Expr *> VarList,
18299                                          SourceLocation StartLoc,
18300                                          SourceLocation LParenLoc,
18301                                          SourceLocation EndLoc) {
18302   SmallVector<Expr *, 8> Vars;
18303   for (Expr *RefExpr : VarList) {
18304     assert(RefExpr && "NULL expr in OpenMP lastprivate clause.");
18305     SourceLocation ELoc;
18306     SourceRange ERange;
18307     Expr *SimpleRefExpr = RefExpr;
18308     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
18309     if (Res.second) {
18310       // It will be analyzed later.
18311       Vars.push_back(RefExpr);
18312     }
18313     ValueDecl *D = Res.first;
18314     if (!D)
18315       continue;
18316 
18317     auto *VD = dyn_cast<VarDecl>(D);
18318     // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
18319     // in a Construct]
18320     //  Variables with the predetermined data-sharing attributes may not be
18321     //  listed in data-sharing attributes clauses, except for the cases
18322     //  listed below. For these exceptions only, listing a predetermined
18323     //  variable in a data-sharing attribute clause is allowed and overrides
18324     //  the variable's predetermined data-sharing attributes.
18325     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(D, /*FromParent=*/false);
18326     if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_shared &&
18327         DVar.RefExpr) {
18328       Diag(ELoc, diag::err_omp_wrong_dsa) << getOpenMPClauseName(DVar.CKind)
18329                                           << getOpenMPClauseName(OMPC_shared);
18330       reportOriginalDsa(*this, DSAStack, D, DVar);
18331       continue;
18332     }
18333 
18334     DeclRefExpr *Ref = nullptr;
18335     if (!VD && isOpenMPCapturedDecl(D) && !CurContext->isDependentContext())
18336       Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/true);
18337     DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_shared, Ref);
18338     Vars.push_back((VD || !Ref || CurContext->isDependentContext())
18339                        ? RefExpr->IgnoreParens()
18340                        : Ref);
18341   }
18342 
18343   if (Vars.empty())
18344     return nullptr;
18345 
18346   return OMPSharedClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars);
18347 }
18348 
18349 namespace {
18350 class DSARefChecker : public StmtVisitor<DSARefChecker, bool> {
18351   DSAStackTy *Stack;
18352 
18353 public:
18354   bool VisitDeclRefExpr(DeclRefExpr *E) {
18355     if (auto *VD = dyn_cast<VarDecl>(E->getDecl())) {
18356       DSAStackTy::DSAVarData DVar = Stack->getTopDSA(VD, /*FromParent=*/false);
18357       if (DVar.CKind == OMPC_shared && !DVar.RefExpr)
18358         return false;
18359       if (DVar.CKind != OMPC_unknown)
18360         return true;
18361       DSAStackTy::DSAVarData DVarPrivate = Stack->hasDSA(
18362           VD,
18363           [](OpenMPClauseKind C, bool AppliedToPointee, bool) {
18364             return isOpenMPPrivate(C) && !AppliedToPointee;
18365           },
18366           [](OpenMPDirectiveKind) { return true; },
18367           /*FromParent=*/true);
18368       return DVarPrivate.CKind != OMPC_unknown;
18369     }
18370     return false;
18371   }
18372   bool VisitStmt(Stmt *S) {
18373     for (Stmt *Child : S->children()) {
18374       if (Child && Visit(Child))
18375         return true;
18376     }
18377     return false;
18378   }
18379   explicit DSARefChecker(DSAStackTy *S) : Stack(S) {}
18380 };
18381 } // namespace
18382 
18383 namespace {
18384 // Transform MemberExpression for specified FieldDecl of current class to
18385 // DeclRefExpr to specified OMPCapturedExprDecl.
18386 class TransformExprToCaptures : public TreeTransform<TransformExprToCaptures> {
18387   typedef TreeTransform<TransformExprToCaptures> BaseTransform;
18388   ValueDecl *Field = nullptr;
18389   DeclRefExpr *CapturedExpr = nullptr;
18390 
18391 public:
18392   TransformExprToCaptures(Sema &SemaRef, ValueDecl *FieldDecl)
18393       : BaseTransform(SemaRef), Field(FieldDecl), CapturedExpr(nullptr) {}
18394 
18395   ExprResult TransformMemberExpr(MemberExpr *E) {
18396     if (isa<CXXThisExpr>(E->getBase()->IgnoreParenImpCasts()) &&
18397         E->getMemberDecl() == Field) {
18398       CapturedExpr = buildCapture(SemaRef, Field, E, /*WithInit=*/false);
18399       return CapturedExpr;
18400     }
18401     return BaseTransform::TransformMemberExpr(E);
18402   }
18403   DeclRefExpr *getCapturedExpr() { return CapturedExpr; }
18404 };
18405 } // namespace
18406 
18407 template <typename T, typename U>
18408 static T filterLookupForUDReductionAndMapper(
18409     SmallVectorImpl<U> &Lookups, const llvm::function_ref<T(ValueDecl *)> Gen) {
18410   for (U &Set : Lookups) {
18411     for (auto *D : Set) {
18412       if (T Res = Gen(cast<ValueDecl>(D)))
18413         return Res;
18414     }
18415   }
18416   return T();
18417 }
18418 
18419 static NamedDecl *findAcceptableDecl(Sema &SemaRef, NamedDecl *D) {
18420   assert(!LookupResult::isVisible(SemaRef, D) && "not in slow case");
18421 
18422   for (auto RD : D->redecls()) {
18423     // Don't bother with extra checks if we already know this one isn't visible.
18424     if (RD == D)
18425       continue;
18426 
18427     auto ND = cast<NamedDecl>(RD);
18428     if (LookupResult::isVisible(SemaRef, ND))
18429       return ND;
18430   }
18431 
18432   return nullptr;
18433 }
18434 
18435 static void
18436 argumentDependentLookup(Sema &SemaRef, const DeclarationNameInfo &Id,
18437                         SourceLocation Loc, QualType Ty,
18438                         SmallVectorImpl<UnresolvedSet<8>> &Lookups) {
18439   // Find all of the associated namespaces and classes based on the
18440   // arguments we have.
18441   Sema::AssociatedNamespaceSet AssociatedNamespaces;
18442   Sema::AssociatedClassSet AssociatedClasses;
18443   OpaqueValueExpr OVE(Loc, Ty, VK_LValue);
18444   SemaRef.FindAssociatedClassesAndNamespaces(Loc, &OVE, AssociatedNamespaces,
18445                                              AssociatedClasses);
18446 
18447   // C++ [basic.lookup.argdep]p3:
18448   //   Let X be the lookup set produced by unqualified lookup (3.4.1)
18449   //   and let Y be the lookup set produced by argument dependent
18450   //   lookup (defined as follows). If X contains [...] then Y is
18451   //   empty. Otherwise Y is the set of declarations found in the
18452   //   namespaces associated with the argument types as described
18453   //   below. The set of declarations found by the lookup of the name
18454   //   is the union of X and Y.
18455   //
18456   // Here, we compute Y and add its members to the overloaded
18457   // candidate set.
18458   for (auto *NS : AssociatedNamespaces) {
18459     //   When considering an associated namespace, the lookup is the
18460     //   same as the lookup performed when the associated namespace is
18461     //   used as a qualifier (3.4.3.2) except that:
18462     //
18463     //     -- Any using-directives in the associated namespace are
18464     //        ignored.
18465     //
18466     //     -- Any namespace-scope friend functions declared in
18467     //        associated classes are visible within their respective
18468     //        namespaces even if they are not visible during an ordinary
18469     //        lookup (11.4).
18470     DeclContext::lookup_result R = NS->lookup(Id.getName());
18471     for (auto *D : R) {
18472       auto *Underlying = D;
18473       if (auto *USD = dyn_cast<UsingShadowDecl>(D))
18474         Underlying = USD->getTargetDecl();
18475 
18476       if (!isa<OMPDeclareReductionDecl>(Underlying) &&
18477           !isa<OMPDeclareMapperDecl>(Underlying))
18478         continue;
18479 
18480       if (!SemaRef.isVisible(D)) {
18481         D = findAcceptableDecl(SemaRef, D);
18482         if (!D)
18483           continue;
18484         if (auto *USD = dyn_cast<UsingShadowDecl>(D))
18485           Underlying = USD->getTargetDecl();
18486       }
18487       Lookups.emplace_back();
18488       Lookups.back().addDecl(Underlying);
18489     }
18490   }
18491 }
18492 
18493 static ExprResult
18494 buildDeclareReductionRef(Sema &SemaRef, SourceLocation Loc, SourceRange Range,
18495                          Scope *S, CXXScopeSpec &ReductionIdScopeSpec,
18496                          const DeclarationNameInfo &ReductionId, QualType Ty,
18497                          CXXCastPath &BasePath, Expr *UnresolvedReduction) {
18498   if (ReductionIdScopeSpec.isInvalid())
18499     return ExprError();
18500   SmallVector<UnresolvedSet<8>, 4> Lookups;
18501   if (S) {
18502     LookupResult Lookup(SemaRef, ReductionId, Sema::LookupOMPReductionName);
18503     Lookup.suppressDiagnostics();
18504     while (S && SemaRef.LookupParsedName(Lookup, S, &ReductionIdScopeSpec)) {
18505       NamedDecl *D = Lookup.getRepresentativeDecl();
18506       do {
18507         S = S->getParent();
18508       } while (S && !S->isDeclScope(D));
18509       if (S)
18510         S = S->getParent();
18511       Lookups.emplace_back();
18512       Lookups.back().append(Lookup.begin(), Lookup.end());
18513       Lookup.clear();
18514     }
18515   } else if (auto *ULE =
18516                  cast_or_null<UnresolvedLookupExpr>(UnresolvedReduction)) {
18517     Lookups.push_back(UnresolvedSet<8>());
18518     Decl *PrevD = nullptr;
18519     for (NamedDecl *D : ULE->decls()) {
18520       if (D == PrevD)
18521         Lookups.push_back(UnresolvedSet<8>());
18522       else if (auto *DRD = dyn_cast<OMPDeclareReductionDecl>(D))
18523         Lookups.back().addDecl(DRD);
18524       PrevD = D;
18525     }
18526   }
18527   if (SemaRef.CurContext->isDependentContext() || Ty->isDependentType() ||
18528       Ty->isInstantiationDependentType() ||
18529       Ty->containsUnexpandedParameterPack() ||
18530       filterLookupForUDReductionAndMapper<bool>(Lookups, [](ValueDecl *D) {
18531         return !D->isInvalidDecl() &&
18532                (D->getType()->isDependentType() ||
18533                 D->getType()->isInstantiationDependentType() ||
18534                 D->getType()->containsUnexpandedParameterPack());
18535       })) {
18536     UnresolvedSet<8> ResSet;
18537     for (const UnresolvedSet<8> &Set : Lookups) {
18538       if (Set.empty())
18539         continue;
18540       ResSet.append(Set.begin(), Set.end());
18541       // The last item marks the end of all declarations at the specified scope.
18542       ResSet.addDecl(Set[Set.size() - 1]);
18543     }
18544     return UnresolvedLookupExpr::Create(
18545         SemaRef.Context, /*NamingClass=*/nullptr,
18546         ReductionIdScopeSpec.getWithLocInContext(SemaRef.Context), ReductionId,
18547         /*ADL=*/true, /*Overloaded=*/true, ResSet.begin(), ResSet.end());
18548   }
18549   // Lookup inside the classes.
18550   // C++ [over.match.oper]p3:
18551   //   For a unary operator @ with an operand of a type whose
18552   //   cv-unqualified version is T1, and for a binary operator @ with
18553   //   a left operand of a type whose cv-unqualified version is T1 and
18554   //   a right operand of a type whose cv-unqualified version is T2,
18555   //   three sets of candidate functions, designated member
18556   //   candidates, non-member candidates and built-in candidates, are
18557   //   constructed as follows:
18558   //     -- If T1 is a complete class type or a class currently being
18559   //        defined, the set of member candidates is the result of the
18560   //        qualified lookup of T1::operator@ (13.3.1.1.1); otherwise,
18561   //        the set of member candidates is empty.
18562   LookupResult Lookup(SemaRef, ReductionId, Sema::LookupOMPReductionName);
18563   Lookup.suppressDiagnostics();
18564   if (const auto *TyRec = Ty->getAs<RecordType>()) {
18565     // Complete the type if it can be completed.
18566     // If the type is neither complete nor being defined, bail out now.
18567     if (SemaRef.isCompleteType(Loc, Ty) || TyRec->isBeingDefined() ||
18568         TyRec->getDecl()->getDefinition()) {
18569       Lookup.clear();
18570       SemaRef.LookupQualifiedName(Lookup, TyRec->getDecl());
18571       if (Lookup.empty()) {
18572         Lookups.emplace_back();
18573         Lookups.back().append(Lookup.begin(), Lookup.end());
18574       }
18575     }
18576   }
18577   // Perform ADL.
18578   if (SemaRef.getLangOpts().CPlusPlus)
18579     argumentDependentLookup(SemaRef, ReductionId, Loc, Ty, Lookups);
18580   if (auto *VD = filterLookupForUDReductionAndMapper<ValueDecl *>(
18581           Lookups, [&SemaRef, Ty](ValueDecl *D) -> ValueDecl * {
18582             if (!D->isInvalidDecl() &&
18583                 SemaRef.Context.hasSameType(D->getType(), Ty))
18584               return D;
18585             return nullptr;
18586           }))
18587     return SemaRef.BuildDeclRefExpr(VD, VD->getType().getNonReferenceType(),
18588                                     VK_LValue, Loc);
18589   if (SemaRef.getLangOpts().CPlusPlus) {
18590     if (auto *VD = filterLookupForUDReductionAndMapper<ValueDecl *>(
18591             Lookups, [&SemaRef, Ty, Loc](ValueDecl *D) -> ValueDecl * {
18592               if (!D->isInvalidDecl() &&
18593                   SemaRef.IsDerivedFrom(Loc, Ty, D->getType()) &&
18594                   !Ty.isMoreQualifiedThan(D->getType()))
18595                 return D;
18596               return nullptr;
18597             })) {
18598       CXXBasePaths Paths(/*FindAmbiguities=*/true, /*RecordPaths=*/true,
18599                          /*DetectVirtual=*/false);
18600       if (SemaRef.IsDerivedFrom(Loc, Ty, VD->getType(), Paths)) {
18601         if (!Paths.isAmbiguous(SemaRef.Context.getCanonicalType(
18602                 VD->getType().getUnqualifiedType()))) {
18603           if (SemaRef.CheckBaseClassAccess(
18604                   Loc, VD->getType(), Ty, Paths.front(),
18605                   /*DiagID=*/0) != Sema::AR_inaccessible) {
18606             SemaRef.BuildBasePathArray(Paths, BasePath);
18607             return SemaRef.BuildDeclRefExpr(
18608                 VD, VD->getType().getNonReferenceType(), VK_LValue, Loc);
18609           }
18610         }
18611       }
18612     }
18613   }
18614   if (ReductionIdScopeSpec.isSet()) {
18615     SemaRef.Diag(Loc, diag::err_omp_not_resolved_reduction_identifier)
18616         << Ty << Range;
18617     return ExprError();
18618   }
18619   return ExprEmpty();
18620 }
18621 
18622 namespace {
18623 /// Data for the reduction-based clauses.
18624 struct ReductionData {
18625   /// List of original reduction items.
18626   SmallVector<Expr *, 8> Vars;
18627   /// List of private copies of the reduction items.
18628   SmallVector<Expr *, 8> Privates;
18629   /// LHS expressions for the reduction_op expressions.
18630   SmallVector<Expr *, 8> LHSs;
18631   /// RHS expressions for the reduction_op expressions.
18632   SmallVector<Expr *, 8> RHSs;
18633   /// Reduction operation expression.
18634   SmallVector<Expr *, 8> ReductionOps;
18635   /// inscan copy operation expressions.
18636   SmallVector<Expr *, 8> InscanCopyOps;
18637   /// inscan copy temp array expressions for prefix sums.
18638   SmallVector<Expr *, 8> InscanCopyArrayTemps;
18639   /// inscan copy temp array element expressions for prefix sums.
18640   SmallVector<Expr *, 8> InscanCopyArrayElems;
18641   /// Taskgroup descriptors for the corresponding reduction items in
18642   /// in_reduction clauses.
18643   SmallVector<Expr *, 8> TaskgroupDescriptors;
18644   /// List of captures for clause.
18645   SmallVector<Decl *, 4> ExprCaptures;
18646   /// List of postupdate expressions.
18647   SmallVector<Expr *, 4> ExprPostUpdates;
18648   /// Reduction modifier.
18649   unsigned RedModifier = 0;
18650   ReductionData() = delete;
18651   /// Reserves required memory for the reduction data.
18652   ReductionData(unsigned Size, unsigned Modifier = 0) : RedModifier(Modifier) {
18653     Vars.reserve(Size);
18654     Privates.reserve(Size);
18655     LHSs.reserve(Size);
18656     RHSs.reserve(Size);
18657     ReductionOps.reserve(Size);
18658     if (RedModifier == OMPC_REDUCTION_inscan) {
18659       InscanCopyOps.reserve(Size);
18660       InscanCopyArrayTemps.reserve(Size);
18661       InscanCopyArrayElems.reserve(Size);
18662     }
18663     TaskgroupDescriptors.reserve(Size);
18664     ExprCaptures.reserve(Size);
18665     ExprPostUpdates.reserve(Size);
18666   }
18667   /// Stores reduction item and reduction operation only (required for dependent
18668   /// reduction item).
18669   void push(Expr *Item, Expr *ReductionOp) {
18670     Vars.emplace_back(Item);
18671     Privates.emplace_back(nullptr);
18672     LHSs.emplace_back(nullptr);
18673     RHSs.emplace_back(nullptr);
18674     ReductionOps.emplace_back(ReductionOp);
18675     TaskgroupDescriptors.emplace_back(nullptr);
18676     if (RedModifier == OMPC_REDUCTION_inscan) {
18677       InscanCopyOps.push_back(nullptr);
18678       InscanCopyArrayTemps.push_back(nullptr);
18679       InscanCopyArrayElems.push_back(nullptr);
18680     }
18681   }
18682   /// Stores reduction data.
18683   void push(Expr *Item, Expr *Private, Expr *LHS, Expr *RHS, Expr *ReductionOp,
18684             Expr *TaskgroupDescriptor, Expr *CopyOp, Expr *CopyArrayTemp,
18685             Expr *CopyArrayElem) {
18686     Vars.emplace_back(Item);
18687     Privates.emplace_back(Private);
18688     LHSs.emplace_back(LHS);
18689     RHSs.emplace_back(RHS);
18690     ReductionOps.emplace_back(ReductionOp);
18691     TaskgroupDescriptors.emplace_back(TaskgroupDescriptor);
18692     if (RedModifier == OMPC_REDUCTION_inscan) {
18693       InscanCopyOps.push_back(CopyOp);
18694       InscanCopyArrayTemps.push_back(CopyArrayTemp);
18695       InscanCopyArrayElems.push_back(CopyArrayElem);
18696     } else {
18697       assert(CopyOp == nullptr && CopyArrayTemp == nullptr &&
18698              CopyArrayElem == nullptr &&
18699              "Copy operation must be used for inscan reductions only.");
18700     }
18701   }
18702 };
18703 } // namespace
18704 
18705 static bool checkOMPArraySectionConstantForReduction(
18706     ASTContext &Context, const OMPArraySectionExpr *OASE, bool &SingleElement,
18707     SmallVectorImpl<llvm::APSInt> &ArraySizes) {
18708   const Expr *Length = OASE->getLength();
18709   if (Length == nullptr) {
18710     // For array sections of the form [1:] or [:], we would need to analyze
18711     // the lower bound...
18712     if (OASE->getColonLocFirst().isValid())
18713       return false;
18714 
18715     // This is an array subscript which has implicit length 1!
18716     SingleElement = true;
18717     ArraySizes.push_back(llvm::APSInt::get(1));
18718   } else {
18719     Expr::EvalResult Result;
18720     if (!Length->EvaluateAsInt(Result, Context))
18721       return false;
18722 
18723     llvm::APSInt ConstantLengthValue = Result.Val.getInt();
18724     SingleElement = (ConstantLengthValue.getSExtValue() == 1);
18725     ArraySizes.push_back(ConstantLengthValue);
18726   }
18727 
18728   // Get the base of this array section and walk up from there.
18729   const Expr *Base = OASE->getBase()->IgnoreParenImpCasts();
18730 
18731   // We require length = 1 for all array sections except the right-most to
18732   // guarantee that the memory region is contiguous and has no holes in it.
18733   while (const auto *TempOASE = dyn_cast<OMPArraySectionExpr>(Base)) {
18734     Length = TempOASE->getLength();
18735     if (Length == nullptr) {
18736       // For array sections of the form [1:] or [:], we would need to analyze
18737       // the lower bound...
18738       if (OASE->getColonLocFirst().isValid())
18739         return false;
18740 
18741       // This is an array subscript which has implicit length 1!
18742       ArraySizes.push_back(llvm::APSInt::get(1));
18743     } else {
18744       Expr::EvalResult Result;
18745       if (!Length->EvaluateAsInt(Result, Context))
18746         return false;
18747 
18748       llvm::APSInt ConstantLengthValue = Result.Val.getInt();
18749       if (ConstantLengthValue.getSExtValue() != 1)
18750         return false;
18751 
18752       ArraySizes.push_back(ConstantLengthValue);
18753     }
18754     Base = TempOASE->getBase()->IgnoreParenImpCasts();
18755   }
18756 
18757   // If we have a single element, we don't need to add the implicit lengths.
18758   if (!SingleElement) {
18759     while (const auto *TempASE = dyn_cast<ArraySubscriptExpr>(Base)) {
18760       // Has implicit length 1!
18761       ArraySizes.push_back(llvm::APSInt::get(1));
18762       Base = TempASE->getBase()->IgnoreParenImpCasts();
18763     }
18764   }
18765 
18766   // This array section can be privatized as a single value or as a constant
18767   // sized array.
18768   return true;
18769 }
18770 
18771 static BinaryOperatorKind
18772 getRelatedCompoundReductionOp(BinaryOperatorKind BOK) {
18773   if (BOK == BO_Add)
18774     return BO_AddAssign;
18775   if (BOK == BO_Mul)
18776     return BO_MulAssign;
18777   if (BOK == BO_And)
18778     return BO_AndAssign;
18779   if (BOK == BO_Or)
18780     return BO_OrAssign;
18781   if (BOK == BO_Xor)
18782     return BO_XorAssign;
18783   return BOK;
18784 }
18785 
18786 static bool actOnOMPReductionKindClause(
18787     Sema &S, DSAStackTy *Stack, OpenMPClauseKind ClauseKind,
18788     ArrayRef<Expr *> VarList, SourceLocation StartLoc, SourceLocation LParenLoc,
18789     SourceLocation ColonLoc, SourceLocation EndLoc,
18790     CXXScopeSpec &ReductionIdScopeSpec, const DeclarationNameInfo &ReductionId,
18791     ArrayRef<Expr *> UnresolvedReductions, ReductionData &RD) {
18792   DeclarationName DN = ReductionId.getName();
18793   OverloadedOperatorKind OOK = DN.getCXXOverloadedOperator();
18794   BinaryOperatorKind BOK = BO_Comma;
18795 
18796   ASTContext &Context = S.Context;
18797   // OpenMP [2.14.3.6, reduction clause]
18798   // C
18799   // reduction-identifier is either an identifier or one of the following
18800   // operators: +, -, *,  &, |, ^, && and ||
18801   // C++
18802   // reduction-identifier is either an id-expression or one of the following
18803   // operators: +, -, *, &, |, ^, && and ||
18804   switch (OOK) {
18805   case OO_Plus:
18806   case OO_Minus:
18807     BOK = BO_Add;
18808     break;
18809   case OO_Star:
18810     BOK = BO_Mul;
18811     break;
18812   case OO_Amp:
18813     BOK = BO_And;
18814     break;
18815   case OO_Pipe:
18816     BOK = BO_Or;
18817     break;
18818   case OO_Caret:
18819     BOK = BO_Xor;
18820     break;
18821   case OO_AmpAmp:
18822     BOK = BO_LAnd;
18823     break;
18824   case OO_PipePipe:
18825     BOK = BO_LOr;
18826     break;
18827   case OO_New:
18828   case OO_Delete:
18829   case OO_Array_New:
18830   case OO_Array_Delete:
18831   case OO_Slash:
18832   case OO_Percent:
18833   case OO_Tilde:
18834   case OO_Exclaim:
18835   case OO_Equal:
18836   case OO_Less:
18837   case OO_Greater:
18838   case OO_LessEqual:
18839   case OO_GreaterEqual:
18840   case OO_PlusEqual:
18841   case OO_MinusEqual:
18842   case OO_StarEqual:
18843   case OO_SlashEqual:
18844   case OO_PercentEqual:
18845   case OO_CaretEqual:
18846   case OO_AmpEqual:
18847   case OO_PipeEqual:
18848   case OO_LessLess:
18849   case OO_GreaterGreater:
18850   case OO_LessLessEqual:
18851   case OO_GreaterGreaterEqual:
18852   case OO_EqualEqual:
18853   case OO_ExclaimEqual:
18854   case OO_Spaceship:
18855   case OO_PlusPlus:
18856   case OO_MinusMinus:
18857   case OO_Comma:
18858   case OO_ArrowStar:
18859   case OO_Arrow:
18860   case OO_Call:
18861   case OO_Subscript:
18862   case OO_Conditional:
18863   case OO_Coawait:
18864   case NUM_OVERLOADED_OPERATORS:
18865     llvm_unreachable("Unexpected reduction identifier");
18866   case OO_None:
18867     if (IdentifierInfo *II = DN.getAsIdentifierInfo()) {
18868       if (II->isStr("max"))
18869         BOK = BO_GT;
18870       else if (II->isStr("min"))
18871         BOK = BO_LT;
18872     }
18873     break;
18874   }
18875   SourceRange ReductionIdRange;
18876   if (ReductionIdScopeSpec.isValid())
18877     ReductionIdRange.setBegin(ReductionIdScopeSpec.getBeginLoc());
18878   else
18879     ReductionIdRange.setBegin(ReductionId.getBeginLoc());
18880   ReductionIdRange.setEnd(ReductionId.getEndLoc());
18881 
18882   auto IR = UnresolvedReductions.begin(), ER = UnresolvedReductions.end();
18883   bool FirstIter = true;
18884   for (Expr *RefExpr : VarList) {
18885     assert(RefExpr && "nullptr expr in OpenMP reduction clause.");
18886     // OpenMP [2.1, C/C++]
18887     //  A list item is a variable or array section, subject to the restrictions
18888     //  specified in Section 2.4 on page 42 and in each of the sections
18889     // describing clauses and directives for which a list appears.
18890     // OpenMP  [2.14.3.3, Restrictions, p.1]
18891     //  A variable that is part of another variable (as an array or
18892     //  structure element) cannot appear in a private clause.
18893     if (!FirstIter && IR != ER)
18894       ++IR;
18895     FirstIter = false;
18896     SourceLocation ELoc;
18897     SourceRange ERange;
18898     Expr *SimpleRefExpr = RefExpr;
18899     auto Res = getPrivateItem(S, SimpleRefExpr, ELoc, ERange,
18900                               /*AllowArraySection=*/true);
18901     if (Res.second) {
18902       // Try to find 'declare reduction' corresponding construct before using
18903       // builtin/overloaded operators.
18904       QualType Type = Context.DependentTy;
18905       CXXCastPath BasePath;
18906       ExprResult DeclareReductionRef = buildDeclareReductionRef(
18907           S, ELoc, ERange, Stack->getCurScope(), ReductionIdScopeSpec,
18908           ReductionId, Type, BasePath, IR == ER ? nullptr : *IR);
18909       Expr *ReductionOp = nullptr;
18910       if (S.CurContext->isDependentContext() &&
18911           (DeclareReductionRef.isUnset() ||
18912            isa<UnresolvedLookupExpr>(DeclareReductionRef.get())))
18913         ReductionOp = DeclareReductionRef.get();
18914       // It will be analyzed later.
18915       RD.push(RefExpr, ReductionOp);
18916     }
18917     ValueDecl *D = Res.first;
18918     if (!D)
18919       continue;
18920 
18921     Expr *TaskgroupDescriptor = nullptr;
18922     QualType Type;
18923     auto *ASE = dyn_cast<ArraySubscriptExpr>(RefExpr->IgnoreParens());
18924     auto *OASE = dyn_cast<OMPArraySectionExpr>(RefExpr->IgnoreParens());
18925     if (ASE) {
18926       Type = ASE->getType().getNonReferenceType();
18927     } else if (OASE) {
18928       QualType BaseType =
18929           OMPArraySectionExpr::getBaseOriginalType(OASE->getBase());
18930       if (const auto *ATy = BaseType->getAsArrayTypeUnsafe())
18931         Type = ATy->getElementType();
18932       else
18933         Type = BaseType->getPointeeType();
18934       Type = Type.getNonReferenceType();
18935     } else {
18936       Type = Context.getBaseElementType(D->getType().getNonReferenceType());
18937     }
18938     auto *VD = dyn_cast<VarDecl>(D);
18939 
18940     // OpenMP [2.9.3.3, Restrictions, C/C++, p.3]
18941     //  A variable that appears in a private clause must not have an incomplete
18942     //  type or a reference type.
18943     if (S.RequireCompleteType(ELoc, D->getType(),
18944                               diag::err_omp_reduction_incomplete_type))
18945       continue;
18946     // OpenMP [2.14.3.6, reduction clause, Restrictions]
18947     // A list item that appears in a reduction clause must not be
18948     // const-qualified.
18949     if (rejectConstNotMutableType(S, D, Type, ClauseKind, ELoc,
18950                                   /*AcceptIfMutable*/ false, ASE || OASE))
18951       continue;
18952 
18953     OpenMPDirectiveKind CurrDir = Stack->getCurrentDirective();
18954     // OpenMP [2.9.3.6, Restrictions, C/C++, p.4]
18955     //  If a list-item is a reference type then it must bind to the same object
18956     //  for all threads of the team.
18957     if (!ASE && !OASE) {
18958       if (VD) {
18959         VarDecl *VDDef = VD->getDefinition();
18960         if (VD->getType()->isReferenceType() && VDDef && VDDef->hasInit()) {
18961           DSARefChecker Check(Stack);
18962           if (Check.Visit(VDDef->getInit())) {
18963             S.Diag(ELoc, diag::err_omp_reduction_ref_type_arg)
18964                 << getOpenMPClauseName(ClauseKind) << ERange;
18965             S.Diag(VDDef->getLocation(), diag::note_defined_here) << VDDef;
18966             continue;
18967           }
18968         }
18969       }
18970 
18971       // OpenMP [2.14.1.1, Data-sharing Attribute Rules for Variables Referenced
18972       // in a Construct]
18973       //  Variables with the predetermined data-sharing attributes may not be
18974       //  listed in data-sharing attributes clauses, except for the cases
18975       //  listed below. For these exceptions only, listing a predetermined
18976       //  variable in a data-sharing attribute clause is allowed and overrides
18977       //  the variable's predetermined data-sharing attributes.
18978       // OpenMP [2.14.3.6, Restrictions, p.3]
18979       //  Any number of reduction clauses can be specified on the directive,
18980       //  but a list item can appear only once in the reduction clauses for that
18981       //  directive.
18982       DSAStackTy::DSAVarData DVar = Stack->getTopDSA(D, /*FromParent=*/false);
18983       if (DVar.CKind == OMPC_reduction) {
18984         S.Diag(ELoc, diag::err_omp_once_referenced)
18985             << getOpenMPClauseName(ClauseKind);
18986         if (DVar.RefExpr)
18987           S.Diag(DVar.RefExpr->getExprLoc(), diag::note_omp_referenced);
18988         continue;
18989       }
18990       if (DVar.CKind != OMPC_unknown) {
18991         S.Diag(ELoc, diag::err_omp_wrong_dsa)
18992             << getOpenMPClauseName(DVar.CKind)
18993             << getOpenMPClauseName(OMPC_reduction);
18994         reportOriginalDsa(S, Stack, D, DVar);
18995         continue;
18996       }
18997 
18998       // OpenMP [2.14.3.6, Restrictions, p.1]
18999       //  A list item that appears in a reduction clause of a worksharing
19000       //  construct must be shared in the parallel regions to which any of the
19001       //  worksharing regions arising from the worksharing construct bind.
19002       if (isOpenMPWorksharingDirective(CurrDir) &&
19003           !isOpenMPParallelDirective(CurrDir) &&
19004           !isOpenMPTeamsDirective(CurrDir)) {
19005         DVar = Stack->getImplicitDSA(D, true);
19006         if (DVar.CKind != OMPC_shared) {
19007           S.Diag(ELoc, diag::err_omp_required_access)
19008               << getOpenMPClauseName(OMPC_reduction)
19009               << getOpenMPClauseName(OMPC_shared);
19010           reportOriginalDsa(S, Stack, D, DVar);
19011           continue;
19012         }
19013       }
19014     } else {
19015       // Threadprivates cannot be shared between threads, so dignose if the base
19016       // is a threadprivate variable.
19017       DSAStackTy::DSAVarData DVar = Stack->getTopDSA(D, /*FromParent=*/false);
19018       if (DVar.CKind == OMPC_threadprivate) {
19019         S.Diag(ELoc, diag::err_omp_wrong_dsa)
19020             << getOpenMPClauseName(DVar.CKind)
19021             << getOpenMPClauseName(OMPC_reduction);
19022         reportOriginalDsa(S, Stack, D, DVar);
19023         continue;
19024       }
19025     }
19026 
19027     // Try to find 'declare reduction' corresponding construct before using
19028     // builtin/overloaded operators.
19029     CXXCastPath BasePath;
19030     ExprResult DeclareReductionRef = buildDeclareReductionRef(
19031         S, ELoc, ERange, Stack->getCurScope(), ReductionIdScopeSpec,
19032         ReductionId, Type, BasePath, IR == ER ? nullptr : *IR);
19033     if (DeclareReductionRef.isInvalid())
19034       continue;
19035     if (S.CurContext->isDependentContext() &&
19036         (DeclareReductionRef.isUnset() ||
19037          isa<UnresolvedLookupExpr>(DeclareReductionRef.get()))) {
19038       RD.push(RefExpr, DeclareReductionRef.get());
19039       continue;
19040     }
19041     if (BOK == BO_Comma && DeclareReductionRef.isUnset()) {
19042       // Not allowed reduction identifier is found.
19043       S.Diag(ReductionId.getBeginLoc(),
19044              diag::err_omp_unknown_reduction_identifier)
19045           << Type << ReductionIdRange;
19046       continue;
19047     }
19048 
19049     // OpenMP [2.14.3.6, reduction clause, Restrictions]
19050     // The type of a list item that appears in a reduction clause must be valid
19051     // for the reduction-identifier. For a max or min reduction in C, the type
19052     // of the list item must be an allowed arithmetic data type: char, int,
19053     // float, double, or _Bool, possibly modified with long, short, signed, or
19054     // unsigned. For a max or min reduction in C++, the type of the list item
19055     // must be an allowed arithmetic data type: char, wchar_t, int, float,
19056     // double, or bool, possibly modified with long, short, signed, or unsigned.
19057     if (DeclareReductionRef.isUnset()) {
19058       if ((BOK == BO_GT || BOK == BO_LT) &&
19059           !(Type->isScalarType() ||
19060             (S.getLangOpts().CPlusPlus && Type->isArithmeticType()))) {
19061         S.Diag(ELoc, diag::err_omp_clause_not_arithmetic_type_arg)
19062             << getOpenMPClauseName(ClauseKind) << S.getLangOpts().CPlusPlus;
19063         if (!ASE && !OASE) {
19064           bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
19065                                    VarDecl::DeclarationOnly;
19066           S.Diag(D->getLocation(),
19067                  IsDecl ? diag::note_previous_decl : diag::note_defined_here)
19068               << D;
19069         }
19070         continue;
19071       }
19072       if ((BOK == BO_OrAssign || BOK == BO_AndAssign || BOK == BO_XorAssign) &&
19073           !S.getLangOpts().CPlusPlus && Type->isFloatingType()) {
19074         S.Diag(ELoc, diag::err_omp_clause_floating_type_arg)
19075             << getOpenMPClauseName(ClauseKind);
19076         if (!ASE && !OASE) {
19077           bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
19078                                    VarDecl::DeclarationOnly;
19079           S.Diag(D->getLocation(),
19080                  IsDecl ? diag::note_previous_decl : diag::note_defined_here)
19081               << D;
19082         }
19083         continue;
19084       }
19085     }
19086 
19087     Type = Type.getNonLValueExprType(Context).getUnqualifiedType();
19088     VarDecl *LHSVD = buildVarDecl(S, ELoc, Type, ".reduction.lhs",
19089                                   D->hasAttrs() ? &D->getAttrs() : nullptr);
19090     VarDecl *RHSVD = buildVarDecl(S, ELoc, Type, D->getName(),
19091                                   D->hasAttrs() ? &D->getAttrs() : nullptr);
19092     QualType PrivateTy = Type;
19093 
19094     // Try if we can determine constant lengths for all array sections and avoid
19095     // the VLA.
19096     bool ConstantLengthOASE = false;
19097     if (OASE) {
19098       bool SingleElement;
19099       llvm::SmallVector<llvm::APSInt, 4> ArraySizes;
19100       ConstantLengthOASE = checkOMPArraySectionConstantForReduction(
19101           Context, OASE, SingleElement, ArraySizes);
19102 
19103       // If we don't have a single element, we must emit a constant array type.
19104       if (ConstantLengthOASE && !SingleElement) {
19105         for (llvm::APSInt &Size : ArraySizes)
19106           PrivateTy = Context.getConstantArrayType(PrivateTy, Size, nullptr,
19107                                                    ArrayType::Normal,
19108                                                    /*IndexTypeQuals=*/0);
19109       }
19110     }
19111 
19112     if ((OASE && !ConstantLengthOASE) ||
19113         (!OASE && !ASE &&
19114          D->getType().getNonReferenceType()->isVariablyModifiedType())) {
19115       if (!Context.getTargetInfo().isVLASupported()) {
19116         if (isOpenMPTargetExecutionDirective(Stack->getCurrentDirective())) {
19117           S.Diag(ELoc, diag::err_omp_reduction_vla_unsupported) << !!OASE;
19118           S.Diag(ELoc, diag::note_vla_unsupported);
19119           continue;
19120         } else {
19121           S.targetDiag(ELoc, diag::err_omp_reduction_vla_unsupported) << !!OASE;
19122           S.targetDiag(ELoc, diag::note_vla_unsupported);
19123         }
19124       }
19125       // For arrays/array sections only:
19126       // Create pseudo array type for private copy. The size for this array will
19127       // be generated during codegen.
19128       // For array subscripts or single variables Private Ty is the same as Type
19129       // (type of the variable or single array element).
19130       PrivateTy = Context.getVariableArrayType(
19131           Type,
19132           new (Context)
19133               OpaqueValueExpr(ELoc, Context.getSizeType(), VK_PRValue),
19134           ArrayType::Normal, /*IndexTypeQuals=*/0, SourceRange());
19135     } else if (!ASE && !OASE &&
19136                Context.getAsArrayType(D->getType().getNonReferenceType())) {
19137       PrivateTy = D->getType().getNonReferenceType();
19138     }
19139     // Private copy.
19140     VarDecl *PrivateVD =
19141         buildVarDecl(S, ELoc, PrivateTy, D->getName(),
19142                      D->hasAttrs() ? &D->getAttrs() : nullptr,
19143                      VD ? cast<DeclRefExpr>(SimpleRefExpr) : nullptr);
19144     // Add initializer for private variable.
19145     Expr *Init = nullptr;
19146     DeclRefExpr *LHSDRE = buildDeclRefExpr(S, LHSVD, Type, ELoc);
19147     DeclRefExpr *RHSDRE = buildDeclRefExpr(S, RHSVD, Type, ELoc);
19148     if (DeclareReductionRef.isUsable()) {
19149       auto *DRDRef = DeclareReductionRef.getAs<DeclRefExpr>();
19150       auto *DRD = cast<OMPDeclareReductionDecl>(DRDRef->getDecl());
19151       if (DRD->getInitializer()) {
19152         Init = DRDRef;
19153         RHSVD->setInit(DRDRef);
19154         RHSVD->setInitStyle(VarDecl::CallInit);
19155       }
19156     } else {
19157       switch (BOK) {
19158       case BO_Add:
19159       case BO_Xor:
19160       case BO_Or:
19161       case BO_LOr:
19162         // '+', '-', '^', '|', '||' reduction ops - initializer is '0'.
19163         if (Type->isScalarType() || Type->isAnyComplexType())
19164           Init = S.ActOnIntegerConstant(ELoc, /*Val=*/0).get();
19165         break;
19166       case BO_Mul:
19167       case BO_LAnd:
19168         if (Type->isScalarType() || Type->isAnyComplexType()) {
19169           // '*' and '&&' reduction ops - initializer is '1'.
19170           Init = S.ActOnIntegerConstant(ELoc, /*Val=*/1).get();
19171         }
19172         break;
19173       case BO_And: {
19174         // '&' reduction op - initializer is '~0'.
19175         QualType OrigType = Type;
19176         if (auto *ComplexTy = OrigType->getAs<ComplexType>())
19177           Type = ComplexTy->getElementType();
19178         if (Type->isRealFloatingType()) {
19179           llvm::APFloat InitValue = llvm::APFloat::getAllOnesValue(
19180               Context.getFloatTypeSemantics(Type));
19181           Init = FloatingLiteral::Create(Context, InitValue, /*isexact=*/true,
19182                                          Type, ELoc);
19183         } else if (Type->isScalarType()) {
19184           uint64_t Size = Context.getTypeSize(Type);
19185           QualType IntTy = Context.getIntTypeForBitwidth(Size, /*Signed=*/0);
19186           llvm::APInt InitValue = llvm::APInt::getAllOnes(Size);
19187           Init = IntegerLiteral::Create(Context, InitValue, IntTy, ELoc);
19188         }
19189         if (Init && OrigType->isAnyComplexType()) {
19190           // Init = 0xFFFF + 0xFFFFi;
19191           auto *Im = new (Context) ImaginaryLiteral(Init, OrigType);
19192           Init = S.CreateBuiltinBinOp(ELoc, BO_Add, Init, Im).get();
19193         }
19194         Type = OrigType;
19195         break;
19196       }
19197       case BO_LT:
19198       case BO_GT: {
19199         // 'min' reduction op - initializer is 'Largest representable number in
19200         // the reduction list item type'.
19201         // 'max' reduction op - initializer is 'Least representable number in
19202         // the reduction list item type'.
19203         if (Type->isIntegerType() || Type->isPointerType()) {
19204           bool IsSigned = Type->hasSignedIntegerRepresentation();
19205           uint64_t Size = Context.getTypeSize(Type);
19206           QualType IntTy =
19207               Context.getIntTypeForBitwidth(Size, /*Signed=*/IsSigned);
19208           llvm::APInt InitValue =
19209               (BOK != BO_LT) ? IsSigned ? llvm::APInt::getSignedMinValue(Size)
19210                                         : llvm::APInt::getMinValue(Size)
19211               : IsSigned ? llvm::APInt::getSignedMaxValue(Size)
19212                              : llvm::APInt::getMaxValue(Size);
19213           Init = IntegerLiteral::Create(Context, InitValue, IntTy, ELoc);
19214           if (Type->isPointerType()) {
19215             // Cast to pointer type.
19216             ExprResult CastExpr = S.BuildCStyleCastExpr(
19217                 ELoc, Context.getTrivialTypeSourceInfo(Type, ELoc), ELoc, Init);
19218             if (CastExpr.isInvalid())
19219               continue;
19220             Init = CastExpr.get();
19221           }
19222         } else if (Type->isRealFloatingType()) {
19223           llvm::APFloat InitValue = llvm::APFloat::getLargest(
19224               Context.getFloatTypeSemantics(Type), BOK != BO_LT);
19225           Init = FloatingLiteral::Create(Context, InitValue, /*isexact=*/true,
19226                                          Type, ELoc);
19227         }
19228         break;
19229       }
19230       case BO_PtrMemD:
19231       case BO_PtrMemI:
19232       case BO_MulAssign:
19233       case BO_Div:
19234       case BO_Rem:
19235       case BO_Sub:
19236       case BO_Shl:
19237       case BO_Shr:
19238       case BO_LE:
19239       case BO_GE:
19240       case BO_EQ:
19241       case BO_NE:
19242       case BO_Cmp:
19243       case BO_AndAssign:
19244       case BO_XorAssign:
19245       case BO_OrAssign:
19246       case BO_Assign:
19247       case BO_AddAssign:
19248       case BO_SubAssign:
19249       case BO_DivAssign:
19250       case BO_RemAssign:
19251       case BO_ShlAssign:
19252       case BO_ShrAssign:
19253       case BO_Comma:
19254         llvm_unreachable("Unexpected reduction operation");
19255       }
19256     }
19257     if (Init && DeclareReductionRef.isUnset()) {
19258       S.AddInitializerToDecl(RHSVD, Init, /*DirectInit=*/false);
19259       // Store initializer for single element in private copy. Will be used
19260       // during codegen.
19261       PrivateVD->setInit(RHSVD->getInit());
19262       PrivateVD->setInitStyle(RHSVD->getInitStyle());
19263     } else if (!Init) {
19264       S.ActOnUninitializedDecl(RHSVD);
19265       // Store initializer for single element in private copy. Will be used
19266       // during codegen.
19267       PrivateVD->setInit(RHSVD->getInit());
19268       PrivateVD->setInitStyle(RHSVD->getInitStyle());
19269     }
19270     if (RHSVD->isInvalidDecl())
19271       continue;
19272     if (!RHSVD->hasInit() && DeclareReductionRef.isUnset()) {
19273       S.Diag(ELoc, diag::err_omp_reduction_id_not_compatible)
19274           << Type << ReductionIdRange;
19275       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
19276                                VarDecl::DeclarationOnly;
19277       S.Diag(D->getLocation(),
19278              IsDecl ? diag::note_previous_decl : diag::note_defined_here)
19279           << D;
19280       continue;
19281     }
19282     DeclRefExpr *PrivateDRE = buildDeclRefExpr(S, PrivateVD, PrivateTy, ELoc);
19283     ExprResult ReductionOp;
19284     if (DeclareReductionRef.isUsable()) {
19285       QualType RedTy = DeclareReductionRef.get()->getType();
19286       QualType PtrRedTy = Context.getPointerType(RedTy);
19287       ExprResult LHS = S.CreateBuiltinUnaryOp(ELoc, UO_AddrOf, LHSDRE);
19288       ExprResult RHS = S.CreateBuiltinUnaryOp(ELoc, UO_AddrOf, RHSDRE);
19289       if (!BasePath.empty()) {
19290         LHS = S.DefaultLvalueConversion(LHS.get());
19291         RHS = S.DefaultLvalueConversion(RHS.get());
19292         LHS = ImplicitCastExpr::Create(
19293             Context, PtrRedTy, CK_UncheckedDerivedToBase, LHS.get(), &BasePath,
19294             LHS.get()->getValueKind(), FPOptionsOverride());
19295         RHS = ImplicitCastExpr::Create(
19296             Context, PtrRedTy, CK_UncheckedDerivedToBase, RHS.get(), &BasePath,
19297             RHS.get()->getValueKind(), FPOptionsOverride());
19298       }
19299       FunctionProtoType::ExtProtoInfo EPI;
19300       QualType Params[] = {PtrRedTy, PtrRedTy};
19301       QualType FnTy = Context.getFunctionType(Context.VoidTy, Params, EPI);
19302       auto *OVE = new (Context) OpaqueValueExpr(
19303           ELoc, Context.getPointerType(FnTy), VK_PRValue, OK_Ordinary,
19304           S.DefaultLvalueConversion(DeclareReductionRef.get()).get());
19305       Expr *Args[] = {LHS.get(), RHS.get()};
19306       ReductionOp =
19307           CallExpr::Create(Context, OVE, Args, Context.VoidTy, VK_PRValue, ELoc,
19308                            S.CurFPFeatureOverrides());
19309     } else {
19310       BinaryOperatorKind CombBOK = getRelatedCompoundReductionOp(BOK);
19311       if (Type->isRecordType() && CombBOK != BOK) {
19312         Sema::TentativeAnalysisScope Trap(S);
19313         ReductionOp =
19314             S.BuildBinOp(Stack->getCurScope(), ReductionId.getBeginLoc(),
19315                          CombBOK, LHSDRE, RHSDRE);
19316       }
19317       if (!ReductionOp.isUsable()) {
19318         ReductionOp =
19319             S.BuildBinOp(Stack->getCurScope(), ReductionId.getBeginLoc(), BOK,
19320                          LHSDRE, RHSDRE);
19321         if (ReductionOp.isUsable()) {
19322           if (BOK != BO_LT && BOK != BO_GT) {
19323             ReductionOp =
19324                 S.BuildBinOp(Stack->getCurScope(), ReductionId.getBeginLoc(),
19325                              BO_Assign, LHSDRE, ReductionOp.get());
19326           } else {
19327             auto *ConditionalOp = new (Context)
19328                 ConditionalOperator(ReductionOp.get(), ELoc, LHSDRE, ELoc,
19329                                     RHSDRE, Type, VK_LValue, OK_Ordinary);
19330             ReductionOp =
19331                 S.BuildBinOp(Stack->getCurScope(), ReductionId.getBeginLoc(),
19332                              BO_Assign, LHSDRE, ConditionalOp);
19333           }
19334         }
19335       }
19336       if (ReductionOp.isUsable())
19337         ReductionOp = S.ActOnFinishFullExpr(ReductionOp.get(),
19338                                             /*DiscardedValue*/ false);
19339       if (!ReductionOp.isUsable())
19340         continue;
19341     }
19342 
19343     // Add copy operations for inscan reductions.
19344     // LHS = RHS;
19345     ExprResult CopyOpRes, TempArrayRes, TempArrayElem;
19346     if (ClauseKind == OMPC_reduction &&
19347         RD.RedModifier == OMPC_REDUCTION_inscan) {
19348       ExprResult RHS = S.DefaultLvalueConversion(RHSDRE);
19349       CopyOpRes = S.BuildBinOp(Stack->getCurScope(), ELoc, BO_Assign, LHSDRE,
19350                                RHS.get());
19351       if (!CopyOpRes.isUsable())
19352         continue;
19353       CopyOpRes =
19354           S.ActOnFinishFullExpr(CopyOpRes.get(), /*DiscardedValue=*/true);
19355       if (!CopyOpRes.isUsable())
19356         continue;
19357       // For simd directive and simd-based directives in simd mode no need to
19358       // construct temp array, need just a single temp element.
19359       if (Stack->getCurrentDirective() == OMPD_simd ||
19360           (S.getLangOpts().OpenMPSimd &&
19361            isOpenMPSimdDirective(Stack->getCurrentDirective()))) {
19362         VarDecl *TempArrayVD =
19363             buildVarDecl(S, ELoc, PrivateTy, D->getName(),
19364                          D->hasAttrs() ? &D->getAttrs() : nullptr);
19365         // Add a constructor to the temp decl.
19366         S.ActOnUninitializedDecl(TempArrayVD);
19367         TempArrayRes = buildDeclRefExpr(S, TempArrayVD, PrivateTy, ELoc);
19368       } else {
19369         // Build temp array for prefix sum.
19370         auto *Dim = new (S.Context)
19371             OpaqueValueExpr(ELoc, S.Context.getSizeType(), VK_PRValue);
19372         QualType ArrayTy =
19373             S.Context.getVariableArrayType(PrivateTy, Dim, ArrayType::Normal,
19374                                            /*IndexTypeQuals=*/0, {ELoc, ELoc});
19375         VarDecl *TempArrayVD =
19376             buildVarDecl(S, ELoc, ArrayTy, D->getName(),
19377                          D->hasAttrs() ? &D->getAttrs() : nullptr);
19378         // Add a constructor to the temp decl.
19379         S.ActOnUninitializedDecl(TempArrayVD);
19380         TempArrayRes = buildDeclRefExpr(S, TempArrayVD, ArrayTy, ELoc);
19381         TempArrayElem =
19382             S.DefaultFunctionArrayLvalueConversion(TempArrayRes.get());
19383         auto *Idx = new (S.Context)
19384             OpaqueValueExpr(ELoc, S.Context.getSizeType(), VK_PRValue);
19385         TempArrayElem = S.CreateBuiltinArraySubscriptExpr(TempArrayElem.get(),
19386                                                           ELoc, Idx, ELoc);
19387       }
19388     }
19389 
19390     // OpenMP [2.15.4.6, Restrictions, p.2]
19391     // A list item that appears in an in_reduction clause of a task construct
19392     // must appear in a task_reduction clause of a construct associated with a
19393     // taskgroup region that includes the participating task in its taskgroup
19394     // set. The construct associated with the innermost region that meets this
19395     // condition must specify the same reduction-identifier as the in_reduction
19396     // clause.
19397     if (ClauseKind == OMPC_in_reduction) {
19398       SourceRange ParentSR;
19399       BinaryOperatorKind ParentBOK;
19400       const Expr *ParentReductionOp = nullptr;
19401       Expr *ParentBOKTD = nullptr, *ParentReductionOpTD = nullptr;
19402       DSAStackTy::DSAVarData ParentBOKDSA =
19403           Stack->getTopMostTaskgroupReductionData(D, ParentSR, ParentBOK,
19404                                                   ParentBOKTD);
19405       DSAStackTy::DSAVarData ParentReductionOpDSA =
19406           Stack->getTopMostTaskgroupReductionData(
19407               D, ParentSR, ParentReductionOp, ParentReductionOpTD);
19408       bool IsParentBOK = ParentBOKDSA.DKind != OMPD_unknown;
19409       bool IsParentReductionOp = ParentReductionOpDSA.DKind != OMPD_unknown;
19410       if ((DeclareReductionRef.isUnset() && IsParentReductionOp) ||
19411           (DeclareReductionRef.isUsable() && IsParentBOK) ||
19412           (IsParentBOK && BOK != ParentBOK) || IsParentReductionOp) {
19413         bool EmitError = true;
19414         if (IsParentReductionOp && DeclareReductionRef.isUsable()) {
19415           llvm::FoldingSetNodeID RedId, ParentRedId;
19416           ParentReductionOp->Profile(ParentRedId, Context, /*Canonical=*/true);
19417           DeclareReductionRef.get()->Profile(RedId, Context,
19418                                              /*Canonical=*/true);
19419           EmitError = RedId != ParentRedId;
19420         }
19421         if (EmitError) {
19422           S.Diag(ReductionId.getBeginLoc(),
19423                  diag::err_omp_reduction_identifier_mismatch)
19424               << ReductionIdRange << RefExpr->getSourceRange();
19425           S.Diag(ParentSR.getBegin(),
19426                  diag::note_omp_previous_reduction_identifier)
19427               << ParentSR
19428               << (IsParentBOK ? ParentBOKDSA.RefExpr
19429                               : ParentReductionOpDSA.RefExpr)
19430                      ->getSourceRange();
19431           continue;
19432         }
19433       }
19434       TaskgroupDescriptor = IsParentBOK ? ParentBOKTD : ParentReductionOpTD;
19435     }
19436 
19437     DeclRefExpr *Ref = nullptr;
19438     Expr *VarsExpr = RefExpr->IgnoreParens();
19439     if (!VD && !S.CurContext->isDependentContext()) {
19440       if (ASE || OASE) {
19441         TransformExprToCaptures RebuildToCapture(S, D);
19442         VarsExpr =
19443             RebuildToCapture.TransformExpr(RefExpr->IgnoreParens()).get();
19444         Ref = RebuildToCapture.getCapturedExpr();
19445       } else {
19446         VarsExpr = Ref = buildCapture(S, D, SimpleRefExpr, /*WithInit=*/false);
19447       }
19448       if (!S.isOpenMPCapturedDecl(D)) {
19449         RD.ExprCaptures.emplace_back(Ref->getDecl());
19450         if (Ref->getDecl()->hasAttr<OMPCaptureNoInitAttr>()) {
19451           ExprResult RefRes = S.DefaultLvalueConversion(Ref);
19452           if (!RefRes.isUsable())
19453             continue;
19454           ExprResult PostUpdateRes =
19455               S.BuildBinOp(Stack->getCurScope(), ELoc, BO_Assign, SimpleRefExpr,
19456                            RefRes.get());
19457           if (!PostUpdateRes.isUsable())
19458             continue;
19459           if (isOpenMPTaskingDirective(Stack->getCurrentDirective()) ||
19460               Stack->getCurrentDirective() == OMPD_taskgroup) {
19461             S.Diag(RefExpr->getExprLoc(),
19462                    diag::err_omp_reduction_non_addressable_expression)
19463                 << RefExpr->getSourceRange();
19464             continue;
19465           }
19466           RD.ExprPostUpdates.emplace_back(
19467               S.IgnoredValueConversions(PostUpdateRes.get()).get());
19468         }
19469       }
19470     }
19471     // All reduction items are still marked as reduction (to do not increase
19472     // code base size).
19473     unsigned Modifier = RD.RedModifier;
19474     // Consider task_reductions as reductions with task modifier. Required for
19475     // correct analysis of in_reduction clauses.
19476     if (CurrDir == OMPD_taskgroup && ClauseKind == OMPC_task_reduction)
19477       Modifier = OMPC_REDUCTION_task;
19478     Stack->addDSA(D, RefExpr->IgnoreParens(), OMPC_reduction, Ref, Modifier,
19479                   ASE || OASE);
19480     if (Modifier == OMPC_REDUCTION_task &&
19481         (CurrDir == OMPD_taskgroup ||
19482          ((isOpenMPParallelDirective(CurrDir) ||
19483            isOpenMPWorksharingDirective(CurrDir)) &&
19484           !isOpenMPSimdDirective(CurrDir)))) {
19485       if (DeclareReductionRef.isUsable())
19486         Stack->addTaskgroupReductionData(D, ReductionIdRange,
19487                                          DeclareReductionRef.get());
19488       else
19489         Stack->addTaskgroupReductionData(D, ReductionIdRange, BOK);
19490     }
19491     RD.push(VarsExpr, PrivateDRE, LHSDRE, RHSDRE, ReductionOp.get(),
19492             TaskgroupDescriptor, CopyOpRes.get(), TempArrayRes.get(),
19493             TempArrayElem.get());
19494   }
19495   return RD.Vars.empty();
19496 }
19497 
19498 OMPClause *Sema::ActOnOpenMPReductionClause(
19499     ArrayRef<Expr *> VarList, OpenMPReductionClauseModifier Modifier,
19500     SourceLocation StartLoc, SourceLocation LParenLoc,
19501     SourceLocation ModifierLoc, SourceLocation ColonLoc, SourceLocation EndLoc,
19502     CXXScopeSpec &ReductionIdScopeSpec, const DeclarationNameInfo &ReductionId,
19503     ArrayRef<Expr *> UnresolvedReductions) {
19504   if (ModifierLoc.isValid() && Modifier == OMPC_REDUCTION_unknown) {
19505     Diag(LParenLoc, diag::err_omp_unexpected_clause_value)
19506         << getListOfPossibleValues(OMPC_reduction, /*First=*/0,
19507                                    /*Last=*/OMPC_REDUCTION_unknown)
19508         << getOpenMPClauseName(OMPC_reduction);
19509     return nullptr;
19510   }
19511   // OpenMP 5.0, 2.19.5.4 reduction Clause, Restrictions
19512   // A reduction clause with the inscan reduction-modifier may only appear on a
19513   // worksharing-loop construct, a worksharing-loop SIMD construct, a simd
19514   // construct, a parallel worksharing-loop construct or a parallel
19515   // worksharing-loop SIMD construct.
19516   if (Modifier == OMPC_REDUCTION_inscan &&
19517       (DSAStack->getCurrentDirective() != OMPD_for &&
19518        DSAStack->getCurrentDirective() != OMPD_for_simd &&
19519        DSAStack->getCurrentDirective() != OMPD_simd &&
19520        DSAStack->getCurrentDirective() != OMPD_parallel_for &&
19521        DSAStack->getCurrentDirective() != OMPD_parallel_for_simd)) {
19522     Diag(ModifierLoc, diag::err_omp_wrong_inscan_reduction);
19523     return nullptr;
19524   }
19525 
19526   ReductionData RD(VarList.size(), Modifier);
19527   if (actOnOMPReductionKindClause(*this, DSAStack, OMPC_reduction, VarList,
19528                                   StartLoc, LParenLoc, ColonLoc, EndLoc,
19529                                   ReductionIdScopeSpec, ReductionId,
19530                                   UnresolvedReductions, RD))
19531     return nullptr;
19532 
19533   return OMPReductionClause::Create(
19534       Context, StartLoc, LParenLoc, ModifierLoc, ColonLoc, EndLoc, Modifier,
19535       RD.Vars, ReductionIdScopeSpec.getWithLocInContext(Context), ReductionId,
19536       RD.Privates, RD.LHSs, RD.RHSs, RD.ReductionOps, RD.InscanCopyOps,
19537       RD.InscanCopyArrayTemps, RD.InscanCopyArrayElems,
19538       buildPreInits(Context, RD.ExprCaptures),
19539       buildPostUpdate(*this, RD.ExprPostUpdates));
19540 }
19541 
19542 OMPClause *Sema::ActOnOpenMPTaskReductionClause(
19543     ArrayRef<Expr *> VarList, SourceLocation StartLoc, SourceLocation LParenLoc,
19544     SourceLocation ColonLoc, SourceLocation EndLoc,
19545     CXXScopeSpec &ReductionIdScopeSpec, const DeclarationNameInfo &ReductionId,
19546     ArrayRef<Expr *> UnresolvedReductions) {
19547   ReductionData RD(VarList.size());
19548   if (actOnOMPReductionKindClause(*this, DSAStack, OMPC_task_reduction, VarList,
19549                                   StartLoc, LParenLoc, ColonLoc, EndLoc,
19550                                   ReductionIdScopeSpec, ReductionId,
19551                                   UnresolvedReductions, RD))
19552     return nullptr;
19553 
19554   return OMPTaskReductionClause::Create(
19555       Context, StartLoc, LParenLoc, ColonLoc, EndLoc, RD.Vars,
19556       ReductionIdScopeSpec.getWithLocInContext(Context), ReductionId,
19557       RD.Privates, RD.LHSs, RD.RHSs, RD.ReductionOps,
19558       buildPreInits(Context, RD.ExprCaptures),
19559       buildPostUpdate(*this, RD.ExprPostUpdates));
19560 }
19561 
19562 OMPClause *Sema::ActOnOpenMPInReductionClause(
19563     ArrayRef<Expr *> VarList, SourceLocation StartLoc, SourceLocation LParenLoc,
19564     SourceLocation ColonLoc, SourceLocation EndLoc,
19565     CXXScopeSpec &ReductionIdScopeSpec, const DeclarationNameInfo &ReductionId,
19566     ArrayRef<Expr *> UnresolvedReductions) {
19567   ReductionData RD(VarList.size());
19568   if (actOnOMPReductionKindClause(*this, DSAStack, OMPC_in_reduction, VarList,
19569                                   StartLoc, LParenLoc, ColonLoc, EndLoc,
19570                                   ReductionIdScopeSpec, ReductionId,
19571                                   UnresolvedReductions, RD))
19572     return nullptr;
19573 
19574   return OMPInReductionClause::Create(
19575       Context, StartLoc, LParenLoc, ColonLoc, EndLoc, RD.Vars,
19576       ReductionIdScopeSpec.getWithLocInContext(Context), ReductionId,
19577       RD.Privates, RD.LHSs, RD.RHSs, RD.ReductionOps, RD.TaskgroupDescriptors,
19578       buildPreInits(Context, RD.ExprCaptures),
19579       buildPostUpdate(*this, RD.ExprPostUpdates));
19580 }
19581 
19582 bool Sema::CheckOpenMPLinearModifier(OpenMPLinearClauseKind LinKind,
19583                                      SourceLocation LinLoc) {
19584   if ((!LangOpts.CPlusPlus && LinKind != OMPC_LINEAR_val) ||
19585       LinKind == OMPC_LINEAR_unknown) {
19586     Diag(LinLoc, diag::err_omp_wrong_linear_modifier) << LangOpts.CPlusPlus;
19587     return true;
19588   }
19589   return false;
19590 }
19591 
19592 bool Sema::CheckOpenMPLinearDecl(const ValueDecl *D, SourceLocation ELoc,
19593                                  OpenMPLinearClauseKind LinKind, QualType Type,
19594                                  bool IsDeclareSimd) {
19595   const auto *VD = dyn_cast_or_null<VarDecl>(D);
19596   // A variable must not have an incomplete type or a reference type.
19597   if (RequireCompleteType(ELoc, Type, diag::err_omp_linear_incomplete_type))
19598     return true;
19599   if ((LinKind == OMPC_LINEAR_uval || LinKind == OMPC_LINEAR_ref) &&
19600       !Type->isReferenceType()) {
19601     Diag(ELoc, diag::err_omp_wrong_linear_modifier_non_reference)
19602         << Type << getOpenMPSimpleClauseTypeName(OMPC_linear, LinKind);
19603     return true;
19604   }
19605   Type = Type.getNonReferenceType();
19606 
19607   // OpenMP 5.0 [2.19.3, List Item Privatization, Restrictions]
19608   // A variable that is privatized must not have a const-qualified type
19609   // unless it is of class type with a mutable member. This restriction does
19610   // not apply to the firstprivate clause, nor to the linear clause on
19611   // declarative directives (like declare simd).
19612   if (!IsDeclareSimd &&
19613       rejectConstNotMutableType(*this, D, Type, OMPC_linear, ELoc))
19614     return true;
19615 
19616   // A list item must be of integral or pointer type.
19617   Type = Type.getUnqualifiedType().getCanonicalType();
19618   const auto *Ty = Type.getTypePtrOrNull();
19619   if (!Ty || (LinKind != OMPC_LINEAR_ref && !Ty->isDependentType() &&
19620               !Ty->isIntegralType(Context) && !Ty->isPointerType())) {
19621     Diag(ELoc, diag::err_omp_linear_expected_int_or_ptr) << Type;
19622     if (D) {
19623       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
19624                                VarDecl::DeclarationOnly;
19625       Diag(D->getLocation(),
19626            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
19627           << D;
19628     }
19629     return true;
19630   }
19631   return false;
19632 }
19633 
19634 OMPClause *Sema::ActOnOpenMPLinearClause(
19635     ArrayRef<Expr *> VarList, Expr *Step, SourceLocation StartLoc,
19636     SourceLocation LParenLoc, OpenMPLinearClauseKind LinKind,
19637     SourceLocation LinLoc, SourceLocation ColonLoc, SourceLocation EndLoc) {
19638   SmallVector<Expr *, 8> Vars;
19639   SmallVector<Expr *, 8> Privates;
19640   SmallVector<Expr *, 8> Inits;
19641   SmallVector<Decl *, 4> ExprCaptures;
19642   SmallVector<Expr *, 4> ExprPostUpdates;
19643   if (CheckOpenMPLinearModifier(LinKind, LinLoc))
19644     LinKind = OMPC_LINEAR_val;
19645   for (Expr *RefExpr : VarList) {
19646     assert(RefExpr && "NULL expr in OpenMP linear clause.");
19647     SourceLocation ELoc;
19648     SourceRange ERange;
19649     Expr *SimpleRefExpr = RefExpr;
19650     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
19651     if (Res.second) {
19652       // It will be analyzed later.
19653       Vars.push_back(RefExpr);
19654       Privates.push_back(nullptr);
19655       Inits.push_back(nullptr);
19656     }
19657     ValueDecl *D = Res.first;
19658     if (!D)
19659       continue;
19660 
19661     QualType Type = D->getType();
19662     auto *VD = dyn_cast<VarDecl>(D);
19663 
19664     // OpenMP [2.14.3.7, linear clause]
19665     //  A list-item cannot appear in more than one linear clause.
19666     //  A list-item that appears in a linear clause cannot appear in any
19667     //  other data-sharing attribute clause.
19668     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(D, /*FromParent=*/false);
19669     if (DVar.RefExpr) {
19670       Diag(ELoc, diag::err_omp_wrong_dsa) << getOpenMPClauseName(DVar.CKind)
19671                                           << getOpenMPClauseName(OMPC_linear);
19672       reportOriginalDsa(*this, DSAStack, D, DVar);
19673       continue;
19674     }
19675 
19676     if (CheckOpenMPLinearDecl(D, ELoc, LinKind, Type))
19677       continue;
19678     Type = Type.getNonReferenceType().getUnqualifiedType().getCanonicalType();
19679 
19680     // Build private copy of original var.
19681     VarDecl *Private =
19682         buildVarDecl(*this, ELoc, Type, D->getName(),
19683                      D->hasAttrs() ? &D->getAttrs() : nullptr,
19684                      VD ? cast<DeclRefExpr>(SimpleRefExpr) : nullptr);
19685     DeclRefExpr *PrivateRef = buildDeclRefExpr(*this, Private, Type, ELoc);
19686     // Build var to save initial value.
19687     VarDecl *Init = buildVarDecl(*this, ELoc, Type, ".linear.start");
19688     Expr *InitExpr;
19689     DeclRefExpr *Ref = nullptr;
19690     if (!VD && !CurContext->isDependentContext()) {
19691       Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/false);
19692       if (!isOpenMPCapturedDecl(D)) {
19693         ExprCaptures.push_back(Ref->getDecl());
19694         if (Ref->getDecl()->hasAttr<OMPCaptureNoInitAttr>()) {
19695           ExprResult RefRes = DefaultLvalueConversion(Ref);
19696           if (!RefRes.isUsable())
19697             continue;
19698           ExprResult PostUpdateRes =
19699               BuildBinOp(DSAStack->getCurScope(), ELoc, BO_Assign,
19700                          SimpleRefExpr, RefRes.get());
19701           if (!PostUpdateRes.isUsable())
19702             continue;
19703           ExprPostUpdates.push_back(
19704               IgnoredValueConversions(PostUpdateRes.get()).get());
19705         }
19706       }
19707     }
19708     if (LinKind == OMPC_LINEAR_uval)
19709       InitExpr = VD ? VD->getInit() : SimpleRefExpr;
19710     else
19711       InitExpr = VD ? SimpleRefExpr : Ref;
19712     AddInitializerToDecl(Init, DefaultLvalueConversion(InitExpr).get(),
19713                          /*DirectInit=*/false);
19714     DeclRefExpr *InitRef = buildDeclRefExpr(*this, Init, Type, ELoc);
19715 
19716     DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_linear, Ref);
19717     Vars.push_back((VD || CurContext->isDependentContext())
19718                        ? RefExpr->IgnoreParens()
19719                        : Ref);
19720     Privates.push_back(PrivateRef);
19721     Inits.push_back(InitRef);
19722   }
19723 
19724   if (Vars.empty())
19725     return nullptr;
19726 
19727   Expr *StepExpr = Step;
19728   Expr *CalcStepExpr = nullptr;
19729   if (Step && !Step->isValueDependent() && !Step->isTypeDependent() &&
19730       !Step->isInstantiationDependent() &&
19731       !Step->containsUnexpandedParameterPack()) {
19732     SourceLocation StepLoc = Step->getBeginLoc();
19733     ExprResult Val = PerformOpenMPImplicitIntegerConversion(StepLoc, Step);
19734     if (Val.isInvalid())
19735       return nullptr;
19736     StepExpr = Val.get();
19737 
19738     // Build var to save the step value.
19739     VarDecl *SaveVar =
19740         buildVarDecl(*this, StepLoc, StepExpr->getType(), ".linear.step");
19741     ExprResult SaveRef =
19742         buildDeclRefExpr(*this, SaveVar, StepExpr->getType(), StepLoc);
19743     ExprResult CalcStep =
19744         BuildBinOp(CurScope, StepLoc, BO_Assign, SaveRef.get(), StepExpr);
19745     CalcStep = ActOnFinishFullExpr(CalcStep.get(), /*DiscardedValue*/ false);
19746 
19747     // Warn about zero linear step (it would be probably better specified as
19748     // making corresponding variables 'const').
19749     if (Optional<llvm::APSInt> Result =
19750             StepExpr->getIntegerConstantExpr(Context)) {
19751       if (!Result->isNegative() && !Result->isStrictlyPositive())
19752         Diag(StepLoc, diag::warn_omp_linear_step_zero)
19753             << Vars[0] << (Vars.size() > 1);
19754     } else if (CalcStep.isUsable()) {
19755       // Calculate the step beforehand instead of doing this on each iteration.
19756       // (This is not used if the number of iterations may be kfold-ed).
19757       CalcStepExpr = CalcStep.get();
19758     }
19759   }
19760 
19761   return OMPLinearClause::Create(Context, StartLoc, LParenLoc, LinKind, LinLoc,
19762                                  ColonLoc, EndLoc, Vars, Privates, Inits,
19763                                  StepExpr, CalcStepExpr,
19764                                  buildPreInits(Context, ExprCaptures),
19765                                  buildPostUpdate(*this, ExprPostUpdates));
19766 }
19767 
19768 static bool FinishOpenMPLinearClause(OMPLinearClause &Clause, DeclRefExpr *IV,
19769                                      Expr *NumIterations, Sema &SemaRef,
19770                                      Scope *S, DSAStackTy *Stack) {
19771   // Walk the vars and build update/final expressions for the CodeGen.
19772   SmallVector<Expr *, 8> Updates;
19773   SmallVector<Expr *, 8> Finals;
19774   SmallVector<Expr *, 8> UsedExprs;
19775   Expr *Step = Clause.getStep();
19776   Expr *CalcStep = Clause.getCalcStep();
19777   // OpenMP [2.14.3.7, linear clause]
19778   // If linear-step is not specified it is assumed to be 1.
19779   if (!Step)
19780     Step = SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get();
19781   else if (CalcStep)
19782     Step = cast<BinaryOperator>(CalcStep)->getLHS();
19783   bool HasErrors = false;
19784   auto CurInit = Clause.inits().begin();
19785   auto CurPrivate = Clause.privates().begin();
19786   OpenMPLinearClauseKind LinKind = Clause.getModifier();
19787   for (Expr *RefExpr : Clause.varlists()) {
19788     SourceLocation ELoc;
19789     SourceRange ERange;
19790     Expr *SimpleRefExpr = RefExpr;
19791     auto Res = getPrivateItem(SemaRef, SimpleRefExpr, ELoc, ERange);
19792     ValueDecl *D = Res.first;
19793     if (Res.second || !D) {
19794       Updates.push_back(nullptr);
19795       Finals.push_back(nullptr);
19796       HasErrors = true;
19797       continue;
19798     }
19799     auto &&Info = Stack->isLoopControlVariable(D);
19800     // OpenMP [2.15.11, distribute simd Construct]
19801     // A list item may not appear in a linear clause, unless it is the loop
19802     // iteration variable.
19803     if (isOpenMPDistributeDirective(Stack->getCurrentDirective()) &&
19804         isOpenMPSimdDirective(Stack->getCurrentDirective()) && !Info.first) {
19805       SemaRef.Diag(ELoc,
19806                    diag::err_omp_linear_distribute_var_non_loop_iteration);
19807       Updates.push_back(nullptr);
19808       Finals.push_back(nullptr);
19809       HasErrors = true;
19810       continue;
19811     }
19812     Expr *InitExpr = *CurInit;
19813 
19814     // Build privatized reference to the current linear var.
19815     auto *DE = cast<DeclRefExpr>(SimpleRefExpr);
19816     Expr *CapturedRef;
19817     if (LinKind == OMPC_LINEAR_uval)
19818       CapturedRef = cast<VarDecl>(DE->getDecl())->getInit();
19819     else
19820       CapturedRef =
19821           buildDeclRefExpr(SemaRef, cast<VarDecl>(DE->getDecl()),
19822                            DE->getType().getUnqualifiedType(), DE->getExprLoc(),
19823                            /*RefersToCapture=*/true);
19824 
19825     // Build update: Var = InitExpr + IV * Step
19826     ExprResult Update;
19827     if (!Info.first)
19828       Update = buildCounterUpdate(
19829           SemaRef, S, RefExpr->getExprLoc(), *CurPrivate, InitExpr, IV, Step,
19830           /*Subtract=*/false, /*IsNonRectangularLB=*/false);
19831     else
19832       Update = *CurPrivate;
19833     Update = SemaRef.ActOnFinishFullExpr(Update.get(), DE->getBeginLoc(),
19834                                          /*DiscardedValue*/ false);
19835 
19836     // Build final: Var = PrivCopy;
19837     ExprResult Final;
19838     if (!Info.first)
19839       Final = SemaRef.BuildBinOp(
19840           S, RefExpr->getExprLoc(), BO_Assign, CapturedRef,
19841           SemaRef.DefaultLvalueConversion(*CurPrivate).get());
19842     else
19843       Final = *CurPrivate;
19844     Final = SemaRef.ActOnFinishFullExpr(Final.get(), DE->getBeginLoc(),
19845                                         /*DiscardedValue*/ false);
19846 
19847     if (!Update.isUsable() || !Final.isUsable()) {
19848       Updates.push_back(nullptr);
19849       Finals.push_back(nullptr);
19850       UsedExprs.push_back(nullptr);
19851       HasErrors = true;
19852     } else {
19853       Updates.push_back(Update.get());
19854       Finals.push_back(Final.get());
19855       if (!Info.first)
19856         UsedExprs.push_back(SimpleRefExpr);
19857     }
19858     ++CurInit;
19859     ++CurPrivate;
19860   }
19861   if (Expr *S = Clause.getStep())
19862     UsedExprs.push_back(S);
19863   // Fill the remaining part with the nullptr.
19864   UsedExprs.append(Clause.varlist_size() + 1 - UsedExprs.size(), nullptr);
19865   Clause.setUpdates(Updates);
19866   Clause.setFinals(Finals);
19867   Clause.setUsedExprs(UsedExprs);
19868   return HasErrors;
19869 }
19870 
19871 OMPClause *Sema::ActOnOpenMPAlignedClause(
19872     ArrayRef<Expr *> VarList, Expr *Alignment, SourceLocation StartLoc,
19873     SourceLocation LParenLoc, SourceLocation ColonLoc, SourceLocation EndLoc) {
19874   SmallVector<Expr *, 8> Vars;
19875   for (Expr *RefExpr : VarList) {
19876     assert(RefExpr && "NULL expr in OpenMP linear clause.");
19877     SourceLocation ELoc;
19878     SourceRange ERange;
19879     Expr *SimpleRefExpr = RefExpr;
19880     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
19881     if (Res.second) {
19882       // It will be analyzed later.
19883       Vars.push_back(RefExpr);
19884     }
19885     ValueDecl *D = Res.first;
19886     if (!D)
19887       continue;
19888 
19889     QualType QType = D->getType();
19890     auto *VD = dyn_cast<VarDecl>(D);
19891 
19892     // OpenMP  [2.8.1, simd construct, Restrictions]
19893     // The type of list items appearing in the aligned clause must be
19894     // array, pointer, reference to array, or reference to pointer.
19895     QType = QType.getNonReferenceType().getUnqualifiedType().getCanonicalType();
19896     const Type *Ty = QType.getTypePtrOrNull();
19897     if (!Ty || (!Ty->isArrayType() && !Ty->isPointerType())) {
19898       Diag(ELoc, diag::err_omp_aligned_expected_array_or_ptr)
19899           << QType << getLangOpts().CPlusPlus << ERange;
19900       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
19901                                VarDecl::DeclarationOnly;
19902       Diag(D->getLocation(),
19903            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
19904           << D;
19905       continue;
19906     }
19907 
19908     // OpenMP  [2.8.1, simd construct, Restrictions]
19909     // A list-item cannot appear in more than one aligned clause.
19910     if (const Expr *PrevRef = DSAStack->addUniqueAligned(D, SimpleRefExpr)) {
19911       Diag(ELoc, diag::err_omp_used_in_clause_twice)
19912           << 0 << getOpenMPClauseName(OMPC_aligned) << ERange;
19913       Diag(PrevRef->getExprLoc(), diag::note_omp_explicit_dsa)
19914           << getOpenMPClauseName(OMPC_aligned);
19915       continue;
19916     }
19917 
19918     DeclRefExpr *Ref = nullptr;
19919     if (!VD && isOpenMPCapturedDecl(D))
19920       Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/true);
19921     Vars.push_back(DefaultFunctionArrayConversion(
19922                        (VD || !Ref) ? RefExpr->IgnoreParens() : Ref)
19923                        .get());
19924   }
19925 
19926   // OpenMP [2.8.1, simd construct, Description]
19927   // The parameter of the aligned clause, alignment, must be a constant
19928   // positive integer expression.
19929   // If no optional parameter is specified, implementation-defined default
19930   // alignments for SIMD instructions on the target platforms are assumed.
19931   if (Alignment != nullptr) {
19932     ExprResult AlignResult =
19933         VerifyPositiveIntegerConstantInClause(Alignment, OMPC_aligned);
19934     if (AlignResult.isInvalid())
19935       return nullptr;
19936     Alignment = AlignResult.get();
19937   }
19938   if (Vars.empty())
19939     return nullptr;
19940 
19941   return OMPAlignedClause::Create(Context, StartLoc, LParenLoc, ColonLoc,
19942                                   EndLoc, Vars, Alignment);
19943 }
19944 
19945 OMPClause *Sema::ActOnOpenMPCopyinClause(ArrayRef<Expr *> VarList,
19946                                          SourceLocation StartLoc,
19947                                          SourceLocation LParenLoc,
19948                                          SourceLocation EndLoc) {
19949   SmallVector<Expr *, 8> Vars;
19950   SmallVector<Expr *, 8> SrcExprs;
19951   SmallVector<Expr *, 8> DstExprs;
19952   SmallVector<Expr *, 8> AssignmentOps;
19953   for (Expr *RefExpr : VarList) {
19954     assert(RefExpr && "NULL expr in OpenMP copyin clause.");
19955     if (isa<DependentScopeDeclRefExpr>(RefExpr)) {
19956       // It will be analyzed later.
19957       Vars.push_back(RefExpr);
19958       SrcExprs.push_back(nullptr);
19959       DstExprs.push_back(nullptr);
19960       AssignmentOps.push_back(nullptr);
19961       continue;
19962     }
19963 
19964     SourceLocation ELoc = RefExpr->getExprLoc();
19965     // OpenMP [2.1, C/C++]
19966     //  A list item is a variable name.
19967     // OpenMP  [2.14.4.1, Restrictions, p.1]
19968     //  A list item that appears in a copyin clause must be threadprivate.
19969     auto *DE = dyn_cast<DeclRefExpr>(RefExpr);
19970     if (!DE || !isa<VarDecl>(DE->getDecl())) {
19971       Diag(ELoc, diag::err_omp_expected_var_name_member_expr)
19972           << 0 << RefExpr->getSourceRange();
19973       continue;
19974     }
19975 
19976     Decl *D = DE->getDecl();
19977     auto *VD = cast<VarDecl>(D);
19978 
19979     QualType Type = VD->getType();
19980     if (Type->isDependentType() || Type->isInstantiationDependentType()) {
19981       // It will be analyzed later.
19982       Vars.push_back(DE);
19983       SrcExprs.push_back(nullptr);
19984       DstExprs.push_back(nullptr);
19985       AssignmentOps.push_back(nullptr);
19986       continue;
19987     }
19988 
19989     // OpenMP [2.14.4.1, Restrictions, C/C++, p.1]
19990     //  A list item that appears in a copyin clause must be threadprivate.
19991     if (!DSAStack->isThreadPrivate(VD)) {
19992       Diag(ELoc, diag::err_omp_required_access)
19993           << getOpenMPClauseName(OMPC_copyin)
19994           << getOpenMPDirectiveName(OMPD_threadprivate);
19995       continue;
19996     }
19997 
19998     // OpenMP [2.14.4.1, Restrictions, C/C++, p.2]
19999     //  A variable of class type (or array thereof) that appears in a
20000     //  copyin clause requires an accessible, unambiguous copy assignment
20001     //  operator for the class type.
20002     QualType ElemType = Context.getBaseElementType(Type).getNonReferenceType();
20003     VarDecl *SrcVD =
20004         buildVarDecl(*this, DE->getBeginLoc(), ElemType.getUnqualifiedType(),
20005                      ".copyin.src", VD->hasAttrs() ? &VD->getAttrs() : nullptr);
20006     DeclRefExpr *PseudoSrcExpr = buildDeclRefExpr(
20007         *this, SrcVD, ElemType.getUnqualifiedType(), DE->getExprLoc());
20008     VarDecl *DstVD =
20009         buildVarDecl(*this, DE->getBeginLoc(), ElemType, ".copyin.dst",
20010                      VD->hasAttrs() ? &VD->getAttrs() : nullptr);
20011     DeclRefExpr *PseudoDstExpr =
20012         buildDeclRefExpr(*this, DstVD, ElemType, DE->getExprLoc());
20013     // For arrays generate assignment operation for single element and replace
20014     // it by the original array element in CodeGen.
20015     ExprResult AssignmentOp =
20016         BuildBinOp(/*S=*/nullptr, DE->getExprLoc(), BO_Assign, PseudoDstExpr,
20017                    PseudoSrcExpr);
20018     if (AssignmentOp.isInvalid())
20019       continue;
20020     AssignmentOp = ActOnFinishFullExpr(AssignmentOp.get(), DE->getExprLoc(),
20021                                        /*DiscardedValue*/ false);
20022     if (AssignmentOp.isInvalid())
20023       continue;
20024 
20025     DSAStack->addDSA(VD, DE, OMPC_copyin);
20026     Vars.push_back(DE);
20027     SrcExprs.push_back(PseudoSrcExpr);
20028     DstExprs.push_back(PseudoDstExpr);
20029     AssignmentOps.push_back(AssignmentOp.get());
20030   }
20031 
20032   if (Vars.empty())
20033     return nullptr;
20034 
20035   return OMPCopyinClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars,
20036                                  SrcExprs, DstExprs, AssignmentOps);
20037 }
20038 
20039 OMPClause *Sema::ActOnOpenMPCopyprivateClause(ArrayRef<Expr *> VarList,
20040                                               SourceLocation StartLoc,
20041                                               SourceLocation LParenLoc,
20042                                               SourceLocation EndLoc) {
20043   SmallVector<Expr *, 8> Vars;
20044   SmallVector<Expr *, 8> SrcExprs;
20045   SmallVector<Expr *, 8> DstExprs;
20046   SmallVector<Expr *, 8> AssignmentOps;
20047   for (Expr *RefExpr : VarList) {
20048     assert(RefExpr && "NULL expr in OpenMP linear clause.");
20049     SourceLocation ELoc;
20050     SourceRange ERange;
20051     Expr *SimpleRefExpr = RefExpr;
20052     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
20053     if (Res.second) {
20054       // It will be analyzed later.
20055       Vars.push_back(RefExpr);
20056       SrcExprs.push_back(nullptr);
20057       DstExprs.push_back(nullptr);
20058       AssignmentOps.push_back(nullptr);
20059     }
20060     ValueDecl *D = Res.first;
20061     if (!D)
20062       continue;
20063 
20064     QualType Type = D->getType();
20065     auto *VD = dyn_cast<VarDecl>(D);
20066 
20067     // OpenMP [2.14.4.2, Restrictions, p.2]
20068     //  A list item that appears in a copyprivate clause may not appear in a
20069     //  private or firstprivate clause on the single construct.
20070     if (!VD || !DSAStack->isThreadPrivate(VD)) {
20071       DSAStackTy::DSAVarData DVar =
20072           DSAStack->getTopDSA(D, /*FromParent=*/false);
20073       if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_copyprivate &&
20074           DVar.RefExpr) {
20075         Diag(ELoc, diag::err_omp_wrong_dsa)
20076             << getOpenMPClauseName(DVar.CKind)
20077             << getOpenMPClauseName(OMPC_copyprivate);
20078         reportOriginalDsa(*this, DSAStack, D, DVar);
20079         continue;
20080       }
20081 
20082       // OpenMP [2.11.4.2, Restrictions, p.1]
20083       //  All list items that appear in a copyprivate clause must be either
20084       //  threadprivate or private in the enclosing context.
20085       if (DVar.CKind == OMPC_unknown) {
20086         DVar = DSAStack->getImplicitDSA(D, false);
20087         if (DVar.CKind == OMPC_shared) {
20088           Diag(ELoc, diag::err_omp_required_access)
20089               << getOpenMPClauseName(OMPC_copyprivate)
20090               << "threadprivate or private in the enclosing context";
20091           reportOriginalDsa(*this, DSAStack, D, DVar);
20092           continue;
20093         }
20094       }
20095     }
20096 
20097     // Variably modified types are not supported.
20098     if (!Type->isAnyPointerType() && Type->isVariablyModifiedType()) {
20099       Diag(ELoc, diag::err_omp_variably_modified_type_not_supported)
20100           << getOpenMPClauseName(OMPC_copyprivate) << Type
20101           << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
20102       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
20103                                VarDecl::DeclarationOnly;
20104       Diag(D->getLocation(),
20105            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
20106           << D;
20107       continue;
20108     }
20109 
20110     // OpenMP [2.14.4.1, Restrictions, C/C++, p.2]
20111     //  A variable of class type (or array thereof) that appears in a
20112     //  copyin clause requires an accessible, unambiguous copy assignment
20113     //  operator for the class type.
20114     Type = Context.getBaseElementType(Type.getNonReferenceType())
20115                .getUnqualifiedType();
20116     VarDecl *SrcVD =
20117         buildVarDecl(*this, RefExpr->getBeginLoc(), Type, ".copyprivate.src",
20118                      D->hasAttrs() ? &D->getAttrs() : nullptr);
20119     DeclRefExpr *PseudoSrcExpr = buildDeclRefExpr(*this, SrcVD, Type, ELoc);
20120     VarDecl *DstVD =
20121         buildVarDecl(*this, RefExpr->getBeginLoc(), Type, ".copyprivate.dst",
20122                      D->hasAttrs() ? &D->getAttrs() : nullptr);
20123     DeclRefExpr *PseudoDstExpr = buildDeclRefExpr(*this, DstVD, Type, ELoc);
20124     ExprResult AssignmentOp = BuildBinOp(
20125         DSAStack->getCurScope(), ELoc, BO_Assign, PseudoDstExpr, PseudoSrcExpr);
20126     if (AssignmentOp.isInvalid())
20127       continue;
20128     AssignmentOp =
20129         ActOnFinishFullExpr(AssignmentOp.get(), ELoc, /*DiscardedValue*/ false);
20130     if (AssignmentOp.isInvalid())
20131       continue;
20132 
20133     // No need to mark vars as copyprivate, they are already threadprivate or
20134     // implicitly private.
20135     assert(VD || isOpenMPCapturedDecl(D));
20136     Vars.push_back(
20137         VD ? RefExpr->IgnoreParens()
20138            : buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/false));
20139     SrcExprs.push_back(PseudoSrcExpr);
20140     DstExprs.push_back(PseudoDstExpr);
20141     AssignmentOps.push_back(AssignmentOp.get());
20142   }
20143 
20144   if (Vars.empty())
20145     return nullptr;
20146 
20147   return OMPCopyprivateClause::Create(Context, StartLoc, LParenLoc, EndLoc,
20148                                       Vars, SrcExprs, DstExprs, AssignmentOps);
20149 }
20150 
20151 OMPClause *Sema::ActOnOpenMPFlushClause(ArrayRef<Expr *> VarList,
20152                                         SourceLocation StartLoc,
20153                                         SourceLocation LParenLoc,
20154                                         SourceLocation EndLoc) {
20155   if (VarList.empty())
20156     return nullptr;
20157 
20158   return OMPFlushClause::Create(Context, StartLoc, LParenLoc, EndLoc, VarList);
20159 }
20160 
20161 /// Tries to find omp_depend_t. type.
20162 static bool findOMPDependT(Sema &S, SourceLocation Loc, DSAStackTy *Stack,
20163                            bool Diagnose = true) {
20164   QualType OMPDependT = Stack->getOMPDependT();
20165   if (!OMPDependT.isNull())
20166     return true;
20167   IdentifierInfo *II = &S.PP.getIdentifierTable().get("omp_depend_t");
20168   ParsedType PT = S.getTypeName(*II, Loc, S.getCurScope());
20169   if (!PT.getAsOpaquePtr() || PT.get().isNull()) {
20170     if (Diagnose)
20171       S.Diag(Loc, diag::err_omp_implied_type_not_found) << "omp_depend_t";
20172     return false;
20173   }
20174   Stack->setOMPDependT(PT.get());
20175   return true;
20176 }
20177 
20178 OMPClause *Sema::ActOnOpenMPDepobjClause(Expr *Depobj, SourceLocation StartLoc,
20179                                          SourceLocation LParenLoc,
20180                                          SourceLocation EndLoc) {
20181   if (!Depobj)
20182     return nullptr;
20183 
20184   bool OMPDependTFound = findOMPDependT(*this, StartLoc, DSAStack);
20185 
20186   // OpenMP 5.0, 2.17.10.1 depobj Construct
20187   // depobj is an lvalue expression of type omp_depend_t.
20188   if (!Depobj->isTypeDependent() && !Depobj->isValueDependent() &&
20189       !Depobj->isInstantiationDependent() &&
20190       !Depobj->containsUnexpandedParameterPack() &&
20191       (OMPDependTFound &&
20192        !Context.typesAreCompatible(DSAStack->getOMPDependT(), Depobj->getType(),
20193                                    /*CompareUnqualified=*/true))) {
20194     Diag(Depobj->getExprLoc(), diag::err_omp_expected_omp_depend_t_lvalue)
20195         << 0 << Depobj->getType() << Depobj->getSourceRange();
20196   }
20197 
20198   if (!Depobj->isLValue()) {
20199     Diag(Depobj->getExprLoc(), diag::err_omp_expected_omp_depend_t_lvalue)
20200         << 1 << Depobj->getSourceRange();
20201   }
20202 
20203   return OMPDepobjClause::Create(Context, StartLoc, LParenLoc, EndLoc, Depobj);
20204 }
20205 
20206 OMPClause *
20207 Sema::ActOnOpenMPDependClause(const OMPDependClause::DependDataTy &Data,
20208                               Expr *DepModifier, ArrayRef<Expr *> VarList,
20209                               SourceLocation StartLoc, SourceLocation LParenLoc,
20210                               SourceLocation EndLoc) {
20211   OpenMPDependClauseKind DepKind = Data.DepKind;
20212   SourceLocation DepLoc = Data.DepLoc;
20213   if (DSAStack->getCurrentDirective() == OMPD_ordered &&
20214       DepKind != OMPC_DEPEND_source && DepKind != OMPC_DEPEND_sink) {
20215     Diag(DepLoc, diag::err_omp_unexpected_clause_value)
20216         << "'source' or 'sink'" << getOpenMPClauseName(OMPC_depend);
20217     return nullptr;
20218   }
20219   if (DSAStack->getCurrentDirective() == OMPD_taskwait &&
20220       DepKind == OMPC_DEPEND_mutexinoutset) {
20221     Diag(DepLoc, diag::err_omp_taskwait_depend_mutexinoutset_not_allowed);
20222     return nullptr;
20223   }
20224   if ((DSAStack->getCurrentDirective() != OMPD_ordered ||
20225        DSAStack->getCurrentDirective() == OMPD_depobj) &&
20226       (DepKind == OMPC_DEPEND_unknown || DepKind == OMPC_DEPEND_source ||
20227        DepKind == OMPC_DEPEND_sink ||
20228        ((LangOpts.OpenMP < 50 ||
20229          DSAStack->getCurrentDirective() == OMPD_depobj) &&
20230         DepKind == OMPC_DEPEND_depobj))) {
20231     SmallVector<unsigned, 6> Except = {OMPC_DEPEND_source, OMPC_DEPEND_sink,
20232                                        OMPC_DEPEND_outallmemory,
20233                                        OMPC_DEPEND_inoutallmemory};
20234     if (LangOpts.OpenMP < 50 || DSAStack->getCurrentDirective() == OMPD_depobj)
20235       Except.push_back(OMPC_DEPEND_depobj);
20236     if (LangOpts.OpenMP < 51)
20237       Except.push_back(OMPC_DEPEND_inoutset);
20238     std::string Expected = (LangOpts.OpenMP >= 50 && !DepModifier)
20239                                ? "depend modifier(iterator) or "
20240                                : "";
20241     Diag(DepLoc, diag::err_omp_unexpected_clause_value)
20242         << Expected + getListOfPossibleValues(OMPC_depend, /*First=*/0,
20243                                               /*Last=*/OMPC_DEPEND_unknown,
20244                                               Except)
20245         << getOpenMPClauseName(OMPC_depend);
20246     return nullptr;
20247   }
20248   if (DepModifier &&
20249       (DepKind == OMPC_DEPEND_source || DepKind == OMPC_DEPEND_sink)) {
20250     Diag(DepModifier->getExprLoc(),
20251          diag::err_omp_depend_sink_source_with_modifier);
20252     return nullptr;
20253   }
20254   if (DepModifier &&
20255       !DepModifier->getType()->isSpecificBuiltinType(BuiltinType::OMPIterator))
20256     Diag(DepModifier->getExprLoc(), diag::err_omp_depend_modifier_not_iterator);
20257 
20258   SmallVector<Expr *, 8> Vars;
20259   DSAStackTy::OperatorOffsetTy OpsOffs;
20260   llvm::APSInt DepCounter(/*BitWidth=*/32);
20261   llvm::APSInt TotalDepCount(/*BitWidth=*/32);
20262   if (DepKind == OMPC_DEPEND_sink || DepKind == OMPC_DEPEND_source) {
20263     if (const Expr *OrderedCountExpr =
20264             DSAStack->getParentOrderedRegionParam().first) {
20265       TotalDepCount = OrderedCountExpr->EvaluateKnownConstInt(Context);
20266       TotalDepCount.setIsUnsigned(/*Val=*/true);
20267     }
20268   }
20269   for (Expr *RefExpr : VarList) {
20270     assert(RefExpr && "NULL expr in OpenMP shared clause.");
20271     if (isa<DependentScopeDeclRefExpr>(RefExpr)) {
20272       // It will be analyzed later.
20273       Vars.push_back(RefExpr);
20274       continue;
20275     }
20276 
20277     SourceLocation ELoc = RefExpr->getExprLoc();
20278     Expr *SimpleExpr = RefExpr->IgnoreParenCasts();
20279     if (DepKind == OMPC_DEPEND_sink) {
20280       if (DSAStack->getParentOrderedRegionParam().first &&
20281           DepCounter >= TotalDepCount) {
20282         Diag(ELoc, diag::err_omp_depend_sink_unexpected_expr);
20283         continue;
20284       }
20285       ++DepCounter;
20286       // OpenMP  [2.13.9, Summary]
20287       // depend(dependence-type : vec), where dependence-type is:
20288       // 'sink' and where vec is the iteration vector, which has the form:
20289       //  x1 [+- d1], x2 [+- d2 ], . . . , xn [+- dn]
20290       // where n is the value specified by the ordered clause in the loop
20291       // directive, xi denotes the loop iteration variable of the i-th nested
20292       // loop associated with the loop directive, and di is a constant
20293       // non-negative integer.
20294       if (CurContext->isDependentContext()) {
20295         // It will be analyzed later.
20296         Vars.push_back(RefExpr);
20297         continue;
20298       }
20299       SimpleExpr = SimpleExpr->IgnoreImplicit();
20300       OverloadedOperatorKind OOK = OO_None;
20301       SourceLocation OOLoc;
20302       Expr *LHS = SimpleExpr;
20303       Expr *RHS = nullptr;
20304       if (auto *BO = dyn_cast<BinaryOperator>(SimpleExpr)) {
20305         OOK = BinaryOperator::getOverloadedOperator(BO->getOpcode());
20306         OOLoc = BO->getOperatorLoc();
20307         LHS = BO->getLHS()->IgnoreParenImpCasts();
20308         RHS = BO->getRHS()->IgnoreParenImpCasts();
20309       } else if (auto *OCE = dyn_cast<CXXOperatorCallExpr>(SimpleExpr)) {
20310         OOK = OCE->getOperator();
20311         OOLoc = OCE->getOperatorLoc();
20312         LHS = OCE->getArg(/*Arg=*/0)->IgnoreParenImpCasts();
20313         RHS = OCE->getArg(/*Arg=*/1)->IgnoreParenImpCasts();
20314       } else if (auto *MCE = dyn_cast<CXXMemberCallExpr>(SimpleExpr)) {
20315         OOK = MCE->getMethodDecl()
20316                   ->getNameInfo()
20317                   .getName()
20318                   .getCXXOverloadedOperator();
20319         OOLoc = MCE->getCallee()->getExprLoc();
20320         LHS = MCE->getImplicitObjectArgument()->IgnoreParenImpCasts();
20321         RHS = MCE->getArg(/*Arg=*/0)->IgnoreParenImpCasts();
20322       }
20323       SourceLocation ELoc;
20324       SourceRange ERange;
20325       auto Res = getPrivateItem(*this, LHS, ELoc, ERange);
20326       if (Res.second) {
20327         // It will be analyzed later.
20328         Vars.push_back(RefExpr);
20329       }
20330       ValueDecl *D = Res.first;
20331       if (!D)
20332         continue;
20333 
20334       if (OOK != OO_Plus && OOK != OO_Minus && (RHS || OOK != OO_None)) {
20335         Diag(OOLoc, diag::err_omp_depend_sink_expected_plus_minus);
20336         continue;
20337       }
20338       if (RHS) {
20339         ExprResult RHSRes = VerifyPositiveIntegerConstantInClause(
20340             RHS, OMPC_depend, /*StrictlyPositive=*/false);
20341         if (RHSRes.isInvalid())
20342           continue;
20343       }
20344       if (!CurContext->isDependentContext() &&
20345           DSAStack->getParentOrderedRegionParam().first &&
20346           DepCounter != DSAStack->isParentLoopControlVariable(D).first) {
20347         const ValueDecl *VD =
20348             DSAStack->getParentLoopControlVariable(DepCounter.getZExtValue());
20349         if (VD)
20350           Diag(ELoc, diag::err_omp_depend_sink_expected_loop_iteration)
20351               << 1 << VD;
20352         else
20353           Diag(ELoc, diag::err_omp_depend_sink_expected_loop_iteration) << 0;
20354         continue;
20355       }
20356       OpsOffs.emplace_back(RHS, OOK);
20357     } else {
20358       bool OMPDependTFound = LangOpts.OpenMP >= 50;
20359       if (OMPDependTFound)
20360         OMPDependTFound = findOMPDependT(*this, StartLoc, DSAStack,
20361                                          DepKind == OMPC_DEPEND_depobj);
20362       if (DepKind == OMPC_DEPEND_depobj) {
20363         // OpenMP 5.0, 2.17.11 depend Clause, Restrictions, C/C++
20364         // List items used in depend clauses with the depobj dependence type
20365         // must be expressions of the omp_depend_t type.
20366         if (!RefExpr->isValueDependent() && !RefExpr->isTypeDependent() &&
20367             !RefExpr->isInstantiationDependent() &&
20368             !RefExpr->containsUnexpandedParameterPack() &&
20369             (OMPDependTFound &&
20370              !Context.hasSameUnqualifiedType(DSAStack->getOMPDependT(),
20371                                              RefExpr->getType()))) {
20372           Diag(ELoc, diag::err_omp_expected_omp_depend_t_lvalue)
20373               << 0 << RefExpr->getType() << RefExpr->getSourceRange();
20374           continue;
20375         }
20376         if (!RefExpr->isLValue()) {
20377           Diag(ELoc, diag::err_omp_expected_omp_depend_t_lvalue)
20378               << 1 << RefExpr->getType() << RefExpr->getSourceRange();
20379           continue;
20380         }
20381       } else {
20382         // OpenMP 5.0 [2.17.11, Restrictions]
20383         // List items used in depend clauses cannot be zero-length array
20384         // sections.
20385         QualType ExprTy = RefExpr->getType().getNonReferenceType();
20386         const auto *OASE = dyn_cast<OMPArraySectionExpr>(SimpleExpr);
20387         if (OASE) {
20388           QualType BaseType =
20389               OMPArraySectionExpr::getBaseOriginalType(OASE->getBase());
20390           if (const auto *ATy = BaseType->getAsArrayTypeUnsafe())
20391             ExprTy = ATy->getElementType();
20392           else
20393             ExprTy = BaseType->getPointeeType();
20394           ExprTy = ExprTy.getNonReferenceType();
20395           const Expr *Length = OASE->getLength();
20396           Expr::EvalResult Result;
20397           if (Length && !Length->isValueDependent() &&
20398               Length->EvaluateAsInt(Result, Context) &&
20399               Result.Val.getInt().isZero()) {
20400             Diag(ELoc,
20401                  diag::err_omp_depend_zero_length_array_section_not_allowed)
20402                 << SimpleExpr->getSourceRange();
20403             continue;
20404           }
20405         }
20406 
20407         // OpenMP 5.0, 2.17.11 depend Clause, Restrictions, C/C++
20408         // List items used in depend clauses with the in, out, inout,
20409         // inoutset, or mutexinoutset dependence types cannot be
20410         // expressions of the omp_depend_t type.
20411         if (!RefExpr->isValueDependent() && !RefExpr->isTypeDependent() &&
20412             !RefExpr->isInstantiationDependent() &&
20413             !RefExpr->containsUnexpandedParameterPack() &&
20414             (!RefExpr->IgnoreParenImpCasts()->isLValue() ||
20415              (OMPDependTFound &&
20416               DSAStack->getOMPDependT().getTypePtr() == ExprTy.getTypePtr()))) {
20417           Diag(ELoc, diag::err_omp_expected_addressable_lvalue_or_array_item)
20418               << (LangOpts.OpenMP >= 50 ? 1 : 0)
20419               << (LangOpts.OpenMP >= 50 ? 1 : 0) << RefExpr->getSourceRange();
20420           continue;
20421         }
20422 
20423         auto *ASE = dyn_cast<ArraySubscriptExpr>(SimpleExpr);
20424         if (ASE && !ASE->getBase()->isTypeDependent() &&
20425             !ASE->getBase()->getType().getNonReferenceType()->isPointerType() &&
20426             !ASE->getBase()->getType().getNonReferenceType()->isArrayType()) {
20427           Diag(ELoc, diag::err_omp_expected_addressable_lvalue_or_array_item)
20428               << (LangOpts.OpenMP >= 50 ? 1 : 0)
20429               << (LangOpts.OpenMP >= 50 ? 1 : 0) << RefExpr->getSourceRange();
20430           continue;
20431         }
20432 
20433         ExprResult Res;
20434         {
20435           Sema::TentativeAnalysisScope Trap(*this);
20436           Res = CreateBuiltinUnaryOp(ELoc, UO_AddrOf,
20437                                      RefExpr->IgnoreParenImpCasts());
20438         }
20439         if (!Res.isUsable() && !isa<OMPArraySectionExpr>(SimpleExpr) &&
20440             !isa<OMPArrayShapingExpr>(SimpleExpr)) {
20441           Diag(ELoc, diag::err_omp_expected_addressable_lvalue_or_array_item)
20442               << (LangOpts.OpenMP >= 50 ? 1 : 0)
20443               << (LangOpts.OpenMP >= 50 ? 1 : 0) << RefExpr->getSourceRange();
20444           continue;
20445         }
20446       }
20447     }
20448     Vars.push_back(RefExpr->IgnoreParenImpCasts());
20449   }
20450 
20451   if (!CurContext->isDependentContext() && DepKind == OMPC_DEPEND_sink &&
20452       TotalDepCount > VarList.size() &&
20453       DSAStack->getParentOrderedRegionParam().first &&
20454       DSAStack->getParentLoopControlVariable(VarList.size() + 1)) {
20455     Diag(EndLoc, diag::err_omp_depend_sink_expected_loop_iteration)
20456         << 1 << DSAStack->getParentLoopControlVariable(VarList.size() + 1);
20457   }
20458   if (DepKind != OMPC_DEPEND_source && DepKind != OMPC_DEPEND_sink &&
20459       DepKind != OMPC_DEPEND_outallmemory &&
20460       DepKind != OMPC_DEPEND_inoutallmemory && Vars.empty())
20461     return nullptr;
20462 
20463   auto *C = OMPDependClause::Create(
20464       Context, StartLoc, LParenLoc, EndLoc,
20465       {DepKind, DepLoc, Data.ColonLoc, Data.OmpAllMemoryLoc}, DepModifier, Vars,
20466       TotalDepCount.getZExtValue());
20467   if ((DepKind == OMPC_DEPEND_sink || DepKind == OMPC_DEPEND_source) &&
20468       DSAStack->isParentOrderedRegion())
20469     DSAStack->addDoacrossDependClause(C, OpsOffs);
20470   return C;
20471 }
20472 
20473 OMPClause *Sema::ActOnOpenMPDeviceClause(OpenMPDeviceClauseModifier Modifier,
20474                                          Expr *Device, SourceLocation StartLoc,
20475                                          SourceLocation LParenLoc,
20476                                          SourceLocation ModifierLoc,
20477                                          SourceLocation EndLoc) {
20478   assert((ModifierLoc.isInvalid() || LangOpts.OpenMP >= 50) &&
20479          "Unexpected device modifier in OpenMP < 50.");
20480 
20481   bool ErrorFound = false;
20482   if (ModifierLoc.isValid() && Modifier == OMPC_DEVICE_unknown) {
20483     std::string Values =
20484         getListOfPossibleValues(OMPC_device, /*First=*/0, OMPC_DEVICE_unknown);
20485     Diag(ModifierLoc, diag::err_omp_unexpected_clause_value)
20486         << Values << getOpenMPClauseName(OMPC_device);
20487     ErrorFound = true;
20488   }
20489 
20490   Expr *ValExpr = Device;
20491   Stmt *HelperValStmt = nullptr;
20492 
20493   // OpenMP [2.9.1, Restrictions]
20494   // The device expression must evaluate to a non-negative integer value.
20495   ErrorFound = !isNonNegativeIntegerValue(ValExpr, *this, OMPC_device,
20496                                           /*StrictlyPositive=*/false) ||
20497                ErrorFound;
20498   if (ErrorFound)
20499     return nullptr;
20500 
20501   // OpenMP 5.0 [2.12.5, Restrictions]
20502   // In case of ancestor device-modifier, a requires directive with
20503   // the reverse_offload clause must be specified.
20504   if (Modifier == OMPC_DEVICE_ancestor) {
20505     if (!DSAStack->hasRequiresDeclWithClause<OMPReverseOffloadClause>()) {
20506       targetDiag(
20507           StartLoc,
20508           diag::err_omp_device_ancestor_without_requires_reverse_offload);
20509       ErrorFound = true;
20510     }
20511   }
20512 
20513   OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
20514   OpenMPDirectiveKind CaptureRegion =
20515       getOpenMPCaptureRegionForClause(DKind, OMPC_device, LangOpts.OpenMP);
20516   if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
20517     ValExpr = MakeFullExpr(ValExpr).get();
20518     llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
20519     ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
20520     HelperValStmt = buildPreInits(Context, Captures);
20521   }
20522 
20523   return new (Context)
20524       OMPDeviceClause(Modifier, ValExpr, HelperValStmt, CaptureRegion, StartLoc,
20525                       LParenLoc, ModifierLoc, EndLoc);
20526 }
20527 
20528 static bool checkTypeMappable(SourceLocation SL, SourceRange SR, Sema &SemaRef,
20529                               DSAStackTy *Stack, QualType QTy,
20530                               bool FullCheck = true) {
20531   if (SemaRef.RequireCompleteType(SL, QTy, diag::err_incomplete_type))
20532     return false;
20533   if (FullCheck && !SemaRef.CurContext->isDependentContext() &&
20534       !QTy.isTriviallyCopyableType(SemaRef.Context))
20535     SemaRef.Diag(SL, diag::warn_omp_non_trivial_type_mapped) << QTy << SR;
20536   return true;
20537 }
20538 
20539 /// Return true if it can be proven that the provided array expression
20540 /// (array section or array subscript) does NOT specify the whole size of the
20541 /// array whose base type is \a BaseQTy.
20542 static bool checkArrayExpressionDoesNotReferToWholeSize(Sema &SemaRef,
20543                                                         const Expr *E,
20544                                                         QualType BaseQTy) {
20545   const auto *OASE = dyn_cast<OMPArraySectionExpr>(E);
20546 
20547   // If this is an array subscript, it refers to the whole size if the size of
20548   // the dimension is constant and equals 1. Also, an array section assumes the
20549   // format of an array subscript if no colon is used.
20550   if (isa<ArraySubscriptExpr>(E) ||
20551       (OASE && OASE->getColonLocFirst().isInvalid())) {
20552     if (const auto *ATy = dyn_cast<ConstantArrayType>(BaseQTy.getTypePtr()))
20553       return ATy->getSize().getSExtValue() != 1;
20554     // Size can't be evaluated statically.
20555     return false;
20556   }
20557 
20558   assert(OASE && "Expecting array section if not an array subscript.");
20559   const Expr *LowerBound = OASE->getLowerBound();
20560   const Expr *Length = OASE->getLength();
20561 
20562   // If there is a lower bound that does not evaluates to zero, we are not
20563   // covering the whole dimension.
20564   if (LowerBound) {
20565     Expr::EvalResult Result;
20566     if (!LowerBound->EvaluateAsInt(Result, SemaRef.getASTContext()))
20567       return false; // Can't get the integer value as a constant.
20568 
20569     llvm::APSInt ConstLowerBound = Result.Val.getInt();
20570     if (ConstLowerBound.getSExtValue())
20571       return true;
20572   }
20573 
20574   // If we don't have a length we covering the whole dimension.
20575   if (!Length)
20576     return false;
20577 
20578   // If the base is a pointer, we don't have a way to get the size of the
20579   // pointee.
20580   if (BaseQTy->isPointerType())
20581     return false;
20582 
20583   // We can only check if the length is the same as the size of the dimension
20584   // if we have a constant array.
20585   const auto *CATy = dyn_cast<ConstantArrayType>(BaseQTy.getTypePtr());
20586   if (!CATy)
20587     return false;
20588 
20589   Expr::EvalResult Result;
20590   if (!Length->EvaluateAsInt(Result, SemaRef.getASTContext()))
20591     return false; // Can't get the integer value as a constant.
20592 
20593   llvm::APSInt ConstLength = Result.Val.getInt();
20594   return CATy->getSize().getSExtValue() != ConstLength.getSExtValue();
20595 }
20596 
20597 // Return true if it can be proven that the provided array expression (array
20598 // section or array subscript) does NOT specify a single element of the array
20599 // whose base type is \a BaseQTy.
20600 static bool checkArrayExpressionDoesNotReferToUnitySize(Sema &SemaRef,
20601                                                         const Expr *E,
20602                                                         QualType BaseQTy) {
20603   const auto *OASE = dyn_cast<OMPArraySectionExpr>(E);
20604 
20605   // An array subscript always refer to a single element. Also, an array section
20606   // assumes the format of an array subscript if no colon is used.
20607   if (isa<ArraySubscriptExpr>(E) ||
20608       (OASE && OASE->getColonLocFirst().isInvalid()))
20609     return false;
20610 
20611   assert(OASE && "Expecting array section if not an array subscript.");
20612   const Expr *Length = OASE->getLength();
20613 
20614   // If we don't have a length we have to check if the array has unitary size
20615   // for this dimension. Also, we should always expect a length if the base type
20616   // is pointer.
20617   if (!Length) {
20618     if (const auto *ATy = dyn_cast<ConstantArrayType>(BaseQTy.getTypePtr()))
20619       return ATy->getSize().getSExtValue() != 1;
20620     // We cannot assume anything.
20621     return false;
20622   }
20623 
20624   // Check if the length evaluates to 1.
20625   Expr::EvalResult Result;
20626   if (!Length->EvaluateAsInt(Result, SemaRef.getASTContext()))
20627     return false; // Can't get the integer value as a constant.
20628 
20629   llvm::APSInt ConstLength = Result.Val.getInt();
20630   return ConstLength.getSExtValue() != 1;
20631 }
20632 
20633 // The base of elements of list in a map clause have to be either:
20634 //  - a reference to variable or field.
20635 //  - a member expression.
20636 //  - an array expression.
20637 //
20638 // E.g. if we have the expression 'r.S.Arr[:12]', we want to retrieve the
20639 // reference to 'r'.
20640 //
20641 // If we have:
20642 //
20643 // struct SS {
20644 //   Bla S;
20645 //   foo() {
20646 //     #pragma omp target map (S.Arr[:12]);
20647 //   }
20648 // }
20649 //
20650 // We want to retrieve the member expression 'this->S';
20651 
20652 // OpenMP 5.0 [2.19.7.1, map Clause, Restrictions, p.2]
20653 //  If a list item is an array section, it must specify contiguous storage.
20654 //
20655 // For this restriction it is sufficient that we make sure only references
20656 // to variables or fields and array expressions, and that no array sections
20657 // exist except in the rightmost expression (unless they cover the whole
20658 // dimension of the array). E.g. these would be invalid:
20659 //
20660 //   r.ArrS[3:5].Arr[6:7]
20661 //
20662 //   r.ArrS[3:5].x
20663 //
20664 // but these would be valid:
20665 //   r.ArrS[3].Arr[6:7]
20666 //
20667 //   r.ArrS[3].x
20668 namespace {
20669 class MapBaseChecker final : public StmtVisitor<MapBaseChecker, bool> {
20670   Sema &SemaRef;
20671   OpenMPClauseKind CKind = OMPC_unknown;
20672   OpenMPDirectiveKind DKind = OMPD_unknown;
20673   OMPClauseMappableExprCommon::MappableExprComponentList &Components;
20674   bool IsNonContiguous = false;
20675   bool NoDiagnose = false;
20676   const Expr *RelevantExpr = nullptr;
20677   bool AllowUnitySizeArraySection = true;
20678   bool AllowWholeSizeArraySection = true;
20679   bool AllowAnotherPtr = true;
20680   SourceLocation ELoc;
20681   SourceRange ERange;
20682 
20683   void emitErrorMsg() {
20684     // If nothing else worked, this is not a valid map clause expression.
20685     if (SemaRef.getLangOpts().OpenMP < 50) {
20686       SemaRef.Diag(ELoc,
20687                    diag::err_omp_expected_named_var_member_or_array_expression)
20688           << ERange;
20689     } else {
20690       SemaRef.Diag(ELoc, diag::err_omp_non_lvalue_in_map_or_motion_clauses)
20691           << getOpenMPClauseName(CKind) << ERange;
20692     }
20693   }
20694 
20695 public:
20696   bool VisitDeclRefExpr(DeclRefExpr *DRE) {
20697     if (!isa<VarDecl>(DRE->getDecl())) {
20698       emitErrorMsg();
20699       return false;
20700     }
20701     assert(!RelevantExpr && "RelevantExpr is expected to be nullptr");
20702     RelevantExpr = DRE;
20703     // Record the component.
20704     Components.emplace_back(DRE, DRE->getDecl(), IsNonContiguous);
20705     return true;
20706   }
20707 
20708   bool VisitMemberExpr(MemberExpr *ME) {
20709     Expr *E = ME;
20710     Expr *BaseE = ME->getBase()->IgnoreParenCasts();
20711 
20712     if (isa<CXXThisExpr>(BaseE)) {
20713       assert(!RelevantExpr && "RelevantExpr is expected to be nullptr");
20714       // We found a base expression: this->Val.
20715       RelevantExpr = ME;
20716     } else {
20717       E = BaseE;
20718     }
20719 
20720     if (!isa<FieldDecl>(ME->getMemberDecl())) {
20721       if (!NoDiagnose) {
20722         SemaRef.Diag(ELoc, diag::err_omp_expected_access_to_data_field)
20723             << ME->getSourceRange();
20724         return false;
20725       }
20726       if (RelevantExpr)
20727         return false;
20728       return Visit(E);
20729     }
20730 
20731     auto *FD = cast<FieldDecl>(ME->getMemberDecl());
20732 
20733     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C/C++, p.3]
20734     //  A bit-field cannot appear in a map clause.
20735     //
20736     if (FD->isBitField()) {
20737       if (!NoDiagnose) {
20738         SemaRef.Diag(ELoc, diag::err_omp_bit_fields_forbidden_in_clause)
20739             << ME->getSourceRange() << getOpenMPClauseName(CKind);
20740         return false;
20741       }
20742       if (RelevantExpr)
20743         return false;
20744       return Visit(E);
20745     }
20746 
20747     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C++, p.1]
20748     //  If the type of a list item is a reference to a type T then the type
20749     //  will be considered to be T for all purposes of this clause.
20750     QualType CurType = BaseE->getType().getNonReferenceType();
20751 
20752     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C/C++, p.2]
20753     //  A list item cannot be a variable that is a member of a structure with
20754     //  a union type.
20755     //
20756     if (CurType->isUnionType()) {
20757       if (!NoDiagnose) {
20758         SemaRef.Diag(ELoc, diag::err_omp_union_type_not_allowed)
20759             << ME->getSourceRange();
20760         return false;
20761       }
20762       return RelevantExpr || Visit(E);
20763     }
20764 
20765     // If we got a member expression, we should not expect any array section
20766     // before that:
20767     //
20768     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.7]
20769     //  If a list item is an element of a structure, only the rightmost symbol
20770     //  of the variable reference can be an array section.
20771     //
20772     AllowUnitySizeArraySection = false;
20773     AllowWholeSizeArraySection = false;
20774 
20775     // Record the component.
20776     Components.emplace_back(ME, FD, IsNonContiguous);
20777     return RelevantExpr || Visit(E);
20778   }
20779 
20780   bool VisitArraySubscriptExpr(ArraySubscriptExpr *AE) {
20781     Expr *E = AE->getBase()->IgnoreParenImpCasts();
20782 
20783     if (!E->getType()->isAnyPointerType() && !E->getType()->isArrayType()) {
20784       if (!NoDiagnose) {
20785         SemaRef.Diag(ELoc, diag::err_omp_expected_base_var_name)
20786             << 0 << AE->getSourceRange();
20787         return false;
20788       }
20789       return RelevantExpr || Visit(E);
20790     }
20791 
20792     // If we got an array subscript that express the whole dimension we
20793     // can have any array expressions before. If it only expressing part of
20794     // the dimension, we can only have unitary-size array expressions.
20795     if (checkArrayExpressionDoesNotReferToWholeSize(SemaRef, AE, E->getType()))
20796       AllowWholeSizeArraySection = false;
20797 
20798     if (const auto *TE = dyn_cast<CXXThisExpr>(E->IgnoreParenCasts())) {
20799       Expr::EvalResult Result;
20800       if (!AE->getIdx()->isValueDependent() &&
20801           AE->getIdx()->EvaluateAsInt(Result, SemaRef.getASTContext()) &&
20802           !Result.Val.getInt().isZero()) {
20803         SemaRef.Diag(AE->getIdx()->getExprLoc(),
20804                      diag::err_omp_invalid_map_this_expr);
20805         SemaRef.Diag(AE->getIdx()->getExprLoc(),
20806                      diag::note_omp_invalid_subscript_on_this_ptr_map);
20807       }
20808       assert(!RelevantExpr && "RelevantExpr is expected to be nullptr");
20809       RelevantExpr = TE;
20810     }
20811 
20812     // Record the component - we don't have any declaration associated.
20813     Components.emplace_back(AE, nullptr, IsNonContiguous);
20814 
20815     return RelevantExpr || Visit(E);
20816   }
20817 
20818   bool VisitOMPArraySectionExpr(OMPArraySectionExpr *OASE) {
20819     // After OMP 5.0  Array section in reduction clause will be implicitly
20820     // mapped
20821     assert(!(SemaRef.getLangOpts().OpenMP < 50 && NoDiagnose) &&
20822            "Array sections cannot be implicitly mapped.");
20823     Expr *E = OASE->getBase()->IgnoreParenImpCasts();
20824     QualType CurType =
20825         OMPArraySectionExpr::getBaseOriginalType(E).getCanonicalType();
20826 
20827     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C++, p.1]
20828     //  If the type of a list item is a reference to a type T then the type
20829     //  will be considered to be T for all purposes of this clause.
20830     if (CurType->isReferenceType())
20831       CurType = CurType->getPointeeType();
20832 
20833     bool IsPointer = CurType->isAnyPointerType();
20834 
20835     if (!IsPointer && !CurType->isArrayType()) {
20836       SemaRef.Diag(ELoc, diag::err_omp_expected_base_var_name)
20837           << 0 << OASE->getSourceRange();
20838       return false;
20839     }
20840 
20841     bool NotWhole =
20842         checkArrayExpressionDoesNotReferToWholeSize(SemaRef, OASE, CurType);
20843     bool NotUnity =
20844         checkArrayExpressionDoesNotReferToUnitySize(SemaRef, OASE, CurType);
20845 
20846     if (AllowWholeSizeArraySection) {
20847       // Any array section is currently allowed. Allowing a whole size array
20848       // section implies allowing a unity array section as well.
20849       //
20850       // If this array section refers to the whole dimension we can still
20851       // accept other array sections before this one, except if the base is a
20852       // pointer. Otherwise, only unitary sections are accepted.
20853       if (NotWhole || IsPointer)
20854         AllowWholeSizeArraySection = false;
20855     } else if (DKind == OMPD_target_update &&
20856                SemaRef.getLangOpts().OpenMP >= 50) {
20857       if (IsPointer && !AllowAnotherPtr)
20858         SemaRef.Diag(ELoc, diag::err_omp_section_length_undefined)
20859             << /*array of unknown bound */ 1;
20860       else
20861         IsNonContiguous = true;
20862     } else if (AllowUnitySizeArraySection && NotUnity) {
20863       // A unity or whole array section is not allowed and that is not
20864       // compatible with the properties of the current array section.
20865       if (NoDiagnose)
20866         return false;
20867       SemaRef.Diag(ELoc,
20868                    diag::err_array_section_does_not_specify_contiguous_storage)
20869           << OASE->getSourceRange();
20870       return false;
20871     }
20872 
20873     if (IsPointer)
20874       AllowAnotherPtr = false;
20875 
20876     if (const auto *TE = dyn_cast<CXXThisExpr>(E)) {
20877       Expr::EvalResult ResultR;
20878       Expr::EvalResult ResultL;
20879       if (!OASE->getLength()->isValueDependent() &&
20880           OASE->getLength()->EvaluateAsInt(ResultR, SemaRef.getASTContext()) &&
20881           !ResultR.Val.getInt().isOne()) {
20882         SemaRef.Diag(OASE->getLength()->getExprLoc(),
20883                      diag::err_omp_invalid_map_this_expr);
20884         SemaRef.Diag(OASE->getLength()->getExprLoc(),
20885                      diag::note_omp_invalid_length_on_this_ptr_mapping);
20886       }
20887       if (OASE->getLowerBound() && !OASE->getLowerBound()->isValueDependent() &&
20888           OASE->getLowerBound()->EvaluateAsInt(ResultL,
20889                                                SemaRef.getASTContext()) &&
20890           !ResultL.Val.getInt().isZero()) {
20891         SemaRef.Diag(OASE->getLowerBound()->getExprLoc(),
20892                      diag::err_omp_invalid_map_this_expr);
20893         SemaRef.Diag(OASE->getLowerBound()->getExprLoc(),
20894                      diag::note_omp_invalid_lower_bound_on_this_ptr_mapping);
20895       }
20896       assert(!RelevantExpr && "RelevantExpr is expected to be nullptr");
20897       RelevantExpr = TE;
20898     }
20899 
20900     // Record the component - we don't have any declaration associated.
20901     Components.emplace_back(OASE, nullptr, /*IsNonContiguous=*/false);
20902     return RelevantExpr || Visit(E);
20903   }
20904   bool VisitOMPArrayShapingExpr(OMPArrayShapingExpr *E) {
20905     Expr *Base = E->getBase();
20906 
20907     // Record the component - we don't have any declaration associated.
20908     Components.emplace_back(E, nullptr, IsNonContiguous);
20909 
20910     return Visit(Base->IgnoreParenImpCasts());
20911   }
20912 
20913   bool VisitUnaryOperator(UnaryOperator *UO) {
20914     if (SemaRef.getLangOpts().OpenMP < 50 || !UO->isLValue() ||
20915         UO->getOpcode() != UO_Deref) {
20916       emitErrorMsg();
20917       return false;
20918     }
20919     if (!RelevantExpr) {
20920       // Record the component if haven't found base decl.
20921       Components.emplace_back(UO, nullptr, /*IsNonContiguous=*/false);
20922     }
20923     return RelevantExpr || Visit(UO->getSubExpr()->IgnoreParenImpCasts());
20924   }
20925   bool VisitBinaryOperator(BinaryOperator *BO) {
20926     if (SemaRef.getLangOpts().OpenMP < 50 || !BO->getType()->isPointerType()) {
20927       emitErrorMsg();
20928       return false;
20929     }
20930 
20931     // Pointer arithmetic is the only thing we expect to happen here so after we
20932     // make sure the binary operator is a pointer type, the we only thing need
20933     // to to is to visit the subtree that has the same type as root (so that we
20934     // know the other subtree is just an offset)
20935     Expr *LE = BO->getLHS()->IgnoreParenImpCasts();
20936     Expr *RE = BO->getRHS()->IgnoreParenImpCasts();
20937     Components.emplace_back(BO, nullptr, false);
20938     assert((LE->getType().getTypePtr() == BO->getType().getTypePtr() ||
20939             RE->getType().getTypePtr() == BO->getType().getTypePtr()) &&
20940            "Either LHS or RHS have base decl inside");
20941     if (BO->getType().getTypePtr() == LE->getType().getTypePtr())
20942       return RelevantExpr || Visit(LE);
20943     return RelevantExpr || Visit(RE);
20944   }
20945   bool VisitCXXThisExpr(CXXThisExpr *CTE) {
20946     assert(!RelevantExpr && "RelevantExpr is expected to be nullptr");
20947     RelevantExpr = CTE;
20948     Components.emplace_back(CTE, nullptr, IsNonContiguous);
20949     return true;
20950   }
20951   bool VisitCXXOperatorCallExpr(CXXOperatorCallExpr *COCE) {
20952     assert(!RelevantExpr && "RelevantExpr is expected to be nullptr");
20953     Components.emplace_back(COCE, nullptr, IsNonContiguous);
20954     return true;
20955   }
20956   bool VisitOpaqueValueExpr(OpaqueValueExpr *E) {
20957     Expr *Source = E->getSourceExpr();
20958     if (!Source) {
20959       emitErrorMsg();
20960       return false;
20961     }
20962     return Visit(Source);
20963   }
20964   bool VisitStmt(Stmt *) {
20965     emitErrorMsg();
20966     return false;
20967   }
20968   const Expr *getFoundBase() const { return RelevantExpr; }
20969   explicit MapBaseChecker(
20970       Sema &SemaRef, OpenMPClauseKind CKind, OpenMPDirectiveKind DKind,
20971       OMPClauseMappableExprCommon::MappableExprComponentList &Components,
20972       bool NoDiagnose, SourceLocation &ELoc, SourceRange &ERange)
20973       : SemaRef(SemaRef), CKind(CKind), DKind(DKind), Components(Components),
20974         NoDiagnose(NoDiagnose), ELoc(ELoc), ERange(ERange) {}
20975 };
20976 } // namespace
20977 
20978 /// Return the expression of the base of the mappable expression or null if it
20979 /// cannot be determined and do all the necessary checks to see if the
20980 /// expression is valid as a standalone mappable expression. In the process,
20981 /// record all the components of the expression.
20982 static const Expr *checkMapClauseExpressionBase(
20983     Sema &SemaRef, Expr *E,
20984     OMPClauseMappableExprCommon::MappableExprComponentList &CurComponents,
20985     OpenMPClauseKind CKind, OpenMPDirectiveKind DKind, bool NoDiagnose) {
20986   SourceLocation ELoc = E->getExprLoc();
20987   SourceRange ERange = E->getSourceRange();
20988   MapBaseChecker Checker(SemaRef, CKind, DKind, CurComponents, NoDiagnose, ELoc,
20989                          ERange);
20990   if (Checker.Visit(E->IgnoreParens())) {
20991     // Check if the highest dimension array section has length specified
20992     if (SemaRef.getLangOpts().OpenMP >= 50 && !CurComponents.empty() &&
20993         (CKind == OMPC_to || CKind == OMPC_from)) {
20994       auto CI = CurComponents.rbegin();
20995       auto CE = CurComponents.rend();
20996       for (; CI != CE; ++CI) {
20997         const auto *OASE =
20998             dyn_cast<OMPArraySectionExpr>(CI->getAssociatedExpression());
20999         if (!OASE)
21000           continue;
21001         if (OASE && OASE->getLength())
21002           break;
21003         SemaRef.Diag(ELoc, diag::err_array_section_does_not_specify_length)
21004             << ERange;
21005       }
21006     }
21007     return Checker.getFoundBase();
21008   }
21009   return nullptr;
21010 }
21011 
21012 // Return true if expression E associated with value VD has conflicts with other
21013 // map information.
21014 static bool checkMapConflicts(
21015     Sema &SemaRef, DSAStackTy *DSAS, const ValueDecl *VD, const Expr *E,
21016     bool CurrentRegionOnly,
21017     OMPClauseMappableExprCommon::MappableExprComponentListRef CurComponents,
21018     OpenMPClauseKind CKind) {
21019   assert(VD && E);
21020   SourceLocation ELoc = E->getExprLoc();
21021   SourceRange ERange = E->getSourceRange();
21022 
21023   // In order to easily check the conflicts we need to match each component of
21024   // the expression under test with the components of the expressions that are
21025   // already in the stack.
21026 
21027   assert(!CurComponents.empty() && "Map clause expression with no components!");
21028   assert(CurComponents.back().getAssociatedDeclaration() == VD &&
21029          "Map clause expression with unexpected base!");
21030 
21031   // Variables to help detecting enclosing problems in data environment nests.
21032   bool IsEnclosedByDataEnvironmentExpr = false;
21033   const Expr *EnclosingExpr = nullptr;
21034 
21035   bool FoundError = DSAS->checkMappableExprComponentListsForDecl(
21036       VD, CurrentRegionOnly,
21037       [&IsEnclosedByDataEnvironmentExpr, &SemaRef, VD, CurrentRegionOnly, ELoc,
21038        ERange, CKind, &EnclosingExpr,
21039        CurComponents](OMPClauseMappableExprCommon::MappableExprComponentListRef
21040                           StackComponents,
21041                       OpenMPClauseKind Kind) {
21042         if (CKind == Kind && SemaRef.LangOpts.OpenMP >= 50)
21043           return false;
21044         assert(!StackComponents.empty() &&
21045                "Map clause expression with no components!");
21046         assert(StackComponents.back().getAssociatedDeclaration() == VD &&
21047                "Map clause expression with unexpected base!");
21048         (void)VD;
21049 
21050         // The whole expression in the stack.
21051         const Expr *RE = StackComponents.front().getAssociatedExpression();
21052 
21053         // Expressions must start from the same base. Here we detect at which
21054         // point both expressions diverge from each other and see if we can
21055         // detect if the memory referred to both expressions is contiguous and
21056         // do not overlap.
21057         auto CI = CurComponents.rbegin();
21058         auto CE = CurComponents.rend();
21059         auto SI = StackComponents.rbegin();
21060         auto SE = StackComponents.rend();
21061         for (; CI != CE && SI != SE; ++CI, ++SI) {
21062 
21063           // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.3]
21064           //  At most one list item can be an array item derived from a given
21065           //  variable in map clauses of the same construct.
21066           if (CurrentRegionOnly &&
21067               (isa<ArraySubscriptExpr>(CI->getAssociatedExpression()) ||
21068                isa<OMPArraySectionExpr>(CI->getAssociatedExpression()) ||
21069                isa<OMPArrayShapingExpr>(CI->getAssociatedExpression())) &&
21070               (isa<ArraySubscriptExpr>(SI->getAssociatedExpression()) ||
21071                isa<OMPArraySectionExpr>(SI->getAssociatedExpression()) ||
21072                isa<OMPArrayShapingExpr>(SI->getAssociatedExpression()))) {
21073             SemaRef.Diag(CI->getAssociatedExpression()->getExprLoc(),
21074                          diag::err_omp_multiple_array_items_in_map_clause)
21075                 << CI->getAssociatedExpression()->getSourceRange();
21076             SemaRef.Diag(SI->getAssociatedExpression()->getExprLoc(),
21077                          diag::note_used_here)
21078                 << SI->getAssociatedExpression()->getSourceRange();
21079             return true;
21080           }
21081 
21082           // Do both expressions have the same kind?
21083           if (CI->getAssociatedExpression()->getStmtClass() !=
21084               SI->getAssociatedExpression()->getStmtClass())
21085             break;
21086 
21087           // Are we dealing with different variables/fields?
21088           if (CI->getAssociatedDeclaration() != SI->getAssociatedDeclaration())
21089             break;
21090         }
21091         // Check if the extra components of the expressions in the enclosing
21092         // data environment are redundant for the current base declaration.
21093         // If they are, the maps completely overlap, which is legal.
21094         for (; SI != SE; ++SI) {
21095           QualType Type;
21096           if (const auto *ASE =
21097                   dyn_cast<ArraySubscriptExpr>(SI->getAssociatedExpression())) {
21098             Type = ASE->getBase()->IgnoreParenImpCasts()->getType();
21099           } else if (const auto *OASE = dyn_cast<OMPArraySectionExpr>(
21100                          SI->getAssociatedExpression())) {
21101             const Expr *E = OASE->getBase()->IgnoreParenImpCasts();
21102             Type =
21103                 OMPArraySectionExpr::getBaseOriginalType(E).getCanonicalType();
21104           } else if (const auto *OASE = dyn_cast<OMPArrayShapingExpr>(
21105                          SI->getAssociatedExpression())) {
21106             Type = OASE->getBase()->getType()->getPointeeType();
21107           }
21108           if (Type.isNull() || Type->isAnyPointerType() ||
21109               checkArrayExpressionDoesNotReferToWholeSize(
21110                   SemaRef, SI->getAssociatedExpression(), Type))
21111             break;
21112         }
21113 
21114         // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.4]
21115         //  List items of map clauses in the same construct must not share
21116         //  original storage.
21117         //
21118         // If the expressions are exactly the same or one is a subset of the
21119         // other, it means they are sharing storage.
21120         if (CI == CE && SI == SE) {
21121           if (CurrentRegionOnly) {
21122             if (CKind == OMPC_map) {
21123               SemaRef.Diag(ELoc, diag::err_omp_map_shared_storage) << ERange;
21124             } else {
21125               assert(CKind == OMPC_to || CKind == OMPC_from);
21126               SemaRef.Diag(ELoc, diag::err_omp_once_referenced_in_target_update)
21127                   << ERange;
21128             }
21129             SemaRef.Diag(RE->getExprLoc(), diag::note_used_here)
21130                 << RE->getSourceRange();
21131             return true;
21132           }
21133           // If we find the same expression in the enclosing data environment,
21134           // that is legal.
21135           IsEnclosedByDataEnvironmentExpr = true;
21136           return false;
21137         }
21138 
21139         QualType DerivedType =
21140             std::prev(CI)->getAssociatedDeclaration()->getType();
21141         SourceLocation DerivedLoc =
21142             std::prev(CI)->getAssociatedExpression()->getExprLoc();
21143 
21144         // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C++, p.1]
21145         //  If the type of a list item is a reference to a type T then the type
21146         //  will be considered to be T for all purposes of this clause.
21147         DerivedType = DerivedType.getNonReferenceType();
21148 
21149         // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C/C++, p.1]
21150         //  A variable for which the type is pointer and an array section
21151         //  derived from that variable must not appear as list items of map
21152         //  clauses of the same construct.
21153         //
21154         // Also, cover one of the cases in:
21155         // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.5]
21156         //  If any part of the original storage of a list item has corresponding
21157         //  storage in the device data environment, all of the original storage
21158         //  must have corresponding storage in the device data environment.
21159         //
21160         if (DerivedType->isAnyPointerType()) {
21161           if (CI == CE || SI == SE) {
21162             SemaRef.Diag(
21163                 DerivedLoc,
21164                 diag::err_omp_pointer_mapped_along_with_derived_section)
21165                 << DerivedLoc;
21166             SemaRef.Diag(RE->getExprLoc(), diag::note_used_here)
21167                 << RE->getSourceRange();
21168             return true;
21169           }
21170           if (CI->getAssociatedExpression()->getStmtClass() !=
21171                   SI->getAssociatedExpression()->getStmtClass() ||
21172               CI->getAssociatedDeclaration()->getCanonicalDecl() ==
21173                   SI->getAssociatedDeclaration()->getCanonicalDecl()) {
21174             assert(CI != CE && SI != SE);
21175             SemaRef.Diag(DerivedLoc, diag::err_omp_same_pointer_dereferenced)
21176                 << DerivedLoc;
21177             SemaRef.Diag(RE->getExprLoc(), diag::note_used_here)
21178                 << RE->getSourceRange();
21179             return true;
21180           }
21181         }
21182 
21183         // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.4]
21184         //  List items of map clauses in the same construct must not share
21185         //  original storage.
21186         //
21187         // An expression is a subset of the other.
21188         if (CurrentRegionOnly && (CI == CE || SI == SE)) {
21189           if (CKind == OMPC_map) {
21190             if (CI != CE || SI != SE) {
21191               // Allow constructs like this: map(s, s.ptr[0:1]), where s.ptr is
21192               // a pointer.
21193               auto Begin =
21194                   CI != CE ? CurComponents.begin() : StackComponents.begin();
21195               auto End = CI != CE ? CurComponents.end() : StackComponents.end();
21196               auto It = Begin;
21197               while (It != End && !It->getAssociatedDeclaration())
21198                 std::advance(It, 1);
21199               assert(It != End &&
21200                      "Expected at least one component with the declaration.");
21201               if (It != Begin && It->getAssociatedDeclaration()
21202                                      ->getType()
21203                                      .getCanonicalType()
21204                                      ->isAnyPointerType()) {
21205                 IsEnclosedByDataEnvironmentExpr = false;
21206                 EnclosingExpr = nullptr;
21207                 return false;
21208               }
21209             }
21210             SemaRef.Diag(ELoc, diag::err_omp_map_shared_storage) << ERange;
21211           } else {
21212             assert(CKind == OMPC_to || CKind == OMPC_from);
21213             SemaRef.Diag(ELoc, diag::err_omp_once_referenced_in_target_update)
21214                 << ERange;
21215           }
21216           SemaRef.Diag(RE->getExprLoc(), diag::note_used_here)
21217               << RE->getSourceRange();
21218           return true;
21219         }
21220 
21221         // The current expression uses the same base as other expression in the
21222         // data environment but does not contain it completely.
21223         if (!CurrentRegionOnly && SI != SE)
21224           EnclosingExpr = RE;
21225 
21226         // The current expression is a subset of the expression in the data
21227         // environment.
21228         IsEnclosedByDataEnvironmentExpr |=
21229             (!CurrentRegionOnly && CI != CE && SI == SE);
21230 
21231         return false;
21232       });
21233 
21234   if (CurrentRegionOnly)
21235     return FoundError;
21236 
21237   // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.5]
21238   //  If any part of the original storage of a list item has corresponding
21239   //  storage in the device data environment, all of the original storage must
21240   //  have corresponding storage in the device data environment.
21241   // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.6]
21242   //  If a list item is an element of a structure, and a different element of
21243   //  the structure has a corresponding list item in the device data environment
21244   //  prior to a task encountering the construct associated with the map clause,
21245   //  then the list item must also have a corresponding list item in the device
21246   //  data environment prior to the task encountering the construct.
21247   //
21248   if (EnclosingExpr && !IsEnclosedByDataEnvironmentExpr) {
21249     SemaRef.Diag(ELoc,
21250                  diag::err_omp_original_storage_is_shared_and_does_not_contain)
21251         << ERange;
21252     SemaRef.Diag(EnclosingExpr->getExprLoc(), diag::note_used_here)
21253         << EnclosingExpr->getSourceRange();
21254     return true;
21255   }
21256 
21257   return FoundError;
21258 }
21259 
21260 // Look up the user-defined mapper given the mapper name and mapped type, and
21261 // build a reference to it.
21262 static ExprResult buildUserDefinedMapperRef(Sema &SemaRef, Scope *S,
21263                                             CXXScopeSpec &MapperIdScopeSpec,
21264                                             const DeclarationNameInfo &MapperId,
21265                                             QualType Type,
21266                                             Expr *UnresolvedMapper) {
21267   if (MapperIdScopeSpec.isInvalid())
21268     return ExprError();
21269   // Get the actual type for the array type.
21270   if (Type->isArrayType()) {
21271     assert(Type->getAsArrayTypeUnsafe() && "Expect to get a valid array type");
21272     Type = Type->getAsArrayTypeUnsafe()->getElementType().getCanonicalType();
21273   }
21274   // Find all user-defined mappers with the given MapperId.
21275   SmallVector<UnresolvedSet<8>, 4> Lookups;
21276   LookupResult Lookup(SemaRef, MapperId, Sema::LookupOMPMapperName);
21277   Lookup.suppressDiagnostics();
21278   if (S) {
21279     while (S && SemaRef.LookupParsedName(Lookup, S, &MapperIdScopeSpec)) {
21280       NamedDecl *D = Lookup.getRepresentativeDecl();
21281       while (S && !S->isDeclScope(D))
21282         S = S->getParent();
21283       if (S)
21284         S = S->getParent();
21285       Lookups.emplace_back();
21286       Lookups.back().append(Lookup.begin(), Lookup.end());
21287       Lookup.clear();
21288     }
21289   } else if (auto *ULE = cast_or_null<UnresolvedLookupExpr>(UnresolvedMapper)) {
21290     // Extract the user-defined mappers with the given MapperId.
21291     Lookups.push_back(UnresolvedSet<8>());
21292     for (NamedDecl *D : ULE->decls()) {
21293       auto *DMD = cast<OMPDeclareMapperDecl>(D);
21294       assert(DMD && "Expect valid OMPDeclareMapperDecl during instantiation.");
21295       Lookups.back().addDecl(DMD);
21296     }
21297   }
21298   // Defer the lookup for dependent types. The results will be passed through
21299   // UnresolvedMapper on instantiation.
21300   if (SemaRef.CurContext->isDependentContext() || Type->isDependentType() ||
21301       Type->isInstantiationDependentType() ||
21302       Type->containsUnexpandedParameterPack() ||
21303       filterLookupForUDReductionAndMapper<bool>(Lookups, [](ValueDecl *D) {
21304         return !D->isInvalidDecl() &&
21305                (D->getType()->isDependentType() ||
21306                 D->getType()->isInstantiationDependentType() ||
21307                 D->getType()->containsUnexpandedParameterPack());
21308       })) {
21309     UnresolvedSet<8> URS;
21310     for (const UnresolvedSet<8> &Set : Lookups) {
21311       if (Set.empty())
21312         continue;
21313       URS.append(Set.begin(), Set.end());
21314     }
21315     return UnresolvedLookupExpr::Create(
21316         SemaRef.Context, /*NamingClass=*/nullptr,
21317         MapperIdScopeSpec.getWithLocInContext(SemaRef.Context), MapperId,
21318         /*ADL=*/false, /*Overloaded=*/true, URS.begin(), URS.end());
21319   }
21320   SourceLocation Loc = MapperId.getLoc();
21321   // [OpenMP 5.0], 2.19.7.3 declare mapper Directive, Restrictions
21322   //  The type must be of struct, union or class type in C and C++
21323   if (!Type->isStructureOrClassType() && !Type->isUnionType() &&
21324       (MapperIdScopeSpec.isSet() || MapperId.getAsString() != "default")) {
21325     SemaRef.Diag(Loc, diag::err_omp_mapper_wrong_type);
21326     return ExprError();
21327   }
21328   // Perform argument dependent lookup.
21329   if (SemaRef.getLangOpts().CPlusPlus && !MapperIdScopeSpec.isSet())
21330     argumentDependentLookup(SemaRef, MapperId, Loc, Type, Lookups);
21331   // Return the first user-defined mapper with the desired type.
21332   if (auto *VD = filterLookupForUDReductionAndMapper<ValueDecl *>(
21333           Lookups, [&SemaRef, Type](ValueDecl *D) -> ValueDecl * {
21334             if (!D->isInvalidDecl() &&
21335                 SemaRef.Context.hasSameType(D->getType(), Type))
21336               return D;
21337             return nullptr;
21338           }))
21339     return SemaRef.BuildDeclRefExpr(VD, Type, VK_LValue, Loc);
21340   // Find the first user-defined mapper with a type derived from the desired
21341   // type.
21342   if (auto *VD = filterLookupForUDReductionAndMapper<ValueDecl *>(
21343           Lookups, [&SemaRef, Type, Loc](ValueDecl *D) -> ValueDecl * {
21344             if (!D->isInvalidDecl() &&
21345                 SemaRef.IsDerivedFrom(Loc, Type, D->getType()) &&
21346                 !Type.isMoreQualifiedThan(D->getType()))
21347               return D;
21348             return nullptr;
21349           })) {
21350     CXXBasePaths Paths(/*FindAmbiguities=*/true, /*RecordPaths=*/true,
21351                        /*DetectVirtual=*/false);
21352     if (SemaRef.IsDerivedFrom(Loc, Type, VD->getType(), Paths)) {
21353       if (!Paths.isAmbiguous(SemaRef.Context.getCanonicalType(
21354               VD->getType().getUnqualifiedType()))) {
21355         if (SemaRef.CheckBaseClassAccess(
21356                 Loc, VD->getType(), Type, Paths.front(),
21357                 /*DiagID=*/0) != Sema::AR_inaccessible) {
21358           return SemaRef.BuildDeclRefExpr(VD, Type, VK_LValue, Loc);
21359         }
21360       }
21361     }
21362   }
21363   // Report error if a mapper is specified, but cannot be found.
21364   if (MapperIdScopeSpec.isSet() || MapperId.getAsString() != "default") {
21365     SemaRef.Diag(Loc, diag::err_omp_invalid_mapper)
21366         << Type << MapperId.getName();
21367     return ExprError();
21368   }
21369   return ExprEmpty();
21370 }
21371 
21372 namespace {
21373 // Utility struct that gathers all the related lists associated with a mappable
21374 // expression.
21375 struct MappableVarListInfo {
21376   // The list of expressions.
21377   ArrayRef<Expr *> VarList;
21378   // The list of processed expressions.
21379   SmallVector<Expr *, 16> ProcessedVarList;
21380   // The mappble components for each expression.
21381   OMPClauseMappableExprCommon::MappableExprComponentLists VarComponents;
21382   // The base declaration of the variable.
21383   SmallVector<ValueDecl *, 16> VarBaseDeclarations;
21384   // The reference to the user-defined mapper associated with every expression.
21385   SmallVector<Expr *, 16> UDMapperList;
21386 
21387   MappableVarListInfo(ArrayRef<Expr *> VarList) : VarList(VarList) {
21388     // We have a list of components and base declarations for each entry in the
21389     // variable list.
21390     VarComponents.reserve(VarList.size());
21391     VarBaseDeclarations.reserve(VarList.size());
21392   }
21393 };
21394 } // namespace
21395 
21396 // Check the validity of the provided variable list for the provided clause kind
21397 // \a CKind. In the check process the valid expressions, mappable expression
21398 // components, variables, and user-defined mappers are extracted and used to
21399 // fill \a ProcessedVarList, \a VarComponents, \a VarBaseDeclarations, and \a
21400 // UDMapperList in MVLI. \a MapType, \a IsMapTypeImplicit, \a MapperIdScopeSpec,
21401 // and \a MapperId are expected to be valid if the clause kind is 'map'.
21402 static void checkMappableExpressionList(
21403     Sema &SemaRef, DSAStackTy *DSAS, OpenMPClauseKind CKind,
21404     MappableVarListInfo &MVLI, SourceLocation StartLoc,
21405     CXXScopeSpec &MapperIdScopeSpec, DeclarationNameInfo MapperId,
21406     ArrayRef<Expr *> UnresolvedMappers,
21407     OpenMPMapClauseKind MapType = OMPC_MAP_unknown,
21408     ArrayRef<OpenMPMapModifierKind> Modifiers = None,
21409     bool IsMapTypeImplicit = false, bool NoDiagnose = false) {
21410   // We only expect mappable expressions in 'to', 'from', and 'map' clauses.
21411   assert((CKind == OMPC_map || CKind == OMPC_to || CKind == OMPC_from) &&
21412          "Unexpected clause kind with mappable expressions!");
21413 
21414   // If the identifier of user-defined mapper is not specified, it is "default".
21415   // We do not change the actual name in this clause to distinguish whether a
21416   // mapper is specified explicitly, i.e., it is not explicitly specified when
21417   // MapperId.getName() is empty.
21418   if (!MapperId.getName() || MapperId.getName().isEmpty()) {
21419     auto &DeclNames = SemaRef.getASTContext().DeclarationNames;
21420     MapperId.setName(DeclNames.getIdentifier(
21421         &SemaRef.getASTContext().Idents.get("default")));
21422     MapperId.setLoc(StartLoc);
21423   }
21424 
21425   // Iterators to find the current unresolved mapper expression.
21426   auto UMIt = UnresolvedMappers.begin(), UMEnd = UnresolvedMappers.end();
21427   bool UpdateUMIt = false;
21428   Expr *UnresolvedMapper = nullptr;
21429 
21430   bool HasHoldModifier =
21431       llvm::is_contained(Modifiers, OMPC_MAP_MODIFIER_ompx_hold);
21432 
21433   // Keep track of the mappable components and base declarations in this clause.
21434   // Each entry in the list is going to have a list of components associated. We
21435   // record each set of the components so that we can build the clause later on.
21436   // In the end we should have the same amount of declarations and component
21437   // lists.
21438 
21439   for (Expr *RE : MVLI.VarList) {
21440     assert(RE && "Null expr in omp to/from/map clause");
21441     SourceLocation ELoc = RE->getExprLoc();
21442 
21443     // Find the current unresolved mapper expression.
21444     if (UpdateUMIt && UMIt != UMEnd) {
21445       UMIt++;
21446       assert(
21447           UMIt != UMEnd &&
21448           "Expect the size of UnresolvedMappers to match with that of VarList");
21449     }
21450     UpdateUMIt = true;
21451     if (UMIt != UMEnd)
21452       UnresolvedMapper = *UMIt;
21453 
21454     const Expr *VE = RE->IgnoreParenLValueCasts();
21455 
21456     if (VE->isValueDependent() || VE->isTypeDependent() ||
21457         VE->isInstantiationDependent() ||
21458         VE->containsUnexpandedParameterPack()) {
21459       // Try to find the associated user-defined mapper.
21460       ExprResult ER = buildUserDefinedMapperRef(
21461           SemaRef, DSAS->getCurScope(), MapperIdScopeSpec, MapperId,
21462           VE->getType().getCanonicalType(), UnresolvedMapper);
21463       if (ER.isInvalid())
21464         continue;
21465       MVLI.UDMapperList.push_back(ER.get());
21466       // We can only analyze this information once the missing information is
21467       // resolved.
21468       MVLI.ProcessedVarList.push_back(RE);
21469       continue;
21470     }
21471 
21472     Expr *SimpleExpr = RE->IgnoreParenCasts();
21473 
21474     if (!RE->isLValue()) {
21475       if (SemaRef.getLangOpts().OpenMP < 50) {
21476         SemaRef.Diag(
21477             ELoc, diag::err_omp_expected_named_var_member_or_array_expression)
21478             << RE->getSourceRange();
21479       } else {
21480         SemaRef.Diag(ELoc, diag::err_omp_non_lvalue_in_map_or_motion_clauses)
21481             << getOpenMPClauseName(CKind) << RE->getSourceRange();
21482       }
21483       continue;
21484     }
21485 
21486     OMPClauseMappableExprCommon::MappableExprComponentList CurComponents;
21487     ValueDecl *CurDeclaration = nullptr;
21488 
21489     // Obtain the array or member expression bases if required. Also, fill the
21490     // components array with all the components identified in the process.
21491     const Expr *BE =
21492         checkMapClauseExpressionBase(SemaRef, SimpleExpr, CurComponents, CKind,
21493                                      DSAS->getCurrentDirective(), NoDiagnose);
21494     if (!BE)
21495       continue;
21496 
21497     assert(!CurComponents.empty() &&
21498            "Invalid mappable expression information.");
21499 
21500     if (const auto *TE = dyn_cast<CXXThisExpr>(BE)) {
21501       // Add store "this" pointer to class in DSAStackTy for future checking
21502       DSAS->addMappedClassesQualTypes(TE->getType());
21503       // Try to find the associated user-defined mapper.
21504       ExprResult ER = buildUserDefinedMapperRef(
21505           SemaRef, DSAS->getCurScope(), MapperIdScopeSpec, MapperId,
21506           VE->getType().getCanonicalType(), UnresolvedMapper);
21507       if (ER.isInvalid())
21508         continue;
21509       MVLI.UDMapperList.push_back(ER.get());
21510       // Skip restriction checking for variable or field declarations
21511       MVLI.ProcessedVarList.push_back(RE);
21512       MVLI.VarComponents.resize(MVLI.VarComponents.size() + 1);
21513       MVLI.VarComponents.back().append(CurComponents.begin(),
21514                                        CurComponents.end());
21515       MVLI.VarBaseDeclarations.push_back(nullptr);
21516       continue;
21517     }
21518 
21519     // For the following checks, we rely on the base declaration which is
21520     // expected to be associated with the last component. The declaration is
21521     // expected to be a variable or a field (if 'this' is being mapped).
21522     CurDeclaration = CurComponents.back().getAssociatedDeclaration();
21523     assert(CurDeclaration && "Null decl on map clause.");
21524     assert(
21525         CurDeclaration->isCanonicalDecl() &&
21526         "Expecting components to have associated only canonical declarations.");
21527 
21528     auto *VD = dyn_cast<VarDecl>(CurDeclaration);
21529     const auto *FD = dyn_cast<FieldDecl>(CurDeclaration);
21530 
21531     assert((VD || FD) && "Only variables or fields are expected here!");
21532     (void)FD;
21533 
21534     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.10]
21535     // threadprivate variables cannot appear in a map clause.
21536     // OpenMP 4.5 [2.10.5, target update Construct]
21537     // threadprivate variables cannot appear in a from clause.
21538     if (VD && DSAS->isThreadPrivate(VD)) {
21539       if (NoDiagnose)
21540         continue;
21541       DSAStackTy::DSAVarData DVar = DSAS->getTopDSA(VD, /*FromParent=*/false);
21542       SemaRef.Diag(ELoc, diag::err_omp_threadprivate_in_clause)
21543           << getOpenMPClauseName(CKind);
21544       reportOriginalDsa(SemaRef, DSAS, VD, DVar);
21545       continue;
21546     }
21547 
21548     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.9]
21549     //  A list item cannot appear in both a map clause and a data-sharing
21550     //  attribute clause on the same construct.
21551 
21552     // Check conflicts with other map clause expressions. We check the conflicts
21553     // with the current construct separately from the enclosing data
21554     // environment, because the restrictions are different. We only have to
21555     // check conflicts across regions for the map clauses.
21556     if (checkMapConflicts(SemaRef, DSAS, CurDeclaration, SimpleExpr,
21557                           /*CurrentRegionOnly=*/true, CurComponents, CKind))
21558       break;
21559     if (CKind == OMPC_map &&
21560         (SemaRef.getLangOpts().OpenMP <= 45 || StartLoc.isValid()) &&
21561         checkMapConflicts(SemaRef, DSAS, CurDeclaration, SimpleExpr,
21562                           /*CurrentRegionOnly=*/false, CurComponents, CKind))
21563       break;
21564 
21565     // OpenMP 4.5 [2.10.5, target update Construct]
21566     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C++, p.1]
21567     //  If the type of a list item is a reference to a type T then the type will
21568     //  be considered to be T for all purposes of this clause.
21569     auto I = llvm::find_if(
21570         CurComponents,
21571         [](const OMPClauseMappableExprCommon::MappableComponent &MC) {
21572           return MC.getAssociatedDeclaration();
21573         });
21574     assert(I != CurComponents.end() && "Null decl on map clause.");
21575     (void)I;
21576     QualType Type;
21577     auto *ASE = dyn_cast<ArraySubscriptExpr>(VE->IgnoreParens());
21578     auto *OASE = dyn_cast<OMPArraySectionExpr>(VE->IgnoreParens());
21579     auto *OAShE = dyn_cast<OMPArrayShapingExpr>(VE->IgnoreParens());
21580     if (ASE) {
21581       Type = ASE->getType().getNonReferenceType();
21582     } else if (OASE) {
21583       QualType BaseType =
21584           OMPArraySectionExpr::getBaseOriginalType(OASE->getBase());
21585       if (const auto *ATy = BaseType->getAsArrayTypeUnsafe())
21586         Type = ATy->getElementType();
21587       else
21588         Type = BaseType->getPointeeType();
21589       Type = Type.getNonReferenceType();
21590     } else if (OAShE) {
21591       Type = OAShE->getBase()->getType()->getPointeeType();
21592     } else {
21593       Type = VE->getType();
21594     }
21595 
21596     // OpenMP 4.5 [2.10.5, target update Construct, Restrictions, p.4]
21597     // A list item in a to or from clause must have a mappable type.
21598     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.9]
21599     //  A list item must have a mappable type.
21600     if (!checkTypeMappable(VE->getExprLoc(), VE->getSourceRange(), SemaRef,
21601                            DSAS, Type, /*FullCheck=*/true))
21602       continue;
21603 
21604     if (CKind == OMPC_map) {
21605       // target enter data
21606       // OpenMP [2.10.2, Restrictions, p. 99]
21607       // A map-type must be specified in all map clauses and must be either
21608       // to or alloc.
21609       OpenMPDirectiveKind DKind = DSAS->getCurrentDirective();
21610       if (DKind == OMPD_target_enter_data &&
21611           !(MapType == OMPC_MAP_to || MapType == OMPC_MAP_alloc)) {
21612         SemaRef.Diag(StartLoc, diag::err_omp_invalid_map_type_for_directive)
21613             << (IsMapTypeImplicit ? 1 : 0)
21614             << getOpenMPSimpleClauseTypeName(OMPC_map, MapType)
21615             << getOpenMPDirectiveName(DKind);
21616         continue;
21617       }
21618 
21619       // target exit_data
21620       // OpenMP [2.10.3, Restrictions, p. 102]
21621       // A map-type must be specified in all map clauses and must be either
21622       // from, release, or delete.
21623       if (DKind == OMPD_target_exit_data &&
21624           !(MapType == OMPC_MAP_from || MapType == OMPC_MAP_release ||
21625             MapType == OMPC_MAP_delete)) {
21626         SemaRef.Diag(StartLoc, diag::err_omp_invalid_map_type_for_directive)
21627             << (IsMapTypeImplicit ? 1 : 0)
21628             << getOpenMPSimpleClauseTypeName(OMPC_map, MapType)
21629             << getOpenMPDirectiveName(DKind);
21630         continue;
21631       }
21632 
21633       // The 'ompx_hold' modifier is specifically intended to be used on a
21634       // 'target' or 'target data' directive to prevent data from being unmapped
21635       // during the associated statement.  It is not permitted on a 'target
21636       // enter data' or 'target exit data' directive, which have no associated
21637       // statement.
21638       if ((DKind == OMPD_target_enter_data || DKind == OMPD_target_exit_data) &&
21639           HasHoldModifier) {
21640         SemaRef.Diag(StartLoc,
21641                      diag::err_omp_invalid_map_type_modifier_for_directive)
21642             << getOpenMPSimpleClauseTypeName(OMPC_map,
21643                                              OMPC_MAP_MODIFIER_ompx_hold)
21644             << getOpenMPDirectiveName(DKind);
21645         continue;
21646       }
21647 
21648       // target, target data
21649       // OpenMP 5.0 [2.12.2, Restrictions, p. 163]
21650       // OpenMP 5.0 [2.12.5, Restrictions, p. 174]
21651       // A map-type in a map clause must be to, from, tofrom or alloc
21652       if ((DKind == OMPD_target_data ||
21653            isOpenMPTargetExecutionDirective(DKind)) &&
21654           !(MapType == OMPC_MAP_to || MapType == OMPC_MAP_from ||
21655             MapType == OMPC_MAP_tofrom || MapType == OMPC_MAP_alloc)) {
21656         SemaRef.Diag(StartLoc, diag::err_omp_invalid_map_type_for_directive)
21657             << (IsMapTypeImplicit ? 1 : 0)
21658             << getOpenMPSimpleClauseTypeName(OMPC_map, MapType)
21659             << getOpenMPDirectiveName(DKind);
21660         continue;
21661       }
21662 
21663       // OpenMP 4.5 [2.15.5.1, Restrictions, p.3]
21664       // A list item cannot appear in both a map clause and a data-sharing
21665       // attribute clause on the same construct
21666       //
21667       // OpenMP 5.0 [2.19.7.1, Restrictions, p.7]
21668       // A list item cannot appear in both a map clause and a data-sharing
21669       // attribute clause on the same construct unless the construct is a
21670       // combined construct.
21671       if (VD && ((SemaRef.LangOpts.OpenMP <= 45 &&
21672                   isOpenMPTargetExecutionDirective(DKind)) ||
21673                  DKind == OMPD_target)) {
21674         DSAStackTy::DSAVarData DVar = DSAS->getTopDSA(VD, /*FromParent=*/false);
21675         if (isOpenMPPrivate(DVar.CKind)) {
21676           SemaRef.Diag(ELoc, diag::err_omp_variable_in_given_clause_and_dsa)
21677               << getOpenMPClauseName(DVar.CKind)
21678               << getOpenMPClauseName(OMPC_map)
21679               << getOpenMPDirectiveName(DSAS->getCurrentDirective());
21680           reportOriginalDsa(SemaRef, DSAS, CurDeclaration, DVar);
21681           continue;
21682         }
21683       }
21684     }
21685 
21686     // Try to find the associated user-defined mapper.
21687     ExprResult ER = buildUserDefinedMapperRef(
21688         SemaRef, DSAS->getCurScope(), MapperIdScopeSpec, MapperId,
21689         Type.getCanonicalType(), UnresolvedMapper);
21690     if (ER.isInvalid())
21691       continue;
21692     MVLI.UDMapperList.push_back(ER.get());
21693 
21694     // Save the current expression.
21695     MVLI.ProcessedVarList.push_back(RE);
21696 
21697     // Store the components in the stack so that they can be used to check
21698     // against other clauses later on.
21699     DSAS->addMappableExpressionComponents(CurDeclaration, CurComponents,
21700                                           /*WhereFoundClauseKind=*/OMPC_map);
21701 
21702     // Save the components and declaration to create the clause. For purposes of
21703     // the clause creation, any component list that has has base 'this' uses
21704     // null as base declaration.
21705     MVLI.VarComponents.resize(MVLI.VarComponents.size() + 1);
21706     MVLI.VarComponents.back().append(CurComponents.begin(),
21707                                      CurComponents.end());
21708     MVLI.VarBaseDeclarations.push_back(isa<MemberExpr>(BE) ? nullptr
21709                                                            : CurDeclaration);
21710   }
21711 }
21712 
21713 OMPClause *Sema::ActOnOpenMPMapClause(
21714     ArrayRef<OpenMPMapModifierKind> MapTypeModifiers,
21715     ArrayRef<SourceLocation> MapTypeModifiersLoc,
21716     CXXScopeSpec &MapperIdScopeSpec, DeclarationNameInfo &MapperId,
21717     OpenMPMapClauseKind MapType, bool IsMapTypeImplicit, SourceLocation MapLoc,
21718     SourceLocation ColonLoc, ArrayRef<Expr *> VarList,
21719     const OMPVarListLocTy &Locs, bool NoDiagnose,
21720     ArrayRef<Expr *> UnresolvedMappers) {
21721   OpenMPMapModifierKind Modifiers[] = {
21722       OMPC_MAP_MODIFIER_unknown, OMPC_MAP_MODIFIER_unknown,
21723       OMPC_MAP_MODIFIER_unknown, OMPC_MAP_MODIFIER_unknown,
21724       OMPC_MAP_MODIFIER_unknown};
21725   SourceLocation ModifiersLoc[NumberOfOMPMapClauseModifiers];
21726 
21727   // Process map-type-modifiers, flag errors for duplicate modifiers.
21728   unsigned Count = 0;
21729   for (unsigned I = 0, E = MapTypeModifiers.size(); I < E; ++I) {
21730     if (MapTypeModifiers[I] != OMPC_MAP_MODIFIER_unknown &&
21731         llvm::is_contained(Modifiers, MapTypeModifiers[I])) {
21732       Diag(MapTypeModifiersLoc[I], diag::err_omp_duplicate_map_type_modifier);
21733       continue;
21734     }
21735     assert(Count < NumberOfOMPMapClauseModifiers &&
21736            "Modifiers exceed the allowed number of map type modifiers");
21737     Modifiers[Count] = MapTypeModifiers[I];
21738     ModifiersLoc[Count] = MapTypeModifiersLoc[I];
21739     ++Count;
21740   }
21741 
21742   MappableVarListInfo MVLI(VarList);
21743   checkMappableExpressionList(*this, DSAStack, OMPC_map, MVLI, Locs.StartLoc,
21744                               MapperIdScopeSpec, MapperId, UnresolvedMappers,
21745                               MapType, Modifiers, IsMapTypeImplicit,
21746                               NoDiagnose);
21747 
21748   // We need to produce a map clause even if we don't have variables so that
21749   // other diagnostics related with non-existing map clauses are accurate.
21750   return OMPMapClause::Create(Context, Locs, MVLI.ProcessedVarList,
21751                               MVLI.VarBaseDeclarations, MVLI.VarComponents,
21752                               MVLI.UDMapperList, Modifiers, ModifiersLoc,
21753                               MapperIdScopeSpec.getWithLocInContext(Context),
21754                               MapperId, MapType, IsMapTypeImplicit, MapLoc);
21755 }
21756 
21757 QualType Sema::ActOnOpenMPDeclareReductionType(SourceLocation TyLoc,
21758                                                TypeResult ParsedType) {
21759   assert(ParsedType.isUsable());
21760 
21761   QualType ReductionType = GetTypeFromParser(ParsedType.get());
21762   if (ReductionType.isNull())
21763     return QualType();
21764 
21765   // [OpenMP 4.0], 2.15 declare reduction Directive, Restrictions, C\C++
21766   // A type name in a declare reduction directive cannot be a function type, an
21767   // array type, a reference type, or a type qualified with const, volatile or
21768   // restrict.
21769   if (ReductionType.hasQualifiers()) {
21770     Diag(TyLoc, diag::err_omp_reduction_wrong_type) << 0;
21771     return QualType();
21772   }
21773 
21774   if (ReductionType->isFunctionType()) {
21775     Diag(TyLoc, diag::err_omp_reduction_wrong_type) << 1;
21776     return QualType();
21777   }
21778   if (ReductionType->isReferenceType()) {
21779     Diag(TyLoc, diag::err_omp_reduction_wrong_type) << 2;
21780     return QualType();
21781   }
21782   if (ReductionType->isArrayType()) {
21783     Diag(TyLoc, diag::err_omp_reduction_wrong_type) << 3;
21784     return QualType();
21785   }
21786   return ReductionType;
21787 }
21788 
21789 Sema::DeclGroupPtrTy Sema::ActOnOpenMPDeclareReductionDirectiveStart(
21790     Scope *S, DeclContext *DC, DeclarationName Name,
21791     ArrayRef<std::pair<QualType, SourceLocation>> ReductionTypes,
21792     AccessSpecifier AS, Decl *PrevDeclInScope) {
21793   SmallVector<Decl *, 8> Decls;
21794   Decls.reserve(ReductionTypes.size());
21795 
21796   LookupResult Lookup(*this, Name, SourceLocation(), LookupOMPReductionName,
21797                       forRedeclarationInCurContext());
21798   // [OpenMP 4.0], 2.15 declare reduction Directive, Restrictions
21799   // A reduction-identifier may not be re-declared in the current scope for the
21800   // same type or for a type that is compatible according to the base language
21801   // rules.
21802   llvm::DenseMap<QualType, SourceLocation> PreviousRedeclTypes;
21803   OMPDeclareReductionDecl *PrevDRD = nullptr;
21804   bool InCompoundScope = true;
21805   if (S != nullptr) {
21806     // Find previous declaration with the same name not referenced in other
21807     // declarations.
21808     FunctionScopeInfo *ParentFn = getEnclosingFunction();
21809     InCompoundScope =
21810         (ParentFn != nullptr) && !ParentFn->CompoundScopes.empty();
21811     LookupName(Lookup, S);
21812     FilterLookupForScope(Lookup, DC, S, /*ConsiderLinkage=*/false,
21813                          /*AllowInlineNamespace=*/false);
21814     llvm::DenseMap<OMPDeclareReductionDecl *, bool> UsedAsPrevious;
21815     LookupResult::Filter Filter = Lookup.makeFilter();
21816     while (Filter.hasNext()) {
21817       auto *PrevDecl = cast<OMPDeclareReductionDecl>(Filter.next());
21818       if (InCompoundScope) {
21819         auto I = UsedAsPrevious.find(PrevDecl);
21820         if (I == UsedAsPrevious.end())
21821           UsedAsPrevious[PrevDecl] = false;
21822         if (OMPDeclareReductionDecl *D = PrevDecl->getPrevDeclInScope())
21823           UsedAsPrevious[D] = true;
21824       }
21825       PreviousRedeclTypes[PrevDecl->getType().getCanonicalType()] =
21826           PrevDecl->getLocation();
21827     }
21828     Filter.done();
21829     if (InCompoundScope) {
21830       for (const auto &PrevData : UsedAsPrevious) {
21831         if (!PrevData.second) {
21832           PrevDRD = PrevData.first;
21833           break;
21834         }
21835       }
21836     }
21837   } else if (PrevDeclInScope != nullptr) {
21838     auto *PrevDRDInScope = PrevDRD =
21839         cast<OMPDeclareReductionDecl>(PrevDeclInScope);
21840     do {
21841       PreviousRedeclTypes[PrevDRDInScope->getType().getCanonicalType()] =
21842           PrevDRDInScope->getLocation();
21843       PrevDRDInScope = PrevDRDInScope->getPrevDeclInScope();
21844     } while (PrevDRDInScope != nullptr);
21845   }
21846   for (const auto &TyData : ReductionTypes) {
21847     const auto I = PreviousRedeclTypes.find(TyData.first.getCanonicalType());
21848     bool Invalid = false;
21849     if (I != PreviousRedeclTypes.end()) {
21850       Diag(TyData.second, diag::err_omp_declare_reduction_redefinition)
21851           << TyData.first;
21852       Diag(I->second, diag::note_previous_definition);
21853       Invalid = true;
21854     }
21855     PreviousRedeclTypes[TyData.first.getCanonicalType()] = TyData.second;
21856     auto *DRD = OMPDeclareReductionDecl::Create(Context, DC, TyData.second,
21857                                                 Name, TyData.first, PrevDRD);
21858     DC->addDecl(DRD);
21859     DRD->setAccess(AS);
21860     Decls.push_back(DRD);
21861     if (Invalid)
21862       DRD->setInvalidDecl();
21863     else
21864       PrevDRD = DRD;
21865   }
21866 
21867   return DeclGroupPtrTy::make(
21868       DeclGroupRef::Create(Context, Decls.begin(), Decls.size()));
21869 }
21870 
21871 void Sema::ActOnOpenMPDeclareReductionCombinerStart(Scope *S, Decl *D) {
21872   auto *DRD = cast<OMPDeclareReductionDecl>(D);
21873 
21874   // Enter new function scope.
21875   PushFunctionScope();
21876   setFunctionHasBranchProtectedScope();
21877   getCurFunction()->setHasOMPDeclareReductionCombiner();
21878 
21879   if (S != nullptr)
21880     PushDeclContext(S, DRD);
21881   else
21882     CurContext = DRD;
21883 
21884   PushExpressionEvaluationContext(
21885       ExpressionEvaluationContext::PotentiallyEvaluated);
21886 
21887   QualType ReductionType = DRD->getType();
21888   // Create 'T* omp_parm;T omp_in;'. All references to 'omp_in' will
21889   // be replaced by '*omp_parm' during codegen. This required because 'omp_in'
21890   // uses semantics of argument handles by value, but it should be passed by
21891   // reference. C lang does not support references, so pass all parameters as
21892   // pointers.
21893   // Create 'T omp_in;' variable.
21894   VarDecl *OmpInParm =
21895       buildVarDecl(*this, D->getLocation(), ReductionType, "omp_in");
21896   // Create 'T* omp_parm;T omp_out;'. All references to 'omp_out' will
21897   // be replaced by '*omp_parm' during codegen. This required because 'omp_out'
21898   // uses semantics of argument handles by value, but it should be passed by
21899   // reference. C lang does not support references, so pass all parameters as
21900   // pointers.
21901   // Create 'T omp_out;' variable.
21902   VarDecl *OmpOutParm =
21903       buildVarDecl(*this, D->getLocation(), ReductionType, "omp_out");
21904   if (S != nullptr) {
21905     PushOnScopeChains(OmpInParm, S);
21906     PushOnScopeChains(OmpOutParm, S);
21907   } else {
21908     DRD->addDecl(OmpInParm);
21909     DRD->addDecl(OmpOutParm);
21910   }
21911   Expr *InE =
21912       ::buildDeclRefExpr(*this, OmpInParm, ReductionType, D->getLocation());
21913   Expr *OutE =
21914       ::buildDeclRefExpr(*this, OmpOutParm, ReductionType, D->getLocation());
21915   DRD->setCombinerData(InE, OutE);
21916 }
21917 
21918 void Sema::ActOnOpenMPDeclareReductionCombinerEnd(Decl *D, Expr *Combiner) {
21919   auto *DRD = cast<OMPDeclareReductionDecl>(D);
21920   DiscardCleanupsInEvaluationContext();
21921   PopExpressionEvaluationContext();
21922 
21923   PopDeclContext();
21924   PopFunctionScopeInfo();
21925 
21926   if (Combiner != nullptr)
21927     DRD->setCombiner(Combiner);
21928   else
21929     DRD->setInvalidDecl();
21930 }
21931 
21932 VarDecl *Sema::ActOnOpenMPDeclareReductionInitializerStart(Scope *S, Decl *D) {
21933   auto *DRD = cast<OMPDeclareReductionDecl>(D);
21934 
21935   // Enter new function scope.
21936   PushFunctionScope();
21937   setFunctionHasBranchProtectedScope();
21938 
21939   if (S != nullptr)
21940     PushDeclContext(S, DRD);
21941   else
21942     CurContext = DRD;
21943 
21944   PushExpressionEvaluationContext(
21945       ExpressionEvaluationContext::PotentiallyEvaluated);
21946 
21947   QualType ReductionType = DRD->getType();
21948   // Create 'T* omp_parm;T omp_priv;'. All references to 'omp_priv' will
21949   // be replaced by '*omp_parm' during codegen. This required because 'omp_priv'
21950   // uses semantics of argument handles by value, but it should be passed by
21951   // reference. C lang does not support references, so pass all parameters as
21952   // pointers.
21953   // Create 'T omp_priv;' variable.
21954   VarDecl *OmpPrivParm =
21955       buildVarDecl(*this, D->getLocation(), ReductionType, "omp_priv");
21956   // Create 'T* omp_parm;T omp_orig;'. All references to 'omp_orig' will
21957   // be replaced by '*omp_parm' during codegen. This required because 'omp_orig'
21958   // uses semantics of argument handles by value, but it should be passed by
21959   // reference. C lang does not support references, so pass all parameters as
21960   // pointers.
21961   // Create 'T omp_orig;' variable.
21962   VarDecl *OmpOrigParm =
21963       buildVarDecl(*this, D->getLocation(), ReductionType, "omp_orig");
21964   if (S != nullptr) {
21965     PushOnScopeChains(OmpPrivParm, S);
21966     PushOnScopeChains(OmpOrigParm, S);
21967   } else {
21968     DRD->addDecl(OmpPrivParm);
21969     DRD->addDecl(OmpOrigParm);
21970   }
21971   Expr *OrigE =
21972       ::buildDeclRefExpr(*this, OmpOrigParm, ReductionType, D->getLocation());
21973   Expr *PrivE =
21974       ::buildDeclRefExpr(*this, OmpPrivParm, ReductionType, D->getLocation());
21975   DRD->setInitializerData(OrigE, PrivE);
21976   return OmpPrivParm;
21977 }
21978 
21979 void Sema::ActOnOpenMPDeclareReductionInitializerEnd(Decl *D, Expr *Initializer,
21980                                                      VarDecl *OmpPrivParm) {
21981   auto *DRD = cast<OMPDeclareReductionDecl>(D);
21982   DiscardCleanupsInEvaluationContext();
21983   PopExpressionEvaluationContext();
21984 
21985   PopDeclContext();
21986   PopFunctionScopeInfo();
21987 
21988   if (Initializer != nullptr) {
21989     DRD->setInitializer(Initializer, OMPDeclareReductionDecl::CallInit);
21990   } else if (OmpPrivParm->hasInit()) {
21991     DRD->setInitializer(OmpPrivParm->getInit(),
21992                         OmpPrivParm->isDirectInit()
21993                             ? OMPDeclareReductionDecl::DirectInit
21994                             : OMPDeclareReductionDecl::CopyInit);
21995   } else {
21996     DRD->setInvalidDecl();
21997   }
21998 }
21999 
22000 Sema::DeclGroupPtrTy Sema::ActOnOpenMPDeclareReductionDirectiveEnd(
22001     Scope *S, DeclGroupPtrTy DeclReductions, bool IsValid) {
22002   for (Decl *D : DeclReductions.get()) {
22003     if (IsValid) {
22004       if (S)
22005         PushOnScopeChains(cast<OMPDeclareReductionDecl>(D), S,
22006                           /*AddToContext=*/false);
22007     } else {
22008       D->setInvalidDecl();
22009     }
22010   }
22011   return DeclReductions;
22012 }
22013 
22014 TypeResult Sema::ActOnOpenMPDeclareMapperVarDecl(Scope *S, Declarator &D) {
22015   TypeSourceInfo *TInfo = GetTypeForDeclarator(D, S);
22016   QualType T = TInfo->getType();
22017   if (D.isInvalidType())
22018     return true;
22019 
22020   if (getLangOpts().CPlusPlus) {
22021     // Check that there are no default arguments (C++ only).
22022     CheckExtraCXXDefaultArguments(D);
22023   }
22024 
22025   return CreateParsedType(T, TInfo);
22026 }
22027 
22028 QualType Sema::ActOnOpenMPDeclareMapperType(SourceLocation TyLoc,
22029                                             TypeResult ParsedType) {
22030   assert(ParsedType.isUsable() && "Expect usable parsed mapper type");
22031 
22032   QualType MapperType = GetTypeFromParser(ParsedType.get());
22033   assert(!MapperType.isNull() && "Expect valid mapper type");
22034 
22035   // [OpenMP 5.0], 2.19.7.3 declare mapper Directive, Restrictions
22036   //  The type must be of struct, union or class type in C and C++
22037   if (!MapperType->isStructureOrClassType() && !MapperType->isUnionType()) {
22038     Diag(TyLoc, diag::err_omp_mapper_wrong_type);
22039     return QualType();
22040   }
22041   return MapperType;
22042 }
22043 
22044 Sema::DeclGroupPtrTy Sema::ActOnOpenMPDeclareMapperDirective(
22045     Scope *S, DeclContext *DC, DeclarationName Name, QualType MapperType,
22046     SourceLocation StartLoc, DeclarationName VN, AccessSpecifier AS,
22047     Expr *MapperVarRef, ArrayRef<OMPClause *> Clauses, Decl *PrevDeclInScope) {
22048   LookupResult Lookup(*this, Name, SourceLocation(), LookupOMPMapperName,
22049                       forRedeclarationInCurContext());
22050   // [OpenMP 5.0], 2.19.7.3 declare mapper Directive, Restrictions
22051   //  A mapper-identifier may not be redeclared in the current scope for the
22052   //  same type or for a type that is compatible according to the base language
22053   //  rules.
22054   llvm::DenseMap<QualType, SourceLocation> PreviousRedeclTypes;
22055   OMPDeclareMapperDecl *PrevDMD = nullptr;
22056   bool InCompoundScope = true;
22057   if (S != nullptr) {
22058     // Find previous declaration with the same name not referenced in other
22059     // declarations.
22060     FunctionScopeInfo *ParentFn = getEnclosingFunction();
22061     InCompoundScope =
22062         (ParentFn != nullptr) && !ParentFn->CompoundScopes.empty();
22063     LookupName(Lookup, S);
22064     FilterLookupForScope(Lookup, DC, S, /*ConsiderLinkage=*/false,
22065                          /*AllowInlineNamespace=*/false);
22066     llvm::DenseMap<OMPDeclareMapperDecl *, bool> UsedAsPrevious;
22067     LookupResult::Filter Filter = Lookup.makeFilter();
22068     while (Filter.hasNext()) {
22069       auto *PrevDecl = cast<OMPDeclareMapperDecl>(Filter.next());
22070       if (InCompoundScope) {
22071         auto I = UsedAsPrevious.find(PrevDecl);
22072         if (I == UsedAsPrevious.end())
22073           UsedAsPrevious[PrevDecl] = false;
22074         if (OMPDeclareMapperDecl *D = PrevDecl->getPrevDeclInScope())
22075           UsedAsPrevious[D] = true;
22076       }
22077       PreviousRedeclTypes[PrevDecl->getType().getCanonicalType()] =
22078           PrevDecl->getLocation();
22079     }
22080     Filter.done();
22081     if (InCompoundScope) {
22082       for (const auto &PrevData : UsedAsPrevious) {
22083         if (!PrevData.second) {
22084           PrevDMD = PrevData.first;
22085           break;
22086         }
22087       }
22088     }
22089   } else if (PrevDeclInScope) {
22090     auto *PrevDMDInScope = PrevDMD =
22091         cast<OMPDeclareMapperDecl>(PrevDeclInScope);
22092     do {
22093       PreviousRedeclTypes[PrevDMDInScope->getType().getCanonicalType()] =
22094           PrevDMDInScope->getLocation();
22095       PrevDMDInScope = PrevDMDInScope->getPrevDeclInScope();
22096     } while (PrevDMDInScope != nullptr);
22097   }
22098   const auto I = PreviousRedeclTypes.find(MapperType.getCanonicalType());
22099   bool Invalid = false;
22100   if (I != PreviousRedeclTypes.end()) {
22101     Diag(StartLoc, diag::err_omp_declare_mapper_redefinition)
22102         << MapperType << Name;
22103     Diag(I->second, diag::note_previous_definition);
22104     Invalid = true;
22105   }
22106   // Build expressions for implicit maps of data members with 'default'
22107   // mappers.
22108   SmallVector<OMPClause *, 4> ClausesWithImplicit(Clauses.begin(),
22109                                                   Clauses.end());
22110   if (LangOpts.OpenMP >= 50)
22111     processImplicitMapsWithDefaultMappers(*this, DSAStack, ClausesWithImplicit);
22112   auto *DMD =
22113       OMPDeclareMapperDecl::Create(Context, DC, StartLoc, Name, MapperType, VN,
22114                                    ClausesWithImplicit, PrevDMD);
22115   if (S)
22116     PushOnScopeChains(DMD, S);
22117   else
22118     DC->addDecl(DMD);
22119   DMD->setAccess(AS);
22120   if (Invalid)
22121     DMD->setInvalidDecl();
22122 
22123   auto *VD = cast<DeclRefExpr>(MapperVarRef)->getDecl();
22124   VD->setDeclContext(DMD);
22125   VD->setLexicalDeclContext(DMD);
22126   DMD->addDecl(VD);
22127   DMD->setMapperVarRef(MapperVarRef);
22128 
22129   return DeclGroupPtrTy::make(DeclGroupRef(DMD));
22130 }
22131 
22132 ExprResult
22133 Sema::ActOnOpenMPDeclareMapperDirectiveVarDecl(Scope *S, QualType MapperType,
22134                                                SourceLocation StartLoc,
22135                                                DeclarationName VN) {
22136   TypeSourceInfo *TInfo =
22137       Context.getTrivialTypeSourceInfo(MapperType, StartLoc);
22138   auto *VD = VarDecl::Create(Context, Context.getTranslationUnitDecl(),
22139                              StartLoc, StartLoc, VN.getAsIdentifierInfo(),
22140                              MapperType, TInfo, SC_None);
22141   if (S)
22142     PushOnScopeChains(VD, S, /*AddToContext=*/false);
22143   Expr *E = buildDeclRefExpr(*this, VD, MapperType, StartLoc);
22144   DSAStack->addDeclareMapperVarRef(E);
22145   return E;
22146 }
22147 
22148 bool Sema::isOpenMPDeclareMapperVarDeclAllowed(const VarDecl *VD) const {
22149   assert(LangOpts.OpenMP && "Expected OpenMP mode.");
22150   const Expr *Ref = DSAStack->getDeclareMapperVarRef();
22151   if (const auto *DRE = cast_or_null<DeclRefExpr>(Ref)) {
22152     if (VD->getCanonicalDecl() == DRE->getDecl()->getCanonicalDecl())
22153       return true;
22154     if (VD->isUsableInConstantExpressions(Context))
22155       return true;
22156     return false;
22157   }
22158   return true;
22159 }
22160 
22161 const ValueDecl *Sema::getOpenMPDeclareMapperVarName() const {
22162   assert(LangOpts.OpenMP && "Expected OpenMP mode.");
22163   return cast<DeclRefExpr>(DSAStack->getDeclareMapperVarRef())->getDecl();
22164 }
22165 
22166 OMPClause *Sema::ActOnOpenMPNumTeamsClause(Expr *NumTeams,
22167                                            SourceLocation StartLoc,
22168                                            SourceLocation LParenLoc,
22169                                            SourceLocation EndLoc) {
22170   Expr *ValExpr = NumTeams;
22171   Stmt *HelperValStmt = nullptr;
22172 
22173   // OpenMP [teams Constrcut, Restrictions]
22174   // The num_teams expression must evaluate to a positive integer value.
22175   if (!isNonNegativeIntegerValue(ValExpr, *this, OMPC_num_teams,
22176                                  /*StrictlyPositive=*/true))
22177     return nullptr;
22178 
22179   OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
22180   OpenMPDirectiveKind CaptureRegion =
22181       getOpenMPCaptureRegionForClause(DKind, OMPC_num_teams, LangOpts.OpenMP);
22182   if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
22183     ValExpr = MakeFullExpr(ValExpr).get();
22184     llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
22185     ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
22186     HelperValStmt = buildPreInits(Context, Captures);
22187   }
22188 
22189   return new (Context) OMPNumTeamsClause(ValExpr, HelperValStmt, CaptureRegion,
22190                                          StartLoc, LParenLoc, EndLoc);
22191 }
22192 
22193 OMPClause *Sema::ActOnOpenMPThreadLimitClause(Expr *ThreadLimit,
22194                                               SourceLocation StartLoc,
22195                                               SourceLocation LParenLoc,
22196                                               SourceLocation EndLoc) {
22197   Expr *ValExpr = ThreadLimit;
22198   Stmt *HelperValStmt = nullptr;
22199 
22200   // OpenMP [teams Constrcut, Restrictions]
22201   // The thread_limit expression must evaluate to a positive integer value.
22202   if (!isNonNegativeIntegerValue(ValExpr, *this, OMPC_thread_limit,
22203                                  /*StrictlyPositive=*/true))
22204     return nullptr;
22205 
22206   OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
22207   OpenMPDirectiveKind CaptureRegion = getOpenMPCaptureRegionForClause(
22208       DKind, OMPC_thread_limit, LangOpts.OpenMP);
22209   if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
22210     ValExpr = MakeFullExpr(ValExpr).get();
22211     llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
22212     ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
22213     HelperValStmt = buildPreInits(Context, Captures);
22214   }
22215 
22216   return new (Context) OMPThreadLimitClause(
22217       ValExpr, HelperValStmt, CaptureRegion, StartLoc, LParenLoc, EndLoc);
22218 }
22219 
22220 OMPClause *Sema::ActOnOpenMPPriorityClause(Expr *Priority,
22221                                            SourceLocation StartLoc,
22222                                            SourceLocation LParenLoc,
22223                                            SourceLocation EndLoc) {
22224   Expr *ValExpr = Priority;
22225   Stmt *HelperValStmt = nullptr;
22226   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
22227 
22228   // OpenMP [2.9.1, task Constrcut]
22229   // The priority-value is a non-negative numerical scalar expression.
22230   if (!isNonNegativeIntegerValue(
22231           ValExpr, *this, OMPC_priority,
22232           /*StrictlyPositive=*/false, /*BuildCapture=*/true,
22233           DSAStack->getCurrentDirective(), &CaptureRegion, &HelperValStmt))
22234     return nullptr;
22235 
22236   return new (Context) OMPPriorityClause(ValExpr, HelperValStmt, CaptureRegion,
22237                                          StartLoc, LParenLoc, EndLoc);
22238 }
22239 
22240 OMPClause *Sema::ActOnOpenMPGrainsizeClause(Expr *Grainsize,
22241                                             SourceLocation StartLoc,
22242                                             SourceLocation LParenLoc,
22243                                             SourceLocation EndLoc) {
22244   Expr *ValExpr = Grainsize;
22245   Stmt *HelperValStmt = nullptr;
22246   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
22247 
22248   // OpenMP [2.9.2, taskloop Constrcut]
22249   // The parameter of the grainsize clause must be a positive integer
22250   // expression.
22251   if (!isNonNegativeIntegerValue(
22252           ValExpr, *this, OMPC_grainsize,
22253           /*StrictlyPositive=*/true, /*BuildCapture=*/true,
22254           DSAStack->getCurrentDirective(), &CaptureRegion, &HelperValStmt))
22255     return nullptr;
22256 
22257   return new (Context) OMPGrainsizeClause(ValExpr, HelperValStmt, CaptureRegion,
22258                                           StartLoc, LParenLoc, EndLoc);
22259 }
22260 
22261 OMPClause *Sema::ActOnOpenMPNumTasksClause(Expr *NumTasks,
22262                                            SourceLocation StartLoc,
22263                                            SourceLocation LParenLoc,
22264                                            SourceLocation EndLoc) {
22265   Expr *ValExpr = NumTasks;
22266   Stmt *HelperValStmt = nullptr;
22267   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
22268 
22269   // OpenMP [2.9.2, taskloop Constrcut]
22270   // The parameter of the num_tasks clause must be a positive integer
22271   // expression.
22272   if (!isNonNegativeIntegerValue(
22273           ValExpr, *this, OMPC_num_tasks,
22274           /*StrictlyPositive=*/true, /*BuildCapture=*/true,
22275           DSAStack->getCurrentDirective(), &CaptureRegion, &HelperValStmt))
22276     return nullptr;
22277 
22278   return new (Context) OMPNumTasksClause(ValExpr, HelperValStmt, CaptureRegion,
22279                                          StartLoc, LParenLoc, EndLoc);
22280 }
22281 
22282 OMPClause *Sema::ActOnOpenMPHintClause(Expr *Hint, SourceLocation StartLoc,
22283                                        SourceLocation LParenLoc,
22284                                        SourceLocation EndLoc) {
22285   // OpenMP [2.13.2, critical construct, Description]
22286   // ... where hint-expression is an integer constant expression that evaluates
22287   // to a valid lock hint.
22288   ExprResult HintExpr =
22289       VerifyPositiveIntegerConstantInClause(Hint, OMPC_hint, false);
22290   if (HintExpr.isInvalid())
22291     return nullptr;
22292   return new (Context)
22293       OMPHintClause(HintExpr.get(), StartLoc, LParenLoc, EndLoc);
22294 }
22295 
22296 /// Tries to find omp_event_handle_t type.
22297 static bool findOMPEventHandleT(Sema &S, SourceLocation Loc,
22298                                 DSAStackTy *Stack) {
22299   QualType OMPEventHandleT = Stack->getOMPEventHandleT();
22300   if (!OMPEventHandleT.isNull())
22301     return true;
22302   IdentifierInfo *II = &S.PP.getIdentifierTable().get("omp_event_handle_t");
22303   ParsedType PT = S.getTypeName(*II, Loc, S.getCurScope());
22304   if (!PT.getAsOpaquePtr() || PT.get().isNull()) {
22305     S.Diag(Loc, diag::err_omp_implied_type_not_found) << "omp_event_handle_t";
22306     return false;
22307   }
22308   Stack->setOMPEventHandleT(PT.get());
22309   return true;
22310 }
22311 
22312 OMPClause *Sema::ActOnOpenMPDetachClause(Expr *Evt, SourceLocation StartLoc,
22313                                          SourceLocation LParenLoc,
22314                                          SourceLocation EndLoc) {
22315   if (!Evt->isValueDependent() && !Evt->isTypeDependent() &&
22316       !Evt->isInstantiationDependent() &&
22317       !Evt->containsUnexpandedParameterPack()) {
22318     if (!findOMPEventHandleT(*this, Evt->getExprLoc(), DSAStack))
22319       return nullptr;
22320     // OpenMP 5.0, 2.10.1 task Construct.
22321     // event-handle is a variable of the omp_event_handle_t type.
22322     auto *Ref = dyn_cast<DeclRefExpr>(Evt->IgnoreParenImpCasts());
22323     if (!Ref) {
22324       Diag(Evt->getExprLoc(), diag::err_omp_var_expected)
22325           << "omp_event_handle_t" << 0 << Evt->getSourceRange();
22326       return nullptr;
22327     }
22328     auto *VD = dyn_cast_or_null<VarDecl>(Ref->getDecl());
22329     if (!VD) {
22330       Diag(Evt->getExprLoc(), diag::err_omp_var_expected)
22331           << "omp_event_handle_t" << 0 << Evt->getSourceRange();
22332       return nullptr;
22333     }
22334     if (!Context.hasSameUnqualifiedType(DSAStack->getOMPEventHandleT(),
22335                                         VD->getType()) ||
22336         VD->getType().isConstant(Context)) {
22337       Diag(Evt->getExprLoc(), diag::err_omp_var_expected)
22338           << "omp_event_handle_t" << 1 << VD->getType()
22339           << Evt->getSourceRange();
22340       return nullptr;
22341     }
22342     // OpenMP 5.0, 2.10.1 task Construct
22343     // [detach clause]... The event-handle will be considered as if it was
22344     // specified on a firstprivate clause.
22345     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(VD, /*FromParent=*/false);
22346     if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_firstprivate &&
22347         DVar.RefExpr) {
22348       Diag(Evt->getExprLoc(), diag::err_omp_wrong_dsa)
22349           << getOpenMPClauseName(DVar.CKind)
22350           << getOpenMPClauseName(OMPC_firstprivate);
22351       reportOriginalDsa(*this, DSAStack, VD, DVar);
22352       return nullptr;
22353     }
22354   }
22355 
22356   return new (Context) OMPDetachClause(Evt, StartLoc, LParenLoc, EndLoc);
22357 }
22358 
22359 OMPClause *Sema::ActOnOpenMPDistScheduleClause(
22360     OpenMPDistScheduleClauseKind Kind, Expr *ChunkSize, SourceLocation StartLoc,
22361     SourceLocation LParenLoc, SourceLocation KindLoc, SourceLocation CommaLoc,
22362     SourceLocation EndLoc) {
22363   if (Kind == OMPC_DIST_SCHEDULE_unknown) {
22364     std::string Values;
22365     Values += "'";
22366     Values += getOpenMPSimpleClauseTypeName(OMPC_dist_schedule, 0);
22367     Values += "'";
22368     Diag(KindLoc, diag::err_omp_unexpected_clause_value)
22369         << Values << getOpenMPClauseName(OMPC_dist_schedule);
22370     return nullptr;
22371   }
22372   Expr *ValExpr = ChunkSize;
22373   Stmt *HelperValStmt = nullptr;
22374   if (ChunkSize) {
22375     if (!ChunkSize->isValueDependent() && !ChunkSize->isTypeDependent() &&
22376         !ChunkSize->isInstantiationDependent() &&
22377         !ChunkSize->containsUnexpandedParameterPack()) {
22378       SourceLocation ChunkSizeLoc = ChunkSize->getBeginLoc();
22379       ExprResult Val =
22380           PerformOpenMPImplicitIntegerConversion(ChunkSizeLoc, ChunkSize);
22381       if (Val.isInvalid())
22382         return nullptr;
22383 
22384       ValExpr = Val.get();
22385 
22386       // OpenMP [2.7.1, Restrictions]
22387       //  chunk_size must be a loop invariant integer expression with a positive
22388       //  value.
22389       if (Optional<llvm::APSInt> Result =
22390               ValExpr->getIntegerConstantExpr(Context)) {
22391         if (Result->isSigned() && !Result->isStrictlyPositive()) {
22392           Diag(ChunkSizeLoc, diag::err_omp_negative_expression_in_clause)
22393               << "dist_schedule" << ChunkSize->getSourceRange();
22394           return nullptr;
22395         }
22396       } else if (getOpenMPCaptureRegionForClause(
22397                      DSAStack->getCurrentDirective(), OMPC_dist_schedule,
22398                      LangOpts.OpenMP) != OMPD_unknown &&
22399                  !CurContext->isDependentContext()) {
22400         ValExpr = MakeFullExpr(ValExpr).get();
22401         llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
22402         ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
22403         HelperValStmt = buildPreInits(Context, Captures);
22404       }
22405     }
22406   }
22407 
22408   return new (Context)
22409       OMPDistScheduleClause(StartLoc, LParenLoc, KindLoc, CommaLoc, EndLoc,
22410                             Kind, ValExpr, HelperValStmt);
22411 }
22412 
22413 OMPClause *Sema::ActOnOpenMPDefaultmapClause(
22414     OpenMPDefaultmapClauseModifier M, OpenMPDefaultmapClauseKind Kind,
22415     SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation MLoc,
22416     SourceLocation KindLoc, SourceLocation EndLoc) {
22417   if (getLangOpts().OpenMP < 50) {
22418     if (M != OMPC_DEFAULTMAP_MODIFIER_tofrom ||
22419         Kind != OMPC_DEFAULTMAP_scalar) {
22420       std::string Value;
22421       SourceLocation Loc;
22422       Value += "'";
22423       if (M != OMPC_DEFAULTMAP_MODIFIER_tofrom) {
22424         Value += getOpenMPSimpleClauseTypeName(OMPC_defaultmap,
22425                                                OMPC_DEFAULTMAP_MODIFIER_tofrom);
22426         Loc = MLoc;
22427       } else {
22428         Value += getOpenMPSimpleClauseTypeName(OMPC_defaultmap,
22429                                                OMPC_DEFAULTMAP_scalar);
22430         Loc = KindLoc;
22431       }
22432       Value += "'";
22433       Diag(Loc, diag::err_omp_unexpected_clause_value)
22434           << Value << getOpenMPClauseName(OMPC_defaultmap);
22435       return nullptr;
22436     }
22437   } else {
22438     bool isDefaultmapModifier = (M != OMPC_DEFAULTMAP_MODIFIER_unknown);
22439     bool isDefaultmapKind = (Kind != OMPC_DEFAULTMAP_unknown) ||
22440                             (LangOpts.OpenMP >= 50 && KindLoc.isInvalid());
22441     if (!isDefaultmapKind || !isDefaultmapModifier) {
22442       StringRef KindValue = "'scalar', 'aggregate', 'pointer'";
22443       if (LangOpts.OpenMP == 50) {
22444         StringRef ModifierValue = "'alloc', 'from', 'to', 'tofrom', "
22445                                   "'firstprivate', 'none', 'default'";
22446         if (!isDefaultmapKind && isDefaultmapModifier) {
22447           Diag(KindLoc, diag::err_omp_unexpected_clause_value)
22448               << KindValue << getOpenMPClauseName(OMPC_defaultmap);
22449         } else if (isDefaultmapKind && !isDefaultmapModifier) {
22450           Diag(MLoc, diag::err_omp_unexpected_clause_value)
22451               << ModifierValue << getOpenMPClauseName(OMPC_defaultmap);
22452         } else {
22453           Diag(MLoc, diag::err_omp_unexpected_clause_value)
22454               << ModifierValue << getOpenMPClauseName(OMPC_defaultmap);
22455           Diag(KindLoc, diag::err_omp_unexpected_clause_value)
22456               << KindValue << getOpenMPClauseName(OMPC_defaultmap);
22457         }
22458       } else {
22459         StringRef ModifierValue =
22460             "'alloc', 'from', 'to', 'tofrom', "
22461             "'firstprivate', 'none', 'default', 'present'";
22462         if (!isDefaultmapKind && isDefaultmapModifier) {
22463           Diag(KindLoc, diag::err_omp_unexpected_clause_value)
22464               << KindValue << getOpenMPClauseName(OMPC_defaultmap);
22465         } else if (isDefaultmapKind && !isDefaultmapModifier) {
22466           Diag(MLoc, diag::err_omp_unexpected_clause_value)
22467               << ModifierValue << getOpenMPClauseName(OMPC_defaultmap);
22468         } else {
22469           Diag(MLoc, diag::err_omp_unexpected_clause_value)
22470               << ModifierValue << getOpenMPClauseName(OMPC_defaultmap);
22471           Diag(KindLoc, diag::err_omp_unexpected_clause_value)
22472               << KindValue << getOpenMPClauseName(OMPC_defaultmap);
22473         }
22474       }
22475       return nullptr;
22476     }
22477 
22478     // OpenMP [5.0, 2.12.5, Restrictions, p. 174]
22479     //  At most one defaultmap clause for each category can appear on the
22480     //  directive.
22481     if (DSAStack->checkDefaultmapCategory(Kind)) {
22482       Diag(StartLoc, diag::err_omp_one_defaultmap_each_category);
22483       return nullptr;
22484     }
22485   }
22486   if (Kind == OMPC_DEFAULTMAP_unknown) {
22487     // Variable category is not specified - mark all categories.
22488     DSAStack->setDefaultDMAAttr(M, OMPC_DEFAULTMAP_aggregate, StartLoc);
22489     DSAStack->setDefaultDMAAttr(M, OMPC_DEFAULTMAP_scalar, StartLoc);
22490     DSAStack->setDefaultDMAAttr(M, OMPC_DEFAULTMAP_pointer, StartLoc);
22491   } else {
22492     DSAStack->setDefaultDMAAttr(M, Kind, StartLoc);
22493   }
22494 
22495   return new (Context)
22496       OMPDefaultmapClause(StartLoc, LParenLoc, MLoc, KindLoc, EndLoc, Kind, M);
22497 }
22498 
22499 bool Sema::ActOnStartOpenMPDeclareTargetContext(
22500     DeclareTargetContextInfo &DTCI) {
22501   DeclContext *CurLexicalContext = getCurLexicalContext();
22502   if (!CurLexicalContext->isFileContext() &&
22503       !CurLexicalContext->isExternCContext() &&
22504       !CurLexicalContext->isExternCXXContext() &&
22505       !isa<CXXRecordDecl>(CurLexicalContext) &&
22506       !isa<ClassTemplateDecl>(CurLexicalContext) &&
22507       !isa<ClassTemplatePartialSpecializationDecl>(CurLexicalContext) &&
22508       !isa<ClassTemplateSpecializationDecl>(CurLexicalContext)) {
22509     Diag(DTCI.Loc, diag::err_omp_region_not_file_context);
22510     return false;
22511   }
22512   DeclareTargetNesting.push_back(DTCI);
22513   return true;
22514 }
22515 
22516 const Sema::DeclareTargetContextInfo
22517 Sema::ActOnOpenMPEndDeclareTargetDirective() {
22518   assert(!DeclareTargetNesting.empty() &&
22519          "check isInOpenMPDeclareTargetContext() first!");
22520   return DeclareTargetNesting.pop_back_val();
22521 }
22522 
22523 void Sema::ActOnFinishedOpenMPDeclareTargetContext(
22524     DeclareTargetContextInfo &DTCI) {
22525   for (auto &It : DTCI.ExplicitlyMapped)
22526     ActOnOpenMPDeclareTargetName(It.first, It.second.Loc, It.second.MT, DTCI);
22527 }
22528 
22529 void Sema::DiagnoseUnterminatedOpenMPDeclareTarget() {
22530   if (DeclareTargetNesting.empty())
22531     return;
22532   DeclareTargetContextInfo &DTCI = DeclareTargetNesting.back();
22533   Diag(DTCI.Loc, diag::warn_omp_unterminated_declare_target)
22534       << getOpenMPDirectiveName(DTCI.Kind);
22535 }
22536 
22537 NamedDecl *Sema::lookupOpenMPDeclareTargetName(Scope *CurScope,
22538                                                CXXScopeSpec &ScopeSpec,
22539                                                const DeclarationNameInfo &Id) {
22540   LookupResult Lookup(*this, Id, LookupOrdinaryName);
22541   LookupParsedName(Lookup, CurScope, &ScopeSpec, true);
22542 
22543   if (Lookup.isAmbiguous())
22544     return nullptr;
22545   Lookup.suppressDiagnostics();
22546 
22547   if (!Lookup.isSingleResult()) {
22548     VarOrFuncDeclFilterCCC CCC(*this);
22549     if (TypoCorrection Corrected =
22550             CorrectTypo(Id, LookupOrdinaryName, CurScope, nullptr, CCC,
22551                         CTK_ErrorRecovery)) {
22552       diagnoseTypo(Corrected, PDiag(diag::err_undeclared_var_use_suggest)
22553                                   << Id.getName());
22554       checkDeclIsAllowedInOpenMPTarget(nullptr, Corrected.getCorrectionDecl());
22555       return nullptr;
22556     }
22557 
22558     Diag(Id.getLoc(), diag::err_undeclared_var_use) << Id.getName();
22559     return nullptr;
22560   }
22561 
22562   NamedDecl *ND = Lookup.getAsSingle<NamedDecl>();
22563   if (!isa<VarDecl>(ND) && !isa<FunctionDecl>(ND) &&
22564       !isa<FunctionTemplateDecl>(ND)) {
22565     Diag(Id.getLoc(), diag::err_omp_invalid_target_decl) << Id.getName();
22566     return nullptr;
22567   }
22568   return ND;
22569 }
22570 
22571 void Sema::ActOnOpenMPDeclareTargetName(NamedDecl *ND, SourceLocation Loc,
22572                                         OMPDeclareTargetDeclAttr::MapTypeTy MT,
22573                                         DeclareTargetContextInfo &DTCI) {
22574   assert((isa<VarDecl>(ND) || isa<FunctionDecl>(ND) ||
22575           isa<FunctionTemplateDecl>(ND)) &&
22576          "Expected variable, function or function template.");
22577 
22578   // Diagnose marking after use as it may lead to incorrect diagnosis and
22579   // codegen.
22580   if (LangOpts.OpenMP >= 50 &&
22581       (ND->isUsed(/*CheckUsedAttr=*/false) || ND->isReferenced()))
22582     Diag(Loc, diag::warn_omp_declare_target_after_first_use);
22583 
22584   // Explicit declare target lists have precedence.
22585   const unsigned Level = -1;
22586 
22587   auto *VD = cast<ValueDecl>(ND);
22588   llvm::Optional<OMPDeclareTargetDeclAttr *> ActiveAttr =
22589       OMPDeclareTargetDeclAttr::getActiveAttr(VD);
22590   if (ActiveAttr && ActiveAttr.getValue()->getDevType() != DTCI.DT &&
22591       ActiveAttr.getValue()->getLevel() == Level) {
22592     Diag(Loc, diag::err_omp_device_type_mismatch)
22593         << OMPDeclareTargetDeclAttr::ConvertDevTypeTyToStr(DTCI.DT)
22594         << OMPDeclareTargetDeclAttr::ConvertDevTypeTyToStr(
22595                ActiveAttr.getValue()->getDevType());
22596     return;
22597   }
22598   if (ActiveAttr && ActiveAttr.getValue()->getMapType() != MT &&
22599       ActiveAttr.getValue()->getLevel() == Level) {
22600     Diag(Loc, diag::err_omp_declare_target_to_and_link) << ND;
22601     return;
22602   }
22603 
22604   if (ActiveAttr && ActiveAttr.getValue()->getLevel() == Level)
22605     return;
22606 
22607   Expr *IndirectE = nullptr;
22608   bool IsIndirect = false;
22609   if (DTCI.Indirect) {
22610     IndirectE = DTCI.Indirect.getValue();
22611     if (!IndirectE)
22612       IsIndirect = true;
22613   }
22614   auto *A = OMPDeclareTargetDeclAttr::CreateImplicit(
22615       Context, MT, DTCI.DT, IndirectE, IsIndirect, Level,
22616       SourceRange(Loc, Loc));
22617   ND->addAttr(A);
22618   if (ASTMutationListener *ML = Context.getASTMutationListener())
22619     ML->DeclarationMarkedOpenMPDeclareTarget(ND, A);
22620   checkDeclIsAllowedInOpenMPTarget(nullptr, ND, Loc);
22621 }
22622 
22623 static void checkDeclInTargetContext(SourceLocation SL, SourceRange SR,
22624                                      Sema &SemaRef, Decl *D) {
22625   if (!D || !isa<VarDecl>(D))
22626     return;
22627   auto *VD = cast<VarDecl>(D);
22628   Optional<OMPDeclareTargetDeclAttr::MapTypeTy> MapTy =
22629       OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(VD);
22630   if (SemaRef.LangOpts.OpenMP >= 50 &&
22631       (SemaRef.getCurLambda(/*IgnoreNonLambdaCapturingScope=*/true) ||
22632        SemaRef.getCurBlock() || SemaRef.getCurCapturedRegion()) &&
22633       VD->hasGlobalStorage()) {
22634     if (!MapTy || *MapTy != OMPDeclareTargetDeclAttr::MT_To) {
22635       // OpenMP 5.0, 2.12.7 declare target Directive, Restrictions
22636       // If a lambda declaration and definition appears between a
22637       // declare target directive and the matching end declare target
22638       // directive, all variables that are captured by the lambda
22639       // expression must also appear in a to clause.
22640       SemaRef.Diag(VD->getLocation(),
22641                    diag::err_omp_lambda_capture_in_declare_target_not_to);
22642       SemaRef.Diag(SL, diag::note_var_explicitly_captured_here)
22643           << VD << 0 << SR;
22644       return;
22645     }
22646   }
22647   if (MapTy)
22648     return;
22649   SemaRef.Diag(VD->getLocation(), diag::warn_omp_not_in_target_context);
22650   SemaRef.Diag(SL, diag::note_used_here) << SR;
22651 }
22652 
22653 static bool checkValueDeclInTarget(SourceLocation SL, SourceRange SR,
22654                                    Sema &SemaRef, DSAStackTy *Stack,
22655                                    ValueDecl *VD) {
22656   return OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(VD) ||
22657          checkTypeMappable(SL, SR, SemaRef, Stack, VD->getType(),
22658                            /*FullCheck=*/false);
22659 }
22660 
22661 void Sema::checkDeclIsAllowedInOpenMPTarget(Expr *E, Decl *D,
22662                                             SourceLocation IdLoc) {
22663   if (!D || D->isInvalidDecl())
22664     return;
22665   SourceRange SR = E ? E->getSourceRange() : D->getSourceRange();
22666   SourceLocation SL = E ? E->getBeginLoc() : D->getLocation();
22667   if (auto *VD = dyn_cast<VarDecl>(D)) {
22668     // Only global variables can be marked as declare target.
22669     if (!VD->isFileVarDecl() && !VD->isStaticLocal() &&
22670         !VD->isStaticDataMember())
22671       return;
22672     // 2.10.6: threadprivate variable cannot appear in a declare target
22673     // directive.
22674     if (DSAStack->isThreadPrivate(VD)) {
22675       Diag(SL, diag::err_omp_threadprivate_in_target);
22676       reportOriginalDsa(*this, DSAStack, VD, DSAStack->getTopDSA(VD, false));
22677       return;
22678     }
22679   }
22680   if (const auto *FTD = dyn_cast<FunctionTemplateDecl>(D))
22681     D = FTD->getTemplatedDecl();
22682   if (auto *FD = dyn_cast<FunctionDecl>(D)) {
22683     llvm::Optional<OMPDeclareTargetDeclAttr::MapTypeTy> Res =
22684         OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(FD);
22685     if (IdLoc.isValid() && Res && *Res == OMPDeclareTargetDeclAttr::MT_Link) {
22686       Diag(IdLoc, diag::err_omp_function_in_link_clause);
22687       Diag(FD->getLocation(), diag::note_defined_here) << FD;
22688       return;
22689     }
22690   }
22691   if (auto *VD = dyn_cast<ValueDecl>(D)) {
22692     // Problem if any with var declared with incomplete type will be reported
22693     // as normal, so no need to check it here.
22694     if ((E || !VD->getType()->isIncompleteType()) &&
22695         !checkValueDeclInTarget(SL, SR, *this, DSAStack, VD))
22696       return;
22697     if (!E && isInOpenMPDeclareTargetContext()) {
22698       // Checking declaration inside declare target region.
22699       if (isa<VarDecl>(D) || isa<FunctionDecl>(D) ||
22700           isa<FunctionTemplateDecl>(D)) {
22701         llvm::Optional<OMPDeclareTargetDeclAttr *> ActiveAttr =
22702             OMPDeclareTargetDeclAttr::getActiveAttr(VD);
22703         unsigned Level = DeclareTargetNesting.size();
22704         if (ActiveAttr && ActiveAttr.getValue()->getLevel() >= Level)
22705           return;
22706         DeclareTargetContextInfo &DTCI = DeclareTargetNesting.back();
22707         Expr *IndirectE = nullptr;
22708         bool IsIndirect = false;
22709         if (DTCI.Indirect) {
22710           IndirectE = DTCI.Indirect.getValue();
22711           if (!IndirectE)
22712             IsIndirect = true;
22713         }
22714         auto *A = OMPDeclareTargetDeclAttr::CreateImplicit(
22715             Context, OMPDeclareTargetDeclAttr::MT_To, DTCI.DT, IndirectE,
22716             IsIndirect, Level, SourceRange(DTCI.Loc, DTCI.Loc));
22717         D->addAttr(A);
22718         if (ASTMutationListener *ML = Context.getASTMutationListener())
22719           ML->DeclarationMarkedOpenMPDeclareTarget(D, A);
22720       }
22721       return;
22722     }
22723   }
22724   if (!E)
22725     return;
22726   checkDeclInTargetContext(E->getExprLoc(), E->getSourceRange(), *this, D);
22727 }
22728 
22729 OMPClause *Sema::ActOnOpenMPToClause(
22730     ArrayRef<OpenMPMotionModifierKind> MotionModifiers,
22731     ArrayRef<SourceLocation> MotionModifiersLoc,
22732     CXXScopeSpec &MapperIdScopeSpec, DeclarationNameInfo &MapperId,
22733     SourceLocation ColonLoc, ArrayRef<Expr *> VarList,
22734     const OMPVarListLocTy &Locs, ArrayRef<Expr *> UnresolvedMappers) {
22735   OpenMPMotionModifierKind Modifiers[] = {OMPC_MOTION_MODIFIER_unknown,
22736                                           OMPC_MOTION_MODIFIER_unknown};
22737   SourceLocation ModifiersLoc[NumberOfOMPMotionModifiers];
22738 
22739   // Process motion-modifiers, flag errors for duplicate modifiers.
22740   unsigned Count = 0;
22741   for (unsigned I = 0, E = MotionModifiers.size(); I < E; ++I) {
22742     if (MotionModifiers[I] != OMPC_MOTION_MODIFIER_unknown &&
22743         llvm::is_contained(Modifiers, MotionModifiers[I])) {
22744       Diag(MotionModifiersLoc[I], diag::err_omp_duplicate_motion_modifier);
22745       continue;
22746     }
22747     assert(Count < NumberOfOMPMotionModifiers &&
22748            "Modifiers exceed the allowed number of motion modifiers");
22749     Modifiers[Count] = MotionModifiers[I];
22750     ModifiersLoc[Count] = MotionModifiersLoc[I];
22751     ++Count;
22752   }
22753 
22754   MappableVarListInfo MVLI(VarList);
22755   checkMappableExpressionList(*this, DSAStack, OMPC_to, MVLI, Locs.StartLoc,
22756                               MapperIdScopeSpec, MapperId, UnresolvedMappers);
22757   if (MVLI.ProcessedVarList.empty())
22758     return nullptr;
22759 
22760   return OMPToClause::Create(
22761       Context, Locs, MVLI.ProcessedVarList, MVLI.VarBaseDeclarations,
22762       MVLI.VarComponents, MVLI.UDMapperList, Modifiers, ModifiersLoc,
22763       MapperIdScopeSpec.getWithLocInContext(Context), MapperId);
22764 }
22765 
22766 OMPClause *Sema::ActOnOpenMPFromClause(
22767     ArrayRef<OpenMPMotionModifierKind> MotionModifiers,
22768     ArrayRef<SourceLocation> MotionModifiersLoc,
22769     CXXScopeSpec &MapperIdScopeSpec, DeclarationNameInfo &MapperId,
22770     SourceLocation ColonLoc, ArrayRef<Expr *> VarList,
22771     const OMPVarListLocTy &Locs, ArrayRef<Expr *> UnresolvedMappers) {
22772   OpenMPMotionModifierKind Modifiers[] = {OMPC_MOTION_MODIFIER_unknown,
22773                                           OMPC_MOTION_MODIFIER_unknown};
22774   SourceLocation ModifiersLoc[NumberOfOMPMotionModifiers];
22775 
22776   // Process motion-modifiers, flag errors for duplicate modifiers.
22777   unsigned Count = 0;
22778   for (unsigned I = 0, E = MotionModifiers.size(); I < E; ++I) {
22779     if (MotionModifiers[I] != OMPC_MOTION_MODIFIER_unknown &&
22780         llvm::is_contained(Modifiers, MotionModifiers[I])) {
22781       Diag(MotionModifiersLoc[I], diag::err_omp_duplicate_motion_modifier);
22782       continue;
22783     }
22784     assert(Count < NumberOfOMPMotionModifiers &&
22785            "Modifiers exceed the allowed number of motion modifiers");
22786     Modifiers[Count] = MotionModifiers[I];
22787     ModifiersLoc[Count] = MotionModifiersLoc[I];
22788     ++Count;
22789   }
22790 
22791   MappableVarListInfo MVLI(VarList);
22792   checkMappableExpressionList(*this, DSAStack, OMPC_from, MVLI, Locs.StartLoc,
22793                               MapperIdScopeSpec, MapperId, UnresolvedMappers);
22794   if (MVLI.ProcessedVarList.empty())
22795     return nullptr;
22796 
22797   return OMPFromClause::Create(
22798       Context, Locs, MVLI.ProcessedVarList, MVLI.VarBaseDeclarations,
22799       MVLI.VarComponents, MVLI.UDMapperList, Modifiers, ModifiersLoc,
22800       MapperIdScopeSpec.getWithLocInContext(Context), MapperId);
22801 }
22802 
22803 OMPClause *Sema::ActOnOpenMPUseDevicePtrClause(ArrayRef<Expr *> VarList,
22804                                                const OMPVarListLocTy &Locs) {
22805   MappableVarListInfo MVLI(VarList);
22806   SmallVector<Expr *, 8> PrivateCopies;
22807   SmallVector<Expr *, 8> Inits;
22808 
22809   for (Expr *RefExpr : VarList) {
22810     assert(RefExpr && "NULL expr in OpenMP use_device_ptr clause.");
22811     SourceLocation ELoc;
22812     SourceRange ERange;
22813     Expr *SimpleRefExpr = RefExpr;
22814     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
22815     if (Res.second) {
22816       // It will be analyzed later.
22817       MVLI.ProcessedVarList.push_back(RefExpr);
22818       PrivateCopies.push_back(nullptr);
22819       Inits.push_back(nullptr);
22820     }
22821     ValueDecl *D = Res.first;
22822     if (!D)
22823       continue;
22824 
22825     QualType Type = D->getType();
22826     Type = Type.getNonReferenceType().getUnqualifiedType();
22827 
22828     auto *VD = dyn_cast<VarDecl>(D);
22829 
22830     // Item should be a pointer or reference to pointer.
22831     if (!Type->isPointerType()) {
22832       Diag(ELoc, diag::err_omp_usedeviceptr_not_a_pointer)
22833           << 0 << RefExpr->getSourceRange();
22834       continue;
22835     }
22836 
22837     // Build the private variable and the expression that refers to it.
22838     auto VDPrivate =
22839         buildVarDecl(*this, ELoc, Type, D->getName(),
22840                      D->hasAttrs() ? &D->getAttrs() : nullptr,
22841                      VD ? cast<DeclRefExpr>(SimpleRefExpr) : nullptr);
22842     if (VDPrivate->isInvalidDecl())
22843       continue;
22844 
22845     CurContext->addDecl(VDPrivate);
22846     DeclRefExpr *VDPrivateRefExpr = buildDeclRefExpr(
22847         *this, VDPrivate, RefExpr->getType().getUnqualifiedType(), ELoc);
22848 
22849     // Add temporary variable to initialize the private copy of the pointer.
22850     VarDecl *VDInit =
22851         buildVarDecl(*this, RefExpr->getExprLoc(), Type, ".devptr.temp");
22852     DeclRefExpr *VDInitRefExpr = buildDeclRefExpr(
22853         *this, VDInit, RefExpr->getType(), RefExpr->getExprLoc());
22854     AddInitializerToDecl(VDPrivate,
22855                          DefaultLvalueConversion(VDInitRefExpr).get(),
22856                          /*DirectInit=*/false);
22857 
22858     // If required, build a capture to implement the privatization initialized
22859     // with the current list item value.
22860     DeclRefExpr *Ref = nullptr;
22861     if (!VD)
22862       Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/true);
22863     MVLI.ProcessedVarList.push_back(VD ? RefExpr->IgnoreParens() : Ref);
22864     PrivateCopies.push_back(VDPrivateRefExpr);
22865     Inits.push_back(VDInitRefExpr);
22866 
22867     // We need to add a data sharing attribute for this variable to make sure it
22868     // is correctly captured. A variable that shows up in a use_device_ptr has
22869     // similar properties of a first private variable.
22870     DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_firstprivate, Ref);
22871 
22872     // Create a mappable component for the list item. List items in this clause
22873     // only need a component.
22874     MVLI.VarBaseDeclarations.push_back(D);
22875     MVLI.VarComponents.resize(MVLI.VarComponents.size() + 1);
22876     MVLI.VarComponents.back().emplace_back(SimpleRefExpr, D,
22877                                            /*IsNonContiguous=*/false);
22878   }
22879 
22880   if (MVLI.ProcessedVarList.empty())
22881     return nullptr;
22882 
22883   return OMPUseDevicePtrClause::Create(
22884       Context, Locs, MVLI.ProcessedVarList, PrivateCopies, Inits,
22885       MVLI.VarBaseDeclarations, MVLI.VarComponents);
22886 }
22887 
22888 OMPClause *Sema::ActOnOpenMPUseDeviceAddrClause(ArrayRef<Expr *> VarList,
22889                                                 const OMPVarListLocTy &Locs) {
22890   MappableVarListInfo MVLI(VarList);
22891 
22892   for (Expr *RefExpr : VarList) {
22893     assert(RefExpr && "NULL expr in OpenMP use_device_addr clause.");
22894     SourceLocation ELoc;
22895     SourceRange ERange;
22896     Expr *SimpleRefExpr = RefExpr;
22897     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange,
22898                               /*AllowArraySection=*/true);
22899     if (Res.second) {
22900       // It will be analyzed later.
22901       MVLI.ProcessedVarList.push_back(RefExpr);
22902     }
22903     ValueDecl *D = Res.first;
22904     if (!D)
22905       continue;
22906     auto *VD = dyn_cast<VarDecl>(D);
22907 
22908     // If required, build a capture to implement the privatization initialized
22909     // with the current list item value.
22910     DeclRefExpr *Ref = nullptr;
22911     if (!VD)
22912       Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/true);
22913     MVLI.ProcessedVarList.push_back(VD ? RefExpr->IgnoreParens() : Ref);
22914 
22915     // We need to add a data sharing attribute for this variable to make sure it
22916     // is correctly captured. A variable that shows up in a use_device_addr has
22917     // similar properties of a first private variable.
22918     DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_firstprivate, Ref);
22919 
22920     // Create a mappable component for the list item. List items in this clause
22921     // only need a component.
22922     MVLI.VarBaseDeclarations.push_back(D);
22923     MVLI.VarComponents.emplace_back();
22924     Expr *Component = SimpleRefExpr;
22925     if (VD && (isa<OMPArraySectionExpr>(RefExpr->IgnoreParenImpCasts()) ||
22926                isa<ArraySubscriptExpr>(RefExpr->IgnoreParenImpCasts())))
22927       Component = DefaultFunctionArrayLvalueConversion(SimpleRefExpr).get();
22928     MVLI.VarComponents.back().emplace_back(Component, D,
22929                                            /*IsNonContiguous=*/false);
22930   }
22931 
22932   if (MVLI.ProcessedVarList.empty())
22933     return nullptr;
22934 
22935   return OMPUseDeviceAddrClause::Create(Context, Locs, MVLI.ProcessedVarList,
22936                                         MVLI.VarBaseDeclarations,
22937                                         MVLI.VarComponents);
22938 }
22939 
22940 OMPClause *Sema::ActOnOpenMPIsDevicePtrClause(ArrayRef<Expr *> VarList,
22941                                               const OMPVarListLocTy &Locs) {
22942   MappableVarListInfo MVLI(VarList);
22943   for (Expr *RefExpr : VarList) {
22944     assert(RefExpr && "NULL expr in OpenMP is_device_ptr clause.");
22945     SourceLocation ELoc;
22946     SourceRange ERange;
22947     Expr *SimpleRefExpr = RefExpr;
22948     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
22949     if (Res.second) {
22950       // It will be analyzed later.
22951       MVLI.ProcessedVarList.push_back(RefExpr);
22952     }
22953     ValueDecl *D = Res.first;
22954     if (!D)
22955       continue;
22956 
22957     QualType Type = D->getType();
22958     // item should be a pointer or array or reference to pointer or array
22959     if (!Type.getNonReferenceType()->isPointerType() &&
22960         !Type.getNonReferenceType()->isArrayType()) {
22961       Diag(ELoc, diag::err_omp_argument_type_isdeviceptr)
22962           << 0 << RefExpr->getSourceRange();
22963       continue;
22964     }
22965 
22966     // Check if the declaration in the clause does not show up in any data
22967     // sharing attribute.
22968     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(D, /*FromParent=*/false);
22969     if (isOpenMPPrivate(DVar.CKind)) {
22970       Diag(ELoc, diag::err_omp_variable_in_given_clause_and_dsa)
22971           << getOpenMPClauseName(DVar.CKind)
22972           << getOpenMPClauseName(OMPC_is_device_ptr)
22973           << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
22974       reportOriginalDsa(*this, DSAStack, D, DVar);
22975       continue;
22976     }
22977 
22978     const Expr *ConflictExpr;
22979     if (DSAStack->checkMappableExprComponentListsForDecl(
22980             D, /*CurrentRegionOnly=*/true,
22981             [&ConflictExpr](
22982                 OMPClauseMappableExprCommon::MappableExprComponentListRef R,
22983                 OpenMPClauseKind) -> bool {
22984               ConflictExpr = R.front().getAssociatedExpression();
22985               return true;
22986             })) {
22987       Diag(ELoc, diag::err_omp_map_shared_storage) << RefExpr->getSourceRange();
22988       Diag(ConflictExpr->getExprLoc(), diag::note_used_here)
22989           << ConflictExpr->getSourceRange();
22990       continue;
22991     }
22992 
22993     // Store the components in the stack so that they can be used to check
22994     // against other clauses later on.
22995     OMPClauseMappableExprCommon::MappableComponent MC(
22996         SimpleRefExpr, D, /*IsNonContiguous=*/false);
22997     DSAStack->addMappableExpressionComponents(
22998         D, MC, /*WhereFoundClauseKind=*/OMPC_is_device_ptr);
22999 
23000     // Record the expression we've just processed.
23001     MVLI.ProcessedVarList.push_back(SimpleRefExpr);
23002 
23003     // Create a mappable component for the list item. List items in this clause
23004     // only need a component. We use a null declaration to signal fields in
23005     // 'this'.
23006     assert((isa<DeclRefExpr>(SimpleRefExpr) ||
23007             isa<CXXThisExpr>(cast<MemberExpr>(SimpleRefExpr)->getBase())) &&
23008            "Unexpected device pointer expression!");
23009     MVLI.VarBaseDeclarations.push_back(
23010         isa<DeclRefExpr>(SimpleRefExpr) ? D : nullptr);
23011     MVLI.VarComponents.resize(MVLI.VarComponents.size() + 1);
23012     MVLI.VarComponents.back().push_back(MC);
23013   }
23014 
23015   if (MVLI.ProcessedVarList.empty())
23016     return nullptr;
23017 
23018   return OMPIsDevicePtrClause::Create(Context, Locs, MVLI.ProcessedVarList,
23019                                       MVLI.VarBaseDeclarations,
23020                                       MVLI.VarComponents);
23021 }
23022 
23023 OMPClause *Sema::ActOnOpenMPHasDeviceAddrClause(ArrayRef<Expr *> VarList,
23024                                                 const OMPVarListLocTy &Locs) {
23025   MappableVarListInfo MVLI(VarList);
23026   for (Expr *RefExpr : VarList) {
23027     assert(RefExpr && "NULL expr in OpenMP has_device_addr clause.");
23028     SourceLocation ELoc;
23029     SourceRange ERange;
23030     Expr *SimpleRefExpr = RefExpr;
23031     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange,
23032                               /*AllowArraySection=*/true);
23033     if (Res.second) {
23034       // It will be analyzed later.
23035       MVLI.ProcessedVarList.push_back(RefExpr);
23036     }
23037     ValueDecl *D = Res.first;
23038     if (!D)
23039       continue;
23040 
23041     // Check if the declaration in the clause does not show up in any data
23042     // sharing attribute.
23043     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(D, /*FromParent=*/false);
23044     if (isOpenMPPrivate(DVar.CKind)) {
23045       Diag(ELoc, diag::err_omp_variable_in_given_clause_and_dsa)
23046           << getOpenMPClauseName(DVar.CKind)
23047           << getOpenMPClauseName(OMPC_has_device_addr)
23048           << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
23049       reportOriginalDsa(*this, DSAStack, D, DVar);
23050       continue;
23051     }
23052 
23053     const Expr *ConflictExpr;
23054     if (DSAStack->checkMappableExprComponentListsForDecl(
23055             D, /*CurrentRegionOnly=*/true,
23056             [&ConflictExpr](
23057                 OMPClauseMappableExprCommon::MappableExprComponentListRef R,
23058                 OpenMPClauseKind) -> bool {
23059               ConflictExpr = R.front().getAssociatedExpression();
23060               return true;
23061             })) {
23062       Diag(ELoc, diag::err_omp_map_shared_storage) << RefExpr->getSourceRange();
23063       Diag(ConflictExpr->getExprLoc(), diag::note_used_here)
23064           << ConflictExpr->getSourceRange();
23065       continue;
23066     }
23067 
23068     // Store the components in the stack so that they can be used to check
23069     // against other clauses later on.
23070     OMPClauseMappableExprCommon::MappableComponent MC(
23071         SimpleRefExpr, D, /*IsNonContiguous=*/false);
23072     DSAStack->addMappableExpressionComponents(
23073         D, MC, /*WhereFoundClauseKind=*/OMPC_has_device_addr);
23074 
23075     // Record the expression we've just processed.
23076     auto *VD = dyn_cast<VarDecl>(D);
23077     if (!VD && !CurContext->isDependentContext()) {
23078       DeclRefExpr *Ref =
23079           buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/true);
23080       assert(Ref && "has_device_addr capture failed");
23081       MVLI.ProcessedVarList.push_back(Ref);
23082     } else
23083       MVLI.ProcessedVarList.push_back(RefExpr->IgnoreParens());
23084 
23085     // Create a mappable component for the list item. List items in this clause
23086     // only need a component. We use a null declaration to signal fields in
23087     // 'this'.
23088     assert((isa<DeclRefExpr>(SimpleRefExpr) ||
23089             isa<CXXThisExpr>(cast<MemberExpr>(SimpleRefExpr)->getBase())) &&
23090            "Unexpected device pointer expression!");
23091     MVLI.VarBaseDeclarations.push_back(
23092         isa<DeclRefExpr>(SimpleRefExpr) ? D : nullptr);
23093     MVLI.VarComponents.resize(MVLI.VarComponents.size() + 1);
23094     MVLI.VarComponents.back().push_back(MC);
23095   }
23096 
23097   if (MVLI.ProcessedVarList.empty())
23098     return nullptr;
23099 
23100   return OMPHasDeviceAddrClause::Create(Context, Locs, MVLI.ProcessedVarList,
23101                                         MVLI.VarBaseDeclarations,
23102                                         MVLI.VarComponents);
23103 }
23104 
23105 OMPClause *Sema::ActOnOpenMPAllocateClause(
23106     Expr *Allocator, ArrayRef<Expr *> VarList, SourceLocation StartLoc,
23107     SourceLocation ColonLoc, SourceLocation LParenLoc, SourceLocation EndLoc) {
23108   if (Allocator) {
23109     // OpenMP [2.11.4 allocate Clause, Description]
23110     // allocator is an expression of omp_allocator_handle_t type.
23111     if (!findOMPAllocatorHandleT(*this, Allocator->getExprLoc(), DSAStack))
23112       return nullptr;
23113 
23114     ExprResult AllocatorRes = DefaultLvalueConversion(Allocator);
23115     if (AllocatorRes.isInvalid())
23116       return nullptr;
23117     AllocatorRes = PerformImplicitConversion(AllocatorRes.get(),
23118                                              DSAStack->getOMPAllocatorHandleT(),
23119                                              Sema::AA_Initializing,
23120                                              /*AllowExplicit=*/true);
23121     if (AllocatorRes.isInvalid())
23122       return nullptr;
23123     Allocator = AllocatorRes.get();
23124   } else {
23125     // OpenMP 5.0, 2.11.4 allocate Clause, Restrictions.
23126     // allocate clauses that appear on a target construct or on constructs in a
23127     // target region must specify an allocator expression unless a requires
23128     // directive with the dynamic_allocators clause is present in the same
23129     // compilation unit.
23130     if (LangOpts.OpenMPIsDevice &&
23131         !DSAStack->hasRequiresDeclWithClause<OMPDynamicAllocatorsClause>())
23132       targetDiag(StartLoc, diag::err_expected_allocator_expression);
23133   }
23134   // Analyze and build list of variables.
23135   SmallVector<Expr *, 8> Vars;
23136   for (Expr *RefExpr : VarList) {
23137     assert(RefExpr && "NULL expr in OpenMP private clause.");
23138     SourceLocation ELoc;
23139     SourceRange ERange;
23140     Expr *SimpleRefExpr = RefExpr;
23141     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
23142     if (Res.second) {
23143       // It will be analyzed later.
23144       Vars.push_back(RefExpr);
23145     }
23146     ValueDecl *D = Res.first;
23147     if (!D)
23148       continue;
23149 
23150     auto *VD = dyn_cast<VarDecl>(D);
23151     DeclRefExpr *Ref = nullptr;
23152     if (!VD && !CurContext->isDependentContext())
23153       Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/false);
23154     Vars.push_back((VD || CurContext->isDependentContext())
23155                        ? RefExpr->IgnoreParens()
23156                        : Ref);
23157   }
23158 
23159   if (Vars.empty())
23160     return nullptr;
23161 
23162   if (Allocator)
23163     DSAStack->addInnerAllocatorExpr(Allocator);
23164   return OMPAllocateClause::Create(Context, StartLoc, LParenLoc, Allocator,
23165                                    ColonLoc, EndLoc, Vars);
23166 }
23167 
23168 OMPClause *Sema::ActOnOpenMPNontemporalClause(ArrayRef<Expr *> VarList,
23169                                               SourceLocation StartLoc,
23170                                               SourceLocation LParenLoc,
23171                                               SourceLocation EndLoc) {
23172   SmallVector<Expr *, 8> Vars;
23173   for (Expr *RefExpr : VarList) {
23174     assert(RefExpr && "NULL expr in OpenMP nontemporal clause.");
23175     SourceLocation ELoc;
23176     SourceRange ERange;
23177     Expr *SimpleRefExpr = RefExpr;
23178     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
23179     if (Res.second)
23180       // It will be analyzed later.
23181       Vars.push_back(RefExpr);
23182     ValueDecl *D = Res.first;
23183     if (!D)
23184       continue;
23185 
23186     // OpenMP 5.0, 2.9.3.1 simd Construct, Restrictions.
23187     // A list-item cannot appear in more than one nontemporal clause.
23188     if (const Expr *PrevRef =
23189             DSAStack->addUniqueNontemporal(D, SimpleRefExpr)) {
23190       Diag(ELoc, diag::err_omp_used_in_clause_twice)
23191           << 0 << getOpenMPClauseName(OMPC_nontemporal) << ERange;
23192       Diag(PrevRef->getExprLoc(), diag::note_omp_explicit_dsa)
23193           << getOpenMPClauseName(OMPC_nontemporal);
23194       continue;
23195     }
23196 
23197     Vars.push_back(RefExpr);
23198   }
23199 
23200   if (Vars.empty())
23201     return nullptr;
23202 
23203   return OMPNontemporalClause::Create(Context, StartLoc, LParenLoc, EndLoc,
23204                                       Vars);
23205 }
23206 
23207 OMPClause *Sema::ActOnOpenMPInclusiveClause(ArrayRef<Expr *> VarList,
23208                                             SourceLocation StartLoc,
23209                                             SourceLocation LParenLoc,
23210                                             SourceLocation EndLoc) {
23211   SmallVector<Expr *, 8> Vars;
23212   for (Expr *RefExpr : VarList) {
23213     assert(RefExpr && "NULL expr in OpenMP nontemporal clause.");
23214     SourceLocation ELoc;
23215     SourceRange ERange;
23216     Expr *SimpleRefExpr = RefExpr;
23217     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange,
23218                               /*AllowArraySection=*/true);
23219     if (Res.second)
23220       // It will be analyzed later.
23221       Vars.push_back(RefExpr);
23222     ValueDecl *D = Res.first;
23223     if (!D)
23224       continue;
23225 
23226     const DSAStackTy::DSAVarData DVar =
23227         DSAStack->getTopDSA(D, /*FromParent=*/true);
23228     // OpenMP 5.0, 2.9.6, scan Directive, Restrictions.
23229     // A list item that appears in the inclusive or exclusive clause must appear
23230     // in a reduction clause with the inscan modifier on the enclosing
23231     // worksharing-loop, worksharing-loop SIMD, or simd construct.
23232     if (DVar.CKind != OMPC_reduction || DVar.Modifier != OMPC_REDUCTION_inscan)
23233       Diag(ELoc, diag::err_omp_inclusive_exclusive_not_reduction)
23234           << RefExpr->getSourceRange();
23235 
23236     if (DSAStack->getParentDirective() != OMPD_unknown)
23237       DSAStack->markDeclAsUsedInScanDirective(D);
23238     Vars.push_back(RefExpr);
23239   }
23240 
23241   if (Vars.empty())
23242     return nullptr;
23243 
23244   return OMPInclusiveClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars);
23245 }
23246 
23247 OMPClause *Sema::ActOnOpenMPExclusiveClause(ArrayRef<Expr *> VarList,
23248                                             SourceLocation StartLoc,
23249                                             SourceLocation LParenLoc,
23250                                             SourceLocation EndLoc) {
23251   SmallVector<Expr *, 8> Vars;
23252   for (Expr *RefExpr : VarList) {
23253     assert(RefExpr && "NULL expr in OpenMP nontemporal clause.");
23254     SourceLocation ELoc;
23255     SourceRange ERange;
23256     Expr *SimpleRefExpr = RefExpr;
23257     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange,
23258                               /*AllowArraySection=*/true);
23259     if (Res.second)
23260       // It will be analyzed later.
23261       Vars.push_back(RefExpr);
23262     ValueDecl *D = Res.first;
23263     if (!D)
23264       continue;
23265 
23266     OpenMPDirectiveKind ParentDirective = DSAStack->getParentDirective();
23267     DSAStackTy::DSAVarData DVar;
23268     if (ParentDirective != OMPD_unknown)
23269       DVar = DSAStack->getTopDSA(D, /*FromParent=*/true);
23270     // OpenMP 5.0, 2.9.6, scan Directive, Restrictions.
23271     // A list item that appears in the inclusive or exclusive clause must appear
23272     // in a reduction clause with the inscan modifier on the enclosing
23273     // worksharing-loop, worksharing-loop SIMD, or simd construct.
23274     if (ParentDirective == OMPD_unknown || DVar.CKind != OMPC_reduction ||
23275         DVar.Modifier != OMPC_REDUCTION_inscan) {
23276       Diag(ELoc, diag::err_omp_inclusive_exclusive_not_reduction)
23277           << RefExpr->getSourceRange();
23278     } else {
23279       DSAStack->markDeclAsUsedInScanDirective(D);
23280     }
23281     Vars.push_back(RefExpr);
23282   }
23283 
23284   if (Vars.empty())
23285     return nullptr;
23286 
23287   return OMPExclusiveClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars);
23288 }
23289 
23290 /// Tries to find omp_alloctrait_t type.
23291 static bool findOMPAlloctraitT(Sema &S, SourceLocation Loc, DSAStackTy *Stack) {
23292   QualType OMPAlloctraitT = Stack->getOMPAlloctraitT();
23293   if (!OMPAlloctraitT.isNull())
23294     return true;
23295   IdentifierInfo &II = S.PP.getIdentifierTable().get("omp_alloctrait_t");
23296   ParsedType PT = S.getTypeName(II, Loc, S.getCurScope());
23297   if (!PT.getAsOpaquePtr() || PT.get().isNull()) {
23298     S.Diag(Loc, diag::err_omp_implied_type_not_found) << "omp_alloctrait_t";
23299     return false;
23300   }
23301   Stack->setOMPAlloctraitT(PT.get());
23302   return true;
23303 }
23304 
23305 OMPClause *Sema::ActOnOpenMPUsesAllocatorClause(
23306     SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc,
23307     ArrayRef<UsesAllocatorsData> Data) {
23308   // OpenMP [2.12.5, target Construct]
23309   // allocator is an identifier of omp_allocator_handle_t type.
23310   if (!findOMPAllocatorHandleT(*this, StartLoc, DSAStack))
23311     return nullptr;
23312   // OpenMP [2.12.5, target Construct]
23313   // allocator-traits-array is an identifier of const omp_alloctrait_t * type.
23314   if (llvm::any_of(
23315           Data,
23316           [](const UsesAllocatorsData &D) { return D.AllocatorTraits; }) &&
23317       !findOMPAlloctraitT(*this, StartLoc, DSAStack))
23318     return nullptr;
23319   llvm::SmallPtrSet<CanonicalDeclPtr<Decl>, 4> PredefinedAllocators;
23320   for (int I = 0; I < OMPAllocateDeclAttr::OMPUserDefinedMemAlloc; ++I) {
23321     auto AllocatorKind = static_cast<OMPAllocateDeclAttr::AllocatorTypeTy>(I);
23322     StringRef Allocator =
23323         OMPAllocateDeclAttr::ConvertAllocatorTypeTyToStr(AllocatorKind);
23324     DeclarationName AllocatorName = &Context.Idents.get(Allocator);
23325     PredefinedAllocators.insert(LookupSingleName(
23326         TUScope, AllocatorName, StartLoc, Sema::LookupAnyName));
23327   }
23328 
23329   SmallVector<OMPUsesAllocatorsClause::Data, 4> NewData;
23330   for (const UsesAllocatorsData &D : Data) {
23331     Expr *AllocatorExpr = nullptr;
23332     // Check allocator expression.
23333     if (D.Allocator->isTypeDependent()) {
23334       AllocatorExpr = D.Allocator;
23335     } else {
23336       // Traits were specified - need to assign new allocator to the specified
23337       // allocator, so it must be an lvalue.
23338       AllocatorExpr = D.Allocator->IgnoreParenImpCasts();
23339       auto *DRE = dyn_cast<DeclRefExpr>(AllocatorExpr);
23340       bool IsPredefinedAllocator = false;
23341       if (DRE)
23342         IsPredefinedAllocator = PredefinedAllocators.count(DRE->getDecl());
23343       if (!DRE ||
23344           !(Context.hasSameUnqualifiedType(
23345                 AllocatorExpr->getType(), DSAStack->getOMPAllocatorHandleT()) ||
23346             Context.typesAreCompatible(AllocatorExpr->getType(),
23347                                        DSAStack->getOMPAllocatorHandleT(),
23348                                        /*CompareUnqualified=*/true)) ||
23349           (!IsPredefinedAllocator &&
23350            (AllocatorExpr->getType().isConstant(Context) ||
23351             !AllocatorExpr->isLValue()))) {
23352         Diag(D.Allocator->getExprLoc(), diag::err_omp_var_expected)
23353             << "omp_allocator_handle_t" << (DRE ? 1 : 0)
23354             << AllocatorExpr->getType() << D.Allocator->getSourceRange();
23355         continue;
23356       }
23357       // OpenMP [2.12.5, target Construct]
23358       // Predefined allocators appearing in a uses_allocators clause cannot have
23359       // traits specified.
23360       if (IsPredefinedAllocator && D.AllocatorTraits) {
23361         Diag(D.AllocatorTraits->getExprLoc(),
23362              diag::err_omp_predefined_allocator_with_traits)
23363             << D.AllocatorTraits->getSourceRange();
23364         Diag(D.Allocator->getExprLoc(), diag::note_omp_predefined_allocator)
23365             << cast<NamedDecl>(DRE->getDecl())->getName()
23366             << D.Allocator->getSourceRange();
23367         continue;
23368       }
23369       // OpenMP [2.12.5, target Construct]
23370       // Non-predefined allocators appearing in a uses_allocators clause must
23371       // have traits specified.
23372       if (!IsPredefinedAllocator && !D.AllocatorTraits) {
23373         Diag(D.Allocator->getExprLoc(),
23374              diag::err_omp_nonpredefined_allocator_without_traits);
23375         continue;
23376       }
23377       // No allocator traits - just convert it to rvalue.
23378       if (!D.AllocatorTraits)
23379         AllocatorExpr = DefaultLvalueConversion(AllocatorExpr).get();
23380       DSAStack->addUsesAllocatorsDecl(
23381           DRE->getDecl(),
23382           IsPredefinedAllocator
23383               ? DSAStackTy::UsesAllocatorsDeclKind::PredefinedAllocator
23384               : DSAStackTy::UsesAllocatorsDeclKind::UserDefinedAllocator);
23385     }
23386     Expr *AllocatorTraitsExpr = nullptr;
23387     if (D.AllocatorTraits) {
23388       if (D.AllocatorTraits->isTypeDependent()) {
23389         AllocatorTraitsExpr = D.AllocatorTraits;
23390       } else {
23391         // OpenMP [2.12.5, target Construct]
23392         // Arrays that contain allocator traits that appear in a uses_allocators
23393         // clause must be constant arrays, have constant values and be defined
23394         // in the same scope as the construct in which the clause appears.
23395         AllocatorTraitsExpr = D.AllocatorTraits->IgnoreParenImpCasts();
23396         // Check that traits expr is a constant array.
23397         QualType TraitTy;
23398         if (const ArrayType *Ty =
23399                 AllocatorTraitsExpr->getType()->getAsArrayTypeUnsafe())
23400           if (const auto *ConstArrayTy = dyn_cast<ConstantArrayType>(Ty))
23401             TraitTy = ConstArrayTy->getElementType();
23402         if (TraitTy.isNull() ||
23403             !(Context.hasSameUnqualifiedType(TraitTy,
23404                                              DSAStack->getOMPAlloctraitT()) ||
23405               Context.typesAreCompatible(TraitTy, DSAStack->getOMPAlloctraitT(),
23406                                          /*CompareUnqualified=*/true))) {
23407           Diag(D.AllocatorTraits->getExprLoc(),
23408                diag::err_omp_expected_array_alloctraits)
23409               << AllocatorTraitsExpr->getType();
23410           continue;
23411         }
23412         // Do not map by default allocator traits if it is a standalone
23413         // variable.
23414         if (auto *DRE = dyn_cast<DeclRefExpr>(AllocatorTraitsExpr))
23415           DSAStack->addUsesAllocatorsDecl(
23416               DRE->getDecl(),
23417               DSAStackTy::UsesAllocatorsDeclKind::AllocatorTrait);
23418       }
23419     }
23420     OMPUsesAllocatorsClause::Data &NewD = NewData.emplace_back();
23421     NewD.Allocator = AllocatorExpr;
23422     NewD.AllocatorTraits = AllocatorTraitsExpr;
23423     NewD.LParenLoc = D.LParenLoc;
23424     NewD.RParenLoc = D.RParenLoc;
23425   }
23426   return OMPUsesAllocatorsClause::Create(Context, StartLoc, LParenLoc, EndLoc,
23427                                          NewData);
23428 }
23429 
23430 OMPClause *Sema::ActOnOpenMPAffinityClause(
23431     SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation ColonLoc,
23432     SourceLocation EndLoc, Expr *Modifier, ArrayRef<Expr *> Locators) {
23433   SmallVector<Expr *, 8> Vars;
23434   for (Expr *RefExpr : Locators) {
23435     assert(RefExpr && "NULL expr in OpenMP shared clause.");
23436     if (isa<DependentScopeDeclRefExpr>(RefExpr) || RefExpr->isTypeDependent()) {
23437       // It will be analyzed later.
23438       Vars.push_back(RefExpr);
23439       continue;
23440     }
23441 
23442     SourceLocation ELoc = RefExpr->getExprLoc();
23443     Expr *SimpleExpr = RefExpr->IgnoreParenImpCasts();
23444 
23445     if (!SimpleExpr->isLValue()) {
23446       Diag(ELoc, diag::err_omp_expected_addressable_lvalue_or_array_item)
23447           << 1 << 0 << RefExpr->getSourceRange();
23448       continue;
23449     }
23450 
23451     ExprResult Res;
23452     {
23453       Sema::TentativeAnalysisScope Trap(*this);
23454       Res = CreateBuiltinUnaryOp(ELoc, UO_AddrOf, SimpleExpr);
23455     }
23456     if (!Res.isUsable() && !isa<OMPArraySectionExpr>(SimpleExpr) &&
23457         !isa<OMPArrayShapingExpr>(SimpleExpr)) {
23458       Diag(ELoc, diag::err_omp_expected_addressable_lvalue_or_array_item)
23459           << 1 << 0 << RefExpr->getSourceRange();
23460       continue;
23461     }
23462     Vars.push_back(SimpleExpr);
23463   }
23464 
23465   return OMPAffinityClause::Create(Context, StartLoc, LParenLoc, ColonLoc,
23466                                    EndLoc, Modifier, Vars);
23467 }
23468 
23469 OMPClause *Sema::ActOnOpenMPBindClause(OpenMPBindClauseKind Kind,
23470                                        SourceLocation KindLoc,
23471                                        SourceLocation StartLoc,
23472                                        SourceLocation LParenLoc,
23473                                        SourceLocation EndLoc) {
23474   if (Kind == OMPC_BIND_unknown) {
23475     Diag(KindLoc, diag::err_omp_unexpected_clause_value)
23476         << getListOfPossibleValues(OMPC_bind, /*First=*/0,
23477                                    /*Last=*/unsigned(OMPC_BIND_unknown))
23478         << getOpenMPClauseName(OMPC_bind);
23479     return nullptr;
23480   }
23481 
23482   return OMPBindClause::Create(Context, Kind, KindLoc, StartLoc, LParenLoc,
23483                                EndLoc);
23484 }
23485