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.has_value();
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.value();
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.has_value();
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.value();
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   // Only rebuild for Field.
2274   if (!dyn_cast<FieldDecl>(D))
2275     return false;
2276   DSAStackTy::DSAVarData DVarPrivate = DSAStack->hasDSA(
2277       D,
2278       [](OpenMPClauseKind C, bool AppliedToPointee,
2279          DefaultDataSharingAttributes DefaultAttr) {
2280         return isOpenMPPrivate(C) && !AppliedToPointee &&
2281                (DefaultAttr == DSA_firstprivate || DefaultAttr == DSA_private);
2282       },
2283       [](OpenMPDirectiveKind) { return true; },
2284       DSAStack->isClauseParsingMode());
2285   if (DVarPrivate.CKind != OMPC_unknown)
2286     return true;
2287   return false;
2288 }
2289 
2290 static OMPCapturedExprDecl *buildCaptureDecl(Sema &S, IdentifierInfo *Id,
2291                                              Expr *CaptureExpr, bool WithInit,
2292                                              DeclContext *CurContext,
2293                                              bool AsExpression);
2294 
2295 VarDecl *Sema::isOpenMPCapturedDecl(ValueDecl *D, bool CheckScopeInfo,
2296                                     unsigned StopAt) {
2297   assert(LangOpts.OpenMP && "OpenMP is not allowed");
2298   D = getCanonicalDecl(D);
2299 
2300   auto *VD = dyn_cast<VarDecl>(D);
2301   // Do not capture constexpr variables.
2302   if (VD && VD->isConstexpr())
2303     return nullptr;
2304 
2305   // If we want to determine whether the variable should be captured from the
2306   // perspective of the current capturing scope, and we've already left all the
2307   // capturing scopes of the top directive on the stack, check from the
2308   // perspective of its parent directive (if any) instead.
2309   DSAStackTy::ParentDirectiveScope InParentDirectiveRAII(
2310       *DSAStack, CheckScopeInfo && DSAStack->isBodyComplete());
2311 
2312   // If we are attempting to capture a global variable in a directive with
2313   // 'target' we return true so that this global is also mapped to the device.
2314   //
2315   if (VD && !VD->hasLocalStorage() &&
2316       (getCurCapturedRegion() || getCurBlock() || getCurLambda())) {
2317     if (isInOpenMPTargetExecutionDirective()) {
2318       DSAStackTy::DSAVarData DVarTop =
2319           DSAStack->getTopDSA(D, DSAStack->isClauseParsingMode());
2320       if (DVarTop.CKind != OMPC_unknown && DVarTop.RefExpr)
2321         return VD;
2322       // If the declaration is enclosed in a 'declare target' directive,
2323       // then it should not be captured.
2324       //
2325       if (OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(VD))
2326         return nullptr;
2327       CapturedRegionScopeInfo *CSI = nullptr;
2328       for (FunctionScopeInfo *FSI : llvm::drop_begin(
2329                llvm::reverse(FunctionScopes),
2330                CheckScopeInfo ? (FunctionScopes.size() - (StopAt + 1)) : 0)) {
2331         if (!isa<CapturingScopeInfo>(FSI))
2332           return nullptr;
2333         if (auto *RSI = dyn_cast<CapturedRegionScopeInfo>(FSI))
2334           if (RSI->CapRegionKind == CR_OpenMP) {
2335             CSI = RSI;
2336             break;
2337           }
2338       }
2339       assert(CSI && "Failed to find CapturedRegionScopeInfo");
2340       SmallVector<OpenMPDirectiveKind, 4> Regions;
2341       getOpenMPCaptureRegions(Regions,
2342                               DSAStack->getDirective(CSI->OpenMPLevel));
2343       if (Regions[CSI->OpenMPCaptureLevel] != OMPD_task)
2344         return VD;
2345     }
2346     if (isInOpenMPDeclareTargetContext()) {
2347       // Try to mark variable as declare target if it is used in capturing
2348       // regions.
2349       if (LangOpts.OpenMP <= 45 &&
2350           !OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(VD))
2351         checkDeclIsAllowedInOpenMPTarget(nullptr, VD);
2352       return nullptr;
2353     }
2354   }
2355 
2356   if (CheckScopeInfo) {
2357     bool OpenMPFound = false;
2358     for (unsigned I = StopAt + 1; I > 0; --I) {
2359       FunctionScopeInfo *FSI = FunctionScopes[I - 1];
2360       if (!isa<CapturingScopeInfo>(FSI))
2361         return nullptr;
2362       if (auto *RSI = dyn_cast<CapturedRegionScopeInfo>(FSI))
2363         if (RSI->CapRegionKind == CR_OpenMP) {
2364           OpenMPFound = true;
2365           break;
2366         }
2367     }
2368     if (!OpenMPFound)
2369       return nullptr;
2370   }
2371 
2372   if (DSAStack->getCurrentDirective() != OMPD_unknown &&
2373       (!DSAStack->isClauseParsingMode() ||
2374        DSAStack->getParentDirective() != OMPD_unknown)) {
2375     auto &&Info = DSAStack->isLoopControlVariable(D);
2376     if (Info.first ||
2377         (VD && VD->hasLocalStorage() &&
2378          isImplicitOrExplicitTaskingRegion(DSAStack->getCurrentDirective())) ||
2379         (VD && DSAStack->isForceVarCapturing()))
2380       return VD ? VD : Info.second;
2381     DSAStackTy::DSAVarData DVarTop =
2382         DSAStack->getTopDSA(D, DSAStack->isClauseParsingMode());
2383     if (DVarTop.CKind != OMPC_unknown && isOpenMPPrivate(DVarTop.CKind) &&
2384         (!VD || VD->hasLocalStorage() || !DVarTop.AppliedToPointee))
2385       return VD ? VD : cast<VarDecl>(DVarTop.PrivateCopy->getDecl());
2386     // Threadprivate variables must not be captured.
2387     if (isOpenMPThreadPrivate(DVarTop.CKind))
2388       return nullptr;
2389     // The variable is not private or it is the variable in the directive with
2390     // default(none) clause and not used in any clause.
2391     DSAStackTy::DSAVarData DVarPrivate = DSAStack->hasDSA(
2392         D,
2393         [](OpenMPClauseKind C, bool AppliedToPointee, bool) {
2394           return isOpenMPPrivate(C) && !AppliedToPointee;
2395         },
2396         [](OpenMPDirectiveKind) { return true; },
2397         DSAStack->isClauseParsingMode());
2398     // Global shared must not be captured.
2399     if (VD && !VD->hasLocalStorage() && DVarPrivate.CKind == OMPC_unknown &&
2400         ((DSAStack->getDefaultDSA() != DSA_none &&
2401           DSAStack->getDefaultDSA() != DSA_private &&
2402           DSAStack->getDefaultDSA() != DSA_firstprivate) ||
2403          DVarTop.CKind == OMPC_shared))
2404       return nullptr;
2405     auto *FD = dyn_cast<FieldDecl>(D);
2406     if (DVarPrivate.CKind != OMPC_unknown && !VD && FD &&
2407         !DVarPrivate.PrivateCopy) {
2408       DSAStackTy::DSAVarData DVarPrivate = DSAStack->hasDSA(
2409           D,
2410           [](OpenMPClauseKind C, bool AppliedToPointee,
2411              DefaultDataSharingAttributes DefaultAttr) {
2412             return isOpenMPPrivate(C) && !AppliedToPointee &&
2413                    (DefaultAttr == DSA_firstprivate ||
2414                     DefaultAttr == DSA_private);
2415           },
2416           [](OpenMPDirectiveKind) { return true; },
2417           DSAStack->isClauseParsingMode());
2418       if (DVarPrivate.CKind == OMPC_unknown)
2419         return nullptr;
2420 
2421       VarDecl *VD = DSAStack->getImplicitFDCapExprDecl(FD);
2422       if (VD)
2423         return VD;
2424       if (getCurrentThisType().isNull())
2425         return nullptr;
2426       Expr *ThisExpr = BuildCXXThisExpr(SourceLocation(), getCurrentThisType(),
2427                                         /*IsImplicit=*/true);
2428       const CXXScopeSpec CS = CXXScopeSpec();
2429       Expr *ME = BuildMemberExpr(ThisExpr, /*IsArrow=*/true, SourceLocation(),
2430                                  NestedNameSpecifierLoc(), SourceLocation(), FD,
2431                                  DeclAccessPair::make(FD, FD->getAccess()),
2432                                  /*HadMultipleCandidates=*/false,
2433                                  DeclarationNameInfo(), FD->getType(),
2434                                  VK_LValue, OK_Ordinary);
2435       OMPCapturedExprDecl *CD = buildCaptureDecl(
2436           *this, FD->getIdentifier(), ME, DVarPrivate.CKind != OMPC_private,
2437           CurContext->getParent(), /*AsExpression=*/false);
2438       DeclRefExpr *VDPrivateRefExpr = buildDeclRefExpr(
2439           *this, CD, CD->getType().getNonReferenceType(), SourceLocation());
2440       VD = cast<VarDecl>(VDPrivateRefExpr->getDecl());
2441       DSAStack->addImplicitDefaultFirstprivateFD(FD, VD);
2442       return VD;
2443     }
2444     if (DVarPrivate.CKind != OMPC_unknown ||
2445         (VD && (DSAStack->getDefaultDSA() == DSA_none ||
2446                 DSAStack->getDefaultDSA() == DSA_private ||
2447                 DSAStack->getDefaultDSA() == DSA_firstprivate)))
2448       return VD ? VD : cast<VarDecl>(DVarPrivate.PrivateCopy->getDecl());
2449   }
2450   return nullptr;
2451 }
2452 
2453 void Sema::adjustOpenMPTargetScopeIndex(unsigned &FunctionScopesIndex,
2454                                         unsigned Level) const {
2455   FunctionScopesIndex -= getOpenMPCaptureLevels(DSAStack->getDirective(Level));
2456 }
2457 
2458 void Sema::startOpenMPLoop() {
2459   assert(LangOpts.OpenMP && "OpenMP must be enabled.");
2460   if (isOpenMPLoopDirective(DSAStack->getCurrentDirective()))
2461     DSAStack->loopInit();
2462 }
2463 
2464 void Sema::startOpenMPCXXRangeFor() {
2465   assert(LangOpts.OpenMP && "OpenMP must be enabled.");
2466   if (isOpenMPLoopDirective(DSAStack->getCurrentDirective())) {
2467     DSAStack->resetPossibleLoopCounter();
2468     DSAStack->loopStart();
2469   }
2470 }
2471 
2472 OpenMPClauseKind Sema::isOpenMPPrivateDecl(ValueDecl *D, unsigned Level,
2473                                            unsigned CapLevel) const {
2474   assert(LangOpts.OpenMP && "OpenMP is not allowed");
2475   if (DSAStack->getCurrentDirective() != OMPD_unknown &&
2476       (!DSAStack->isClauseParsingMode() ||
2477        DSAStack->getParentDirective() != OMPD_unknown)) {
2478     DSAStackTy::DSAVarData DVarPrivate = DSAStack->hasDSA(
2479         D,
2480         [](OpenMPClauseKind C, bool AppliedToPointee,
2481            DefaultDataSharingAttributes DefaultAttr) {
2482           return isOpenMPPrivate(C) && !AppliedToPointee &&
2483                  DefaultAttr == DSA_private;
2484         },
2485         [](OpenMPDirectiveKind) { return true; },
2486         DSAStack->isClauseParsingMode());
2487     if (DVarPrivate.CKind == OMPC_private && isa<OMPCapturedExprDecl>(D) &&
2488         DSAStack->isImplicitDefaultFirstprivateFD(cast<VarDecl>(D)) &&
2489         !DSAStack->isLoopControlVariable(D).first)
2490       return OMPC_private;
2491   }
2492   if (DSAStack->hasExplicitDirective(isOpenMPTaskingDirective, Level)) {
2493     bool IsTriviallyCopyable =
2494         D->getType().getNonReferenceType().isTriviallyCopyableType(Context) &&
2495         !D->getType()
2496              .getNonReferenceType()
2497              .getCanonicalType()
2498              ->getAsCXXRecordDecl();
2499     OpenMPDirectiveKind DKind = DSAStack->getDirective(Level);
2500     SmallVector<OpenMPDirectiveKind, 4> CaptureRegions;
2501     getOpenMPCaptureRegions(CaptureRegions, DKind);
2502     if (isOpenMPTaskingDirective(CaptureRegions[CapLevel]) &&
2503         (IsTriviallyCopyable ||
2504          !isOpenMPTaskLoopDirective(CaptureRegions[CapLevel]))) {
2505       if (DSAStack->hasExplicitDSA(
2506               D,
2507               [](OpenMPClauseKind K, bool) { return K == OMPC_firstprivate; },
2508               Level, /*NotLastprivate=*/true))
2509         return OMPC_firstprivate;
2510       DSAStackTy::DSAVarData DVar = DSAStack->getImplicitDSA(D, Level);
2511       if (DVar.CKind != OMPC_shared &&
2512           !DSAStack->isLoopControlVariable(D, Level).first && !DVar.RefExpr) {
2513         DSAStack->addImplicitTaskFirstprivate(Level, D);
2514         return OMPC_firstprivate;
2515       }
2516     }
2517   }
2518   if (isOpenMPLoopDirective(DSAStack->getCurrentDirective())) {
2519     if (DSAStack->getAssociatedLoops() > 0 && !DSAStack->isLoopStarted()) {
2520       DSAStack->resetPossibleLoopCounter(D);
2521       DSAStack->loopStart();
2522       return OMPC_private;
2523     }
2524     if ((DSAStack->getPossiblyLoopCunter() == D->getCanonicalDecl() ||
2525          DSAStack->isLoopControlVariable(D).first) &&
2526         !DSAStack->hasExplicitDSA(
2527             D, [](OpenMPClauseKind K, bool) { return K != OMPC_private; },
2528             Level) &&
2529         !isOpenMPSimdDirective(DSAStack->getCurrentDirective()))
2530       return OMPC_private;
2531   }
2532   if (const auto *VD = dyn_cast<VarDecl>(D)) {
2533     if (DSAStack->isThreadPrivate(const_cast<VarDecl *>(VD)) &&
2534         DSAStack->isForceVarCapturing() &&
2535         !DSAStack->hasExplicitDSA(
2536             D, [](OpenMPClauseKind K, bool) { return K == OMPC_copyin; },
2537             Level))
2538       return OMPC_private;
2539   }
2540   // User-defined allocators are private since they must be defined in the
2541   // context of target region.
2542   if (DSAStack->hasExplicitDirective(isOpenMPTargetExecutionDirective, Level) &&
2543       DSAStack->isUsesAllocatorsDecl(Level, D).value_or(
2544           DSAStackTy::UsesAllocatorsDeclKind::AllocatorTrait) ==
2545           DSAStackTy::UsesAllocatorsDeclKind::UserDefinedAllocator)
2546     return OMPC_private;
2547   return (DSAStack->hasExplicitDSA(
2548               D, [](OpenMPClauseKind K, bool) { return K == OMPC_private; },
2549               Level) ||
2550           (DSAStack->isClauseParsingMode() &&
2551            DSAStack->getClauseParsingMode() == OMPC_private) ||
2552           // Consider taskgroup reduction descriptor variable a private
2553           // to avoid possible capture in the region.
2554           (DSAStack->hasExplicitDirective(
2555                [](OpenMPDirectiveKind K) {
2556                  return K == OMPD_taskgroup ||
2557                         ((isOpenMPParallelDirective(K) ||
2558                           isOpenMPWorksharingDirective(K)) &&
2559                          !isOpenMPSimdDirective(K));
2560                },
2561                Level) &&
2562            DSAStack->isTaskgroupReductionRef(D, Level)))
2563              ? OMPC_private
2564              : OMPC_unknown;
2565 }
2566 
2567 void Sema::setOpenMPCaptureKind(FieldDecl *FD, const ValueDecl *D,
2568                                 unsigned Level) {
2569   assert(LangOpts.OpenMP && "OpenMP is not allowed");
2570   D = getCanonicalDecl(D);
2571   OpenMPClauseKind OMPC = OMPC_unknown;
2572   for (unsigned I = DSAStack->getNestingLevel() + 1; I > Level; --I) {
2573     const unsigned NewLevel = I - 1;
2574     if (DSAStack->hasExplicitDSA(
2575             D,
2576             [&OMPC](const OpenMPClauseKind K, bool AppliedToPointee) {
2577               if (isOpenMPPrivate(K) && !AppliedToPointee) {
2578                 OMPC = K;
2579                 return true;
2580               }
2581               return false;
2582             },
2583             NewLevel))
2584       break;
2585     if (DSAStack->checkMappableExprComponentListsForDeclAtLevel(
2586             D, NewLevel,
2587             [](OMPClauseMappableExprCommon::MappableExprComponentListRef,
2588                OpenMPClauseKind) { return true; })) {
2589       OMPC = OMPC_map;
2590       break;
2591     }
2592     if (DSAStack->hasExplicitDirective(isOpenMPTargetExecutionDirective,
2593                                        NewLevel)) {
2594       OMPC = OMPC_map;
2595       if (DSAStack->mustBeFirstprivateAtLevel(
2596               NewLevel, getVariableCategoryFromDecl(LangOpts, D)))
2597         OMPC = OMPC_firstprivate;
2598       break;
2599     }
2600   }
2601   if (OMPC != OMPC_unknown)
2602     FD->addAttr(OMPCaptureKindAttr::CreateImplicit(Context, unsigned(OMPC)));
2603 }
2604 
2605 bool Sema::isOpenMPTargetCapturedDecl(const ValueDecl *D, unsigned Level,
2606                                       unsigned CaptureLevel) const {
2607   assert(LangOpts.OpenMP && "OpenMP is not allowed");
2608   // Return true if the current level is no longer enclosed in a target region.
2609 
2610   SmallVector<OpenMPDirectiveKind, 4> Regions;
2611   getOpenMPCaptureRegions(Regions, DSAStack->getDirective(Level));
2612   const auto *VD = dyn_cast<VarDecl>(D);
2613   return VD && !VD->hasLocalStorage() &&
2614          DSAStack->hasExplicitDirective(isOpenMPTargetExecutionDirective,
2615                                         Level) &&
2616          Regions[CaptureLevel] != OMPD_task;
2617 }
2618 
2619 bool Sema::isOpenMPGlobalCapturedDecl(ValueDecl *D, unsigned Level,
2620                                       unsigned CaptureLevel) const {
2621   assert(LangOpts.OpenMP && "OpenMP is not allowed");
2622   // Return true if the current level is no longer enclosed in a target region.
2623 
2624   if (const auto *VD = dyn_cast<VarDecl>(D)) {
2625     if (!VD->hasLocalStorage()) {
2626       if (isInOpenMPTargetExecutionDirective())
2627         return true;
2628       DSAStackTy::DSAVarData TopDVar =
2629           DSAStack->getTopDSA(D, /*FromParent=*/false);
2630       unsigned NumLevels =
2631           getOpenMPCaptureLevels(DSAStack->getDirective(Level));
2632       if (Level == 0)
2633         // non-file scope static variale with default(firstprivate)
2634         // should be gloabal captured.
2635         return (NumLevels == CaptureLevel + 1 &&
2636                 (TopDVar.CKind != OMPC_shared ||
2637                  DSAStack->getDefaultDSA() == DSA_firstprivate));
2638       do {
2639         --Level;
2640         DSAStackTy::DSAVarData DVar = DSAStack->getImplicitDSA(D, Level);
2641         if (DVar.CKind != OMPC_shared)
2642           return true;
2643       } while (Level > 0);
2644     }
2645   }
2646   return true;
2647 }
2648 
2649 void Sema::DestroyDataSharingAttributesStack() { delete DSAStack; }
2650 
2651 void Sema::ActOnOpenMPBeginDeclareVariant(SourceLocation Loc,
2652                                           OMPTraitInfo &TI) {
2653   OMPDeclareVariantScopes.push_back(OMPDeclareVariantScope(TI));
2654 }
2655 
2656 void Sema::ActOnOpenMPEndDeclareVariant() {
2657   assert(isInOpenMPDeclareVariantScope() &&
2658          "Not in OpenMP declare variant scope!");
2659 
2660   OMPDeclareVariantScopes.pop_back();
2661 }
2662 
2663 void Sema::finalizeOpenMPDelayedAnalysis(const FunctionDecl *Caller,
2664                                          const FunctionDecl *Callee,
2665                                          SourceLocation Loc) {
2666   assert(LangOpts.OpenMP && "Expected OpenMP compilation mode.");
2667   Optional<OMPDeclareTargetDeclAttr::DevTypeTy> DevTy =
2668       OMPDeclareTargetDeclAttr::getDeviceType(Caller->getMostRecentDecl());
2669   // Ignore host functions during device analyzis.
2670   if (LangOpts.OpenMPIsDevice &&
2671       (!DevTy || *DevTy == OMPDeclareTargetDeclAttr::DT_Host))
2672     return;
2673   // Ignore nohost functions during host analyzis.
2674   if (!LangOpts.OpenMPIsDevice && DevTy &&
2675       *DevTy == OMPDeclareTargetDeclAttr::DT_NoHost)
2676     return;
2677   const FunctionDecl *FD = Callee->getMostRecentDecl();
2678   DevTy = OMPDeclareTargetDeclAttr::getDeviceType(FD);
2679   if (LangOpts.OpenMPIsDevice && DevTy &&
2680       *DevTy == OMPDeclareTargetDeclAttr::DT_Host) {
2681     // Diagnose host function called during device codegen.
2682     StringRef HostDevTy =
2683         getOpenMPSimpleClauseTypeName(OMPC_device_type, OMPC_DEVICE_TYPE_host);
2684     Diag(Loc, diag::err_omp_wrong_device_function_call) << HostDevTy << 0;
2685     Diag(*OMPDeclareTargetDeclAttr::getLocation(FD),
2686          diag::note_omp_marked_device_type_here)
2687         << HostDevTy;
2688     return;
2689   }
2690   if (!LangOpts.OpenMPIsDevice && !LangOpts.OpenMPOffloadMandatory && DevTy &&
2691       *DevTy == OMPDeclareTargetDeclAttr::DT_NoHost) {
2692     // Diagnose nohost function called during host codegen.
2693     StringRef NoHostDevTy = getOpenMPSimpleClauseTypeName(
2694         OMPC_device_type, OMPC_DEVICE_TYPE_nohost);
2695     Diag(Loc, diag::err_omp_wrong_device_function_call) << NoHostDevTy << 1;
2696     Diag(*OMPDeclareTargetDeclAttr::getLocation(FD),
2697          diag::note_omp_marked_device_type_here)
2698         << NoHostDevTy;
2699   }
2700 }
2701 
2702 void Sema::StartOpenMPDSABlock(OpenMPDirectiveKind DKind,
2703                                const DeclarationNameInfo &DirName,
2704                                Scope *CurScope, SourceLocation Loc) {
2705   DSAStack->push(DKind, DirName, CurScope, Loc);
2706   PushExpressionEvaluationContext(
2707       ExpressionEvaluationContext::PotentiallyEvaluated);
2708 }
2709 
2710 void Sema::StartOpenMPClause(OpenMPClauseKind K) {
2711   DSAStack->setClauseParsingMode(K);
2712 }
2713 
2714 void Sema::EndOpenMPClause() {
2715   DSAStack->setClauseParsingMode(/*K=*/OMPC_unknown);
2716   CleanupVarDeclMarking();
2717 }
2718 
2719 static std::pair<ValueDecl *, bool>
2720 getPrivateItem(Sema &S, Expr *&RefExpr, SourceLocation &ELoc,
2721                SourceRange &ERange, bool AllowArraySection = false);
2722 
2723 /// Check consistency of the reduction clauses.
2724 static void checkReductionClauses(Sema &S, DSAStackTy *Stack,
2725                                   ArrayRef<OMPClause *> Clauses) {
2726   bool InscanFound = false;
2727   SourceLocation InscanLoc;
2728   // OpenMP 5.0, 2.19.5.4 reduction Clause, Restrictions.
2729   // A reduction clause without the inscan reduction-modifier may not appear on
2730   // a construct on which a reduction clause with the inscan reduction-modifier
2731   // appears.
2732   for (OMPClause *C : Clauses) {
2733     if (C->getClauseKind() != OMPC_reduction)
2734       continue;
2735     auto *RC = cast<OMPReductionClause>(C);
2736     if (RC->getModifier() == OMPC_REDUCTION_inscan) {
2737       InscanFound = true;
2738       InscanLoc = RC->getModifierLoc();
2739       continue;
2740     }
2741     if (RC->getModifier() == OMPC_REDUCTION_task) {
2742       // OpenMP 5.0, 2.19.5.4 reduction Clause.
2743       // A reduction clause with the task reduction-modifier may only appear on
2744       // a parallel construct, a worksharing construct or a combined or
2745       // composite construct for which any of the aforementioned constructs is a
2746       // constituent construct and simd or loop are not constituent constructs.
2747       OpenMPDirectiveKind CurDir = Stack->getCurrentDirective();
2748       if (!(isOpenMPParallelDirective(CurDir) ||
2749             isOpenMPWorksharingDirective(CurDir)) ||
2750           isOpenMPSimdDirective(CurDir))
2751         S.Diag(RC->getModifierLoc(),
2752                diag::err_omp_reduction_task_not_parallel_or_worksharing);
2753       continue;
2754     }
2755   }
2756   if (InscanFound) {
2757     for (OMPClause *C : Clauses) {
2758       if (C->getClauseKind() != OMPC_reduction)
2759         continue;
2760       auto *RC = cast<OMPReductionClause>(C);
2761       if (RC->getModifier() != OMPC_REDUCTION_inscan) {
2762         S.Diag(RC->getModifier() == OMPC_REDUCTION_unknown
2763                    ? RC->getBeginLoc()
2764                    : RC->getModifierLoc(),
2765                diag::err_omp_inscan_reduction_expected);
2766         S.Diag(InscanLoc, diag::note_omp_previous_inscan_reduction);
2767         continue;
2768       }
2769       for (Expr *Ref : RC->varlists()) {
2770         assert(Ref && "NULL expr in OpenMP nontemporal clause.");
2771         SourceLocation ELoc;
2772         SourceRange ERange;
2773         Expr *SimpleRefExpr = Ref;
2774         auto Res = getPrivateItem(S, SimpleRefExpr, ELoc, ERange,
2775                                   /*AllowArraySection=*/true);
2776         ValueDecl *D = Res.first;
2777         if (!D)
2778           continue;
2779         if (!Stack->isUsedInScanDirective(getCanonicalDecl(D))) {
2780           S.Diag(Ref->getExprLoc(),
2781                  diag::err_omp_reduction_not_inclusive_exclusive)
2782               << Ref->getSourceRange();
2783         }
2784       }
2785     }
2786   }
2787 }
2788 
2789 static void checkAllocateClauses(Sema &S, DSAStackTy *Stack,
2790                                  ArrayRef<OMPClause *> Clauses);
2791 static DeclRefExpr *buildCapture(Sema &S, ValueDecl *D, Expr *CaptureExpr,
2792                                  bool WithInit);
2793 
2794 static void reportOriginalDsa(Sema &SemaRef, const DSAStackTy *Stack,
2795                               const ValueDecl *D,
2796                               const DSAStackTy::DSAVarData &DVar,
2797                               bool IsLoopIterVar = false);
2798 
2799 void Sema::EndOpenMPDSABlock(Stmt *CurDirective) {
2800   // OpenMP [2.14.3.5, Restrictions, C/C++, p.1]
2801   //  A variable of class type (or array thereof) that appears in a lastprivate
2802   //  clause requires an accessible, unambiguous default constructor for the
2803   //  class type, unless the list item is also specified in a firstprivate
2804   //  clause.
2805   if (const auto *D = dyn_cast_or_null<OMPExecutableDirective>(CurDirective)) {
2806     for (OMPClause *C : D->clauses()) {
2807       if (auto *Clause = dyn_cast<OMPLastprivateClause>(C)) {
2808         SmallVector<Expr *, 8> PrivateCopies;
2809         for (Expr *DE : Clause->varlists()) {
2810           if (DE->isValueDependent() || DE->isTypeDependent()) {
2811             PrivateCopies.push_back(nullptr);
2812             continue;
2813           }
2814           auto *DRE = cast<DeclRefExpr>(DE->IgnoreParens());
2815           auto *VD = cast<VarDecl>(DRE->getDecl());
2816           QualType Type = VD->getType().getNonReferenceType();
2817           const DSAStackTy::DSAVarData DVar =
2818               DSAStack->getTopDSA(VD, /*FromParent=*/false);
2819           if (DVar.CKind == OMPC_lastprivate) {
2820             // Generate helper private variable and initialize it with the
2821             // default value. The address of the original variable is replaced
2822             // by the address of the new private variable in CodeGen. This new
2823             // variable is not added to IdResolver, so the code in the OpenMP
2824             // region uses original variable for proper diagnostics.
2825             VarDecl *VDPrivate = buildVarDecl(
2826                 *this, DE->getExprLoc(), Type.getUnqualifiedType(),
2827                 VD->getName(), VD->hasAttrs() ? &VD->getAttrs() : nullptr, DRE);
2828             ActOnUninitializedDecl(VDPrivate);
2829             if (VDPrivate->isInvalidDecl()) {
2830               PrivateCopies.push_back(nullptr);
2831               continue;
2832             }
2833             PrivateCopies.push_back(buildDeclRefExpr(
2834                 *this, VDPrivate, DE->getType(), DE->getExprLoc()));
2835           } else {
2836             // The variable is also a firstprivate, so initialization sequence
2837             // for private copy is generated already.
2838             PrivateCopies.push_back(nullptr);
2839           }
2840         }
2841         Clause->setPrivateCopies(PrivateCopies);
2842         continue;
2843       }
2844       // Finalize nontemporal clause by handling private copies, if any.
2845       if (auto *Clause = dyn_cast<OMPNontemporalClause>(C)) {
2846         SmallVector<Expr *, 8> PrivateRefs;
2847         for (Expr *RefExpr : Clause->varlists()) {
2848           assert(RefExpr && "NULL expr in OpenMP nontemporal clause.");
2849           SourceLocation ELoc;
2850           SourceRange ERange;
2851           Expr *SimpleRefExpr = RefExpr;
2852           auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
2853           if (Res.second)
2854             // It will be analyzed later.
2855             PrivateRefs.push_back(RefExpr);
2856           ValueDecl *D = Res.first;
2857           if (!D)
2858             continue;
2859 
2860           const DSAStackTy::DSAVarData DVar =
2861               DSAStack->getTopDSA(D, /*FromParent=*/false);
2862           PrivateRefs.push_back(DVar.PrivateCopy ? DVar.PrivateCopy
2863                                                  : SimpleRefExpr);
2864         }
2865         Clause->setPrivateRefs(PrivateRefs);
2866         continue;
2867       }
2868       if (auto *Clause = dyn_cast<OMPUsesAllocatorsClause>(C)) {
2869         for (unsigned I = 0, E = Clause->getNumberOfAllocators(); I < E; ++I) {
2870           OMPUsesAllocatorsClause::Data D = Clause->getAllocatorData(I);
2871           auto *DRE = dyn_cast<DeclRefExpr>(D.Allocator->IgnoreParenImpCasts());
2872           if (!DRE)
2873             continue;
2874           ValueDecl *VD = DRE->getDecl();
2875           if (!VD || !isa<VarDecl>(VD))
2876             continue;
2877           DSAStackTy::DSAVarData DVar =
2878               DSAStack->getTopDSA(VD, /*FromParent=*/false);
2879           // OpenMP [2.12.5, target Construct]
2880           // Memory allocators that appear in a uses_allocators clause cannot
2881           // appear in other data-sharing attribute clauses or data-mapping
2882           // attribute clauses in the same construct.
2883           Expr *MapExpr = nullptr;
2884           if (DVar.RefExpr ||
2885               DSAStack->checkMappableExprComponentListsForDecl(
2886                   VD, /*CurrentRegionOnly=*/true,
2887                   [VD, &MapExpr](
2888                       OMPClauseMappableExprCommon::MappableExprComponentListRef
2889                           MapExprComponents,
2890                       OpenMPClauseKind C) {
2891                     auto MI = MapExprComponents.rbegin();
2892                     auto ME = MapExprComponents.rend();
2893                     if (MI != ME &&
2894                         MI->getAssociatedDeclaration()->getCanonicalDecl() ==
2895                             VD->getCanonicalDecl()) {
2896                       MapExpr = MI->getAssociatedExpression();
2897                       return true;
2898                     }
2899                     return false;
2900                   })) {
2901             Diag(D.Allocator->getExprLoc(),
2902                  diag::err_omp_allocator_used_in_clauses)
2903                 << D.Allocator->getSourceRange();
2904             if (DVar.RefExpr)
2905               reportOriginalDsa(*this, DSAStack, VD, DVar);
2906             else
2907               Diag(MapExpr->getExprLoc(), diag::note_used_here)
2908                   << MapExpr->getSourceRange();
2909           }
2910         }
2911         continue;
2912       }
2913     }
2914     // Check allocate clauses.
2915     if (!CurContext->isDependentContext())
2916       checkAllocateClauses(*this, DSAStack, D->clauses());
2917     checkReductionClauses(*this, DSAStack, D->clauses());
2918   }
2919 
2920   DSAStack->pop();
2921   DiscardCleanupsInEvaluationContext();
2922   PopExpressionEvaluationContext();
2923 }
2924 
2925 static bool FinishOpenMPLinearClause(OMPLinearClause &Clause, DeclRefExpr *IV,
2926                                      Expr *NumIterations, Sema &SemaRef,
2927                                      Scope *S, DSAStackTy *Stack);
2928 
2929 namespace {
2930 
2931 class VarDeclFilterCCC final : public CorrectionCandidateCallback {
2932 private:
2933   Sema &SemaRef;
2934 
2935 public:
2936   explicit VarDeclFilterCCC(Sema &S) : SemaRef(S) {}
2937   bool ValidateCandidate(const TypoCorrection &Candidate) override {
2938     NamedDecl *ND = Candidate.getCorrectionDecl();
2939     if (const auto *VD = dyn_cast_or_null<VarDecl>(ND)) {
2940       return VD->hasGlobalStorage() &&
2941              SemaRef.isDeclInScope(ND, SemaRef.getCurLexicalContext(),
2942                                    SemaRef.getCurScope());
2943     }
2944     return false;
2945   }
2946 
2947   std::unique_ptr<CorrectionCandidateCallback> clone() override {
2948     return std::make_unique<VarDeclFilterCCC>(*this);
2949   }
2950 };
2951 
2952 class VarOrFuncDeclFilterCCC final : public CorrectionCandidateCallback {
2953 private:
2954   Sema &SemaRef;
2955 
2956 public:
2957   explicit VarOrFuncDeclFilterCCC(Sema &S) : SemaRef(S) {}
2958   bool ValidateCandidate(const TypoCorrection &Candidate) override {
2959     NamedDecl *ND = Candidate.getCorrectionDecl();
2960     if (ND && ((isa<VarDecl>(ND) && ND->getKind() == Decl::Var) ||
2961                isa<FunctionDecl>(ND))) {
2962       return SemaRef.isDeclInScope(ND, SemaRef.getCurLexicalContext(),
2963                                    SemaRef.getCurScope());
2964     }
2965     return false;
2966   }
2967 
2968   std::unique_ptr<CorrectionCandidateCallback> clone() override {
2969     return std::make_unique<VarOrFuncDeclFilterCCC>(*this);
2970   }
2971 };
2972 
2973 } // namespace
2974 
2975 ExprResult Sema::ActOnOpenMPIdExpression(Scope *CurScope,
2976                                          CXXScopeSpec &ScopeSpec,
2977                                          const DeclarationNameInfo &Id,
2978                                          OpenMPDirectiveKind Kind) {
2979   LookupResult Lookup(*this, Id, LookupOrdinaryName);
2980   LookupParsedName(Lookup, CurScope, &ScopeSpec, true);
2981 
2982   if (Lookup.isAmbiguous())
2983     return ExprError();
2984 
2985   VarDecl *VD;
2986   if (!Lookup.isSingleResult()) {
2987     VarDeclFilterCCC CCC(*this);
2988     if (TypoCorrection Corrected =
2989             CorrectTypo(Id, LookupOrdinaryName, CurScope, nullptr, CCC,
2990                         CTK_ErrorRecovery)) {
2991       diagnoseTypo(Corrected,
2992                    PDiag(Lookup.empty()
2993                              ? diag::err_undeclared_var_use_suggest
2994                              : diag::err_omp_expected_var_arg_suggest)
2995                        << Id.getName());
2996       VD = Corrected.getCorrectionDeclAs<VarDecl>();
2997     } else {
2998       Diag(Id.getLoc(), Lookup.empty() ? diag::err_undeclared_var_use
2999                                        : diag::err_omp_expected_var_arg)
3000           << Id.getName();
3001       return ExprError();
3002     }
3003   } else if (!(VD = Lookup.getAsSingle<VarDecl>())) {
3004     Diag(Id.getLoc(), diag::err_omp_expected_var_arg) << Id.getName();
3005     Diag(Lookup.getFoundDecl()->getLocation(), diag::note_declared_at);
3006     return ExprError();
3007   }
3008   Lookup.suppressDiagnostics();
3009 
3010   // OpenMP [2.9.2, Syntax, C/C++]
3011   //   Variables must be file-scope, namespace-scope, or static block-scope.
3012   if (Kind == OMPD_threadprivate && !VD->hasGlobalStorage()) {
3013     Diag(Id.getLoc(), diag::err_omp_global_var_arg)
3014         << getOpenMPDirectiveName(Kind) << !VD->isStaticLocal();
3015     bool IsDecl =
3016         VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3017     Diag(VD->getLocation(),
3018          IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3019         << VD;
3020     return ExprError();
3021   }
3022 
3023   VarDecl *CanonicalVD = VD->getCanonicalDecl();
3024   NamedDecl *ND = CanonicalVD;
3025   // OpenMP [2.9.2, Restrictions, C/C++, p.2]
3026   //   A threadprivate directive for file-scope variables must appear outside
3027   //   any definition or declaration.
3028   if (CanonicalVD->getDeclContext()->isTranslationUnit() &&
3029       !getCurLexicalContext()->isTranslationUnit()) {
3030     Diag(Id.getLoc(), diag::err_omp_var_scope)
3031         << getOpenMPDirectiveName(Kind) << VD;
3032     bool IsDecl =
3033         VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3034     Diag(VD->getLocation(),
3035          IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3036         << VD;
3037     return ExprError();
3038   }
3039   // OpenMP [2.9.2, Restrictions, C/C++, p.3]
3040   //   A threadprivate directive for static class member variables must appear
3041   //   in the class definition, in the same scope in which the member
3042   //   variables are declared.
3043   if (CanonicalVD->isStaticDataMember() &&
3044       !CanonicalVD->getDeclContext()->Equals(getCurLexicalContext())) {
3045     Diag(Id.getLoc(), diag::err_omp_var_scope)
3046         << getOpenMPDirectiveName(Kind) << VD;
3047     bool IsDecl =
3048         VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3049     Diag(VD->getLocation(),
3050          IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3051         << VD;
3052     return ExprError();
3053   }
3054   // OpenMP [2.9.2, Restrictions, C/C++, p.4]
3055   //   A threadprivate directive for namespace-scope variables must appear
3056   //   outside any definition or declaration other than the namespace
3057   //   definition itself.
3058   if (CanonicalVD->getDeclContext()->isNamespace() &&
3059       (!getCurLexicalContext()->isFileContext() ||
3060        !getCurLexicalContext()->Encloses(CanonicalVD->getDeclContext()))) {
3061     Diag(Id.getLoc(), diag::err_omp_var_scope)
3062         << getOpenMPDirectiveName(Kind) << VD;
3063     bool IsDecl =
3064         VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3065     Diag(VD->getLocation(),
3066          IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3067         << VD;
3068     return ExprError();
3069   }
3070   // OpenMP [2.9.2, Restrictions, C/C++, p.6]
3071   //   A threadprivate directive for static block-scope variables must appear
3072   //   in the scope of the variable and not in a nested scope.
3073   if (CanonicalVD->isLocalVarDecl() && CurScope &&
3074       !isDeclInScope(ND, getCurLexicalContext(), CurScope)) {
3075     Diag(Id.getLoc(), diag::err_omp_var_scope)
3076         << getOpenMPDirectiveName(Kind) << VD;
3077     bool IsDecl =
3078         VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3079     Diag(VD->getLocation(),
3080          IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3081         << VD;
3082     return ExprError();
3083   }
3084 
3085   // OpenMP [2.9.2, Restrictions, C/C++, p.2-6]
3086   //   A threadprivate directive must lexically precede all references to any
3087   //   of the variables in its list.
3088   if (Kind == OMPD_threadprivate && VD->isUsed() &&
3089       !DSAStack->isThreadPrivate(VD)) {
3090     Diag(Id.getLoc(), diag::err_omp_var_used)
3091         << getOpenMPDirectiveName(Kind) << VD;
3092     return ExprError();
3093   }
3094 
3095   QualType ExprType = VD->getType().getNonReferenceType();
3096   return DeclRefExpr::Create(Context, NestedNameSpecifierLoc(),
3097                              SourceLocation(), VD,
3098                              /*RefersToEnclosingVariableOrCapture=*/false,
3099                              Id.getLoc(), ExprType, VK_LValue);
3100 }
3101 
3102 Sema::DeclGroupPtrTy
3103 Sema::ActOnOpenMPThreadprivateDirective(SourceLocation Loc,
3104                                         ArrayRef<Expr *> VarList) {
3105   if (OMPThreadPrivateDecl *D = CheckOMPThreadPrivateDecl(Loc, VarList)) {
3106     CurContext->addDecl(D);
3107     return DeclGroupPtrTy::make(DeclGroupRef(D));
3108   }
3109   return nullptr;
3110 }
3111 
3112 namespace {
3113 class LocalVarRefChecker final
3114     : public ConstStmtVisitor<LocalVarRefChecker, bool> {
3115   Sema &SemaRef;
3116 
3117 public:
3118   bool VisitDeclRefExpr(const DeclRefExpr *E) {
3119     if (const auto *VD = dyn_cast<VarDecl>(E->getDecl())) {
3120       if (VD->hasLocalStorage()) {
3121         SemaRef.Diag(E->getBeginLoc(),
3122                      diag::err_omp_local_var_in_threadprivate_init)
3123             << E->getSourceRange();
3124         SemaRef.Diag(VD->getLocation(), diag::note_defined_here)
3125             << VD << VD->getSourceRange();
3126         return true;
3127       }
3128     }
3129     return false;
3130   }
3131   bool VisitStmt(const Stmt *S) {
3132     for (const Stmt *Child : S->children()) {
3133       if (Child && Visit(Child))
3134         return true;
3135     }
3136     return false;
3137   }
3138   explicit LocalVarRefChecker(Sema &SemaRef) : SemaRef(SemaRef) {}
3139 };
3140 } // namespace
3141 
3142 OMPThreadPrivateDecl *
3143 Sema::CheckOMPThreadPrivateDecl(SourceLocation Loc, ArrayRef<Expr *> VarList) {
3144   SmallVector<Expr *, 8> Vars;
3145   for (Expr *RefExpr : VarList) {
3146     auto *DE = cast<DeclRefExpr>(RefExpr);
3147     auto *VD = cast<VarDecl>(DE->getDecl());
3148     SourceLocation ILoc = DE->getExprLoc();
3149 
3150     // Mark variable as used.
3151     VD->setReferenced();
3152     VD->markUsed(Context);
3153 
3154     QualType QType = VD->getType();
3155     if (QType->isDependentType() || QType->isInstantiationDependentType()) {
3156       // It will be analyzed later.
3157       Vars.push_back(DE);
3158       continue;
3159     }
3160 
3161     // OpenMP [2.9.2, Restrictions, C/C++, p.10]
3162     //   A threadprivate variable must not have an incomplete type.
3163     if (RequireCompleteType(ILoc, VD->getType(),
3164                             diag::err_omp_threadprivate_incomplete_type)) {
3165       continue;
3166     }
3167 
3168     // OpenMP [2.9.2, Restrictions, C/C++, p.10]
3169     //   A threadprivate variable must not have a reference type.
3170     if (VD->getType()->isReferenceType()) {
3171       Diag(ILoc, diag::err_omp_ref_type_arg)
3172           << getOpenMPDirectiveName(OMPD_threadprivate) << VD->getType();
3173       bool IsDecl =
3174           VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3175       Diag(VD->getLocation(),
3176            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3177           << VD;
3178       continue;
3179     }
3180 
3181     // Check if this is a TLS variable. If TLS is not being supported, produce
3182     // the corresponding diagnostic.
3183     if ((VD->getTLSKind() != VarDecl::TLS_None &&
3184          !(VD->hasAttr<OMPThreadPrivateDeclAttr>() &&
3185            getLangOpts().OpenMPUseTLS &&
3186            getASTContext().getTargetInfo().isTLSSupported())) ||
3187         (VD->getStorageClass() == SC_Register && VD->hasAttr<AsmLabelAttr>() &&
3188          !VD->isLocalVarDecl())) {
3189       Diag(ILoc, diag::err_omp_var_thread_local)
3190           << VD << ((VD->getTLSKind() != VarDecl::TLS_None) ? 0 : 1);
3191       bool IsDecl =
3192           VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly;
3193       Diag(VD->getLocation(),
3194            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3195           << VD;
3196       continue;
3197     }
3198 
3199     // Check if initial value of threadprivate variable reference variable with
3200     // local storage (it is not supported by runtime).
3201     if (const Expr *Init = VD->getAnyInitializer()) {
3202       LocalVarRefChecker Checker(*this);
3203       if (Checker.Visit(Init))
3204         continue;
3205     }
3206 
3207     Vars.push_back(RefExpr);
3208     DSAStack->addDSA(VD, DE, OMPC_threadprivate);
3209     VD->addAttr(OMPThreadPrivateDeclAttr::CreateImplicit(
3210         Context, SourceRange(Loc, Loc)));
3211     if (ASTMutationListener *ML = Context.getASTMutationListener())
3212       ML->DeclarationMarkedOpenMPThreadPrivate(VD);
3213   }
3214   OMPThreadPrivateDecl *D = nullptr;
3215   if (!Vars.empty()) {
3216     D = OMPThreadPrivateDecl::Create(Context, getCurLexicalContext(), Loc,
3217                                      Vars);
3218     D->setAccess(AS_public);
3219   }
3220   return D;
3221 }
3222 
3223 static OMPAllocateDeclAttr::AllocatorTypeTy
3224 getAllocatorKind(Sema &S, DSAStackTy *Stack, Expr *Allocator) {
3225   if (!Allocator)
3226     return OMPAllocateDeclAttr::OMPNullMemAlloc;
3227   if (Allocator->isTypeDependent() || Allocator->isValueDependent() ||
3228       Allocator->isInstantiationDependent() ||
3229       Allocator->containsUnexpandedParameterPack())
3230     return OMPAllocateDeclAttr::OMPUserDefinedMemAlloc;
3231   auto AllocatorKindRes = OMPAllocateDeclAttr::OMPUserDefinedMemAlloc;
3232   const Expr *AE = Allocator->IgnoreParenImpCasts();
3233   for (int I = 0; I < OMPAllocateDeclAttr::OMPUserDefinedMemAlloc; ++I) {
3234     auto AllocatorKind = static_cast<OMPAllocateDeclAttr::AllocatorTypeTy>(I);
3235     const Expr *DefAllocator = Stack->getAllocator(AllocatorKind);
3236     llvm::FoldingSetNodeID AEId, DAEId;
3237     AE->Profile(AEId, S.getASTContext(), /*Canonical=*/true);
3238     DefAllocator->Profile(DAEId, S.getASTContext(), /*Canonical=*/true);
3239     if (AEId == DAEId) {
3240       AllocatorKindRes = AllocatorKind;
3241       break;
3242     }
3243   }
3244   return AllocatorKindRes;
3245 }
3246 
3247 static bool checkPreviousOMPAllocateAttribute(
3248     Sema &S, DSAStackTy *Stack, Expr *RefExpr, VarDecl *VD,
3249     OMPAllocateDeclAttr::AllocatorTypeTy AllocatorKind, Expr *Allocator) {
3250   if (!VD->hasAttr<OMPAllocateDeclAttr>())
3251     return false;
3252   const auto *A = VD->getAttr<OMPAllocateDeclAttr>();
3253   Expr *PrevAllocator = A->getAllocator();
3254   OMPAllocateDeclAttr::AllocatorTypeTy PrevAllocatorKind =
3255       getAllocatorKind(S, Stack, PrevAllocator);
3256   bool AllocatorsMatch = AllocatorKind == PrevAllocatorKind;
3257   if (AllocatorsMatch &&
3258       AllocatorKind == OMPAllocateDeclAttr::OMPUserDefinedMemAlloc &&
3259       Allocator && PrevAllocator) {
3260     const Expr *AE = Allocator->IgnoreParenImpCasts();
3261     const Expr *PAE = PrevAllocator->IgnoreParenImpCasts();
3262     llvm::FoldingSetNodeID AEId, PAEId;
3263     AE->Profile(AEId, S.Context, /*Canonical=*/true);
3264     PAE->Profile(PAEId, S.Context, /*Canonical=*/true);
3265     AllocatorsMatch = AEId == PAEId;
3266   }
3267   if (!AllocatorsMatch) {
3268     SmallString<256> AllocatorBuffer;
3269     llvm::raw_svector_ostream AllocatorStream(AllocatorBuffer);
3270     if (Allocator)
3271       Allocator->printPretty(AllocatorStream, nullptr, S.getPrintingPolicy());
3272     SmallString<256> PrevAllocatorBuffer;
3273     llvm::raw_svector_ostream PrevAllocatorStream(PrevAllocatorBuffer);
3274     if (PrevAllocator)
3275       PrevAllocator->printPretty(PrevAllocatorStream, nullptr,
3276                                  S.getPrintingPolicy());
3277 
3278     SourceLocation AllocatorLoc =
3279         Allocator ? Allocator->getExprLoc() : RefExpr->getExprLoc();
3280     SourceRange AllocatorRange =
3281         Allocator ? Allocator->getSourceRange() : RefExpr->getSourceRange();
3282     SourceLocation PrevAllocatorLoc =
3283         PrevAllocator ? PrevAllocator->getExprLoc() : A->getLocation();
3284     SourceRange PrevAllocatorRange =
3285         PrevAllocator ? PrevAllocator->getSourceRange() : A->getRange();
3286     S.Diag(AllocatorLoc, diag::warn_omp_used_different_allocator)
3287         << (Allocator ? 1 : 0) << AllocatorStream.str()
3288         << (PrevAllocator ? 1 : 0) << PrevAllocatorStream.str()
3289         << AllocatorRange;
3290     S.Diag(PrevAllocatorLoc, diag::note_omp_previous_allocator)
3291         << PrevAllocatorRange;
3292     return true;
3293   }
3294   return false;
3295 }
3296 
3297 static void
3298 applyOMPAllocateAttribute(Sema &S, VarDecl *VD,
3299                           OMPAllocateDeclAttr::AllocatorTypeTy AllocatorKind,
3300                           Expr *Allocator, Expr *Alignment, SourceRange SR) {
3301   if (VD->hasAttr<OMPAllocateDeclAttr>())
3302     return;
3303   if (Alignment &&
3304       (Alignment->isTypeDependent() || Alignment->isValueDependent() ||
3305        Alignment->isInstantiationDependent() ||
3306        Alignment->containsUnexpandedParameterPack()))
3307     // Apply later when we have a usable value.
3308     return;
3309   if (Allocator &&
3310       (Allocator->isTypeDependent() || Allocator->isValueDependent() ||
3311        Allocator->isInstantiationDependent() ||
3312        Allocator->containsUnexpandedParameterPack()))
3313     return;
3314   auto *A = OMPAllocateDeclAttr::CreateImplicit(S.Context, AllocatorKind,
3315                                                 Allocator, Alignment, SR);
3316   VD->addAttr(A);
3317   if (ASTMutationListener *ML = S.Context.getASTMutationListener())
3318     ML->DeclarationMarkedOpenMPAllocate(VD, A);
3319 }
3320 
3321 Sema::DeclGroupPtrTy
3322 Sema::ActOnOpenMPAllocateDirective(SourceLocation Loc, ArrayRef<Expr *> VarList,
3323                                    ArrayRef<OMPClause *> Clauses,
3324                                    DeclContext *Owner) {
3325   assert(Clauses.size() <= 2 && "Expected at most two clauses.");
3326   Expr *Alignment = nullptr;
3327   Expr *Allocator = nullptr;
3328   if (Clauses.empty()) {
3329     // OpenMP 5.0, 2.11.3 allocate Directive, Restrictions.
3330     // allocate directives that appear in a target region must specify an
3331     // allocator clause unless a requires directive with the dynamic_allocators
3332     // clause is present in the same compilation unit.
3333     if (LangOpts.OpenMPIsDevice &&
3334         !DSAStack->hasRequiresDeclWithClause<OMPDynamicAllocatorsClause>())
3335       targetDiag(Loc, diag::err_expected_allocator_clause);
3336   } else {
3337     for (const OMPClause *C : Clauses)
3338       if (const auto *AC = dyn_cast<OMPAllocatorClause>(C))
3339         Allocator = AC->getAllocator();
3340       else if (const auto *AC = dyn_cast<OMPAlignClause>(C))
3341         Alignment = AC->getAlignment();
3342       else
3343         llvm_unreachable("Unexpected clause on allocate directive");
3344   }
3345   OMPAllocateDeclAttr::AllocatorTypeTy AllocatorKind =
3346       getAllocatorKind(*this, DSAStack, Allocator);
3347   SmallVector<Expr *, 8> Vars;
3348   for (Expr *RefExpr : VarList) {
3349     auto *DE = cast<DeclRefExpr>(RefExpr);
3350     auto *VD = cast<VarDecl>(DE->getDecl());
3351 
3352     // Check if this is a TLS variable or global register.
3353     if (VD->getTLSKind() != VarDecl::TLS_None ||
3354         VD->hasAttr<OMPThreadPrivateDeclAttr>() ||
3355         (VD->getStorageClass() == SC_Register && VD->hasAttr<AsmLabelAttr>() &&
3356          !VD->isLocalVarDecl()))
3357       continue;
3358 
3359     // If the used several times in the allocate directive, the same allocator
3360     // must be used.
3361     if (checkPreviousOMPAllocateAttribute(*this, DSAStack, RefExpr, VD,
3362                                           AllocatorKind, Allocator))
3363       continue;
3364 
3365     // OpenMP, 2.11.3 allocate Directive, Restrictions, C / C++
3366     // If a list item has a static storage type, the allocator expression in the
3367     // allocator clause must be a constant expression that evaluates to one of
3368     // the predefined memory allocator values.
3369     if (Allocator && VD->hasGlobalStorage()) {
3370       if (AllocatorKind == OMPAllocateDeclAttr::OMPUserDefinedMemAlloc) {
3371         Diag(Allocator->getExprLoc(),
3372              diag::err_omp_expected_predefined_allocator)
3373             << Allocator->getSourceRange();
3374         bool IsDecl = VD->isThisDeclarationADefinition(Context) ==
3375                       VarDecl::DeclarationOnly;
3376         Diag(VD->getLocation(),
3377              IsDecl ? diag::note_previous_decl : diag::note_defined_here)
3378             << VD;
3379         continue;
3380       }
3381     }
3382 
3383     Vars.push_back(RefExpr);
3384     applyOMPAllocateAttribute(*this, VD, AllocatorKind, Allocator, Alignment,
3385                               DE->getSourceRange());
3386   }
3387   if (Vars.empty())
3388     return nullptr;
3389   if (!Owner)
3390     Owner = getCurLexicalContext();
3391   auto *D = OMPAllocateDecl::Create(Context, Owner, Loc, Vars, Clauses);
3392   D->setAccess(AS_public);
3393   Owner->addDecl(D);
3394   return DeclGroupPtrTy::make(DeclGroupRef(D));
3395 }
3396 
3397 Sema::DeclGroupPtrTy
3398 Sema::ActOnOpenMPRequiresDirective(SourceLocation Loc,
3399                                    ArrayRef<OMPClause *> ClauseList) {
3400   OMPRequiresDecl *D = nullptr;
3401   if (!CurContext->isFileContext()) {
3402     Diag(Loc, diag::err_omp_invalid_scope) << "requires";
3403   } else {
3404     D = CheckOMPRequiresDecl(Loc, ClauseList);
3405     if (D) {
3406       CurContext->addDecl(D);
3407       DSAStack->addRequiresDecl(D);
3408     }
3409   }
3410   return DeclGroupPtrTy::make(DeclGroupRef(D));
3411 }
3412 
3413 void Sema::ActOnOpenMPAssumesDirective(SourceLocation Loc,
3414                                        OpenMPDirectiveKind DKind,
3415                                        ArrayRef<std::string> Assumptions,
3416                                        bool SkippedClauses) {
3417   if (!SkippedClauses && Assumptions.empty())
3418     Diag(Loc, diag::err_omp_no_clause_for_directive)
3419         << llvm::omp::getAllAssumeClauseOptions()
3420         << llvm::omp::getOpenMPDirectiveName(DKind);
3421 
3422   auto *AA = AssumptionAttr::Create(Context, llvm::join(Assumptions, ","), Loc);
3423   if (DKind == llvm::omp::Directive::OMPD_begin_assumes) {
3424     OMPAssumeScoped.push_back(AA);
3425     return;
3426   }
3427 
3428   // Global assumes without assumption clauses are ignored.
3429   if (Assumptions.empty())
3430     return;
3431 
3432   assert(DKind == llvm::omp::Directive::OMPD_assumes &&
3433          "Unexpected omp assumption directive!");
3434   OMPAssumeGlobal.push_back(AA);
3435 
3436   // The OMPAssumeGlobal scope above will take care of new declarations but
3437   // we also want to apply the assumption to existing ones, e.g., to
3438   // declarations in included headers. To this end, we traverse all existing
3439   // declaration contexts and annotate function declarations here.
3440   SmallVector<DeclContext *, 8> DeclContexts;
3441   auto *Ctx = CurContext;
3442   while (Ctx->getLexicalParent())
3443     Ctx = Ctx->getLexicalParent();
3444   DeclContexts.push_back(Ctx);
3445   while (!DeclContexts.empty()) {
3446     DeclContext *DC = DeclContexts.pop_back_val();
3447     for (auto *SubDC : DC->decls()) {
3448       if (SubDC->isInvalidDecl())
3449         continue;
3450       if (auto *CTD = dyn_cast<ClassTemplateDecl>(SubDC)) {
3451         DeclContexts.push_back(CTD->getTemplatedDecl());
3452         llvm::append_range(DeclContexts, CTD->specializations());
3453         continue;
3454       }
3455       if (auto *DC = dyn_cast<DeclContext>(SubDC))
3456         DeclContexts.push_back(DC);
3457       if (auto *F = dyn_cast<FunctionDecl>(SubDC)) {
3458         F->addAttr(AA);
3459         continue;
3460       }
3461     }
3462   }
3463 }
3464 
3465 void Sema::ActOnOpenMPEndAssumesDirective() {
3466   assert(isInOpenMPAssumeScope() && "Not in OpenMP assumes scope!");
3467   OMPAssumeScoped.pop_back();
3468 }
3469 
3470 OMPRequiresDecl *Sema::CheckOMPRequiresDecl(SourceLocation Loc,
3471                                             ArrayRef<OMPClause *> ClauseList) {
3472   /// For target specific clauses, the requires directive cannot be
3473   /// specified after the handling of any of the target regions in the
3474   /// current compilation unit.
3475   ArrayRef<SourceLocation> TargetLocations =
3476       DSAStack->getEncounteredTargetLocs();
3477   SourceLocation AtomicLoc = DSAStack->getAtomicDirectiveLoc();
3478   if (!TargetLocations.empty() || !AtomicLoc.isInvalid()) {
3479     for (const OMPClause *CNew : ClauseList) {
3480       // Check if any of the requires clauses affect target regions.
3481       if (isa<OMPUnifiedSharedMemoryClause>(CNew) ||
3482           isa<OMPUnifiedAddressClause>(CNew) ||
3483           isa<OMPReverseOffloadClause>(CNew) ||
3484           isa<OMPDynamicAllocatorsClause>(CNew)) {
3485         Diag(Loc, diag::err_omp_directive_before_requires)
3486             << "target" << getOpenMPClauseName(CNew->getClauseKind());
3487         for (SourceLocation TargetLoc : TargetLocations) {
3488           Diag(TargetLoc, diag::note_omp_requires_encountered_directive)
3489               << "target";
3490         }
3491       } else if (!AtomicLoc.isInvalid() &&
3492                  isa<OMPAtomicDefaultMemOrderClause>(CNew)) {
3493         Diag(Loc, diag::err_omp_directive_before_requires)
3494             << "atomic" << getOpenMPClauseName(CNew->getClauseKind());
3495         Diag(AtomicLoc, diag::note_omp_requires_encountered_directive)
3496             << "atomic";
3497       }
3498     }
3499   }
3500 
3501   if (!DSAStack->hasDuplicateRequiresClause(ClauseList))
3502     return OMPRequiresDecl::Create(Context, getCurLexicalContext(), Loc,
3503                                    ClauseList);
3504   return nullptr;
3505 }
3506 
3507 static void reportOriginalDsa(Sema &SemaRef, const DSAStackTy *Stack,
3508                               const ValueDecl *D,
3509                               const DSAStackTy::DSAVarData &DVar,
3510                               bool IsLoopIterVar) {
3511   if (DVar.RefExpr) {
3512     SemaRef.Diag(DVar.RefExpr->getExprLoc(), diag::note_omp_explicit_dsa)
3513         << getOpenMPClauseName(DVar.CKind);
3514     return;
3515   }
3516   enum {
3517     PDSA_StaticMemberShared,
3518     PDSA_StaticLocalVarShared,
3519     PDSA_LoopIterVarPrivate,
3520     PDSA_LoopIterVarLinear,
3521     PDSA_LoopIterVarLastprivate,
3522     PDSA_ConstVarShared,
3523     PDSA_GlobalVarShared,
3524     PDSA_TaskVarFirstprivate,
3525     PDSA_LocalVarPrivate,
3526     PDSA_Implicit
3527   } Reason = PDSA_Implicit;
3528   bool ReportHint = false;
3529   auto ReportLoc = D->getLocation();
3530   auto *VD = dyn_cast<VarDecl>(D);
3531   if (IsLoopIterVar) {
3532     if (DVar.CKind == OMPC_private)
3533       Reason = PDSA_LoopIterVarPrivate;
3534     else if (DVar.CKind == OMPC_lastprivate)
3535       Reason = PDSA_LoopIterVarLastprivate;
3536     else
3537       Reason = PDSA_LoopIterVarLinear;
3538   } else if (isOpenMPTaskingDirective(DVar.DKind) &&
3539              DVar.CKind == OMPC_firstprivate) {
3540     Reason = PDSA_TaskVarFirstprivate;
3541     ReportLoc = DVar.ImplicitDSALoc;
3542   } else if (VD && VD->isStaticLocal())
3543     Reason = PDSA_StaticLocalVarShared;
3544   else if (VD && VD->isStaticDataMember())
3545     Reason = PDSA_StaticMemberShared;
3546   else if (VD && VD->isFileVarDecl())
3547     Reason = PDSA_GlobalVarShared;
3548   else if (D->getType().isConstant(SemaRef.getASTContext()))
3549     Reason = PDSA_ConstVarShared;
3550   else if (VD && VD->isLocalVarDecl() && DVar.CKind == OMPC_private) {
3551     ReportHint = true;
3552     Reason = PDSA_LocalVarPrivate;
3553   }
3554   if (Reason != PDSA_Implicit) {
3555     SemaRef.Diag(ReportLoc, diag::note_omp_predetermined_dsa)
3556         << Reason << ReportHint
3557         << getOpenMPDirectiveName(Stack->getCurrentDirective());
3558   } else if (DVar.ImplicitDSALoc.isValid()) {
3559     SemaRef.Diag(DVar.ImplicitDSALoc, diag::note_omp_implicit_dsa)
3560         << getOpenMPClauseName(DVar.CKind);
3561   }
3562 }
3563 
3564 static OpenMPMapClauseKind
3565 getMapClauseKindFromModifier(OpenMPDefaultmapClauseModifier M,
3566                              bool IsAggregateOrDeclareTarget) {
3567   OpenMPMapClauseKind Kind = OMPC_MAP_unknown;
3568   switch (M) {
3569   case OMPC_DEFAULTMAP_MODIFIER_alloc:
3570     Kind = OMPC_MAP_alloc;
3571     break;
3572   case OMPC_DEFAULTMAP_MODIFIER_to:
3573     Kind = OMPC_MAP_to;
3574     break;
3575   case OMPC_DEFAULTMAP_MODIFIER_from:
3576     Kind = OMPC_MAP_from;
3577     break;
3578   case OMPC_DEFAULTMAP_MODIFIER_tofrom:
3579     Kind = OMPC_MAP_tofrom;
3580     break;
3581   case OMPC_DEFAULTMAP_MODIFIER_present:
3582     // OpenMP 5.1 [2.21.7.3] defaultmap clause, Description]
3583     // If implicit-behavior is present, each variable referenced in the
3584     // construct in the category specified by variable-category is treated as if
3585     // it had been listed in a map clause with the map-type of alloc and
3586     // map-type-modifier of present.
3587     Kind = OMPC_MAP_alloc;
3588     break;
3589   case OMPC_DEFAULTMAP_MODIFIER_firstprivate:
3590   case OMPC_DEFAULTMAP_MODIFIER_last:
3591     llvm_unreachable("Unexpected defaultmap implicit behavior");
3592   case OMPC_DEFAULTMAP_MODIFIER_none:
3593   case OMPC_DEFAULTMAP_MODIFIER_default:
3594   case OMPC_DEFAULTMAP_MODIFIER_unknown:
3595     // IsAggregateOrDeclareTarget could be true if:
3596     // 1. the implicit behavior for aggregate is tofrom
3597     // 2. it's a declare target link
3598     if (IsAggregateOrDeclareTarget) {
3599       Kind = OMPC_MAP_tofrom;
3600       break;
3601     }
3602     llvm_unreachable("Unexpected defaultmap implicit behavior");
3603   }
3604   assert(Kind != OMPC_MAP_unknown && "Expect map kind to be known");
3605   return Kind;
3606 }
3607 
3608 namespace {
3609 class DSAAttrChecker final : public StmtVisitor<DSAAttrChecker, void> {
3610   DSAStackTy *Stack;
3611   Sema &SemaRef;
3612   bool ErrorFound = false;
3613   bool TryCaptureCXXThisMembers = false;
3614   CapturedStmt *CS = nullptr;
3615   const static unsigned DefaultmapKindNum = OMPC_DEFAULTMAP_pointer + 1;
3616   llvm::SmallVector<Expr *, 4> ImplicitFirstprivate;
3617   llvm::SmallVector<Expr *, 4> ImplicitPrivate;
3618   llvm::SmallVector<Expr *, 4> ImplicitMap[DefaultmapKindNum][OMPC_MAP_delete];
3619   llvm::SmallVector<OpenMPMapModifierKind, NumberOfOMPMapClauseModifiers>
3620       ImplicitMapModifier[DefaultmapKindNum];
3621   Sema::VarsWithInheritedDSAType VarsWithInheritedDSA;
3622   llvm::SmallDenseSet<const ValueDecl *, 4> ImplicitDeclarations;
3623 
3624   void VisitSubCaptures(OMPExecutableDirective *S) {
3625     // Check implicitly captured variables.
3626     if (!S->hasAssociatedStmt() || !S->getAssociatedStmt())
3627       return;
3628     if (S->getDirectiveKind() == OMPD_atomic ||
3629         S->getDirectiveKind() == OMPD_critical ||
3630         S->getDirectiveKind() == OMPD_section ||
3631         S->getDirectiveKind() == OMPD_master ||
3632         S->getDirectiveKind() == OMPD_masked ||
3633         isOpenMPLoopTransformationDirective(S->getDirectiveKind())) {
3634       Visit(S->getAssociatedStmt());
3635       return;
3636     }
3637     visitSubCaptures(S->getInnermostCapturedStmt());
3638     // Try to capture inner this->member references to generate correct mappings
3639     // and diagnostics.
3640     if (TryCaptureCXXThisMembers ||
3641         (isOpenMPTargetExecutionDirective(Stack->getCurrentDirective()) &&
3642          llvm::any_of(S->getInnermostCapturedStmt()->captures(),
3643                       [](const CapturedStmt::Capture &C) {
3644                         return C.capturesThis();
3645                       }))) {
3646       bool SavedTryCaptureCXXThisMembers = TryCaptureCXXThisMembers;
3647       TryCaptureCXXThisMembers = true;
3648       Visit(S->getInnermostCapturedStmt()->getCapturedStmt());
3649       TryCaptureCXXThisMembers = SavedTryCaptureCXXThisMembers;
3650     }
3651     // In tasks firstprivates are not captured anymore, need to analyze them
3652     // explicitly.
3653     if (isOpenMPTaskingDirective(S->getDirectiveKind()) &&
3654         !isOpenMPTaskLoopDirective(S->getDirectiveKind())) {
3655       for (OMPClause *C : S->clauses())
3656         if (auto *FC = dyn_cast<OMPFirstprivateClause>(C)) {
3657           for (Expr *Ref : FC->varlists())
3658             Visit(Ref);
3659         }
3660     }
3661   }
3662 
3663 public:
3664   void VisitDeclRefExpr(DeclRefExpr *E) {
3665     if (TryCaptureCXXThisMembers || E->isTypeDependent() ||
3666         E->isValueDependent() || E->containsUnexpandedParameterPack() ||
3667         E->isInstantiationDependent())
3668       return;
3669     if (auto *VD = dyn_cast<VarDecl>(E->getDecl())) {
3670       // Check the datasharing rules for the expressions in the clauses.
3671       if (!CS || (isa<OMPCapturedExprDecl>(VD) && !CS->capturesVariable(VD) &&
3672                   !Stack->getTopDSA(VD, /*FromParent=*/false).RefExpr &&
3673                   !Stack->isImplicitDefaultFirstprivateFD(VD))) {
3674         if (auto *CED = dyn_cast<OMPCapturedExprDecl>(VD))
3675           if (!CED->hasAttr<OMPCaptureNoInitAttr>()) {
3676             Visit(CED->getInit());
3677             return;
3678           }
3679       } else if (VD->isImplicit() || isa<OMPCapturedExprDecl>(VD))
3680         // Do not analyze internal variables and do not enclose them into
3681         // implicit clauses.
3682         if (!Stack->isImplicitDefaultFirstprivateFD(VD))
3683           return;
3684       VD = VD->getCanonicalDecl();
3685       // Skip internally declared variables.
3686       if (VD->hasLocalStorage() && CS && !CS->capturesVariable(VD) &&
3687           !Stack->isImplicitDefaultFirstprivateFD(VD) &&
3688           !Stack->isImplicitTaskFirstprivate(VD))
3689         return;
3690       // Skip allocators in uses_allocators clauses.
3691       if (Stack->isUsesAllocatorsDecl(VD))
3692         return;
3693 
3694       DSAStackTy::DSAVarData DVar = Stack->getTopDSA(VD, /*FromParent=*/false);
3695       // Check if the variable has explicit DSA set and stop analysis if it so.
3696       if (DVar.RefExpr || !ImplicitDeclarations.insert(VD).second)
3697         return;
3698 
3699       // Skip internally declared static variables.
3700       llvm::Optional<OMPDeclareTargetDeclAttr::MapTypeTy> Res =
3701           OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(VD);
3702       if (VD->hasGlobalStorage() && CS && !CS->capturesVariable(VD) &&
3703           (Stack->hasRequiresDeclWithClause<OMPUnifiedSharedMemoryClause>() ||
3704            !Res || *Res != OMPDeclareTargetDeclAttr::MT_Link) &&
3705           !Stack->isImplicitDefaultFirstprivateFD(VD) &&
3706           !Stack->isImplicitTaskFirstprivate(VD))
3707         return;
3708 
3709       SourceLocation ELoc = E->getExprLoc();
3710       OpenMPDirectiveKind DKind = Stack->getCurrentDirective();
3711       // The default(none) clause requires that each variable that is referenced
3712       // in the construct, and does not have a predetermined data-sharing
3713       // attribute, must have its data-sharing attribute explicitly determined
3714       // by being listed in a data-sharing attribute clause.
3715       if (DVar.CKind == OMPC_unknown &&
3716           (Stack->getDefaultDSA() == DSA_none ||
3717            Stack->getDefaultDSA() == DSA_private ||
3718            Stack->getDefaultDSA() == DSA_firstprivate) &&
3719           isImplicitOrExplicitTaskingRegion(DKind) &&
3720           VarsWithInheritedDSA.count(VD) == 0) {
3721         bool InheritedDSA = Stack->getDefaultDSA() == DSA_none;
3722         if (!InheritedDSA && (Stack->getDefaultDSA() == DSA_firstprivate ||
3723                               Stack->getDefaultDSA() == DSA_private)) {
3724           DSAStackTy::DSAVarData DVar =
3725               Stack->getImplicitDSA(VD, /*FromParent=*/false);
3726           InheritedDSA = DVar.CKind == OMPC_unknown;
3727         }
3728         if (InheritedDSA)
3729           VarsWithInheritedDSA[VD] = E;
3730         if (Stack->getDefaultDSA() == DSA_none)
3731           return;
3732       }
3733 
3734       // OpenMP 5.0 [2.19.7.2, defaultmap clause, Description]
3735       // If implicit-behavior is none, each variable referenced in the
3736       // construct that does not have a predetermined data-sharing attribute
3737       // and does not appear in a to or link clause on a declare target
3738       // directive must be listed in a data-mapping attribute clause, a
3739       // data-sharing attribute clause (including a data-sharing attribute
3740       // clause on a combined construct where target. is one of the
3741       // constituent constructs), or an is_device_ptr clause.
3742       OpenMPDefaultmapClauseKind ClauseKind =
3743           getVariableCategoryFromDecl(SemaRef.getLangOpts(), VD);
3744       if (SemaRef.getLangOpts().OpenMP >= 50) {
3745         bool IsModifierNone = Stack->getDefaultmapModifier(ClauseKind) ==
3746                               OMPC_DEFAULTMAP_MODIFIER_none;
3747         if (DVar.CKind == OMPC_unknown && IsModifierNone &&
3748             VarsWithInheritedDSA.count(VD) == 0 && !Res) {
3749           // Only check for data-mapping attribute and is_device_ptr here
3750           // since we have already make sure that the declaration does not
3751           // have a data-sharing attribute above
3752           if (!Stack->checkMappableExprComponentListsForDecl(
3753                   VD, /*CurrentRegionOnly=*/true,
3754                   [VD](OMPClauseMappableExprCommon::MappableExprComponentListRef
3755                            MapExprComponents,
3756                        OpenMPClauseKind) {
3757                     auto MI = MapExprComponents.rbegin();
3758                     auto ME = MapExprComponents.rend();
3759                     return MI != ME && MI->getAssociatedDeclaration() == VD;
3760                   })) {
3761             VarsWithInheritedDSA[VD] = E;
3762             return;
3763           }
3764         }
3765       }
3766       if (SemaRef.getLangOpts().OpenMP > 50) {
3767         bool IsModifierPresent = Stack->getDefaultmapModifier(ClauseKind) ==
3768                                  OMPC_DEFAULTMAP_MODIFIER_present;
3769         if (IsModifierPresent) {
3770           if (llvm::find(ImplicitMapModifier[ClauseKind],
3771                          OMPC_MAP_MODIFIER_present) ==
3772               std::end(ImplicitMapModifier[ClauseKind])) {
3773             ImplicitMapModifier[ClauseKind].push_back(
3774                 OMPC_MAP_MODIFIER_present);
3775           }
3776         }
3777       }
3778 
3779       if (isOpenMPTargetExecutionDirective(DKind) &&
3780           !Stack->isLoopControlVariable(VD).first) {
3781         if (!Stack->checkMappableExprComponentListsForDecl(
3782                 VD, /*CurrentRegionOnly=*/true,
3783                 [this](OMPClauseMappableExprCommon::MappableExprComponentListRef
3784                            StackComponents,
3785                        OpenMPClauseKind) {
3786                   if (SemaRef.LangOpts.OpenMP >= 50)
3787                     return !StackComponents.empty();
3788                   // Variable is used if it has been marked as an array, array
3789                   // section, array shaping or the variable iself.
3790                   return StackComponents.size() == 1 ||
3791                          std::all_of(
3792                              std::next(StackComponents.rbegin()),
3793                              StackComponents.rend(),
3794                              [](const OMPClauseMappableExprCommon::
3795                                     MappableComponent &MC) {
3796                                return MC.getAssociatedDeclaration() ==
3797                                           nullptr &&
3798                                       (isa<OMPArraySectionExpr>(
3799                                            MC.getAssociatedExpression()) ||
3800                                        isa<OMPArrayShapingExpr>(
3801                                            MC.getAssociatedExpression()) ||
3802                                        isa<ArraySubscriptExpr>(
3803                                            MC.getAssociatedExpression()));
3804                              });
3805                 })) {
3806           bool IsFirstprivate = false;
3807           // By default lambdas are captured as firstprivates.
3808           if (const auto *RD =
3809                   VD->getType().getNonReferenceType()->getAsCXXRecordDecl())
3810             IsFirstprivate = RD->isLambda();
3811           IsFirstprivate =
3812               IsFirstprivate || (Stack->mustBeFirstprivate(ClauseKind) && !Res);
3813           if (IsFirstprivate) {
3814             ImplicitFirstprivate.emplace_back(E);
3815           } else {
3816             OpenMPDefaultmapClauseModifier M =
3817                 Stack->getDefaultmapModifier(ClauseKind);
3818             OpenMPMapClauseKind Kind = getMapClauseKindFromModifier(
3819                 M, ClauseKind == OMPC_DEFAULTMAP_aggregate || Res);
3820             ImplicitMap[ClauseKind][Kind].emplace_back(E);
3821           }
3822           return;
3823         }
3824       }
3825 
3826       // OpenMP [2.9.3.6, Restrictions, p.2]
3827       //  A list item that appears in a reduction clause of the innermost
3828       //  enclosing worksharing or parallel construct may not be accessed in an
3829       //  explicit task.
3830       DVar = Stack->hasInnermostDSA(
3831           VD,
3832           [](OpenMPClauseKind C, bool AppliedToPointee) {
3833             return C == OMPC_reduction && !AppliedToPointee;
3834           },
3835           [](OpenMPDirectiveKind K) {
3836             return isOpenMPParallelDirective(K) ||
3837                    isOpenMPWorksharingDirective(K) || isOpenMPTeamsDirective(K);
3838           },
3839           /*FromParent=*/true);
3840       if (isOpenMPTaskingDirective(DKind) && DVar.CKind == OMPC_reduction) {
3841         ErrorFound = true;
3842         SemaRef.Diag(ELoc, diag::err_omp_reduction_in_task);
3843         reportOriginalDsa(SemaRef, Stack, VD, DVar);
3844         return;
3845       }
3846 
3847       // Define implicit data-sharing attributes for task.
3848       DVar = Stack->getImplicitDSA(VD, /*FromParent=*/false);
3849       if (((isOpenMPTaskingDirective(DKind) && DVar.CKind != OMPC_shared) ||
3850            (((Stack->getDefaultDSA() == DSA_firstprivate &&
3851               DVar.CKind == OMPC_firstprivate) ||
3852              (Stack->getDefaultDSA() == DSA_private &&
3853               DVar.CKind == OMPC_private)) &&
3854             !DVar.RefExpr)) &&
3855           !Stack->isLoopControlVariable(VD).first) {
3856         if (Stack->getDefaultDSA() == DSA_private)
3857           ImplicitPrivate.push_back(E);
3858         else
3859           ImplicitFirstprivate.push_back(E);
3860         return;
3861       }
3862 
3863       // Store implicitly used globals with declare target link for parent
3864       // target.
3865       if (!isOpenMPTargetExecutionDirective(DKind) && Res &&
3866           *Res == OMPDeclareTargetDeclAttr::MT_Link) {
3867         Stack->addToParentTargetRegionLinkGlobals(E);
3868         return;
3869       }
3870     }
3871   }
3872   void VisitMemberExpr(MemberExpr *E) {
3873     if (E->isTypeDependent() || E->isValueDependent() ||
3874         E->containsUnexpandedParameterPack() || E->isInstantiationDependent())
3875       return;
3876     auto *FD = dyn_cast<FieldDecl>(E->getMemberDecl());
3877     OpenMPDirectiveKind DKind = Stack->getCurrentDirective();
3878     if (auto *TE = dyn_cast<CXXThisExpr>(E->getBase()->IgnoreParenCasts())) {
3879       if (!FD)
3880         return;
3881       DSAStackTy::DSAVarData DVar = Stack->getTopDSA(FD, /*FromParent=*/false);
3882       // Check if the variable has explicit DSA set and stop analysis if it
3883       // so.
3884       if (DVar.RefExpr || !ImplicitDeclarations.insert(FD).second)
3885         return;
3886 
3887       if (isOpenMPTargetExecutionDirective(DKind) &&
3888           !Stack->isLoopControlVariable(FD).first &&
3889           !Stack->checkMappableExprComponentListsForDecl(
3890               FD, /*CurrentRegionOnly=*/true,
3891               [](OMPClauseMappableExprCommon::MappableExprComponentListRef
3892                      StackComponents,
3893                  OpenMPClauseKind) {
3894                 return isa<CXXThisExpr>(
3895                     cast<MemberExpr>(
3896                         StackComponents.back().getAssociatedExpression())
3897                         ->getBase()
3898                         ->IgnoreParens());
3899               })) {
3900         // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C/C++, p.3]
3901         //  A bit-field cannot appear in a map clause.
3902         //
3903         if (FD->isBitField())
3904           return;
3905 
3906         // Check to see if the member expression is referencing a class that
3907         // has already been explicitly mapped
3908         if (Stack->isClassPreviouslyMapped(TE->getType()))
3909           return;
3910 
3911         OpenMPDefaultmapClauseModifier Modifier =
3912             Stack->getDefaultmapModifier(OMPC_DEFAULTMAP_aggregate);
3913         OpenMPDefaultmapClauseKind ClauseKind =
3914             getVariableCategoryFromDecl(SemaRef.getLangOpts(), FD);
3915         OpenMPMapClauseKind Kind = getMapClauseKindFromModifier(
3916             Modifier, /*IsAggregateOrDeclareTarget*/ true);
3917         ImplicitMap[ClauseKind][Kind].emplace_back(E);
3918         return;
3919       }
3920 
3921       SourceLocation ELoc = E->getExprLoc();
3922       // OpenMP [2.9.3.6, Restrictions, p.2]
3923       //  A list item that appears in a reduction clause of the innermost
3924       //  enclosing worksharing or parallel construct may not be accessed in
3925       //  an  explicit task.
3926       DVar = Stack->hasInnermostDSA(
3927           FD,
3928           [](OpenMPClauseKind C, bool AppliedToPointee) {
3929             return C == OMPC_reduction && !AppliedToPointee;
3930           },
3931           [](OpenMPDirectiveKind K) {
3932             return isOpenMPParallelDirective(K) ||
3933                    isOpenMPWorksharingDirective(K) || isOpenMPTeamsDirective(K);
3934           },
3935           /*FromParent=*/true);
3936       if (isOpenMPTaskingDirective(DKind) && DVar.CKind == OMPC_reduction) {
3937         ErrorFound = true;
3938         SemaRef.Diag(ELoc, diag::err_omp_reduction_in_task);
3939         reportOriginalDsa(SemaRef, Stack, FD, DVar);
3940         return;
3941       }
3942 
3943       // Define implicit data-sharing attributes for task.
3944       DVar = Stack->getImplicitDSA(FD, /*FromParent=*/false);
3945       if (isOpenMPTaskingDirective(DKind) && DVar.CKind != OMPC_shared &&
3946           !Stack->isLoopControlVariable(FD).first) {
3947         // Check if there is a captured expression for the current field in the
3948         // region. Do not mark it as firstprivate unless there is no captured
3949         // expression.
3950         // TODO: try to make it firstprivate.
3951         if (DVar.CKind != OMPC_unknown)
3952           ImplicitFirstprivate.push_back(E);
3953       }
3954       return;
3955     }
3956     if (isOpenMPTargetExecutionDirective(DKind)) {
3957       OMPClauseMappableExprCommon::MappableExprComponentList CurComponents;
3958       if (!checkMapClauseExpressionBase(SemaRef, E, CurComponents, OMPC_map,
3959                                         Stack->getCurrentDirective(),
3960                                         /*NoDiagnose=*/true))
3961         return;
3962       const auto *VD = cast<ValueDecl>(
3963           CurComponents.back().getAssociatedDeclaration()->getCanonicalDecl());
3964       if (!Stack->checkMappableExprComponentListsForDecl(
3965               VD, /*CurrentRegionOnly=*/true,
3966               [&CurComponents](
3967                   OMPClauseMappableExprCommon::MappableExprComponentListRef
3968                       StackComponents,
3969                   OpenMPClauseKind) {
3970                 auto CCI = CurComponents.rbegin();
3971                 auto CCE = CurComponents.rend();
3972                 for (const auto &SC : llvm::reverse(StackComponents)) {
3973                   // Do both expressions have the same kind?
3974                   if (CCI->getAssociatedExpression()->getStmtClass() !=
3975                       SC.getAssociatedExpression()->getStmtClass())
3976                     if (!((isa<OMPArraySectionExpr>(
3977                                SC.getAssociatedExpression()) ||
3978                            isa<OMPArrayShapingExpr>(
3979                                SC.getAssociatedExpression())) &&
3980                           isa<ArraySubscriptExpr>(
3981                               CCI->getAssociatedExpression())))
3982                       return false;
3983 
3984                   const Decl *CCD = CCI->getAssociatedDeclaration();
3985                   const Decl *SCD = SC.getAssociatedDeclaration();
3986                   CCD = CCD ? CCD->getCanonicalDecl() : nullptr;
3987                   SCD = SCD ? SCD->getCanonicalDecl() : nullptr;
3988                   if (SCD != CCD)
3989                     return false;
3990                   std::advance(CCI, 1);
3991                   if (CCI == CCE)
3992                     break;
3993                 }
3994                 return true;
3995               })) {
3996         Visit(E->getBase());
3997       }
3998     } else if (!TryCaptureCXXThisMembers) {
3999       Visit(E->getBase());
4000     }
4001   }
4002   void VisitOMPExecutableDirective(OMPExecutableDirective *S) {
4003     for (OMPClause *C : S->clauses()) {
4004       // Skip analysis of arguments of private clauses for task|target
4005       // directives.
4006       if (isa_and_nonnull<OMPPrivateClause>(C))
4007         continue;
4008       // Skip analysis of arguments of implicitly defined firstprivate clause
4009       // for task|target directives.
4010       // Skip analysis of arguments of implicitly defined map clause for target
4011       // directives.
4012       if (C && !((isa<OMPFirstprivateClause>(C) || isa<OMPMapClause>(C)) &&
4013                  C->isImplicit() &&
4014                  !isOpenMPTaskingDirective(Stack->getCurrentDirective()))) {
4015         for (Stmt *CC : C->children()) {
4016           if (CC)
4017             Visit(CC);
4018         }
4019       }
4020     }
4021     // Check implicitly captured variables.
4022     VisitSubCaptures(S);
4023   }
4024 
4025   void VisitOMPLoopTransformationDirective(OMPLoopTransformationDirective *S) {
4026     // Loop transformation directives do not introduce data sharing
4027     VisitStmt(S);
4028   }
4029 
4030   void VisitCallExpr(CallExpr *S) {
4031     for (Stmt *C : S->arguments()) {
4032       if (C) {
4033         // Check implicitly captured variables in the task-based directives to
4034         // check if they must be firstprivatized.
4035         Visit(C);
4036       }
4037     }
4038     if (Expr *Callee = S->getCallee())
4039       if (auto *CE = dyn_cast<MemberExpr>(Callee->IgnoreParenImpCasts()))
4040         Visit(CE->getBase());
4041   }
4042   void VisitStmt(Stmt *S) {
4043     for (Stmt *C : S->children()) {
4044       if (C) {
4045         // Check implicitly captured variables in the task-based directives to
4046         // check if they must be firstprivatized.
4047         Visit(C);
4048       }
4049     }
4050   }
4051 
4052   void visitSubCaptures(CapturedStmt *S) {
4053     for (const CapturedStmt::Capture &Cap : S->captures()) {
4054       if (!Cap.capturesVariable() && !Cap.capturesVariableByCopy())
4055         continue;
4056       VarDecl *VD = Cap.getCapturedVar();
4057       // Do not try to map the variable if it or its sub-component was mapped
4058       // already.
4059       if (isOpenMPTargetExecutionDirective(Stack->getCurrentDirective()) &&
4060           Stack->checkMappableExprComponentListsForDecl(
4061               VD, /*CurrentRegionOnly=*/true,
4062               [](OMPClauseMappableExprCommon::MappableExprComponentListRef,
4063                  OpenMPClauseKind) { return true; }))
4064         continue;
4065       DeclRefExpr *DRE = buildDeclRefExpr(
4066           SemaRef, VD, VD->getType().getNonLValueExprType(SemaRef.Context),
4067           Cap.getLocation(), /*RefersToCapture=*/true);
4068       Visit(DRE);
4069     }
4070   }
4071   bool isErrorFound() const { return ErrorFound; }
4072   ArrayRef<Expr *> getImplicitFirstprivate() const {
4073     return ImplicitFirstprivate;
4074   }
4075   ArrayRef<Expr *> getImplicitPrivate() const { return ImplicitPrivate; }
4076   ArrayRef<Expr *> getImplicitMap(OpenMPDefaultmapClauseKind DK,
4077                                   OpenMPMapClauseKind MK) const {
4078     return ImplicitMap[DK][MK];
4079   }
4080   ArrayRef<OpenMPMapModifierKind>
4081   getImplicitMapModifier(OpenMPDefaultmapClauseKind Kind) const {
4082     return ImplicitMapModifier[Kind];
4083   }
4084   const Sema::VarsWithInheritedDSAType &getVarsWithInheritedDSA() const {
4085     return VarsWithInheritedDSA;
4086   }
4087 
4088   DSAAttrChecker(DSAStackTy *S, Sema &SemaRef, CapturedStmt *CS)
4089       : Stack(S), SemaRef(SemaRef), ErrorFound(false), CS(CS) {
4090     // Process declare target link variables for the target directives.
4091     if (isOpenMPTargetExecutionDirective(S->getCurrentDirective())) {
4092       for (DeclRefExpr *E : Stack->getLinkGlobals())
4093         Visit(E);
4094     }
4095   }
4096 };
4097 } // namespace
4098 
4099 static void handleDeclareVariantConstructTrait(DSAStackTy *Stack,
4100                                                OpenMPDirectiveKind DKind,
4101                                                bool ScopeEntry) {
4102   SmallVector<llvm::omp::TraitProperty, 8> Traits;
4103   if (isOpenMPTargetExecutionDirective(DKind))
4104     Traits.emplace_back(llvm::omp::TraitProperty::construct_target_target);
4105   if (isOpenMPTeamsDirective(DKind))
4106     Traits.emplace_back(llvm::omp::TraitProperty::construct_teams_teams);
4107   if (isOpenMPParallelDirective(DKind))
4108     Traits.emplace_back(llvm::omp::TraitProperty::construct_parallel_parallel);
4109   if (isOpenMPWorksharingDirective(DKind))
4110     Traits.emplace_back(llvm::omp::TraitProperty::construct_for_for);
4111   if (isOpenMPSimdDirective(DKind))
4112     Traits.emplace_back(llvm::omp::TraitProperty::construct_simd_simd);
4113   Stack->handleConstructTrait(Traits, ScopeEntry);
4114 }
4115 
4116 void Sema::ActOnOpenMPRegionStart(OpenMPDirectiveKind DKind, Scope *CurScope) {
4117   switch (DKind) {
4118   case OMPD_parallel:
4119   case OMPD_parallel_for:
4120   case OMPD_parallel_for_simd:
4121   case OMPD_parallel_sections:
4122   case OMPD_parallel_master:
4123   case OMPD_parallel_masked:
4124   case OMPD_parallel_loop:
4125   case OMPD_teams:
4126   case OMPD_teams_distribute:
4127   case OMPD_teams_distribute_simd: {
4128     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4129     QualType KmpInt32PtrTy =
4130         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4131     Sema::CapturedParamNameType Params[] = {
4132         std::make_pair(".global_tid.", KmpInt32PtrTy),
4133         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4134         std::make_pair(StringRef(), QualType()) // __context with shared vars
4135     };
4136     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4137                              Params);
4138     break;
4139   }
4140   case OMPD_target_teams:
4141   case OMPD_target_parallel:
4142   case OMPD_target_parallel_for:
4143   case OMPD_target_parallel_for_simd:
4144   case OMPD_target_teams_loop:
4145   case OMPD_target_parallel_loop:
4146   case OMPD_target_teams_distribute:
4147   case OMPD_target_teams_distribute_simd: {
4148     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4149     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4150     QualType KmpInt32PtrTy =
4151         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4152     QualType Args[] = {VoidPtrTy};
4153     FunctionProtoType::ExtProtoInfo EPI;
4154     EPI.Variadic = true;
4155     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4156     Sema::CapturedParamNameType Params[] = {
4157         std::make_pair(".global_tid.", KmpInt32Ty),
4158         std::make_pair(".part_id.", KmpInt32PtrTy),
4159         std::make_pair(".privates.", VoidPtrTy),
4160         std::make_pair(
4161             ".copy_fn.",
4162             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4163         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4164         std::make_pair(StringRef(), QualType()) // __context with shared vars
4165     };
4166     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4167                              Params, /*OpenMPCaptureLevel=*/0);
4168     // Mark this captured region as inlined, because we don't use outlined
4169     // function directly.
4170     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4171         AlwaysInlineAttr::CreateImplicit(
4172             Context, {}, AttributeCommonInfo::AS_Keyword,
4173             AlwaysInlineAttr::Keyword_forceinline));
4174     Sema::CapturedParamNameType ParamsTarget[] = {
4175         std::make_pair(StringRef(), QualType()) // __context with shared vars
4176     };
4177     // Start a captured region for 'target' with no implicit parameters.
4178     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4179                              ParamsTarget, /*OpenMPCaptureLevel=*/1);
4180     Sema::CapturedParamNameType ParamsTeamsOrParallel[] = {
4181         std::make_pair(".global_tid.", KmpInt32PtrTy),
4182         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4183         std::make_pair(StringRef(), QualType()) // __context with shared vars
4184     };
4185     // Start a captured region for 'teams' or 'parallel'.  Both regions have
4186     // the same implicit parameters.
4187     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4188                              ParamsTeamsOrParallel, /*OpenMPCaptureLevel=*/2);
4189     break;
4190   }
4191   case OMPD_target:
4192   case OMPD_target_simd: {
4193     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4194     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4195     QualType KmpInt32PtrTy =
4196         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4197     QualType Args[] = {VoidPtrTy};
4198     FunctionProtoType::ExtProtoInfo EPI;
4199     EPI.Variadic = true;
4200     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4201     Sema::CapturedParamNameType Params[] = {
4202         std::make_pair(".global_tid.", KmpInt32Ty),
4203         std::make_pair(".part_id.", KmpInt32PtrTy),
4204         std::make_pair(".privates.", VoidPtrTy),
4205         std::make_pair(
4206             ".copy_fn.",
4207             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4208         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4209         std::make_pair(StringRef(), QualType()) // __context with shared vars
4210     };
4211     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4212                              Params, /*OpenMPCaptureLevel=*/0);
4213     // Mark this captured region as inlined, because we don't use outlined
4214     // function directly.
4215     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4216         AlwaysInlineAttr::CreateImplicit(
4217             Context, {}, AttributeCommonInfo::AS_Keyword,
4218             AlwaysInlineAttr::Keyword_forceinline));
4219     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4220                              std::make_pair(StringRef(), QualType()),
4221                              /*OpenMPCaptureLevel=*/1);
4222     break;
4223   }
4224   case OMPD_atomic:
4225   case OMPD_critical:
4226   case OMPD_section:
4227   case OMPD_master:
4228   case OMPD_masked:
4229   case OMPD_tile:
4230   case OMPD_unroll:
4231     break;
4232   case OMPD_loop:
4233     // TODO: 'loop' may require additional parameters depending on the binding.
4234     // Treat similar to OMPD_simd/OMPD_for for now.
4235   case OMPD_simd:
4236   case OMPD_for:
4237   case OMPD_for_simd:
4238   case OMPD_sections:
4239   case OMPD_single:
4240   case OMPD_taskgroup:
4241   case OMPD_distribute:
4242   case OMPD_distribute_simd:
4243   case OMPD_ordered:
4244   case OMPD_target_data:
4245   case OMPD_dispatch: {
4246     Sema::CapturedParamNameType Params[] = {
4247         std::make_pair(StringRef(), QualType()) // __context with shared vars
4248     };
4249     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4250                              Params);
4251     break;
4252   }
4253   case OMPD_task: {
4254     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4255     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4256     QualType KmpInt32PtrTy =
4257         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4258     QualType Args[] = {VoidPtrTy};
4259     FunctionProtoType::ExtProtoInfo EPI;
4260     EPI.Variadic = true;
4261     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4262     Sema::CapturedParamNameType Params[] = {
4263         std::make_pair(".global_tid.", KmpInt32Ty),
4264         std::make_pair(".part_id.", KmpInt32PtrTy),
4265         std::make_pair(".privates.", VoidPtrTy),
4266         std::make_pair(
4267             ".copy_fn.",
4268             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4269         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4270         std::make_pair(StringRef(), QualType()) // __context with shared vars
4271     };
4272     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4273                              Params);
4274     // Mark this captured region as inlined, because we don't use outlined
4275     // function directly.
4276     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4277         AlwaysInlineAttr::CreateImplicit(
4278             Context, {}, AttributeCommonInfo::AS_Keyword,
4279             AlwaysInlineAttr::Keyword_forceinline));
4280     break;
4281   }
4282   case OMPD_taskloop:
4283   case OMPD_taskloop_simd:
4284   case OMPD_master_taskloop:
4285   case OMPD_masked_taskloop:
4286   case OMPD_masked_taskloop_simd:
4287   case OMPD_master_taskloop_simd: {
4288     QualType KmpInt32Ty =
4289         Context.getIntTypeForBitwidth(/*DestWidth=*/32, /*Signed=*/1)
4290             .withConst();
4291     QualType KmpUInt64Ty =
4292         Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/0)
4293             .withConst();
4294     QualType KmpInt64Ty =
4295         Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/1)
4296             .withConst();
4297     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4298     QualType KmpInt32PtrTy =
4299         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4300     QualType Args[] = {VoidPtrTy};
4301     FunctionProtoType::ExtProtoInfo EPI;
4302     EPI.Variadic = true;
4303     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4304     Sema::CapturedParamNameType Params[] = {
4305         std::make_pair(".global_tid.", KmpInt32Ty),
4306         std::make_pair(".part_id.", KmpInt32PtrTy),
4307         std::make_pair(".privates.", VoidPtrTy),
4308         std::make_pair(
4309             ".copy_fn.",
4310             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4311         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4312         std::make_pair(".lb.", KmpUInt64Ty),
4313         std::make_pair(".ub.", KmpUInt64Ty),
4314         std::make_pair(".st.", KmpInt64Ty),
4315         std::make_pair(".liter.", KmpInt32Ty),
4316         std::make_pair(".reductions.", VoidPtrTy),
4317         std::make_pair(StringRef(), QualType()) // __context with shared vars
4318     };
4319     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4320                              Params);
4321     // Mark this captured region as inlined, because we don't use outlined
4322     // function directly.
4323     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4324         AlwaysInlineAttr::CreateImplicit(
4325             Context, {}, AttributeCommonInfo::AS_Keyword,
4326             AlwaysInlineAttr::Keyword_forceinline));
4327     break;
4328   }
4329   case OMPD_parallel_masked_taskloop:
4330   case OMPD_parallel_masked_taskloop_simd:
4331   case OMPD_parallel_master_taskloop:
4332   case OMPD_parallel_master_taskloop_simd: {
4333     QualType KmpInt32Ty =
4334         Context.getIntTypeForBitwidth(/*DestWidth=*/32, /*Signed=*/1)
4335             .withConst();
4336     QualType KmpUInt64Ty =
4337         Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/0)
4338             .withConst();
4339     QualType KmpInt64Ty =
4340         Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/1)
4341             .withConst();
4342     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4343     QualType KmpInt32PtrTy =
4344         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4345     Sema::CapturedParamNameType ParamsParallel[] = {
4346         std::make_pair(".global_tid.", KmpInt32PtrTy),
4347         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4348         std::make_pair(StringRef(), QualType()) // __context with shared vars
4349     };
4350     // Start a captured region for 'parallel'.
4351     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4352                              ParamsParallel, /*OpenMPCaptureLevel=*/0);
4353     QualType Args[] = {VoidPtrTy};
4354     FunctionProtoType::ExtProtoInfo EPI;
4355     EPI.Variadic = true;
4356     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4357     Sema::CapturedParamNameType Params[] = {
4358         std::make_pair(".global_tid.", KmpInt32Ty),
4359         std::make_pair(".part_id.", KmpInt32PtrTy),
4360         std::make_pair(".privates.", VoidPtrTy),
4361         std::make_pair(
4362             ".copy_fn.",
4363             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4364         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4365         std::make_pair(".lb.", KmpUInt64Ty),
4366         std::make_pair(".ub.", KmpUInt64Ty),
4367         std::make_pair(".st.", KmpInt64Ty),
4368         std::make_pair(".liter.", KmpInt32Ty),
4369         std::make_pair(".reductions.", VoidPtrTy),
4370         std::make_pair(StringRef(), QualType()) // __context with shared vars
4371     };
4372     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4373                              Params, /*OpenMPCaptureLevel=*/1);
4374     // Mark this captured region as inlined, because we don't use outlined
4375     // function directly.
4376     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4377         AlwaysInlineAttr::CreateImplicit(
4378             Context, {}, AttributeCommonInfo::AS_Keyword,
4379             AlwaysInlineAttr::Keyword_forceinline));
4380     break;
4381   }
4382   case OMPD_distribute_parallel_for_simd:
4383   case OMPD_distribute_parallel_for: {
4384     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4385     QualType KmpInt32PtrTy =
4386         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4387     Sema::CapturedParamNameType Params[] = {
4388         std::make_pair(".global_tid.", KmpInt32PtrTy),
4389         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4390         std::make_pair(".previous.lb.", Context.getSizeType().withConst()),
4391         std::make_pair(".previous.ub.", Context.getSizeType().withConst()),
4392         std::make_pair(StringRef(), QualType()) // __context with shared vars
4393     };
4394     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4395                              Params);
4396     break;
4397   }
4398   case OMPD_target_teams_distribute_parallel_for:
4399   case OMPD_target_teams_distribute_parallel_for_simd: {
4400     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4401     QualType KmpInt32PtrTy =
4402         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4403     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4404 
4405     QualType Args[] = {VoidPtrTy};
4406     FunctionProtoType::ExtProtoInfo EPI;
4407     EPI.Variadic = true;
4408     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4409     Sema::CapturedParamNameType Params[] = {
4410         std::make_pair(".global_tid.", KmpInt32Ty),
4411         std::make_pair(".part_id.", KmpInt32PtrTy),
4412         std::make_pair(".privates.", VoidPtrTy),
4413         std::make_pair(
4414             ".copy_fn.",
4415             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4416         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4417         std::make_pair(StringRef(), QualType()) // __context with shared vars
4418     };
4419     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4420                              Params, /*OpenMPCaptureLevel=*/0);
4421     // Mark this captured region as inlined, because we don't use outlined
4422     // function directly.
4423     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4424         AlwaysInlineAttr::CreateImplicit(
4425             Context, {}, AttributeCommonInfo::AS_Keyword,
4426             AlwaysInlineAttr::Keyword_forceinline));
4427     Sema::CapturedParamNameType ParamsTarget[] = {
4428         std::make_pair(StringRef(), QualType()) // __context with shared vars
4429     };
4430     // Start a captured region for 'target' with no implicit parameters.
4431     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4432                              ParamsTarget, /*OpenMPCaptureLevel=*/1);
4433 
4434     Sema::CapturedParamNameType ParamsTeams[] = {
4435         std::make_pair(".global_tid.", KmpInt32PtrTy),
4436         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4437         std::make_pair(StringRef(), QualType()) // __context with shared vars
4438     };
4439     // Start a captured region for 'target' with no implicit parameters.
4440     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4441                              ParamsTeams, /*OpenMPCaptureLevel=*/2);
4442 
4443     Sema::CapturedParamNameType ParamsParallel[] = {
4444         std::make_pair(".global_tid.", KmpInt32PtrTy),
4445         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4446         std::make_pair(".previous.lb.", Context.getSizeType().withConst()),
4447         std::make_pair(".previous.ub.", Context.getSizeType().withConst()),
4448         std::make_pair(StringRef(), QualType()) // __context with shared vars
4449     };
4450     // Start a captured region for 'teams' or 'parallel'.  Both regions have
4451     // the same implicit parameters.
4452     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4453                              ParamsParallel, /*OpenMPCaptureLevel=*/3);
4454     break;
4455   }
4456 
4457   case OMPD_teams_loop: {
4458     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4459     QualType KmpInt32PtrTy =
4460         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4461 
4462     Sema::CapturedParamNameType ParamsTeams[] = {
4463         std::make_pair(".global_tid.", KmpInt32PtrTy),
4464         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4465         std::make_pair(StringRef(), QualType()) // __context with shared vars
4466     };
4467     // Start a captured region for 'teams'.
4468     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4469                              ParamsTeams, /*OpenMPCaptureLevel=*/0);
4470     break;
4471   }
4472 
4473   case OMPD_teams_distribute_parallel_for:
4474   case OMPD_teams_distribute_parallel_for_simd: {
4475     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4476     QualType KmpInt32PtrTy =
4477         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4478 
4479     Sema::CapturedParamNameType ParamsTeams[] = {
4480         std::make_pair(".global_tid.", KmpInt32PtrTy),
4481         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4482         std::make_pair(StringRef(), QualType()) // __context with shared vars
4483     };
4484     // Start a captured region for 'target' with no implicit parameters.
4485     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4486                              ParamsTeams, /*OpenMPCaptureLevel=*/0);
4487 
4488     Sema::CapturedParamNameType ParamsParallel[] = {
4489         std::make_pair(".global_tid.", KmpInt32PtrTy),
4490         std::make_pair(".bound_tid.", KmpInt32PtrTy),
4491         std::make_pair(".previous.lb.", Context.getSizeType().withConst()),
4492         std::make_pair(".previous.ub.", Context.getSizeType().withConst()),
4493         std::make_pair(StringRef(), QualType()) // __context with shared vars
4494     };
4495     // Start a captured region for 'teams' or 'parallel'.  Both regions have
4496     // the same implicit parameters.
4497     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4498                              ParamsParallel, /*OpenMPCaptureLevel=*/1);
4499     break;
4500   }
4501   case OMPD_target_update:
4502   case OMPD_target_enter_data:
4503   case OMPD_target_exit_data: {
4504     QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1).withConst();
4505     QualType VoidPtrTy = Context.VoidPtrTy.withConst().withRestrict();
4506     QualType KmpInt32PtrTy =
4507         Context.getPointerType(KmpInt32Ty).withConst().withRestrict();
4508     QualType Args[] = {VoidPtrTy};
4509     FunctionProtoType::ExtProtoInfo EPI;
4510     EPI.Variadic = true;
4511     QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI);
4512     Sema::CapturedParamNameType Params[] = {
4513         std::make_pair(".global_tid.", KmpInt32Ty),
4514         std::make_pair(".part_id.", KmpInt32PtrTy),
4515         std::make_pair(".privates.", VoidPtrTy),
4516         std::make_pair(
4517             ".copy_fn.",
4518             Context.getPointerType(CopyFnType).withConst().withRestrict()),
4519         std::make_pair(".task_t.", Context.VoidPtrTy.withConst()),
4520         std::make_pair(StringRef(), QualType()) // __context with shared vars
4521     };
4522     ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP,
4523                              Params);
4524     // Mark this captured region as inlined, because we don't use outlined
4525     // function directly.
4526     getCurCapturedRegion()->TheCapturedDecl->addAttr(
4527         AlwaysInlineAttr::CreateImplicit(
4528             Context, {}, AttributeCommonInfo::AS_Keyword,
4529             AlwaysInlineAttr::Keyword_forceinline));
4530     break;
4531   }
4532   case OMPD_threadprivate:
4533   case OMPD_allocate:
4534   case OMPD_taskyield:
4535   case OMPD_barrier:
4536   case OMPD_taskwait:
4537   case OMPD_cancellation_point:
4538   case OMPD_cancel:
4539   case OMPD_flush:
4540   case OMPD_depobj:
4541   case OMPD_scan:
4542   case OMPD_declare_reduction:
4543   case OMPD_declare_mapper:
4544   case OMPD_declare_simd:
4545   case OMPD_declare_target:
4546   case OMPD_end_declare_target:
4547   case OMPD_requires:
4548   case OMPD_declare_variant:
4549   case OMPD_begin_declare_variant:
4550   case OMPD_end_declare_variant:
4551   case OMPD_metadirective:
4552     llvm_unreachable("OpenMP Directive is not allowed");
4553   case OMPD_unknown:
4554   default:
4555     llvm_unreachable("Unknown OpenMP directive");
4556   }
4557   DSAStack->setContext(CurContext);
4558   handleDeclareVariantConstructTrait(DSAStack, DKind, /* ScopeEntry */ true);
4559 }
4560 
4561 int Sema::getNumberOfConstructScopes(unsigned Level) const {
4562   return getOpenMPCaptureLevels(DSAStack->getDirective(Level));
4563 }
4564 
4565 int Sema::getOpenMPCaptureLevels(OpenMPDirectiveKind DKind) {
4566   SmallVector<OpenMPDirectiveKind, 4> CaptureRegions;
4567   getOpenMPCaptureRegions(CaptureRegions, DKind);
4568   return CaptureRegions.size();
4569 }
4570 
4571 static OMPCapturedExprDecl *buildCaptureDecl(Sema &S, IdentifierInfo *Id,
4572                                              Expr *CaptureExpr, bool WithInit,
4573                                              DeclContext *CurContext,
4574                                              bool AsExpression) {
4575   assert(CaptureExpr);
4576   ASTContext &C = S.getASTContext();
4577   Expr *Init = AsExpression ? CaptureExpr : CaptureExpr->IgnoreImpCasts();
4578   QualType Ty = Init->getType();
4579   if (CaptureExpr->getObjectKind() == OK_Ordinary && CaptureExpr->isGLValue()) {
4580     if (S.getLangOpts().CPlusPlus) {
4581       Ty = C.getLValueReferenceType(Ty);
4582     } else {
4583       Ty = C.getPointerType(Ty);
4584       ExprResult Res =
4585           S.CreateBuiltinUnaryOp(CaptureExpr->getExprLoc(), UO_AddrOf, Init);
4586       if (!Res.isUsable())
4587         return nullptr;
4588       Init = Res.get();
4589     }
4590     WithInit = true;
4591   }
4592   auto *CED = OMPCapturedExprDecl::Create(C, CurContext, Id, Ty,
4593                                           CaptureExpr->getBeginLoc());
4594   if (!WithInit)
4595     CED->addAttr(OMPCaptureNoInitAttr::CreateImplicit(C));
4596   CurContext->addHiddenDecl(CED);
4597   Sema::TentativeAnalysisScope Trap(S);
4598   S.AddInitializerToDecl(CED, Init, /*DirectInit=*/false);
4599   return CED;
4600 }
4601 
4602 static DeclRefExpr *buildCapture(Sema &S, ValueDecl *D, Expr *CaptureExpr,
4603                                  bool WithInit) {
4604   OMPCapturedExprDecl *CD;
4605   if (VarDecl *VD = S.isOpenMPCapturedDecl(D))
4606     CD = cast<OMPCapturedExprDecl>(VD);
4607   else
4608     CD = buildCaptureDecl(S, D->getIdentifier(), CaptureExpr, WithInit,
4609                           S.CurContext,
4610                           /*AsExpression=*/false);
4611   return buildDeclRefExpr(S, CD, CD->getType().getNonReferenceType(),
4612                           CaptureExpr->getExprLoc());
4613 }
4614 
4615 static ExprResult buildCapture(Sema &S, Expr *CaptureExpr, DeclRefExpr *&Ref) {
4616   CaptureExpr = S.DefaultLvalueConversion(CaptureExpr).get();
4617   if (!Ref) {
4618     OMPCapturedExprDecl *CD = buildCaptureDecl(
4619         S, &S.getASTContext().Idents.get(".capture_expr."), CaptureExpr,
4620         /*WithInit=*/true, S.CurContext, /*AsExpression=*/true);
4621     Ref = buildDeclRefExpr(S, CD, CD->getType().getNonReferenceType(),
4622                            CaptureExpr->getExprLoc());
4623   }
4624   ExprResult Res = Ref;
4625   if (!S.getLangOpts().CPlusPlus &&
4626       CaptureExpr->getObjectKind() == OK_Ordinary && CaptureExpr->isGLValue() &&
4627       Ref->getType()->isPointerType()) {
4628     Res = S.CreateBuiltinUnaryOp(CaptureExpr->getExprLoc(), UO_Deref, Ref);
4629     if (!Res.isUsable())
4630       return ExprError();
4631   }
4632   return S.DefaultLvalueConversion(Res.get());
4633 }
4634 
4635 namespace {
4636 // OpenMP directives parsed in this section are represented as a
4637 // CapturedStatement with an associated statement.  If a syntax error
4638 // is detected during the parsing of the associated statement, the
4639 // compiler must abort processing and close the CapturedStatement.
4640 //
4641 // Combined directives such as 'target parallel' have more than one
4642 // nested CapturedStatements.  This RAII ensures that we unwind out
4643 // of all the nested CapturedStatements when an error is found.
4644 class CaptureRegionUnwinderRAII {
4645 private:
4646   Sema &S;
4647   bool &ErrorFound;
4648   OpenMPDirectiveKind DKind = OMPD_unknown;
4649 
4650 public:
4651   CaptureRegionUnwinderRAII(Sema &S, bool &ErrorFound,
4652                             OpenMPDirectiveKind DKind)
4653       : S(S), ErrorFound(ErrorFound), DKind(DKind) {}
4654   ~CaptureRegionUnwinderRAII() {
4655     if (ErrorFound) {
4656       int ThisCaptureLevel = S.getOpenMPCaptureLevels(DKind);
4657       while (--ThisCaptureLevel >= 0)
4658         S.ActOnCapturedRegionError();
4659     }
4660   }
4661 };
4662 } // namespace
4663 
4664 void Sema::tryCaptureOpenMPLambdas(ValueDecl *V) {
4665   // Capture variables captured by reference in lambdas for target-based
4666   // directives.
4667   if (!CurContext->isDependentContext() &&
4668       (isOpenMPTargetExecutionDirective(DSAStack->getCurrentDirective()) ||
4669        isOpenMPTargetDataManagementDirective(
4670            DSAStack->getCurrentDirective()))) {
4671     QualType Type = V->getType();
4672     if (const auto *RD = Type.getCanonicalType()
4673                              .getNonReferenceType()
4674                              ->getAsCXXRecordDecl()) {
4675       bool SavedForceCaptureByReferenceInTargetExecutable =
4676           DSAStack->isForceCaptureByReferenceInTargetExecutable();
4677       DSAStack->setForceCaptureByReferenceInTargetExecutable(
4678           /*V=*/true);
4679       if (RD->isLambda()) {
4680         llvm::DenseMap<const VarDecl *, FieldDecl *> Captures;
4681         FieldDecl *ThisCapture;
4682         RD->getCaptureFields(Captures, ThisCapture);
4683         for (const LambdaCapture &LC : RD->captures()) {
4684           if (LC.getCaptureKind() == LCK_ByRef) {
4685             VarDecl *VD = LC.getCapturedVar();
4686             DeclContext *VDC = VD->getDeclContext();
4687             if (!VDC->Encloses(CurContext))
4688               continue;
4689             MarkVariableReferenced(LC.getLocation(), VD);
4690           } else if (LC.getCaptureKind() == LCK_This) {
4691             QualType ThisTy = getCurrentThisType();
4692             if (!ThisTy.isNull() &&
4693                 Context.typesAreCompatible(ThisTy, ThisCapture->getType()))
4694               CheckCXXThisCapture(LC.getLocation());
4695           }
4696         }
4697       }
4698       DSAStack->setForceCaptureByReferenceInTargetExecutable(
4699           SavedForceCaptureByReferenceInTargetExecutable);
4700     }
4701   }
4702 }
4703 
4704 static bool checkOrderedOrderSpecified(Sema &S,
4705                                        const ArrayRef<OMPClause *> Clauses) {
4706   const OMPOrderedClause *Ordered = nullptr;
4707   const OMPOrderClause *Order = nullptr;
4708 
4709   for (const OMPClause *Clause : Clauses) {
4710     if (Clause->getClauseKind() == OMPC_ordered)
4711       Ordered = cast<OMPOrderedClause>(Clause);
4712     else if (Clause->getClauseKind() == OMPC_order) {
4713       Order = cast<OMPOrderClause>(Clause);
4714       if (Order->getKind() != OMPC_ORDER_concurrent)
4715         Order = nullptr;
4716     }
4717     if (Ordered && Order)
4718       break;
4719   }
4720 
4721   if (Ordered && Order) {
4722     S.Diag(Order->getKindKwLoc(),
4723            diag::err_omp_simple_clause_incompatible_with_ordered)
4724         << getOpenMPClauseName(OMPC_order)
4725         << getOpenMPSimpleClauseTypeName(OMPC_order, OMPC_ORDER_concurrent)
4726         << SourceRange(Order->getBeginLoc(), Order->getEndLoc());
4727     S.Diag(Ordered->getBeginLoc(), diag::note_omp_ordered_param)
4728         << 0 << SourceRange(Ordered->getBeginLoc(), Ordered->getEndLoc());
4729     return true;
4730   }
4731   return false;
4732 }
4733 
4734 StmtResult Sema::ActOnOpenMPRegionEnd(StmtResult S,
4735                                       ArrayRef<OMPClause *> Clauses) {
4736   handleDeclareVariantConstructTrait(DSAStack, DSAStack->getCurrentDirective(),
4737                                      /* ScopeEntry */ false);
4738   if (DSAStack->getCurrentDirective() == OMPD_atomic ||
4739       DSAStack->getCurrentDirective() == OMPD_critical ||
4740       DSAStack->getCurrentDirective() == OMPD_section ||
4741       DSAStack->getCurrentDirective() == OMPD_master ||
4742       DSAStack->getCurrentDirective() == OMPD_masked)
4743     return S;
4744 
4745   bool ErrorFound = false;
4746   CaptureRegionUnwinderRAII CaptureRegionUnwinder(
4747       *this, ErrorFound, DSAStack->getCurrentDirective());
4748   if (!S.isUsable()) {
4749     ErrorFound = true;
4750     return StmtError();
4751   }
4752 
4753   SmallVector<OpenMPDirectiveKind, 4> CaptureRegions;
4754   getOpenMPCaptureRegions(CaptureRegions, DSAStack->getCurrentDirective());
4755   OMPOrderedClause *OC = nullptr;
4756   OMPScheduleClause *SC = nullptr;
4757   SmallVector<const OMPLinearClause *, 4> LCs;
4758   SmallVector<const OMPClauseWithPreInit *, 4> PICs;
4759   // This is required for proper codegen.
4760   for (OMPClause *Clause : Clauses) {
4761     if (!LangOpts.OpenMPSimd &&
4762         (isOpenMPTaskingDirective(DSAStack->getCurrentDirective()) ||
4763          DSAStack->getCurrentDirective() == OMPD_target) &&
4764         Clause->getClauseKind() == OMPC_in_reduction) {
4765       // Capture taskgroup task_reduction descriptors inside the tasking regions
4766       // with the corresponding in_reduction items.
4767       auto *IRC = cast<OMPInReductionClause>(Clause);
4768       for (Expr *E : IRC->taskgroup_descriptors())
4769         if (E)
4770           MarkDeclarationsReferencedInExpr(E);
4771     }
4772     if (isOpenMPPrivate(Clause->getClauseKind()) ||
4773         Clause->getClauseKind() == OMPC_copyprivate ||
4774         (getLangOpts().OpenMPUseTLS &&
4775          getASTContext().getTargetInfo().isTLSSupported() &&
4776          Clause->getClauseKind() == OMPC_copyin)) {
4777       DSAStack->setForceVarCapturing(Clause->getClauseKind() == OMPC_copyin);
4778       // Mark all variables in private list clauses as used in inner region.
4779       for (Stmt *VarRef : Clause->children()) {
4780         if (auto *E = cast_or_null<Expr>(VarRef)) {
4781           MarkDeclarationsReferencedInExpr(E);
4782         }
4783       }
4784       DSAStack->setForceVarCapturing(/*V=*/false);
4785     } else if (isOpenMPLoopTransformationDirective(
4786                    DSAStack->getCurrentDirective())) {
4787       assert(CaptureRegions.empty() &&
4788              "No captured regions in loop transformation directives.");
4789     } else if (CaptureRegions.size() > 1 ||
4790                CaptureRegions.back() != OMPD_unknown) {
4791       if (auto *C = OMPClauseWithPreInit::get(Clause))
4792         PICs.push_back(C);
4793       if (auto *C = OMPClauseWithPostUpdate::get(Clause)) {
4794         if (Expr *E = C->getPostUpdateExpr())
4795           MarkDeclarationsReferencedInExpr(E);
4796       }
4797     }
4798     if (Clause->getClauseKind() == OMPC_schedule)
4799       SC = cast<OMPScheduleClause>(Clause);
4800     else if (Clause->getClauseKind() == OMPC_ordered)
4801       OC = cast<OMPOrderedClause>(Clause);
4802     else if (Clause->getClauseKind() == OMPC_linear)
4803       LCs.push_back(cast<OMPLinearClause>(Clause));
4804   }
4805   // Capture allocator expressions if used.
4806   for (Expr *E : DSAStack->getInnerAllocators())
4807     MarkDeclarationsReferencedInExpr(E);
4808   // OpenMP, 2.7.1 Loop Construct, Restrictions
4809   // The nonmonotonic modifier cannot be specified if an ordered clause is
4810   // specified.
4811   if (SC &&
4812       (SC->getFirstScheduleModifier() == OMPC_SCHEDULE_MODIFIER_nonmonotonic ||
4813        SC->getSecondScheduleModifier() ==
4814            OMPC_SCHEDULE_MODIFIER_nonmonotonic) &&
4815       OC) {
4816     Diag(SC->getFirstScheduleModifier() == OMPC_SCHEDULE_MODIFIER_nonmonotonic
4817              ? SC->getFirstScheduleModifierLoc()
4818              : SC->getSecondScheduleModifierLoc(),
4819          diag::err_omp_simple_clause_incompatible_with_ordered)
4820         << getOpenMPClauseName(OMPC_schedule)
4821         << getOpenMPSimpleClauseTypeName(OMPC_schedule,
4822                                          OMPC_SCHEDULE_MODIFIER_nonmonotonic)
4823         << SourceRange(OC->getBeginLoc(), OC->getEndLoc());
4824     ErrorFound = true;
4825   }
4826   // OpenMP 5.0, 2.9.2 Worksharing-Loop Construct, Restrictions.
4827   // If an order(concurrent) clause is present, an ordered clause may not appear
4828   // on the same directive.
4829   if (checkOrderedOrderSpecified(*this, Clauses))
4830     ErrorFound = true;
4831   if (!LCs.empty() && OC && OC->getNumForLoops()) {
4832     for (const OMPLinearClause *C : LCs) {
4833       Diag(C->getBeginLoc(), diag::err_omp_linear_ordered)
4834           << SourceRange(OC->getBeginLoc(), OC->getEndLoc());
4835     }
4836     ErrorFound = true;
4837   }
4838   if (isOpenMPWorksharingDirective(DSAStack->getCurrentDirective()) &&
4839       isOpenMPSimdDirective(DSAStack->getCurrentDirective()) && OC &&
4840       OC->getNumForLoops()) {
4841     Diag(OC->getBeginLoc(), diag::err_omp_ordered_simd)
4842         << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
4843     ErrorFound = true;
4844   }
4845   if (ErrorFound) {
4846     return StmtError();
4847   }
4848   StmtResult SR = S;
4849   unsigned CompletedRegions = 0;
4850   for (OpenMPDirectiveKind ThisCaptureRegion : llvm::reverse(CaptureRegions)) {
4851     // Mark all variables in private list clauses as used in inner region.
4852     // Required for proper codegen of combined directives.
4853     // TODO: add processing for other clauses.
4854     if (ThisCaptureRegion != OMPD_unknown) {
4855       for (const clang::OMPClauseWithPreInit *C : PICs) {
4856         OpenMPDirectiveKind CaptureRegion = C->getCaptureRegion();
4857         // Find the particular capture region for the clause if the
4858         // directive is a combined one with multiple capture regions.
4859         // If the directive is not a combined one, the capture region
4860         // associated with the clause is OMPD_unknown and is generated
4861         // only once.
4862         if (CaptureRegion == ThisCaptureRegion ||
4863             CaptureRegion == OMPD_unknown) {
4864           if (auto *DS = cast_or_null<DeclStmt>(C->getPreInitStmt())) {
4865             for (Decl *D : DS->decls())
4866               MarkVariableReferenced(D->getLocation(), cast<VarDecl>(D));
4867           }
4868         }
4869       }
4870     }
4871     if (ThisCaptureRegion == OMPD_target) {
4872       // Capture allocator traits in the target region. They are used implicitly
4873       // and, thus, are not captured by default.
4874       for (OMPClause *C : Clauses) {
4875         if (const auto *UAC = dyn_cast<OMPUsesAllocatorsClause>(C)) {
4876           for (unsigned I = 0, End = UAC->getNumberOfAllocators(); I < End;
4877                ++I) {
4878             OMPUsesAllocatorsClause::Data D = UAC->getAllocatorData(I);
4879             if (Expr *E = D.AllocatorTraits)
4880               MarkDeclarationsReferencedInExpr(E);
4881           }
4882           continue;
4883         }
4884       }
4885     }
4886     if (ThisCaptureRegion == OMPD_parallel) {
4887       // Capture temp arrays for inscan reductions and locals in aligned
4888       // clauses.
4889       for (OMPClause *C : Clauses) {
4890         if (auto *RC = dyn_cast<OMPReductionClause>(C)) {
4891           if (RC->getModifier() != OMPC_REDUCTION_inscan)
4892             continue;
4893           for (Expr *E : RC->copy_array_temps())
4894             MarkDeclarationsReferencedInExpr(E);
4895         }
4896         if (auto *AC = dyn_cast<OMPAlignedClause>(C)) {
4897           for (Expr *E : AC->varlists())
4898             MarkDeclarationsReferencedInExpr(E);
4899         }
4900       }
4901     }
4902     if (++CompletedRegions == CaptureRegions.size())
4903       DSAStack->setBodyComplete();
4904     SR = ActOnCapturedRegionEnd(SR.get());
4905   }
4906   return SR;
4907 }
4908 
4909 static bool checkCancelRegion(Sema &SemaRef, OpenMPDirectiveKind CurrentRegion,
4910                               OpenMPDirectiveKind CancelRegion,
4911                               SourceLocation StartLoc) {
4912   // CancelRegion is only needed for cancel and cancellation_point.
4913   if (CurrentRegion != OMPD_cancel && CurrentRegion != OMPD_cancellation_point)
4914     return false;
4915 
4916   if (CancelRegion == OMPD_parallel || CancelRegion == OMPD_for ||
4917       CancelRegion == OMPD_sections || CancelRegion == OMPD_taskgroup)
4918     return false;
4919 
4920   SemaRef.Diag(StartLoc, diag::err_omp_wrong_cancel_region)
4921       << getOpenMPDirectiveName(CancelRegion);
4922   return true;
4923 }
4924 
4925 static bool checkNestingOfRegions(Sema &SemaRef, const DSAStackTy *Stack,
4926                                   OpenMPDirectiveKind CurrentRegion,
4927                                   const DeclarationNameInfo &CurrentName,
4928                                   OpenMPDirectiveKind CancelRegion,
4929                                   OpenMPBindClauseKind BindKind,
4930                                   SourceLocation StartLoc) {
4931   if (Stack->getCurScope()) {
4932     OpenMPDirectiveKind ParentRegion = Stack->getParentDirective();
4933     OpenMPDirectiveKind OffendingRegion = ParentRegion;
4934     bool NestingProhibited = false;
4935     bool CloseNesting = true;
4936     bool OrphanSeen = false;
4937     enum {
4938       NoRecommend,
4939       ShouldBeInParallelRegion,
4940       ShouldBeInOrderedRegion,
4941       ShouldBeInTargetRegion,
4942       ShouldBeInTeamsRegion,
4943       ShouldBeInLoopSimdRegion,
4944     } Recommend = NoRecommend;
4945     if (isOpenMPSimdDirective(ParentRegion) &&
4946         ((SemaRef.LangOpts.OpenMP <= 45 && CurrentRegion != OMPD_ordered) ||
4947          (SemaRef.LangOpts.OpenMP >= 50 && CurrentRegion != OMPD_ordered &&
4948           CurrentRegion != OMPD_simd && CurrentRegion != OMPD_atomic &&
4949           CurrentRegion != OMPD_scan))) {
4950       // OpenMP [2.16, Nesting of Regions]
4951       // OpenMP constructs may not be nested inside a simd region.
4952       // OpenMP [2.8.1,simd Construct, Restrictions]
4953       // An ordered construct with the simd clause is the only OpenMP
4954       // construct that can appear in the simd region.
4955       // Allowing a SIMD construct nested in another SIMD construct is an
4956       // extension. The OpenMP 4.5 spec does not allow it. Issue a warning
4957       // message.
4958       // OpenMP 5.0 [2.9.3.1, simd Construct, Restrictions]
4959       // The only OpenMP constructs that can be encountered during execution of
4960       // a simd region are the atomic construct, the loop construct, the simd
4961       // construct and the ordered construct with the simd clause.
4962       SemaRef.Diag(StartLoc, (CurrentRegion != OMPD_simd)
4963                                  ? diag::err_omp_prohibited_region_simd
4964                                  : diag::warn_omp_nesting_simd)
4965           << (SemaRef.LangOpts.OpenMP >= 50 ? 1 : 0);
4966       return CurrentRegion != OMPD_simd;
4967     }
4968     if (ParentRegion == OMPD_atomic) {
4969       // OpenMP [2.16, Nesting of Regions]
4970       // OpenMP constructs may not be nested inside an atomic region.
4971       SemaRef.Diag(StartLoc, diag::err_omp_prohibited_region_atomic);
4972       return true;
4973     }
4974     if (CurrentRegion == OMPD_section) {
4975       // OpenMP [2.7.2, sections Construct, Restrictions]
4976       // Orphaned section directives are prohibited. That is, the section
4977       // directives must appear within the sections construct and must not be
4978       // encountered elsewhere in the sections region.
4979       if (ParentRegion != OMPD_sections &&
4980           ParentRegion != OMPD_parallel_sections) {
4981         SemaRef.Diag(StartLoc, diag::err_omp_orphaned_section_directive)
4982             << (ParentRegion != OMPD_unknown)
4983             << getOpenMPDirectiveName(ParentRegion);
4984         return true;
4985       }
4986       return false;
4987     }
4988     // Allow some constructs (except teams and cancellation constructs) to be
4989     // orphaned (they could be used in functions, called from OpenMP regions
4990     // with the required preconditions).
4991     if (ParentRegion == OMPD_unknown &&
4992         !isOpenMPNestingTeamsDirective(CurrentRegion) &&
4993         CurrentRegion != OMPD_cancellation_point &&
4994         CurrentRegion != OMPD_cancel && CurrentRegion != OMPD_scan)
4995       return false;
4996     if (CurrentRegion == OMPD_cancellation_point ||
4997         CurrentRegion == OMPD_cancel) {
4998       // OpenMP [2.16, Nesting of Regions]
4999       // A cancellation point construct for which construct-type-clause is
5000       // taskgroup must be nested inside a task construct. A cancellation
5001       // point construct for which construct-type-clause is not taskgroup must
5002       // be closely nested inside an OpenMP construct that matches the type
5003       // specified in construct-type-clause.
5004       // A cancel construct for which construct-type-clause is taskgroup must be
5005       // nested inside a task construct. A cancel construct for which
5006       // construct-type-clause is not taskgroup must be closely nested inside an
5007       // OpenMP construct that matches the type specified in
5008       // construct-type-clause.
5009       NestingProhibited =
5010           !((CancelRegion == OMPD_parallel &&
5011              (ParentRegion == OMPD_parallel ||
5012               ParentRegion == OMPD_target_parallel)) ||
5013             (CancelRegion == OMPD_for &&
5014              (ParentRegion == OMPD_for || ParentRegion == OMPD_parallel_for ||
5015               ParentRegion == OMPD_target_parallel_for ||
5016               ParentRegion == OMPD_distribute_parallel_for ||
5017               ParentRegion == OMPD_teams_distribute_parallel_for ||
5018               ParentRegion == OMPD_target_teams_distribute_parallel_for)) ||
5019             (CancelRegion == OMPD_taskgroup &&
5020              (ParentRegion == OMPD_task ||
5021               (SemaRef.getLangOpts().OpenMP >= 50 &&
5022                (ParentRegion == OMPD_taskloop ||
5023                 ParentRegion == OMPD_master_taskloop ||
5024                 ParentRegion == OMPD_masked_taskloop ||
5025                 ParentRegion == OMPD_parallel_masked_taskloop ||
5026                 ParentRegion == OMPD_parallel_master_taskloop)))) ||
5027             (CancelRegion == OMPD_sections &&
5028              (ParentRegion == OMPD_section || ParentRegion == OMPD_sections ||
5029               ParentRegion == OMPD_parallel_sections)));
5030       OrphanSeen = ParentRegion == OMPD_unknown;
5031     } else if (CurrentRegion == OMPD_master || CurrentRegion == OMPD_masked) {
5032       // OpenMP 5.1 [2.22, Nesting of Regions]
5033       // A masked region may not be closely nested inside a worksharing, loop,
5034       // atomic, task, or taskloop region.
5035       NestingProhibited = isOpenMPWorksharingDirective(ParentRegion) ||
5036                           isOpenMPGenericLoopDirective(ParentRegion) ||
5037                           isOpenMPTaskingDirective(ParentRegion);
5038     } else if (CurrentRegion == OMPD_critical && CurrentName.getName()) {
5039       // OpenMP [2.16, Nesting of Regions]
5040       // A critical region may not be nested (closely or otherwise) inside a
5041       // critical region with the same name. Note that this restriction is not
5042       // sufficient to prevent deadlock.
5043       SourceLocation PreviousCriticalLoc;
5044       bool DeadLock = Stack->hasDirective(
5045           [CurrentName, &PreviousCriticalLoc](OpenMPDirectiveKind K,
5046                                               const DeclarationNameInfo &DNI,
5047                                               SourceLocation Loc) {
5048             if (K == OMPD_critical && DNI.getName() == CurrentName.getName()) {
5049               PreviousCriticalLoc = Loc;
5050               return true;
5051             }
5052             return false;
5053           },
5054           false /* skip top directive */);
5055       if (DeadLock) {
5056         SemaRef.Diag(StartLoc,
5057                      diag::err_omp_prohibited_region_critical_same_name)
5058             << CurrentName.getName();
5059         if (PreviousCriticalLoc.isValid())
5060           SemaRef.Diag(PreviousCriticalLoc,
5061                        diag::note_omp_previous_critical_region);
5062         return true;
5063       }
5064     } else if (CurrentRegion == OMPD_barrier) {
5065       // OpenMP 5.1 [2.22, Nesting of Regions]
5066       // A barrier region may not be closely nested inside a worksharing, loop,
5067       // task, taskloop, critical, ordered, atomic, or masked region.
5068       NestingProhibited =
5069           isOpenMPWorksharingDirective(ParentRegion) ||
5070           isOpenMPGenericLoopDirective(ParentRegion) ||
5071           isOpenMPTaskingDirective(ParentRegion) ||
5072           ParentRegion == OMPD_master || ParentRegion == OMPD_masked ||
5073           ParentRegion == OMPD_parallel_master ||
5074           ParentRegion == OMPD_parallel_masked ||
5075           ParentRegion == OMPD_critical || ParentRegion == OMPD_ordered;
5076     } else if (isOpenMPWorksharingDirective(CurrentRegion) &&
5077                !isOpenMPParallelDirective(CurrentRegion) &&
5078                !isOpenMPTeamsDirective(CurrentRegion)) {
5079       // OpenMP 5.1 [2.22, Nesting of Regions]
5080       // A loop region that binds to a parallel region or a worksharing region
5081       // may not be closely nested inside a worksharing, loop, task, taskloop,
5082       // critical, ordered, atomic, or masked region.
5083       NestingProhibited =
5084           isOpenMPWorksharingDirective(ParentRegion) ||
5085           isOpenMPGenericLoopDirective(ParentRegion) ||
5086           isOpenMPTaskingDirective(ParentRegion) ||
5087           ParentRegion == OMPD_master || ParentRegion == OMPD_masked ||
5088           ParentRegion == OMPD_parallel_master ||
5089           ParentRegion == OMPD_parallel_masked ||
5090           ParentRegion == OMPD_critical || ParentRegion == OMPD_ordered;
5091       Recommend = ShouldBeInParallelRegion;
5092     } else if (CurrentRegion == OMPD_ordered) {
5093       // OpenMP [2.16, Nesting of Regions]
5094       // An ordered region may not be closely nested inside a critical,
5095       // atomic, or explicit task region.
5096       // An ordered region must be closely nested inside a loop region (or
5097       // parallel loop region) with an ordered clause.
5098       // OpenMP [2.8.1,simd Construct, Restrictions]
5099       // An ordered construct with the simd clause is the only OpenMP construct
5100       // that can appear in the simd region.
5101       NestingProhibited = ParentRegion == OMPD_critical ||
5102                           isOpenMPTaskingDirective(ParentRegion) ||
5103                           !(isOpenMPSimdDirective(ParentRegion) ||
5104                             Stack->isParentOrderedRegion());
5105       Recommend = ShouldBeInOrderedRegion;
5106     } else if (isOpenMPNestingTeamsDirective(CurrentRegion)) {
5107       // OpenMP [2.16, Nesting of Regions]
5108       // If specified, a teams construct must be contained within a target
5109       // construct.
5110       NestingProhibited =
5111           (SemaRef.LangOpts.OpenMP <= 45 && ParentRegion != OMPD_target) ||
5112           (SemaRef.LangOpts.OpenMP >= 50 && ParentRegion != OMPD_unknown &&
5113            ParentRegion != OMPD_target);
5114       OrphanSeen = ParentRegion == OMPD_unknown;
5115       Recommend = ShouldBeInTargetRegion;
5116     } else if (CurrentRegion == OMPD_scan) {
5117       // OpenMP [2.16, Nesting of Regions]
5118       // If specified, a teams construct must be contained within a target
5119       // construct.
5120       NestingProhibited =
5121           SemaRef.LangOpts.OpenMP < 50 ||
5122           (ParentRegion != OMPD_simd && ParentRegion != OMPD_for &&
5123            ParentRegion != OMPD_for_simd && ParentRegion != OMPD_parallel_for &&
5124            ParentRegion != OMPD_parallel_for_simd);
5125       OrphanSeen = ParentRegion == OMPD_unknown;
5126       Recommend = ShouldBeInLoopSimdRegion;
5127     }
5128     if (!NestingProhibited &&
5129         !isOpenMPTargetExecutionDirective(CurrentRegion) &&
5130         !isOpenMPTargetDataManagementDirective(CurrentRegion) &&
5131         (ParentRegion == OMPD_teams || ParentRegion == OMPD_target_teams)) {
5132       // OpenMP [5.1, 2.22, Nesting of Regions]
5133       // distribute, distribute simd, distribute parallel worksharing-loop,
5134       // distribute parallel worksharing-loop SIMD, loop, parallel regions,
5135       // including any parallel regions arising from combined constructs,
5136       // omp_get_num_teams() regions, and omp_get_team_num() regions are the
5137       // only OpenMP regions that may be strictly nested inside the teams
5138       // region.
5139       //
5140       // As an extension, we permit atomic within teams as well.
5141       NestingProhibited = !isOpenMPParallelDirective(CurrentRegion) &&
5142                           !isOpenMPDistributeDirective(CurrentRegion) &&
5143                           CurrentRegion != OMPD_loop &&
5144                           !(SemaRef.getLangOpts().OpenMPExtensions &&
5145                             CurrentRegion == OMPD_atomic);
5146       Recommend = ShouldBeInParallelRegion;
5147     }
5148     if (!NestingProhibited && CurrentRegion == OMPD_loop) {
5149       // OpenMP [5.1, 2.11.7, loop Construct, Restrictions]
5150       // If the bind clause is present on the loop construct and binding is
5151       // teams then the corresponding loop region must be strictly nested inside
5152       // a teams region.
5153       NestingProhibited = BindKind == OMPC_BIND_teams &&
5154                           ParentRegion != OMPD_teams &&
5155                           ParentRegion != OMPD_target_teams;
5156       Recommend = ShouldBeInTeamsRegion;
5157     }
5158     if (!NestingProhibited &&
5159         isOpenMPNestingDistributeDirective(CurrentRegion)) {
5160       // OpenMP 4.5 [2.17 Nesting of Regions]
5161       // The region associated with the distribute construct must be strictly
5162       // nested inside a teams region
5163       NestingProhibited =
5164           (ParentRegion != OMPD_teams && ParentRegion != OMPD_target_teams);
5165       Recommend = ShouldBeInTeamsRegion;
5166     }
5167     if (!NestingProhibited &&
5168         (isOpenMPTargetExecutionDirective(CurrentRegion) ||
5169          isOpenMPTargetDataManagementDirective(CurrentRegion))) {
5170       // OpenMP 4.5 [2.17 Nesting of Regions]
5171       // If a target, target update, target data, target enter data, or
5172       // target exit data construct is encountered during execution of a
5173       // target region, the behavior is unspecified.
5174       NestingProhibited = Stack->hasDirective(
5175           [&OffendingRegion](OpenMPDirectiveKind K, const DeclarationNameInfo &,
5176                              SourceLocation) {
5177             if (isOpenMPTargetExecutionDirective(K)) {
5178               OffendingRegion = K;
5179               return true;
5180             }
5181             return false;
5182           },
5183           false /* don't skip top directive */);
5184       CloseNesting = false;
5185     }
5186     if (NestingProhibited) {
5187       if (OrphanSeen) {
5188         SemaRef.Diag(StartLoc, diag::err_omp_orphaned_device_directive)
5189             << getOpenMPDirectiveName(CurrentRegion) << Recommend;
5190       } else {
5191         SemaRef.Diag(StartLoc, diag::err_omp_prohibited_region)
5192             << CloseNesting << getOpenMPDirectiveName(OffendingRegion)
5193             << Recommend << getOpenMPDirectiveName(CurrentRegion);
5194       }
5195       return true;
5196     }
5197   }
5198   return false;
5199 }
5200 
5201 struct Kind2Unsigned {
5202   using argument_type = OpenMPDirectiveKind;
5203   unsigned operator()(argument_type DK) { return unsigned(DK); }
5204 };
5205 static bool checkIfClauses(Sema &S, OpenMPDirectiveKind Kind,
5206                            ArrayRef<OMPClause *> Clauses,
5207                            ArrayRef<OpenMPDirectiveKind> AllowedNameModifiers) {
5208   bool ErrorFound = false;
5209   unsigned NamedModifiersNumber = 0;
5210   llvm::IndexedMap<const OMPIfClause *, Kind2Unsigned> FoundNameModifiers;
5211   FoundNameModifiers.resize(llvm::omp::Directive_enumSize + 1);
5212   SmallVector<SourceLocation, 4> NameModifierLoc;
5213   for (const OMPClause *C : Clauses) {
5214     if (const auto *IC = dyn_cast_or_null<OMPIfClause>(C)) {
5215       // At most one if clause without a directive-name-modifier can appear on
5216       // the directive.
5217       OpenMPDirectiveKind CurNM = IC->getNameModifier();
5218       if (FoundNameModifiers[CurNM]) {
5219         S.Diag(C->getBeginLoc(), diag::err_omp_more_one_clause)
5220             << getOpenMPDirectiveName(Kind) << getOpenMPClauseName(OMPC_if)
5221             << (CurNM != OMPD_unknown) << getOpenMPDirectiveName(CurNM);
5222         ErrorFound = true;
5223       } else if (CurNM != OMPD_unknown) {
5224         NameModifierLoc.push_back(IC->getNameModifierLoc());
5225         ++NamedModifiersNumber;
5226       }
5227       FoundNameModifiers[CurNM] = IC;
5228       if (CurNM == OMPD_unknown)
5229         continue;
5230       // Check if the specified name modifier is allowed for the current
5231       // directive.
5232       // At most one if clause with the particular directive-name-modifier can
5233       // appear on the directive.
5234       if (!llvm::is_contained(AllowedNameModifiers, CurNM)) {
5235         S.Diag(IC->getNameModifierLoc(),
5236                diag::err_omp_wrong_if_directive_name_modifier)
5237             << getOpenMPDirectiveName(CurNM) << getOpenMPDirectiveName(Kind);
5238         ErrorFound = true;
5239       }
5240     }
5241   }
5242   // If any if clause on the directive includes a directive-name-modifier then
5243   // all if clauses on the directive must include a directive-name-modifier.
5244   if (FoundNameModifiers[OMPD_unknown] && NamedModifiersNumber > 0) {
5245     if (NamedModifiersNumber == AllowedNameModifiers.size()) {
5246       S.Diag(FoundNameModifiers[OMPD_unknown]->getBeginLoc(),
5247              diag::err_omp_no_more_if_clause);
5248     } else {
5249       std::string Values;
5250       std::string Sep(", ");
5251       unsigned AllowedCnt = 0;
5252       unsigned TotalAllowedNum =
5253           AllowedNameModifiers.size() - NamedModifiersNumber;
5254       for (unsigned Cnt = 0, End = AllowedNameModifiers.size(); Cnt < End;
5255            ++Cnt) {
5256         OpenMPDirectiveKind NM = AllowedNameModifiers[Cnt];
5257         if (!FoundNameModifiers[NM]) {
5258           Values += "'";
5259           Values += getOpenMPDirectiveName(NM);
5260           Values += "'";
5261           if (AllowedCnt + 2 == TotalAllowedNum)
5262             Values += " or ";
5263           else if (AllowedCnt + 1 != TotalAllowedNum)
5264             Values += Sep;
5265           ++AllowedCnt;
5266         }
5267       }
5268       S.Diag(FoundNameModifiers[OMPD_unknown]->getCondition()->getBeginLoc(),
5269              diag::err_omp_unnamed_if_clause)
5270           << (TotalAllowedNum > 1) << Values;
5271     }
5272     for (SourceLocation Loc : NameModifierLoc) {
5273       S.Diag(Loc, diag::note_omp_previous_named_if_clause);
5274     }
5275     ErrorFound = true;
5276   }
5277   return ErrorFound;
5278 }
5279 
5280 static std::pair<ValueDecl *, bool> getPrivateItem(Sema &S, Expr *&RefExpr,
5281                                                    SourceLocation &ELoc,
5282                                                    SourceRange &ERange,
5283                                                    bool AllowArraySection) {
5284   if (RefExpr->isTypeDependent() || RefExpr->isValueDependent() ||
5285       RefExpr->containsUnexpandedParameterPack())
5286     return std::make_pair(nullptr, true);
5287 
5288   // OpenMP [3.1, C/C++]
5289   //  A list item is a variable name.
5290   // OpenMP  [2.9.3.3, Restrictions, p.1]
5291   //  A variable that is part of another variable (as an array or
5292   //  structure element) cannot appear in a private clause.
5293   RefExpr = RefExpr->IgnoreParens();
5294   enum {
5295     NoArrayExpr = -1,
5296     ArraySubscript = 0,
5297     OMPArraySection = 1
5298   } IsArrayExpr = NoArrayExpr;
5299   if (AllowArraySection) {
5300     if (auto *ASE = dyn_cast_or_null<ArraySubscriptExpr>(RefExpr)) {
5301       Expr *Base = ASE->getBase()->IgnoreParenImpCasts();
5302       while (auto *TempASE = dyn_cast<ArraySubscriptExpr>(Base))
5303         Base = TempASE->getBase()->IgnoreParenImpCasts();
5304       RefExpr = Base;
5305       IsArrayExpr = ArraySubscript;
5306     } else if (auto *OASE = dyn_cast_or_null<OMPArraySectionExpr>(RefExpr)) {
5307       Expr *Base = OASE->getBase()->IgnoreParenImpCasts();
5308       while (auto *TempOASE = dyn_cast<OMPArraySectionExpr>(Base))
5309         Base = TempOASE->getBase()->IgnoreParenImpCasts();
5310       while (auto *TempASE = dyn_cast<ArraySubscriptExpr>(Base))
5311         Base = TempASE->getBase()->IgnoreParenImpCasts();
5312       RefExpr = Base;
5313       IsArrayExpr = OMPArraySection;
5314     }
5315   }
5316   ELoc = RefExpr->getExprLoc();
5317   ERange = RefExpr->getSourceRange();
5318   RefExpr = RefExpr->IgnoreParenImpCasts();
5319   auto *DE = dyn_cast_or_null<DeclRefExpr>(RefExpr);
5320   auto *ME = dyn_cast_or_null<MemberExpr>(RefExpr);
5321   if ((!DE || !isa<VarDecl>(DE->getDecl())) &&
5322       (S.getCurrentThisType().isNull() || !ME ||
5323        !isa<CXXThisExpr>(ME->getBase()->IgnoreParenImpCasts()) ||
5324        !isa<FieldDecl>(ME->getMemberDecl()))) {
5325     if (IsArrayExpr != NoArrayExpr) {
5326       S.Diag(ELoc, diag::err_omp_expected_base_var_name)
5327           << IsArrayExpr << ERange;
5328     } else {
5329       S.Diag(ELoc,
5330              AllowArraySection
5331                  ? diag::err_omp_expected_var_name_member_expr_or_array_item
5332                  : diag::err_omp_expected_var_name_member_expr)
5333           << (S.getCurrentThisType().isNull() ? 0 : 1) << ERange;
5334     }
5335     return std::make_pair(nullptr, false);
5336   }
5337   return std::make_pair(
5338       getCanonicalDecl(DE ? DE->getDecl() : ME->getMemberDecl()), false);
5339 }
5340 
5341 namespace {
5342 /// Checks if the allocator is used in uses_allocators clause to be allowed in
5343 /// target regions.
5344 class AllocatorChecker final : public ConstStmtVisitor<AllocatorChecker, bool> {
5345   DSAStackTy *S = nullptr;
5346 
5347 public:
5348   bool VisitDeclRefExpr(const DeclRefExpr *E) {
5349     return S->isUsesAllocatorsDecl(E->getDecl())
5350                .value_or(DSAStackTy::UsesAllocatorsDeclKind::AllocatorTrait) ==
5351            DSAStackTy::UsesAllocatorsDeclKind::AllocatorTrait;
5352   }
5353   bool VisitStmt(const Stmt *S) {
5354     for (const Stmt *Child : S->children()) {
5355       if (Child && Visit(Child))
5356         return true;
5357     }
5358     return false;
5359   }
5360   explicit AllocatorChecker(DSAStackTy *S) : S(S) {}
5361 };
5362 } // namespace
5363 
5364 static void checkAllocateClauses(Sema &S, DSAStackTy *Stack,
5365                                  ArrayRef<OMPClause *> Clauses) {
5366   assert(!S.CurContext->isDependentContext() &&
5367          "Expected non-dependent context.");
5368   auto AllocateRange =
5369       llvm::make_filter_range(Clauses, OMPAllocateClause::classof);
5370   llvm::DenseMap<CanonicalDeclPtr<Decl>, CanonicalDeclPtr<VarDecl>> DeclToCopy;
5371   auto PrivateRange = llvm::make_filter_range(Clauses, [](const OMPClause *C) {
5372     return isOpenMPPrivate(C->getClauseKind());
5373   });
5374   for (OMPClause *Cl : PrivateRange) {
5375     MutableArrayRef<Expr *>::iterator I, It, Et;
5376     if (Cl->getClauseKind() == OMPC_private) {
5377       auto *PC = cast<OMPPrivateClause>(Cl);
5378       I = PC->private_copies().begin();
5379       It = PC->varlist_begin();
5380       Et = PC->varlist_end();
5381     } else if (Cl->getClauseKind() == OMPC_firstprivate) {
5382       auto *PC = cast<OMPFirstprivateClause>(Cl);
5383       I = PC->private_copies().begin();
5384       It = PC->varlist_begin();
5385       Et = PC->varlist_end();
5386     } else if (Cl->getClauseKind() == OMPC_lastprivate) {
5387       auto *PC = cast<OMPLastprivateClause>(Cl);
5388       I = PC->private_copies().begin();
5389       It = PC->varlist_begin();
5390       Et = PC->varlist_end();
5391     } else if (Cl->getClauseKind() == OMPC_linear) {
5392       auto *PC = cast<OMPLinearClause>(Cl);
5393       I = PC->privates().begin();
5394       It = PC->varlist_begin();
5395       Et = PC->varlist_end();
5396     } else if (Cl->getClauseKind() == OMPC_reduction) {
5397       auto *PC = cast<OMPReductionClause>(Cl);
5398       I = PC->privates().begin();
5399       It = PC->varlist_begin();
5400       Et = PC->varlist_end();
5401     } else if (Cl->getClauseKind() == OMPC_task_reduction) {
5402       auto *PC = cast<OMPTaskReductionClause>(Cl);
5403       I = PC->privates().begin();
5404       It = PC->varlist_begin();
5405       Et = PC->varlist_end();
5406     } else if (Cl->getClauseKind() == OMPC_in_reduction) {
5407       auto *PC = cast<OMPInReductionClause>(Cl);
5408       I = PC->privates().begin();
5409       It = PC->varlist_begin();
5410       Et = PC->varlist_end();
5411     } else {
5412       llvm_unreachable("Expected private clause.");
5413     }
5414     for (Expr *E : llvm::make_range(It, Et)) {
5415       if (!*I) {
5416         ++I;
5417         continue;
5418       }
5419       SourceLocation ELoc;
5420       SourceRange ERange;
5421       Expr *SimpleRefExpr = E;
5422       auto Res = getPrivateItem(S, SimpleRefExpr, ELoc, ERange,
5423                                 /*AllowArraySection=*/true);
5424       DeclToCopy.try_emplace(Res.first,
5425                              cast<VarDecl>(cast<DeclRefExpr>(*I)->getDecl()));
5426       ++I;
5427     }
5428   }
5429   for (OMPClause *C : AllocateRange) {
5430     auto *AC = cast<OMPAllocateClause>(C);
5431     if (S.getLangOpts().OpenMP >= 50 &&
5432         !Stack->hasRequiresDeclWithClause<OMPDynamicAllocatorsClause>() &&
5433         isOpenMPTargetExecutionDirective(Stack->getCurrentDirective()) &&
5434         AC->getAllocator()) {
5435       Expr *Allocator = AC->getAllocator();
5436       // OpenMP, 2.12.5 target Construct
5437       // Memory allocators that do not appear in a uses_allocators clause cannot
5438       // appear as an allocator in an allocate clause or be used in the target
5439       // region unless a requires directive with the dynamic_allocators clause
5440       // is present in the same compilation unit.
5441       AllocatorChecker Checker(Stack);
5442       if (Checker.Visit(Allocator))
5443         S.Diag(Allocator->getExprLoc(),
5444                diag::err_omp_allocator_not_in_uses_allocators)
5445             << Allocator->getSourceRange();
5446     }
5447     OMPAllocateDeclAttr::AllocatorTypeTy AllocatorKind =
5448         getAllocatorKind(S, Stack, AC->getAllocator());
5449     // OpenMP, 2.11.4 allocate Clause, Restrictions.
5450     // For task, taskloop or target directives, allocation requests to memory
5451     // allocators with the trait access set to thread result in unspecified
5452     // behavior.
5453     if (AllocatorKind == OMPAllocateDeclAttr::OMPThreadMemAlloc &&
5454         (isOpenMPTaskingDirective(Stack->getCurrentDirective()) ||
5455          isOpenMPTargetExecutionDirective(Stack->getCurrentDirective()))) {
5456       S.Diag(AC->getAllocator()->getExprLoc(),
5457              diag::warn_omp_allocate_thread_on_task_target_directive)
5458           << getOpenMPDirectiveName(Stack->getCurrentDirective());
5459     }
5460     for (Expr *E : AC->varlists()) {
5461       SourceLocation ELoc;
5462       SourceRange ERange;
5463       Expr *SimpleRefExpr = E;
5464       auto Res = getPrivateItem(S, SimpleRefExpr, ELoc, ERange);
5465       ValueDecl *VD = Res.first;
5466       DSAStackTy::DSAVarData Data = Stack->getTopDSA(VD, /*FromParent=*/false);
5467       if (!isOpenMPPrivate(Data.CKind)) {
5468         S.Diag(E->getExprLoc(),
5469                diag::err_omp_expected_private_copy_for_allocate);
5470         continue;
5471       }
5472       VarDecl *PrivateVD = DeclToCopy[VD];
5473       if (checkPreviousOMPAllocateAttribute(S, Stack, E, PrivateVD,
5474                                             AllocatorKind, AC->getAllocator()))
5475         continue;
5476       // Placeholder until allocate clause supports align modifier.
5477       Expr *Alignment = nullptr;
5478       applyOMPAllocateAttribute(S, PrivateVD, AllocatorKind, AC->getAllocator(),
5479                                 Alignment, E->getSourceRange());
5480     }
5481   }
5482 }
5483 
5484 namespace {
5485 /// Rewrite statements and expressions for Sema \p Actions CurContext.
5486 ///
5487 /// Used to wrap already parsed statements/expressions into a new CapturedStmt
5488 /// context. DeclRefExpr used inside the new context are changed to refer to the
5489 /// captured variable instead.
5490 class CaptureVars : public TreeTransform<CaptureVars> {
5491   using BaseTransform = TreeTransform<CaptureVars>;
5492 
5493 public:
5494   CaptureVars(Sema &Actions) : BaseTransform(Actions) {}
5495 
5496   bool AlwaysRebuild() { return true; }
5497 };
5498 } // namespace
5499 
5500 static VarDecl *precomputeExpr(Sema &Actions,
5501                                SmallVectorImpl<Stmt *> &BodyStmts, Expr *E,
5502                                StringRef Name) {
5503   Expr *NewE = AssertSuccess(CaptureVars(Actions).TransformExpr(E));
5504   VarDecl *NewVar = buildVarDecl(Actions, {}, NewE->getType(), Name, nullptr,
5505                                  dyn_cast<DeclRefExpr>(E->IgnoreImplicit()));
5506   auto *NewDeclStmt = cast<DeclStmt>(AssertSuccess(
5507       Actions.ActOnDeclStmt(Actions.ConvertDeclToDeclGroup(NewVar), {}, {})));
5508   Actions.AddInitializerToDecl(NewDeclStmt->getSingleDecl(), NewE, false);
5509   BodyStmts.push_back(NewDeclStmt);
5510   return NewVar;
5511 }
5512 
5513 /// Create a closure that computes the number of iterations of a loop.
5514 ///
5515 /// \param Actions   The Sema object.
5516 /// \param LogicalTy Type for the logical iteration number.
5517 /// \param Rel       Comparison operator of the loop condition.
5518 /// \param StartExpr Value of the loop counter at the first iteration.
5519 /// \param StopExpr  Expression the loop counter is compared against in the loop
5520 /// condition. \param StepExpr      Amount of increment after each iteration.
5521 ///
5522 /// \return Closure (CapturedStmt) of the distance calculation.
5523 static CapturedStmt *buildDistanceFunc(Sema &Actions, QualType LogicalTy,
5524                                        BinaryOperator::Opcode Rel,
5525                                        Expr *StartExpr, Expr *StopExpr,
5526                                        Expr *StepExpr) {
5527   ASTContext &Ctx = Actions.getASTContext();
5528   TypeSourceInfo *LogicalTSI = Ctx.getTrivialTypeSourceInfo(LogicalTy);
5529 
5530   // Captured regions currently don't support return values, we use an
5531   // out-parameter instead. All inputs are implicit captures.
5532   // TODO: Instead of capturing each DeclRefExpr occurring in
5533   // StartExpr/StopExpr/Step, these could also be passed as a value capture.
5534   QualType ResultTy = Ctx.getLValueReferenceType(LogicalTy);
5535   Sema::CapturedParamNameType Params[] = {{"Distance", ResultTy},
5536                                           {StringRef(), QualType()}};
5537   Actions.ActOnCapturedRegionStart({}, nullptr, CR_Default, Params);
5538 
5539   Stmt *Body;
5540   {
5541     Sema::CompoundScopeRAII CompoundScope(Actions);
5542     CapturedDecl *CS = cast<CapturedDecl>(Actions.CurContext);
5543 
5544     // Get the LValue expression for the result.
5545     ImplicitParamDecl *DistParam = CS->getParam(0);
5546     DeclRefExpr *DistRef = Actions.BuildDeclRefExpr(
5547         DistParam, LogicalTy, VK_LValue, {}, nullptr, nullptr, {}, nullptr);
5548 
5549     SmallVector<Stmt *, 4> BodyStmts;
5550 
5551     // Capture all referenced variable references.
5552     // TODO: Instead of computing NewStart/NewStop/NewStep inside the
5553     // CapturedStmt, we could compute them before and capture the result, to be
5554     // used jointly with the LoopVar function.
5555     VarDecl *NewStart = precomputeExpr(Actions, BodyStmts, StartExpr, ".start");
5556     VarDecl *NewStop = precomputeExpr(Actions, BodyStmts, StopExpr, ".stop");
5557     VarDecl *NewStep = precomputeExpr(Actions, BodyStmts, StepExpr, ".step");
5558     auto BuildVarRef = [&](VarDecl *VD) {
5559       return buildDeclRefExpr(Actions, VD, VD->getType(), {});
5560     };
5561 
5562     IntegerLiteral *Zero = IntegerLiteral::Create(
5563         Ctx, llvm::APInt(Ctx.getIntWidth(LogicalTy), 0), LogicalTy, {});
5564     IntegerLiteral *One = IntegerLiteral::Create(
5565         Ctx, llvm::APInt(Ctx.getIntWidth(LogicalTy), 1), LogicalTy, {});
5566     Expr *Dist;
5567     if (Rel == BO_NE) {
5568       // When using a != comparison, the increment can be +1 or -1. This can be
5569       // dynamic at runtime, so we need to check for the direction.
5570       Expr *IsNegStep = AssertSuccess(
5571           Actions.BuildBinOp(nullptr, {}, BO_LT, BuildVarRef(NewStep), Zero));
5572 
5573       // Positive increment.
5574       Expr *ForwardRange = AssertSuccess(Actions.BuildBinOp(
5575           nullptr, {}, BO_Sub, BuildVarRef(NewStop), BuildVarRef(NewStart)));
5576       ForwardRange = AssertSuccess(
5577           Actions.BuildCStyleCastExpr({}, LogicalTSI, {}, ForwardRange));
5578       Expr *ForwardDist = AssertSuccess(Actions.BuildBinOp(
5579           nullptr, {}, BO_Div, ForwardRange, BuildVarRef(NewStep)));
5580 
5581       // Negative increment.
5582       Expr *BackwardRange = AssertSuccess(Actions.BuildBinOp(
5583           nullptr, {}, BO_Sub, BuildVarRef(NewStart), BuildVarRef(NewStop)));
5584       BackwardRange = AssertSuccess(
5585           Actions.BuildCStyleCastExpr({}, LogicalTSI, {}, BackwardRange));
5586       Expr *NegIncAmount = AssertSuccess(
5587           Actions.BuildUnaryOp(nullptr, {}, UO_Minus, BuildVarRef(NewStep)));
5588       Expr *BackwardDist = AssertSuccess(
5589           Actions.BuildBinOp(nullptr, {}, BO_Div, BackwardRange, NegIncAmount));
5590 
5591       // Use the appropriate case.
5592       Dist = AssertSuccess(Actions.ActOnConditionalOp(
5593           {}, {}, IsNegStep, BackwardDist, ForwardDist));
5594     } else {
5595       assert((Rel == BO_LT || Rel == BO_LE || Rel == BO_GE || Rel == BO_GT) &&
5596              "Expected one of these relational operators");
5597 
5598       // We can derive the direction from any other comparison operator. It is
5599       // non well-formed OpenMP if Step increments/decrements in the other
5600       // directions. Whether at least the first iteration passes the loop
5601       // condition.
5602       Expr *HasAnyIteration = AssertSuccess(Actions.BuildBinOp(
5603           nullptr, {}, Rel, BuildVarRef(NewStart), BuildVarRef(NewStop)));
5604 
5605       // Compute the range between first and last counter value.
5606       Expr *Range;
5607       if (Rel == BO_GE || Rel == BO_GT)
5608         Range = AssertSuccess(Actions.BuildBinOp(
5609             nullptr, {}, BO_Sub, BuildVarRef(NewStart), BuildVarRef(NewStop)));
5610       else
5611         Range = AssertSuccess(Actions.BuildBinOp(
5612             nullptr, {}, BO_Sub, BuildVarRef(NewStop), BuildVarRef(NewStart)));
5613 
5614       // Ensure unsigned range space.
5615       Range =
5616           AssertSuccess(Actions.BuildCStyleCastExpr({}, LogicalTSI, {}, Range));
5617 
5618       if (Rel == BO_LE || Rel == BO_GE) {
5619         // Add one to the range if the relational operator is inclusive.
5620         Range =
5621             AssertSuccess(Actions.BuildBinOp(nullptr, {}, BO_Add, Range, One));
5622       }
5623 
5624       // Divide by the absolute step amount. If the range is not a multiple of
5625       // the step size, rounding-up the effective upper bound ensures that the
5626       // last iteration is included.
5627       // Note that the rounding-up may cause an overflow in a temporry that
5628       // could be avoided, but would have occurred in a C-style for-loop as well.
5629       Expr *Divisor = BuildVarRef(NewStep);
5630       if (Rel == BO_GE || Rel == BO_GT)
5631         Divisor =
5632             AssertSuccess(Actions.BuildUnaryOp(nullptr, {}, UO_Minus, Divisor));
5633       Expr *DivisorMinusOne =
5634           AssertSuccess(Actions.BuildBinOp(nullptr, {}, BO_Sub, Divisor, One));
5635       Expr *RangeRoundUp = AssertSuccess(
5636           Actions.BuildBinOp(nullptr, {}, BO_Add, Range, DivisorMinusOne));
5637       Dist = AssertSuccess(
5638           Actions.BuildBinOp(nullptr, {}, BO_Div, RangeRoundUp, Divisor));
5639 
5640       // If there is not at least one iteration, the range contains garbage. Fix
5641       // to zero in this case.
5642       Dist = AssertSuccess(
5643           Actions.ActOnConditionalOp({}, {}, HasAnyIteration, Dist, Zero));
5644     }
5645 
5646     // Assign the result to the out-parameter.
5647     Stmt *ResultAssign = AssertSuccess(Actions.BuildBinOp(
5648         Actions.getCurScope(), {}, BO_Assign, DistRef, Dist));
5649     BodyStmts.push_back(ResultAssign);
5650 
5651     Body = AssertSuccess(Actions.ActOnCompoundStmt({}, {}, BodyStmts, false));
5652   }
5653 
5654   return cast<CapturedStmt>(
5655       AssertSuccess(Actions.ActOnCapturedRegionEnd(Body)));
5656 }
5657 
5658 /// Create a closure that computes the loop variable from the logical iteration
5659 /// number.
5660 ///
5661 /// \param Actions   The Sema object.
5662 /// \param LoopVarTy Type for the loop variable used for result value.
5663 /// \param LogicalTy Type for the logical iteration number.
5664 /// \param StartExpr Value of the loop counter at the first iteration.
5665 /// \param Step      Amount of increment after each iteration.
5666 /// \param Deref     Whether the loop variable is a dereference of the loop
5667 /// counter variable.
5668 ///
5669 /// \return Closure (CapturedStmt) of the loop value calculation.
5670 static CapturedStmt *buildLoopVarFunc(Sema &Actions, QualType LoopVarTy,
5671                                       QualType LogicalTy,
5672                                       DeclRefExpr *StartExpr, Expr *Step,
5673                                       bool Deref) {
5674   ASTContext &Ctx = Actions.getASTContext();
5675 
5676   // Pass the result as an out-parameter. Passing as return value would require
5677   // the OpenMPIRBuilder to know additional C/C++ semantics, such as how to
5678   // invoke a copy constructor.
5679   QualType TargetParamTy = Ctx.getLValueReferenceType(LoopVarTy);
5680   Sema::CapturedParamNameType Params[] = {{"LoopVar", TargetParamTy},
5681                                           {"Logical", LogicalTy},
5682                                           {StringRef(), QualType()}};
5683   Actions.ActOnCapturedRegionStart({}, nullptr, CR_Default, Params);
5684 
5685   // Capture the initial iterator which represents the LoopVar value at the
5686   // zero's logical iteration. Since the original ForStmt/CXXForRangeStmt update
5687   // it in every iteration, capture it by value before it is modified.
5688   VarDecl *StartVar = cast<VarDecl>(StartExpr->getDecl());
5689   bool Invalid = Actions.tryCaptureVariable(StartVar, {},
5690                                             Sema::TryCapture_ExplicitByVal, {});
5691   (void)Invalid;
5692   assert(!Invalid && "Expecting capture-by-value to work.");
5693 
5694   Expr *Body;
5695   {
5696     Sema::CompoundScopeRAII CompoundScope(Actions);
5697     auto *CS = cast<CapturedDecl>(Actions.CurContext);
5698 
5699     ImplicitParamDecl *TargetParam = CS->getParam(0);
5700     DeclRefExpr *TargetRef = Actions.BuildDeclRefExpr(
5701         TargetParam, LoopVarTy, VK_LValue, {}, nullptr, nullptr, {}, nullptr);
5702     ImplicitParamDecl *IndvarParam = CS->getParam(1);
5703     DeclRefExpr *LogicalRef = Actions.BuildDeclRefExpr(
5704         IndvarParam, LogicalTy, VK_LValue, {}, nullptr, nullptr, {}, nullptr);
5705 
5706     // Capture the Start expression.
5707     CaptureVars Recap(Actions);
5708     Expr *NewStart = AssertSuccess(Recap.TransformExpr(StartExpr));
5709     Expr *NewStep = AssertSuccess(Recap.TransformExpr(Step));
5710 
5711     Expr *Skip = AssertSuccess(
5712         Actions.BuildBinOp(nullptr, {}, BO_Mul, NewStep, LogicalRef));
5713     // TODO: Explicitly cast to the iterator's difference_type instead of
5714     // relying on implicit conversion.
5715     Expr *Advanced =
5716         AssertSuccess(Actions.BuildBinOp(nullptr, {}, BO_Add, NewStart, Skip));
5717 
5718     if (Deref) {
5719       // For range-based for-loops convert the loop counter value to a concrete
5720       // loop variable value by dereferencing the iterator.
5721       Advanced =
5722           AssertSuccess(Actions.BuildUnaryOp(nullptr, {}, UO_Deref, Advanced));
5723     }
5724 
5725     // Assign the result to the output parameter.
5726     Body = AssertSuccess(Actions.BuildBinOp(Actions.getCurScope(), {},
5727                                             BO_Assign, TargetRef, Advanced));
5728   }
5729   return cast<CapturedStmt>(
5730       AssertSuccess(Actions.ActOnCapturedRegionEnd(Body)));
5731 }
5732 
5733 StmtResult Sema::ActOnOpenMPCanonicalLoop(Stmt *AStmt) {
5734   ASTContext &Ctx = getASTContext();
5735 
5736   // Extract the common elements of ForStmt and CXXForRangeStmt:
5737   // Loop variable, repeat condition, increment
5738   Expr *Cond, *Inc;
5739   VarDecl *LIVDecl, *LUVDecl;
5740   if (auto *For = dyn_cast<ForStmt>(AStmt)) {
5741     Stmt *Init = For->getInit();
5742     if (auto *LCVarDeclStmt = dyn_cast<DeclStmt>(Init)) {
5743       // For statement declares loop variable.
5744       LIVDecl = cast<VarDecl>(LCVarDeclStmt->getSingleDecl());
5745     } else if (auto *LCAssign = dyn_cast<BinaryOperator>(Init)) {
5746       // For statement reuses variable.
5747       assert(LCAssign->getOpcode() == BO_Assign &&
5748              "init part must be a loop variable assignment");
5749       auto *CounterRef = cast<DeclRefExpr>(LCAssign->getLHS());
5750       LIVDecl = cast<VarDecl>(CounterRef->getDecl());
5751     } else
5752       llvm_unreachable("Cannot determine loop variable");
5753     LUVDecl = LIVDecl;
5754 
5755     Cond = For->getCond();
5756     Inc = For->getInc();
5757   } else if (auto *RangeFor = dyn_cast<CXXForRangeStmt>(AStmt)) {
5758     DeclStmt *BeginStmt = RangeFor->getBeginStmt();
5759     LIVDecl = cast<VarDecl>(BeginStmt->getSingleDecl());
5760     LUVDecl = RangeFor->getLoopVariable();
5761 
5762     Cond = RangeFor->getCond();
5763     Inc = RangeFor->getInc();
5764   } else
5765     llvm_unreachable("unhandled kind of loop");
5766 
5767   QualType CounterTy = LIVDecl->getType();
5768   QualType LVTy = LUVDecl->getType();
5769 
5770   // Analyze the loop condition.
5771   Expr *LHS, *RHS;
5772   BinaryOperator::Opcode CondRel;
5773   Cond = Cond->IgnoreImplicit();
5774   if (auto *CondBinExpr = dyn_cast<BinaryOperator>(Cond)) {
5775     LHS = CondBinExpr->getLHS();
5776     RHS = CondBinExpr->getRHS();
5777     CondRel = CondBinExpr->getOpcode();
5778   } else if (auto *CondCXXOp = dyn_cast<CXXOperatorCallExpr>(Cond)) {
5779     assert(CondCXXOp->getNumArgs() == 2 && "Comparison should have 2 operands");
5780     LHS = CondCXXOp->getArg(0);
5781     RHS = CondCXXOp->getArg(1);
5782     switch (CondCXXOp->getOperator()) {
5783     case OO_ExclaimEqual:
5784       CondRel = BO_NE;
5785       break;
5786     case OO_Less:
5787       CondRel = BO_LT;
5788       break;
5789     case OO_LessEqual:
5790       CondRel = BO_LE;
5791       break;
5792     case OO_Greater:
5793       CondRel = BO_GT;
5794       break;
5795     case OO_GreaterEqual:
5796       CondRel = BO_GE;
5797       break;
5798     default:
5799       llvm_unreachable("unexpected iterator operator");
5800     }
5801   } else
5802     llvm_unreachable("unexpected loop condition");
5803 
5804   // Normalize such that the loop counter is on the LHS.
5805   if (!isa<DeclRefExpr>(LHS->IgnoreImplicit()) ||
5806       cast<DeclRefExpr>(LHS->IgnoreImplicit())->getDecl() != LIVDecl) {
5807     std::swap(LHS, RHS);
5808     CondRel = BinaryOperator::reverseComparisonOp(CondRel);
5809   }
5810   auto *CounterRef = cast<DeclRefExpr>(LHS->IgnoreImplicit());
5811 
5812   // Decide the bit width for the logical iteration counter. By default use the
5813   // unsigned ptrdiff_t integer size (for iterators and pointers).
5814   // TODO: For iterators, use iterator::difference_type,
5815   // std::iterator_traits<>::difference_type or decltype(it - end).
5816   QualType LogicalTy = Ctx.getUnsignedPointerDiffType();
5817   if (CounterTy->isIntegerType()) {
5818     unsigned BitWidth = Ctx.getIntWidth(CounterTy);
5819     LogicalTy = Ctx.getIntTypeForBitwidth(BitWidth, false);
5820   }
5821 
5822   // Analyze the loop increment.
5823   Expr *Step;
5824   if (auto *IncUn = dyn_cast<UnaryOperator>(Inc)) {
5825     int Direction;
5826     switch (IncUn->getOpcode()) {
5827     case UO_PreInc:
5828     case UO_PostInc:
5829       Direction = 1;
5830       break;
5831     case UO_PreDec:
5832     case UO_PostDec:
5833       Direction = -1;
5834       break;
5835     default:
5836       llvm_unreachable("unhandled unary increment operator");
5837     }
5838     Step = IntegerLiteral::Create(
5839         Ctx, llvm::APInt(Ctx.getIntWidth(LogicalTy), Direction), LogicalTy, {});
5840   } else if (auto *IncBin = dyn_cast<BinaryOperator>(Inc)) {
5841     if (IncBin->getOpcode() == BO_AddAssign) {
5842       Step = IncBin->getRHS();
5843     } else if (IncBin->getOpcode() == BO_SubAssign) {
5844       Step =
5845           AssertSuccess(BuildUnaryOp(nullptr, {}, UO_Minus, IncBin->getRHS()));
5846     } else
5847       llvm_unreachable("unhandled binary increment operator");
5848   } else if (auto *CondCXXOp = dyn_cast<CXXOperatorCallExpr>(Inc)) {
5849     switch (CondCXXOp->getOperator()) {
5850     case OO_PlusPlus:
5851       Step = IntegerLiteral::Create(
5852           Ctx, llvm::APInt(Ctx.getIntWidth(LogicalTy), 1), LogicalTy, {});
5853       break;
5854     case OO_MinusMinus:
5855       Step = IntegerLiteral::Create(
5856           Ctx, llvm::APInt(Ctx.getIntWidth(LogicalTy), -1), LogicalTy, {});
5857       break;
5858     case OO_PlusEqual:
5859       Step = CondCXXOp->getArg(1);
5860       break;
5861     case OO_MinusEqual:
5862       Step = AssertSuccess(
5863           BuildUnaryOp(nullptr, {}, UO_Minus, CondCXXOp->getArg(1)));
5864       break;
5865     default:
5866       llvm_unreachable("unhandled overloaded increment operator");
5867     }
5868   } else
5869     llvm_unreachable("unknown increment expression");
5870 
5871   CapturedStmt *DistanceFunc =
5872       buildDistanceFunc(*this, LogicalTy, CondRel, LHS, RHS, Step);
5873   CapturedStmt *LoopVarFunc = buildLoopVarFunc(
5874       *this, LVTy, LogicalTy, CounterRef, Step, isa<CXXForRangeStmt>(AStmt));
5875   DeclRefExpr *LVRef = BuildDeclRefExpr(LUVDecl, LUVDecl->getType(), VK_LValue,
5876                                         {}, nullptr, nullptr, {}, nullptr);
5877   return OMPCanonicalLoop::create(getASTContext(), AStmt, DistanceFunc,
5878                                   LoopVarFunc, LVRef);
5879 }
5880 
5881 StmtResult Sema::ActOnOpenMPLoopnest(Stmt *AStmt) {
5882   // Handle a literal loop.
5883   if (isa<ForStmt>(AStmt) || isa<CXXForRangeStmt>(AStmt))
5884     return ActOnOpenMPCanonicalLoop(AStmt);
5885 
5886   // If not a literal loop, it must be the result of a loop transformation.
5887   OMPExecutableDirective *LoopTransform = cast<OMPExecutableDirective>(AStmt);
5888   assert(
5889       isOpenMPLoopTransformationDirective(LoopTransform->getDirectiveKind()) &&
5890       "Loop transformation directive expected");
5891   return LoopTransform;
5892 }
5893 
5894 static ExprResult buildUserDefinedMapperRef(Sema &SemaRef, Scope *S,
5895                                             CXXScopeSpec &MapperIdScopeSpec,
5896                                             const DeclarationNameInfo &MapperId,
5897                                             QualType Type,
5898                                             Expr *UnresolvedMapper);
5899 
5900 /// Perform DFS through the structure/class data members trying to find
5901 /// member(s) with user-defined 'default' mapper and generate implicit map
5902 /// clauses for such members with the found 'default' mapper.
5903 static void
5904 processImplicitMapsWithDefaultMappers(Sema &S, DSAStackTy *Stack,
5905                                       SmallVectorImpl<OMPClause *> &Clauses) {
5906   // Check for the deault mapper for data members.
5907   if (S.getLangOpts().OpenMP < 50)
5908     return;
5909   SmallVector<OMPClause *, 4> ImplicitMaps;
5910   for (int Cnt = 0, EndCnt = Clauses.size(); Cnt < EndCnt; ++Cnt) {
5911     auto *C = dyn_cast<OMPMapClause>(Clauses[Cnt]);
5912     if (!C)
5913       continue;
5914     SmallVector<Expr *, 4> SubExprs;
5915     auto *MI = C->mapperlist_begin();
5916     for (auto I = C->varlist_begin(), End = C->varlist_end(); I != End;
5917          ++I, ++MI) {
5918       // Expression is mapped using mapper - skip it.
5919       if (*MI)
5920         continue;
5921       Expr *E = *I;
5922       // Expression is dependent - skip it, build the mapper when it gets
5923       // instantiated.
5924       if (E->isTypeDependent() || E->isValueDependent() ||
5925           E->containsUnexpandedParameterPack())
5926         continue;
5927       // Array section - need to check for the mapping of the array section
5928       // element.
5929       QualType CanonType = E->getType().getCanonicalType();
5930       if (CanonType->isSpecificBuiltinType(BuiltinType::OMPArraySection)) {
5931         const auto *OASE = cast<OMPArraySectionExpr>(E->IgnoreParenImpCasts());
5932         QualType BaseType =
5933             OMPArraySectionExpr::getBaseOriginalType(OASE->getBase());
5934         QualType ElemType;
5935         if (const auto *ATy = BaseType->getAsArrayTypeUnsafe())
5936           ElemType = ATy->getElementType();
5937         else
5938           ElemType = BaseType->getPointeeType();
5939         CanonType = ElemType;
5940       }
5941 
5942       // DFS over data members in structures/classes.
5943       SmallVector<std::pair<QualType, FieldDecl *>, 4> Types(
5944           1, {CanonType, nullptr});
5945       llvm::DenseMap<const Type *, Expr *> Visited;
5946       SmallVector<std::pair<FieldDecl *, unsigned>, 4> ParentChain(
5947           1, {nullptr, 1});
5948       while (!Types.empty()) {
5949         QualType BaseType;
5950         FieldDecl *CurFD;
5951         std::tie(BaseType, CurFD) = Types.pop_back_val();
5952         while (ParentChain.back().second == 0)
5953           ParentChain.pop_back();
5954         --ParentChain.back().second;
5955         if (BaseType.isNull())
5956           continue;
5957         // Only structs/classes are allowed to have mappers.
5958         const RecordDecl *RD = BaseType.getCanonicalType()->getAsRecordDecl();
5959         if (!RD)
5960           continue;
5961         auto It = Visited.find(BaseType.getTypePtr());
5962         if (It == Visited.end()) {
5963           // Try to find the associated user-defined mapper.
5964           CXXScopeSpec MapperIdScopeSpec;
5965           DeclarationNameInfo DefaultMapperId;
5966           DefaultMapperId.setName(S.Context.DeclarationNames.getIdentifier(
5967               &S.Context.Idents.get("default")));
5968           DefaultMapperId.setLoc(E->getExprLoc());
5969           ExprResult ER = buildUserDefinedMapperRef(
5970               S, Stack->getCurScope(), MapperIdScopeSpec, DefaultMapperId,
5971               BaseType, /*UnresolvedMapper=*/nullptr);
5972           if (ER.isInvalid())
5973             continue;
5974           It = Visited.try_emplace(BaseType.getTypePtr(), ER.get()).first;
5975         }
5976         // Found default mapper.
5977         if (It->second) {
5978           auto *OE = new (S.Context) OpaqueValueExpr(E->getExprLoc(), CanonType,
5979                                                      VK_LValue, OK_Ordinary, E);
5980           OE->setIsUnique(/*V=*/true);
5981           Expr *BaseExpr = OE;
5982           for (const auto &P : ParentChain) {
5983             if (P.first) {
5984               BaseExpr = S.BuildMemberExpr(
5985                   BaseExpr, /*IsArrow=*/false, E->getExprLoc(),
5986                   NestedNameSpecifierLoc(), SourceLocation(), P.first,
5987                   DeclAccessPair::make(P.first, P.first->getAccess()),
5988                   /*HadMultipleCandidates=*/false, DeclarationNameInfo(),
5989                   P.first->getType(), VK_LValue, OK_Ordinary);
5990               BaseExpr = S.DefaultLvalueConversion(BaseExpr).get();
5991             }
5992           }
5993           if (CurFD)
5994             BaseExpr = S.BuildMemberExpr(
5995                 BaseExpr, /*IsArrow=*/false, E->getExprLoc(),
5996                 NestedNameSpecifierLoc(), SourceLocation(), CurFD,
5997                 DeclAccessPair::make(CurFD, CurFD->getAccess()),
5998                 /*HadMultipleCandidates=*/false, DeclarationNameInfo(),
5999                 CurFD->getType(), VK_LValue, OK_Ordinary);
6000           SubExprs.push_back(BaseExpr);
6001           continue;
6002         }
6003         // Check for the "default" mapper for data members.
6004         bool FirstIter = true;
6005         for (FieldDecl *FD : RD->fields()) {
6006           if (!FD)
6007             continue;
6008           QualType FieldTy = FD->getType();
6009           if (FieldTy.isNull() ||
6010               !(FieldTy->isStructureOrClassType() || FieldTy->isUnionType()))
6011             continue;
6012           if (FirstIter) {
6013             FirstIter = false;
6014             ParentChain.emplace_back(CurFD, 1);
6015           } else {
6016             ++ParentChain.back().second;
6017           }
6018           Types.emplace_back(FieldTy, FD);
6019         }
6020       }
6021     }
6022     if (SubExprs.empty())
6023       continue;
6024     CXXScopeSpec MapperIdScopeSpec;
6025     DeclarationNameInfo MapperId;
6026     if (OMPClause *NewClause = S.ActOnOpenMPMapClause(
6027             C->getMapTypeModifiers(), C->getMapTypeModifiersLoc(),
6028             MapperIdScopeSpec, MapperId, C->getMapType(),
6029             /*IsMapTypeImplicit=*/true, SourceLocation(), SourceLocation(),
6030             SubExprs, OMPVarListLocTy()))
6031       Clauses.push_back(NewClause);
6032   }
6033 }
6034 
6035 StmtResult Sema::ActOnOpenMPExecutableDirective(
6036     OpenMPDirectiveKind Kind, const DeclarationNameInfo &DirName,
6037     OpenMPDirectiveKind CancelRegion, ArrayRef<OMPClause *> Clauses,
6038     Stmt *AStmt, SourceLocation StartLoc, SourceLocation EndLoc) {
6039   StmtResult Res = StmtError();
6040   OpenMPBindClauseKind BindKind = OMPC_BIND_unknown;
6041   if (const OMPBindClause *BC =
6042           OMPExecutableDirective::getSingleClause<OMPBindClause>(Clauses))
6043     BindKind = BC->getBindKind();
6044   // First check CancelRegion which is then used in checkNestingOfRegions.
6045   if (checkCancelRegion(*this, Kind, CancelRegion, StartLoc) ||
6046       checkNestingOfRegions(*this, DSAStack, Kind, DirName, CancelRegion,
6047                             BindKind, StartLoc))
6048     return StmtError();
6049 
6050   llvm::SmallVector<OMPClause *, 8> ClausesWithImplicit;
6051   VarsWithInheritedDSAType VarsWithInheritedDSA;
6052   bool ErrorFound = false;
6053   ClausesWithImplicit.append(Clauses.begin(), Clauses.end());
6054   if (AStmt && !CurContext->isDependentContext() && Kind != OMPD_atomic &&
6055       Kind != OMPD_critical && Kind != OMPD_section && Kind != OMPD_master &&
6056       Kind != OMPD_masked && !isOpenMPLoopTransformationDirective(Kind)) {
6057     assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
6058 
6059     // Check default data sharing attributes for referenced variables.
6060     DSAAttrChecker DSAChecker(DSAStack, *this, cast<CapturedStmt>(AStmt));
6061     int ThisCaptureLevel = getOpenMPCaptureLevels(Kind);
6062     Stmt *S = AStmt;
6063     while (--ThisCaptureLevel >= 0)
6064       S = cast<CapturedStmt>(S)->getCapturedStmt();
6065     DSAChecker.Visit(S);
6066     if (!isOpenMPTargetDataManagementDirective(Kind) &&
6067         !isOpenMPTaskingDirective(Kind)) {
6068       // Visit subcaptures to generate implicit clauses for captured vars.
6069       auto *CS = cast<CapturedStmt>(AStmt);
6070       SmallVector<OpenMPDirectiveKind, 4> CaptureRegions;
6071       getOpenMPCaptureRegions(CaptureRegions, Kind);
6072       // Ignore outer tasking regions for target directives.
6073       if (CaptureRegions.size() > 1 && CaptureRegions.front() == OMPD_task)
6074         CS = cast<CapturedStmt>(CS->getCapturedStmt());
6075       DSAChecker.visitSubCaptures(CS);
6076     }
6077     if (DSAChecker.isErrorFound())
6078       return StmtError();
6079     // Generate list of implicitly defined firstprivate variables.
6080     VarsWithInheritedDSA = DSAChecker.getVarsWithInheritedDSA();
6081 
6082     SmallVector<Expr *, 4> ImplicitFirstprivates(
6083         DSAChecker.getImplicitFirstprivate().begin(),
6084         DSAChecker.getImplicitFirstprivate().end());
6085     SmallVector<Expr *, 4> ImplicitPrivates(
6086         DSAChecker.getImplicitPrivate().begin(),
6087         DSAChecker.getImplicitPrivate().end());
6088     const unsigned DefaultmapKindNum = OMPC_DEFAULTMAP_pointer + 1;
6089     SmallVector<Expr *, 4> ImplicitMaps[DefaultmapKindNum][OMPC_MAP_delete];
6090     SmallVector<OpenMPMapModifierKind, NumberOfOMPMapClauseModifiers>
6091         ImplicitMapModifiers[DefaultmapKindNum];
6092     SmallVector<SourceLocation, NumberOfOMPMapClauseModifiers>
6093         ImplicitMapModifiersLoc[DefaultmapKindNum];
6094     // Get the original location of present modifier from Defaultmap clause.
6095     SourceLocation PresentModifierLocs[DefaultmapKindNum];
6096     for (OMPClause *C : Clauses) {
6097       if (auto *DMC = dyn_cast<OMPDefaultmapClause>(C))
6098         if (DMC->getDefaultmapModifier() == OMPC_DEFAULTMAP_MODIFIER_present)
6099           PresentModifierLocs[DMC->getDefaultmapKind()] =
6100               DMC->getDefaultmapModifierLoc();
6101     }
6102     for (unsigned VC = 0; VC < DefaultmapKindNum; ++VC) {
6103       auto Kind = static_cast<OpenMPDefaultmapClauseKind>(VC);
6104       for (unsigned I = 0; I < OMPC_MAP_delete; ++I) {
6105         ArrayRef<Expr *> ImplicitMap = DSAChecker.getImplicitMap(
6106             Kind, static_cast<OpenMPMapClauseKind>(I));
6107         ImplicitMaps[VC][I].append(ImplicitMap.begin(), ImplicitMap.end());
6108       }
6109       ArrayRef<OpenMPMapModifierKind> ImplicitModifier =
6110           DSAChecker.getImplicitMapModifier(Kind);
6111       ImplicitMapModifiers[VC].append(ImplicitModifier.begin(),
6112                                       ImplicitModifier.end());
6113       std::fill_n(std::back_inserter(ImplicitMapModifiersLoc[VC]),
6114                   ImplicitModifier.size(), PresentModifierLocs[VC]);
6115     }
6116     // Mark taskgroup task_reduction descriptors as implicitly firstprivate.
6117     for (OMPClause *C : Clauses) {
6118       if (auto *IRC = dyn_cast<OMPInReductionClause>(C)) {
6119         for (Expr *E : IRC->taskgroup_descriptors())
6120           if (E)
6121             ImplicitFirstprivates.emplace_back(E);
6122       }
6123       // OpenMP 5.0, 2.10.1 task Construct
6124       // [detach clause]... The event-handle will be considered as if it was
6125       // specified on a firstprivate clause.
6126       if (auto *DC = dyn_cast<OMPDetachClause>(C))
6127         ImplicitFirstprivates.push_back(DC->getEventHandler());
6128     }
6129     if (!ImplicitFirstprivates.empty()) {
6130       if (OMPClause *Implicit = ActOnOpenMPFirstprivateClause(
6131               ImplicitFirstprivates, SourceLocation(), SourceLocation(),
6132               SourceLocation())) {
6133         ClausesWithImplicit.push_back(Implicit);
6134         ErrorFound = cast<OMPFirstprivateClause>(Implicit)->varlist_size() !=
6135                      ImplicitFirstprivates.size();
6136       } else {
6137         ErrorFound = true;
6138       }
6139     }
6140     if (!ImplicitPrivates.empty()) {
6141       if (OMPClause *Implicit =
6142               ActOnOpenMPPrivateClause(ImplicitPrivates, SourceLocation(),
6143                                        SourceLocation(), SourceLocation())) {
6144         ClausesWithImplicit.push_back(Implicit);
6145         ErrorFound = cast<OMPPrivateClause>(Implicit)->varlist_size() !=
6146                      ImplicitPrivates.size();
6147       } else {
6148         ErrorFound = true;
6149       }
6150     }
6151     // OpenMP 5.0 [2.19.7]
6152     // If a list item appears in a reduction, lastprivate or linear
6153     // clause on a combined target construct then it is treated as
6154     // if it also appears in a map clause with a map-type of tofrom
6155     if (getLangOpts().OpenMP >= 50 && Kind != OMPD_target &&
6156         isOpenMPTargetExecutionDirective(Kind)) {
6157       SmallVector<Expr *, 4> ImplicitExprs;
6158       for (OMPClause *C : Clauses) {
6159         if (auto *RC = dyn_cast<OMPReductionClause>(C))
6160           for (Expr *E : RC->varlists())
6161             if (!isa<DeclRefExpr>(E->IgnoreParenImpCasts()))
6162               ImplicitExprs.emplace_back(E);
6163       }
6164       if (!ImplicitExprs.empty()) {
6165         ArrayRef<Expr *> Exprs = ImplicitExprs;
6166         CXXScopeSpec MapperIdScopeSpec;
6167         DeclarationNameInfo MapperId;
6168         if (OMPClause *Implicit = ActOnOpenMPMapClause(
6169                 OMPC_MAP_MODIFIER_unknown, SourceLocation(), MapperIdScopeSpec,
6170                 MapperId, OMPC_MAP_tofrom,
6171                 /*IsMapTypeImplicit=*/true, SourceLocation(), SourceLocation(),
6172                 Exprs, OMPVarListLocTy(), /*NoDiagnose=*/true))
6173           ClausesWithImplicit.emplace_back(Implicit);
6174       }
6175     }
6176     for (unsigned I = 0, E = DefaultmapKindNum; I < E; ++I) {
6177       int ClauseKindCnt = -1;
6178       for (ArrayRef<Expr *> ImplicitMap : ImplicitMaps[I]) {
6179         ++ClauseKindCnt;
6180         if (ImplicitMap.empty())
6181           continue;
6182         CXXScopeSpec MapperIdScopeSpec;
6183         DeclarationNameInfo MapperId;
6184         auto Kind = static_cast<OpenMPMapClauseKind>(ClauseKindCnt);
6185         if (OMPClause *Implicit = ActOnOpenMPMapClause(
6186                 ImplicitMapModifiers[I], ImplicitMapModifiersLoc[I],
6187                 MapperIdScopeSpec, MapperId, Kind, /*IsMapTypeImplicit=*/true,
6188                 SourceLocation(), SourceLocation(), ImplicitMap,
6189                 OMPVarListLocTy())) {
6190           ClausesWithImplicit.emplace_back(Implicit);
6191           ErrorFound |= cast<OMPMapClause>(Implicit)->varlist_size() !=
6192                         ImplicitMap.size();
6193         } else {
6194           ErrorFound = true;
6195         }
6196       }
6197     }
6198     // Build expressions for implicit maps of data members with 'default'
6199     // mappers.
6200     if (LangOpts.OpenMP >= 50)
6201       processImplicitMapsWithDefaultMappers(*this, DSAStack,
6202                                             ClausesWithImplicit);
6203   }
6204 
6205   llvm::SmallVector<OpenMPDirectiveKind, 4> AllowedNameModifiers;
6206   switch (Kind) {
6207   case OMPD_parallel:
6208     Res = ActOnOpenMPParallelDirective(ClausesWithImplicit, AStmt, StartLoc,
6209                                        EndLoc);
6210     AllowedNameModifiers.push_back(OMPD_parallel);
6211     break;
6212   case OMPD_simd:
6213     Res = ActOnOpenMPSimdDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc,
6214                                    VarsWithInheritedDSA);
6215     if (LangOpts.OpenMP >= 50)
6216       AllowedNameModifiers.push_back(OMPD_simd);
6217     break;
6218   case OMPD_tile:
6219     Res =
6220         ActOnOpenMPTileDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc);
6221     break;
6222   case OMPD_unroll:
6223     Res = ActOnOpenMPUnrollDirective(ClausesWithImplicit, AStmt, StartLoc,
6224                                      EndLoc);
6225     break;
6226   case OMPD_for:
6227     Res = ActOnOpenMPForDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc,
6228                                   VarsWithInheritedDSA);
6229     break;
6230   case OMPD_for_simd:
6231     Res = ActOnOpenMPForSimdDirective(ClausesWithImplicit, AStmt, StartLoc,
6232                                       EndLoc, VarsWithInheritedDSA);
6233     if (LangOpts.OpenMP >= 50)
6234       AllowedNameModifiers.push_back(OMPD_simd);
6235     break;
6236   case OMPD_sections:
6237     Res = ActOnOpenMPSectionsDirective(ClausesWithImplicit, AStmt, StartLoc,
6238                                        EndLoc);
6239     break;
6240   case OMPD_section:
6241     assert(ClausesWithImplicit.empty() &&
6242            "No clauses are allowed for 'omp section' directive");
6243     Res = ActOnOpenMPSectionDirective(AStmt, StartLoc, EndLoc);
6244     break;
6245   case OMPD_single:
6246     Res = ActOnOpenMPSingleDirective(ClausesWithImplicit, AStmt, StartLoc,
6247                                      EndLoc);
6248     break;
6249   case OMPD_master:
6250     assert(ClausesWithImplicit.empty() &&
6251            "No clauses are allowed for 'omp master' directive");
6252     Res = ActOnOpenMPMasterDirective(AStmt, StartLoc, EndLoc);
6253     break;
6254   case OMPD_masked:
6255     Res = ActOnOpenMPMaskedDirective(ClausesWithImplicit, AStmt, StartLoc,
6256                                      EndLoc);
6257     break;
6258   case OMPD_critical:
6259     Res = ActOnOpenMPCriticalDirective(DirName, ClausesWithImplicit, AStmt,
6260                                        StartLoc, EndLoc);
6261     break;
6262   case OMPD_parallel_for:
6263     Res = ActOnOpenMPParallelForDirective(ClausesWithImplicit, AStmt, StartLoc,
6264                                           EndLoc, VarsWithInheritedDSA);
6265     AllowedNameModifiers.push_back(OMPD_parallel);
6266     break;
6267   case OMPD_parallel_for_simd:
6268     Res = ActOnOpenMPParallelForSimdDirective(
6269         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6270     AllowedNameModifiers.push_back(OMPD_parallel);
6271     if (LangOpts.OpenMP >= 50)
6272       AllowedNameModifiers.push_back(OMPD_simd);
6273     break;
6274   case OMPD_parallel_master:
6275     Res = ActOnOpenMPParallelMasterDirective(ClausesWithImplicit, AStmt,
6276                                              StartLoc, EndLoc);
6277     AllowedNameModifiers.push_back(OMPD_parallel);
6278     break;
6279   case OMPD_parallel_masked:
6280     Res = ActOnOpenMPParallelMaskedDirective(ClausesWithImplicit, AStmt,
6281                                              StartLoc, EndLoc);
6282     AllowedNameModifiers.push_back(OMPD_parallel);
6283     break;
6284   case OMPD_parallel_sections:
6285     Res = ActOnOpenMPParallelSectionsDirective(ClausesWithImplicit, AStmt,
6286                                                StartLoc, EndLoc);
6287     AllowedNameModifiers.push_back(OMPD_parallel);
6288     break;
6289   case OMPD_task:
6290     Res =
6291         ActOnOpenMPTaskDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc);
6292     AllowedNameModifiers.push_back(OMPD_task);
6293     break;
6294   case OMPD_taskyield:
6295     assert(ClausesWithImplicit.empty() &&
6296            "No clauses are allowed for 'omp taskyield' directive");
6297     assert(AStmt == nullptr &&
6298            "No associated statement allowed for 'omp taskyield' directive");
6299     Res = ActOnOpenMPTaskyieldDirective(StartLoc, EndLoc);
6300     break;
6301   case OMPD_barrier:
6302     assert(ClausesWithImplicit.empty() &&
6303            "No clauses are allowed for 'omp barrier' directive");
6304     assert(AStmt == nullptr &&
6305            "No associated statement allowed for 'omp barrier' directive");
6306     Res = ActOnOpenMPBarrierDirective(StartLoc, EndLoc);
6307     break;
6308   case OMPD_taskwait:
6309     assert(AStmt == nullptr &&
6310            "No associated statement allowed for 'omp taskwait' directive");
6311     Res = ActOnOpenMPTaskwaitDirective(ClausesWithImplicit, StartLoc, EndLoc);
6312     break;
6313   case OMPD_taskgroup:
6314     Res = ActOnOpenMPTaskgroupDirective(ClausesWithImplicit, AStmt, StartLoc,
6315                                         EndLoc);
6316     break;
6317   case OMPD_flush:
6318     assert(AStmt == nullptr &&
6319            "No associated statement allowed for 'omp flush' directive");
6320     Res = ActOnOpenMPFlushDirective(ClausesWithImplicit, StartLoc, EndLoc);
6321     break;
6322   case OMPD_depobj:
6323     assert(AStmt == nullptr &&
6324            "No associated statement allowed for 'omp depobj' directive");
6325     Res = ActOnOpenMPDepobjDirective(ClausesWithImplicit, StartLoc, EndLoc);
6326     break;
6327   case OMPD_scan:
6328     assert(AStmt == nullptr &&
6329            "No associated statement allowed for 'omp scan' directive");
6330     Res = ActOnOpenMPScanDirective(ClausesWithImplicit, StartLoc, EndLoc);
6331     break;
6332   case OMPD_ordered:
6333     Res = ActOnOpenMPOrderedDirective(ClausesWithImplicit, AStmt, StartLoc,
6334                                       EndLoc);
6335     break;
6336   case OMPD_atomic:
6337     Res = ActOnOpenMPAtomicDirective(ClausesWithImplicit, AStmt, StartLoc,
6338                                      EndLoc);
6339     break;
6340   case OMPD_teams:
6341     Res =
6342         ActOnOpenMPTeamsDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc);
6343     break;
6344   case OMPD_target:
6345     Res = ActOnOpenMPTargetDirective(ClausesWithImplicit, AStmt, StartLoc,
6346                                      EndLoc);
6347     AllowedNameModifiers.push_back(OMPD_target);
6348     break;
6349   case OMPD_target_parallel:
6350     Res = ActOnOpenMPTargetParallelDirective(ClausesWithImplicit, AStmt,
6351                                              StartLoc, EndLoc);
6352     AllowedNameModifiers.push_back(OMPD_target);
6353     AllowedNameModifiers.push_back(OMPD_parallel);
6354     break;
6355   case OMPD_target_parallel_for:
6356     Res = ActOnOpenMPTargetParallelForDirective(
6357         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6358     AllowedNameModifiers.push_back(OMPD_target);
6359     AllowedNameModifiers.push_back(OMPD_parallel);
6360     break;
6361   case OMPD_cancellation_point:
6362     assert(ClausesWithImplicit.empty() &&
6363            "No clauses are allowed for 'omp cancellation point' directive");
6364     assert(AStmt == nullptr && "No associated statement allowed for 'omp "
6365                                "cancellation point' directive");
6366     Res = ActOnOpenMPCancellationPointDirective(StartLoc, EndLoc, CancelRegion);
6367     break;
6368   case OMPD_cancel:
6369     assert(AStmt == nullptr &&
6370            "No associated statement allowed for 'omp cancel' directive");
6371     Res = ActOnOpenMPCancelDirective(ClausesWithImplicit, StartLoc, EndLoc,
6372                                      CancelRegion);
6373     AllowedNameModifiers.push_back(OMPD_cancel);
6374     break;
6375   case OMPD_target_data:
6376     Res = ActOnOpenMPTargetDataDirective(ClausesWithImplicit, AStmt, StartLoc,
6377                                          EndLoc);
6378     AllowedNameModifiers.push_back(OMPD_target_data);
6379     break;
6380   case OMPD_target_enter_data:
6381     Res = ActOnOpenMPTargetEnterDataDirective(ClausesWithImplicit, StartLoc,
6382                                               EndLoc, AStmt);
6383     AllowedNameModifiers.push_back(OMPD_target_enter_data);
6384     break;
6385   case OMPD_target_exit_data:
6386     Res = ActOnOpenMPTargetExitDataDirective(ClausesWithImplicit, StartLoc,
6387                                              EndLoc, AStmt);
6388     AllowedNameModifiers.push_back(OMPD_target_exit_data);
6389     break;
6390   case OMPD_taskloop:
6391     Res = ActOnOpenMPTaskLoopDirective(ClausesWithImplicit, AStmt, StartLoc,
6392                                        EndLoc, VarsWithInheritedDSA);
6393     AllowedNameModifiers.push_back(OMPD_taskloop);
6394     break;
6395   case OMPD_taskloop_simd:
6396     Res = ActOnOpenMPTaskLoopSimdDirective(ClausesWithImplicit, AStmt, StartLoc,
6397                                            EndLoc, VarsWithInheritedDSA);
6398     AllowedNameModifiers.push_back(OMPD_taskloop);
6399     if (LangOpts.OpenMP >= 50)
6400       AllowedNameModifiers.push_back(OMPD_simd);
6401     break;
6402   case OMPD_master_taskloop:
6403     Res = ActOnOpenMPMasterTaskLoopDirective(
6404         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6405     AllowedNameModifiers.push_back(OMPD_taskloop);
6406     break;
6407   case OMPD_masked_taskloop:
6408     Res = ActOnOpenMPMaskedTaskLoopDirective(
6409         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6410     AllowedNameModifiers.push_back(OMPD_taskloop);
6411     break;
6412   case OMPD_master_taskloop_simd:
6413     Res = ActOnOpenMPMasterTaskLoopSimdDirective(
6414         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6415     AllowedNameModifiers.push_back(OMPD_taskloop);
6416     if (LangOpts.OpenMP >= 50)
6417       AllowedNameModifiers.push_back(OMPD_simd);
6418     break;
6419   case OMPD_masked_taskloop_simd:
6420     Res = ActOnOpenMPMaskedTaskLoopSimdDirective(
6421         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6422     if (LangOpts.OpenMP >= 51) {
6423       AllowedNameModifiers.push_back(OMPD_taskloop);
6424       AllowedNameModifiers.push_back(OMPD_simd);
6425     }
6426     break;
6427   case OMPD_parallel_master_taskloop:
6428     Res = ActOnOpenMPParallelMasterTaskLoopDirective(
6429         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6430     AllowedNameModifiers.push_back(OMPD_taskloop);
6431     AllowedNameModifiers.push_back(OMPD_parallel);
6432     break;
6433   case OMPD_parallel_masked_taskloop:
6434     Res = ActOnOpenMPParallelMaskedTaskLoopDirective(
6435         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6436     if (LangOpts.OpenMP >= 51) {
6437       AllowedNameModifiers.push_back(OMPD_taskloop);
6438       AllowedNameModifiers.push_back(OMPD_parallel);
6439     }
6440     break;
6441   case OMPD_parallel_master_taskloop_simd:
6442     Res = ActOnOpenMPParallelMasterTaskLoopSimdDirective(
6443         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6444     AllowedNameModifiers.push_back(OMPD_taskloop);
6445     AllowedNameModifiers.push_back(OMPD_parallel);
6446     if (LangOpts.OpenMP >= 50)
6447       AllowedNameModifiers.push_back(OMPD_simd);
6448     break;
6449   case OMPD_parallel_masked_taskloop_simd:
6450     Res = ActOnOpenMPParallelMaskedTaskLoopSimdDirective(
6451         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6452     if (LangOpts.OpenMP >= 51) {
6453       AllowedNameModifiers.push_back(OMPD_taskloop);
6454       AllowedNameModifiers.push_back(OMPD_parallel);
6455       AllowedNameModifiers.push_back(OMPD_simd);
6456     }
6457     break;
6458   case OMPD_distribute:
6459     Res = ActOnOpenMPDistributeDirective(ClausesWithImplicit, AStmt, StartLoc,
6460                                          EndLoc, VarsWithInheritedDSA);
6461     break;
6462   case OMPD_target_update:
6463     Res = ActOnOpenMPTargetUpdateDirective(ClausesWithImplicit, StartLoc,
6464                                            EndLoc, AStmt);
6465     AllowedNameModifiers.push_back(OMPD_target_update);
6466     break;
6467   case OMPD_distribute_parallel_for:
6468     Res = ActOnOpenMPDistributeParallelForDirective(
6469         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6470     AllowedNameModifiers.push_back(OMPD_parallel);
6471     break;
6472   case OMPD_distribute_parallel_for_simd:
6473     Res = ActOnOpenMPDistributeParallelForSimdDirective(
6474         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6475     AllowedNameModifiers.push_back(OMPD_parallel);
6476     if (LangOpts.OpenMP >= 50)
6477       AllowedNameModifiers.push_back(OMPD_simd);
6478     break;
6479   case OMPD_distribute_simd:
6480     Res = ActOnOpenMPDistributeSimdDirective(
6481         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6482     if (LangOpts.OpenMP >= 50)
6483       AllowedNameModifiers.push_back(OMPD_simd);
6484     break;
6485   case OMPD_target_parallel_for_simd:
6486     Res = ActOnOpenMPTargetParallelForSimdDirective(
6487         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6488     AllowedNameModifiers.push_back(OMPD_target);
6489     AllowedNameModifiers.push_back(OMPD_parallel);
6490     if (LangOpts.OpenMP >= 50)
6491       AllowedNameModifiers.push_back(OMPD_simd);
6492     break;
6493   case OMPD_target_simd:
6494     Res = ActOnOpenMPTargetSimdDirective(ClausesWithImplicit, AStmt, StartLoc,
6495                                          EndLoc, VarsWithInheritedDSA);
6496     AllowedNameModifiers.push_back(OMPD_target);
6497     if (LangOpts.OpenMP >= 50)
6498       AllowedNameModifiers.push_back(OMPD_simd);
6499     break;
6500   case OMPD_teams_distribute:
6501     Res = ActOnOpenMPTeamsDistributeDirective(
6502         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6503     break;
6504   case OMPD_teams_distribute_simd:
6505     Res = ActOnOpenMPTeamsDistributeSimdDirective(
6506         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6507     if (LangOpts.OpenMP >= 50)
6508       AllowedNameModifiers.push_back(OMPD_simd);
6509     break;
6510   case OMPD_teams_distribute_parallel_for_simd:
6511     Res = ActOnOpenMPTeamsDistributeParallelForSimdDirective(
6512         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6513     AllowedNameModifiers.push_back(OMPD_parallel);
6514     if (LangOpts.OpenMP >= 50)
6515       AllowedNameModifiers.push_back(OMPD_simd);
6516     break;
6517   case OMPD_teams_distribute_parallel_for:
6518     Res = ActOnOpenMPTeamsDistributeParallelForDirective(
6519         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6520     AllowedNameModifiers.push_back(OMPD_parallel);
6521     break;
6522   case OMPD_target_teams:
6523     Res = ActOnOpenMPTargetTeamsDirective(ClausesWithImplicit, AStmt, StartLoc,
6524                                           EndLoc);
6525     AllowedNameModifiers.push_back(OMPD_target);
6526     break;
6527   case OMPD_target_teams_distribute:
6528     Res = ActOnOpenMPTargetTeamsDistributeDirective(
6529         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6530     AllowedNameModifiers.push_back(OMPD_target);
6531     break;
6532   case OMPD_target_teams_distribute_parallel_for:
6533     Res = ActOnOpenMPTargetTeamsDistributeParallelForDirective(
6534         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6535     AllowedNameModifiers.push_back(OMPD_target);
6536     AllowedNameModifiers.push_back(OMPD_parallel);
6537     break;
6538   case OMPD_target_teams_distribute_parallel_for_simd:
6539     Res = ActOnOpenMPTargetTeamsDistributeParallelForSimdDirective(
6540         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6541     AllowedNameModifiers.push_back(OMPD_target);
6542     AllowedNameModifiers.push_back(OMPD_parallel);
6543     if (LangOpts.OpenMP >= 50)
6544       AllowedNameModifiers.push_back(OMPD_simd);
6545     break;
6546   case OMPD_target_teams_distribute_simd:
6547     Res = ActOnOpenMPTargetTeamsDistributeSimdDirective(
6548         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6549     AllowedNameModifiers.push_back(OMPD_target);
6550     if (LangOpts.OpenMP >= 50)
6551       AllowedNameModifiers.push_back(OMPD_simd);
6552     break;
6553   case OMPD_interop:
6554     assert(AStmt == nullptr &&
6555            "No associated statement allowed for 'omp interop' directive");
6556     Res = ActOnOpenMPInteropDirective(ClausesWithImplicit, StartLoc, EndLoc);
6557     break;
6558   case OMPD_dispatch:
6559     Res = ActOnOpenMPDispatchDirective(ClausesWithImplicit, AStmt, StartLoc,
6560                                        EndLoc);
6561     break;
6562   case OMPD_loop:
6563     Res = ActOnOpenMPGenericLoopDirective(ClausesWithImplicit, AStmt, StartLoc,
6564                                           EndLoc, VarsWithInheritedDSA);
6565     break;
6566   case OMPD_teams_loop:
6567     Res = ActOnOpenMPTeamsGenericLoopDirective(
6568         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6569     break;
6570   case OMPD_target_teams_loop:
6571     Res = ActOnOpenMPTargetTeamsGenericLoopDirective(
6572         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6573     break;
6574   case OMPD_parallel_loop:
6575     Res = ActOnOpenMPParallelGenericLoopDirective(
6576         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6577     break;
6578   case OMPD_target_parallel_loop:
6579     Res = ActOnOpenMPTargetParallelGenericLoopDirective(
6580         ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA);
6581     break;
6582   case OMPD_declare_target:
6583   case OMPD_end_declare_target:
6584   case OMPD_threadprivate:
6585   case OMPD_allocate:
6586   case OMPD_declare_reduction:
6587   case OMPD_declare_mapper:
6588   case OMPD_declare_simd:
6589   case OMPD_requires:
6590   case OMPD_declare_variant:
6591   case OMPD_begin_declare_variant:
6592   case OMPD_end_declare_variant:
6593     llvm_unreachable("OpenMP Directive is not allowed");
6594   case OMPD_unknown:
6595   default:
6596     llvm_unreachable("Unknown OpenMP directive");
6597   }
6598 
6599   ErrorFound = Res.isInvalid() || ErrorFound;
6600 
6601   // Check variables in the clauses if default(none) or
6602   // default(firstprivate) was specified.
6603   if (DSAStack->getDefaultDSA() == DSA_none ||
6604       DSAStack->getDefaultDSA() == DSA_private ||
6605       DSAStack->getDefaultDSA() == DSA_firstprivate) {
6606     DSAAttrChecker DSAChecker(DSAStack, *this, nullptr);
6607     for (OMPClause *C : Clauses) {
6608       switch (C->getClauseKind()) {
6609       case OMPC_num_threads:
6610       case OMPC_dist_schedule:
6611         // Do not analyse if no parent teams directive.
6612         if (isOpenMPTeamsDirective(Kind))
6613           break;
6614         continue;
6615       case OMPC_if:
6616         if (isOpenMPTeamsDirective(Kind) &&
6617             cast<OMPIfClause>(C)->getNameModifier() != OMPD_target)
6618           break;
6619         if (isOpenMPParallelDirective(Kind) &&
6620             isOpenMPTaskLoopDirective(Kind) &&
6621             cast<OMPIfClause>(C)->getNameModifier() != OMPD_parallel)
6622           break;
6623         continue;
6624       case OMPC_schedule:
6625       case OMPC_detach:
6626         break;
6627       case OMPC_grainsize:
6628       case OMPC_num_tasks:
6629       case OMPC_final:
6630       case OMPC_priority:
6631       case OMPC_novariants:
6632       case OMPC_nocontext:
6633         // Do not analyze if no parent parallel directive.
6634         if (isOpenMPParallelDirective(Kind))
6635           break;
6636         continue;
6637       case OMPC_ordered:
6638       case OMPC_device:
6639       case OMPC_num_teams:
6640       case OMPC_thread_limit:
6641       case OMPC_hint:
6642       case OMPC_collapse:
6643       case OMPC_safelen:
6644       case OMPC_simdlen:
6645       case OMPC_sizes:
6646       case OMPC_default:
6647       case OMPC_proc_bind:
6648       case OMPC_private:
6649       case OMPC_firstprivate:
6650       case OMPC_lastprivate:
6651       case OMPC_shared:
6652       case OMPC_reduction:
6653       case OMPC_task_reduction:
6654       case OMPC_in_reduction:
6655       case OMPC_linear:
6656       case OMPC_aligned:
6657       case OMPC_copyin:
6658       case OMPC_copyprivate:
6659       case OMPC_nowait:
6660       case OMPC_untied:
6661       case OMPC_mergeable:
6662       case OMPC_allocate:
6663       case OMPC_read:
6664       case OMPC_write:
6665       case OMPC_update:
6666       case OMPC_capture:
6667       case OMPC_compare:
6668       case OMPC_seq_cst:
6669       case OMPC_acq_rel:
6670       case OMPC_acquire:
6671       case OMPC_release:
6672       case OMPC_relaxed:
6673       case OMPC_depend:
6674       case OMPC_threads:
6675       case OMPC_simd:
6676       case OMPC_map:
6677       case OMPC_nogroup:
6678       case OMPC_defaultmap:
6679       case OMPC_to:
6680       case OMPC_from:
6681       case OMPC_use_device_ptr:
6682       case OMPC_use_device_addr:
6683       case OMPC_is_device_ptr:
6684       case OMPC_has_device_addr:
6685       case OMPC_nontemporal:
6686       case OMPC_order:
6687       case OMPC_destroy:
6688       case OMPC_inclusive:
6689       case OMPC_exclusive:
6690       case OMPC_uses_allocators:
6691       case OMPC_affinity:
6692       case OMPC_bind:
6693       case OMPC_filter:
6694         continue;
6695       case OMPC_allocator:
6696       case OMPC_flush:
6697       case OMPC_depobj:
6698       case OMPC_threadprivate:
6699       case OMPC_uniform:
6700       case OMPC_unknown:
6701       case OMPC_unified_address:
6702       case OMPC_unified_shared_memory:
6703       case OMPC_reverse_offload:
6704       case OMPC_dynamic_allocators:
6705       case OMPC_atomic_default_mem_order:
6706       case OMPC_device_type:
6707       case OMPC_match:
6708       case OMPC_when:
6709       default:
6710         llvm_unreachable("Unexpected clause");
6711       }
6712       for (Stmt *CC : C->children()) {
6713         if (CC)
6714           DSAChecker.Visit(CC);
6715       }
6716     }
6717     for (const auto &P : DSAChecker.getVarsWithInheritedDSA())
6718       VarsWithInheritedDSA[P.getFirst()] = P.getSecond();
6719   }
6720   for (const auto &P : VarsWithInheritedDSA) {
6721     if (P.getFirst()->isImplicit() || isa<OMPCapturedExprDecl>(P.getFirst()))
6722       continue;
6723     ErrorFound = true;
6724     if (DSAStack->getDefaultDSA() == DSA_none ||
6725         DSAStack->getDefaultDSA() == DSA_private ||
6726         DSAStack->getDefaultDSA() == DSA_firstprivate) {
6727       Diag(P.second->getExprLoc(), diag::err_omp_no_dsa_for_variable)
6728           << P.first << P.second->getSourceRange();
6729       Diag(DSAStack->getDefaultDSALocation(), diag::note_omp_default_dsa_none);
6730     } else if (getLangOpts().OpenMP >= 50) {
6731       Diag(P.second->getExprLoc(),
6732            diag::err_omp_defaultmap_no_attr_for_variable)
6733           << P.first << P.second->getSourceRange();
6734       Diag(DSAStack->getDefaultDSALocation(),
6735            diag::note_omp_defaultmap_attr_none);
6736     }
6737   }
6738 
6739   if (!AllowedNameModifiers.empty())
6740     ErrorFound = checkIfClauses(*this, Kind, Clauses, AllowedNameModifiers) ||
6741                  ErrorFound;
6742 
6743   if (ErrorFound)
6744     return StmtError();
6745 
6746   if (!CurContext->isDependentContext() &&
6747       isOpenMPTargetExecutionDirective(Kind) &&
6748       !(DSAStack->hasRequiresDeclWithClause<OMPUnifiedSharedMemoryClause>() ||
6749         DSAStack->hasRequiresDeclWithClause<OMPUnifiedAddressClause>() ||
6750         DSAStack->hasRequiresDeclWithClause<OMPReverseOffloadClause>() ||
6751         DSAStack->hasRequiresDeclWithClause<OMPDynamicAllocatorsClause>())) {
6752     // Register target to DSA Stack.
6753     DSAStack->addTargetDirLocation(StartLoc);
6754   }
6755 
6756   return Res;
6757 }
6758 
6759 Sema::DeclGroupPtrTy Sema::ActOnOpenMPDeclareSimdDirective(
6760     DeclGroupPtrTy DG, OMPDeclareSimdDeclAttr::BranchStateTy BS, Expr *Simdlen,
6761     ArrayRef<Expr *> Uniforms, ArrayRef<Expr *> Aligneds,
6762     ArrayRef<Expr *> Alignments, ArrayRef<Expr *> Linears,
6763     ArrayRef<unsigned> LinModifiers, ArrayRef<Expr *> Steps, SourceRange SR) {
6764   assert(Aligneds.size() == Alignments.size());
6765   assert(Linears.size() == LinModifiers.size());
6766   assert(Linears.size() == Steps.size());
6767   if (!DG || DG.get().isNull())
6768     return DeclGroupPtrTy();
6769 
6770   const int SimdId = 0;
6771   if (!DG.get().isSingleDecl()) {
6772     Diag(SR.getBegin(), diag::err_omp_single_decl_in_declare_simd_variant)
6773         << SimdId;
6774     return DG;
6775   }
6776   Decl *ADecl = DG.get().getSingleDecl();
6777   if (auto *FTD = dyn_cast<FunctionTemplateDecl>(ADecl))
6778     ADecl = FTD->getTemplatedDecl();
6779 
6780   auto *FD = dyn_cast<FunctionDecl>(ADecl);
6781   if (!FD) {
6782     Diag(ADecl->getLocation(), diag::err_omp_function_expected) << SimdId;
6783     return DeclGroupPtrTy();
6784   }
6785 
6786   // OpenMP [2.8.2, declare simd construct, Description]
6787   // The parameter of the simdlen clause must be a constant positive integer
6788   // expression.
6789   ExprResult SL;
6790   if (Simdlen)
6791     SL = VerifyPositiveIntegerConstantInClause(Simdlen, OMPC_simdlen);
6792   // OpenMP [2.8.2, declare simd construct, Description]
6793   // The special this pointer can be used as if was one of the arguments to the
6794   // function in any of the linear, aligned, or uniform clauses.
6795   // The uniform clause declares one or more arguments to have an invariant
6796   // value for all concurrent invocations of the function in the execution of a
6797   // single SIMD loop.
6798   llvm::DenseMap<const Decl *, const Expr *> UniformedArgs;
6799   const Expr *UniformedLinearThis = nullptr;
6800   for (const Expr *E : Uniforms) {
6801     E = E->IgnoreParenImpCasts();
6802     if (const auto *DRE = dyn_cast<DeclRefExpr>(E))
6803       if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl()))
6804         if (FD->getNumParams() > PVD->getFunctionScopeIndex() &&
6805             FD->getParamDecl(PVD->getFunctionScopeIndex())
6806                     ->getCanonicalDecl() == PVD->getCanonicalDecl()) {
6807           UniformedArgs.try_emplace(PVD->getCanonicalDecl(), E);
6808           continue;
6809         }
6810     if (isa<CXXThisExpr>(E)) {
6811       UniformedLinearThis = E;
6812       continue;
6813     }
6814     Diag(E->getExprLoc(), diag::err_omp_param_or_this_in_clause)
6815         << FD->getDeclName() << (isa<CXXMethodDecl>(ADecl) ? 1 : 0);
6816   }
6817   // OpenMP [2.8.2, declare simd construct, Description]
6818   // The aligned clause declares that the object to which each list item points
6819   // is aligned to the number of bytes expressed in the optional parameter of
6820   // the aligned clause.
6821   // The special this pointer can be used as if was one of the arguments to the
6822   // function in any of the linear, aligned, or uniform clauses.
6823   // The type of list items appearing in the aligned clause must be array,
6824   // pointer, reference to array, or reference to pointer.
6825   llvm::DenseMap<const Decl *, const Expr *> AlignedArgs;
6826   const Expr *AlignedThis = nullptr;
6827   for (const Expr *E : Aligneds) {
6828     E = E->IgnoreParenImpCasts();
6829     if (const auto *DRE = dyn_cast<DeclRefExpr>(E))
6830       if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl())) {
6831         const VarDecl *CanonPVD = PVD->getCanonicalDecl();
6832         if (FD->getNumParams() > PVD->getFunctionScopeIndex() &&
6833             FD->getParamDecl(PVD->getFunctionScopeIndex())
6834                     ->getCanonicalDecl() == CanonPVD) {
6835           // OpenMP  [2.8.1, simd construct, Restrictions]
6836           // A list-item cannot appear in more than one aligned clause.
6837           if (AlignedArgs.count(CanonPVD) > 0) {
6838             Diag(E->getExprLoc(), diag::err_omp_used_in_clause_twice)
6839                 << 1 << getOpenMPClauseName(OMPC_aligned)
6840                 << E->getSourceRange();
6841             Diag(AlignedArgs[CanonPVD]->getExprLoc(),
6842                  diag::note_omp_explicit_dsa)
6843                 << getOpenMPClauseName(OMPC_aligned);
6844             continue;
6845           }
6846           AlignedArgs[CanonPVD] = E;
6847           QualType QTy = PVD->getType()
6848                              .getNonReferenceType()
6849                              .getUnqualifiedType()
6850                              .getCanonicalType();
6851           const Type *Ty = QTy.getTypePtrOrNull();
6852           if (!Ty || (!Ty->isArrayType() && !Ty->isPointerType())) {
6853             Diag(E->getExprLoc(), diag::err_omp_aligned_expected_array_or_ptr)
6854                 << QTy << getLangOpts().CPlusPlus << E->getSourceRange();
6855             Diag(PVD->getLocation(), diag::note_previous_decl) << PVD;
6856           }
6857           continue;
6858         }
6859       }
6860     if (isa<CXXThisExpr>(E)) {
6861       if (AlignedThis) {
6862         Diag(E->getExprLoc(), diag::err_omp_used_in_clause_twice)
6863             << 2 << getOpenMPClauseName(OMPC_aligned) << E->getSourceRange();
6864         Diag(AlignedThis->getExprLoc(), diag::note_omp_explicit_dsa)
6865             << getOpenMPClauseName(OMPC_aligned);
6866       }
6867       AlignedThis = E;
6868       continue;
6869     }
6870     Diag(E->getExprLoc(), diag::err_omp_param_or_this_in_clause)
6871         << FD->getDeclName() << (isa<CXXMethodDecl>(ADecl) ? 1 : 0);
6872   }
6873   // The optional parameter of the aligned clause, alignment, must be a constant
6874   // positive integer expression. If no optional parameter is specified,
6875   // implementation-defined default alignments for SIMD instructions on the
6876   // target platforms are assumed.
6877   SmallVector<const Expr *, 4> NewAligns;
6878   for (Expr *E : Alignments) {
6879     ExprResult Align;
6880     if (E)
6881       Align = VerifyPositiveIntegerConstantInClause(E, OMPC_aligned);
6882     NewAligns.push_back(Align.get());
6883   }
6884   // OpenMP [2.8.2, declare simd construct, Description]
6885   // The linear clause declares one or more list items to be private to a SIMD
6886   // lane and to have a linear relationship with respect to the iteration space
6887   // of a loop.
6888   // The special this pointer can be used as if was one of the arguments to the
6889   // function in any of the linear, aligned, or uniform clauses.
6890   // When a linear-step expression is specified in a linear clause it must be
6891   // either a constant integer expression or an integer-typed parameter that is
6892   // specified in a uniform clause on the directive.
6893   llvm::DenseMap<const Decl *, const Expr *> LinearArgs;
6894   const bool IsUniformedThis = UniformedLinearThis != nullptr;
6895   auto MI = LinModifiers.begin();
6896   for (const Expr *E : Linears) {
6897     auto LinKind = static_cast<OpenMPLinearClauseKind>(*MI);
6898     ++MI;
6899     E = E->IgnoreParenImpCasts();
6900     if (const auto *DRE = dyn_cast<DeclRefExpr>(E))
6901       if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl())) {
6902         const VarDecl *CanonPVD = PVD->getCanonicalDecl();
6903         if (FD->getNumParams() > PVD->getFunctionScopeIndex() &&
6904             FD->getParamDecl(PVD->getFunctionScopeIndex())
6905                     ->getCanonicalDecl() == CanonPVD) {
6906           // OpenMP  [2.15.3.7, linear Clause, Restrictions]
6907           // A list-item cannot appear in more than one linear clause.
6908           if (LinearArgs.count(CanonPVD) > 0) {
6909             Diag(E->getExprLoc(), diag::err_omp_wrong_dsa)
6910                 << getOpenMPClauseName(OMPC_linear)
6911                 << getOpenMPClauseName(OMPC_linear) << E->getSourceRange();
6912             Diag(LinearArgs[CanonPVD]->getExprLoc(),
6913                  diag::note_omp_explicit_dsa)
6914                 << getOpenMPClauseName(OMPC_linear);
6915             continue;
6916           }
6917           // Each argument can appear in at most one uniform or linear clause.
6918           if (UniformedArgs.count(CanonPVD) > 0) {
6919             Diag(E->getExprLoc(), diag::err_omp_wrong_dsa)
6920                 << getOpenMPClauseName(OMPC_linear)
6921                 << getOpenMPClauseName(OMPC_uniform) << E->getSourceRange();
6922             Diag(UniformedArgs[CanonPVD]->getExprLoc(),
6923                  diag::note_omp_explicit_dsa)
6924                 << getOpenMPClauseName(OMPC_uniform);
6925             continue;
6926           }
6927           LinearArgs[CanonPVD] = E;
6928           if (E->isValueDependent() || E->isTypeDependent() ||
6929               E->isInstantiationDependent() ||
6930               E->containsUnexpandedParameterPack())
6931             continue;
6932           (void)CheckOpenMPLinearDecl(CanonPVD, E->getExprLoc(), LinKind,
6933                                       PVD->getOriginalType(),
6934                                       /*IsDeclareSimd=*/true);
6935           continue;
6936         }
6937       }
6938     if (isa<CXXThisExpr>(E)) {
6939       if (UniformedLinearThis) {
6940         Diag(E->getExprLoc(), diag::err_omp_wrong_dsa)
6941             << getOpenMPClauseName(OMPC_linear)
6942             << getOpenMPClauseName(IsUniformedThis ? OMPC_uniform : OMPC_linear)
6943             << E->getSourceRange();
6944         Diag(UniformedLinearThis->getExprLoc(), diag::note_omp_explicit_dsa)
6945             << getOpenMPClauseName(IsUniformedThis ? OMPC_uniform
6946                                                    : OMPC_linear);
6947         continue;
6948       }
6949       UniformedLinearThis = E;
6950       if (E->isValueDependent() || E->isTypeDependent() ||
6951           E->isInstantiationDependent() || E->containsUnexpandedParameterPack())
6952         continue;
6953       (void)CheckOpenMPLinearDecl(/*D=*/nullptr, E->getExprLoc(), LinKind,
6954                                   E->getType(), /*IsDeclareSimd=*/true);
6955       continue;
6956     }
6957     Diag(E->getExprLoc(), diag::err_omp_param_or_this_in_clause)
6958         << FD->getDeclName() << (isa<CXXMethodDecl>(ADecl) ? 1 : 0);
6959   }
6960   Expr *Step = nullptr;
6961   Expr *NewStep = nullptr;
6962   SmallVector<Expr *, 4> NewSteps;
6963   for (Expr *E : Steps) {
6964     // Skip the same step expression, it was checked already.
6965     if (Step == E || !E) {
6966       NewSteps.push_back(E ? NewStep : nullptr);
6967       continue;
6968     }
6969     Step = E;
6970     if (const auto *DRE = dyn_cast<DeclRefExpr>(Step))
6971       if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl())) {
6972         const VarDecl *CanonPVD = PVD->getCanonicalDecl();
6973         if (UniformedArgs.count(CanonPVD) == 0) {
6974           Diag(Step->getExprLoc(), diag::err_omp_expected_uniform_param)
6975               << Step->getSourceRange();
6976         } else if (E->isValueDependent() || E->isTypeDependent() ||
6977                    E->isInstantiationDependent() ||
6978                    E->containsUnexpandedParameterPack() ||
6979                    CanonPVD->getType()->hasIntegerRepresentation()) {
6980           NewSteps.push_back(Step);
6981         } else {
6982           Diag(Step->getExprLoc(), diag::err_omp_expected_int_param)
6983               << Step->getSourceRange();
6984         }
6985         continue;
6986       }
6987     NewStep = Step;
6988     if (Step && !Step->isValueDependent() && !Step->isTypeDependent() &&
6989         !Step->isInstantiationDependent() &&
6990         !Step->containsUnexpandedParameterPack()) {
6991       NewStep = PerformOpenMPImplicitIntegerConversion(Step->getExprLoc(), Step)
6992                     .get();
6993       if (NewStep)
6994         NewStep =
6995             VerifyIntegerConstantExpression(NewStep, /*FIXME*/ AllowFold).get();
6996     }
6997     NewSteps.push_back(NewStep);
6998   }
6999   auto *NewAttr = OMPDeclareSimdDeclAttr::CreateImplicit(
7000       Context, BS, SL.get(), const_cast<Expr **>(Uniforms.data()),
7001       Uniforms.size(), const_cast<Expr **>(Aligneds.data()), Aligneds.size(),
7002       const_cast<Expr **>(NewAligns.data()), NewAligns.size(),
7003       const_cast<Expr **>(Linears.data()), Linears.size(),
7004       const_cast<unsigned *>(LinModifiers.data()), LinModifiers.size(),
7005       NewSteps.data(), NewSteps.size(), SR);
7006   ADecl->addAttr(NewAttr);
7007   return DG;
7008 }
7009 
7010 static void setPrototype(Sema &S, FunctionDecl *FD, FunctionDecl *FDWithProto,
7011                          QualType NewType) {
7012   assert(NewType->isFunctionProtoType() &&
7013          "Expected function type with prototype.");
7014   assert(FD->getType()->isFunctionNoProtoType() &&
7015          "Expected function with type with no prototype.");
7016   assert(FDWithProto->getType()->isFunctionProtoType() &&
7017          "Expected function with prototype.");
7018   // Synthesize parameters with the same types.
7019   FD->setType(NewType);
7020   SmallVector<ParmVarDecl *, 16> Params;
7021   for (const ParmVarDecl *P : FDWithProto->parameters()) {
7022     auto *Param = ParmVarDecl::Create(S.getASTContext(), FD, SourceLocation(),
7023                                       SourceLocation(), nullptr, P->getType(),
7024                                       /*TInfo=*/nullptr, SC_None, nullptr);
7025     Param->setScopeInfo(0, Params.size());
7026     Param->setImplicit();
7027     Params.push_back(Param);
7028   }
7029 
7030   FD->setParams(Params);
7031 }
7032 
7033 void Sema::ActOnFinishedFunctionDefinitionInOpenMPAssumeScope(Decl *D) {
7034   if (D->isInvalidDecl())
7035     return;
7036   FunctionDecl *FD = nullptr;
7037   if (auto *UTemplDecl = dyn_cast<FunctionTemplateDecl>(D))
7038     FD = UTemplDecl->getTemplatedDecl();
7039   else
7040     FD = cast<FunctionDecl>(D);
7041   assert(FD && "Expected a function declaration!");
7042 
7043   // If we are instantiating templates we do *not* apply scoped assumptions but
7044   // only global ones. We apply scoped assumption to the template definition
7045   // though.
7046   if (!inTemplateInstantiation()) {
7047     for (AssumptionAttr *AA : OMPAssumeScoped)
7048       FD->addAttr(AA);
7049   }
7050   for (AssumptionAttr *AA : OMPAssumeGlobal)
7051     FD->addAttr(AA);
7052 }
7053 
7054 Sema::OMPDeclareVariantScope::OMPDeclareVariantScope(OMPTraitInfo &TI)
7055     : TI(&TI), NameSuffix(TI.getMangledName()) {}
7056 
7057 void Sema::ActOnStartOfFunctionDefinitionInOpenMPDeclareVariantScope(
7058     Scope *S, Declarator &D, MultiTemplateParamsArg TemplateParamLists,
7059     SmallVectorImpl<FunctionDecl *> &Bases) {
7060   if (!D.getIdentifier())
7061     return;
7062 
7063   OMPDeclareVariantScope &DVScope = OMPDeclareVariantScopes.back();
7064 
7065   // Template specialization is an extension, check if we do it.
7066   bool IsTemplated = !TemplateParamLists.empty();
7067   if (IsTemplated &
7068       !DVScope.TI->isExtensionActive(
7069           llvm::omp::TraitProperty::implementation_extension_allow_templates))
7070     return;
7071 
7072   IdentifierInfo *BaseII = D.getIdentifier();
7073   LookupResult Lookup(*this, DeclarationName(BaseII), D.getIdentifierLoc(),
7074                       LookupOrdinaryName);
7075   LookupParsedName(Lookup, S, &D.getCXXScopeSpec());
7076 
7077   TypeSourceInfo *TInfo = GetTypeForDeclarator(D, S);
7078   QualType FType = TInfo->getType();
7079 
7080   bool IsConstexpr =
7081       D.getDeclSpec().getConstexprSpecifier() == ConstexprSpecKind::Constexpr;
7082   bool IsConsteval =
7083       D.getDeclSpec().getConstexprSpecifier() == ConstexprSpecKind::Consteval;
7084 
7085   for (auto *Candidate : Lookup) {
7086     auto *CandidateDecl = Candidate->getUnderlyingDecl();
7087     FunctionDecl *UDecl = nullptr;
7088     if (IsTemplated && isa<FunctionTemplateDecl>(CandidateDecl)) {
7089       auto *FTD = cast<FunctionTemplateDecl>(CandidateDecl);
7090       if (FTD->getTemplateParameters()->size() == TemplateParamLists.size())
7091         UDecl = FTD->getTemplatedDecl();
7092     } else if (!IsTemplated)
7093       UDecl = dyn_cast<FunctionDecl>(CandidateDecl);
7094     if (!UDecl)
7095       continue;
7096 
7097     // Don't specialize constexpr/consteval functions with
7098     // non-constexpr/consteval functions.
7099     if (UDecl->isConstexpr() && !IsConstexpr)
7100       continue;
7101     if (UDecl->isConsteval() && !IsConsteval)
7102       continue;
7103 
7104     QualType UDeclTy = UDecl->getType();
7105     if (!UDeclTy->isDependentType()) {
7106       QualType NewType = Context.mergeFunctionTypes(
7107           FType, UDeclTy, /* OfBlockPointer */ false,
7108           /* Unqualified */ false, /* AllowCXX */ true);
7109       if (NewType.isNull())
7110         continue;
7111     }
7112 
7113     // Found a base!
7114     Bases.push_back(UDecl);
7115   }
7116 
7117   bool UseImplicitBase = !DVScope.TI->isExtensionActive(
7118       llvm::omp::TraitProperty::implementation_extension_disable_implicit_base);
7119   // If no base was found we create a declaration that we use as base.
7120   if (Bases.empty() && UseImplicitBase) {
7121     D.setFunctionDefinitionKind(FunctionDefinitionKind::Declaration);
7122     Decl *BaseD = HandleDeclarator(S, D, TemplateParamLists);
7123     BaseD->setImplicit(true);
7124     if (auto *BaseTemplD = dyn_cast<FunctionTemplateDecl>(BaseD))
7125       Bases.push_back(BaseTemplD->getTemplatedDecl());
7126     else
7127       Bases.push_back(cast<FunctionDecl>(BaseD));
7128   }
7129 
7130   std::string MangledName;
7131   MangledName += D.getIdentifier()->getName();
7132   MangledName += getOpenMPVariantManglingSeparatorStr();
7133   MangledName += DVScope.NameSuffix;
7134   IdentifierInfo &VariantII = Context.Idents.get(MangledName);
7135 
7136   VariantII.setMangledOpenMPVariantName(true);
7137   D.SetIdentifier(&VariantII, D.getBeginLoc());
7138 }
7139 
7140 void Sema::ActOnFinishedFunctionDefinitionInOpenMPDeclareVariantScope(
7141     Decl *D, SmallVectorImpl<FunctionDecl *> &Bases) {
7142   // Do not mark function as is used to prevent its emission if this is the
7143   // only place where it is used.
7144   EnterExpressionEvaluationContext Unevaluated(
7145       *this, Sema::ExpressionEvaluationContext::Unevaluated);
7146 
7147   FunctionDecl *FD = nullptr;
7148   if (auto *UTemplDecl = dyn_cast<FunctionTemplateDecl>(D))
7149     FD = UTemplDecl->getTemplatedDecl();
7150   else
7151     FD = cast<FunctionDecl>(D);
7152   auto *VariantFuncRef = DeclRefExpr::Create(
7153       Context, NestedNameSpecifierLoc(), SourceLocation(), FD,
7154       /* RefersToEnclosingVariableOrCapture */ false,
7155       /* NameLoc */ FD->getLocation(), FD->getType(),
7156       ExprValueKind::VK_PRValue);
7157 
7158   OMPDeclareVariantScope &DVScope = OMPDeclareVariantScopes.back();
7159   auto *OMPDeclareVariantA = OMPDeclareVariantAttr::CreateImplicit(
7160       Context, VariantFuncRef, DVScope.TI,
7161       /*NothingArgs=*/nullptr, /*NothingArgsSize=*/0,
7162       /*NeedDevicePtrArgs=*/nullptr, /*NeedDevicePtrArgsSize=*/0,
7163       /*AppendArgs=*/nullptr, /*AppendArgsSize=*/0);
7164   for (FunctionDecl *BaseFD : Bases)
7165     BaseFD->addAttr(OMPDeclareVariantA);
7166 }
7167 
7168 ExprResult Sema::ActOnOpenMPCall(ExprResult Call, Scope *Scope,
7169                                  SourceLocation LParenLoc,
7170                                  MultiExprArg ArgExprs,
7171                                  SourceLocation RParenLoc, Expr *ExecConfig) {
7172   // The common case is a regular call we do not want to specialize at all. Try
7173   // to make that case fast by bailing early.
7174   CallExpr *CE = dyn_cast<CallExpr>(Call.get());
7175   if (!CE)
7176     return Call;
7177 
7178   FunctionDecl *CalleeFnDecl = CE->getDirectCallee();
7179   if (!CalleeFnDecl)
7180     return Call;
7181 
7182   if (!CalleeFnDecl->hasAttr<OMPDeclareVariantAttr>())
7183     return Call;
7184 
7185   ASTContext &Context = getASTContext();
7186   std::function<void(StringRef)> DiagUnknownTrait = [this,
7187                                                      CE](StringRef ISATrait) {
7188     // TODO Track the selector locations in a way that is accessible here to
7189     // improve the diagnostic location.
7190     Diag(CE->getBeginLoc(), diag::warn_unknown_declare_variant_isa_trait)
7191         << ISATrait;
7192   };
7193   TargetOMPContext OMPCtx(Context, std::move(DiagUnknownTrait),
7194                           getCurFunctionDecl(), DSAStack->getConstructTraits());
7195 
7196   QualType CalleeFnType = CalleeFnDecl->getType();
7197 
7198   SmallVector<Expr *, 4> Exprs;
7199   SmallVector<VariantMatchInfo, 4> VMIs;
7200   while (CalleeFnDecl) {
7201     for (OMPDeclareVariantAttr *A :
7202          CalleeFnDecl->specific_attrs<OMPDeclareVariantAttr>()) {
7203       Expr *VariantRef = A->getVariantFuncRef();
7204 
7205       VariantMatchInfo VMI;
7206       OMPTraitInfo &TI = A->getTraitInfo();
7207       TI.getAsVariantMatchInfo(Context, VMI);
7208       if (!isVariantApplicableInContext(VMI, OMPCtx,
7209                                         /* DeviceSetOnly */ false))
7210         continue;
7211 
7212       VMIs.push_back(VMI);
7213       Exprs.push_back(VariantRef);
7214     }
7215 
7216     CalleeFnDecl = CalleeFnDecl->getPreviousDecl();
7217   }
7218 
7219   ExprResult NewCall;
7220   do {
7221     int BestIdx = getBestVariantMatchForContext(VMIs, OMPCtx);
7222     if (BestIdx < 0)
7223       return Call;
7224     Expr *BestExpr = cast<DeclRefExpr>(Exprs[BestIdx]);
7225     Decl *BestDecl = cast<DeclRefExpr>(BestExpr)->getDecl();
7226 
7227     {
7228       // Try to build a (member) call expression for the current best applicable
7229       // variant expression. We allow this to fail in which case we continue
7230       // with the next best variant expression. The fail case is part of the
7231       // implementation defined behavior in the OpenMP standard when it talks
7232       // about what differences in the function prototypes: "Any differences
7233       // that the specific OpenMP context requires in the prototype of the
7234       // variant from the base function prototype are implementation defined."
7235       // This wording is there to allow the specialized variant to have a
7236       // different type than the base function. This is intended and OK but if
7237       // we cannot create a call the difference is not in the "implementation
7238       // defined range" we allow.
7239       Sema::TentativeAnalysisScope Trap(*this);
7240 
7241       if (auto *SpecializedMethod = dyn_cast<CXXMethodDecl>(BestDecl)) {
7242         auto *MemberCall = dyn_cast<CXXMemberCallExpr>(CE);
7243         BestExpr = MemberExpr::CreateImplicit(
7244             Context, MemberCall->getImplicitObjectArgument(),
7245             /* IsArrow */ false, SpecializedMethod, Context.BoundMemberTy,
7246             MemberCall->getValueKind(), MemberCall->getObjectKind());
7247       }
7248       NewCall = BuildCallExpr(Scope, BestExpr, LParenLoc, ArgExprs, RParenLoc,
7249                               ExecConfig);
7250       if (NewCall.isUsable()) {
7251         if (CallExpr *NCE = dyn_cast<CallExpr>(NewCall.get())) {
7252           FunctionDecl *NewCalleeFnDecl = NCE->getDirectCallee();
7253           QualType NewType = Context.mergeFunctionTypes(
7254               CalleeFnType, NewCalleeFnDecl->getType(),
7255               /* OfBlockPointer */ false,
7256               /* Unqualified */ false, /* AllowCXX */ true);
7257           if (!NewType.isNull())
7258             break;
7259           // Don't use the call if the function type was not compatible.
7260           NewCall = nullptr;
7261         }
7262       }
7263     }
7264 
7265     VMIs.erase(VMIs.begin() + BestIdx);
7266     Exprs.erase(Exprs.begin() + BestIdx);
7267   } while (!VMIs.empty());
7268 
7269   if (!NewCall.isUsable())
7270     return Call;
7271   return PseudoObjectExpr::Create(Context, CE, {NewCall.get()}, 0);
7272 }
7273 
7274 Optional<std::pair<FunctionDecl *, Expr *>>
7275 Sema::checkOpenMPDeclareVariantFunction(Sema::DeclGroupPtrTy DG,
7276                                         Expr *VariantRef, OMPTraitInfo &TI,
7277                                         unsigned NumAppendArgs,
7278                                         SourceRange SR) {
7279   if (!DG || DG.get().isNull())
7280     return None;
7281 
7282   const int VariantId = 1;
7283   // Must be applied only to single decl.
7284   if (!DG.get().isSingleDecl()) {
7285     Diag(SR.getBegin(), diag::err_omp_single_decl_in_declare_simd_variant)
7286         << VariantId << SR;
7287     return None;
7288   }
7289   Decl *ADecl = DG.get().getSingleDecl();
7290   if (auto *FTD = dyn_cast<FunctionTemplateDecl>(ADecl))
7291     ADecl = FTD->getTemplatedDecl();
7292 
7293   // Decl must be a function.
7294   auto *FD = dyn_cast<FunctionDecl>(ADecl);
7295   if (!FD) {
7296     Diag(ADecl->getLocation(), diag::err_omp_function_expected)
7297         << VariantId << SR;
7298     return None;
7299   }
7300 
7301   auto &&HasMultiVersionAttributes = [](const FunctionDecl *FD) {
7302     // The 'target' attribute needs to be separately checked because it does
7303     // not always signify a multiversion function declaration.
7304     return FD->isMultiVersion() || FD->hasAttr<TargetAttr>();
7305   };
7306   // OpenMP is not compatible with multiversion function attributes.
7307   if (HasMultiVersionAttributes(FD)) {
7308     Diag(FD->getLocation(), diag::err_omp_declare_variant_incompat_attributes)
7309         << SR;
7310     return None;
7311   }
7312 
7313   // Allow #pragma omp declare variant only if the function is not used.
7314   if (FD->isUsed(false))
7315     Diag(SR.getBegin(), diag::warn_omp_declare_variant_after_used)
7316         << FD->getLocation();
7317 
7318   // Check if the function was emitted already.
7319   const FunctionDecl *Definition;
7320   if (!FD->isThisDeclarationADefinition() && FD->isDefined(Definition) &&
7321       (LangOpts.EmitAllDecls || Context.DeclMustBeEmitted(Definition)))
7322     Diag(SR.getBegin(), diag::warn_omp_declare_variant_after_emitted)
7323         << FD->getLocation();
7324 
7325   // The VariantRef must point to function.
7326   if (!VariantRef) {
7327     Diag(SR.getBegin(), diag::err_omp_function_expected) << VariantId;
7328     return None;
7329   }
7330 
7331   auto ShouldDelayChecks = [](Expr *&E, bool) {
7332     return E && (E->isTypeDependent() || E->isValueDependent() ||
7333                  E->containsUnexpandedParameterPack() ||
7334                  E->isInstantiationDependent());
7335   };
7336   // Do not check templates, wait until instantiation.
7337   if (FD->isDependentContext() || ShouldDelayChecks(VariantRef, false) ||
7338       TI.anyScoreOrCondition(ShouldDelayChecks))
7339     return std::make_pair(FD, VariantRef);
7340 
7341   // Deal with non-constant score and user condition expressions.
7342   auto HandleNonConstantScoresAndConditions = [this](Expr *&E,
7343                                                      bool IsScore) -> bool {
7344     if (!E || E->isIntegerConstantExpr(Context))
7345       return false;
7346 
7347     if (IsScore) {
7348       // We warn on non-constant scores and pretend they were not present.
7349       Diag(E->getExprLoc(), diag::warn_omp_declare_variant_score_not_constant)
7350           << E;
7351       E = nullptr;
7352     } else {
7353       // We could replace a non-constant user condition with "false" but we
7354       // will soon need to handle these anyway for the dynamic version of
7355       // OpenMP context selectors.
7356       Diag(E->getExprLoc(),
7357            diag::err_omp_declare_variant_user_condition_not_constant)
7358           << E;
7359     }
7360     return true;
7361   };
7362   if (TI.anyScoreOrCondition(HandleNonConstantScoresAndConditions))
7363     return None;
7364 
7365   QualType AdjustedFnType = FD->getType();
7366   if (NumAppendArgs) {
7367     const auto *PTy = AdjustedFnType->getAsAdjusted<FunctionProtoType>();
7368     if (!PTy) {
7369       Diag(FD->getLocation(), diag::err_omp_declare_variant_prototype_required)
7370           << SR;
7371       return None;
7372     }
7373     // Adjust the function type to account for an extra omp_interop_t for each
7374     // specified in the append_args clause.
7375     const TypeDecl *TD = nullptr;
7376     LookupResult Result(*this, &Context.Idents.get("omp_interop_t"),
7377                         SR.getBegin(), Sema::LookupOrdinaryName);
7378     if (LookupName(Result, getCurScope())) {
7379       NamedDecl *ND = Result.getFoundDecl();
7380       TD = dyn_cast_or_null<TypeDecl>(ND);
7381     }
7382     if (!TD) {
7383       Diag(SR.getBegin(), diag::err_omp_interop_type_not_found) << SR;
7384       return None;
7385     }
7386     QualType InteropType = Context.getTypeDeclType(TD);
7387     if (PTy->isVariadic()) {
7388       Diag(FD->getLocation(), diag::err_omp_append_args_with_varargs) << SR;
7389       return None;
7390     }
7391     llvm::SmallVector<QualType, 8> Params;
7392     Params.append(PTy->param_type_begin(), PTy->param_type_end());
7393     Params.insert(Params.end(), NumAppendArgs, InteropType);
7394     AdjustedFnType = Context.getFunctionType(PTy->getReturnType(), Params,
7395                                              PTy->getExtProtoInfo());
7396   }
7397 
7398   // Convert VariantRef expression to the type of the original function to
7399   // resolve possible conflicts.
7400   ExprResult VariantRefCast = VariantRef;
7401   if (LangOpts.CPlusPlus) {
7402     QualType FnPtrType;
7403     auto *Method = dyn_cast<CXXMethodDecl>(FD);
7404     if (Method && !Method->isStatic()) {
7405       const Type *ClassType =
7406           Context.getTypeDeclType(Method->getParent()).getTypePtr();
7407       FnPtrType = Context.getMemberPointerType(AdjustedFnType, ClassType);
7408       ExprResult ER;
7409       {
7410         // Build adrr_of unary op to correctly handle type checks for member
7411         // functions.
7412         Sema::TentativeAnalysisScope Trap(*this);
7413         ER = CreateBuiltinUnaryOp(VariantRef->getBeginLoc(), UO_AddrOf,
7414                                   VariantRef);
7415       }
7416       if (!ER.isUsable()) {
7417         Diag(VariantRef->getExprLoc(), diag::err_omp_function_expected)
7418             << VariantId << VariantRef->getSourceRange();
7419         return None;
7420       }
7421       VariantRef = ER.get();
7422     } else {
7423       FnPtrType = Context.getPointerType(AdjustedFnType);
7424     }
7425     QualType VarianPtrType = Context.getPointerType(VariantRef->getType());
7426     if (VarianPtrType.getUnqualifiedType() != FnPtrType.getUnqualifiedType()) {
7427       ImplicitConversionSequence ICS = TryImplicitConversion(
7428           VariantRef, FnPtrType.getUnqualifiedType(),
7429           /*SuppressUserConversions=*/false, AllowedExplicit::None,
7430           /*InOverloadResolution=*/false,
7431           /*CStyle=*/false,
7432           /*AllowObjCWritebackConversion=*/false);
7433       if (ICS.isFailure()) {
7434         Diag(VariantRef->getExprLoc(),
7435              diag::err_omp_declare_variant_incompat_types)
7436             << VariantRef->getType()
7437             << ((Method && !Method->isStatic()) ? FnPtrType : FD->getType())
7438             << (NumAppendArgs ? 1 : 0) << VariantRef->getSourceRange();
7439         return None;
7440       }
7441       VariantRefCast = PerformImplicitConversion(
7442           VariantRef, FnPtrType.getUnqualifiedType(), AA_Converting);
7443       if (!VariantRefCast.isUsable())
7444         return None;
7445     }
7446     // Drop previously built artificial addr_of unary op for member functions.
7447     if (Method && !Method->isStatic()) {
7448       Expr *PossibleAddrOfVariantRef = VariantRefCast.get();
7449       if (auto *UO = dyn_cast<UnaryOperator>(
7450               PossibleAddrOfVariantRef->IgnoreImplicit()))
7451         VariantRefCast = UO->getSubExpr();
7452     }
7453   }
7454 
7455   ExprResult ER = CheckPlaceholderExpr(VariantRefCast.get());
7456   if (!ER.isUsable() ||
7457       !ER.get()->IgnoreParenImpCasts()->getType()->isFunctionType()) {
7458     Diag(VariantRef->getExprLoc(), diag::err_omp_function_expected)
7459         << VariantId << VariantRef->getSourceRange();
7460     return None;
7461   }
7462 
7463   // The VariantRef must point to function.
7464   auto *DRE = dyn_cast<DeclRefExpr>(ER.get()->IgnoreParenImpCasts());
7465   if (!DRE) {
7466     Diag(VariantRef->getExprLoc(), diag::err_omp_function_expected)
7467         << VariantId << VariantRef->getSourceRange();
7468     return None;
7469   }
7470   auto *NewFD = dyn_cast_or_null<FunctionDecl>(DRE->getDecl());
7471   if (!NewFD) {
7472     Diag(VariantRef->getExprLoc(), diag::err_omp_function_expected)
7473         << VariantId << VariantRef->getSourceRange();
7474     return None;
7475   }
7476 
7477   if (FD->getCanonicalDecl() == NewFD->getCanonicalDecl()) {
7478     Diag(VariantRef->getExprLoc(),
7479          diag::err_omp_declare_variant_same_base_function)
7480         << VariantRef->getSourceRange();
7481     return None;
7482   }
7483 
7484   // Check if function types are compatible in C.
7485   if (!LangOpts.CPlusPlus) {
7486     QualType NewType =
7487         Context.mergeFunctionTypes(AdjustedFnType, NewFD->getType());
7488     if (NewType.isNull()) {
7489       Diag(VariantRef->getExprLoc(),
7490            diag::err_omp_declare_variant_incompat_types)
7491           << NewFD->getType() << FD->getType() << (NumAppendArgs ? 1 : 0)
7492           << VariantRef->getSourceRange();
7493       return None;
7494     }
7495     if (NewType->isFunctionProtoType()) {
7496       if (FD->getType()->isFunctionNoProtoType())
7497         setPrototype(*this, FD, NewFD, NewType);
7498       else if (NewFD->getType()->isFunctionNoProtoType())
7499         setPrototype(*this, NewFD, FD, NewType);
7500     }
7501   }
7502 
7503   // Check if variant function is not marked with declare variant directive.
7504   if (NewFD->hasAttrs() && NewFD->hasAttr<OMPDeclareVariantAttr>()) {
7505     Diag(VariantRef->getExprLoc(),
7506          diag::warn_omp_declare_variant_marked_as_declare_variant)
7507         << VariantRef->getSourceRange();
7508     SourceRange SR =
7509         NewFD->specific_attr_begin<OMPDeclareVariantAttr>()->getRange();
7510     Diag(SR.getBegin(), diag::note_omp_marked_declare_variant_here) << SR;
7511     return None;
7512   }
7513 
7514   enum DoesntSupport {
7515     VirtFuncs = 1,
7516     Constructors = 3,
7517     Destructors = 4,
7518     DeletedFuncs = 5,
7519     DefaultedFuncs = 6,
7520     ConstexprFuncs = 7,
7521     ConstevalFuncs = 8,
7522   };
7523   if (const auto *CXXFD = dyn_cast<CXXMethodDecl>(FD)) {
7524     if (CXXFD->isVirtual()) {
7525       Diag(FD->getLocation(), diag::err_omp_declare_variant_doesnt_support)
7526           << VirtFuncs;
7527       return None;
7528     }
7529 
7530     if (isa<CXXConstructorDecl>(FD)) {
7531       Diag(FD->getLocation(), diag::err_omp_declare_variant_doesnt_support)
7532           << Constructors;
7533       return None;
7534     }
7535 
7536     if (isa<CXXDestructorDecl>(FD)) {
7537       Diag(FD->getLocation(), diag::err_omp_declare_variant_doesnt_support)
7538           << Destructors;
7539       return None;
7540     }
7541   }
7542 
7543   if (FD->isDeleted()) {
7544     Diag(FD->getLocation(), diag::err_omp_declare_variant_doesnt_support)
7545         << DeletedFuncs;
7546     return None;
7547   }
7548 
7549   if (FD->isDefaulted()) {
7550     Diag(FD->getLocation(), diag::err_omp_declare_variant_doesnt_support)
7551         << DefaultedFuncs;
7552     return None;
7553   }
7554 
7555   if (FD->isConstexpr()) {
7556     Diag(FD->getLocation(), diag::err_omp_declare_variant_doesnt_support)
7557         << (NewFD->isConsteval() ? ConstevalFuncs : ConstexprFuncs);
7558     return None;
7559   }
7560 
7561   // Check general compatibility.
7562   if (areMultiversionVariantFunctionsCompatible(
7563           FD, NewFD, PartialDiagnostic::NullDiagnostic(),
7564           PartialDiagnosticAt(SourceLocation(),
7565                               PartialDiagnostic::NullDiagnostic()),
7566           PartialDiagnosticAt(
7567               VariantRef->getExprLoc(),
7568               PDiag(diag::err_omp_declare_variant_doesnt_support)),
7569           PartialDiagnosticAt(VariantRef->getExprLoc(),
7570                               PDiag(diag::err_omp_declare_variant_diff)
7571                                   << FD->getLocation()),
7572           /*TemplatesSupported=*/true, /*ConstexprSupported=*/false,
7573           /*CLinkageMayDiffer=*/true))
7574     return None;
7575   return std::make_pair(FD, cast<Expr>(DRE));
7576 }
7577 
7578 void Sema::ActOnOpenMPDeclareVariantDirective(
7579     FunctionDecl *FD, Expr *VariantRef, OMPTraitInfo &TI,
7580     ArrayRef<Expr *> AdjustArgsNothing,
7581     ArrayRef<Expr *> AdjustArgsNeedDevicePtr,
7582     ArrayRef<OMPDeclareVariantAttr::InteropType> AppendArgs,
7583     SourceLocation AdjustArgsLoc, SourceLocation AppendArgsLoc,
7584     SourceRange SR) {
7585 
7586   // OpenMP 5.1 [2.3.5, declare variant directive, Restrictions]
7587   // An adjust_args clause or append_args clause can only be specified if the
7588   // dispatch selector of the construct selector set appears in the match
7589   // clause.
7590 
7591   SmallVector<Expr *, 8> AllAdjustArgs;
7592   llvm::append_range(AllAdjustArgs, AdjustArgsNothing);
7593   llvm::append_range(AllAdjustArgs, AdjustArgsNeedDevicePtr);
7594 
7595   if (!AllAdjustArgs.empty() || !AppendArgs.empty()) {
7596     VariantMatchInfo VMI;
7597     TI.getAsVariantMatchInfo(Context, VMI);
7598     if (!llvm::is_contained(
7599             VMI.ConstructTraits,
7600             llvm::omp::TraitProperty::construct_dispatch_dispatch)) {
7601       if (!AllAdjustArgs.empty())
7602         Diag(AdjustArgsLoc, diag::err_omp_clause_requires_dispatch_construct)
7603             << getOpenMPClauseName(OMPC_adjust_args);
7604       if (!AppendArgs.empty())
7605         Diag(AppendArgsLoc, diag::err_omp_clause_requires_dispatch_construct)
7606             << getOpenMPClauseName(OMPC_append_args);
7607       return;
7608     }
7609   }
7610 
7611   // OpenMP 5.1 [2.3.5, declare variant directive, Restrictions]
7612   // Each argument can only appear in a single adjust_args clause for each
7613   // declare variant directive.
7614   llvm::SmallPtrSet<const VarDecl *, 4> AdjustVars;
7615 
7616   for (Expr *E : AllAdjustArgs) {
7617     E = E->IgnoreParenImpCasts();
7618     if (const auto *DRE = dyn_cast<DeclRefExpr>(E)) {
7619       if (const auto *PVD = dyn_cast<ParmVarDecl>(DRE->getDecl())) {
7620         const VarDecl *CanonPVD = PVD->getCanonicalDecl();
7621         if (FD->getNumParams() > PVD->getFunctionScopeIndex() &&
7622             FD->getParamDecl(PVD->getFunctionScopeIndex())
7623                     ->getCanonicalDecl() == CanonPVD) {
7624           // It's a parameter of the function, check duplicates.
7625           if (!AdjustVars.insert(CanonPVD).second) {
7626             Diag(DRE->getLocation(), diag::err_omp_adjust_arg_multiple_clauses)
7627                 << PVD;
7628             return;
7629           }
7630           continue;
7631         }
7632       }
7633     }
7634     // Anything that is not a function parameter is an error.
7635     Diag(E->getExprLoc(), diag::err_omp_param_or_this_in_clause) << FD << 0;
7636     return;
7637   }
7638 
7639   auto *NewAttr = OMPDeclareVariantAttr::CreateImplicit(
7640       Context, VariantRef, &TI, const_cast<Expr **>(AdjustArgsNothing.data()),
7641       AdjustArgsNothing.size(),
7642       const_cast<Expr **>(AdjustArgsNeedDevicePtr.data()),
7643       AdjustArgsNeedDevicePtr.size(),
7644       const_cast<OMPDeclareVariantAttr::InteropType *>(AppendArgs.data()),
7645       AppendArgs.size(), SR);
7646   FD->addAttr(NewAttr);
7647 }
7648 
7649 StmtResult Sema::ActOnOpenMPParallelDirective(ArrayRef<OMPClause *> Clauses,
7650                                               Stmt *AStmt,
7651                                               SourceLocation StartLoc,
7652                                               SourceLocation EndLoc) {
7653   if (!AStmt)
7654     return StmtError();
7655 
7656   auto *CS = cast<CapturedStmt>(AStmt);
7657   // 1.2.2 OpenMP Language Terminology
7658   // Structured block - An executable statement with a single entry at the
7659   // top and a single exit at the bottom.
7660   // The point of exit cannot be a branch out of the structured block.
7661   // longjmp() and throw() must not violate the entry/exit criteria.
7662   CS->getCapturedDecl()->setNothrow();
7663 
7664   setFunctionHasBranchProtectedScope();
7665 
7666   return OMPParallelDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
7667                                       DSAStack->getTaskgroupReductionRef(),
7668                                       DSAStack->isCancelRegion());
7669 }
7670 
7671 namespace {
7672 /// Iteration space of a single for loop.
7673 struct LoopIterationSpace final {
7674   /// True if the condition operator is the strict compare operator (<, > or
7675   /// !=).
7676   bool IsStrictCompare = false;
7677   /// Condition of the loop.
7678   Expr *PreCond = nullptr;
7679   /// This expression calculates the number of iterations in the loop.
7680   /// It is always possible to calculate it before starting the loop.
7681   Expr *NumIterations = nullptr;
7682   /// The loop counter variable.
7683   Expr *CounterVar = nullptr;
7684   /// Private loop counter variable.
7685   Expr *PrivateCounterVar = nullptr;
7686   /// This is initializer for the initial value of #CounterVar.
7687   Expr *CounterInit = nullptr;
7688   /// This is step for the #CounterVar used to generate its update:
7689   /// #CounterVar = #CounterInit + #CounterStep * CurrentIteration.
7690   Expr *CounterStep = nullptr;
7691   /// Should step be subtracted?
7692   bool Subtract = false;
7693   /// Source range of the loop init.
7694   SourceRange InitSrcRange;
7695   /// Source range of the loop condition.
7696   SourceRange CondSrcRange;
7697   /// Source range of the loop increment.
7698   SourceRange IncSrcRange;
7699   /// Minimum value that can have the loop control variable. Used to support
7700   /// non-rectangular loops. Applied only for LCV with the non-iterator types,
7701   /// since only such variables can be used in non-loop invariant expressions.
7702   Expr *MinValue = nullptr;
7703   /// Maximum value that can have the loop control variable. Used to support
7704   /// non-rectangular loops. Applied only for LCV with the non-iterator type,
7705   /// since only such variables can be used in non-loop invariant expressions.
7706   Expr *MaxValue = nullptr;
7707   /// true, if the lower bound depends on the outer loop control var.
7708   bool IsNonRectangularLB = false;
7709   /// true, if the upper bound depends on the outer loop control var.
7710   bool IsNonRectangularUB = false;
7711   /// Index of the loop this loop depends on and forms non-rectangular loop
7712   /// nest.
7713   unsigned LoopDependentIdx = 0;
7714   /// Final condition for the non-rectangular loop nest support. It is used to
7715   /// check that the number of iterations for this particular counter must be
7716   /// finished.
7717   Expr *FinalCondition = nullptr;
7718 };
7719 
7720 /// Helper class for checking canonical form of the OpenMP loops and
7721 /// extracting iteration space of each loop in the loop nest, that will be used
7722 /// for IR generation.
7723 class OpenMPIterationSpaceChecker {
7724   /// Reference to Sema.
7725   Sema &SemaRef;
7726   /// Does the loop associated directive support non-rectangular loops?
7727   bool SupportsNonRectangular;
7728   /// Data-sharing stack.
7729   DSAStackTy &Stack;
7730   /// A location for diagnostics (when there is no some better location).
7731   SourceLocation DefaultLoc;
7732   /// A location for diagnostics (when increment is not compatible).
7733   SourceLocation ConditionLoc;
7734   /// A source location for referring to loop init later.
7735   SourceRange InitSrcRange;
7736   /// A source location for referring to condition later.
7737   SourceRange ConditionSrcRange;
7738   /// A source location for referring to increment later.
7739   SourceRange IncrementSrcRange;
7740   /// Loop variable.
7741   ValueDecl *LCDecl = nullptr;
7742   /// Reference to loop variable.
7743   Expr *LCRef = nullptr;
7744   /// Lower bound (initializer for the var).
7745   Expr *LB = nullptr;
7746   /// Upper bound.
7747   Expr *UB = nullptr;
7748   /// Loop step (increment).
7749   Expr *Step = nullptr;
7750   /// This flag is true when condition is one of:
7751   ///   Var <  UB
7752   ///   Var <= UB
7753   ///   UB  >  Var
7754   ///   UB  >= Var
7755   /// This will have no value when the condition is !=
7756   llvm::Optional<bool> TestIsLessOp;
7757   /// This flag is true when condition is strict ( < or > ).
7758   bool TestIsStrictOp = false;
7759   /// This flag is true when step is subtracted on each iteration.
7760   bool SubtractStep = false;
7761   /// The outer loop counter this loop depends on (if any).
7762   const ValueDecl *DepDecl = nullptr;
7763   /// Contains number of loop (starts from 1) on which loop counter init
7764   /// expression of this loop depends on.
7765   Optional<unsigned> InitDependOnLC;
7766   /// Contains number of loop (starts from 1) on which loop counter condition
7767   /// expression of this loop depends on.
7768   Optional<unsigned> CondDependOnLC;
7769   /// Checks if the provide statement depends on the loop counter.
7770   Optional<unsigned> doesDependOnLoopCounter(const Stmt *S, bool IsInitializer);
7771   /// Original condition required for checking of the exit condition for
7772   /// non-rectangular loop.
7773   Expr *Condition = nullptr;
7774 
7775 public:
7776   OpenMPIterationSpaceChecker(Sema &SemaRef, bool SupportsNonRectangular,
7777                               DSAStackTy &Stack, SourceLocation DefaultLoc)
7778       : SemaRef(SemaRef), SupportsNonRectangular(SupportsNonRectangular),
7779         Stack(Stack), DefaultLoc(DefaultLoc), ConditionLoc(DefaultLoc) {}
7780   /// Check init-expr for canonical loop form and save loop counter
7781   /// variable - #Var and its initialization value - #LB.
7782   bool checkAndSetInit(Stmt *S, bool EmitDiags = true);
7783   /// Check test-expr for canonical form, save upper-bound (#UB), flags
7784   /// for less/greater and for strict/non-strict comparison.
7785   bool checkAndSetCond(Expr *S);
7786   /// Check incr-expr for canonical loop form and return true if it
7787   /// does not conform, otherwise save loop step (#Step).
7788   bool checkAndSetInc(Expr *S);
7789   /// Return the loop counter variable.
7790   ValueDecl *getLoopDecl() const { return LCDecl; }
7791   /// Return the reference expression to loop counter variable.
7792   Expr *getLoopDeclRefExpr() const { return LCRef; }
7793   /// Source range of the loop init.
7794   SourceRange getInitSrcRange() const { return InitSrcRange; }
7795   /// Source range of the loop condition.
7796   SourceRange getConditionSrcRange() const { return ConditionSrcRange; }
7797   /// Source range of the loop increment.
7798   SourceRange getIncrementSrcRange() const { return IncrementSrcRange; }
7799   /// True if the step should be subtracted.
7800   bool shouldSubtractStep() const { return SubtractStep; }
7801   /// True, if the compare operator is strict (<, > or !=).
7802   bool isStrictTestOp() const { return TestIsStrictOp; }
7803   /// Build the expression to calculate the number of iterations.
7804   Expr *buildNumIterations(
7805       Scope *S, ArrayRef<LoopIterationSpace> ResultIterSpaces, bool LimitedType,
7806       llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const;
7807   /// Build the precondition expression for the loops.
7808   Expr *
7809   buildPreCond(Scope *S, Expr *Cond,
7810                llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const;
7811   /// Build reference expression to the counter be used for codegen.
7812   DeclRefExpr *
7813   buildCounterVar(llvm::MapVector<const Expr *, DeclRefExpr *> &Captures,
7814                   DSAStackTy &DSA) const;
7815   /// Build reference expression to the private counter be used for
7816   /// codegen.
7817   Expr *buildPrivateCounterVar() const;
7818   /// Build initialization of the counter be used for codegen.
7819   Expr *buildCounterInit() const;
7820   /// Build step of the counter be used for codegen.
7821   Expr *buildCounterStep() const;
7822   /// Build loop data with counter value for depend clauses in ordered
7823   /// directives.
7824   Expr *
7825   buildOrderedLoopData(Scope *S, Expr *Counter,
7826                        llvm::MapVector<const Expr *, DeclRefExpr *> &Captures,
7827                        SourceLocation Loc, Expr *Inc = nullptr,
7828                        OverloadedOperatorKind OOK = OO_Amp);
7829   /// Builds the minimum value for the loop counter.
7830   std::pair<Expr *, Expr *> buildMinMaxValues(
7831       Scope *S, llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const;
7832   /// Builds final condition for the non-rectangular loops.
7833   Expr *buildFinalCondition(Scope *S) const;
7834   /// Return true if any expression is dependent.
7835   bool dependent() const;
7836   /// Returns true if the initializer forms non-rectangular loop.
7837   bool doesInitDependOnLC() const { return InitDependOnLC.has_value(); }
7838   /// Returns true if the condition forms non-rectangular loop.
7839   bool doesCondDependOnLC() const { return CondDependOnLC.has_value(); }
7840   /// Returns index of the loop we depend on (starting from 1), or 0 otherwise.
7841   unsigned getLoopDependentIdx() const {
7842     return InitDependOnLC.value_or(CondDependOnLC.value_or(0));
7843   }
7844 
7845 private:
7846   /// Check the right-hand side of an assignment in the increment
7847   /// expression.
7848   bool checkAndSetIncRHS(Expr *RHS);
7849   /// Helper to set loop counter variable and its initializer.
7850   bool setLCDeclAndLB(ValueDecl *NewLCDecl, Expr *NewDeclRefExpr, Expr *NewLB,
7851                       bool EmitDiags);
7852   /// Helper to set upper bound.
7853   bool setUB(Expr *NewUB, llvm::Optional<bool> LessOp, bool StrictOp,
7854              SourceRange SR, SourceLocation SL);
7855   /// Helper to set loop increment.
7856   bool setStep(Expr *NewStep, bool Subtract);
7857 };
7858 
7859 bool OpenMPIterationSpaceChecker::dependent() const {
7860   if (!LCDecl) {
7861     assert(!LB && !UB && !Step);
7862     return false;
7863   }
7864   return LCDecl->getType()->isDependentType() ||
7865          (LB && LB->isValueDependent()) || (UB && UB->isValueDependent()) ||
7866          (Step && Step->isValueDependent());
7867 }
7868 
7869 bool OpenMPIterationSpaceChecker::setLCDeclAndLB(ValueDecl *NewLCDecl,
7870                                                  Expr *NewLCRefExpr,
7871                                                  Expr *NewLB, bool EmitDiags) {
7872   // State consistency checking to ensure correct usage.
7873   assert(LCDecl == nullptr && LB == nullptr && LCRef == nullptr &&
7874          UB == nullptr && Step == nullptr && !TestIsLessOp && !TestIsStrictOp);
7875   if (!NewLCDecl || !NewLB || NewLB->containsErrors())
7876     return true;
7877   LCDecl = getCanonicalDecl(NewLCDecl);
7878   LCRef = NewLCRefExpr;
7879   if (auto *CE = dyn_cast_or_null<CXXConstructExpr>(NewLB))
7880     if (const CXXConstructorDecl *Ctor = CE->getConstructor())
7881       if ((Ctor->isCopyOrMoveConstructor() ||
7882            Ctor->isConvertingConstructor(/*AllowExplicit=*/false)) &&
7883           CE->getNumArgs() > 0 && CE->getArg(0) != nullptr)
7884         NewLB = CE->getArg(0)->IgnoreParenImpCasts();
7885   LB = NewLB;
7886   if (EmitDiags)
7887     InitDependOnLC = doesDependOnLoopCounter(LB, /*IsInitializer=*/true);
7888   return false;
7889 }
7890 
7891 bool OpenMPIterationSpaceChecker::setUB(Expr *NewUB,
7892                                         llvm::Optional<bool> LessOp,
7893                                         bool StrictOp, SourceRange SR,
7894                                         SourceLocation SL) {
7895   // State consistency checking to ensure correct usage.
7896   assert(LCDecl != nullptr && LB != nullptr && UB == nullptr &&
7897          Step == nullptr && !TestIsLessOp && !TestIsStrictOp);
7898   if (!NewUB || NewUB->containsErrors())
7899     return true;
7900   UB = NewUB;
7901   if (LessOp)
7902     TestIsLessOp = LessOp;
7903   TestIsStrictOp = StrictOp;
7904   ConditionSrcRange = SR;
7905   ConditionLoc = SL;
7906   CondDependOnLC = doesDependOnLoopCounter(UB, /*IsInitializer=*/false);
7907   return false;
7908 }
7909 
7910 bool OpenMPIterationSpaceChecker::setStep(Expr *NewStep, bool Subtract) {
7911   // State consistency checking to ensure correct usage.
7912   assert(LCDecl != nullptr && LB != nullptr && Step == nullptr);
7913   if (!NewStep || NewStep->containsErrors())
7914     return true;
7915   if (!NewStep->isValueDependent()) {
7916     // Check that the step is integer expression.
7917     SourceLocation StepLoc = NewStep->getBeginLoc();
7918     ExprResult Val = SemaRef.PerformOpenMPImplicitIntegerConversion(
7919         StepLoc, getExprAsWritten(NewStep));
7920     if (Val.isInvalid())
7921       return true;
7922     NewStep = Val.get();
7923 
7924     // OpenMP [2.6, Canonical Loop Form, Restrictions]
7925     //  If test-expr is of form var relational-op b and relational-op is < or
7926     //  <= then incr-expr must cause var to increase on each iteration of the
7927     //  loop. If test-expr is of form var relational-op b and relational-op is
7928     //  > or >= then incr-expr must cause var to decrease on each iteration of
7929     //  the loop.
7930     //  If test-expr is of form b relational-op var and relational-op is < or
7931     //  <= then incr-expr must cause var to decrease on each iteration of the
7932     //  loop. If test-expr is of form b relational-op var and relational-op is
7933     //  > or >= then incr-expr must cause var to increase on each iteration of
7934     //  the loop.
7935     Optional<llvm::APSInt> Result =
7936         NewStep->getIntegerConstantExpr(SemaRef.Context);
7937     bool IsUnsigned = !NewStep->getType()->hasSignedIntegerRepresentation();
7938     bool IsConstNeg =
7939         Result && Result->isSigned() && (Subtract != Result->isNegative());
7940     bool IsConstPos =
7941         Result && Result->isSigned() && (Subtract == Result->isNegative());
7942     bool IsConstZero = Result && !Result->getBoolValue();
7943 
7944     // != with increment is treated as <; != with decrement is treated as >
7945     if (!TestIsLessOp)
7946       TestIsLessOp = IsConstPos || (IsUnsigned && !Subtract);
7947     if (UB &&
7948         (IsConstZero ||
7949          (TestIsLessOp.value() ? (IsConstNeg || (IsUnsigned && Subtract))
7950                                : (IsConstPos || (IsUnsigned && !Subtract))))) {
7951       SemaRef.Diag(NewStep->getExprLoc(),
7952                    diag::err_omp_loop_incr_not_compatible)
7953           << LCDecl << TestIsLessOp.value() << NewStep->getSourceRange();
7954       SemaRef.Diag(ConditionLoc,
7955                    diag::note_omp_loop_cond_requres_compatible_incr)
7956           << TestIsLessOp.value() << ConditionSrcRange;
7957       return true;
7958     }
7959     if (TestIsLessOp.value() == Subtract) {
7960       NewStep =
7961           SemaRef.CreateBuiltinUnaryOp(NewStep->getExprLoc(), UO_Minus, NewStep)
7962               .get();
7963       Subtract = !Subtract;
7964     }
7965   }
7966 
7967   Step = NewStep;
7968   SubtractStep = Subtract;
7969   return false;
7970 }
7971 
7972 namespace {
7973 /// Checker for the non-rectangular loops. Checks if the initializer or
7974 /// condition expression references loop counter variable.
7975 class LoopCounterRefChecker final
7976     : public ConstStmtVisitor<LoopCounterRefChecker, bool> {
7977   Sema &SemaRef;
7978   DSAStackTy &Stack;
7979   const ValueDecl *CurLCDecl = nullptr;
7980   const ValueDecl *DepDecl = nullptr;
7981   const ValueDecl *PrevDepDecl = nullptr;
7982   bool IsInitializer = true;
7983   bool SupportsNonRectangular;
7984   unsigned BaseLoopId = 0;
7985   bool checkDecl(const Expr *E, const ValueDecl *VD) {
7986     if (getCanonicalDecl(VD) == getCanonicalDecl(CurLCDecl)) {
7987       SemaRef.Diag(E->getExprLoc(), diag::err_omp_stmt_depends_on_loop_counter)
7988           << (IsInitializer ? 0 : 1);
7989       return false;
7990     }
7991     const auto &&Data = Stack.isLoopControlVariable(VD);
7992     // OpenMP, 2.9.1 Canonical Loop Form, Restrictions.
7993     // The type of the loop iterator on which we depend may not have a random
7994     // access iterator type.
7995     if (Data.first && VD->getType()->isRecordType()) {
7996       SmallString<128> Name;
7997       llvm::raw_svector_ostream OS(Name);
7998       VD->getNameForDiagnostic(OS, SemaRef.getPrintingPolicy(),
7999                                /*Qualified=*/true);
8000       SemaRef.Diag(E->getExprLoc(),
8001                    diag::err_omp_wrong_dependency_iterator_type)
8002           << OS.str();
8003       SemaRef.Diag(VD->getLocation(), diag::note_previous_decl) << VD;
8004       return false;
8005     }
8006     if (Data.first && !SupportsNonRectangular) {
8007       SemaRef.Diag(E->getExprLoc(), diag::err_omp_invariant_dependency);
8008       return false;
8009     }
8010     if (Data.first &&
8011         (DepDecl || (PrevDepDecl &&
8012                      getCanonicalDecl(VD) != getCanonicalDecl(PrevDepDecl)))) {
8013       if (!DepDecl && PrevDepDecl)
8014         DepDecl = PrevDepDecl;
8015       SmallString<128> Name;
8016       llvm::raw_svector_ostream OS(Name);
8017       DepDecl->getNameForDiagnostic(OS, SemaRef.getPrintingPolicy(),
8018                                     /*Qualified=*/true);
8019       SemaRef.Diag(E->getExprLoc(),
8020                    diag::err_omp_invariant_or_linear_dependency)
8021           << OS.str();
8022       return false;
8023     }
8024     if (Data.first) {
8025       DepDecl = VD;
8026       BaseLoopId = Data.first;
8027     }
8028     return Data.first;
8029   }
8030 
8031 public:
8032   bool VisitDeclRefExpr(const DeclRefExpr *E) {
8033     const ValueDecl *VD = E->getDecl();
8034     if (isa<VarDecl>(VD))
8035       return checkDecl(E, VD);
8036     return false;
8037   }
8038   bool VisitMemberExpr(const MemberExpr *E) {
8039     if (isa<CXXThisExpr>(E->getBase()->IgnoreParens())) {
8040       const ValueDecl *VD = E->getMemberDecl();
8041       if (isa<VarDecl>(VD) || isa<FieldDecl>(VD))
8042         return checkDecl(E, VD);
8043     }
8044     return false;
8045   }
8046   bool VisitStmt(const Stmt *S) {
8047     bool Res = false;
8048     for (const Stmt *Child : S->children())
8049       Res = (Child && Visit(Child)) || Res;
8050     return Res;
8051   }
8052   explicit LoopCounterRefChecker(Sema &SemaRef, DSAStackTy &Stack,
8053                                  const ValueDecl *CurLCDecl, bool IsInitializer,
8054                                  const ValueDecl *PrevDepDecl = nullptr,
8055                                  bool SupportsNonRectangular = true)
8056       : SemaRef(SemaRef), Stack(Stack), CurLCDecl(CurLCDecl),
8057         PrevDepDecl(PrevDepDecl), IsInitializer(IsInitializer),
8058         SupportsNonRectangular(SupportsNonRectangular) {}
8059   unsigned getBaseLoopId() const {
8060     assert(CurLCDecl && "Expected loop dependency.");
8061     return BaseLoopId;
8062   }
8063   const ValueDecl *getDepDecl() const {
8064     assert(CurLCDecl && "Expected loop dependency.");
8065     return DepDecl;
8066   }
8067 };
8068 } // namespace
8069 
8070 Optional<unsigned>
8071 OpenMPIterationSpaceChecker::doesDependOnLoopCounter(const Stmt *S,
8072                                                      bool IsInitializer) {
8073   // Check for the non-rectangular loops.
8074   LoopCounterRefChecker LoopStmtChecker(SemaRef, Stack, LCDecl, IsInitializer,
8075                                         DepDecl, SupportsNonRectangular);
8076   if (LoopStmtChecker.Visit(S)) {
8077     DepDecl = LoopStmtChecker.getDepDecl();
8078     return LoopStmtChecker.getBaseLoopId();
8079   }
8080   return llvm::None;
8081 }
8082 
8083 bool OpenMPIterationSpaceChecker::checkAndSetInit(Stmt *S, bool EmitDiags) {
8084   // Check init-expr for canonical loop form and save loop counter
8085   // variable - #Var and its initialization value - #LB.
8086   // OpenMP [2.6] Canonical loop form. init-expr may be one of the following:
8087   //   var = lb
8088   //   integer-type var = lb
8089   //   random-access-iterator-type var = lb
8090   //   pointer-type var = lb
8091   //
8092   if (!S) {
8093     if (EmitDiags) {
8094       SemaRef.Diag(DefaultLoc, diag::err_omp_loop_not_canonical_init);
8095     }
8096     return true;
8097   }
8098   if (auto *ExprTemp = dyn_cast<ExprWithCleanups>(S))
8099     if (!ExprTemp->cleanupsHaveSideEffects())
8100       S = ExprTemp->getSubExpr();
8101 
8102   InitSrcRange = S->getSourceRange();
8103   if (Expr *E = dyn_cast<Expr>(S))
8104     S = E->IgnoreParens();
8105   if (auto *BO = dyn_cast<BinaryOperator>(S)) {
8106     if (BO->getOpcode() == BO_Assign) {
8107       Expr *LHS = BO->getLHS()->IgnoreParens();
8108       if (auto *DRE = dyn_cast<DeclRefExpr>(LHS)) {
8109         if (auto *CED = dyn_cast<OMPCapturedExprDecl>(DRE->getDecl()))
8110           if (auto *ME = dyn_cast<MemberExpr>(getExprAsWritten(CED->getInit())))
8111             return setLCDeclAndLB(ME->getMemberDecl(), ME, BO->getRHS(),
8112                                   EmitDiags);
8113         return setLCDeclAndLB(DRE->getDecl(), DRE, BO->getRHS(), EmitDiags);
8114       }
8115       if (auto *ME = dyn_cast<MemberExpr>(LHS)) {
8116         if (ME->isArrow() &&
8117             isa<CXXThisExpr>(ME->getBase()->IgnoreParenImpCasts()))
8118           return setLCDeclAndLB(ME->getMemberDecl(), ME, BO->getRHS(),
8119                                 EmitDiags);
8120       }
8121     }
8122   } else if (auto *DS = dyn_cast<DeclStmt>(S)) {
8123     if (DS->isSingleDecl()) {
8124       if (auto *Var = dyn_cast_or_null<VarDecl>(DS->getSingleDecl())) {
8125         if (Var->hasInit() && !Var->getType()->isReferenceType()) {
8126           // Accept non-canonical init form here but emit ext. warning.
8127           if (Var->getInitStyle() != VarDecl::CInit && EmitDiags)
8128             SemaRef.Diag(S->getBeginLoc(),
8129                          diag::ext_omp_loop_not_canonical_init)
8130                 << S->getSourceRange();
8131           return setLCDeclAndLB(
8132               Var,
8133               buildDeclRefExpr(SemaRef, Var,
8134                                Var->getType().getNonReferenceType(),
8135                                DS->getBeginLoc()),
8136               Var->getInit(), EmitDiags);
8137         }
8138       }
8139     }
8140   } else if (auto *CE = dyn_cast<CXXOperatorCallExpr>(S)) {
8141     if (CE->getOperator() == OO_Equal) {
8142       Expr *LHS = CE->getArg(0);
8143       if (auto *DRE = dyn_cast<DeclRefExpr>(LHS)) {
8144         if (auto *CED = dyn_cast<OMPCapturedExprDecl>(DRE->getDecl()))
8145           if (auto *ME = dyn_cast<MemberExpr>(getExprAsWritten(CED->getInit())))
8146             return setLCDeclAndLB(ME->getMemberDecl(), ME, BO->getRHS(),
8147                                   EmitDiags);
8148         return setLCDeclAndLB(DRE->getDecl(), DRE, CE->getArg(1), EmitDiags);
8149       }
8150       if (auto *ME = dyn_cast<MemberExpr>(LHS)) {
8151         if (ME->isArrow() &&
8152             isa<CXXThisExpr>(ME->getBase()->IgnoreParenImpCasts()))
8153           return setLCDeclAndLB(ME->getMemberDecl(), ME, BO->getRHS(),
8154                                 EmitDiags);
8155       }
8156     }
8157   }
8158 
8159   if (dependent() || SemaRef.CurContext->isDependentContext())
8160     return false;
8161   if (EmitDiags) {
8162     SemaRef.Diag(S->getBeginLoc(), diag::err_omp_loop_not_canonical_init)
8163         << S->getSourceRange();
8164   }
8165   return true;
8166 }
8167 
8168 /// Ignore parenthesizes, implicit casts, copy constructor and return the
8169 /// variable (which may be the loop variable) if possible.
8170 static const ValueDecl *getInitLCDecl(const Expr *E) {
8171   if (!E)
8172     return nullptr;
8173   E = getExprAsWritten(E);
8174   if (const auto *CE = dyn_cast_or_null<CXXConstructExpr>(E))
8175     if (const CXXConstructorDecl *Ctor = CE->getConstructor())
8176       if ((Ctor->isCopyOrMoveConstructor() ||
8177            Ctor->isConvertingConstructor(/*AllowExplicit=*/false)) &&
8178           CE->getNumArgs() > 0 && CE->getArg(0) != nullptr)
8179         E = CE->getArg(0)->IgnoreParenImpCasts();
8180   if (const auto *DRE = dyn_cast_or_null<DeclRefExpr>(E)) {
8181     if (const auto *VD = dyn_cast<VarDecl>(DRE->getDecl()))
8182       return getCanonicalDecl(VD);
8183   }
8184   if (const auto *ME = dyn_cast_or_null<MemberExpr>(E))
8185     if (ME->isArrow() && isa<CXXThisExpr>(ME->getBase()->IgnoreParenImpCasts()))
8186       return getCanonicalDecl(ME->getMemberDecl());
8187   return nullptr;
8188 }
8189 
8190 bool OpenMPIterationSpaceChecker::checkAndSetCond(Expr *S) {
8191   // Check test-expr for canonical form, save upper-bound UB, flags for
8192   // less/greater and for strict/non-strict comparison.
8193   // OpenMP [2.9] Canonical loop form. Test-expr may be one of the following:
8194   //   var relational-op b
8195   //   b relational-op var
8196   //
8197   bool IneqCondIsCanonical = SemaRef.getLangOpts().OpenMP >= 50;
8198   if (!S) {
8199     SemaRef.Diag(DefaultLoc, diag::err_omp_loop_not_canonical_cond)
8200         << (IneqCondIsCanonical ? 1 : 0) << LCDecl;
8201     return true;
8202   }
8203   Condition = S;
8204   S = getExprAsWritten(S);
8205   SourceLocation CondLoc = S->getBeginLoc();
8206   auto &&CheckAndSetCond = [this, IneqCondIsCanonical](
8207                                BinaryOperatorKind Opcode, const Expr *LHS,
8208                                const Expr *RHS, SourceRange SR,
8209                                SourceLocation OpLoc) -> llvm::Optional<bool> {
8210     if (BinaryOperator::isRelationalOp(Opcode)) {
8211       if (getInitLCDecl(LHS) == LCDecl)
8212         return setUB(const_cast<Expr *>(RHS),
8213                      (Opcode == BO_LT || Opcode == BO_LE),
8214                      (Opcode == BO_LT || Opcode == BO_GT), SR, OpLoc);
8215       if (getInitLCDecl(RHS) == LCDecl)
8216         return setUB(const_cast<Expr *>(LHS),
8217                      (Opcode == BO_GT || Opcode == BO_GE),
8218                      (Opcode == BO_LT || Opcode == BO_GT), SR, OpLoc);
8219     } else if (IneqCondIsCanonical && Opcode == BO_NE) {
8220       return setUB(const_cast<Expr *>(getInitLCDecl(LHS) == LCDecl ? RHS : LHS),
8221                    /*LessOp=*/llvm::None,
8222                    /*StrictOp=*/true, SR, OpLoc);
8223     }
8224     return llvm::None;
8225   };
8226   llvm::Optional<bool> Res;
8227   if (auto *RBO = dyn_cast<CXXRewrittenBinaryOperator>(S)) {
8228     CXXRewrittenBinaryOperator::DecomposedForm DF = RBO->getDecomposedForm();
8229     Res = CheckAndSetCond(DF.Opcode, DF.LHS, DF.RHS, RBO->getSourceRange(),
8230                           RBO->getOperatorLoc());
8231   } else if (auto *BO = dyn_cast<BinaryOperator>(S)) {
8232     Res = CheckAndSetCond(BO->getOpcode(), BO->getLHS(), BO->getRHS(),
8233                           BO->getSourceRange(), BO->getOperatorLoc());
8234   } else if (auto *CE = dyn_cast<CXXOperatorCallExpr>(S)) {
8235     if (CE->getNumArgs() == 2) {
8236       Res = CheckAndSetCond(
8237           BinaryOperator::getOverloadedOpcode(CE->getOperator()), CE->getArg(0),
8238           CE->getArg(1), CE->getSourceRange(), CE->getOperatorLoc());
8239     }
8240   }
8241   if (Res)
8242     return *Res;
8243   if (dependent() || SemaRef.CurContext->isDependentContext())
8244     return false;
8245   SemaRef.Diag(CondLoc, diag::err_omp_loop_not_canonical_cond)
8246       << (IneqCondIsCanonical ? 1 : 0) << S->getSourceRange() << LCDecl;
8247   return true;
8248 }
8249 
8250 bool OpenMPIterationSpaceChecker::checkAndSetIncRHS(Expr *RHS) {
8251   // RHS of canonical loop form increment can be:
8252   //   var + incr
8253   //   incr + var
8254   //   var - incr
8255   //
8256   RHS = RHS->IgnoreParenImpCasts();
8257   if (auto *BO = dyn_cast<BinaryOperator>(RHS)) {
8258     if (BO->isAdditiveOp()) {
8259       bool IsAdd = BO->getOpcode() == BO_Add;
8260       if (getInitLCDecl(BO->getLHS()) == LCDecl)
8261         return setStep(BO->getRHS(), !IsAdd);
8262       if (IsAdd && getInitLCDecl(BO->getRHS()) == LCDecl)
8263         return setStep(BO->getLHS(), /*Subtract=*/false);
8264     }
8265   } else if (auto *CE = dyn_cast<CXXOperatorCallExpr>(RHS)) {
8266     bool IsAdd = CE->getOperator() == OO_Plus;
8267     if ((IsAdd || CE->getOperator() == OO_Minus) && CE->getNumArgs() == 2) {
8268       if (getInitLCDecl(CE->getArg(0)) == LCDecl)
8269         return setStep(CE->getArg(1), !IsAdd);
8270       if (IsAdd && getInitLCDecl(CE->getArg(1)) == LCDecl)
8271         return setStep(CE->getArg(0), /*Subtract=*/false);
8272     }
8273   }
8274   if (dependent() || SemaRef.CurContext->isDependentContext())
8275     return false;
8276   SemaRef.Diag(RHS->getBeginLoc(), diag::err_omp_loop_not_canonical_incr)
8277       << RHS->getSourceRange() << LCDecl;
8278   return true;
8279 }
8280 
8281 bool OpenMPIterationSpaceChecker::checkAndSetInc(Expr *S) {
8282   // Check incr-expr for canonical loop form and return true if it
8283   // does not conform.
8284   // OpenMP [2.6] Canonical loop form. Test-expr may be one of the following:
8285   //   ++var
8286   //   var++
8287   //   --var
8288   //   var--
8289   //   var += incr
8290   //   var -= incr
8291   //   var = var + incr
8292   //   var = incr + var
8293   //   var = var - incr
8294   //
8295   if (!S) {
8296     SemaRef.Diag(DefaultLoc, diag::err_omp_loop_not_canonical_incr) << LCDecl;
8297     return true;
8298   }
8299   if (auto *ExprTemp = dyn_cast<ExprWithCleanups>(S))
8300     if (!ExprTemp->cleanupsHaveSideEffects())
8301       S = ExprTemp->getSubExpr();
8302 
8303   IncrementSrcRange = S->getSourceRange();
8304   S = S->IgnoreParens();
8305   if (auto *UO = dyn_cast<UnaryOperator>(S)) {
8306     if (UO->isIncrementDecrementOp() &&
8307         getInitLCDecl(UO->getSubExpr()) == LCDecl)
8308       return setStep(SemaRef
8309                          .ActOnIntegerConstant(UO->getBeginLoc(),
8310                                                (UO->isDecrementOp() ? -1 : 1))
8311                          .get(),
8312                      /*Subtract=*/false);
8313   } else if (auto *BO = dyn_cast<BinaryOperator>(S)) {
8314     switch (BO->getOpcode()) {
8315     case BO_AddAssign:
8316     case BO_SubAssign:
8317       if (getInitLCDecl(BO->getLHS()) == LCDecl)
8318         return setStep(BO->getRHS(), BO->getOpcode() == BO_SubAssign);
8319       break;
8320     case BO_Assign:
8321       if (getInitLCDecl(BO->getLHS()) == LCDecl)
8322         return checkAndSetIncRHS(BO->getRHS());
8323       break;
8324     default:
8325       break;
8326     }
8327   } else if (auto *CE = dyn_cast<CXXOperatorCallExpr>(S)) {
8328     switch (CE->getOperator()) {
8329     case OO_PlusPlus:
8330     case OO_MinusMinus:
8331       if (getInitLCDecl(CE->getArg(0)) == LCDecl)
8332         return setStep(SemaRef
8333                            .ActOnIntegerConstant(
8334                                CE->getBeginLoc(),
8335                                ((CE->getOperator() == OO_MinusMinus) ? -1 : 1))
8336                            .get(),
8337                        /*Subtract=*/false);
8338       break;
8339     case OO_PlusEqual:
8340     case OO_MinusEqual:
8341       if (getInitLCDecl(CE->getArg(0)) == LCDecl)
8342         return setStep(CE->getArg(1), CE->getOperator() == OO_MinusEqual);
8343       break;
8344     case OO_Equal:
8345       if (getInitLCDecl(CE->getArg(0)) == LCDecl)
8346         return checkAndSetIncRHS(CE->getArg(1));
8347       break;
8348     default:
8349       break;
8350     }
8351   }
8352   if (dependent() || SemaRef.CurContext->isDependentContext())
8353     return false;
8354   SemaRef.Diag(S->getBeginLoc(), diag::err_omp_loop_not_canonical_incr)
8355       << S->getSourceRange() << LCDecl;
8356   return true;
8357 }
8358 
8359 static ExprResult
8360 tryBuildCapture(Sema &SemaRef, Expr *Capture,
8361                 llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
8362   if (SemaRef.CurContext->isDependentContext() || Capture->containsErrors())
8363     return Capture;
8364   if (Capture->isEvaluatable(SemaRef.Context, Expr::SE_AllowSideEffects))
8365     return SemaRef.PerformImplicitConversion(
8366         Capture->IgnoreImpCasts(), Capture->getType(), Sema::AA_Converting,
8367         /*AllowExplicit=*/true);
8368   auto I = Captures.find(Capture);
8369   if (I != Captures.end())
8370     return buildCapture(SemaRef, Capture, I->second);
8371   DeclRefExpr *Ref = nullptr;
8372   ExprResult Res = buildCapture(SemaRef, Capture, Ref);
8373   Captures[Capture] = Ref;
8374   return Res;
8375 }
8376 
8377 /// Calculate number of iterations, transforming to unsigned, if number of
8378 /// iterations may be larger than the original type.
8379 static Expr *
8380 calculateNumIters(Sema &SemaRef, Scope *S, SourceLocation DefaultLoc,
8381                   Expr *Lower, Expr *Upper, Expr *Step, QualType LCTy,
8382                   bool TestIsStrictOp, bool RoundToStep,
8383                   llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
8384   ExprResult NewStep = tryBuildCapture(SemaRef, Step, Captures);
8385   if (!NewStep.isUsable())
8386     return nullptr;
8387   llvm::APSInt LRes, SRes;
8388   bool IsLowerConst = false, IsStepConst = false;
8389   if (Optional<llvm::APSInt> Res =
8390           Lower->getIntegerConstantExpr(SemaRef.Context)) {
8391     LRes = *Res;
8392     IsLowerConst = true;
8393   }
8394   if (Optional<llvm::APSInt> Res =
8395           Step->getIntegerConstantExpr(SemaRef.Context)) {
8396     SRes = *Res;
8397     IsStepConst = true;
8398   }
8399   bool NoNeedToConvert = IsLowerConst && !RoundToStep &&
8400                          ((!TestIsStrictOp && LRes.isNonNegative()) ||
8401                           (TestIsStrictOp && LRes.isStrictlyPositive()));
8402   bool NeedToReorganize = false;
8403   // Check if any subexpressions in Lower -Step [+ 1] lead to overflow.
8404   if (!NoNeedToConvert && IsLowerConst &&
8405       (TestIsStrictOp || (RoundToStep && IsStepConst))) {
8406     NoNeedToConvert = true;
8407     if (RoundToStep) {
8408       unsigned BW = LRes.getBitWidth() > SRes.getBitWidth()
8409                         ? LRes.getBitWidth()
8410                         : SRes.getBitWidth();
8411       LRes = LRes.extend(BW + 1);
8412       LRes.setIsSigned(true);
8413       SRes = SRes.extend(BW + 1);
8414       SRes.setIsSigned(true);
8415       LRes -= SRes;
8416       NoNeedToConvert = LRes.trunc(BW).extend(BW + 1) == LRes;
8417       LRes = LRes.trunc(BW);
8418     }
8419     if (TestIsStrictOp) {
8420       unsigned BW = LRes.getBitWidth();
8421       LRes = LRes.extend(BW + 1);
8422       LRes.setIsSigned(true);
8423       ++LRes;
8424       NoNeedToConvert =
8425           NoNeedToConvert && LRes.trunc(BW).extend(BW + 1) == LRes;
8426       // truncate to the original bitwidth.
8427       LRes = LRes.trunc(BW);
8428     }
8429     NeedToReorganize = NoNeedToConvert;
8430   }
8431   llvm::APSInt URes;
8432   bool IsUpperConst = false;
8433   if (Optional<llvm::APSInt> Res =
8434           Upper->getIntegerConstantExpr(SemaRef.Context)) {
8435     URes = *Res;
8436     IsUpperConst = true;
8437   }
8438   if (NoNeedToConvert && IsLowerConst && IsUpperConst &&
8439       (!RoundToStep || IsStepConst)) {
8440     unsigned BW = LRes.getBitWidth() > URes.getBitWidth() ? LRes.getBitWidth()
8441                                                           : URes.getBitWidth();
8442     LRes = LRes.extend(BW + 1);
8443     LRes.setIsSigned(true);
8444     URes = URes.extend(BW + 1);
8445     URes.setIsSigned(true);
8446     URes -= LRes;
8447     NoNeedToConvert = URes.trunc(BW).extend(BW + 1) == URes;
8448     NeedToReorganize = NoNeedToConvert;
8449   }
8450   // If the boundaries are not constant or (Lower - Step [+ 1]) is not constant
8451   // or less than zero (Upper - (Lower - Step [+ 1]) may overflow) - promote to
8452   // unsigned.
8453   if ((!NoNeedToConvert || (LRes.isNegative() && !IsUpperConst)) &&
8454       !LCTy->isDependentType() && LCTy->isIntegerType()) {
8455     QualType LowerTy = Lower->getType();
8456     QualType UpperTy = Upper->getType();
8457     uint64_t LowerSize = SemaRef.Context.getTypeSize(LowerTy);
8458     uint64_t UpperSize = SemaRef.Context.getTypeSize(UpperTy);
8459     if ((LowerSize <= UpperSize && UpperTy->hasSignedIntegerRepresentation()) ||
8460         (LowerSize > UpperSize && LowerTy->hasSignedIntegerRepresentation())) {
8461       QualType CastType = SemaRef.Context.getIntTypeForBitwidth(
8462           LowerSize > UpperSize ? LowerSize : UpperSize, /*Signed=*/0);
8463       Upper =
8464           SemaRef
8465               .PerformImplicitConversion(
8466                   SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Upper).get(),
8467                   CastType, Sema::AA_Converting)
8468               .get();
8469       Lower = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Lower).get();
8470       NewStep = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, NewStep.get());
8471     }
8472   }
8473   if (!Lower || !Upper || NewStep.isInvalid())
8474     return nullptr;
8475 
8476   ExprResult Diff;
8477   // If need to reorganize, then calculate the form as Upper - (Lower - Step [+
8478   // 1]).
8479   if (NeedToReorganize) {
8480     Diff = Lower;
8481 
8482     if (RoundToStep) {
8483       // Lower - Step
8484       Diff =
8485           SemaRef.BuildBinOp(S, DefaultLoc, BO_Sub, Diff.get(), NewStep.get());
8486       if (!Diff.isUsable())
8487         return nullptr;
8488     }
8489 
8490     // Lower - Step [+ 1]
8491     if (TestIsStrictOp)
8492       Diff = SemaRef.BuildBinOp(
8493           S, DefaultLoc, BO_Add, Diff.get(),
8494           SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get());
8495     if (!Diff.isUsable())
8496       return nullptr;
8497 
8498     Diff = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Diff.get());
8499     if (!Diff.isUsable())
8500       return nullptr;
8501 
8502     // Upper - (Lower - Step [+ 1]).
8503     Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Sub, Upper, Diff.get());
8504     if (!Diff.isUsable())
8505       return nullptr;
8506   } else {
8507     Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Sub, Upper, Lower);
8508 
8509     if (!Diff.isUsable() && LCTy->getAsCXXRecordDecl()) {
8510       // BuildBinOp already emitted error, this one is to point user to upper
8511       // and lower bound, and to tell what is passed to 'operator-'.
8512       SemaRef.Diag(Upper->getBeginLoc(), diag::err_omp_loop_diff_cxx)
8513           << Upper->getSourceRange() << Lower->getSourceRange();
8514       return nullptr;
8515     }
8516 
8517     if (!Diff.isUsable())
8518       return nullptr;
8519 
8520     // Upper - Lower [- 1]
8521     if (TestIsStrictOp)
8522       Diff = SemaRef.BuildBinOp(
8523           S, DefaultLoc, BO_Sub, Diff.get(),
8524           SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get());
8525     if (!Diff.isUsable())
8526       return nullptr;
8527 
8528     if (RoundToStep) {
8529       // Upper - Lower [- 1] + Step
8530       Diff =
8531           SemaRef.BuildBinOp(S, DefaultLoc, BO_Add, Diff.get(), NewStep.get());
8532       if (!Diff.isUsable())
8533         return nullptr;
8534     }
8535   }
8536 
8537   // Parentheses (for dumping/debugging purposes only).
8538   Diff = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Diff.get());
8539   if (!Diff.isUsable())
8540     return nullptr;
8541 
8542   // (Upper - Lower [- 1] + Step) / Step or (Upper - Lower) / Step
8543   Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Div, Diff.get(), NewStep.get());
8544   if (!Diff.isUsable())
8545     return nullptr;
8546 
8547   return Diff.get();
8548 }
8549 
8550 /// Build the expression to calculate the number of iterations.
8551 Expr *OpenMPIterationSpaceChecker::buildNumIterations(
8552     Scope *S, ArrayRef<LoopIterationSpace> ResultIterSpaces, bool LimitedType,
8553     llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const {
8554   QualType VarType = LCDecl->getType().getNonReferenceType();
8555   if (!VarType->isIntegerType() && !VarType->isPointerType() &&
8556       !SemaRef.getLangOpts().CPlusPlus)
8557     return nullptr;
8558   Expr *LBVal = LB;
8559   Expr *UBVal = UB;
8560   // LB = TestIsLessOp.getValue() ? min(LB(MinVal), LB(MaxVal)) :
8561   // max(LB(MinVal), LB(MaxVal))
8562   if (InitDependOnLC) {
8563     const LoopIterationSpace &IS = ResultIterSpaces[*InitDependOnLC - 1];
8564     if (!IS.MinValue || !IS.MaxValue)
8565       return nullptr;
8566     // OuterVar = Min
8567     ExprResult MinValue =
8568         SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, IS.MinValue);
8569     if (!MinValue.isUsable())
8570       return nullptr;
8571 
8572     ExprResult LBMinVal = SemaRef.BuildBinOp(S, DefaultLoc, BO_Assign,
8573                                              IS.CounterVar, MinValue.get());
8574     if (!LBMinVal.isUsable())
8575       return nullptr;
8576     // OuterVar = Min, LBVal
8577     LBMinVal =
8578         SemaRef.BuildBinOp(S, DefaultLoc, BO_Comma, LBMinVal.get(), LBVal);
8579     if (!LBMinVal.isUsable())
8580       return nullptr;
8581     // (OuterVar = Min, LBVal)
8582     LBMinVal = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, LBMinVal.get());
8583     if (!LBMinVal.isUsable())
8584       return nullptr;
8585 
8586     // OuterVar = Max
8587     ExprResult MaxValue =
8588         SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, IS.MaxValue);
8589     if (!MaxValue.isUsable())
8590       return nullptr;
8591 
8592     ExprResult LBMaxVal = SemaRef.BuildBinOp(S, DefaultLoc, BO_Assign,
8593                                              IS.CounterVar, MaxValue.get());
8594     if (!LBMaxVal.isUsable())
8595       return nullptr;
8596     // OuterVar = Max, LBVal
8597     LBMaxVal =
8598         SemaRef.BuildBinOp(S, DefaultLoc, BO_Comma, LBMaxVal.get(), LBVal);
8599     if (!LBMaxVal.isUsable())
8600       return nullptr;
8601     // (OuterVar = Max, LBVal)
8602     LBMaxVal = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, LBMaxVal.get());
8603     if (!LBMaxVal.isUsable())
8604       return nullptr;
8605 
8606     Expr *LBMin = tryBuildCapture(SemaRef, LBMinVal.get(), Captures).get();
8607     Expr *LBMax = tryBuildCapture(SemaRef, LBMaxVal.get(), Captures).get();
8608     if (!LBMin || !LBMax)
8609       return nullptr;
8610     // LB(MinVal) < LB(MaxVal)
8611     ExprResult MinLessMaxRes =
8612         SemaRef.BuildBinOp(S, DefaultLoc, BO_LT, LBMin, LBMax);
8613     if (!MinLessMaxRes.isUsable())
8614       return nullptr;
8615     Expr *MinLessMax =
8616         tryBuildCapture(SemaRef, MinLessMaxRes.get(), Captures).get();
8617     if (!MinLessMax)
8618       return nullptr;
8619     if (*TestIsLessOp) {
8620       // LB(MinVal) < LB(MaxVal) ? LB(MinVal) : LB(MaxVal) - min(LB(MinVal),
8621       // LB(MaxVal))
8622       ExprResult MinLB = SemaRef.ActOnConditionalOp(DefaultLoc, DefaultLoc,
8623                                                     MinLessMax, LBMin, LBMax);
8624       if (!MinLB.isUsable())
8625         return nullptr;
8626       LBVal = MinLB.get();
8627     } else {
8628       // LB(MinVal) < LB(MaxVal) ? LB(MaxVal) : LB(MinVal) - max(LB(MinVal),
8629       // LB(MaxVal))
8630       ExprResult MaxLB = SemaRef.ActOnConditionalOp(DefaultLoc, DefaultLoc,
8631                                                     MinLessMax, LBMax, LBMin);
8632       if (!MaxLB.isUsable())
8633         return nullptr;
8634       LBVal = MaxLB.get();
8635     }
8636   }
8637   // UB = TestIsLessOp.getValue() ? max(UB(MinVal), UB(MaxVal)) :
8638   // min(UB(MinVal), UB(MaxVal))
8639   if (CondDependOnLC) {
8640     const LoopIterationSpace &IS = ResultIterSpaces[*CondDependOnLC - 1];
8641     if (!IS.MinValue || !IS.MaxValue)
8642       return nullptr;
8643     // OuterVar = Min
8644     ExprResult MinValue =
8645         SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, IS.MinValue);
8646     if (!MinValue.isUsable())
8647       return nullptr;
8648 
8649     ExprResult UBMinVal = SemaRef.BuildBinOp(S, DefaultLoc, BO_Assign,
8650                                              IS.CounterVar, MinValue.get());
8651     if (!UBMinVal.isUsable())
8652       return nullptr;
8653     // OuterVar = Min, UBVal
8654     UBMinVal =
8655         SemaRef.BuildBinOp(S, DefaultLoc, BO_Comma, UBMinVal.get(), UBVal);
8656     if (!UBMinVal.isUsable())
8657       return nullptr;
8658     // (OuterVar = Min, UBVal)
8659     UBMinVal = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, UBMinVal.get());
8660     if (!UBMinVal.isUsable())
8661       return nullptr;
8662 
8663     // OuterVar = Max
8664     ExprResult MaxValue =
8665         SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, IS.MaxValue);
8666     if (!MaxValue.isUsable())
8667       return nullptr;
8668 
8669     ExprResult UBMaxVal = SemaRef.BuildBinOp(S, DefaultLoc, BO_Assign,
8670                                              IS.CounterVar, MaxValue.get());
8671     if (!UBMaxVal.isUsable())
8672       return nullptr;
8673     // OuterVar = Max, UBVal
8674     UBMaxVal =
8675         SemaRef.BuildBinOp(S, DefaultLoc, BO_Comma, UBMaxVal.get(), UBVal);
8676     if (!UBMaxVal.isUsable())
8677       return nullptr;
8678     // (OuterVar = Max, UBVal)
8679     UBMaxVal = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, UBMaxVal.get());
8680     if (!UBMaxVal.isUsable())
8681       return nullptr;
8682 
8683     Expr *UBMin = tryBuildCapture(SemaRef, UBMinVal.get(), Captures).get();
8684     Expr *UBMax = tryBuildCapture(SemaRef, UBMaxVal.get(), Captures).get();
8685     if (!UBMin || !UBMax)
8686       return nullptr;
8687     // UB(MinVal) > UB(MaxVal)
8688     ExprResult MinGreaterMaxRes =
8689         SemaRef.BuildBinOp(S, DefaultLoc, BO_GT, UBMin, UBMax);
8690     if (!MinGreaterMaxRes.isUsable())
8691       return nullptr;
8692     Expr *MinGreaterMax =
8693         tryBuildCapture(SemaRef, MinGreaterMaxRes.get(), Captures).get();
8694     if (!MinGreaterMax)
8695       return nullptr;
8696     if (*TestIsLessOp) {
8697       // UB(MinVal) > UB(MaxVal) ? UB(MinVal) : UB(MaxVal) - max(UB(MinVal),
8698       // UB(MaxVal))
8699       ExprResult MaxUB = SemaRef.ActOnConditionalOp(
8700           DefaultLoc, DefaultLoc, MinGreaterMax, UBMin, UBMax);
8701       if (!MaxUB.isUsable())
8702         return nullptr;
8703       UBVal = MaxUB.get();
8704     } else {
8705       // UB(MinVal) > UB(MaxVal) ? UB(MaxVal) : UB(MinVal) - min(UB(MinVal),
8706       // UB(MaxVal))
8707       ExprResult MinUB = SemaRef.ActOnConditionalOp(
8708           DefaultLoc, DefaultLoc, MinGreaterMax, UBMax, UBMin);
8709       if (!MinUB.isUsable())
8710         return nullptr;
8711       UBVal = MinUB.get();
8712     }
8713   }
8714   Expr *UBExpr = TestIsLessOp.value() ? UBVal : LBVal;
8715   Expr *LBExpr = TestIsLessOp.value() ? LBVal : UBVal;
8716   Expr *Upper = tryBuildCapture(SemaRef, UBExpr, Captures).get();
8717   Expr *Lower = tryBuildCapture(SemaRef, LBExpr, Captures).get();
8718   if (!Upper || !Lower)
8719     return nullptr;
8720 
8721   ExprResult Diff = calculateNumIters(SemaRef, S, DefaultLoc, Lower, Upper,
8722                                       Step, VarType, TestIsStrictOp,
8723                                       /*RoundToStep=*/true, Captures);
8724   if (!Diff.isUsable())
8725     return nullptr;
8726 
8727   // OpenMP runtime requires 32-bit or 64-bit loop variables.
8728   QualType Type = Diff.get()->getType();
8729   ASTContext &C = SemaRef.Context;
8730   bool UseVarType = VarType->hasIntegerRepresentation() &&
8731                     C.getTypeSize(Type) > C.getTypeSize(VarType);
8732   if (!Type->isIntegerType() || UseVarType) {
8733     unsigned NewSize =
8734         UseVarType ? C.getTypeSize(VarType) : C.getTypeSize(Type);
8735     bool IsSigned = UseVarType ? VarType->hasSignedIntegerRepresentation()
8736                                : Type->hasSignedIntegerRepresentation();
8737     Type = C.getIntTypeForBitwidth(NewSize, IsSigned);
8738     if (!SemaRef.Context.hasSameType(Diff.get()->getType(), Type)) {
8739       Diff = SemaRef.PerformImplicitConversion(
8740           Diff.get(), Type, Sema::AA_Converting, /*AllowExplicit=*/true);
8741       if (!Diff.isUsable())
8742         return nullptr;
8743     }
8744   }
8745   if (LimitedType) {
8746     unsigned NewSize = (C.getTypeSize(Type) > 32) ? 64 : 32;
8747     if (NewSize != C.getTypeSize(Type)) {
8748       if (NewSize < C.getTypeSize(Type)) {
8749         assert(NewSize == 64 && "incorrect loop var size");
8750         SemaRef.Diag(DefaultLoc, diag::warn_omp_loop_64_bit_var)
8751             << InitSrcRange << ConditionSrcRange;
8752       }
8753       QualType NewType = C.getIntTypeForBitwidth(
8754           NewSize, Type->hasSignedIntegerRepresentation() ||
8755                        C.getTypeSize(Type) < NewSize);
8756       if (!SemaRef.Context.hasSameType(Diff.get()->getType(), NewType)) {
8757         Diff = SemaRef.PerformImplicitConversion(Diff.get(), NewType,
8758                                                  Sema::AA_Converting, true);
8759         if (!Diff.isUsable())
8760           return nullptr;
8761       }
8762     }
8763   }
8764 
8765   return Diff.get();
8766 }
8767 
8768 std::pair<Expr *, Expr *> OpenMPIterationSpaceChecker::buildMinMaxValues(
8769     Scope *S, llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const {
8770   // Do not build for iterators, they cannot be used in non-rectangular loop
8771   // nests.
8772   if (LCDecl->getType()->isRecordType())
8773     return std::make_pair(nullptr, nullptr);
8774   // If we subtract, the min is in the condition, otherwise the min is in the
8775   // init value.
8776   Expr *MinExpr = nullptr;
8777   Expr *MaxExpr = nullptr;
8778   Expr *LBExpr = TestIsLessOp.value() ? LB : UB;
8779   Expr *UBExpr = TestIsLessOp.value() ? UB : LB;
8780   bool LBNonRect = TestIsLessOp.value() ? InitDependOnLC.has_value()
8781                                         : CondDependOnLC.has_value();
8782   bool UBNonRect = TestIsLessOp.value() ? CondDependOnLC.has_value()
8783                                         : InitDependOnLC.has_value();
8784   Expr *Lower =
8785       LBNonRect ? LBExpr : tryBuildCapture(SemaRef, LBExpr, Captures).get();
8786   Expr *Upper =
8787       UBNonRect ? UBExpr : tryBuildCapture(SemaRef, UBExpr, Captures).get();
8788   if (!Upper || !Lower)
8789     return std::make_pair(nullptr, nullptr);
8790 
8791   if (*TestIsLessOp)
8792     MinExpr = Lower;
8793   else
8794     MaxExpr = Upper;
8795 
8796   // Build minimum/maximum value based on number of iterations.
8797   QualType VarType = LCDecl->getType().getNonReferenceType();
8798 
8799   ExprResult Diff = calculateNumIters(SemaRef, S, DefaultLoc, Lower, Upper,
8800                                       Step, VarType, TestIsStrictOp,
8801                                       /*RoundToStep=*/false, Captures);
8802   if (!Diff.isUsable())
8803     return std::make_pair(nullptr, nullptr);
8804 
8805   // ((Upper - Lower [- 1]) / Step) * Step
8806   // Parentheses (for dumping/debugging purposes only).
8807   Diff = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Diff.get());
8808   if (!Diff.isUsable())
8809     return std::make_pair(nullptr, nullptr);
8810 
8811   ExprResult NewStep = tryBuildCapture(SemaRef, Step, Captures);
8812   if (!NewStep.isUsable())
8813     return std::make_pair(nullptr, nullptr);
8814   Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Mul, Diff.get(), NewStep.get());
8815   if (!Diff.isUsable())
8816     return std::make_pair(nullptr, nullptr);
8817 
8818   // Parentheses (for dumping/debugging purposes only).
8819   Diff = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Diff.get());
8820   if (!Diff.isUsable())
8821     return std::make_pair(nullptr, nullptr);
8822 
8823   // Convert to the ptrdiff_t, if original type is pointer.
8824   if (VarType->isAnyPointerType() &&
8825       !SemaRef.Context.hasSameType(
8826           Diff.get()->getType(),
8827           SemaRef.Context.getUnsignedPointerDiffType())) {
8828     Diff = SemaRef.PerformImplicitConversion(
8829         Diff.get(), SemaRef.Context.getUnsignedPointerDiffType(),
8830         Sema::AA_Converting, /*AllowExplicit=*/true);
8831   }
8832   if (!Diff.isUsable())
8833     return std::make_pair(nullptr, nullptr);
8834 
8835   if (*TestIsLessOp) {
8836     // MinExpr = Lower;
8837     // MaxExpr = Lower + (((Upper - Lower [- 1]) / Step) * Step)
8838     Diff = SemaRef.BuildBinOp(
8839         S, DefaultLoc, BO_Add,
8840         SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Lower).get(),
8841         Diff.get());
8842     if (!Diff.isUsable())
8843       return std::make_pair(nullptr, nullptr);
8844   } else {
8845     // MaxExpr = Upper;
8846     // MinExpr = Upper - (((Upper - Lower [- 1]) / Step) * Step)
8847     Diff = SemaRef.BuildBinOp(
8848         S, DefaultLoc, BO_Sub,
8849         SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Upper).get(),
8850         Diff.get());
8851     if (!Diff.isUsable())
8852       return std::make_pair(nullptr, nullptr);
8853   }
8854 
8855   // Convert to the original type.
8856   if (SemaRef.Context.hasSameType(Diff.get()->getType(), VarType))
8857     Diff = SemaRef.PerformImplicitConversion(Diff.get(), VarType,
8858                                              Sema::AA_Converting,
8859                                              /*AllowExplicit=*/true);
8860   if (!Diff.isUsable())
8861     return std::make_pair(nullptr, nullptr);
8862 
8863   Sema::TentativeAnalysisScope Trap(SemaRef);
8864   Diff = SemaRef.ActOnFinishFullExpr(Diff.get(), /*DiscardedValue=*/false);
8865   if (!Diff.isUsable())
8866     return std::make_pair(nullptr, nullptr);
8867 
8868   if (*TestIsLessOp)
8869     MaxExpr = Diff.get();
8870   else
8871     MinExpr = Diff.get();
8872 
8873   return std::make_pair(MinExpr, MaxExpr);
8874 }
8875 
8876 Expr *OpenMPIterationSpaceChecker::buildFinalCondition(Scope *S) const {
8877   if (InitDependOnLC || CondDependOnLC)
8878     return Condition;
8879   return nullptr;
8880 }
8881 
8882 Expr *OpenMPIterationSpaceChecker::buildPreCond(
8883     Scope *S, Expr *Cond,
8884     llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) const {
8885   // Do not build a precondition when the condition/initialization is dependent
8886   // to prevent pessimistic early loop exit.
8887   // TODO: this can be improved by calculating min/max values but not sure that
8888   // it will be very effective.
8889   if (CondDependOnLC || InitDependOnLC)
8890     return SemaRef
8891         .PerformImplicitConversion(
8892             SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get(),
8893             SemaRef.Context.BoolTy, /*Action=*/Sema::AA_Casting,
8894             /*AllowExplicit=*/true)
8895         .get();
8896 
8897   // Try to build LB <op> UB, where <op> is <, >, <=, or >=.
8898   Sema::TentativeAnalysisScope Trap(SemaRef);
8899 
8900   ExprResult NewLB = tryBuildCapture(SemaRef, LB, Captures);
8901   ExprResult NewUB = tryBuildCapture(SemaRef, UB, Captures);
8902   if (!NewLB.isUsable() || !NewUB.isUsable())
8903     return nullptr;
8904 
8905   ExprResult CondExpr = SemaRef.BuildBinOp(
8906       S, DefaultLoc,
8907       TestIsLessOp.value() ? (TestIsStrictOp ? BO_LT : BO_LE)
8908                            : (TestIsStrictOp ? BO_GT : BO_GE),
8909       NewLB.get(), NewUB.get());
8910   if (CondExpr.isUsable()) {
8911     if (!SemaRef.Context.hasSameUnqualifiedType(CondExpr.get()->getType(),
8912                                                 SemaRef.Context.BoolTy))
8913       CondExpr = SemaRef.PerformImplicitConversion(
8914           CondExpr.get(), SemaRef.Context.BoolTy, /*Action=*/Sema::AA_Casting,
8915           /*AllowExplicit=*/true);
8916   }
8917 
8918   // Otherwise use original loop condition and evaluate it in runtime.
8919   return CondExpr.isUsable() ? CondExpr.get() : Cond;
8920 }
8921 
8922 /// Build reference expression to the counter be used for codegen.
8923 DeclRefExpr *OpenMPIterationSpaceChecker::buildCounterVar(
8924     llvm::MapVector<const Expr *, DeclRefExpr *> &Captures,
8925     DSAStackTy &DSA) const {
8926   auto *VD = dyn_cast<VarDecl>(LCDecl);
8927   if (!VD) {
8928     VD = SemaRef.isOpenMPCapturedDecl(LCDecl);
8929     DeclRefExpr *Ref = buildDeclRefExpr(
8930         SemaRef, VD, VD->getType().getNonReferenceType(), DefaultLoc);
8931     const DSAStackTy::DSAVarData Data =
8932         DSA.getTopDSA(LCDecl, /*FromParent=*/false);
8933     // If the loop control decl is explicitly marked as private, do not mark it
8934     // as captured again.
8935     if (!isOpenMPPrivate(Data.CKind) || !Data.RefExpr)
8936       Captures.insert(std::make_pair(LCRef, Ref));
8937     return Ref;
8938   }
8939   return cast<DeclRefExpr>(LCRef);
8940 }
8941 
8942 Expr *OpenMPIterationSpaceChecker::buildPrivateCounterVar() const {
8943   if (LCDecl && !LCDecl->isInvalidDecl()) {
8944     QualType Type = LCDecl->getType().getNonReferenceType();
8945     VarDecl *PrivateVar = buildVarDecl(
8946         SemaRef, DefaultLoc, Type, LCDecl->getName(),
8947         LCDecl->hasAttrs() ? &LCDecl->getAttrs() : nullptr,
8948         isa<VarDecl>(LCDecl)
8949             ? buildDeclRefExpr(SemaRef, cast<VarDecl>(LCDecl), Type, DefaultLoc)
8950             : nullptr);
8951     if (PrivateVar->isInvalidDecl())
8952       return nullptr;
8953     return buildDeclRefExpr(SemaRef, PrivateVar, Type, DefaultLoc);
8954   }
8955   return nullptr;
8956 }
8957 
8958 /// Build initialization of the counter to be used for codegen.
8959 Expr *OpenMPIterationSpaceChecker::buildCounterInit() const { return LB; }
8960 
8961 /// Build step of the counter be used for codegen.
8962 Expr *OpenMPIterationSpaceChecker::buildCounterStep() const { return Step; }
8963 
8964 Expr *OpenMPIterationSpaceChecker::buildOrderedLoopData(
8965     Scope *S, Expr *Counter,
8966     llvm::MapVector<const Expr *, DeclRefExpr *> &Captures, SourceLocation Loc,
8967     Expr *Inc, OverloadedOperatorKind OOK) {
8968   Expr *Cnt = SemaRef.DefaultLvalueConversion(Counter).get();
8969   if (!Cnt)
8970     return nullptr;
8971   if (Inc) {
8972     assert((OOK == OO_Plus || OOK == OO_Minus) &&
8973            "Expected only + or - operations for depend clauses.");
8974     BinaryOperatorKind BOK = (OOK == OO_Plus) ? BO_Add : BO_Sub;
8975     Cnt = SemaRef.BuildBinOp(S, Loc, BOK, Cnt, Inc).get();
8976     if (!Cnt)
8977       return nullptr;
8978   }
8979   QualType VarType = LCDecl->getType().getNonReferenceType();
8980   if (!VarType->isIntegerType() && !VarType->isPointerType() &&
8981       !SemaRef.getLangOpts().CPlusPlus)
8982     return nullptr;
8983   // Upper - Lower
8984   Expr *Upper =
8985       TestIsLessOp.value() ? Cnt : tryBuildCapture(SemaRef, LB, Captures).get();
8986   Expr *Lower =
8987       TestIsLessOp.value() ? tryBuildCapture(SemaRef, LB, Captures).get() : Cnt;
8988   if (!Upper || !Lower)
8989     return nullptr;
8990 
8991   ExprResult Diff = calculateNumIters(
8992       SemaRef, S, DefaultLoc, Lower, Upper, Step, VarType,
8993       /*TestIsStrictOp=*/false, /*RoundToStep=*/false, Captures);
8994   if (!Diff.isUsable())
8995     return nullptr;
8996 
8997   return Diff.get();
8998 }
8999 } // namespace
9000 
9001 void Sema::ActOnOpenMPLoopInitialization(SourceLocation ForLoc, Stmt *Init) {
9002   assert(getLangOpts().OpenMP && "OpenMP is not active.");
9003   assert(Init && "Expected loop in canonical form.");
9004   unsigned AssociatedLoops = DSAStack->getAssociatedLoops();
9005   if (AssociatedLoops > 0 &&
9006       isOpenMPLoopDirective(DSAStack->getCurrentDirective())) {
9007     DSAStack->loopStart();
9008     OpenMPIterationSpaceChecker ISC(*this, /*SupportsNonRectangular=*/true,
9009                                     *DSAStack, ForLoc);
9010     if (!ISC.checkAndSetInit(Init, /*EmitDiags=*/false)) {
9011       if (ValueDecl *D = ISC.getLoopDecl()) {
9012         auto *VD = dyn_cast<VarDecl>(D);
9013         DeclRefExpr *PrivateRef = nullptr;
9014         if (!VD) {
9015           if (VarDecl *Private = isOpenMPCapturedDecl(D)) {
9016             VD = Private;
9017           } else {
9018             PrivateRef = buildCapture(*this, D, ISC.getLoopDeclRefExpr(),
9019                                       /*WithInit=*/false);
9020             VD = cast<VarDecl>(PrivateRef->getDecl());
9021           }
9022         }
9023         DSAStack->addLoopControlVariable(D, VD);
9024         const Decl *LD = DSAStack->getPossiblyLoopCunter();
9025         if (LD != D->getCanonicalDecl()) {
9026           DSAStack->resetPossibleLoopCounter();
9027           if (auto *Var = dyn_cast_or_null<VarDecl>(LD))
9028             MarkDeclarationsReferencedInExpr(
9029                 buildDeclRefExpr(*this, const_cast<VarDecl *>(Var),
9030                                  Var->getType().getNonLValueExprType(Context),
9031                                  ForLoc, /*RefersToCapture=*/true));
9032         }
9033         OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
9034         // OpenMP [2.14.1.1, Data-sharing Attribute Rules for Variables
9035         // Referenced in a Construct, C/C++]. The loop iteration variable in the
9036         // associated for-loop of a simd construct with just one associated
9037         // for-loop may be listed in a linear clause with a constant-linear-step
9038         // that is the increment of the associated for-loop. The loop iteration
9039         // variable(s) in the associated for-loop(s) of a for or parallel for
9040         // construct may be listed in a private or lastprivate clause.
9041         DSAStackTy::DSAVarData DVar =
9042             DSAStack->getTopDSA(D, /*FromParent=*/false);
9043         // If LoopVarRefExpr is nullptr it means the corresponding loop variable
9044         // is declared in the loop and it is predetermined as a private.
9045         Expr *LoopDeclRefExpr = ISC.getLoopDeclRefExpr();
9046         OpenMPClauseKind PredeterminedCKind =
9047             isOpenMPSimdDirective(DKind)
9048                 ? (DSAStack->hasMutipleLoops() ? OMPC_lastprivate : OMPC_linear)
9049                 : OMPC_private;
9050         if (((isOpenMPSimdDirective(DKind) && DVar.CKind != OMPC_unknown &&
9051               DVar.CKind != PredeterminedCKind && DVar.RefExpr &&
9052               (LangOpts.OpenMP <= 45 || (DVar.CKind != OMPC_lastprivate &&
9053                                          DVar.CKind != OMPC_private))) ||
9054              ((isOpenMPWorksharingDirective(DKind) || DKind == OMPD_taskloop ||
9055                DKind == OMPD_master_taskloop || DKind == OMPD_masked_taskloop ||
9056                DKind == OMPD_parallel_master_taskloop ||
9057                DKind == OMPD_parallel_masked_taskloop ||
9058                isOpenMPDistributeDirective(DKind)) &&
9059               !isOpenMPSimdDirective(DKind) && DVar.CKind != OMPC_unknown &&
9060               DVar.CKind != OMPC_private && DVar.CKind != OMPC_lastprivate)) &&
9061             (DVar.CKind != OMPC_private || DVar.RefExpr)) {
9062           Diag(Init->getBeginLoc(), diag::err_omp_loop_var_dsa)
9063               << getOpenMPClauseName(DVar.CKind)
9064               << getOpenMPDirectiveName(DKind)
9065               << getOpenMPClauseName(PredeterminedCKind);
9066           if (DVar.RefExpr == nullptr)
9067             DVar.CKind = PredeterminedCKind;
9068           reportOriginalDsa(*this, DSAStack, D, DVar,
9069                             /*IsLoopIterVar=*/true);
9070         } else if (LoopDeclRefExpr) {
9071           // Make the loop iteration variable private (for worksharing
9072           // constructs), linear (for simd directives with the only one
9073           // associated loop) or lastprivate (for simd directives with several
9074           // collapsed or ordered loops).
9075           if (DVar.CKind == OMPC_unknown)
9076             DSAStack->addDSA(D, LoopDeclRefExpr, PredeterminedCKind,
9077                              PrivateRef);
9078         }
9079       }
9080     }
9081     DSAStack->setAssociatedLoops(AssociatedLoops - 1);
9082   }
9083 }
9084 
9085 /// Called on a for stmt to check and extract its iteration space
9086 /// for further processing (such as collapsing).
9087 static bool checkOpenMPIterationSpace(
9088     OpenMPDirectiveKind DKind, Stmt *S, Sema &SemaRef, DSAStackTy &DSA,
9089     unsigned CurrentNestedLoopCount, unsigned NestedLoopCount,
9090     unsigned TotalNestedLoopCount, Expr *CollapseLoopCountExpr,
9091     Expr *OrderedLoopCountExpr,
9092     Sema::VarsWithInheritedDSAType &VarsWithImplicitDSA,
9093     llvm::MutableArrayRef<LoopIterationSpace> ResultIterSpaces,
9094     llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
9095   bool SupportsNonRectangular = !isOpenMPLoopTransformationDirective(DKind);
9096   // OpenMP [2.9.1, Canonical Loop Form]
9097   //   for (init-expr; test-expr; incr-expr) structured-block
9098   //   for (range-decl: range-expr) structured-block
9099   if (auto *CanonLoop = dyn_cast_or_null<OMPCanonicalLoop>(S))
9100     S = CanonLoop->getLoopStmt();
9101   auto *For = dyn_cast_or_null<ForStmt>(S);
9102   auto *CXXFor = dyn_cast_or_null<CXXForRangeStmt>(S);
9103   // Ranged for is supported only in OpenMP 5.0.
9104   if (!For && (SemaRef.LangOpts.OpenMP <= 45 || !CXXFor)) {
9105     SemaRef.Diag(S->getBeginLoc(), diag::err_omp_not_for)
9106         << (CollapseLoopCountExpr != nullptr || OrderedLoopCountExpr != nullptr)
9107         << getOpenMPDirectiveName(DKind) << TotalNestedLoopCount
9108         << (CurrentNestedLoopCount > 0) << CurrentNestedLoopCount;
9109     if (TotalNestedLoopCount > 1) {
9110       if (CollapseLoopCountExpr && OrderedLoopCountExpr)
9111         SemaRef.Diag(DSA.getConstructLoc(),
9112                      diag::note_omp_collapse_ordered_expr)
9113             << 2 << CollapseLoopCountExpr->getSourceRange()
9114             << OrderedLoopCountExpr->getSourceRange();
9115       else if (CollapseLoopCountExpr)
9116         SemaRef.Diag(CollapseLoopCountExpr->getExprLoc(),
9117                      diag::note_omp_collapse_ordered_expr)
9118             << 0 << CollapseLoopCountExpr->getSourceRange();
9119       else
9120         SemaRef.Diag(OrderedLoopCountExpr->getExprLoc(),
9121                      diag::note_omp_collapse_ordered_expr)
9122             << 1 << OrderedLoopCountExpr->getSourceRange();
9123     }
9124     return true;
9125   }
9126   assert(((For && For->getBody()) || (CXXFor && CXXFor->getBody())) &&
9127          "No loop body.");
9128   // Postpone analysis in dependent contexts for ranged for loops.
9129   if (CXXFor && SemaRef.CurContext->isDependentContext())
9130     return false;
9131 
9132   OpenMPIterationSpaceChecker ISC(SemaRef, SupportsNonRectangular, DSA,
9133                                   For ? For->getForLoc() : CXXFor->getForLoc());
9134 
9135   // Check init.
9136   Stmt *Init = For ? For->getInit() : CXXFor->getBeginStmt();
9137   if (ISC.checkAndSetInit(Init))
9138     return true;
9139 
9140   bool HasErrors = false;
9141 
9142   // Check loop variable's type.
9143   if (ValueDecl *LCDecl = ISC.getLoopDecl()) {
9144     // OpenMP [2.6, Canonical Loop Form]
9145     // Var is one of the following:
9146     //   A variable of signed or unsigned integer type.
9147     //   For C++, a variable of a random access iterator type.
9148     //   For C, a variable of a pointer type.
9149     QualType VarType = LCDecl->getType().getNonReferenceType();
9150     if (!VarType->isDependentType() && !VarType->isIntegerType() &&
9151         !VarType->isPointerType() &&
9152         !(SemaRef.getLangOpts().CPlusPlus && VarType->isOverloadableType())) {
9153       SemaRef.Diag(Init->getBeginLoc(), diag::err_omp_loop_variable_type)
9154           << SemaRef.getLangOpts().CPlusPlus;
9155       HasErrors = true;
9156     }
9157 
9158     // OpenMP, 2.14.1.1 Data-sharing Attribute Rules for Variables Referenced in
9159     // a Construct
9160     // The loop iteration variable(s) in the associated for-loop(s) of a for or
9161     // parallel for construct is (are) private.
9162     // The loop iteration variable in the associated for-loop of a simd
9163     // construct with just one associated for-loop is linear with a
9164     // constant-linear-step that is the increment of the associated for-loop.
9165     // Exclude loop var from the list of variables with implicitly defined data
9166     // sharing attributes.
9167     VarsWithImplicitDSA.erase(LCDecl);
9168 
9169     assert(isOpenMPLoopDirective(DKind) && "DSA for non-loop vars");
9170 
9171     // Check test-expr.
9172     HasErrors |= ISC.checkAndSetCond(For ? For->getCond() : CXXFor->getCond());
9173 
9174     // Check incr-expr.
9175     HasErrors |= ISC.checkAndSetInc(For ? For->getInc() : CXXFor->getInc());
9176   }
9177 
9178   if (ISC.dependent() || SemaRef.CurContext->isDependentContext() || HasErrors)
9179     return HasErrors;
9180 
9181   // Build the loop's iteration space representation.
9182   ResultIterSpaces[CurrentNestedLoopCount].PreCond = ISC.buildPreCond(
9183       DSA.getCurScope(), For ? For->getCond() : CXXFor->getCond(), Captures);
9184   ResultIterSpaces[CurrentNestedLoopCount].NumIterations =
9185       ISC.buildNumIterations(DSA.getCurScope(), ResultIterSpaces,
9186                              (isOpenMPWorksharingDirective(DKind) ||
9187                               isOpenMPGenericLoopDirective(DKind) ||
9188                               isOpenMPTaskLoopDirective(DKind) ||
9189                               isOpenMPDistributeDirective(DKind) ||
9190                               isOpenMPLoopTransformationDirective(DKind)),
9191                              Captures);
9192   ResultIterSpaces[CurrentNestedLoopCount].CounterVar =
9193       ISC.buildCounterVar(Captures, DSA);
9194   ResultIterSpaces[CurrentNestedLoopCount].PrivateCounterVar =
9195       ISC.buildPrivateCounterVar();
9196   ResultIterSpaces[CurrentNestedLoopCount].CounterInit = ISC.buildCounterInit();
9197   ResultIterSpaces[CurrentNestedLoopCount].CounterStep = ISC.buildCounterStep();
9198   ResultIterSpaces[CurrentNestedLoopCount].InitSrcRange = ISC.getInitSrcRange();
9199   ResultIterSpaces[CurrentNestedLoopCount].CondSrcRange =
9200       ISC.getConditionSrcRange();
9201   ResultIterSpaces[CurrentNestedLoopCount].IncSrcRange =
9202       ISC.getIncrementSrcRange();
9203   ResultIterSpaces[CurrentNestedLoopCount].Subtract = ISC.shouldSubtractStep();
9204   ResultIterSpaces[CurrentNestedLoopCount].IsStrictCompare =
9205       ISC.isStrictTestOp();
9206   std::tie(ResultIterSpaces[CurrentNestedLoopCount].MinValue,
9207            ResultIterSpaces[CurrentNestedLoopCount].MaxValue) =
9208       ISC.buildMinMaxValues(DSA.getCurScope(), Captures);
9209   ResultIterSpaces[CurrentNestedLoopCount].FinalCondition =
9210       ISC.buildFinalCondition(DSA.getCurScope());
9211   ResultIterSpaces[CurrentNestedLoopCount].IsNonRectangularLB =
9212       ISC.doesInitDependOnLC();
9213   ResultIterSpaces[CurrentNestedLoopCount].IsNonRectangularUB =
9214       ISC.doesCondDependOnLC();
9215   ResultIterSpaces[CurrentNestedLoopCount].LoopDependentIdx =
9216       ISC.getLoopDependentIdx();
9217 
9218   HasErrors |=
9219       (ResultIterSpaces[CurrentNestedLoopCount].PreCond == nullptr ||
9220        ResultIterSpaces[CurrentNestedLoopCount].NumIterations == nullptr ||
9221        ResultIterSpaces[CurrentNestedLoopCount].CounterVar == nullptr ||
9222        ResultIterSpaces[CurrentNestedLoopCount].PrivateCounterVar == nullptr ||
9223        ResultIterSpaces[CurrentNestedLoopCount].CounterInit == nullptr ||
9224        ResultIterSpaces[CurrentNestedLoopCount].CounterStep == nullptr);
9225   if (!HasErrors && DSA.isOrderedRegion()) {
9226     if (DSA.getOrderedRegionParam().second->getNumForLoops()) {
9227       if (CurrentNestedLoopCount <
9228           DSA.getOrderedRegionParam().second->getLoopNumIterations().size()) {
9229         DSA.getOrderedRegionParam().second->setLoopNumIterations(
9230             CurrentNestedLoopCount,
9231             ResultIterSpaces[CurrentNestedLoopCount].NumIterations);
9232         DSA.getOrderedRegionParam().second->setLoopCounter(
9233             CurrentNestedLoopCount,
9234             ResultIterSpaces[CurrentNestedLoopCount].CounterVar);
9235       }
9236     }
9237     for (auto &Pair : DSA.getDoacrossDependClauses()) {
9238       if (CurrentNestedLoopCount >= Pair.first->getNumLoops()) {
9239         // Erroneous case - clause has some problems.
9240         continue;
9241       }
9242       if (Pair.first->getDependencyKind() == OMPC_DEPEND_sink &&
9243           Pair.second.size() <= CurrentNestedLoopCount) {
9244         // Erroneous case - clause has some problems.
9245         Pair.first->setLoopData(CurrentNestedLoopCount, nullptr);
9246         continue;
9247       }
9248       Expr *CntValue;
9249       if (Pair.first->getDependencyKind() == OMPC_DEPEND_source)
9250         CntValue = ISC.buildOrderedLoopData(
9251             DSA.getCurScope(),
9252             ResultIterSpaces[CurrentNestedLoopCount].CounterVar, Captures,
9253             Pair.first->getDependencyLoc());
9254       else
9255         CntValue = ISC.buildOrderedLoopData(
9256             DSA.getCurScope(),
9257             ResultIterSpaces[CurrentNestedLoopCount].CounterVar, Captures,
9258             Pair.first->getDependencyLoc(),
9259             Pair.second[CurrentNestedLoopCount].first,
9260             Pair.second[CurrentNestedLoopCount].second);
9261       Pair.first->setLoopData(CurrentNestedLoopCount, CntValue);
9262     }
9263   }
9264 
9265   return HasErrors;
9266 }
9267 
9268 /// Build 'VarRef = Start.
9269 static ExprResult
9270 buildCounterInit(Sema &SemaRef, Scope *S, SourceLocation Loc, ExprResult VarRef,
9271                  ExprResult Start, bool IsNonRectangularLB,
9272                  llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
9273   // Build 'VarRef = Start.
9274   ExprResult NewStart = IsNonRectangularLB
9275                             ? Start.get()
9276                             : tryBuildCapture(SemaRef, Start.get(), Captures);
9277   if (!NewStart.isUsable())
9278     return ExprError();
9279   if (!SemaRef.Context.hasSameType(NewStart.get()->getType(),
9280                                    VarRef.get()->getType())) {
9281     NewStart = SemaRef.PerformImplicitConversion(
9282         NewStart.get(), VarRef.get()->getType(), Sema::AA_Converting,
9283         /*AllowExplicit=*/true);
9284     if (!NewStart.isUsable())
9285       return ExprError();
9286   }
9287 
9288   ExprResult Init =
9289       SemaRef.BuildBinOp(S, Loc, BO_Assign, VarRef.get(), NewStart.get());
9290   return Init;
9291 }
9292 
9293 /// Build 'VarRef = Start + Iter * Step'.
9294 static ExprResult buildCounterUpdate(
9295     Sema &SemaRef, Scope *S, SourceLocation Loc, ExprResult VarRef,
9296     ExprResult Start, ExprResult Iter, ExprResult Step, bool Subtract,
9297     bool IsNonRectangularLB,
9298     llvm::MapVector<const Expr *, DeclRefExpr *> *Captures = nullptr) {
9299   // Add parentheses (for debugging purposes only).
9300   Iter = SemaRef.ActOnParenExpr(Loc, Loc, Iter.get());
9301   if (!VarRef.isUsable() || !Start.isUsable() || !Iter.isUsable() ||
9302       !Step.isUsable())
9303     return ExprError();
9304 
9305   ExprResult NewStep = Step;
9306   if (Captures)
9307     NewStep = tryBuildCapture(SemaRef, Step.get(), *Captures);
9308   if (NewStep.isInvalid())
9309     return ExprError();
9310   ExprResult Update =
9311       SemaRef.BuildBinOp(S, Loc, BO_Mul, Iter.get(), NewStep.get());
9312   if (!Update.isUsable())
9313     return ExprError();
9314 
9315   // Try to build 'VarRef = Start, VarRef (+|-)= Iter * Step' or
9316   // 'VarRef = Start (+|-) Iter * Step'.
9317   if (!Start.isUsable())
9318     return ExprError();
9319   ExprResult NewStart = SemaRef.ActOnParenExpr(Loc, Loc, Start.get());
9320   if (!NewStart.isUsable())
9321     return ExprError();
9322   if (Captures && !IsNonRectangularLB)
9323     NewStart = tryBuildCapture(SemaRef, Start.get(), *Captures);
9324   if (NewStart.isInvalid())
9325     return ExprError();
9326 
9327   // First attempt: try to build 'VarRef = Start, VarRef += Iter * Step'.
9328   ExprResult SavedUpdate = Update;
9329   ExprResult UpdateVal;
9330   if (VarRef.get()->getType()->isOverloadableType() ||
9331       NewStart.get()->getType()->isOverloadableType() ||
9332       Update.get()->getType()->isOverloadableType()) {
9333     Sema::TentativeAnalysisScope Trap(SemaRef);
9334 
9335     Update =
9336         SemaRef.BuildBinOp(S, Loc, BO_Assign, VarRef.get(), NewStart.get());
9337     if (Update.isUsable()) {
9338       UpdateVal =
9339           SemaRef.BuildBinOp(S, Loc, Subtract ? BO_SubAssign : BO_AddAssign,
9340                              VarRef.get(), SavedUpdate.get());
9341       if (UpdateVal.isUsable()) {
9342         Update = SemaRef.CreateBuiltinBinOp(Loc, BO_Comma, Update.get(),
9343                                             UpdateVal.get());
9344       }
9345     }
9346   }
9347 
9348   // Second attempt: try to build 'VarRef = Start (+|-) Iter * Step'.
9349   if (!Update.isUsable() || !UpdateVal.isUsable()) {
9350     Update = SemaRef.BuildBinOp(S, Loc, Subtract ? BO_Sub : BO_Add,
9351                                 NewStart.get(), SavedUpdate.get());
9352     if (!Update.isUsable())
9353       return ExprError();
9354 
9355     if (!SemaRef.Context.hasSameType(Update.get()->getType(),
9356                                      VarRef.get()->getType())) {
9357       Update = SemaRef.PerformImplicitConversion(
9358           Update.get(), VarRef.get()->getType(), Sema::AA_Converting, true);
9359       if (!Update.isUsable())
9360         return ExprError();
9361     }
9362 
9363     Update = SemaRef.BuildBinOp(S, Loc, BO_Assign, VarRef.get(), Update.get());
9364   }
9365   return Update;
9366 }
9367 
9368 /// Convert integer expression \a E to make it have at least \a Bits
9369 /// bits.
9370 static ExprResult widenIterationCount(unsigned Bits, Expr *E, Sema &SemaRef) {
9371   if (E == nullptr)
9372     return ExprError();
9373   ASTContext &C = SemaRef.Context;
9374   QualType OldType = E->getType();
9375   unsigned HasBits = C.getTypeSize(OldType);
9376   if (HasBits >= Bits)
9377     return ExprResult(E);
9378   // OK to convert to signed, because new type has more bits than old.
9379   QualType NewType = C.getIntTypeForBitwidth(Bits, /* Signed */ true);
9380   return SemaRef.PerformImplicitConversion(E, NewType, Sema::AA_Converting,
9381                                            true);
9382 }
9383 
9384 /// Check if the given expression \a E is a constant integer that fits
9385 /// into \a Bits bits.
9386 static bool fitsInto(unsigned Bits, bool Signed, const Expr *E, Sema &SemaRef) {
9387   if (E == nullptr)
9388     return false;
9389   if (Optional<llvm::APSInt> Result =
9390           E->getIntegerConstantExpr(SemaRef.Context))
9391     return Signed ? Result->isSignedIntN(Bits) : Result->isIntN(Bits);
9392   return false;
9393 }
9394 
9395 /// Build preinits statement for the given declarations.
9396 static Stmt *buildPreInits(ASTContext &Context,
9397                            MutableArrayRef<Decl *> PreInits) {
9398   if (!PreInits.empty()) {
9399     return new (Context) DeclStmt(
9400         DeclGroupRef::Create(Context, PreInits.begin(), PreInits.size()),
9401         SourceLocation(), SourceLocation());
9402   }
9403   return nullptr;
9404 }
9405 
9406 /// Build preinits statement for the given declarations.
9407 static Stmt *
9408 buildPreInits(ASTContext &Context,
9409               const llvm::MapVector<const Expr *, DeclRefExpr *> &Captures) {
9410   if (!Captures.empty()) {
9411     SmallVector<Decl *, 16> PreInits;
9412     for (const auto &Pair : Captures)
9413       PreInits.push_back(Pair.second->getDecl());
9414     return buildPreInits(Context, PreInits);
9415   }
9416   return nullptr;
9417 }
9418 
9419 /// Build postupdate expression for the given list of postupdates expressions.
9420 static Expr *buildPostUpdate(Sema &S, ArrayRef<Expr *> PostUpdates) {
9421   Expr *PostUpdate = nullptr;
9422   if (!PostUpdates.empty()) {
9423     for (Expr *E : PostUpdates) {
9424       Expr *ConvE = S.BuildCStyleCastExpr(
9425                          E->getExprLoc(),
9426                          S.Context.getTrivialTypeSourceInfo(S.Context.VoidTy),
9427                          E->getExprLoc(), E)
9428                         .get();
9429       PostUpdate = PostUpdate
9430                        ? S.CreateBuiltinBinOp(ConvE->getExprLoc(), BO_Comma,
9431                                               PostUpdate, ConvE)
9432                              .get()
9433                        : ConvE;
9434     }
9435   }
9436   return PostUpdate;
9437 }
9438 
9439 /// Called on a for stmt to check itself and nested loops (if any).
9440 /// \return Returns 0 if one of the collapsed stmts is not canonical for loop,
9441 /// number of collapsed loops otherwise.
9442 static unsigned
9443 checkOpenMPLoop(OpenMPDirectiveKind DKind, Expr *CollapseLoopCountExpr,
9444                 Expr *OrderedLoopCountExpr, Stmt *AStmt, Sema &SemaRef,
9445                 DSAStackTy &DSA,
9446                 Sema::VarsWithInheritedDSAType &VarsWithImplicitDSA,
9447                 OMPLoopBasedDirective::HelperExprs &Built) {
9448   unsigned NestedLoopCount = 1;
9449   bool SupportsNonPerfectlyNested = (SemaRef.LangOpts.OpenMP >= 50) &&
9450                                     !isOpenMPLoopTransformationDirective(DKind);
9451 
9452   if (CollapseLoopCountExpr) {
9453     // Found 'collapse' clause - calculate collapse number.
9454     Expr::EvalResult Result;
9455     if (!CollapseLoopCountExpr->isValueDependent() &&
9456         CollapseLoopCountExpr->EvaluateAsInt(Result, SemaRef.getASTContext())) {
9457       NestedLoopCount = Result.Val.getInt().getLimitedValue();
9458     } else {
9459       Built.clear(/*Size=*/1);
9460       return 1;
9461     }
9462   }
9463   unsigned OrderedLoopCount = 1;
9464   if (OrderedLoopCountExpr) {
9465     // Found 'ordered' clause - calculate collapse number.
9466     Expr::EvalResult EVResult;
9467     if (!OrderedLoopCountExpr->isValueDependent() &&
9468         OrderedLoopCountExpr->EvaluateAsInt(EVResult,
9469                                             SemaRef.getASTContext())) {
9470       llvm::APSInt Result = EVResult.Val.getInt();
9471       if (Result.getLimitedValue() < NestedLoopCount) {
9472         SemaRef.Diag(OrderedLoopCountExpr->getExprLoc(),
9473                      diag::err_omp_wrong_ordered_loop_count)
9474             << OrderedLoopCountExpr->getSourceRange();
9475         SemaRef.Diag(CollapseLoopCountExpr->getExprLoc(),
9476                      diag::note_collapse_loop_count)
9477             << CollapseLoopCountExpr->getSourceRange();
9478       }
9479       OrderedLoopCount = Result.getLimitedValue();
9480     } else {
9481       Built.clear(/*Size=*/1);
9482       return 1;
9483     }
9484   }
9485   // This is helper routine for loop directives (e.g., 'for', 'simd',
9486   // 'for simd', etc.).
9487   llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
9488   unsigned NumLoops = std::max(OrderedLoopCount, NestedLoopCount);
9489   SmallVector<LoopIterationSpace, 4> IterSpaces(NumLoops);
9490   if (!OMPLoopBasedDirective::doForAllLoops(
9491           AStmt->IgnoreContainers(!isOpenMPLoopTransformationDirective(DKind)),
9492           SupportsNonPerfectlyNested, NumLoops,
9493           [DKind, &SemaRef, &DSA, NumLoops, NestedLoopCount,
9494            CollapseLoopCountExpr, OrderedLoopCountExpr, &VarsWithImplicitDSA,
9495            &IterSpaces, &Captures](unsigned Cnt, Stmt *CurStmt) {
9496             if (checkOpenMPIterationSpace(
9497                     DKind, CurStmt, SemaRef, DSA, Cnt, NestedLoopCount,
9498                     NumLoops, CollapseLoopCountExpr, OrderedLoopCountExpr,
9499                     VarsWithImplicitDSA, IterSpaces, Captures))
9500               return true;
9501             if (Cnt > 0 && Cnt >= NestedLoopCount &&
9502                 IterSpaces[Cnt].CounterVar) {
9503               // Handle initialization of captured loop iterator variables.
9504               auto *DRE = cast<DeclRefExpr>(IterSpaces[Cnt].CounterVar);
9505               if (isa<OMPCapturedExprDecl>(DRE->getDecl())) {
9506                 Captures[DRE] = DRE;
9507               }
9508             }
9509             return false;
9510           },
9511           [&SemaRef, &Captures](OMPLoopTransformationDirective *Transform) {
9512             Stmt *DependentPreInits = Transform->getPreInits();
9513             if (!DependentPreInits)
9514               return;
9515             for (Decl *C : cast<DeclStmt>(DependentPreInits)->getDeclGroup()) {
9516               auto *D = cast<VarDecl>(C);
9517               DeclRefExpr *Ref = buildDeclRefExpr(SemaRef, D, D->getType(),
9518                                                   Transform->getBeginLoc());
9519               Captures[Ref] = Ref;
9520             }
9521           }))
9522     return 0;
9523 
9524   Built.clear(/* size */ NestedLoopCount);
9525 
9526   if (SemaRef.CurContext->isDependentContext())
9527     return NestedLoopCount;
9528 
9529   // An example of what is generated for the following code:
9530   //
9531   //   #pragma omp simd collapse(2) ordered(2)
9532   //   for (i = 0; i < NI; ++i)
9533   //     for (k = 0; k < NK; ++k)
9534   //       for (j = J0; j < NJ; j+=2) {
9535   //         <loop body>
9536   //       }
9537   //
9538   // We generate the code below.
9539   // Note: the loop body may be outlined in CodeGen.
9540   // Note: some counters may be C++ classes, operator- is used to find number of
9541   // iterations and operator+= to calculate counter value.
9542   // Note: decltype(NumIterations) must be integer type (in 'omp for', only i32
9543   // or i64 is currently supported).
9544   //
9545   //   #define NumIterations (NI * ((NJ - J0 - 1 + 2) / 2))
9546   //   for (int[32|64]_t IV = 0; IV < NumIterations; ++IV ) {
9547   //     .local.i = IV / ((NJ - J0 - 1 + 2) / 2);
9548   //     .local.j = J0 + (IV % ((NJ - J0 - 1 + 2) / 2)) * 2;
9549   //     // similar updates for vars in clauses (e.g. 'linear')
9550   //     <loop body (using local i and j)>
9551   //   }
9552   //   i = NI; // assign final values of counters
9553   //   j = NJ;
9554   //
9555 
9556   // Last iteration number is (I1 * I2 * ... In) - 1, where I1, I2 ... In are
9557   // the iteration counts of the collapsed for loops.
9558   // Precondition tests if there is at least one iteration (all conditions are
9559   // true).
9560   auto PreCond = ExprResult(IterSpaces[0].PreCond);
9561   Expr *N0 = IterSpaces[0].NumIterations;
9562   ExprResult LastIteration32 =
9563       widenIterationCount(/*Bits=*/32,
9564                           SemaRef
9565                               .PerformImplicitConversion(
9566                                   N0->IgnoreImpCasts(), N0->getType(),
9567                                   Sema::AA_Converting, /*AllowExplicit=*/true)
9568                               .get(),
9569                           SemaRef);
9570   ExprResult LastIteration64 = widenIterationCount(
9571       /*Bits=*/64,
9572       SemaRef
9573           .PerformImplicitConversion(N0->IgnoreImpCasts(), N0->getType(),
9574                                      Sema::AA_Converting,
9575                                      /*AllowExplicit=*/true)
9576           .get(),
9577       SemaRef);
9578 
9579   if (!LastIteration32.isUsable() || !LastIteration64.isUsable())
9580     return NestedLoopCount;
9581 
9582   ASTContext &C = SemaRef.Context;
9583   bool AllCountsNeedLessThan32Bits = C.getTypeSize(N0->getType()) < 32;
9584 
9585   Scope *CurScope = DSA.getCurScope();
9586   for (unsigned Cnt = 1; Cnt < NestedLoopCount; ++Cnt) {
9587     if (PreCond.isUsable()) {
9588       PreCond =
9589           SemaRef.BuildBinOp(CurScope, PreCond.get()->getExprLoc(), BO_LAnd,
9590                              PreCond.get(), IterSpaces[Cnt].PreCond);
9591     }
9592     Expr *N = IterSpaces[Cnt].NumIterations;
9593     SourceLocation Loc = N->getExprLoc();
9594     AllCountsNeedLessThan32Bits &= C.getTypeSize(N->getType()) < 32;
9595     if (LastIteration32.isUsable())
9596       LastIteration32 = SemaRef.BuildBinOp(
9597           CurScope, Loc, BO_Mul, LastIteration32.get(),
9598           SemaRef
9599               .PerformImplicitConversion(N->IgnoreImpCasts(), N->getType(),
9600                                          Sema::AA_Converting,
9601                                          /*AllowExplicit=*/true)
9602               .get());
9603     if (LastIteration64.isUsable())
9604       LastIteration64 = SemaRef.BuildBinOp(
9605           CurScope, Loc, BO_Mul, LastIteration64.get(),
9606           SemaRef
9607               .PerformImplicitConversion(N->IgnoreImpCasts(), N->getType(),
9608                                          Sema::AA_Converting,
9609                                          /*AllowExplicit=*/true)
9610               .get());
9611   }
9612 
9613   // Choose either the 32-bit or 64-bit version.
9614   ExprResult LastIteration = LastIteration64;
9615   if (SemaRef.getLangOpts().OpenMPOptimisticCollapse ||
9616       (LastIteration32.isUsable() &&
9617        C.getTypeSize(LastIteration32.get()->getType()) == 32 &&
9618        (AllCountsNeedLessThan32Bits || NestedLoopCount == 1 ||
9619         fitsInto(
9620             /*Bits=*/32,
9621             LastIteration32.get()->getType()->hasSignedIntegerRepresentation(),
9622             LastIteration64.get(), SemaRef))))
9623     LastIteration = LastIteration32;
9624   QualType VType = LastIteration.get()->getType();
9625   QualType RealVType = VType;
9626   QualType StrideVType = VType;
9627   if (isOpenMPTaskLoopDirective(DKind)) {
9628     VType =
9629         SemaRef.Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/0);
9630     StrideVType =
9631         SemaRef.Context.getIntTypeForBitwidth(/*DestWidth=*/64, /*Signed=*/1);
9632   }
9633 
9634   if (!LastIteration.isUsable())
9635     return 0;
9636 
9637   // Save the number of iterations.
9638   ExprResult NumIterations = LastIteration;
9639   {
9640     LastIteration = SemaRef.BuildBinOp(
9641         CurScope, LastIteration.get()->getExprLoc(), BO_Sub,
9642         LastIteration.get(),
9643         SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get());
9644     if (!LastIteration.isUsable())
9645       return 0;
9646   }
9647 
9648   // Calculate the last iteration number beforehand instead of doing this on
9649   // each iteration. Do not do this if the number of iterations may be kfold-ed.
9650   bool IsConstant = LastIteration.get()->isIntegerConstantExpr(SemaRef.Context);
9651   ExprResult CalcLastIteration;
9652   if (!IsConstant) {
9653     ExprResult SaveRef =
9654         tryBuildCapture(SemaRef, LastIteration.get(), Captures);
9655     LastIteration = SaveRef;
9656 
9657     // Prepare SaveRef + 1.
9658     NumIterations = SemaRef.BuildBinOp(
9659         CurScope, SaveRef.get()->getExprLoc(), BO_Add, SaveRef.get(),
9660         SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get());
9661     if (!NumIterations.isUsable())
9662       return 0;
9663   }
9664 
9665   SourceLocation InitLoc = IterSpaces[0].InitSrcRange.getBegin();
9666 
9667   // Build variables passed into runtime, necessary for worksharing directives.
9668   ExprResult LB, UB, IL, ST, EUB, CombLB, CombUB, PrevLB, PrevUB, CombEUB;
9669   if (isOpenMPWorksharingDirective(DKind) || isOpenMPTaskLoopDirective(DKind) ||
9670       isOpenMPDistributeDirective(DKind) ||
9671       isOpenMPGenericLoopDirective(DKind) ||
9672       isOpenMPLoopTransformationDirective(DKind)) {
9673     // Lower bound variable, initialized with zero.
9674     VarDecl *LBDecl = buildVarDecl(SemaRef, InitLoc, VType, ".omp.lb");
9675     LB = buildDeclRefExpr(SemaRef, LBDecl, VType, InitLoc);
9676     SemaRef.AddInitializerToDecl(LBDecl,
9677                                  SemaRef.ActOnIntegerConstant(InitLoc, 0).get(),
9678                                  /*DirectInit*/ false);
9679 
9680     // Upper bound variable, initialized with last iteration number.
9681     VarDecl *UBDecl = buildVarDecl(SemaRef, InitLoc, VType, ".omp.ub");
9682     UB = buildDeclRefExpr(SemaRef, UBDecl, VType, InitLoc);
9683     SemaRef.AddInitializerToDecl(UBDecl, LastIteration.get(),
9684                                  /*DirectInit*/ false);
9685 
9686     // A 32-bit variable-flag where runtime returns 1 for the last iteration.
9687     // This will be used to implement clause 'lastprivate'.
9688     QualType Int32Ty = SemaRef.Context.getIntTypeForBitwidth(32, true);
9689     VarDecl *ILDecl = buildVarDecl(SemaRef, InitLoc, Int32Ty, ".omp.is_last");
9690     IL = buildDeclRefExpr(SemaRef, ILDecl, Int32Ty, InitLoc);
9691     SemaRef.AddInitializerToDecl(ILDecl,
9692                                  SemaRef.ActOnIntegerConstant(InitLoc, 0).get(),
9693                                  /*DirectInit*/ false);
9694 
9695     // Stride variable returned by runtime (we initialize it to 1 by default).
9696     VarDecl *STDecl =
9697         buildVarDecl(SemaRef, InitLoc, StrideVType, ".omp.stride");
9698     ST = buildDeclRefExpr(SemaRef, STDecl, StrideVType, InitLoc);
9699     SemaRef.AddInitializerToDecl(STDecl,
9700                                  SemaRef.ActOnIntegerConstant(InitLoc, 1).get(),
9701                                  /*DirectInit*/ false);
9702 
9703     // Build expression: UB = min(UB, LastIteration)
9704     // It is necessary for CodeGen of directives with static scheduling.
9705     ExprResult IsUBGreater = SemaRef.BuildBinOp(CurScope, InitLoc, BO_GT,
9706                                                 UB.get(), LastIteration.get());
9707     ExprResult CondOp = SemaRef.ActOnConditionalOp(
9708         LastIteration.get()->getExprLoc(), InitLoc, IsUBGreater.get(),
9709         LastIteration.get(), UB.get());
9710     EUB = SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, UB.get(),
9711                              CondOp.get());
9712     EUB = SemaRef.ActOnFinishFullExpr(EUB.get(), /*DiscardedValue*/ false);
9713 
9714     // If we have a combined directive that combines 'distribute', 'for' or
9715     // 'simd' we need to be able to access the bounds of the schedule of the
9716     // enclosing region. E.g. in 'distribute parallel for' the bounds obtained
9717     // by scheduling 'distribute' have to be passed to the schedule of 'for'.
9718     if (isOpenMPLoopBoundSharingDirective(DKind)) {
9719       // Lower bound variable, initialized with zero.
9720       VarDecl *CombLBDecl =
9721           buildVarDecl(SemaRef, InitLoc, VType, ".omp.comb.lb");
9722       CombLB = buildDeclRefExpr(SemaRef, CombLBDecl, VType, InitLoc);
9723       SemaRef.AddInitializerToDecl(
9724           CombLBDecl, SemaRef.ActOnIntegerConstant(InitLoc, 0).get(),
9725           /*DirectInit*/ false);
9726 
9727       // Upper bound variable, initialized with last iteration number.
9728       VarDecl *CombUBDecl =
9729           buildVarDecl(SemaRef, InitLoc, VType, ".omp.comb.ub");
9730       CombUB = buildDeclRefExpr(SemaRef, CombUBDecl, VType, InitLoc);
9731       SemaRef.AddInitializerToDecl(CombUBDecl, LastIteration.get(),
9732                                    /*DirectInit*/ false);
9733 
9734       ExprResult CombIsUBGreater = SemaRef.BuildBinOp(
9735           CurScope, InitLoc, BO_GT, CombUB.get(), LastIteration.get());
9736       ExprResult CombCondOp =
9737           SemaRef.ActOnConditionalOp(InitLoc, InitLoc, CombIsUBGreater.get(),
9738                                      LastIteration.get(), CombUB.get());
9739       CombEUB = SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, CombUB.get(),
9740                                    CombCondOp.get());
9741       CombEUB =
9742           SemaRef.ActOnFinishFullExpr(CombEUB.get(), /*DiscardedValue*/ false);
9743 
9744       const CapturedDecl *CD = cast<CapturedStmt>(AStmt)->getCapturedDecl();
9745       // We expect to have at least 2 more parameters than the 'parallel'
9746       // directive does - the lower and upper bounds of the previous schedule.
9747       assert(CD->getNumParams() >= 4 &&
9748              "Unexpected number of parameters in loop combined directive");
9749 
9750       // Set the proper type for the bounds given what we learned from the
9751       // enclosed loops.
9752       ImplicitParamDecl *PrevLBDecl = CD->getParam(/*PrevLB=*/2);
9753       ImplicitParamDecl *PrevUBDecl = CD->getParam(/*PrevUB=*/3);
9754 
9755       // Previous lower and upper bounds are obtained from the region
9756       // parameters.
9757       PrevLB =
9758           buildDeclRefExpr(SemaRef, PrevLBDecl, PrevLBDecl->getType(), InitLoc);
9759       PrevUB =
9760           buildDeclRefExpr(SemaRef, PrevUBDecl, PrevUBDecl->getType(), InitLoc);
9761     }
9762   }
9763 
9764   // Build the iteration variable and its initialization before loop.
9765   ExprResult IV;
9766   ExprResult Init, CombInit;
9767   {
9768     VarDecl *IVDecl = buildVarDecl(SemaRef, InitLoc, RealVType, ".omp.iv");
9769     IV = buildDeclRefExpr(SemaRef, IVDecl, RealVType, InitLoc);
9770     Expr *RHS = (isOpenMPWorksharingDirective(DKind) ||
9771                  isOpenMPGenericLoopDirective(DKind) ||
9772                  isOpenMPTaskLoopDirective(DKind) ||
9773                  isOpenMPDistributeDirective(DKind) ||
9774                  isOpenMPLoopTransformationDirective(DKind))
9775                     ? LB.get()
9776                     : SemaRef.ActOnIntegerConstant(SourceLocation(), 0).get();
9777     Init = SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, IV.get(), RHS);
9778     Init = SemaRef.ActOnFinishFullExpr(Init.get(), /*DiscardedValue*/ false);
9779 
9780     if (isOpenMPLoopBoundSharingDirective(DKind)) {
9781       Expr *CombRHS =
9782           (isOpenMPWorksharingDirective(DKind) ||
9783            isOpenMPGenericLoopDirective(DKind) ||
9784            isOpenMPTaskLoopDirective(DKind) ||
9785            isOpenMPDistributeDirective(DKind))
9786               ? CombLB.get()
9787               : SemaRef.ActOnIntegerConstant(SourceLocation(), 0).get();
9788       CombInit =
9789           SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, IV.get(), CombRHS);
9790       CombInit =
9791           SemaRef.ActOnFinishFullExpr(CombInit.get(), /*DiscardedValue*/ false);
9792     }
9793   }
9794 
9795   bool UseStrictCompare =
9796       RealVType->hasUnsignedIntegerRepresentation() &&
9797       llvm::all_of(IterSpaces, [](const LoopIterationSpace &LIS) {
9798         return LIS.IsStrictCompare;
9799       });
9800   // Loop condition (IV < NumIterations) or (IV <= UB or IV < UB + 1 (for
9801   // unsigned IV)) for worksharing loops.
9802   SourceLocation CondLoc = AStmt->getBeginLoc();
9803   Expr *BoundUB = UB.get();
9804   if (UseStrictCompare) {
9805     BoundUB =
9806         SemaRef
9807             .BuildBinOp(CurScope, CondLoc, BO_Add, BoundUB,
9808                         SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get())
9809             .get();
9810     BoundUB =
9811         SemaRef.ActOnFinishFullExpr(BoundUB, /*DiscardedValue*/ false).get();
9812   }
9813   ExprResult Cond =
9814       (isOpenMPWorksharingDirective(DKind) ||
9815        isOpenMPGenericLoopDirective(DKind) ||
9816        isOpenMPTaskLoopDirective(DKind) || isOpenMPDistributeDirective(DKind) ||
9817        isOpenMPLoopTransformationDirective(DKind))
9818           ? SemaRef.BuildBinOp(CurScope, CondLoc,
9819                                UseStrictCompare ? BO_LT : BO_LE, IV.get(),
9820                                BoundUB)
9821           : SemaRef.BuildBinOp(CurScope, CondLoc, BO_LT, IV.get(),
9822                                NumIterations.get());
9823   ExprResult CombDistCond;
9824   if (isOpenMPLoopBoundSharingDirective(DKind)) {
9825     CombDistCond = SemaRef.BuildBinOp(CurScope, CondLoc, BO_LT, IV.get(),
9826                                       NumIterations.get());
9827   }
9828 
9829   ExprResult CombCond;
9830   if (isOpenMPLoopBoundSharingDirective(DKind)) {
9831     Expr *BoundCombUB = CombUB.get();
9832     if (UseStrictCompare) {
9833       BoundCombUB =
9834           SemaRef
9835               .BuildBinOp(
9836                   CurScope, CondLoc, BO_Add, BoundCombUB,
9837                   SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get())
9838               .get();
9839       BoundCombUB =
9840           SemaRef.ActOnFinishFullExpr(BoundCombUB, /*DiscardedValue*/ false)
9841               .get();
9842     }
9843     CombCond =
9844         SemaRef.BuildBinOp(CurScope, CondLoc, UseStrictCompare ? BO_LT : BO_LE,
9845                            IV.get(), BoundCombUB);
9846   }
9847   // Loop increment (IV = IV + 1)
9848   SourceLocation IncLoc = AStmt->getBeginLoc();
9849   ExprResult Inc =
9850       SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, IV.get(),
9851                          SemaRef.ActOnIntegerConstant(IncLoc, 1).get());
9852   if (!Inc.isUsable())
9853     return 0;
9854   Inc = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, IV.get(), Inc.get());
9855   Inc = SemaRef.ActOnFinishFullExpr(Inc.get(), /*DiscardedValue*/ false);
9856   if (!Inc.isUsable())
9857     return 0;
9858 
9859   // Increments for worksharing loops (LB = LB + ST; UB = UB + ST).
9860   // Used for directives with static scheduling.
9861   // In combined construct, add combined version that use CombLB and CombUB
9862   // base variables for the update
9863   ExprResult NextLB, NextUB, CombNextLB, CombNextUB;
9864   if (isOpenMPWorksharingDirective(DKind) || isOpenMPTaskLoopDirective(DKind) ||
9865       isOpenMPGenericLoopDirective(DKind) ||
9866       isOpenMPDistributeDirective(DKind) ||
9867       isOpenMPLoopTransformationDirective(DKind)) {
9868     // LB + ST
9869     NextLB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, LB.get(), ST.get());
9870     if (!NextLB.isUsable())
9871       return 0;
9872     // LB = LB + ST
9873     NextLB =
9874         SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, LB.get(), NextLB.get());
9875     NextLB =
9876         SemaRef.ActOnFinishFullExpr(NextLB.get(), /*DiscardedValue*/ false);
9877     if (!NextLB.isUsable())
9878       return 0;
9879     // UB + ST
9880     NextUB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, UB.get(), ST.get());
9881     if (!NextUB.isUsable())
9882       return 0;
9883     // UB = UB + ST
9884     NextUB =
9885         SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, UB.get(), NextUB.get());
9886     NextUB =
9887         SemaRef.ActOnFinishFullExpr(NextUB.get(), /*DiscardedValue*/ false);
9888     if (!NextUB.isUsable())
9889       return 0;
9890     if (isOpenMPLoopBoundSharingDirective(DKind)) {
9891       CombNextLB =
9892           SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, CombLB.get(), ST.get());
9893       if (!NextLB.isUsable())
9894         return 0;
9895       // LB = LB + ST
9896       CombNextLB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, CombLB.get(),
9897                                       CombNextLB.get());
9898       CombNextLB = SemaRef.ActOnFinishFullExpr(CombNextLB.get(),
9899                                                /*DiscardedValue*/ false);
9900       if (!CombNextLB.isUsable())
9901         return 0;
9902       // UB + ST
9903       CombNextUB =
9904           SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, CombUB.get(), ST.get());
9905       if (!CombNextUB.isUsable())
9906         return 0;
9907       // UB = UB + ST
9908       CombNextUB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, CombUB.get(),
9909                                       CombNextUB.get());
9910       CombNextUB = SemaRef.ActOnFinishFullExpr(CombNextUB.get(),
9911                                                /*DiscardedValue*/ false);
9912       if (!CombNextUB.isUsable())
9913         return 0;
9914     }
9915   }
9916 
9917   // Create increment expression for distribute loop when combined in a same
9918   // directive with for as IV = IV + ST; ensure upper bound expression based
9919   // on PrevUB instead of NumIterations - used to implement 'for' when found
9920   // in combination with 'distribute', like in 'distribute parallel for'
9921   SourceLocation DistIncLoc = AStmt->getBeginLoc();
9922   ExprResult DistCond, DistInc, PrevEUB, ParForInDistCond;
9923   if (isOpenMPLoopBoundSharingDirective(DKind)) {
9924     DistCond = SemaRef.BuildBinOp(
9925         CurScope, CondLoc, UseStrictCompare ? BO_LT : BO_LE, IV.get(), BoundUB);
9926     assert(DistCond.isUsable() && "distribute cond expr was not built");
9927 
9928     DistInc =
9929         SemaRef.BuildBinOp(CurScope, DistIncLoc, BO_Add, IV.get(), ST.get());
9930     assert(DistInc.isUsable() && "distribute inc expr was not built");
9931     DistInc = SemaRef.BuildBinOp(CurScope, DistIncLoc, BO_Assign, IV.get(),
9932                                  DistInc.get());
9933     DistInc =
9934         SemaRef.ActOnFinishFullExpr(DistInc.get(), /*DiscardedValue*/ false);
9935     assert(DistInc.isUsable() && "distribute inc expr was not built");
9936 
9937     // Build expression: UB = min(UB, prevUB) for #for in composite or combined
9938     // construct
9939     ExprResult NewPrevUB = PrevUB;
9940     SourceLocation DistEUBLoc = AStmt->getBeginLoc();
9941     if (!SemaRef.Context.hasSameType(UB.get()->getType(),
9942                                      PrevUB.get()->getType())) {
9943       NewPrevUB = SemaRef.BuildCStyleCastExpr(
9944           DistEUBLoc,
9945           SemaRef.Context.getTrivialTypeSourceInfo(UB.get()->getType()),
9946           DistEUBLoc, NewPrevUB.get());
9947       if (!NewPrevUB.isUsable())
9948         return 0;
9949     }
9950     ExprResult IsUBGreater = SemaRef.BuildBinOp(CurScope, DistEUBLoc, BO_GT,
9951                                                 UB.get(), NewPrevUB.get());
9952     ExprResult CondOp = SemaRef.ActOnConditionalOp(
9953         DistEUBLoc, DistEUBLoc, IsUBGreater.get(), NewPrevUB.get(), UB.get());
9954     PrevEUB = SemaRef.BuildBinOp(CurScope, DistIncLoc, BO_Assign, UB.get(),
9955                                  CondOp.get());
9956     PrevEUB =
9957         SemaRef.ActOnFinishFullExpr(PrevEUB.get(), /*DiscardedValue*/ false);
9958 
9959     // Build IV <= PrevUB or IV < PrevUB + 1 for unsigned IV to be used in
9960     // parallel for is in combination with a distribute directive with
9961     // schedule(static, 1)
9962     Expr *BoundPrevUB = PrevUB.get();
9963     if (UseStrictCompare) {
9964       BoundPrevUB =
9965           SemaRef
9966               .BuildBinOp(
9967                   CurScope, CondLoc, BO_Add, BoundPrevUB,
9968                   SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get())
9969               .get();
9970       BoundPrevUB =
9971           SemaRef.ActOnFinishFullExpr(BoundPrevUB, /*DiscardedValue*/ false)
9972               .get();
9973     }
9974     ParForInDistCond =
9975         SemaRef.BuildBinOp(CurScope, CondLoc, UseStrictCompare ? BO_LT : BO_LE,
9976                            IV.get(), BoundPrevUB);
9977   }
9978 
9979   // Build updates and final values of the loop counters.
9980   bool HasErrors = false;
9981   Built.Counters.resize(NestedLoopCount);
9982   Built.Inits.resize(NestedLoopCount);
9983   Built.Updates.resize(NestedLoopCount);
9984   Built.Finals.resize(NestedLoopCount);
9985   Built.DependentCounters.resize(NestedLoopCount);
9986   Built.DependentInits.resize(NestedLoopCount);
9987   Built.FinalsConditions.resize(NestedLoopCount);
9988   {
9989     // We implement the following algorithm for obtaining the
9990     // original loop iteration variable values based on the
9991     // value of the collapsed loop iteration variable IV.
9992     //
9993     // Let n+1 be the number of collapsed loops in the nest.
9994     // Iteration variables (I0, I1, .... In)
9995     // Iteration counts (N0, N1, ... Nn)
9996     //
9997     // Acc = IV;
9998     //
9999     // To compute Ik for loop k, 0 <= k <= n, generate:
10000     //    Prod = N(k+1) * N(k+2) * ... * Nn;
10001     //    Ik = Acc / Prod;
10002     //    Acc -= Ik * Prod;
10003     //
10004     ExprResult Acc = IV;
10005     for (unsigned int Cnt = 0; Cnt < NestedLoopCount; ++Cnt) {
10006       LoopIterationSpace &IS = IterSpaces[Cnt];
10007       SourceLocation UpdLoc = IS.IncSrcRange.getBegin();
10008       ExprResult Iter;
10009 
10010       // Compute prod
10011       ExprResult Prod = SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get();
10012       for (unsigned int K = Cnt + 1; K < NestedLoopCount; ++K)
10013         Prod = SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Mul, Prod.get(),
10014                                   IterSpaces[K].NumIterations);
10015 
10016       // Iter = Acc / Prod
10017       // If there is at least one more inner loop to avoid
10018       // multiplication by 1.
10019       if (Cnt + 1 < NestedLoopCount)
10020         Iter =
10021             SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Div, Acc.get(), Prod.get());
10022       else
10023         Iter = Acc;
10024       if (!Iter.isUsable()) {
10025         HasErrors = true;
10026         break;
10027       }
10028 
10029       // Update Acc:
10030       // Acc -= Iter * Prod
10031       // Check if there is at least one more inner loop to avoid
10032       // multiplication by 1.
10033       if (Cnt + 1 < NestedLoopCount)
10034         Prod = SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Mul, Iter.get(),
10035                                   Prod.get());
10036       else
10037         Prod = Iter;
10038       Acc = SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Sub, Acc.get(), Prod.get());
10039 
10040       // Build update: IS.CounterVar(Private) = IS.Start + Iter * IS.Step
10041       auto *VD = cast<VarDecl>(cast<DeclRefExpr>(IS.CounterVar)->getDecl());
10042       DeclRefExpr *CounterVar = buildDeclRefExpr(
10043           SemaRef, VD, IS.CounterVar->getType(), IS.CounterVar->getExprLoc(),
10044           /*RefersToCapture=*/true);
10045       ExprResult Init =
10046           buildCounterInit(SemaRef, CurScope, UpdLoc, CounterVar,
10047                            IS.CounterInit, IS.IsNonRectangularLB, Captures);
10048       if (!Init.isUsable()) {
10049         HasErrors = true;
10050         break;
10051       }
10052       ExprResult Update = buildCounterUpdate(
10053           SemaRef, CurScope, UpdLoc, CounterVar, IS.CounterInit, Iter,
10054           IS.CounterStep, IS.Subtract, IS.IsNonRectangularLB, &Captures);
10055       if (!Update.isUsable()) {
10056         HasErrors = true;
10057         break;
10058       }
10059 
10060       // Build final: IS.CounterVar = IS.Start + IS.NumIters * IS.Step
10061       ExprResult Final =
10062           buildCounterUpdate(SemaRef, CurScope, UpdLoc, CounterVar,
10063                              IS.CounterInit, IS.NumIterations, IS.CounterStep,
10064                              IS.Subtract, IS.IsNonRectangularLB, &Captures);
10065       if (!Final.isUsable()) {
10066         HasErrors = true;
10067         break;
10068       }
10069 
10070       if (!Update.isUsable() || !Final.isUsable()) {
10071         HasErrors = true;
10072         break;
10073       }
10074       // Save results
10075       Built.Counters[Cnt] = IS.CounterVar;
10076       Built.PrivateCounters[Cnt] = IS.PrivateCounterVar;
10077       Built.Inits[Cnt] = Init.get();
10078       Built.Updates[Cnt] = Update.get();
10079       Built.Finals[Cnt] = Final.get();
10080       Built.DependentCounters[Cnt] = nullptr;
10081       Built.DependentInits[Cnt] = nullptr;
10082       Built.FinalsConditions[Cnt] = nullptr;
10083       if (IS.IsNonRectangularLB || IS.IsNonRectangularUB) {
10084         Built.DependentCounters[Cnt] =
10085             Built.Counters[NestedLoopCount - 1 - IS.LoopDependentIdx];
10086         Built.DependentInits[Cnt] =
10087             Built.Inits[NestedLoopCount - 1 - IS.LoopDependentIdx];
10088         Built.FinalsConditions[Cnt] = IS.FinalCondition;
10089       }
10090     }
10091   }
10092 
10093   if (HasErrors)
10094     return 0;
10095 
10096   // Save results
10097   Built.IterationVarRef = IV.get();
10098   Built.LastIteration = LastIteration.get();
10099   Built.NumIterations = NumIterations.get();
10100   Built.CalcLastIteration = SemaRef
10101                                 .ActOnFinishFullExpr(CalcLastIteration.get(),
10102                                                      /*DiscardedValue=*/false)
10103                                 .get();
10104   Built.PreCond = PreCond.get();
10105   Built.PreInits = buildPreInits(C, Captures);
10106   Built.Cond = Cond.get();
10107   Built.Init = Init.get();
10108   Built.Inc = Inc.get();
10109   Built.LB = LB.get();
10110   Built.UB = UB.get();
10111   Built.IL = IL.get();
10112   Built.ST = ST.get();
10113   Built.EUB = EUB.get();
10114   Built.NLB = NextLB.get();
10115   Built.NUB = NextUB.get();
10116   Built.PrevLB = PrevLB.get();
10117   Built.PrevUB = PrevUB.get();
10118   Built.DistInc = DistInc.get();
10119   Built.PrevEUB = PrevEUB.get();
10120   Built.DistCombinedFields.LB = CombLB.get();
10121   Built.DistCombinedFields.UB = CombUB.get();
10122   Built.DistCombinedFields.EUB = CombEUB.get();
10123   Built.DistCombinedFields.Init = CombInit.get();
10124   Built.DistCombinedFields.Cond = CombCond.get();
10125   Built.DistCombinedFields.NLB = CombNextLB.get();
10126   Built.DistCombinedFields.NUB = CombNextUB.get();
10127   Built.DistCombinedFields.DistCond = CombDistCond.get();
10128   Built.DistCombinedFields.ParForInDistCond = ParForInDistCond.get();
10129 
10130   return NestedLoopCount;
10131 }
10132 
10133 static Expr *getCollapseNumberExpr(ArrayRef<OMPClause *> Clauses) {
10134   auto CollapseClauses =
10135       OMPExecutableDirective::getClausesOfKind<OMPCollapseClause>(Clauses);
10136   if (CollapseClauses.begin() != CollapseClauses.end())
10137     return (*CollapseClauses.begin())->getNumForLoops();
10138   return nullptr;
10139 }
10140 
10141 static Expr *getOrderedNumberExpr(ArrayRef<OMPClause *> Clauses) {
10142   auto OrderedClauses =
10143       OMPExecutableDirective::getClausesOfKind<OMPOrderedClause>(Clauses);
10144   if (OrderedClauses.begin() != OrderedClauses.end())
10145     return (*OrderedClauses.begin())->getNumForLoops();
10146   return nullptr;
10147 }
10148 
10149 static bool checkSimdlenSafelenSpecified(Sema &S,
10150                                          const ArrayRef<OMPClause *> Clauses) {
10151   const OMPSafelenClause *Safelen = nullptr;
10152   const OMPSimdlenClause *Simdlen = nullptr;
10153 
10154   for (const OMPClause *Clause : Clauses) {
10155     if (Clause->getClauseKind() == OMPC_safelen)
10156       Safelen = cast<OMPSafelenClause>(Clause);
10157     else if (Clause->getClauseKind() == OMPC_simdlen)
10158       Simdlen = cast<OMPSimdlenClause>(Clause);
10159     if (Safelen && Simdlen)
10160       break;
10161   }
10162 
10163   if (Simdlen && Safelen) {
10164     const Expr *SimdlenLength = Simdlen->getSimdlen();
10165     const Expr *SafelenLength = Safelen->getSafelen();
10166     if (SimdlenLength->isValueDependent() || SimdlenLength->isTypeDependent() ||
10167         SimdlenLength->isInstantiationDependent() ||
10168         SimdlenLength->containsUnexpandedParameterPack())
10169       return false;
10170     if (SafelenLength->isValueDependent() || SafelenLength->isTypeDependent() ||
10171         SafelenLength->isInstantiationDependent() ||
10172         SafelenLength->containsUnexpandedParameterPack())
10173       return false;
10174     Expr::EvalResult SimdlenResult, SafelenResult;
10175     SimdlenLength->EvaluateAsInt(SimdlenResult, S.Context);
10176     SafelenLength->EvaluateAsInt(SafelenResult, S.Context);
10177     llvm::APSInt SimdlenRes = SimdlenResult.Val.getInt();
10178     llvm::APSInt SafelenRes = SafelenResult.Val.getInt();
10179     // OpenMP 4.5 [2.8.1, simd Construct, Restrictions]
10180     // If both simdlen and safelen clauses are specified, the value of the
10181     // simdlen parameter must be less than or equal to the value of the safelen
10182     // parameter.
10183     if (SimdlenRes > SafelenRes) {
10184       S.Diag(SimdlenLength->getExprLoc(),
10185              diag::err_omp_wrong_simdlen_safelen_values)
10186           << SimdlenLength->getSourceRange() << SafelenLength->getSourceRange();
10187       return true;
10188     }
10189   }
10190   return false;
10191 }
10192 
10193 StmtResult
10194 Sema::ActOnOpenMPSimdDirective(ArrayRef<OMPClause *> Clauses, Stmt *AStmt,
10195                                SourceLocation StartLoc, SourceLocation EndLoc,
10196                                VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10197   if (!AStmt)
10198     return StmtError();
10199 
10200   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10201   OMPLoopBasedDirective::HelperExprs B;
10202   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
10203   // define the nested loops number.
10204   unsigned NestedLoopCount = checkOpenMPLoop(
10205       OMPD_simd, getCollapseNumberExpr(Clauses), getOrderedNumberExpr(Clauses),
10206       AStmt, *this, *DSAStack, VarsWithImplicitDSA, B);
10207   if (NestedLoopCount == 0)
10208     return StmtError();
10209 
10210   assert((CurContext->isDependentContext() || B.builtAll()) &&
10211          "omp simd loop exprs were not built");
10212 
10213   if (!CurContext->isDependentContext()) {
10214     // Finalize the clauses that need pre-built expressions for CodeGen.
10215     for (OMPClause *C : Clauses) {
10216       if (auto *LC = dyn_cast<OMPLinearClause>(C))
10217         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
10218                                      B.NumIterations, *this, CurScope,
10219                                      DSAStack))
10220           return StmtError();
10221     }
10222   }
10223 
10224   if (checkSimdlenSafelenSpecified(*this, Clauses))
10225     return StmtError();
10226 
10227   setFunctionHasBranchProtectedScope();
10228   return OMPSimdDirective::Create(Context, StartLoc, EndLoc, NestedLoopCount,
10229                                   Clauses, AStmt, B);
10230 }
10231 
10232 StmtResult
10233 Sema::ActOnOpenMPForDirective(ArrayRef<OMPClause *> Clauses, Stmt *AStmt,
10234                               SourceLocation StartLoc, SourceLocation EndLoc,
10235                               VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10236   if (!AStmt)
10237     return StmtError();
10238 
10239   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10240   OMPLoopBasedDirective::HelperExprs B;
10241   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
10242   // define the nested loops number.
10243   unsigned NestedLoopCount = checkOpenMPLoop(
10244       OMPD_for, getCollapseNumberExpr(Clauses), getOrderedNumberExpr(Clauses),
10245       AStmt, *this, *DSAStack, VarsWithImplicitDSA, B);
10246   if (NestedLoopCount == 0)
10247     return StmtError();
10248 
10249   assert((CurContext->isDependentContext() || B.builtAll()) &&
10250          "omp for loop exprs were not built");
10251 
10252   if (!CurContext->isDependentContext()) {
10253     // Finalize the clauses that need pre-built expressions for CodeGen.
10254     for (OMPClause *C : Clauses) {
10255       if (auto *LC = dyn_cast<OMPLinearClause>(C))
10256         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
10257                                      B.NumIterations, *this, CurScope,
10258                                      DSAStack))
10259           return StmtError();
10260     }
10261   }
10262 
10263   setFunctionHasBranchProtectedScope();
10264   return OMPForDirective::Create(
10265       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
10266       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
10267 }
10268 
10269 StmtResult Sema::ActOnOpenMPForSimdDirective(
10270     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10271     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10272   if (!AStmt)
10273     return StmtError();
10274 
10275   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10276   OMPLoopBasedDirective::HelperExprs B;
10277   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
10278   // define the nested loops number.
10279   unsigned NestedLoopCount =
10280       checkOpenMPLoop(OMPD_for_simd, getCollapseNumberExpr(Clauses),
10281                       getOrderedNumberExpr(Clauses), AStmt, *this, *DSAStack,
10282                       VarsWithImplicitDSA, B);
10283   if (NestedLoopCount == 0)
10284     return StmtError();
10285 
10286   assert((CurContext->isDependentContext() || B.builtAll()) &&
10287          "omp for simd loop exprs were not built");
10288 
10289   if (!CurContext->isDependentContext()) {
10290     // Finalize the clauses that need pre-built expressions for CodeGen.
10291     for (OMPClause *C : Clauses) {
10292       if (auto *LC = dyn_cast<OMPLinearClause>(C))
10293         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
10294                                      B.NumIterations, *this, CurScope,
10295                                      DSAStack))
10296           return StmtError();
10297     }
10298   }
10299 
10300   if (checkSimdlenSafelenSpecified(*this, Clauses))
10301     return StmtError();
10302 
10303   setFunctionHasBranchProtectedScope();
10304   return OMPForSimdDirective::Create(Context, StartLoc, EndLoc, NestedLoopCount,
10305                                      Clauses, AStmt, B);
10306 }
10307 
10308 StmtResult Sema::ActOnOpenMPSectionsDirective(ArrayRef<OMPClause *> Clauses,
10309                                               Stmt *AStmt,
10310                                               SourceLocation StartLoc,
10311                                               SourceLocation EndLoc) {
10312   if (!AStmt)
10313     return StmtError();
10314 
10315   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10316   auto BaseStmt = AStmt;
10317   while (auto *CS = dyn_cast_or_null<CapturedStmt>(BaseStmt))
10318     BaseStmt = CS->getCapturedStmt();
10319   if (auto *C = dyn_cast_or_null<CompoundStmt>(BaseStmt)) {
10320     auto S = C->children();
10321     if (S.begin() == S.end())
10322       return StmtError();
10323     // All associated statements must be '#pragma omp section' except for
10324     // the first one.
10325     for (Stmt *SectionStmt : llvm::drop_begin(S)) {
10326       if (!SectionStmt || !isa<OMPSectionDirective>(SectionStmt)) {
10327         if (SectionStmt)
10328           Diag(SectionStmt->getBeginLoc(),
10329                diag::err_omp_sections_substmt_not_section);
10330         return StmtError();
10331       }
10332       cast<OMPSectionDirective>(SectionStmt)
10333           ->setHasCancel(DSAStack->isCancelRegion());
10334     }
10335   } else {
10336     Diag(AStmt->getBeginLoc(), diag::err_omp_sections_not_compound_stmt);
10337     return StmtError();
10338   }
10339 
10340   setFunctionHasBranchProtectedScope();
10341 
10342   return OMPSectionsDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
10343                                       DSAStack->getTaskgroupReductionRef(),
10344                                       DSAStack->isCancelRegion());
10345 }
10346 
10347 StmtResult Sema::ActOnOpenMPSectionDirective(Stmt *AStmt,
10348                                              SourceLocation StartLoc,
10349                                              SourceLocation EndLoc) {
10350   if (!AStmt)
10351     return StmtError();
10352 
10353   setFunctionHasBranchProtectedScope();
10354   DSAStack->setParentCancelRegion(DSAStack->isCancelRegion());
10355 
10356   return OMPSectionDirective::Create(Context, StartLoc, EndLoc, AStmt,
10357                                      DSAStack->isCancelRegion());
10358 }
10359 
10360 static Expr *getDirectCallExpr(Expr *E) {
10361   E = E->IgnoreParenCasts()->IgnoreImplicit();
10362   if (auto *CE = dyn_cast<CallExpr>(E))
10363     if (CE->getDirectCallee())
10364       return E;
10365   return nullptr;
10366 }
10367 
10368 StmtResult Sema::ActOnOpenMPDispatchDirective(ArrayRef<OMPClause *> Clauses,
10369                                               Stmt *AStmt,
10370                                               SourceLocation StartLoc,
10371                                               SourceLocation EndLoc) {
10372   if (!AStmt)
10373     return StmtError();
10374 
10375   Stmt *S = cast<CapturedStmt>(AStmt)->getCapturedStmt();
10376 
10377   // 5.1 OpenMP
10378   // expression-stmt : an expression statement with one of the following forms:
10379   //   expression = target-call ( [expression-list] );
10380   //   target-call ( [expression-list] );
10381 
10382   SourceLocation TargetCallLoc;
10383 
10384   if (!CurContext->isDependentContext()) {
10385     Expr *TargetCall = nullptr;
10386 
10387     auto *E = dyn_cast<Expr>(S);
10388     if (!E) {
10389       Diag(S->getBeginLoc(), diag::err_omp_dispatch_statement_call);
10390       return StmtError();
10391     }
10392 
10393     E = E->IgnoreParenCasts()->IgnoreImplicit();
10394 
10395     if (auto *BO = dyn_cast<BinaryOperator>(E)) {
10396       if (BO->getOpcode() == BO_Assign)
10397         TargetCall = getDirectCallExpr(BO->getRHS());
10398     } else {
10399       if (auto *COCE = dyn_cast<CXXOperatorCallExpr>(E))
10400         if (COCE->getOperator() == OO_Equal)
10401           TargetCall = getDirectCallExpr(COCE->getArg(1));
10402       if (!TargetCall)
10403         TargetCall = getDirectCallExpr(E);
10404     }
10405     if (!TargetCall) {
10406       Diag(E->getBeginLoc(), diag::err_omp_dispatch_statement_call);
10407       return StmtError();
10408     }
10409     TargetCallLoc = TargetCall->getExprLoc();
10410   }
10411 
10412   setFunctionHasBranchProtectedScope();
10413 
10414   return OMPDispatchDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
10415                                       TargetCallLoc);
10416 }
10417 
10418 static bool checkGenericLoopLastprivate(Sema &S, ArrayRef<OMPClause *> Clauses,
10419                                         OpenMPDirectiveKind K,
10420                                         DSAStackTy *Stack) {
10421   bool ErrorFound = false;
10422   for (OMPClause *C : Clauses) {
10423     if (auto *LPC = dyn_cast<OMPLastprivateClause>(C)) {
10424       for (Expr *RefExpr : LPC->varlists()) {
10425         SourceLocation ELoc;
10426         SourceRange ERange;
10427         Expr *SimpleRefExpr = RefExpr;
10428         auto Res = getPrivateItem(S, SimpleRefExpr, ELoc, ERange);
10429         if (ValueDecl *D = Res.first) {
10430           auto &&Info = Stack->isLoopControlVariable(D);
10431           if (!Info.first) {
10432             S.Diag(ELoc, diag::err_omp_lastprivate_loop_var_non_loop_iteration)
10433                 << getOpenMPDirectiveName(K);
10434             ErrorFound = true;
10435           }
10436         }
10437       }
10438     }
10439   }
10440   return ErrorFound;
10441 }
10442 
10443 StmtResult Sema::ActOnOpenMPGenericLoopDirective(
10444     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10445     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10446   if (!AStmt)
10447     return StmtError();
10448 
10449   // OpenMP 5.1 [2.11.7, loop construct, Restrictions]
10450   // A list item may not appear in a lastprivate clause unless it is the
10451   // loop iteration variable of a loop that is associated with the construct.
10452   if (checkGenericLoopLastprivate(*this, Clauses, OMPD_loop, DSAStack))
10453     return StmtError();
10454 
10455   auto *CS = cast<CapturedStmt>(AStmt);
10456   // 1.2.2 OpenMP Language Terminology
10457   // Structured block - An executable statement with a single entry at the
10458   // top and a single exit at the bottom.
10459   // The point of exit cannot be a branch out of the structured block.
10460   // longjmp() and throw() must not violate the entry/exit criteria.
10461   CS->getCapturedDecl()->setNothrow();
10462 
10463   OMPLoopDirective::HelperExprs B;
10464   // In presence of clause 'collapse', it will define the nested loops number.
10465   unsigned NestedLoopCount = checkOpenMPLoop(
10466       OMPD_loop, getCollapseNumberExpr(Clauses), getOrderedNumberExpr(Clauses),
10467       AStmt, *this, *DSAStack, VarsWithImplicitDSA, B);
10468   if (NestedLoopCount == 0)
10469     return StmtError();
10470 
10471   assert((CurContext->isDependentContext() || B.builtAll()) &&
10472          "omp loop exprs were not built");
10473 
10474   setFunctionHasBranchProtectedScope();
10475   return OMPGenericLoopDirective::Create(Context, StartLoc, EndLoc,
10476                                          NestedLoopCount, Clauses, AStmt, B);
10477 }
10478 
10479 StmtResult Sema::ActOnOpenMPTeamsGenericLoopDirective(
10480     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10481     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10482   if (!AStmt)
10483     return StmtError();
10484 
10485   // OpenMP 5.1 [2.11.7, loop construct, Restrictions]
10486   // A list item may not appear in a lastprivate clause unless it is the
10487   // loop iteration variable of a loop that is associated with the construct.
10488   if (checkGenericLoopLastprivate(*this, Clauses, OMPD_teams_loop, DSAStack))
10489     return StmtError();
10490 
10491   auto *CS = cast<CapturedStmt>(AStmt);
10492   // 1.2.2 OpenMP Language Terminology
10493   // Structured block - An executable statement with a single entry at the
10494   // top and a single exit at the bottom.
10495   // The point of exit cannot be a branch out of the structured block.
10496   // longjmp() and throw() must not violate the entry/exit criteria.
10497   CS->getCapturedDecl()->setNothrow();
10498   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_teams_loop);
10499        ThisCaptureLevel > 1; --ThisCaptureLevel) {
10500     CS = cast<CapturedStmt>(CS->getCapturedStmt());
10501     // 1.2.2 OpenMP Language Terminology
10502     // Structured block - An executable statement with a single entry at the
10503     // top and a single exit at the bottom.
10504     // The point of exit cannot be a branch out of the structured block.
10505     // longjmp() and throw() must not violate the entry/exit criteria.
10506     CS->getCapturedDecl()->setNothrow();
10507   }
10508 
10509   OMPLoopDirective::HelperExprs B;
10510   // In presence of clause 'collapse', it will define the nested loops number.
10511   unsigned NestedLoopCount =
10512       checkOpenMPLoop(OMPD_teams_loop, getCollapseNumberExpr(Clauses),
10513                       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
10514                       VarsWithImplicitDSA, B);
10515   if (NestedLoopCount == 0)
10516     return StmtError();
10517 
10518   assert((CurContext->isDependentContext() || B.builtAll()) &&
10519          "omp loop exprs were not built");
10520 
10521   setFunctionHasBranchProtectedScope();
10522   DSAStack->setParentTeamsRegionLoc(StartLoc);
10523 
10524   return OMPTeamsGenericLoopDirective::Create(
10525       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
10526 }
10527 
10528 StmtResult Sema::ActOnOpenMPTargetTeamsGenericLoopDirective(
10529     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10530     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10531   if (!AStmt)
10532     return StmtError();
10533 
10534   // OpenMP 5.1 [2.11.7, loop construct, Restrictions]
10535   // A list item may not appear in a lastprivate clause unless it is the
10536   // loop iteration variable of a loop that is associated with the construct.
10537   if (checkGenericLoopLastprivate(*this, Clauses, OMPD_target_teams_loop,
10538                                   DSAStack))
10539     return StmtError();
10540 
10541   auto *CS = cast<CapturedStmt>(AStmt);
10542   // 1.2.2 OpenMP Language Terminology
10543   // Structured block - An executable statement with a single entry at the
10544   // top and a single exit at the bottom.
10545   // The point of exit cannot be a branch out of the structured block.
10546   // longjmp() and throw() must not violate the entry/exit criteria.
10547   CS->getCapturedDecl()->setNothrow();
10548   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_teams_loop);
10549        ThisCaptureLevel > 1; --ThisCaptureLevel) {
10550     CS = cast<CapturedStmt>(CS->getCapturedStmt());
10551     // 1.2.2 OpenMP Language Terminology
10552     // Structured block - An executable statement with a single entry at the
10553     // top and a single exit at the bottom.
10554     // The point of exit cannot be a branch out of the structured block.
10555     // longjmp() and throw() must not violate the entry/exit criteria.
10556     CS->getCapturedDecl()->setNothrow();
10557   }
10558 
10559   OMPLoopDirective::HelperExprs B;
10560   // In presence of clause 'collapse', it will define the nested loops number.
10561   unsigned NestedLoopCount =
10562       checkOpenMPLoop(OMPD_target_teams_loop, getCollapseNumberExpr(Clauses),
10563                       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
10564                       VarsWithImplicitDSA, B);
10565   if (NestedLoopCount == 0)
10566     return StmtError();
10567 
10568   assert((CurContext->isDependentContext() || B.builtAll()) &&
10569          "omp loop exprs were not built");
10570 
10571   setFunctionHasBranchProtectedScope();
10572 
10573   return OMPTargetTeamsGenericLoopDirective::Create(
10574       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
10575 }
10576 
10577 StmtResult Sema::ActOnOpenMPParallelGenericLoopDirective(
10578     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10579     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10580   if (!AStmt)
10581     return StmtError();
10582 
10583   // OpenMP 5.1 [2.11.7, loop construct, Restrictions]
10584   // A list item may not appear in a lastprivate clause unless it is the
10585   // loop iteration variable of a loop that is associated with the construct.
10586   if (checkGenericLoopLastprivate(*this, Clauses, OMPD_parallel_loop, DSAStack))
10587     return StmtError();
10588 
10589   auto *CS = cast<CapturedStmt>(AStmt);
10590   // 1.2.2 OpenMP Language Terminology
10591   // Structured block - An executable statement with a single entry at the
10592   // top and a single exit at the bottom.
10593   // The point of exit cannot be a branch out of the structured block.
10594   // longjmp() and throw() must not violate the entry/exit criteria.
10595   CS->getCapturedDecl()->setNothrow();
10596   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_parallel_loop);
10597        ThisCaptureLevel > 1; --ThisCaptureLevel) {
10598     CS = cast<CapturedStmt>(CS->getCapturedStmt());
10599     // 1.2.2 OpenMP Language Terminology
10600     // Structured block - An executable statement with a single entry at the
10601     // top and a single exit at the bottom.
10602     // The point of exit cannot be a branch out of the structured block.
10603     // longjmp() and throw() must not violate the entry/exit criteria.
10604     CS->getCapturedDecl()->setNothrow();
10605   }
10606 
10607   OMPLoopDirective::HelperExprs B;
10608   // In presence of clause 'collapse', it will define the nested loops number.
10609   unsigned NestedLoopCount =
10610       checkOpenMPLoop(OMPD_parallel_loop, getCollapseNumberExpr(Clauses),
10611                       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
10612                       VarsWithImplicitDSA, B);
10613   if (NestedLoopCount == 0)
10614     return StmtError();
10615 
10616   assert((CurContext->isDependentContext() || B.builtAll()) &&
10617          "omp loop exprs were not built");
10618 
10619   setFunctionHasBranchProtectedScope();
10620 
10621   return OMPParallelGenericLoopDirective::Create(
10622       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
10623 }
10624 
10625 StmtResult Sema::ActOnOpenMPTargetParallelGenericLoopDirective(
10626     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10627     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10628   if (!AStmt)
10629     return StmtError();
10630 
10631   // OpenMP 5.1 [2.11.7, loop construct, Restrictions]
10632   // A list item may not appear in a lastprivate clause unless it is the
10633   // loop iteration variable of a loop that is associated with the construct.
10634   if (checkGenericLoopLastprivate(*this, Clauses, OMPD_target_parallel_loop,
10635                                   DSAStack))
10636     return StmtError();
10637 
10638   auto *CS = cast<CapturedStmt>(AStmt);
10639   // 1.2.2 OpenMP Language Terminology
10640   // Structured block - An executable statement with a single entry at the
10641   // top and a single exit at the bottom.
10642   // The point of exit cannot be a branch out of the structured block.
10643   // longjmp() and throw() must not violate the entry/exit criteria.
10644   CS->getCapturedDecl()->setNothrow();
10645   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_parallel_loop);
10646        ThisCaptureLevel > 1; --ThisCaptureLevel) {
10647     CS = cast<CapturedStmt>(CS->getCapturedStmt());
10648     // 1.2.2 OpenMP Language Terminology
10649     // Structured block - An executable statement with a single entry at the
10650     // top and a single exit at the bottom.
10651     // The point of exit cannot be a branch out of the structured block.
10652     // longjmp() and throw() must not violate the entry/exit criteria.
10653     CS->getCapturedDecl()->setNothrow();
10654   }
10655 
10656   OMPLoopDirective::HelperExprs B;
10657   // In presence of clause 'collapse', it will define the nested loops number.
10658   unsigned NestedLoopCount =
10659       checkOpenMPLoop(OMPD_target_parallel_loop, getCollapseNumberExpr(Clauses),
10660                       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
10661                       VarsWithImplicitDSA, B);
10662   if (NestedLoopCount == 0)
10663     return StmtError();
10664 
10665   assert((CurContext->isDependentContext() || B.builtAll()) &&
10666          "omp loop exprs were not built");
10667 
10668   setFunctionHasBranchProtectedScope();
10669 
10670   return OMPTargetParallelGenericLoopDirective::Create(
10671       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
10672 }
10673 
10674 StmtResult Sema::ActOnOpenMPSingleDirective(ArrayRef<OMPClause *> Clauses,
10675                                             Stmt *AStmt,
10676                                             SourceLocation StartLoc,
10677                                             SourceLocation EndLoc) {
10678   if (!AStmt)
10679     return StmtError();
10680 
10681   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10682 
10683   setFunctionHasBranchProtectedScope();
10684 
10685   // OpenMP [2.7.3, single Construct, Restrictions]
10686   // The copyprivate clause must not be used with the nowait clause.
10687   const OMPClause *Nowait = nullptr;
10688   const OMPClause *Copyprivate = nullptr;
10689   for (const OMPClause *Clause : Clauses) {
10690     if (Clause->getClauseKind() == OMPC_nowait)
10691       Nowait = Clause;
10692     else if (Clause->getClauseKind() == OMPC_copyprivate)
10693       Copyprivate = Clause;
10694     if (Copyprivate && Nowait) {
10695       Diag(Copyprivate->getBeginLoc(),
10696            diag::err_omp_single_copyprivate_with_nowait);
10697       Diag(Nowait->getBeginLoc(), diag::note_omp_nowait_clause_here);
10698       return StmtError();
10699     }
10700   }
10701 
10702   return OMPSingleDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt);
10703 }
10704 
10705 StmtResult Sema::ActOnOpenMPMasterDirective(Stmt *AStmt,
10706                                             SourceLocation StartLoc,
10707                                             SourceLocation EndLoc) {
10708   if (!AStmt)
10709     return StmtError();
10710 
10711   setFunctionHasBranchProtectedScope();
10712 
10713   return OMPMasterDirective::Create(Context, StartLoc, EndLoc, AStmt);
10714 }
10715 
10716 StmtResult Sema::ActOnOpenMPMaskedDirective(ArrayRef<OMPClause *> Clauses,
10717                                             Stmt *AStmt,
10718                                             SourceLocation StartLoc,
10719                                             SourceLocation EndLoc) {
10720   if (!AStmt)
10721     return StmtError();
10722 
10723   setFunctionHasBranchProtectedScope();
10724 
10725   return OMPMaskedDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt);
10726 }
10727 
10728 StmtResult Sema::ActOnOpenMPCriticalDirective(
10729     const DeclarationNameInfo &DirName, ArrayRef<OMPClause *> Clauses,
10730     Stmt *AStmt, SourceLocation StartLoc, SourceLocation EndLoc) {
10731   if (!AStmt)
10732     return StmtError();
10733 
10734   bool ErrorFound = false;
10735   llvm::APSInt Hint;
10736   SourceLocation HintLoc;
10737   bool DependentHint = false;
10738   for (const OMPClause *C : Clauses) {
10739     if (C->getClauseKind() == OMPC_hint) {
10740       if (!DirName.getName()) {
10741         Diag(C->getBeginLoc(), diag::err_omp_hint_clause_no_name);
10742         ErrorFound = true;
10743       }
10744       Expr *E = cast<OMPHintClause>(C)->getHint();
10745       if (E->isTypeDependent() || E->isValueDependent() ||
10746           E->isInstantiationDependent()) {
10747         DependentHint = true;
10748       } else {
10749         Hint = E->EvaluateKnownConstInt(Context);
10750         HintLoc = C->getBeginLoc();
10751       }
10752     }
10753   }
10754   if (ErrorFound)
10755     return StmtError();
10756   const auto Pair = DSAStack->getCriticalWithHint(DirName);
10757   if (Pair.first && DirName.getName() && !DependentHint) {
10758     if (llvm::APSInt::compareValues(Hint, Pair.second) != 0) {
10759       Diag(StartLoc, diag::err_omp_critical_with_hint);
10760       if (HintLoc.isValid())
10761         Diag(HintLoc, diag::note_omp_critical_hint_here)
10762             << 0 << toString(Hint, /*Radix=*/10, /*Signed=*/false);
10763       else
10764         Diag(StartLoc, diag::note_omp_critical_no_hint) << 0;
10765       if (const auto *C = Pair.first->getSingleClause<OMPHintClause>()) {
10766         Diag(C->getBeginLoc(), diag::note_omp_critical_hint_here)
10767             << 1
10768             << toString(C->getHint()->EvaluateKnownConstInt(Context),
10769                         /*Radix=*/10, /*Signed=*/false);
10770       } else {
10771         Diag(Pair.first->getBeginLoc(), diag::note_omp_critical_no_hint) << 1;
10772       }
10773     }
10774   }
10775 
10776   setFunctionHasBranchProtectedScope();
10777 
10778   auto *Dir = OMPCriticalDirective::Create(Context, DirName, StartLoc, EndLoc,
10779                                            Clauses, AStmt);
10780   if (!Pair.first && DirName.getName() && !DependentHint)
10781     DSAStack->addCriticalWithHint(Dir, Hint);
10782   return Dir;
10783 }
10784 
10785 StmtResult Sema::ActOnOpenMPParallelForDirective(
10786     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10787     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10788   if (!AStmt)
10789     return StmtError();
10790 
10791   auto *CS = cast<CapturedStmt>(AStmt);
10792   // 1.2.2 OpenMP Language Terminology
10793   // Structured block - An executable statement with a single entry at the
10794   // top and a single exit at the bottom.
10795   // The point of exit cannot be a branch out of the structured block.
10796   // longjmp() and throw() must not violate the entry/exit criteria.
10797   CS->getCapturedDecl()->setNothrow();
10798 
10799   OMPLoopBasedDirective::HelperExprs B;
10800   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
10801   // define the nested loops number.
10802   unsigned NestedLoopCount =
10803       checkOpenMPLoop(OMPD_parallel_for, getCollapseNumberExpr(Clauses),
10804                       getOrderedNumberExpr(Clauses), AStmt, *this, *DSAStack,
10805                       VarsWithImplicitDSA, B);
10806   if (NestedLoopCount == 0)
10807     return StmtError();
10808 
10809   assert((CurContext->isDependentContext() || B.builtAll()) &&
10810          "omp parallel for loop exprs were not built");
10811 
10812   if (!CurContext->isDependentContext()) {
10813     // Finalize the clauses that need pre-built expressions for CodeGen.
10814     for (OMPClause *C : Clauses) {
10815       if (auto *LC = dyn_cast<OMPLinearClause>(C))
10816         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
10817                                      B.NumIterations, *this, CurScope,
10818                                      DSAStack))
10819           return StmtError();
10820     }
10821   }
10822 
10823   setFunctionHasBranchProtectedScope();
10824   return OMPParallelForDirective::Create(
10825       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
10826       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
10827 }
10828 
10829 StmtResult Sema::ActOnOpenMPParallelForSimdDirective(
10830     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
10831     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
10832   if (!AStmt)
10833     return StmtError();
10834 
10835   auto *CS = cast<CapturedStmt>(AStmt);
10836   // 1.2.2 OpenMP Language Terminology
10837   // Structured block - An executable statement with a single entry at the
10838   // top and a single exit at the bottom.
10839   // The point of exit cannot be a branch out of the structured block.
10840   // longjmp() and throw() must not violate the entry/exit criteria.
10841   CS->getCapturedDecl()->setNothrow();
10842 
10843   OMPLoopBasedDirective::HelperExprs B;
10844   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
10845   // define the nested loops number.
10846   unsigned NestedLoopCount =
10847       checkOpenMPLoop(OMPD_parallel_for_simd, getCollapseNumberExpr(Clauses),
10848                       getOrderedNumberExpr(Clauses), AStmt, *this, *DSAStack,
10849                       VarsWithImplicitDSA, B);
10850   if (NestedLoopCount == 0)
10851     return StmtError();
10852 
10853   if (!CurContext->isDependentContext()) {
10854     // Finalize the clauses that need pre-built expressions for CodeGen.
10855     for (OMPClause *C : Clauses) {
10856       if (auto *LC = dyn_cast<OMPLinearClause>(C))
10857         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
10858                                      B.NumIterations, *this, CurScope,
10859                                      DSAStack))
10860           return StmtError();
10861     }
10862   }
10863 
10864   if (checkSimdlenSafelenSpecified(*this, Clauses))
10865     return StmtError();
10866 
10867   setFunctionHasBranchProtectedScope();
10868   return OMPParallelForSimdDirective::Create(
10869       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
10870 }
10871 
10872 StmtResult
10873 Sema::ActOnOpenMPParallelMasterDirective(ArrayRef<OMPClause *> Clauses,
10874                                          Stmt *AStmt, SourceLocation StartLoc,
10875                                          SourceLocation EndLoc) {
10876   if (!AStmt)
10877     return StmtError();
10878 
10879   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10880   auto *CS = cast<CapturedStmt>(AStmt);
10881   // 1.2.2 OpenMP Language Terminology
10882   // Structured block - An executable statement with a single entry at the
10883   // top and a single exit at the bottom.
10884   // The point of exit cannot be a branch out of the structured block.
10885   // longjmp() and throw() must not violate the entry/exit criteria.
10886   CS->getCapturedDecl()->setNothrow();
10887 
10888   setFunctionHasBranchProtectedScope();
10889 
10890   return OMPParallelMasterDirective::Create(
10891       Context, StartLoc, EndLoc, Clauses, AStmt,
10892       DSAStack->getTaskgroupReductionRef());
10893 }
10894 
10895 StmtResult
10896 Sema::ActOnOpenMPParallelMaskedDirective(ArrayRef<OMPClause *> Clauses,
10897                                          Stmt *AStmt, SourceLocation StartLoc,
10898                                          SourceLocation EndLoc) {
10899   if (!AStmt)
10900     return StmtError();
10901 
10902   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10903   auto *CS = cast<CapturedStmt>(AStmt);
10904   // 1.2.2 OpenMP Language Terminology
10905   // Structured block - An executable statement with a single entry at the
10906   // top and a single exit at the bottom.
10907   // The point of exit cannot be a branch out of the structured block.
10908   // longjmp() and throw() must not violate the entry/exit criteria.
10909   CS->getCapturedDecl()->setNothrow();
10910 
10911   setFunctionHasBranchProtectedScope();
10912 
10913   return OMPParallelMaskedDirective::Create(
10914       Context, StartLoc, EndLoc, Clauses, AStmt,
10915       DSAStack->getTaskgroupReductionRef());
10916 }
10917 
10918 StmtResult
10919 Sema::ActOnOpenMPParallelSectionsDirective(ArrayRef<OMPClause *> Clauses,
10920                                            Stmt *AStmt, SourceLocation StartLoc,
10921                                            SourceLocation EndLoc) {
10922   if (!AStmt)
10923     return StmtError();
10924 
10925   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
10926   auto BaseStmt = AStmt;
10927   while (auto *CS = dyn_cast_or_null<CapturedStmt>(BaseStmt))
10928     BaseStmt = CS->getCapturedStmt();
10929   if (auto *C = dyn_cast_or_null<CompoundStmt>(BaseStmt)) {
10930     auto S = C->children();
10931     if (S.begin() == S.end())
10932       return StmtError();
10933     // All associated statements must be '#pragma omp section' except for
10934     // the first one.
10935     for (Stmt *SectionStmt : llvm::drop_begin(S)) {
10936       if (!SectionStmt || !isa<OMPSectionDirective>(SectionStmt)) {
10937         if (SectionStmt)
10938           Diag(SectionStmt->getBeginLoc(),
10939                diag::err_omp_parallel_sections_substmt_not_section);
10940         return StmtError();
10941       }
10942       cast<OMPSectionDirective>(SectionStmt)
10943           ->setHasCancel(DSAStack->isCancelRegion());
10944     }
10945   } else {
10946     Diag(AStmt->getBeginLoc(),
10947          diag::err_omp_parallel_sections_not_compound_stmt);
10948     return StmtError();
10949   }
10950 
10951   setFunctionHasBranchProtectedScope();
10952 
10953   return OMPParallelSectionsDirective::Create(
10954       Context, StartLoc, EndLoc, Clauses, AStmt,
10955       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
10956 }
10957 
10958 /// Find and diagnose mutually exclusive clause kinds.
10959 static bool checkMutuallyExclusiveClauses(
10960     Sema &S, ArrayRef<OMPClause *> Clauses,
10961     ArrayRef<OpenMPClauseKind> MutuallyExclusiveClauses) {
10962   const OMPClause *PrevClause = nullptr;
10963   bool ErrorFound = false;
10964   for (const OMPClause *C : Clauses) {
10965     if (llvm::is_contained(MutuallyExclusiveClauses, C->getClauseKind())) {
10966       if (!PrevClause) {
10967         PrevClause = C;
10968       } else if (PrevClause->getClauseKind() != C->getClauseKind()) {
10969         S.Diag(C->getBeginLoc(), diag::err_omp_clauses_mutually_exclusive)
10970             << getOpenMPClauseName(C->getClauseKind())
10971             << getOpenMPClauseName(PrevClause->getClauseKind());
10972         S.Diag(PrevClause->getBeginLoc(), diag::note_omp_previous_clause)
10973             << getOpenMPClauseName(PrevClause->getClauseKind());
10974         ErrorFound = true;
10975       }
10976     }
10977   }
10978   return ErrorFound;
10979 }
10980 
10981 StmtResult Sema::ActOnOpenMPTaskDirective(ArrayRef<OMPClause *> Clauses,
10982                                           Stmt *AStmt, SourceLocation StartLoc,
10983                                           SourceLocation EndLoc) {
10984   if (!AStmt)
10985     return StmtError();
10986 
10987   // OpenMP 5.0, 2.10.1 task Construct
10988   // If a detach clause appears on the directive, then a mergeable clause cannot
10989   // appear on the same directive.
10990   if (checkMutuallyExclusiveClauses(*this, Clauses,
10991                                     {OMPC_detach, OMPC_mergeable}))
10992     return StmtError();
10993 
10994   auto *CS = cast<CapturedStmt>(AStmt);
10995   // 1.2.2 OpenMP Language Terminology
10996   // Structured block - An executable statement with a single entry at the
10997   // top and a single exit at the bottom.
10998   // The point of exit cannot be a branch out of the structured block.
10999   // longjmp() and throw() must not violate the entry/exit criteria.
11000   CS->getCapturedDecl()->setNothrow();
11001 
11002   setFunctionHasBranchProtectedScope();
11003 
11004   return OMPTaskDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
11005                                   DSAStack->isCancelRegion());
11006 }
11007 
11008 StmtResult Sema::ActOnOpenMPTaskyieldDirective(SourceLocation StartLoc,
11009                                                SourceLocation EndLoc) {
11010   return OMPTaskyieldDirective::Create(Context, StartLoc, EndLoc);
11011 }
11012 
11013 StmtResult Sema::ActOnOpenMPBarrierDirective(SourceLocation StartLoc,
11014                                              SourceLocation EndLoc) {
11015   return OMPBarrierDirective::Create(Context, StartLoc, EndLoc);
11016 }
11017 
11018 StmtResult Sema::ActOnOpenMPTaskwaitDirective(ArrayRef<OMPClause *> Clauses,
11019                                               SourceLocation StartLoc,
11020                                               SourceLocation EndLoc) {
11021   return OMPTaskwaitDirective::Create(Context, StartLoc, EndLoc, Clauses);
11022 }
11023 
11024 StmtResult Sema::ActOnOpenMPTaskgroupDirective(ArrayRef<OMPClause *> Clauses,
11025                                                Stmt *AStmt,
11026                                                SourceLocation StartLoc,
11027                                                SourceLocation EndLoc) {
11028   if (!AStmt)
11029     return StmtError();
11030 
11031   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
11032 
11033   setFunctionHasBranchProtectedScope();
11034 
11035   return OMPTaskgroupDirective::Create(Context, StartLoc, EndLoc, Clauses,
11036                                        AStmt,
11037                                        DSAStack->getTaskgroupReductionRef());
11038 }
11039 
11040 StmtResult Sema::ActOnOpenMPFlushDirective(ArrayRef<OMPClause *> Clauses,
11041                                            SourceLocation StartLoc,
11042                                            SourceLocation EndLoc) {
11043   OMPFlushClause *FC = nullptr;
11044   OMPClause *OrderClause = nullptr;
11045   for (OMPClause *C : Clauses) {
11046     if (C->getClauseKind() == OMPC_flush)
11047       FC = cast<OMPFlushClause>(C);
11048     else
11049       OrderClause = C;
11050   }
11051   OpenMPClauseKind MemOrderKind = OMPC_unknown;
11052   SourceLocation MemOrderLoc;
11053   for (const OMPClause *C : Clauses) {
11054     if (C->getClauseKind() == OMPC_acq_rel ||
11055         C->getClauseKind() == OMPC_acquire ||
11056         C->getClauseKind() == OMPC_release) {
11057       if (MemOrderKind != OMPC_unknown) {
11058         Diag(C->getBeginLoc(), diag::err_omp_several_mem_order_clauses)
11059             << getOpenMPDirectiveName(OMPD_flush) << 1
11060             << SourceRange(C->getBeginLoc(), C->getEndLoc());
11061         Diag(MemOrderLoc, diag::note_omp_previous_mem_order_clause)
11062             << getOpenMPClauseName(MemOrderKind);
11063       } else {
11064         MemOrderKind = C->getClauseKind();
11065         MemOrderLoc = C->getBeginLoc();
11066       }
11067     }
11068   }
11069   if (FC && OrderClause) {
11070     Diag(FC->getLParenLoc(), diag::err_omp_flush_order_clause_and_list)
11071         << getOpenMPClauseName(OrderClause->getClauseKind());
11072     Diag(OrderClause->getBeginLoc(), diag::note_omp_flush_order_clause_here)
11073         << getOpenMPClauseName(OrderClause->getClauseKind());
11074     return StmtError();
11075   }
11076   return OMPFlushDirective::Create(Context, StartLoc, EndLoc, Clauses);
11077 }
11078 
11079 StmtResult Sema::ActOnOpenMPDepobjDirective(ArrayRef<OMPClause *> Clauses,
11080                                             SourceLocation StartLoc,
11081                                             SourceLocation EndLoc) {
11082   if (Clauses.empty()) {
11083     Diag(StartLoc, diag::err_omp_depobj_expected);
11084     return StmtError();
11085   } else if (Clauses[0]->getClauseKind() != OMPC_depobj) {
11086     Diag(Clauses[0]->getBeginLoc(), diag::err_omp_depobj_expected);
11087     return StmtError();
11088   }
11089   // Only depobj expression and another single clause is allowed.
11090   if (Clauses.size() > 2) {
11091     Diag(Clauses[2]->getBeginLoc(),
11092          diag::err_omp_depobj_single_clause_expected);
11093     return StmtError();
11094   } else if (Clauses.size() < 1) {
11095     Diag(Clauses[0]->getEndLoc(), diag::err_omp_depobj_single_clause_expected);
11096     return StmtError();
11097   }
11098   return OMPDepobjDirective::Create(Context, StartLoc, EndLoc, Clauses);
11099 }
11100 
11101 StmtResult Sema::ActOnOpenMPScanDirective(ArrayRef<OMPClause *> Clauses,
11102                                           SourceLocation StartLoc,
11103                                           SourceLocation EndLoc) {
11104   // Check that exactly one clause is specified.
11105   if (Clauses.size() != 1) {
11106     Diag(Clauses.empty() ? EndLoc : Clauses[1]->getBeginLoc(),
11107          diag::err_omp_scan_single_clause_expected);
11108     return StmtError();
11109   }
11110   // Check that scan directive is used in the scopeof the OpenMP loop body.
11111   if (Scope *S = DSAStack->getCurScope()) {
11112     Scope *ParentS = S->getParent();
11113     if (!ParentS || ParentS->getParent() != ParentS->getBreakParent() ||
11114         !ParentS->getBreakParent()->isOpenMPLoopScope())
11115       return StmtError(Diag(StartLoc, diag::err_omp_orphaned_device_directive)
11116                        << getOpenMPDirectiveName(OMPD_scan) << 5);
11117   }
11118   // Check that only one instance of scan directives is used in the same outer
11119   // region.
11120   if (DSAStack->doesParentHasScanDirective()) {
11121     Diag(StartLoc, diag::err_omp_several_directives_in_region) << "scan";
11122     Diag(DSAStack->getParentScanDirectiveLoc(),
11123          diag::note_omp_previous_directive)
11124         << "scan";
11125     return StmtError();
11126   }
11127   DSAStack->setParentHasScanDirective(StartLoc);
11128   return OMPScanDirective::Create(Context, StartLoc, EndLoc, Clauses);
11129 }
11130 
11131 StmtResult Sema::ActOnOpenMPOrderedDirective(ArrayRef<OMPClause *> Clauses,
11132                                              Stmt *AStmt,
11133                                              SourceLocation StartLoc,
11134                                              SourceLocation EndLoc) {
11135   const OMPClause *DependFound = nullptr;
11136   const OMPClause *DependSourceClause = nullptr;
11137   const OMPClause *DependSinkClause = nullptr;
11138   bool ErrorFound = false;
11139   const OMPThreadsClause *TC = nullptr;
11140   const OMPSIMDClause *SC = nullptr;
11141   for (const OMPClause *C : Clauses) {
11142     if (auto *DC = dyn_cast<OMPDependClause>(C)) {
11143       DependFound = C;
11144       if (DC->getDependencyKind() == OMPC_DEPEND_source) {
11145         if (DependSourceClause) {
11146           Diag(C->getBeginLoc(), diag::err_omp_more_one_clause)
11147               << getOpenMPDirectiveName(OMPD_ordered)
11148               << getOpenMPClauseName(OMPC_depend) << 2;
11149           ErrorFound = true;
11150         } else {
11151           DependSourceClause = C;
11152         }
11153         if (DependSinkClause) {
11154           Diag(C->getBeginLoc(), diag::err_omp_depend_sink_source_not_allowed)
11155               << 0;
11156           ErrorFound = true;
11157         }
11158       } else if (DC->getDependencyKind() == OMPC_DEPEND_sink) {
11159         if (DependSourceClause) {
11160           Diag(C->getBeginLoc(), diag::err_omp_depend_sink_source_not_allowed)
11161               << 1;
11162           ErrorFound = true;
11163         }
11164         DependSinkClause = C;
11165       }
11166     } else if (C->getClauseKind() == OMPC_threads) {
11167       TC = cast<OMPThreadsClause>(C);
11168     } else if (C->getClauseKind() == OMPC_simd) {
11169       SC = cast<OMPSIMDClause>(C);
11170     }
11171   }
11172   if (!ErrorFound && !SC &&
11173       isOpenMPSimdDirective(DSAStack->getParentDirective())) {
11174     // OpenMP [2.8.1,simd Construct, Restrictions]
11175     // An ordered construct with the simd clause is the only OpenMP construct
11176     // that can appear in the simd region.
11177     Diag(StartLoc, diag::err_omp_prohibited_region_simd)
11178         << (LangOpts.OpenMP >= 50 ? 1 : 0);
11179     ErrorFound = true;
11180   } else if (DependFound && (TC || SC)) {
11181     Diag(DependFound->getBeginLoc(), diag::err_omp_depend_clause_thread_simd)
11182         << getOpenMPClauseName(TC ? TC->getClauseKind() : SC->getClauseKind());
11183     ErrorFound = true;
11184   } else if (DependFound && !DSAStack->getParentOrderedRegionParam().first) {
11185     Diag(DependFound->getBeginLoc(),
11186          diag::err_omp_ordered_directive_without_param);
11187     ErrorFound = true;
11188   } else if (TC || Clauses.empty()) {
11189     if (const Expr *Param = DSAStack->getParentOrderedRegionParam().first) {
11190       SourceLocation ErrLoc = TC ? TC->getBeginLoc() : StartLoc;
11191       Diag(ErrLoc, diag::err_omp_ordered_directive_with_param)
11192           << (TC != nullptr);
11193       Diag(Param->getBeginLoc(), diag::note_omp_ordered_param) << 1;
11194       ErrorFound = true;
11195     }
11196   }
11197   if ((!AStmt && !DependFound) || ErrorFound)
11198     return StmtError();
11199 
11200   // OpenMP 5.0, 2.17.9, ordered Construct, Restrictions.
11201   // During execution of an iteration of a worksharing-loop or a loop nest
11202   // within a worksharing-loop, simd, or worksharing-loop SIMD region, a thread
11203   // must not execute more than one ordered region corresponding to an ordered
11204   // construct without a depend clause.
11205   if (!DependFound) {
11206     if (DSAStack->doesParentHasOrderedDirective()) {
11207       Diag(StartLoc, diag::err_omp_several_directives_in_region) << "ordered";
11208       Diag(DSAStack->getParentOrderedDirectiveLoc(),
11209            diag::note_omp_previous_directive)
11210           << "ordered";
11211       return StmtError();
11212     }
11213     DSAStack->setParentHasOrderedDirective(StartLoc);
11214   }
11215 
11216   if (AStmt) {
11217     assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
11218 
11219     setFunctionHasBranchProtectedScope();
11220   }
11221 
11222   return OMPOrderedDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt);
11223 }
11224 
11225 namespace {
11226 /// Helper class for checking expression in 'omp atomic [update]'
11227 /// construct.
11228 class OpenMPAtomicUpdateChecker {
11229   /// Error results for atomic update expressions.
11230   enum ExprAnalysisErrorCode {
11231     /// A statement is not an expression statement.
11232     NotAnExpression,
11233     /// Expression is not builtin binary or unary operation.
11234     NotABinaryOrUnaryExpression,
11235     /// Unary operation is not post-/pre- increment/decrement operation.
11236     NotAnUnaryIncDecExpression,
11237     /// An expression is not of scalar type.
11238     NotAScalarType,
11239     /// A binary operation is not an assignment operation.
11240     NotAnAssignmentOp,
11241     /// RHS part of the binary operation is not a binary expression.
11242     NotABinaryExpression,
11243     /// RHS part is not additive/multiplicative/shift/biwise binary
11244     /// expression.
11245     NotABinaryOperator,
11246     /// RHS binary operation does not have reference to the updated LHS
11247     /// part.
11248     NotAnUpdateExpression,
11249     /// No errors is found.
11250     NoError
11251   };
11252   /// Reference to Sema.
11253   Sema &SemaRef;
11254   /// A location for note diagnostics (when error is found).
11255   SourceLocation NoteLoc;
11256   /// 'x' lvalue part of the source atomic expression.
11257   Expr *X;
11258   /// 'expr' rvalue part of the source atomic expression.
11259   Expr *E;
11260   /// Helper expression of the form
11261   /// 'OpaqueValueExpr(x) binop OpaqueValueExpr(expr)' or
11262   /// 'OpaqueValueExpr(expr) binop OpaqueValueExpr(x)'.
11263   Expr *UpdateExpr;
11264   /// Is 'x' a LHS in a RHS part of full update expression. It is
11265   /// important for non-associative operations.
11266   bool IsXLHSInRHSPart;
11267   BinaryOperatorKind Op;
11268   SourceLocation OpLoc;
11269   /// true if the source expression is a postfix unary operation, false
11270   /// if it is a prefix unary operation.
11271   bool IsPostfixUpdate;
11272 
11273 public:
11274   OpenMPAtomicUpdateChecker(Sema &SemaRef)
11275       : SemaRef(SemaRef), X(nullptr), E(nullptr), UpdateExpr(nullptr),
11276         IsXLHSInRHSPart(false), Op(BO_PtrMemD), IsPostfixUpdate(false) {}
11277   /// Check specified statement that it is suitable for 'atomic update'
11278   /// constructs and extract 'x', 'expr' and Operation from the original
11279   /// expression. If DiagId and NoteId == 0, then only check is performed
11280   /// without error notification.
11281   /// \param DiagId Diagnostic which should be emitted if error is found.
11282   /// \param NoteId Diagnostic note for the main error message.
11283   /// \return true if statement is not an update expression, false otherwise.
11284   bool checkStatement(Stmt *S, unsigned DiagId = 0, unsigned NoteId = 0);
11285   /// Return the 'x' lvalue part of the source atomic expression.
11286   Expr *getX() const { return X; }
11287   /// Return the 'expr' rvalue part of the source atomic expression.
11288   Expr *getExpr() const { return E; }
11289   /// Return the update expression used in calculation of the updated
11290   /// value. Always has form 'OpaqueValueExpr(x) binop OpaqueValueExpr(expr)' or
11291   /// 'OpaqueValueExpr(expr) binop OpaqueValueExpr(x)'.
11292   Expr *getUpdateExpr() const { return UpdateExpr; }
11293   /// Return true if 'x' is LHS in RHS part of full update expression,
11294   /// false otherwise.
11295   bool isXLHSInRHSPart() const { return IsXLHSInRHSPart; }
11296 
11297   /// true if the source expression is a postfix unary operation, false
11298   /// if it is a prefix unary operation.
11299   bool isPostfixUpdate() const { return IsPostfixUpdate; }
11300 
11301 private:
11302   bool checkBinaryOperation(BinaryOperator *AtomicBinOp, unsigned DiagId = 0,
11303                             unsigned NoteId = 0);
11304 };
11305 
11306 bool OpenMPAtomicUpdateChecker::checkBinaryOperation(
11307     BinaryOperator *AtomicBinOp, unsigned DiagId, unsigned NoteId) {
11308   ExprAnalysisErrorCode ErrorFound = NoError;
11309   SourceLocation ErrorLoc, NoteLoc;
11310   SourceRange ErrorRange, NoteRange;
11311   // Allowed constructs are:
11312   //  x = x binop expr;
11313   //  x = expr binop x;
11314   if (AtomicBinOp->getOpcode() == BO_Assign) {
11315     X = AtomicBinOp->getLHS();
11316     if (const auto *AtomicInnerBinOp = dyn_cast<BinaryOperator>(
11317             AtomicBinOp->getRHS()->IgnoreParenImpCasts())) {
11318       if (AtomicInnerBinOp->isMultiplicativeOp() ||
11319           AtomicInnerBinOp->isAdditiveOp() || AtomicInnerBinOp->isShiftOp() ||
11320           AtomicInnerBinOp->isBitwiseOp()) {
11321         Op = AtomicInnerBinOp->getOpcode();
11322         OpLoc = AtomicInnerBinOp->getOperatorLoc();
11323         Expr *LHS = AtomicInnerBinOp->getLHS();
11324         Expr *RHS = AtomicInnerBinOp->getRHS();
11325         llvm::FoldingSetNodeID XId, LHSId, RHSId;
11326         X->IgnoreParenImpCasts()->Profile(XId, SemaRef.getASTContext(),
11327                                           /*Canonical=*/true);
11328         LHS->IgnoreParenImpCasts()->Profile(LHSId, SemaRef.getASTContext(),
11329                                             /*Canonical=*/true);
11330         RHS->IgnoreParenImpCasts()->Profile(RHSId, SemaRef.getASTContext(),
11331                                             /*Canonical=*/true);
11332         if (XId == LHSId) {
11333           E = RHS;
11334           IsXLHSInRHSPart = true;
11335         } else if (XId == RHSId) {
11336           E = LHS;
11337           IsXLHSInRHSPart = false;
11338         } else {
11339           ErrorLoc = AtomicInnerBinOp->getExprLoc();
11340           ErrorRange = AtomicInnerBinOp->getSourceRange();
11341           NoteLoc = X->getExprLoc();
11342           NoteRange = X->getSourceRange();
11343           ErrorFound = NotAnUpdateExpression;
11344         }
11345       } else {
11346         ErrorLoc = AtomicInnerBinOp->getExprLoc();
11347         ErrorRange = AtomicInnerBinOp->getSourceRange();
11348         NoteLoc = AtomicInnerBinOp->getOperatorLoc();
11349         NoteRange = SourceRange(NoteLoc, NoteLoc);
11350         ErrorFound = NotABinaryOperator;
11351       }
11352     } else {
11353       NoteLoc = ErrorLoc = AtomicBinOp->getRHS()->getExprLoc();
11354       NoteRange = ErrorRange = AtomicBinOp->getRHS()->getSourceRange();
11355       ErrorFound = NotABinaryExpression;
11356     }
11357   } else {
11358     ErrorLoc = AtomicBinOp->getExprLoc();
11359     ErrorRange = AtomicBinOp->getSourceRange();
11360     NoteLoc = AtomicBinOp->getOperatorLoc();
11361     NoteRange = SourceRange(NoteLoc, NoteLoc);
11362     ErrorFound = NotAnAssignmentOp;
11363   }
11364   if (ErrorFound != NoError && DiagId != 0 && NoteId != 0) {
11365     SemaRef.Diag(ErrorLoc, DiagId) << ErrorRange;
11366     SemaRef.Diag(NoteLoc, NoteId) << ErrorFound << NoteRange;
11367     return true;
11368   }
11369   if (SemaRef.CurContext->isDependentContext())
11370     E = X = UpdateExpr = nullptr;
11371   return ErrorFound != NoError;
11372 }
11373 
11374 bool OpenMPAtomicUpdateChecker::checkStatement(Stmt *S, unsigned DiagId,
11375                                                unsigned NoteId) {
11376   ExprAnalysisErrorCode ErrorFound = NoError;
11377   SourceLocation ErrorLoc, NoteLoc;
11378   SourceRange ErrorRange, NoteRange;
11379   // Allowed constructs are:
11380   //  x++;
11381   //  x--;
11382   //  ++x;
11383   //  --x;
11384   //  x binop= expr;
11385   //  x = x binop expr;
11386   //  x = expr binop x;
11387   if (auto *AtomicBody = dyn_cast<Expr>(S)) {
11388     AtomicBody = AtomicBody->IgnoreParenImpCasts();
11389     if (AtomicBody->getType()->isScalarType() ||
11390         AtomicBody->isInstantiationDependent()) {
11391       if (const auto *AtomicCompAssignOp = dyn_cast<CompoundAssignOperator>(
11392               AtomicBody->IgnoreParenImpCasts())) {
11393         // Check for Compound Assignment Operation
11394         Op = BinaryOperator::getOpForCompoundAssignment(
11395             AtomicCompAssignOp->getOpcode());
11396         OpLoc = AtomicCompAssignOp->getOperatorLoc();
11397         E = AtomicCompAssignOp->getRHS();
11398         X = AtomicCompAssignOp->getLHS()->IgnoreParens();
11399         IsXLHSInRHSPart = true;
11400       } else if (auto *AtomicBinOp = dyn_cast<BinaryOperator>(
11401                      AtomicBody->IgnoreParenImpCasts())) {
11402         // Check for Binary Operation
11403         if (checkBinaryOperation(AtomicBinOp, DiagId, NoteId))
11404           return true;
11405       } else if (const auto *AtomicUnaryOp = dyn_cast<UnaryOperator>(
11406                      AtomicBody->IgnoreParenImpCasts())) {
11407         // Check for Unary Operation
11408         if (AtomicUnaryOp->isIncrementDecrementOp()) {
11409           IsPostfixUpdate = AtomicUnaryOp->isPostfix();
11410           Op = AtomicUnaryOp->isIncrementOp() ? BO_Add : BO_Sub;
11411           OpLoc = AtomicUnaryOp->getOperatorLoc();
11412           X = AtomicUnaryOp->getSubExpr()->IgnoreParens();
11413           E = SemaRef.ActOnIntegerConstant(OpLoc, /*uint64_t Val=*/1).get();
11414           IsXLHSInRHSPart = true;
11415         } else {
11416           ErrorFound = NotAnUnaryIncDecExpression;
11417           ErrorLoc = AtomicUnaryOp->getExprLoc();
11418           ErrorRange = AtomicUnaryOp->getSourceRange();
11419           NoteLoc = AtomicUnaryOp->getOperatorLoc();
11420           NoteRange = SourceRange(NoteLoc, NoteLoc);
11421         }
11422       } else if (!AtomicBody->isInstantiationDependent()) {
11423         ErrorFound = NotABinaryOrUnaryExpression;
11424         NoteLoc = ErrorLoc = AtomicBody->getExprLoc();
11425         NoteRange = ErrorRange = AtomicBody->getSourceRange();
11426       }
11427     } else {
11428       ErrorFound = NotAScalarType;
11429       NoteLoc = ErrorLoc = AtomicBody->getBeginLoc();
11430       NoteRange = ErrorRange = SourceRange(NoteLoc, NoteLoc);
11431     }
11432   } else {
11433     ErrorFound = NotAnExpression;
11434     NoteLoc = ErrorLoc = S->getBeginLoc();
11435     NoteRange = ErrorRange = SourceRange(NoteLoc, NoteLoc);
11436   }
11437   if (ErrorFound != NoError && DiagId != 0 && NoteId != 0) {
11438     SemaRef.Diag(ErrorLoc, DiagId) << ErrorRange;
11439     SemaRef.Diag(NoteLoc, NoteId) << ErrorFound << NoteRange;
11440     return true;
11441   }
11442   if (SemaRef.CurContext->isDependentContext())
11443     E = X = UpdateExpr = nullptr;
11444   if (ErrorFound == NoError && E && X) {
11445     // Build an update expression of form 'OpaqueValueExpr(x) binop
11446     // OpaqueValueExpr(expr)' or 'OpaqueValueExpr(expr) binop
11447     // OpaqueValueExpr(x)' and then cast it to the type of the 'x' expression.
11448     auto *OVEX = new (SemaRef.getASTContext())
11449         OpaqueValueExpr(X->getExprLoc(), X->getType(), VK_PRValue);
11450     auto *OVEExpr = new (SemaRef.getASTContext())
11451         OpaqueValueExpr(E->getExprLoc(), E->getType(), VK_PRValue);
11452     ExprResult Update =
11453         SemaRef.CreateBuiltinBinOp(OpLoc, Op, IsXLHSInRHSPart ? OVEX : OVEExpr,
11454                                    IsXLHSInRHSPart ? OVEExpr : OVEX);
11455     if (Update.isInvalid())
11456       return true;
11457     Update = SemaRef.PerformImplicitConversion(Update.get(), X->getType(),
11458                                                Sema::AA_Casting);
11459     if (Update.isInvalid())
11460       return true;
11461     UpdateExpr = Update.get();
11462   }
11463   return ErrorFound != NoError;
11464 }
11465 
11466 /// Get the node id of the fixed point of an expression \a S.
11467 llvm::FoldingSetNodeID getNodeId(ASTContext &Context, const Expr *S) {
11468   llvm::FoldingSetNodeID Id;
11469   S->IgnoreParenImpCasts()->Profile(Id, Context, true);
11470   return Id;
11471 }
11472 
11473 /// Check if two expressions are same.
11474 bool checkIfTwoExprsAreSame(ASTContext &Context, const Expr *LHS,
11475                             const Expr *RHS) {
11476   return getNodeId(Context, LHS) == getNodeId(Context, RHS);
11477 }
11478 
11479 class OpenMPAtomicCompareChecker {
11480 public:
11481   /// All kinds of errors that can occur in `atomic compare`
11482   enum ErrorTy {
11483     /// Empty compound statement.
11484     NoStmt = 0,
11485     /// More than one statement in a compound statement.
11486     MoreThanOneStmt,
11487     /// Not an assignment binary operator.
11488     NotAnAssignment,
11489     /// Not a conditional operator.
11490     NotCondOp,
11491     /// Wrong false expr. According to the spec, 'x' should be at the false
11492     /// expression of a conditional expression.
11493     WrongFalseExpr,
11494     /// The condition of a conditional expression is not a binary operator.
11495     NotABinaryOp,
11496     /// Invalid binary operator (not <, >, or ==).
11497     InvalidBinaryOp,
11498     /// Invalid comparison (not x == e, e == x, x ordop expr, or expr ordop x).
11499     InvalidComparison,
11500     /// X is not a lvalue.
11501     XNotLValue,
11502     /// Not a scalar.
11503     NotScalar,
11504     /// Not an integer.
11505     NotInteger,
11506     /// 'else' statement is not expected.
11507     UnexpectedElse,
11508     /// Not an equality operator.
11509     NotEQ,
11510     /// Invalid assignment (not v == x).
11511     InvalidAssignment,
11512     /// Not if statement
11513     NotIfStmt,
11514     /// More than two statements in a compund statement.
11515     MoreThanTwoStmts,
11516     /// Not a compound statement.
11517     NotCompoundStmt,
11518     /// No else statement.
11519     NoElse,
11520     /// Not 'if (r)'.
11521     InvalidCondition,
11522     /// No error.
11523     NoError,
11524   };
11525 
11526   struct ErrorInfoTy {
11527     ErrorTy Error;
11528     SourceLocation ErrorLoc;
11529     SourceRange ErrorRange;
11530     SourceLocation NoteLoc;
11531     SourceRange NoteRange;
11532   };
11533 
11534   OpenMPAtomicCompareChecker(Sema &S) : ContextRef(S.getASTContext()) {}
11535 
11536   /// Check if statement \a S is valid for <tt>atomic compare</tt>.
11537   bool checkStmt(Stmt *S, ErrorInfoTy &ErrorInfo);
11538 
11539   Expr *getX() const { return X; }
11540   Expr *getE() const { return E; }
11541   Expr *getD() const { return D; }
11542   Expr *getCond() const { return C; }
11543   bool isXBinopExpr() const { return IsXBinopExpr; }
11544 
11545 protected:
11546   /// Reference to ASTContext
11547   ASTContext &ContextRef;
11548   /// 'x' lvalue part of the source atomic expression.
11549   Expr *X = nullptr;
11550   /// 'expr' or 'e' rvalue part of the source atomic expression.
11551   Expr *E = nullptr;
11552   /// 'd' rvalue part of the source atomic expression.
11553   Expr *D = nullptr;
11554   /// 'cond' part of the source atomic expression. It is in one of the following
11555   /// forms:
11556   /// expr ordop x
11557   /// x ordop expr
11558   /// x == e
11559   /// e == x
11560   Expr *C = nullptr;
11561   /// True if the cond expr is in the form of 'x ordop expr'.
11562   bool IsXBinopExpr = true;
11563 
11564   /// Check if it is a valid conditional update statement (cond-update-stmt).
11565   bool checkCondUpdateStmt(IfStmt *S, ErrorInfoTy &ErrorInfo);
11566 
11567   /// Check if it is a valid conditional expression statement (cond-expr-stmt).
11568   bool checkCondExprStmt(Stmt *S, ErrorInfoTy &ErrorInfo);
11569 
11570   /// Check if all captured values have right type.
11571   bool checkType(ErrorInfoTy &ErrorInfo) const;
11572 
11573   static bool CheckValue(const Expr *E, ErrorInfoTy &ErrorInfo,
11574                          bool ShouldBeLValue, bool ShouldBeInteger = false) {
11575     if (ShouldBeLValue && !E->isLValue()) {
11576       ErrorInfo.Error = ErrorTy::XNotLValue;
11577       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = E->getExprLoc();
11578       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = E->getSourceRange();
11579       return false;
11580     }
11581 
11582     if (!E->isInstantiationDependent()) {
11583       QualType QTy = E->getType();
11584       if (!QTy->isScalarType()) {
11585         ErrorInfo.Error = ErrorTy::NotScalar;
11586         ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = E->getExprLoc();
11587         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = E->getSourceRange();
11588         return false;
11589       }
11590       if (ShouldBeInteger && !QTy->isIntegerType()) {
11591         ErrorInfo.Error = ErrorTy::NotInteger;
11592         ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = E->getExprLoc();
11593         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = E->getSourceRange();
11594         return false;
11595       }
11596     }
11597 
11598     return true;
11599   }
11600 };
11601 
11602 bool OpenMPAtomicCompareChecker::checkCondUpdateStmt(IfStmt *S,
11603                                                      ErrorInfoTy &ErrorInfo) {
11604   auto *Then = S->getThen();
11605   if (auto *CS = dyn_cast<CompoundStmt>(Then)) {
11606     if (CS->body_empty()) {
11607       ErrorInfo.Error = ErrorTy::NoStmt;
11608       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11609       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
11610       return false;
11611     }
11612     if (CS->size() > 1) {
11613       ErrorInfo.Error = ErrorTy::MoreThanOneStmt;
11614       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11615       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getSourceRange();
11616       return false;
11617     }
11618     Then = CS->body_front();
11619   }
11620 
11621   auto *BO = dyn_cast<BinaryOperator>(Then);
11622   if (!BO) {
11623     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11624     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Then->getBeginLoc();
11625     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Then->getSourceRange();
11626     return false;
11627   }
11628   if (BO->getOpcode() != BO_Assign) {
11629     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11630     ErrorInfo.ErrorLoc = BO->getExprLoc();
11631     ErrorInfo.NoteLoc = BO->getOperatorLoc();
11632     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getSourceRange();
11633     return false;
11634   }
11635 
11636   X = BO->getLHS();
11637 
11638   auto *Cond = dyn_cast<BinaryOperator>(S->getCond());
11639   if (!Cond) {
11640     ErrorInfo.Error = ErrorTy::NotABinaryOp;
11641     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S->getCond()->getExprLoc();
11642     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getCond()->getSourceRange();
11643     return false;
11644   }
11645 
11646   switch (Cond->getOpcode()) {
11647   case BO_EQ: {
11648     C = Cond;
11649     D = BO->getRHS();
11650     if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getLHS())) {
11651       E = Cond->getRHS();
11652     } else if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getRHS())) {
11653       E = Cond->getLHS();
11654     } else {
11655       ErrorInfo.Error = ErrorTy::InvalidComparison;
11656       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11657       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11658       return false;
11659     }
11660     break;
11661   }
11662   case BO_LT:
11663   case BO_GT: {
11664     E = BO->getRHS();
11665     if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getLHS()) &&
11666         checkIfTwoExprsAreSame(ContextRef, E, Cond->getRHS())) {
11667       C = Cond;
11668     } else if (checkIfTwoExprsAreSame(ContextRef, E, Cond->getLHS()) &&
11669                checkIfTwoExprsAreSame(ContextRef, X, Cond->getRHS())) {
11670       C = Cond;
11671       IsXBinopExpr = false;
11672     } else {
11673       ErrorInfo.Error = ErrorTy::InvalidComparison;
11674       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11675       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11676       return false;
11677     }
11678     break;
11679   }
11680   default:
11681     ErrorInfo.Error = ErrorTy::InvalidBinaryOp;
11682     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11683     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11684     return false;
11685   }
11686 
11687   if (S->getElse()) {
11688     ErrorInfo.Error = ErrorTy::UnexpectedElse;
11689     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S->getElse()->getBeginLoc();
11690     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getElse()->getSourceRange();
11691     return false;
11692   }
11693 
11694   return true;
11695 }
11696 
11697 bool OpenMPAtomicCompareChecker::checkCondExprStmt(Stmt *S,
11698                                                    ErrorInfoTy &ErrorInfo) {
11699   auto *BO = dyn_cast<BinaryOperator>(S);
11700   if (!BO) {
11701     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11702     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S->getBeginLoc();
11703     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getSourceRange();
11704     return false;
11705   }
11706   if (BO->getOpcode() != BO_Assign) {
11707     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11708     ErrorInfo.ErrorLoc = BO->getExprLoc();
11709     ErrorInfo.NoteLoc = BO->getOperatorLoc();
11710     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getSourceRange();
11711     return false;
11712   }
11713 
11714   X = BO->getLHS();
11715 
11716   auto *CO = dyn_cast<ConditionalOperator>(BO->getRHS()->IgnoreParenImpCasts());
11717   if (!CO) {
11718     ErrorInfo.Error = ErrorTy::NotCondOp;
11719     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = BO->getRHS()->getExprLoc();
11720     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getRHS()->getSourceRange();
11721     return false;
11722   }
11723 
11724   if (!checkIfTwoExprsAreSame(ContextRef, X, CO->getFalseExpr())) {
11725     ErrorInfo.Error = ErrorTy::WrongFalseExpr;
11726     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CO->getFalseExpr()->getExprLoc();
11727     ErrorInfo.ErrorRange = ErrorInfo.NoteRange =
11728         CO->getFalseExpr()->getSourceRange();
11729     return false;
11730   }
11731 
11732   auto *Cond = dyn_cast<BinaryOperator>(CO->getCond());
11733   if (!Cond) {
11734     ErrorInfo.Error = ErrorTy::NotABinaryOp;
11735     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CO->getCond()->getExprLoc();
11736     ErrorInfo.ErrorRange = ErrorInfo.NoteRange =
11737         CO->getCond()->getSourceRange();
11738     return false;
11739   }
11740 
11741   switch (Cond->getOpcode()) {
11742   case BO_EQ: {
11743     C = Cond;
11744     D = CO->getTrueExpr();
11745     if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getLHS())) {
11746       E = Cond->getRHS();
11747     } else if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getRHS())) {
11748       E = Cond->getLHS();
11749     } else {
11750       ErrorInfo.Error = ErrorTy::InvalidComparison;
11751       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11752       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11753       return false;
11754     }
11755     break;
11756   }
11757   case BO_LT:
11758   case BO_GT: {
11759     E = CO->getTrueExpr();
11760     if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getLHS()) &&
11761         checkIfTwoExprsAreSame(ContextRef, E, Cond->getRHS())) {
11762       C = Cond;
11763     } else if (checkIfTwoExprsAreSame(ContextRef, E, Cond->getLHS()) &&
11764                checkIfTwoExprsAreSame(ContextRef, X, Cond->getRHS())) {
11765       C = Cond;
11766       IsXBinopExpr = false;
11767     } else {
11768       ErrorInfo.Error = ErrorTy::InvalidComparison;
11769       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11770       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11771       return false;
11772     }
11773     break;
11774   }
11775   default:
11776     ErrorInfo.Error = ErrorTy::InvalidBinaryOp;
11777     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11778     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11779     return false;
11780   }
11781 
11782   return true;
11783 }
11784 
11785 bool OpenMPAtomicCompareChecker::checkType(ErrorInfoTy &ErrorInfo) const {
11786   // 'x' and 'e' cannot be nullptr
11787   assert(X && E && "X and E cannot be nullptr");
11788 
11789   if (!CheckValue(X, ErrorInfo, true))
11790     return false;
11791 
11792   if (!CheckValue(E, ErrorInfo, false))
11793     return false;
11794 
11795   if (D && !CheckValue(D, ErrorInfo, false))
11796     return false;
11797 
11798   return true;
11799 }
11800 
11801 bool OpenMPAtomicCompareChecker::checkStmt(
11802     Stmt *S, OpenMPAtomicCompareChecker::ErrorInfoTy &ErrorInfo) {
11803   auto *CS = dyn_cast<CompoundStmt>(S);
11804   if (CS) {
11805     if (CS->body_empty()) {
11806       ErrorInfo.Error = ErrorTy::NoStmt;
11807       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11808       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
11809       return false;
11810     }
11811 
11812     if (CS->size() != 1) {
11813       ErrorInfo.Error = ErrorTy::MoreThanOneStmt;
11814       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11815       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
11816       return false;
11817     }
11818     S = CS->body_front();
11819   }
11820 
11821   auto Res = false;
11822 
11823   if (auto *IS = dyn_cast<IfStmt>(S)) {
11824     // Check if the statement is in one of the following forms
11825     // (cond-update-stmt):
11826     // if (expr ordop x) { x = expr; }
11827     // if (x ordop expr) { x = expr; }
11828     // if (x == e) { x = d; }
11829     Res = checkCondUpdateStmt(IS, ErrorInfo);
11830   } else {
11831     // Check if the statement is in one of the following forms (cond-expr-stmt):
11832     // x = expr ordop x ? expr : x;
11833     // x = x ordop expr ? expr : x;
11834     // x = x == e ? d : x;
11835     Res = checkCondExprStmt(S, ErrorInfo);
11836   }
11837 
11838   if (!Res)
11839     return false;
11840 
11841   return checkType(ErrorInfo);
11842 }
11843 
11844 class OpenMPAtomicCompareCaptureChecker final
11845     : public OpenMPAtomicCompareChecker {
11846 public:
11847   OpenMPAtomicCompareCaptureChecker(Sema &S) : OpenMPAtomicCompareChecker(S) {}
11848 
11849   Expr *getV() const { return V; }
11850   Expr *getR() const { return R; }
11851   bool isFailOnly() const { return IsFailOnly; }
11852   bool isPostfixUpdate() const { return IsPostfixUpdate; }
11853 
11854   /// Check if statement \a S is valid for <tt>atomic compare capture</tt>.
11855   bool checkStmt(Stmt *S, ErrorInfoTy &ErrorInfo);
11856 
11857 private:
11858   bool checkType(ErrorInfoTy &ErrorInfo);
11859 
11860   // NOTE: Form 3, 4, 5 in the following comments mean the 3rd, 4th, and 5th
11861   // form of 'conditional-update-capture-atomic' structured block on the v5.2
11862   // spec p.p. 82:
11863   // (1) { v = x; cond-update-stmt }
11864   // (2) { cond-update-stmt v = x; }
11865   // (3) if(x == e) { x = d; } else { v = x; }
11866   // (4) { r = x == e; if(r) { x = d; } }
11867   // (5) { r = x == e; if(r) { x = d; } else { v = x; } }
11868 
11869   /// Check if it is valid 'if(x == e) { x = d; } else { v = x; }' (form 3)
11870   bool checkForm3(IfStmt *S, ErrorInfoTy &ErrorInfo);
11871 
11872   /// Check if it is valid '{ r = x == e; if(r) { x = d; } }',
11873   /// or '{ r = x == e; if(r) { x = d; } else { v = x; } }' (form 4 and 5)
11874   bool checkForm45(Stmt *S, ErrorInfoTy &ErrorInfo);
11875 
11876   /// 'v' lvalue part of the source atomic expression.
11877   Expr *V = nullptr;
11878   /// 'r' lvalue part of the source atomic expression.
11879   Expr *R = nullptr;
11880   /// If 'v' is only updated when the comparison fails.
11881   bool IsFailOnly = false;
11882   /// If original value of 'x' must be stored in 'v', not an updated one.
11883   bool IsPostfixUpdate = false;
11884 };
11885 
11886 bool OpenMPAtomicCompareCaptureChecker::checkType(ErrorInfoTy &ErrorInfo) {
11887   if (!OpenMPAtomicCompareChecker::checkType(ErrorInfo))
11888     return false;
11889 
11890   if (V && !CheckValue(V, ErrorInfo, true))
11891     return false;
11892 
11893   if (R && !CheckValue(R, ErrorInfo, true, true))
11894     return false;
11895 
11896   return true;
11897 }
11898 
11899 bool OpenMPAtomicCompareCaptureChecker::checkForm3(IfStmt *S,
11900                                                    ErrorInfoTy &ErrorInfo) {
11901   IsFailOnly = true;
11902 
11903   auto *Then = S->getThen();
11904   if (auto *CS = dyn_cast<CompoundStmt>(Then)) {
11905     if (CS->body_empty()) {
11906       ErrorInfo.Error = ErrorTy::NoStmt;
11907       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11908       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
11909       return false;
11910     }
11911     if (CS->size() > 1) {
11912       ErrorInfo.Error = ErrorTy::MoreThanOneStmt;
11913       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11914       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
11915       return false;
11916     }
11917     Then = CS->body_front();
11918   }
11919 
11920   auto *BO = dyn_cast<BinaryOperator>(Then);
11921   if (!BO) {
11922     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11923     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Then->getBeginLoc();
11924     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Then->getSourceRange();
11925     return false;
11926   }
11927   if (BO->getOpcode() != BO_Assign) {
11928     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11929     ErrorInfo.ErrorLoc = BO->getExprLoc();
11930     ErrorInfo.NoteLoc = BO->getOperatorLoc();
11931     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getSourceRange();
11932     return false;
11933   }
11934 
11935   X = BO->getLHS();
11936   D = BO->getRHS();
11937 
11938   auto *Cond = dyn_cast<BinaryOperator>(S->getCond());
11939   if (!Cond) {
11940     ErrorInfo.Error = ErrorTy::NotABinaryOp;
11941     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S->getCond()->getExprLoc();
11942     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getCond()->getSourceRange();
11943     return false;
11944   }
11945   if (Cond->getOpcode() != BO_EQ) {
11946     ErrorInfo.Error = ErrorTy::NotEQ;
11947     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11948     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11949     return false;
11950   }
11951 
11952   if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getLHS())) {
11953     E = Cond->getRHS();
11954   } else if (checkIfTwoExprsAreSame(ContextRef, X, Cond->getRHS())) {
11955     E = Cond->getLHS();
11956   } else {
11957     ErrorInfo.Error = ErrorTy::InvalidComparison;
11958     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Cond->getExprLoc();
11959     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Cond->getSourceRange();
11960     return false;
11961   }
11962 
11963   C = Cond;
11964 
11965   if (!S->getElse()) {
11966     ErrorInfo.Error = ErrorTy::NoElse;
11967     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S->getBeginLoc();
11968     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getSourceRange();
11969     return false;
11970   }
11971 
11972   auto *Else = S->getElse();
11973   if (auto *CS = dyn_cast<CompoundStmt>(Else)) {
11974     if (CS->body_empty()) {
11975       ErrorInfo.Error = ErrorTy::NoStmt;
11976       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11977       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
11978       return false;
11979     }
11980     if (CS->size() > 1) {
11981       ErrorInfo.Error = ErrorTy::MoreThanOneStmt;
11982       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
11983       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getSourceRange();
11984       return false;
11985     }
11986     Else = CS->body_front();
11987   }
11988 
11989   auto *ElseBO = dyn_cast<BinaryOperator>(Else);
11990   if (!ElseBO) {
11991     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11992     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Else->getBeginLoc();
11993     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Else->getSourceRange();
11994     return false;
11995   }
11996   if (ElseBO->getOpcode() != BO_Assign) {
11997     ErrorInfo.Error = ErrorTy::NotAnAssignment;
11998     ErrorInfo.ErrorLoc = ElseBO->getExprLoc();
11999     ErrorInfo.NoteLoc = ElseBO->getOperatorLoc();
12000     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ElseBO->getSourceRange();
12001     return false;
12002   }
12003 
12004   if (!checkIfTwoExprsAreSame(ContextRef, X, ElseBO->getRHS())) {
12005     ErrorInfo.Error = ErrorTy::InvalidAssignment;
12006     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = ElseBO->getRHS()->getExprLoc();
12007     ErrorInfo.ErrorRange = ErrorInfo.NoteRange =
12008         ElseBO->getRHS()->getSourceRange();
12009     return false;
12010   }
12011 
12012   V = ElseBO->getLHS();
12013 
12014   return checkType(ErrorInfo);
12015 }
12016 
12017 bool OpenMPAtomicCompareCaptureChecker::checkForm45(Stmt *S,
12018                                                     ErrorInfoTy &ErrorInfo) {
12019   // We don't check here as they should be already done before call this
12020   // function.
12021   auto *CS = cast<CompoundStmt>(S);
12022   assert(CS->size() == 2 && "CompoundStmt size is not expected");
12023   auto *S1 = cast<BinaryOperator>(CS->body_front());
12024   auto *S2 = cast<IfStmt>(CS->body_back());
12025   assert(S1->getOpcode() == BO_Assign && "unexpected binary operator");
12026 
12027   if (!checkIfTwoExprsAreSame(ContextRef, S1->getLHS(), S2->getCond())) {
12028     ErrorInfo.Error = ErrorTy::InvalidCondition;
12029     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S2->getCond()->getExprLoc();
12030     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S1->getLHS()->getSourceRange();
12031     return false;
12032   }
12033 
12034   R = S1->getLHS();
12035 
12036   auto *Then = S2->getThen();
12037   if (auto *ThenCS = dyn_cast<CompoundStmt>(Then)) {
12038     if (ThenCS->body_empty()) {
12039       ErrorInfo.Error = ErrorTy::NoStmt;
12040       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = ThenCS->getBeginLoc();
12041       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ThenCS->getSourceRange();
12042       return false;
12043     }
12044     if (ThenCS->size() > 1) {
12045       ErrorInfo.Error = ErrorTy::MoreThanOneStmt;
12046       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = ThenCS->getBeginLoc();
12047       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ThenCS->getSourceRange();
12048       return false;
12049     }
12050     Then = ThenCS->body_front();
12051   }
12052 
12053   auto *ThenBO = dyn_cast<BinaryOperator>(Then);
12054   if (!ThenBO) {
12055     ErrorInfo.Error = ErrorTy::NotAnAssignment;
12056     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S2->getBeginLoc();
12057     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S2->getSourceRange();
12058     return false;
12059   }
12060   if (ThenBO->getOpcode() != BO_Assign) {
12061     ErrorInfo.Error = ErrorTy::NotAnAssignment;
12062     ErrorInfo.ErrorLoc = ThenBO->getExprLoc();
12063     ErrorInfo.NoteLoc = ThenBO->getOperatorLoc();
12064     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ThenBO->getSourceRange();
12065     return false;
12066   }
12067 
12068   X = ThenBO->getLHS();
12069   D = ThenBO->getRHS();
12070 
12071   auto *BO = cast<BinaryOperator>(S1->getRHS()->IgnoreImpCasts());
12072   if (BO->getOpcode() != BO_EQ) {
12073     ErrorInfo.Error = ErrorTy::NotEQ;
12074     ErrorInfo.ErrorLoc = BO->getExprLoc();
12075     ErrorInfo.NoteLoc = BO->getOperatorLoc();
12076     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getSourceRange();
12077     return false;
12078   }
12079 
12080   C = BO;
12081 
12082   if (checkIfTwoExprsAreSame(ContextRef, X, BO->getLHS())) {
12083     E = BO->getRHS();
12084   } else if (checkIfTwoExprsAreSame(ContextRef, X, BO->getRHS())) {
12085     E = BO->getLHS();
12086   } else {
12087     ErrorInfo.Error = ErrorTy::InvalidComparison;
12088     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = BO->getExprLoc();
12089     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getSourceRange();
12090     return false;
12091   }
12092 
12093   if (S2->getElse()) {
12094     IsFailOnly = true;
12095 
12096     auto *Else = S2->getElse();
12097     if (auto *ElseCS = dyn_cast<CompoundStmt>(Else)) {
12098       if (ElseCS->body_empty()) {
12099         ErrorInfo.Error = ErrorTy::NoStmt;
12100         ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = ElseCS->getBeginLoc();
12101         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ElseCS->getSourceRange();
12102         return false;
12103       }
12104       if (ElseCS->size() > 1) {
12105         ErrorInfo.Error = ErrorTy::MoreThanOneStmt;
12106         ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = ElseCS->getBeginLoc();
12107         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ElseCS->getSourceRange();
12108         return false;
12109       }
12110       Else = ElseCS->body_front();
12111     }
12112 
12113     auto *ElseBO = dyn_cast<BinaryOperator>(Else);
12114     if (!ElseBO) {
12115       ErrorInfo.Error = ErrorTy::NotAnAssignment;
12116       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = Else->getBeginLoc();
12117       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = Else->getSourceRange();
12118       return false;
12119     }
12120     if (ElseBO->getOpcode() != BO_Assign) {
12121       ErrorInfo.Error = ErrorTy::NotAnAssignment;
12122       ErrorInfo.ErrorLoc = ElseBO->getExprLoc();
12123       ErrorInfo.NoteLoc = ElseBO->getOperatorLoc();
12124       ErrorInfo.ErrorRange = ErrorInfo.NoteRange = ElseBO->getSourceRange();
12125       return false;
12126     }
12127     if (!checkIfTwoExprsAreSame(ContextRef, X, ElseBO->getRHS())) {
12128       ErrorInfo.Error = ErrorTy::InvalidAssignment;
12129       ErrorInfo.ErrorLoc = ElseBO->getRHS()->getExprLoc();
12130       ErrorInfo.NoteLoc = X->getExprLoc();
12131       ErrorInfo.ErrorRange = ElseBO->getRHS()->getSourceRange();
12132       ErrorInfo.NoteRange = X->getSourceRange();
12133       return false;
12134     }
12135 
12136     V = ElseBO->getLHS();
12137   }
12138 
12139   return checkType(ErrorInfo);
12140 }
12141 
12142 bool OpenMPAtomicCompareCaptureChecker::checkStmt(Stmt *S,
12143                                                   ErrorInfoTy &ErrorInfo) {
12144   // if(x == e) { x = d; } else { v = x; }
12145   if (auto *IS = dyn_cast<IfStmt>(S))
12146     return checkForm3(IS, ErrorInfo);
12147 
12148   auto *CS = dyn_cast<CompoundStmt>(S);
12149   if (!CS) {
12150     ErrorInfo.Error = ErrorTy::NotCompoundStmt;
12151     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = S->getBeginLoc();
12152     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = S->getSourceRange();
12153     return false;
12154   }
12155   if (CS->body_empty()) {
12156     ErrorInfo.Error = ErrorTy::NoStmt;
12157     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
12158     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
12159     return false;
12160   }
12161 
12162   // { if(x == e) { x = d; } else { v = x; } }
12163   if (CS->size() == 1) {
12164     auto *IS = dyn_cast<IfStmt>(CS->body_front());
12165     if (!IS) {
12166       ErrorInfo.Error = ErrorTy::NotIfStmt;
12167       ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->body_front()->getBeginLoc();
12168       ErrorInfo.ErrorRange = ErrorInfo.NoteRange =
12169           CS->body_front()->getSourceRange();
12170       return false;
12171     }
12172 
12173     return checkForm3(IS, ErrorInfo);
12174   } else if (CS->size() == 2) {
12175     auto *S1 = CS->body_front();
12176     auto *S2 = CS->body_back();
12177 
12178     Stmt *UpdateStmt = nullptr;
12179     Stmt *CondUpdateStmt = nullptr;
12180 
12181     if (auto *BO = dyn_cast<BinaryOperator>(S1)) {
12182       // { v = x; cond-update-stmt } or form 45.
12183       UpdateStmt = S1;
12184       CondUpdateStmt = S2;
12185       // Check if form 45.
12186       if (isa<BinaryOperator>(BO->getRHS()->IgnoreImpCasts()) &&
12187           isa<IfStmt>(S2))
12188         return checkForm45(CS, ErrorInfo);
12189       // It cannot be set before we the check for form45.
12190       IsPostfixUpdate = true;
12191     } else {
12192       // { cond-update-stmt v = x; }
12193       UpdateStmt = S2;
12194       CondUpdateStmt = S1;
12195     }
12196 
12197     auto CheckCondUpdateStmt = [this, &ErrorInfo](Stmt *CUS) {
12198       auto *IS = dyn_cast<IfStmt>(CUS);
12199       if (!IS) {
12200         ErrorInfo.Error = ErrorTy::NotIfStmt;
12201         ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CUS->getBeginLoc();
12202         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CUS->getSourceRange();
12203         return false;
12204       }
12205 
12206       if (!checkCondUpdateStmt(IS, ErrorInfo))
12207         return false;
12208 
12209       return true;
12210     };
12211 
12212     // CheckUpdateStmt has to be called *after* CheckCondUpdateStmt.
12213     auto CheckUpdateStmt = [this, &ErrorInfo](Stmt *US) {
12214       auto *BO = dyn_cast<BinaryOperator>(US);
12215       if (!BO) {
12216         ErrorInfo.Error = ErrorTy::NotAnAssignment;
12217         ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = US->getBeginLoc();
12218         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = US->getSourceRange();
12219         return false;
12220       }
12221       if (BO->getOpcode() != BO_Assign) {
12222         ErrorInfo.Error = ErrorTy::NotAnAssignment;
12223         ErrorInfo.ErrorLoc = BO->getExprLoc();
12224         ErrorInfo.NoteLoc = BO->getOperatorLoc();
12225         ErrorInfo.ErrorRange = ErrorInfo.NoteRange = BO->getSourceRange();
12226         return false;
12227       }
12228       if (!checkIfTwoExprsAreSame(ContextRef, this->X, BO->getRHS())) {
12229         ErrorInfo.Error = ErrorTy::InvalidAssignment;
12230         ErrorInfo.ErrorLoc = BO->getRHS()->getExprLoc();
12231         ErrorInfo.NoteLoc = this->X->getExprLoc();
12232         ErrorInfo.ErrorRange = BO->getRHS()->getSourceRange();
12233         ErrorInfo.NoteRange = this->X->getSourceRange();
12234         return false;
12235       }
12236 
12237       this->V = BO->getLHS();
12238 
12239       return true;
12240     };
12241 
12242     if (!CheckCondUpdateStmt(CondUpdateStmt))
12243       return false;
12244     if (!CheckUpdateStmt(UpdateStmt))
12245       return false;
12246   } else {
12247     ErrorInfo.Error = ErrorTy::MoreThanTwoStmts;
12248     ErrorInfo.ErrorLoc = ErrorInfo.NoteLoc = CS->getBeginLoc();
12249     ErrorInfo.ErrorRange = ErrorInfo.NoteRange = CS->getSourceRange();
12250     return false;
12251   }
12252 
12253   return checkType(ErrorInfo);
12254 }
12255 } // namespace
12256 
12257 StmtResult Sema::ActOnOpenMPAtomicDirective(ArrayRef<OMPClause *> Clauses,
12258                                             Stmt *AStmt,
12259                                             SourceLocation StartLoc,
12260                                             SourceLocation EndLoc) {
12261   // Register location of the first atomic directive.
12262   DSAStack->addAtomicDirectiveLoc(StartLoc);
12263   if (!AStmt)
12264     return StmtError();
12265 
12266   // 1.2.2 OpenMP Language Terminology
12267   // Structured block - An executable statement with a single entry at the
12268   // top and a single exit at the bottom.
12269   // The point of exit cannot be a branch out of the structured block.
12270   // longjmp() and throw() must not violate the entry/exit criteria.
12271   OpenMPClauseKind AtomicKind = OMPC_unknown;
12272   SourceLocation AtomicKindLoc;
12273   OpenMPClauseKind MemOrderKind = OMPC_unknown;
12274   SourceLocation MemOrderLoc;
12275   bool MutexClauseEncountered = false;
12276   llvm::SmallSet<OpenMPClauseKind, 2> EncounteredAtomicKinds;
12277   for (const OMPClause *C : Clauses) {
12278     switch (C->getClauseKind()) {
12279     case OMPC_read:
12280     case OMPC_write:
12281     case OMPC_update:
12282       MutexClauseEncountered = true;
12283       LLVM_FALLTHROUGH;
12284     case OMPC_capture:
12285     case OMPC_compare: {
12286       if (AtomicKind != OMPC_unknown && MutexClauseEncountered) {
12287         Diag(C->getBeginLoc(), diag::err_omp_atomic_several_clauses)
12288             << SourceRange(C->getBeginLoc(), C->getEndLoc());
12289         Diag(AtomicKindLoc, diag::note_omp_previous_mem_order_clause)
12290             << getOpenMPClauseName(AtomicKind);
12291       } else {
12292         AtomicKind = C->getClauseKind();
12293         AtomicKindLoc = C->getBeginLoc();
12294         if (!EncounteredAtomicKinds.insert(C->getClauseKind()).second) {
12295           Diag(C->getBeginLoc(), diag::err_omp_atomic_several_clauses)
12296               << SourceRange(C->getBeginLoc(), C->getEndLoc());
12297           Diag(AtomicKindLoc, diag::note_omp_previous_mem_order_clause)
12298               << getOpenMPClauseName(AtomicKind);
12299         }
12300       }
12301       break;
12302     }
12303     case OMPC_seq_cst:
12304     case OMPC_acq_rel:
12305     case OMPC_acquire:
12306     case OMPC_release:
12307     case OMPC_relaxed: {
12308       if (MemOrderKind != OMPC_unknown) {
12309         Diag(C->getBeginLoc(), diag::err_omp_several_mem_order_clauses)
12310             << getOpenMPDirectiveName(OMPD_atomic) << 0
12311             << SourceRange(C->getBeginLoc(), C->getEndLoc());
12312         Diag(MemOrderLoc, diag::note_omp_previous_mem_order_clause)
12313             << getOpenMPClauseName(MemOrderKind);
12314       } else {
12315         MemOrderKind = C->getClauseKind();
12316         MemOrderLoc = C->getBeginLoc();
12317       }
12318       break;
12319     }
12320     // The following clauses are allowed, but we don't need to do anything here.
12321     case OMPC_hint:
12322       break;
12323     default:
12324       llvm_unreachable("unknown clause is encountered");
12325     }
12326   }
12327   bool IsCompareCapture = false;
12328   if (EncounteredAtomicKinds.contains(OMPC_compare) &&
12329       EncounteredAtomicKinds.contains(OMPC_capture)) {
12330     IsCompareCapture = true;
12331     AtomicKind = OMPC_compare;
12332   }
12333   // OpenMP 5.0, 2.17.7 atomic Construct, Restrictions
12334   // If atomic-clause is read then memory-order-clause must not be acq_rel or
12335   // release.
12336   // If atomic-clause is write then memory-order-clause must not be acq_rel or
12337   // acquire.
12338   // If atomic-clause is update or not present then memory-order-clause must not
12339   // be acq_rel or acquire.
12340   if ((AtomicKind == OMPC_read &&
12341        (MemOrderKind == OMPC_acq_rel || MemOrderKind == OMPC_release)) ||
12342       ((AtomicKind == OMPC_write || AtomicKind == OMPC_update ||
12343         AtomicKind == OMPC_unknown) &&
12344        (MemOrderKind == OMPC_acq_rel || MemOrderKind == OMPC_acquire))) {
12345     SourceLocation Loc = AtomicKindLoc;
12346     if (AtomicKind == OMPC_unknown)
12347       Loc = StartLoc;
12348     Diag(Loc, diag::err_omp_atomic_incompatible_mem_order_clause)
12349         << getOpenMPClauseName(AtomicKind)
12350         << (AtomicKind == OMPC_unknown ? 1 : 0)
12351         << getOpenMPClauseName(MemOrderKind);
12352     Diag(MemOrderLoc, diag::note_omp_previous_mem_order_clause)
12353         << getOpenMPClauseName(MemOrderKind);
12354   }
12355 
12356   Stmt *Body = AStmt;
12357   if (auto *EWC = dyn_cast<ExprWithCleanups>(Body))
12358     Body = EWC->getSubExpr();
12359 
12360   Expr *X = nullptr;
12361   Expr *V = nullptr;
12362   Expr *E = nullptr;
12363   Expr *UE = nullptr;
12364   Expr *D = nullptr;
12365   Expr *CE = nullptr;
12366   Expr *R = nullptr;
12367   bool IsXLHSInRHSPart = false;
12368   bool IsPostfixUpdate = false;
12369   bool IsFailOnly = false;
12370   // OpenMP [2.12.6, atomic Construct]
12371   // In the next expressions:
12372   // * x and v (as applicable) are both l-value expressions with scalar type.
12373   // * During the execution of an atomic region, multiple syntactic
12374   // occurrences of x must designate the same storage location.
12375   // * Neither of v and expr (as applicable) may access the storage location
12376   // designated by x.
12377   // * Neither of x and expr (as applicable) may access the storage location
12378   // designated by v.
12379   // * expr is an expression with scalar type.
12380   // * binop is one of +, *, -, /, &, ^, |, <<, or >>.
12381   // * binop, binop=, ++, and -- are not overloaded operators.
12382   // * The expression x binop expr must be numerically equivalent to x binop
12383   // (expr). This requirement is satisfied if the operators in expr have
12384   // precedence greater than binop, or by using parentheses around expr or
12385   // subexpressions of expr.
12386   // * The expression expr binop x must be numerically equivalent to (expr)
12387   // binop x. This requirement is satisfied if the operators in expr have
12388   // precedence equal to or greater than binop, or by using parentheses around
12389   // expr or subexpressions of expr.
12390   // * For forms that allow multiple occurrences of x, the number of times
12391   // that x is evaluated is unspecified.
12392   if (AtomicKind == OMPC_read) {
12393     enum {
12394       NotAnExpression,
12395       NotAnAssignmentOp,
12396       NotAScalarType,
12397       NotAnLValue,
12398       NoError
12399     } ErrorFound = NoError;
12400     SourceLocation ErrorLoc, NoteLoc;
12401     SourceRange ErrorRange, NoteRange;
12402     // If clause is read:
12403     //  v = x;
12404     if (const auto *AtomicBody = dyn_cast<Expr>(Body)) {
12405       const auto *AtomicBinOp =
12406           dyn_cast<BinaryOperator>(AtomicBody->IgnoreParenImpCasts());
12407       if (AtomicBinOp && AtomicBinOp->getOpcode() == BO_Assign) {
12408         X = AtomicBinOp->getRHS()->IgnoreParenImpCasts();
12409         V = AtomicBinOp->getLHS()->IgnoreParenImpCasts();
12410         if ((X->isInstantiationDependent() || X->getType()->isScalarType()) &&
12411             (V->isInstantiationDependent() || V->getType()->isScalarType())) {
12412           if (!X->isLValue() || !V->isLValue()) {
12413             const Expr *NotLValueExpr = X->isLValue() ? V : X;
12414             ErrorFound = NotAnLValue;
12415             ErrorLoc = AtomicBinOp->getExprLoc();
12416             ErrorRange = AtomicBinOp->getSourceRange();
12417             NoteLoc = NotLValueExpr->getExprLoc();
12418             NoteRange = NotLValueExpr->getSourceRange();
12419           }
12420         } else if (!X->isInstantiationDependent() ||
12421                    !V->isInstantiationDependent()) {
12422           const Expr *NotScalarExpr =
12423               (X->isInstantiationDependent() || X->getType()->isScalarType())
12424                   ? V
12425                   : X;
12426           ErrorFound = NotAScalarType;
12427           ErrorLoc = AtomicBinOp->getExprLoc();
12428           ErrorRange = AtomicBinOp->getSourceRange();
12429           NoteLoc = NotScalarExpr->getExprLoc();
12430           NoteRange = NotScalarExpr->getSourceRange();
12431         }
12432       } else if (!AtomicBody->isInstantiationDependent()) {
12433         ErrorFound = NotAnAssignmentOp;
12434         ErrorLoc = AtomicBody->getExprLoc();
12435         ErrorRange = AtomicBody->getSourceRange();
12436         NoteLoc = AtomicBinOp ? AtomicBinOp->getOperatorLoc()
12437                               : AtomicBody->getExprLoc();
12438         NoteRange = AtomicBinOp ? AtomicBinOp->getSourceRange()
12439                                 : AtomicBody->getSourceRange();
12440       }
12441     } else {
12442       ErrorFound = NotAnExpression;
12443       NoteLoc = ErrorLoc = Body->getBeginLoc();
12444       NoteRange = ErrorRange = SourceRange(NoteLoc, NoteLoc);
12445     }
12446     if (ErrorFound != NoError) {
12447       Diag(ErrorLoc, diag::err_omp_atomic_read_not_expression_statement)
12448           << ErrorRange;
12449       Diag(NoteLoc, diag::note_omp_atomic_read_write)
12450           << ErrorFound << NoteRange;
12451       return StmtError();
12452     }
12453     if (CurContext->isDependentContext())
12454       V = X = nullptr;
12455   } else if (AtomicKind == OMPC_write) {
12456     enum {
12457       NotAnExpression,
12458       NotAnAssignmentOp,
12459       NotAScalarType,
12460       NotAnLValue,
12461       NoError
12462     } ErrorFound = NoError;
12463     SourceLocation ErrorLoc, NoteLoc;
12464     SourceRange ErrorRange, NoteRange;
12465     // If clause is write:
12466     //  x = expr;
12467     if (const auto *AtomicBody = dyn_cast<Expr>(Body)) {
12468       const auto *AtomicBinOp =
12469           dyn_cast<BinaryOperator>(AtomicBody->IgnoreParenImpCasts());
12470       if (AtomicBinOp && AtomicBinOp->getOpcode() == BO_Assign) {
12471         X = AtomicBinOp->getLHS();
12472         E = AtomicBinOp->getRHS();
12473         if ((X->isInstantiationDependent() || X->getType()->isScalarType()) &&
12474             (E->isInstantiationDependent() || E->getType()->isScalarType())) {
12475           if (!X->isLValue()) {
12476             ErrorFound = NotAnLValue;
12477             ErrorLoc = AtomicBinOp->getExprLoc();
12478             ErrorRange = AtomicBinOp->getSourceRange();
12479             NoteLoc = X->getExprLoc();
12480             NoteRange = X->getSourceRange();
12481           }
12482         } else if (!X->isInstantiationDependent() ||
12483                    !E->isInstantiationDependent()) {
12484           const Expr *NotScalarExpr =
12485               (X->isInstantiationDependent() || X->getType()->isScalarType())
12486                   ? E
12487                   : X;
12488           ErrorFound = NotAScalarType;
12489           ErrorLoc = AtomicBinOp->getExprLoc();
12490           ErrorRange = AtomicBinOp->getSourceRange();
12491           NoteLoc = NotScalarExpr->getExprLoc();
12492           NoteRange = NotScalarExpr->getSourceRange();
12493         }
12494       } else if (!AtomicBody->isInstantiationDependent()) {
12495         ErrorFound = NotAnAssignmentOp;
12496         ErrorLoc = AtomicBody->getExprLoc();
12497         ErrorRange = AtomicBody->getSourceRange();
12498         NoteLoc = AtomicBinOp ? AtomicBinOp->getOperatorLoc()
12499                               : AtomicBody->getExprLoc();
12500         NoteRange = AtomicBinOp ? AtomicBinOp->getSourceRange()
12501                                 : AtomicBody->getSourceRange();
12502       }
12503     } else {
12504       ErrorFound = NotAnExpression;
12505       NoteLoc = ErrorLoc = Body->getBeginLoc();
12506       NoteRange = ErrorRange = SourceRange(NoteLoc, NoteLoc);
12507     }
12508     if (ErrorFound != NoError) {
12509       Diag(ErrorLoc, diag::err_omp_atomic_write_not_expression_statement)
12510           << ErrorRange;
12511       Diag(NoteLoc, diag::note_omp_atomic_read_write)
12512           << ErrorFound << NoteRange;
12513       return StmtError();
12514     }
12515     if (CurContext->isDependentContext())
12516       E = X = nullptr;
12517   } else if (AtomicKind == OMPC_update || AtomicKind == OMPC_unknown) {
12518     // If clause is update:
12519     //  x++;
12520     //  x--;
12521     //  ++x;
12522     //  --x;
12523     //  x binop= expr;
12524     //  x = x binop expr;
12525     //  x = expr binop x;
12526     OpenMPAtomicUpdateChecker Checker(*this);
12527     if (Checker.checkStatement(
12528             Body,
12529             (AtomicKind == OMPC_update)
12530                 ? diag::err_omp_atomic_update_not_expression_statement
12531                 : diag::err_omp_atomic_not_expression_statement,
12532             diag::note_omp_atomic_update))
12533       return StmtError();
12534     if (!CurContext->isDependentContext()) {
12535       E = Checker.getExpr();
12536       X = Checker.getX();
12537       UE = Checker.getUpdateExpr();
12538       IsXLHSInRHSPart = Checker.isXLHSInRHSPart();
12539     }
12540   } else if (AtomicKind == OMPC_capture) {
12541     enum {
12542       NotAnAssignmentOp,
12543       NotACompoundStatement,
12544       NotTwoSubstatements,
12545       NotASpecificExpression,
12546       NoError
12547     } ErrorFound = NoError;
12548     SourceLocation ErrorLoc, NoteLoc;
12549     SourceRange ErrorRange, NoteRange;
12550     if (const auto *AtomicBody = dyn_cast<Expr>(Body)) {
12551       // If clause is a capture:
12552       //  v = x++;
12553       //  v = x--;
12554       //  v = ++x;
12555       //  v = --x;
12556       //  v = x binop= expr;
12557       //  v = x = x binop expr;
12558       //  v = x = expr binop x;
12559       const auto *AtomicBinOp =
12560           dyn_cast<BinaryOperator>(AtomicBody->IgnoreParenImpCasts());
12561       if (AtomicBinOp && AtomicBinOp->getOpcode() == BO_Assign) {
12562         V = AtomicBinOp->getLHS();
12563         Body = AtomicBinOp->getRHS()->IgnoreParenImpCasts();
12564         OpenMPAtomicUpdateChecker Checker(*this);
12565         if (Checker.checkStatement(
12566                 Body, diag::err_omp_atomic_capture_not_expression_statement,
12567                 diag::note_omp_atomic_update))
12568           return StmtError();
12569         E = Checker.getExpr();
12570         X = Checker.getX();
12571         UE = Checker.getUpdateExpr();
12572         IsXLHSInRHSPart = Checker.isXLHSInRHSPart();
12573         IsPostfixUpdate = Checker.isPostfixUpdate();
12574       } else if (!AtomicBody->isInstantiationDependent()) {
12575         ErrorLoc = AtomicBody->getExprLoc();
12576         ErrorRange = AtomicBody->getSourceRange();
12577         NoteLoc = AtomicBinOp ? AtomicBinOp->getOperatorLoc()
12578                               : AtomicBody->getExprLoc();
12579         NoteRange = AtomicBinOp ? AtomicBinOp->getSourceRange()
12580                                 : AtomicBody->getSourceRange();
12581         ErrorFound = NotAnAssignmentOp;
12582       }
12583       if (ErrorFound != NoError) {
12584         Diag(ErrorLoc, diag::err_omp_atomic_capture_not_expression_statement)
12585             << ErrorRange;
12586         Diag(NoteLoc, diag::note_omp_atomic_capture) << ErrorFound << NoteRange;
12587         return StmtError();
12588       }
12589       if (CurContext->isDependentContext())
12590         UE = V = E = X = nullptr;
12591     } else {
12592       // If clause is a capture:
12593       //  { v = x; x = expr; }
12594       //  { v = x; x++; }
12595       //  { v = x; x--; }
12596       //  { v = x; ++x; }
12597       //  { v = x; --x; }
12598       //  { v = x; x binop= expr; }
12599       //  { v = x; x = x binop expr; }
12600       //  { v = x; x = expr binop x; }
12601       //  { x++; v = x; }
12602       //  { x--; v = x; }
12603       //  { ++x; v = x; }
12604       //  { --x; v = x; }
12605       //  { x binop= expr; v = x; }
12606       //  { x = x binop expr; v = x; }
12607       //  { x = expr binop x; v = x; }
12608       if (auto *CS = dyn_cast<CompoundStmt>(Body)) {
12609         // Check that this is { expr1; expr2; }
12610         if (CS->size() == 2) {
12611           Stmt *First = CS->body_front();
12612           Stmt *Second = CS->body_back();
12613           if (auto *EWC = dyn_cast<ExprWithCleanups>(First))
12614             First = EWC->getSubExpr()->IgnoreParenImpCasts();
12615           if (auto *EWC = dyn_cast<ExprWithCleanups>(Second))
12616             Second = EWC->getSubExpr()->IgnoreParenImpCasts();
12617           // Need to find what subexpression is 'v' and what is 'x'.
12618           OpenMPAtomicUpdateChecker Checker(*this);
12619           bool IsUpdateExprFound = !Checker.checkStatement(Second);
12620           BinaryOperator *BinOp = nullptr;
12621           if (IsUpdateExprFound) {
12622             BinOp = dyn_cast<BinaryOperator>(First);
12623             IsUpdateExprFound = BinOp && BinOp->getOpcode() == BO_Assign;
12624           }
12625           if (IsUpdateExprFound && !CurContext->isDependentContext()) {
12626             //  { v = x; x++; }
12627             //  { v = x; x--; }
12628             //  { v = x; ++x; }
12629             //  { v = x; --x; }
12630             //  { v = x; x binop= expr; }
12631             //  { v = x; x = x binop expr; }
12632             //  { v = x; x = expr binop x; }
12633             // Check that the first expression has form v = x.
12634             Expr *PossibleX = BinOp->getRHS()->IgnoreParenImpCasts();
12635             llvm::FoldingSetNodeID XId, PossibleXId;
12636             Checker.getX()->Profile(XId, Context, /*Canonical=*/true);
12637             PossibleX->Profile(PossibleXId, Context, /*Canonical=*/true);
12638             IsUpdateExprFound = XId == PossibleXId;
12639             if (IsUpdateExprFound) {
12640               V = BinOp->getLHS();
12641               X = Checker.getX();
12642               E = Checker.getExpr();
12643               UE = Checker.getUpdateExpr();
12644               IsXLHSInRHSPart = Checker.isXLHSInRHSPart();
12645               IsPostfixUpdate = true;
12646             }
12647           }
12648           if (!IsUpdateExprFound) {
12649             IsUpdateExprFound = !Checker.checkStatement(First);
12650             BinOp = nullptr;
12651             if (IsUpdateExprFound) {
12652               BinOp = dyn_cast<BinaryOperator>(Second);
12653               IsUpdateExprFound = BinOp && BinOp->getOpcode() == BO_Assign;
12654             }
12655             if (IsUpdateExprFound && !CurContext->isDependentContext()) {
12656               //  { x++; v = x; }
12657               //  { x--; v = x; }
12658               //  { ++x; v = x; }
12659               //  { --x; v = x; }
12660               //  { x binop= expr; v = x; }
12661               //  { x = x binop expr; v = x; }
12662               //  { x = expr binop x; v = x; }
12663               // Check that the second expression has form v = x.
12664               Expr *PossibleX = BinOp->getRHS()->IgnoreParenImpCasts();
12665               llvm::FoldingSetNodeID XId, PossibleXId;
12666               Checker.getX()->Profile(XId, Context, /*Canonical=*/true);
12667               PossibleX->Profile(PossibleXId, Context, /*Canonical=*/true);
12668               IsUpdateExprFound = XId == PossibleXId;
12669               if (IsUpdateExprFound) {
12670                 V = BinOp->getLHS();
12671                 X = Checker.getX();
12672                 E = Checker.getExpr();
12673                 UE = Checker.getUpdateExpr();
12674                 IsXLHSInRHSPart = Checker.isXLHSInRHSPart();
12675                 IsPostfixUpdate = false;
12676               }
12677             }
12678           }
12679           if (!IsUpdateExprFound) {
12680             //  { v = x; x = expr; }
12681             auto *FirstExpr = dyn_cast<Expr>(First);
12682             auto *SecondExpr = dyn_cast<Expr>(Second);
12683             if (!FirstExpr || !SecondExpr ||
12684                 !(FirstExpr->isInstantiationDependent() ||
12685                   SecondExpr->isInstantiationDependent())) {
12686               auto *FirstBinOp = dyn_cast<BinaryOperator>(First);
12687               if (!FirstBinOp || FirstBinOp->getOpcode() != BO_Assign) {
12688                 ErrorFound = NotAnAssignmentOp;
12689                 NoteLoc = ErrorLoc = FirstBinOp ? FirstBinOp->getOperatorLoc()
12690                                                 : First->getBeginLoc();
12691                 NoteRange = ErrorRange = FirstBinOp
12692                                              ? FirstBinOp->getSourceRange()
12693                                              : SourceRange(ErrorLoc, ErrorLoc);
12694               } else {
12695                 auto *SecondBinOp = dyn_cast<BinaryOperator>(Second);
12696                 if (!SecondBinOp || SecondBinOp->getOpcode() != BO_Assign) {
12697                   ErrorFound = NotAnAssignmentOp;
12698                   NoteLoc = ErrorLoc = SecondBinOp
12699                                            ? SecondBinOp->getOperatorLoc()
12700                                            : Second->getBeginLoc();
12701                   NoteRange = ErrorRange =
12702                       SecondBinOp ? SecondBinOp->getSourceRange()
12703                                   : SourceRange(ErrorLoc, ErrorLoc);
12704                 } else {
12705                   Expr *PossibleXRHSInFirst =
12706                       FirstBinOp->getRHS()->IgnoreParenImpCasts();
12707                   Expr *PossibleXLHSInSecond =
12708                       SecondBinOp->getLHS()->IgnoreParenImpCasts();
12709                   llvm::FoldingSetNodeID X1Id, X2Id;
12710                   PossibleXRHSInFirst->Profile(X1Id, Context,
12711                                                /*Canonical=*/true);
12712                   PossibleXLHSInSecond->Profile(X2Id, Context,
12713                                                 /*Canonical=*/true);
12714                   IsUpdateExprFound = X1Id == X2Id;
12715                   if (IsUpdateExprFound) {
12716                     V = FirstBinOp->getLHS();
12717                     X = SecondBinOp->getLHS();
12718                     E = SecondBinOp->getRHS();
12719                     UE = nullptr;
12720                     IsXLHSInRHSPart = false;
12721                     IsPostfixUpdate = true;
12722                   } else {
12723                     ErrorFound = NotASpecificExpression;
12724                     ErrorLoc = FirstBinOp->getExprLoc();
12725                     ErrorRange = FirstBinOp->getSourceRange();
12726                     NoteLoc = SecondBinOp->getLHS()->getExprLoc();
12727                     NoteRange = SecondBinOp->getRHS()->getSourceRange();
12728                   }
12729                 }
12730               }
12731             }
12732           }
12733         } else {
12734           NoteLoc = ErrorLoc = Body->getBeginLoc();
12735           NoteRange = ErrorRange =
12736               SourceRange(Body->getBeginLoc(), Body->getBeginLoc());
12737           ErrorFound = NotTwoSubstatements;
12738         }
12739       } else {
12740         NoteLoc = ErrorLoc = Body->getBeginLoc();
12741         NoteRange = ErrorRange =
12742             SourceRange(Body->getBeginLoc(), Body->getBeginLoc());
12743         ErrorFound = NotACompoundStatement;
12744       }
12745     }
12746     if (ErrorFound != NoError) {
12747       Diag(ErrorLoc, diag::err_omp_atomic_capture_not_compound_statement)
12748           << ErrorRange;
12749       Diag(NoteLoc, diag::note_omp_atomic_capture) << ErrorFound << NoteRange;
12750       return StmtError();
12751     }
12752     if (CurContext->isDependentContext())
12753       UE = V = E = X = nullptr;
12754   } else if (AtomicKind == OMPC_compare) {
12755     if (IsCompareCapture) {
12756       OpenMPAtomicCompareCaptureChecker::ErrorInfoTy ErrorInfo;
12757       OpenMPAtomicCompareCaptureChecker Checker(*this);
12758       if (!Checker.checkStmt(Body, ErrorInfo)) {
12759         Diag(ErrorInfo.ErrorLoc, diag::err_omp_atomic_compare_capture)
12760             << ErrorInfo.ErrorRange;
12761         Diag(ErrorInfo.NoteLoc, diag::note_omp_atomic_compare)
12762             << ErrorInfo.Error << ErrorInfo.NoteRange;
12763         return StmtError();
12764       }
12765       X = Checker.getX();
12766       E = Checker.getE();
12767       D = Checker.getD();
12768       CE = Checker.getCond();
12769       V = Checker.getV();
12770       R = Checker.getR();
12771       // We reuse IsXLHSInRHSPart to tell if it is in the form 'x ordop expr'.
12772       IsXLHSInRHSPart = Checker.isXBinopExpr();
12773       IsFailOnly = Checker.isFailOnly();
12774       IsPostfixUpdate = Checker.isPostfixUpdate();
12775     } else {
12776       OpenMPAtomicCompareChecker::ErrorInfoTy ErrorInfo;
12777       OpenMPAtomicCompareChecker Checker(*this);
12778       if (!Checker.checkStmt(Body, ErrorInfo)) {
12779         Diag(ErrorInfo.ErrorLoc, diag::err_omp_atomic_compare)
12780             << ErrorInfo.ErrorRange;
12781         Diag(ErrorInfo.NoteLoc, diag::note_omp_atomic_compare)
12782           << ErrorInfo.Error << ErrorInfo.NoteRange;
12783         return StmtError();
12784       }
12785       X = Checker.getX();
12786       E = Checker.getE();
12787       D = Checker.getD();
12788       CE = Checker.getCond();
12789       // We reuse IsXLHSInRHSPart to tell if it is in the form 'x ordop expr'.
12790       IsXLHSInRHSPart = Checker.isXBinopExpr();
12791     }
12792   }
12793 
12794   setFunctionHasBranchProtectedScope();
12795 
12796   return OMPAtomicDirective::Create(
12797       Context, StartLoc, EndLoc, Clauses, AStmt,
12798       {X, V, R, E, UE, D, CE, IsXLHSInRHSPart, IsPostfixUpdate, IsFailOnly});
12799 }
12800 
12801 StmtResult Sema::ActOnOpenMPTargetDirective(ArrayRef<OMPClause *> Clauses,
12802                                             Stmt *AStmt,
12803                                             SourceLocation StartLoc,
12804                                             SourceLocation EndLoc) {
12805   if (!AStmt)
12806     return StmtError();
12807 
12808   auto *CS = cast<CapturedStmt>(AStmt);
12809   // 1.2.2 OpenMP Language Terminology
12810   // Structured block - An executable statement with a single entry at the
12811   // top and a single exit at the bottom.
12812   // The point of exit cannot be a branch out of the structured block.
12813   // longjmp() and throw() must not violate the entry/exit criteria.
12814   CS->getCapturedDecl()->setNothrow();
12815   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target);
12816        ThisCaptureLevel > 1; --ThisCaptureLevel) {
12817     CS = cast<CapturedStmt>(CS->getCapturedStmt());
12818     // 1.2.2 OpenMP Language Terminology
12819     // Structured block - An executable statement with a single entry at the
12820     // top and a single exit at the bottom.
12821     // The point of exit cannot be a branch out of the structured block.
12822     // longjmp() and throw() must not violate the entry/exit criteria.
12823     CS->getCapturedDecl()->setNothrow();
12824   }
12825 
12826   // OpenMP [2.16, Nesting of Regions]
12827   // If specified, a teams construct must be contained within a target
12828   // construct. That target construct must contain no statements or directives
12829   // outside of the teams construct.
12830   if (DSAStack->hasInnerTeamsRegion()) {
12831     const Stmt *S = CS->IgnoreContainers(/*IgnoreCaptured=*/true);
12832     bool OMPTeamsFound = true;
12833     if (const auto *CS = dyn_cast<CompoundStmt>(S)) {
12834       auto I = CS->body_begin();
12835       while (I != CS->body_end()) {
12836         const auto *OED = dyn_cast<OMPExecutableDirective>(*I);
12837         if (!OED || !isOpenMPTeamsDirective(OED->getDirectiveKind()) ||
12838             OMPTeamsFound) {
12839 
12840           OMPTeamsFound = false;
12841           break;
12842         }
12843         ++I;
12844       }
12845       assert(I != CS->body_end() && "Not found statement");
12846       S = *I;
12847     } else {
12848       const auto *OED = dyn_cast<OMPExecutableDirective>(S);
12849       OMPTeamsFound = OED && isOpenMPTeamsDirective(OED->getDirectiveKind());
12850     }
12851     if (!OMPTeamsFound) {
12852       Diag(StartLoc, diag::err_omp_target_contains_not_only_teams);
12853       Diag(DSAStack->getInnerTeamsRegionLoc(),
12854            diag::note_omp_nested_teams_construct_here);
12855       Diag(S->getBeginLoc(), diag::note_omp_nested_statement_here)
12856           << isa<OMPExecutableDirective>(S);
12857       return StmtError();
12858     }
12859   }
12860 
12861   setFunctionHasBranchProtectedScope();
12862 
12863   return OMPTargetDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt);
12864 }
12865 
12866 StmtResult
12867 Sema::ActOnOpenMPTargetParallelDirective(ArrayRef<OMPClause *> Clauses,
12868                                          Stmt *AStmt, SourceLocation StartLoc,
12869                                          SourceLocation EndLoc) {
12870   if (!AStmt)
12871     return StmtError();
12872 
12873   auto *CS = cast<CapturedStmt>(AStmt);
12874   // 1.2.2 OpenMP Language Terminology
12875   // Structured block - An executable statement with a single entry at the
12876   // top and a single exit at the bottom.
12877   // The point of exit cannot be a branch out of the structured block.
12878   // longjmp() and throw() must not violate the entry/exit criteria.
12879   CS->getCapturedDecl()->setNothrow();
12880   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_parallel);
12881        ThisCaptureLevel > 1; --ThisCaptureLevel) {
12882     CS = cast<CapturedStmt>(CS->getCapturedStmt());
12883     // 1.2.2 OpenMP Language Terminology
12884     // Structured block - An executable statement with a single entry at the
12885     // top and a single exit at the bottom.
12886     // The point of exit cannot be a branch out of the structured block.
12887     // longjmp() and throw() must not violate the entry/exit criteria.
12888     CS->getCapturedDecl()->setNothrow();
12889   }
12890 
12891   setFunctionHasBranchProtectedScope();
12892 
12893   return OMPTargetParallelDirective::Create(
12894       Context, StartLoc, EndLoc, Clauses, AStmt,
12895       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
12896 }
12897 
12898 StmtResult Sema::ActOnOpenMPTargetParallelForDirective(
12899     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
12900     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
12901   if (!AStmt)
12902     return StmtError();
12903 
12904   auto *CS = cast<CapturedStmt>(AStmt);
12905   // 1.2.2 OpenMP Language Terminology
12906   // Structured block - An executable statement with a single entry at the
12907   // top and a single exit at the bottom.
12908   // The point of exit cannot be a branch out of the structured block.
12909   // longjmp() and throw() must not violate the entry/exit criteria.
12910   CS->getCapturedDecl()->setNothrow();
12911   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_parallel_for);
12912        ThisCaptureLevel > 1; --ThisCaptureLevel) {
12913     CS = cast<CapturedStmt>(CS->getCapturedStmt());
12914     // 1.2.2 OpenMP Language Terminology
12915     // Structured block - An executable statement with a single entry at the
12916     // top and a single exit at the bottom.
12917     // The point of exit cannot be a branch out of the structured block.
12918     // longjmp() and throw() must not violate the entry/exit criteria.
12919     CS->getCapturedDecl()->setNothrow();
12920   }
12921 
12922   OMPLoopBasedDirective::HelperExprs B;
12923   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
12924   // define the nested loops number.
12925   unsigned NestedLoopCount =
12926       checkOpenMPLoop(OMPD_target_parallel_for, getCollapseNumberExpr(Clauses),
12927                       getOrderedNumberExpr(Clauses), CS, *this, *DSAStack,
12928                       VarsWithImplicitDSA, B);
12929   if (NestedLoopCount == 0)
12930     return StmtError();
12931 
12932   assert((CurContext->isDependentContext() || B.builtAll()) &&
12933          "omp target parallel for loop exprs were not built");
12934 
12935   if (!CurContext->isDependentContext()) {
12936     // Finalize the clauses that need pre-built expressions for CodeGen.
12937     for (OMPClause *C : Clauses) {
12938       if (auto *LC = dyn_cast<OMPLinearClause>(C))
12939         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
12940                                      B.NumIterations, *this, CurScope,
12941                                      DSAStack))
12942           return StmtError();
12943     }
12944   }
12945 
12946   setFunctionHasBranchProtectedScope();
12947   return OMPTargetParallelForDirective::Create(
12948       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
12949       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
12950 }
12951 
12952 /// Check for existence of a map clause in the list of clauses.
12953 static bool hasClauses(ArrayRef<OMPClause *> Clauses,
12954                        const OpenMPClauseKind K) {
12955   return llvm::any_of(
12956       Clauses, [K](const OMPClause *C) { return C->getClauseKind() == K; });
12957 }
12958 
12959 template <typename... Params>
12960 static bool hasClauses(ArrayRef<OMPClause *> Clauses, const OpenMPClauseKind K,
12961                        const Params... ClauseTypes) {
12962   return hasClauses(Clauses, K) || hasClauses(Clauses, ClauseTypes...);
12963 }
12964 
12965 /// Check if the variables in the mapping clause are externally visible.
12966 static bool isClauseMappable(ArrayRef<OMPClause *> Clauses) {
12967   for (const OMPClause *C : Clauses) {
12968     if (auto *TC = dyn_cast<OMPToClause>(C))
12969       return llvm::all_of(TC->all_decls(), [](ValueDecl *VD) {
12970         return !VD || !VD->hasAttr<OMPDeclareTargetDeclAttr>() ||
12971                (VD->isExternallyVisible() &&
12972                 VD->getVisibility() != HiddenVisibility);
12973       });
12974     else if (auto *FC = dyn_cast<OMPFromClause>(C))
12975       return llvm::all_of(FC->all_decls(), [](ValueDecl *VD) {
12976         return !VD || !VD->hasAttr<OMPDeclareTargetDeclAttr>() ||
12977                (VD->isExternallyVisible() &&
12978                 VD->getVisibility() != HiddenVisibility);
12979       });
12980   }
12981 
12982   return true;
12983 }
12984 
12985 StmtResult Sema::ActOnOpenMPTargetDataDirective(ArrayRef<OMPClause *> Clauses,
12986                                                 Stmt *AStmt,
12987                                                 SourceLocation StartLoc,
12988                                                 SourceLocation EndLoc) {
12989   if (!AStmt)
12990     return StmtError();
12991 
12992   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
12993 
12994   // OpenMP [2.12.2, target data Construct, Restrictions]
12995   // At least one map, use_device_addr or use_device_ptr clause must appear on
12996   // the directive.
12997   if (!hasClauses(Clauses, OMPC_map, OMPC_use_device_ptr) &&
12998       (LangOpts.OpenMP < 50 || !hasClauses(Clauses, OMPC_use_device_addr))) {
12999     StringRef Expected;
13000     if (LangOpts.OpenMP < 50)
13001       Expected = "'map' or 'use_device_ptr'";
13002     else
13003       Expected = "'map', 'use_device_ptr', or 'use_device_addr'";
13004     Diag(StartLoc, diag::err_omp_no_clause_for_directive)
13005         << Expected << getOpenMPDirectiveName(OMPD_target_data);
13006     return StmtError();
13007   }
13008 
13009   setFunctionHasBranchProtectedScope();
13010 
13011   return OMPTargetDataDirective::Create(Context, StartLoc, EndLoc, Clauses,
13012                                         AStmt);
13013 }
13014 
13015 StmtResult
13016 Sema::ActOnOpenMPTargetEnterDataDirective(ArrayRef<OMPClause *> Clauses,
13017                                           SourceLocation StartLoc,
13018                                           SourceLocation EndLoc, Stmt *AStmt) {
13019   if (!AStmt)
13020     return StmtError();
13021 
13022   auto *CS = cast<CapturedStmt>(AStmt);
13023   // 1.2.2 OpenMP Language Terminology
13024   // Structured block - An executable statement with a single entry at the
13025   // top and a single exit at the bottom.
13026   // The point of exit cannot be a branch out of the structured block.
13027   // longjmp() and throw() must not violate the entry/exit criteria.
13028   CS->getCapturedDecl()->setNothrow();
13029   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_enter_data);
13030        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13031     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13032     // 1.2.2 OpenMP Language Terminology
13033     // Structured block - An executable statement with a single entry at the
13034     // top and a single exit at the bottom.
13035     // The point of exit cannot be a branch out of the structured block.
13036     // longjmp() and throw() must not violate the entry/exit criteria.
13037     CS->getCapturedDecl()->setNothrow();
13038   }
13039 
13040   // OpenMP [2.10.2, Restrictions, p. 99]
13041   // At least one map clause must appear on the directive.
13042   if (!hasClauses(Clauses, OMPC_map)) {
13043     Diag(StartLoc, diag::err_omp_no_clause_for_directive)
13044         << "'map'" << getOpenMPDirectiveName(OMPD_target_enter_data);
13045     return StmtError();
13046   }
13047 
13048   return OMPTargetEnterDataDirective::Create(Context, StartLoc, EndLoc, Clauses,
13049                                              AStmt);
13050 }
13051 
13052 StmtResult
13053 Sema::ActOnOpenMPTargetExitDataDirective(ArrayRef<OMPClause *> Clauses,
13054                                          SourceLocation StartLoc,
13055                                          SourceLocation EndLoc, Stmt *AStmt) {
13056   if (!AStmt)
13057     return StmtError();
13058 
13059   auto *CS = cast<CapturedStmt>(AStmt);
13060   // 1.2.2 OpenMP Language Terminology
13061   // Structured block - An executable statement with a single entry at the
13062   // top and a single exit at the bottom.
13063   // The point of exit cannot be a branch out of the structured block.
13064   // longjmp() and throw() must not violate the entry/exit criteria.
13065   CS->getCapturedDecl()->setNothrow();
13066   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_exit_data);
13067        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13068     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13069     // 1.2.2 OpenMP Language Terminology
13070     // Structured block - An executable statement with a single entry at the
13071     // top and a single exit at the bottom.
13072     // The point of exit cannot be a branch out of the structured block.
13073     // longjmp() and throw() must not violate the entry/exit criteria.
13074     CS->getCapturedDecl()->setNothrow();
13075   }
13076 
13077   // OpenMP [2.10.3, Restrictions, p. 102]
13078   // At least one map clause must appear on the directive.
13079   if (!hasClauses(Clauses, OMPC_map)) {
13080     Diag(StartLoc, diag::err_omp_no_clause_for_directive)
13081         << "'map'" << getOpenMPDirectiveName(OMPD_target_exit_data);
13082     return StmtError();
13083   }
13084 
13085   return OMPTargetExitDataDirective::Create(Context, StartLoc, EndLoc, Clauses,
13086                                             AStmt);
13087 }
13088 
13089 StmtResult Sema::ActOnOpenMPTargetUpdateDirective(ArrayRef<OMPClause *> Clauses,
13090                                                   SourceLocation StartLoc,
13091                                                   SourceLocation EndLoc,
13092                                                   Stmt *AStmt) {
13093   if (!AStmt)
13094     return StmtError();
13095 
13096   auto *CS = cast<CapturedStmt>(AStmt);
13097   // 1.2.2 OpenMP Language Terminology
13098   // Structured block - An executable statement with a single entry at the
13099   // top and a single exit at the bottom.
13100   // The point of exit cannot be a branch out of the structured block.
13101   // longjmp() and throw() must not violate the entry/exit criteria.
13102   CS->getCapturedDecl()->setNothrow();
13103   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_update);
13104        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13105     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13106     // 1.2.2 OpenMP Language Terminology
13107     // Structured block - An executable statement with a single entry at the
13108     // top and a single exit at the bottom.
13109     // The point of exit cannot be a branch out of the structured block.
13110     // longjmp() and throw() must not violate the entry/exit criteria.
13111     CS->getCapturedDecl()->setNothrow();
13112   }
13113 
13114   if (!hasClauses(Clauses, OMPC_to, OMPC_from)) {
13115     Diag(StartLoc, diag::err_omp_at_least_one_motion_clause_required);
13116     return StmtError();
13117   }
13118 
13119   if (!isClauseMappable(Clauses)) {
13120     Diag(StartLoc, diag::err_omp_cannot_update_with_internal_linkage);
13121     return StmtError();
13122   }
13123 
13124   return OMPTargetUpdateDirective::Create(Context, StartLoc, EndLoc, Clauses,
13125                                           AStmt);
13126 }
13127 
13128 StmtResult Sema::ActOnOpenMPTeamsDirective(ArrayRef<OMPClause *> Clauses,
13129                                            Stmt *AStmt, SourceLocation StartLoc,
13130                                            SourceLocation EndLoc) {
13131   if (!AStmt)
13132     return StmtError();
13133 
13134   auto *CS = cast<CapturedStmt>(AStmt);
13135   // 1.2.2 OpenMP Language Terminology
13136   // Structured block - An executable statement with a single entry at the
13137   // top and a single exit at the bottom.
13138   // The point of exit cannot be a branch out of the structured block.
13139   // longjmp() and throw() must not violate the entry/exit criteria.
13140   CS->getCapturedDecl()->setNothrow();
13141 
13142   setFunctionHasBranchProtectedScope();
13143 
13144   DSAStack->setParentTeamsRegionLoc(StartLoc);
13145 
13146   return OMPTeamsDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt);
13147 }
13148 
13149 StmtResult
13150 Sema::ActOnOpenMPCancellationPointDirective(SourceLocation StartLoc,
13151                                             SourceLocation EndLoc,
13152                                             OpenMPDirectiveKind CancelRegion) {
13153   if (DSAStack->isParentNowaitRegion()) {
13154     Diag(StartLoc, diag::err_omp_parent_cancel_region_nowait) << 0;
13155     return StmtError();
13156   }
13157   if (DSAStack->isParentOrderedRegion()) {
13158     Diag(StartLoc, diag::err_omp_parent_cancel_region_ordered) << 0;
13159     return StmtError();
13160   }
13161   return OMPCancellationPointDirective::Create(Context, StartLoc, EndLoc,
13162                                                CancelRegion);
13163 }
13164 
13165 StmtResult Sema::ActOnOpenMPCancelDirective(ArrayRef<OMPClause *> Clauses,
13166                                             SourceLocation StartLoc,
13167                                             SourceLocation EndLoc,
13168                                             OpenMPDirectiveKind CancelRegion) {
13169   if (DSAStack->isParentNowaitRegion()) {
13170     Diag(StartLoc, diag::err_omp_parent_cancel_region_nowait) << 1;
13171     return StmtError();
13172   }
13173   if (DSAStack->isParentOrderedRegion()) {
13174     Diag(StartLoc, diag::err_omp_parent_cancel_region_ordered) << 1;
13175     return StmtError();
13176   }
13177   DSAStack->setParentCancelRegion(/*Cancel=*/true);
13178   return OMPCancelDirective::Create(Context, StartLoc, EndLoc, Clauses,
13179                                     CancelRegion);
13180 }
13181 
13182 static bool checkReductionClauseWithNogroup(Sema &S,
13183                                             ArrayRef<OMPClause *> Clauses) {
13184   const OMPClause *ReductionClause = nullptr;
13185   const OMPClause *NogroupClause = nullptr;
13186   for (const OMPClause *C : Clauses) {
13187     if (C->getClauseKind() == OMPC_reduction) {
13188       ReductionClause = C;
13189       if (NogroupClause)
13190         break;
13191       continue;
13192     }
13193     if (C->getClauseKind() == OMPC_nogroup) {
13194       NogroupClause = C;
13195       if (ReductionClause)
13196         break;
13197       continue;
13198     }
13199   }
13200   if (ReductionClause && NogroupClause) {
13201     S.Diag(ReductionClause->getBeginLoc(), diag::err_omp_reduction_with_nogroup)
13202         << SourceRange(NogroupClause->getBeginLoc(),
13203                        NogroupClause->getEndLoc());
13204     return true;
13205   }
13206   return false;
13207 }
13208 
13209 StmtResult Sema::ActOnOpenMPTaskLoopDirective(
13210     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13211     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13212   if (!AStmt)
13213     return StmtError();
13214 
13215   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13216   OMPLoopBasedDirective::HelperExprs B;
13217   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13218   // define the nested loops number.
13219   unsigned NestedLoopCount =
13220       checkOpenMPLoop(OMPD_taskloop, getCollapseNumberExpr(Clauses),
13221                       /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack,
13222                       VarsWithImplicitDSA, B);
13223   if (NestedLoopCount == 0)
13224     return StmtError();
13225 
13226   assert((CurContext->isDependentContext() || B.builtAll()) &&
13227          "omp for loop exprs were not built");
13228 
13229   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13230   // The grainsize clause and num_tasks clause are mutually exclusive and may
13231   // not appear on the same taskloop directive.
13232   if (checkMutuallyExclusiveClauses(*this, Clauses,
13233                                     {OMPC_grainsize, OMPC_num_tasks}))
13234     return StmtError();
13235   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13236   // If a reduction clause is present on the taskloop directive, the nogroup
13237   // clause must not be specified.
13238   if (checkReductionClauseWithNogroup(*this, Clauses))
13239     return StmtError();
13240 
13241   setFunctionHasBranchProtectedScope();
13242   return OMPTaskLoopDirective::Create(Context, StartLoc, EndLoc,
13243                                       NestedLoopCount, Clauses, AStmt, B,
13244                                       DSAStack->isCancelRegion());
13245 }
13246 
13247 StmtResult Sema::ActOnOpenMPTaskLoopSimdDirective(
13248     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13249     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13250   if (!AStmt)
13251     return StmtError();
13252 
13253   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13254   OMPLoopBasedDirective::HelperExprs B;
13255   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13256   // define the nested loops number.
13257   unsigned NestedLoopCount =
13258       checkOpenMPLoop(OMPD_taskloop_simd, getCollapseNumberExpr(Clauses),
13259                       /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack,
13260                       VarsWithImplicitDSA, B);
13261   if (NestedLoopCount == 0)
13262     return StmtError();
13263 
13264   assert((CurContext->isDependentContext() || B.builtAll()) &&
13265          "omp for loop exprs were not built");
13266 
13267   if (!CurContext->isDependentContext()) {
13268     // Finalize the clauses that need pre-built expressions for CodeGen.
13269     for (OMPClause *C : Clauses) {
13270       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13271         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13272                                      B.NumIterations, *this, CurScope,
13273                                      DSAStack))
13274           return StmtError();
13275     }
13276   }
13277 
13278   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13279   // The grainsize clause and num_tasks clause are mutually exclusive and may
13280   // not appear on the same taskloop directive.
13281   if (checkMutuallyExclusiveClauses(*this, Clauses,
13282                                     {OMPC_grainsize, OMPC_num_tasks}))
13283     return StmtError();
13284   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13285   // If a reduction clause is present on the taskloop directive, the nogroup
13286   // clause must not be specified.
13287   if (checkReductionClauseWithNogroup(*this, Clauses))
13288     return StmtError();
13289   if (checkSimdlenSafelenSpecified(*this, Clauses))
13290     return StmtError();
13291 
13292   setFunctionHasBranchProtectedScope();
13293   return OMPTaskLoopSimdDirective::Create(Context, StartLoc, EndLoc,
13294                                           NestedLoopCount, Clauses, AStmt, B);
13295 }
13296 
13297 StmtResult Sema::ActOnOpenMPMasterTaskLoopDirective(
13298     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13299     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13300   if (!AStmt)
13301     return StmtError();
13302 
13303   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13304   OMPLoopBasedDirective::HelperExprs B;
13305   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13306   // define the nested loops number.
13307   unsigned NestedLoopCount =
13308       checkOpenMPLoop(OMPD_master_taskloop, getCollapseNumberExpr(Clauses),
13309                       /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack,
13310                       VarsWithImplicitDSA, B);
13311   if (NestedLoopCount == 0)
13312     return StmtError();
13313 
13314   assert((CurContext->isDependentContext() || B.builtAll()) &&
13315          "omp for loop exprs were not built");
13316 
13317   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13318   // The grainsize clause and num_tasks clause are mutually exclusive and may
13319   // not appear on the same taskloop directive.
13320   if (checkMutuallyExclusiveClauses(*this, Clauses,
13321                                     {OMPC_grainsize, OMPC_num_tasks}))
13322     return StmtError();
13323   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13324   // If a reduction clause is present on the taskloop directive, the nogroup
13325   // clause must not be specified.
13326   if (checkReductionClauseWithNogroup(*this, Clauses))
13327     return StmtError();
13328 
13329   setFunctionHasBranchProtectedScope();
13330   return OMPMasterTaskLoopDirective::Create(Context, StartLoc, EndLoc,
13331                                             NestedLoopCount, Clauses, AStmt, B,
13332                                             DSAStack->isCancelRegion());
13333 }
13334 
13335 StmtResult Sema::ActOnOpenMPMaskedTaskLoopDirective(
13336     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13337     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13338   if (!AStmt)
13339     return StmtError();
13340 
13341   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13342   OMPLoopBasedDirective::HelperExprs B;
13343   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13344   // define the nested loops number.
13345   unsigned NestedLoopCount =
13346       checkOpenMPLoop(OMPD_masked_taskloop, getCollapseNumberExpr(Clauses),
13347                       /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack,
13348                       VarsWithImplicitDSA, B);
13349   if (NestedLoopCount == 0)
13350     return StmtError();
13351 
13352   assert((CurContext->isDependentContext() || B.builtAll()) &&
13353          "omp for loop exprs were not built");
13354 
13355   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13356   // The grainsize clause and num_tasks clause are mutually exclusive and may
13357   // not appear on the same taskloop directive.
13358   if (checkMutuallyExclusiveClauses(*this, Clauses,
13359                                     {OMPC_grainsize, OMPC_num_tasks}))
13360     return StmtError();
13361   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13362   // If a reduction clause is present on the taskloop directive, the nogroup
13363   // clause must not be specified.
13364   if (checkReductionClauseWithNogroup(*this, Clauses))
13365     return StmtError();
13366 
13367   setFunctionHasBranchProtectedScope();
13368   return OMPMaskedTaskLoopDirective::Create(Context, StartLoc, EndLoc,
13369                                             NestedLoopCount, Clauses, AStmt, B,
13370                                             DSAStack->isCancelRegion());
13371 }
13372 
13373 StmtResult Sema::ActOnOpenMPMasterTaskLoopSimdDirective(
13374     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13375     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13376   if (!AStmt)
13377     return StmtError();
13378 
13379   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13380   OMPLoopBasedDirective::HelperExprs B;
13381   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13382   // define the nested loops number.
13383   unsigned NestedLoopCount =
13384       checkOpenMPLoop(OMPD_master_taskloop_simd, getCollapseNumberExpr(Clauses),
13385                       /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack,
13386                       VarsWithImplicitDSA, B);
13387   if (NestedLoopCount == 0)
13388     return StmtError();
13389 
13390   assert((CurContext->isDependentContext() || B.builtAll()) &&
13391          "omp for loop exprs were not built");
13392 
13393   if (!CurContext->isDependentContext()) {
13394     // Finalize the clauses that need pre-built expressions for CodeGen.
13395     for (OMPClause *C : Clauses) {
13396       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13397         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13398                                      B.NumIterations, *this, CurScope,
13399                                      DSAStack))
13400           return StmtError();
13401     }
13402   }
13403 
13404   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13405   // The grainsize clause and num_tasks clause are mutually exclusive and may
13406   // not appear on the same taskloop directive.
13407   if (checkMutuallyExclusiveClauses(*this, Clauses,
13408                                     {OMPC_grainsize, OMPC_num_tasks}))
13409     return StmtError();
13410   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13411   // If a reduction clause is present on the taskloop directive, the nogroup
13412   // clause must not be specified.
13413   if (checkReductionClauseWithNogroup(*this, Clauses))
13414     return StmtError();
13415   if (checkSimdlenSafelenSpecified(*this, Clauses))
13416     return StmtError();
13417 
13418   setFunctionHasBranchProtectedScope();
13419   return OMPMasterTaskLoopSimdDirective::Create(
13420       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
13421 }
13422 
13423 StmtResult Sema::ActOnOpenMPMaskedTaskLoopSimdDirective(
13424     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13425     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13426   if (!AStmt)
13427     return StmtError();
13428 
13429   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13430   OMPLoopBasedDirective::HelperExprs B;
13431   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13432   // define the nested loops number.
13433   unsigned NestedLoopCount =
13434       checkOpenMPLoop(OMPD_masked_taskloop_simd, getCollapseNumberExpr(Clauses),
13435                       /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack,
13436                       VarsWithImplicitDSA, B);
13437   if (NestedLoopCount == 0)
13438     return StmtError();
13439 
13440   assert((CurContext->isDependentContext() || B.builtAll()) &&
13441          "omp for loop exprs were not built");
13442 
13443   if (!CurContext->isDependentContext()) {
13444     // Finalize the clauses that need pre-built expressions for CodeGen.
13445     for (OMPClause *C : Clauses) {
13446       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13447         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13448                                      B.NumIterations, *this, CurScope,
13449                                      DSAStack))
13450           return StmtError();
13451     }
13452   }
13453 
13454   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13455   // The grainsize clause and num_tasks clause are mutually exclusive and may
13456   // not appear on the same taskloop directive.
13457   if (checkMutuallyExclusiveClauses(*this, Clauses,
13458                                     {OMPC_grainsize, OMPC_num_tasks}))
13459     return StmtError();
13460   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13461   // If a reduction clause is present on the taskloop directive, the nogroup
13462   // clause must not be specified.
13463   if (checkReductionClauseWithNogroup(*this, Clauses))
13464     return StmtError();
13465   if (checkSimdlenSafelenSpecified(*this, Clauses))
13466     return StmtError();
13467 
13468   setFunctionHasBranchProtectedScope();
13469   return OMPMaskedTaskLoopSimdDirective::Create(
13470       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
13471 }
13472 
13473 StmtResult Sema::ActOnOpenMPParallelMasterTaskLoopDirective(
13474     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13475     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13476   if (!AStmt)
13477     return StmtError();
13478 
13479   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13480   auto *CS = cast<CapturedStmt>(AStmt);
13481   // 1.2.2 OpenMP Language Terminology
13482   // Structured block - An executable statement with a single entry at the
13483   // top and a single exit at the bottom.
13484   // The point of exit cannot be a branch out of the structured block.
13485   // longjmp() and throw() must not violate the entry/exit criteria.
13486   CS->getCapturedDecl()->setNothrow();
13487   for (int ThisCaptureLevel =
13488            getOpenMPCaptureLevels(OMPD_parallel_master_taskloop);
13489        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13490     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13491     // 1.2.2 OpenMP Language Terminology
13492     // Structured block - An executable statement with a single entry at the
13493     // top and a single exit at the bottom.
13494     // The point of exit cannot be a branch out of the structured block.
13495     // longjmp() and throw() must not violate the entry/exit criteria.
13496     CS->getCapturedDecl()->setNothrow();
13497   }
13498 
13499   OMPLoopBasedDirective::HelperExprs B;
13500   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13501   // define the nested loops number.
13502   unsigned NestedLoopCount = checkOpenMPLoop(
13503       OMPD_parallel_master_taskloop, getCollapseNumberExpr(Clauses),
13504       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
13505       VarsWithImplicitDSA, B);
13506   if (NestedLoopCount == 0)
13507     return StmtError();
13508 
13509   assert((CurContext->isDependentContext() || B.builtAll()) &&
13510          "omp for loop exprs were not built");
13511 
13512   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13513   // The grainsize clause and num_tasks clause are mutually exclusive and may
13514   // not appear on the same taskloop directive.
13515   if (checkMutuallyExclusiveClauses(*this, Clauses,
13516                                     {OMPC_grainsize, OMPC_num_tasks}))
13517     return StmtError();
13518   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13519   // If a reduction clause is present on the taskloop directive, the nogroup
13520   // clause must not be specified.
13521   if (checkReductionClauseWithNogroup(*this, Clauses))
13522     return StmtError();
13523 
13524   setFunctionHasBranchProtectedScope();
13525   return OMPParallelMasterTaskLoopDirective::Create(
13526       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
13527       DSAStack->isCancelRegion());
13528 }
13529 
13530 StmtResult Sema::ActOnOpenMPParallelMaskedTaskLoopDirective(
13531     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13532     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13533   if (!AStmt)
13534     return StmtError();
13535 
13536   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13537   auto *CS = cast<CapturedStmt>(AStmt);
13538   // 1.2.2 OpenMP Language Terminology
13539   // Structured block - An executable statement with a single entry at the
13540   // top and a single exit at the bottom.
13541   // The point of exit cannot be a branch out of the structured block.
13542   // longjmp() and throw() must not violate the entry/exit criteria.
13543   CS->getCapturedDecl()->setNothrow();
13544   for (int ThisCaptureLevel =
13545            getOpenMPCaptureLevels(OMPD_parallel_masked_taskloop);
13546        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13547     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13548     // 1.2.2 OpenMP Language Terminology
13549     // Structured block - An executable statement with a single entry at the
13550     // top and a single exit at the bottom.
13551     // The point of exit cannot be a branch out of the structured block.
13552     // longjmp() and throw() must not violate the entry/exit criteria.
13553     CS->getCapturedDecl()->setNothrow();
13554   }
13555 
13556   OMPLoopBasedDirective::HelperExprs B;
13557   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13558   // define the nested loops number.
13559   unsigned NestedLoopCount = checkOpenMPLoop(
13560       OMPD_parallel_masked_taskloop, getCollapseNumberExpr(Clauses),
13561       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
13562       VarsWithImplicitDSA, B);
13563   if (NestedLoopCount == 0)
13564     return StmtError();
13565 
13566   assert((CurContext->isDependentContext() || B.builtAll()) &&
13567          "omp for loop exprs were not built");
13568 
13569   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13570   // The grainsize clause and num_tasks clause are mutually exclusive and may
13571   // not appear on the same taskloop directive.
13572   if (checkMutuallyExclusiveClauses(*this, Clauses,
13573                                     {OMPC_grainsize, OMPC_num_tasks}))
13574     return StmtError();
13575   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13576   // If a reduction clause is present on the taskloop directive, the nogroup
13577   // clause must not be specified.
13578   if (checkReductionClauseWithNogroup(*this, Clauses))
13579     return StmtError();
13580 
13581   setFunctionHasBranchProtectedScope();
13582   return OMPParallelMaskedTaskLoopDirective::Create(
13583       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
13584       DSAStack->isCancelRegion());
13585 }
13586 
13587 StmtResult Sema::ActOnOpenMPParallelMasterTaskLoopSimdDirective(
13588     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13589     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13590   if (!AStmt)
13591     return StmtError();
13592 
13593   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13594   auto *CS = cast<CapturedStmt>(AStmt);
13595   // 1.2.2 OpenMP Language Terminology
13596   // Structured block - An executable statement with a single entry at the
13597   // top and a single exit at the bottom.
13598   // The point of exit cannot be a branch out of the structured block.
13599   // longjmp() and throw() must not violate the entry/exit criteria.
13600   CS->getCapturedDecl()->setNothrow();
13601   for (int ThisCaptureLevel =
13602            getOpenMPCaptureLevels(OMPD_parallel_master_taskloop_simd);
13603        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13604     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13605     // 1.2.2 OpenMP Language Terminology
13606     // Structured block - An executable statement with a single entry at the
13607     // top and a single exit at the bottom.
13608     // The point of exit cannot be a branch out of the structured block.
13609     // longjmp() and throw() must not violate the entry/exit criteria.
13610     CS->getCapturedDecl()->setNothrow();
13611   }
13612 
13613   OMPLoopBasedDirective::HelperExprs B;
13614   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13615   // define the nested loops number.
13616   unsigned NestedLoopCount = checkOpenMPLoop(
13617       OMPD_parallel_master_taskloop_simd, getCollapseNumberExpr(Clauses),
13618       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
13619       VarsWithImplicitDSA, B);
13620   if (NestedLoopCount == 0)
13621     return StmtError();
13622 
13623   assert((CurContext->isDependentContext() || B.builtAll()) &&
13624          "omp for loop exprs were not built");
13625 
13626   if (!CurContext->isDependentContext()) {
13627     // Finalize the clauses that need pre-built expressions for CodeGen.
13628     for (OMPClause *C : Clauses) {
13629       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13630         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13631                                      B.NumIterations, *this, CurScope,
13632                                      DSAStack))
13633           return StmtError();
13634     }
13635   }
13636 
13637   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13638   // The grainsize clause and num_tasks clause are mutually exclusive and may
13639   // not appear on the same taskloop directive.
13640   if (checkMutuallyExclusiveClauses(*this, Clauses,
13641                                     {OMPC_grainsize, OMPC_num_tasks}))
13642     return StmtError();
13643   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13644   // If a reduction clause is present on the taskloop directive, the nogroup
13645   // clause must not be specified.
13646   if (checkReductionClauseWithNogroup(*this, Clauses))
13647     return StmtError();
13648   if (checkSimdlenSafelenSpecified(*this, Clauses))
13649     return StmtError();
13650 
13651   setFunctionHasBranchProtectedScope();
13652   return OMPParallelMasterTaskLoopSimdDirective::Create(
13653       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
13654 }
13655 
13656 StmtResult Sema::ActOnOpenMPParallelMaskedTaskLoopSimdDirective(
13657     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13658     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13659   if (!AStmt)
13660     return StmtError();
13661 
13662   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13663   auto *CS = cast<CapturedStmt>(AStmt);
13664   // 1.2.2 OpenMP Language Terminology
13665   // Structured block - An executable statement with a single entry at the
13666   // top and a single exit at the bottom.
13667   // The point of exit cannot be a branch out of the structured block.
13668   // longjmp() and throw() must not violate the entry/exit criteria.
13669   CS->getCapturedDecl()->setNothrow();
13670   for (int ThisCaptureLevel =
13671            getOpenMPCaptureLevels(OMPD_parallel_masked_taskloop_simd);
13672        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13673     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13674     // 1.2.2 OpenMP Language Terminology
13675     // Structured block - An executable statement with a single entry at the
13676     // top and a single exit at the bottom.
13677     // The point of exit cannot be a branch out of the structured block.
13678     // longjmp() and throw() must not violate the entry/exit criteria.
13679     CS->getCapturedDecl()->setNothrow();
13680   }
13681 
13682   OMPLoopBasedDirective::HelperExprs B;
13683   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13684   // define the nested loops number.
13685   unsigned NestedLoopCount = checkOpenMPLoop(
13686       OMPD_parallel_masked_taskloop_simd, getCollapseNumberExpr(Clauses),
13687       /*OrderedLoopCountExpr=*/nullptr, CS, *this, *DSAStack,
13688       VarsWithImplicitDSA, B);
13689   if (NestedLoopCount == 0)
13690     return StmtError();
13691 
13692   assert((CurContext->isDependentContext() || B.builtAll()) &&
13693          "omp for loop exprs were not built");
13694 
13695   if (!CurContext->isDependentContext()) {
13696     // Finalize the clauses that need pre-built expressions for CodeGen.
13697     for (OMPClause *C : Clauses) {
13698       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13699         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13700                                      B.NumIterations, *this, CurScope,
13701                                      DSAStack))
13702           return StmtError();
13703     }
13704   }
13705 
13706   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13707   // The grainsize clause and num_tasks clause are mutually exclusive and may
13708   // not appear on the same taskloop directive.
13709   if (checkMutuallyExclusiveClauses(*this, Clauses,
13710                                     {OMPC_grainsize, OMPC_num_tasks}))
13711     return StmtError();
13712   // OpenMP, [2.9.2 taskloop Construct, Restrictions]
13713   // If a reduction clause is present on the taskloop directive, the nogroup
13714   // clause must not be specified.
13715   if (checkReductionClauseWithNogroup(*this, Clauses))
13716     return StmtError();
13717   if (checkSimdlenSafelenSpecified(*this, Clauses))
13718     return StmtError();
13719 
13720   setFunctionHasBranchProtectedScope();
13721   return OMPParallelMaskedTaskLoopSimdDirective::Create(
13722       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
13723 }
13724 
13725 StmtResult Sema::ActOnOpenMPDistributeDirective(
13726     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13727     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13728   if (!AStmt)
13729     return StmtError();
13730 
13731   assert(isa<CapturedStmt>(AStmt) && "Captured statement expected");
13732   OMPLoopBasedDirective::HelperExprs B;
13733   // In presence of clause 'collapse' with number of loops, it will
13734   // define the nested loops number.
13735   unsigned NestedLoopCount =
13736       checkOpenMPLoop(OMPD_distribute, getCollapseNumberExpr(Clauses),
13737                       nullptr /*ordered not a clause on distribute*/, AStmt,
13738                       *this, *DSAStack, VarsWithImplicitDSA, B);
13739   if (NestedLoopCount == 0)
13740     return StmtError();
13741 
13742   assert((CurContext->isDependentContext() || B.builtAll()) &&
13743          "omp for loop exprs were not built");
13744 
13745   setFunctionHasBranchProtectedScope();
13746   return OMPDistributeDirective::Create(Context, StartLoc, EndLoc,
13747                                         NestedLoopCount, Clauses, AStmt, B);
13748 }
13749 
13750 StmtResult Sema::ActOnOpenMPDistributeParallelForDirective(
13751     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13752     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13753   if (!AStmt)
13754     return StmtError();
13755 
13756   auto *CS = cast<CapturedStmt>(AStmt);
13757   // 1.2.2 OpenMP Language Terminology
13758   // Structured block - An executable statement with a single entry at the
13759   // top and a single exit at the bottom.
13760   // The point of exit cannot be a branch out of the structured block.
13761   // longjmp() and throw() must not violate the entry/exit criteria.
13762   CS->getCapturedDecl()->setNothrow();
13763   for (int ThisCaptureLevel =
13764            getOpenMPCaptureLevels(OMPD_distribute_parallel_for);
13765        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13766     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13767     // 1.2.2 OpenMP Language Terminology
13768     // Structured block - An executable statement with a single entry at the
13769     // top and a single exit at the bottom.
13770     // The point of exit cannot be a branch out of the structured block.
13771     // longjmp() and throw() must not violate the entry/exit criteria.
13772     CS->getCapturedDecl()->setNothrow();
13773   }
13774 
13775   OMPLoopBasedDirective::HelperExprs B;
13776   // In presence of clause 'collapse' with number of loops, it will
13777   // define the nested loops number.
13778   unsigned NestedLoopCount = checkOpenMPLoop(
13779       OMPD_distribute_parallel_for, getCollapseNumberExpr(Clauses),
13780       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
13781       VarsWithImplicitDSA, B);
13782   if (NestedLoopCount == 0)
13783     return StmtError();
13784 
13785   assert((CurContext->isDependentContext() || B.builtAll()) &&
13786          "omp for loop exprs were not built");
13787 
13788   setFunctionHasBranchProtectedScope();
13789   return OMPDistributeParallelForDirective::Create(
13790       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
13791       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
13792 }
13793 
13794 StmtResult Sema::ActOnOpenMPDistributeParallelForSimdDirective(
13795     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13796     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13797   if (!AStmt)
13798     return StmtError();
13799 
13800   auto *CS = cast<CapturedStmt>(AStmt);
13801   // 1.2.2 OpenMP Language Terminology
13802   // Structured block - An executable statement with a single entry at the
13803   // top and a single exit at the bottom.
13804   // The point of exit cannot be a branch out of the structured block.
13805   // longjmp() and throw() must not violate the entry/exit criteria.
13806   CS->getCapturedDecl()->setNothrow();
13807   for (int ThisCaptureLevel =
13808            getOpenMPCaptureLevels(OMPD_distribute_parallel_for_simd);
13809        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13810     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13811     // 1.2.2 OpenMP Language Terminology
13812     // Structured block - An executable statement with a single entry at the
13813     // top and a single exit at the bottom.
13814     // The point of exit cannot be a branch out of the structured block.
13815     // longjmp() and throw() must not violate the entry/exit criteria.
13816     CS->getCapturedDecl()->setNothrow();
13817   }
13818 
13819   OMPLoopBasedDirective::HelperExprs B;
13820   // In presence of clause 'collapse' with number of loops, it will
13821   // define the nested loops number.
13822   unsigned NestedLoopCount = checkOpenMPLoop(
13823       OMPD_distribute_parallel_for_simd, getCollapseNumberExpr(Clauses),
13824       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
13825       VarsWithImplicitDSA, B);
13826   if (NestedLoopCount == 0)
13827     return StmtError();
13828 
13829   assert((CurContext->isDependentContext() || B.builtAll()) &&
13830          "omp for loop exprs were not built");
13831 
13832   if (!CurContext->isDependentContext()) {
13833     // Finalize the clauses that need pre-built expressions for CodeGen.
13834     for (OMPClause *C : Clauses) {
13835       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13836         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13837                                      B.NumIterations, *this, CurScope,
13838                                      DSAStack))
13839           return StmtError();
13840     }
13841   }
13842 
13843   if (checkSimdlenSafelenSpecified(*this, Clauses))
13844     return StmtError();
13845 
13846   setFunctionHasBranchProtectedScope();
13847   return OMPDistributeParallelForSimdDirective::Create(
13848       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
13849 }
13850 
13851 StmtResult Sema::ActOnOpenMPDistributeSimdDirective(
13852     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13853     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13854   if (!AStmt)
13855     return StmtError();
13856 
13857   auto *CS = cast<CapturedStmt>(AStmt);
13858   // 1.2.2 OpenMP Language Terminology
13859   // Structured block - An executable statement with a single entry at the
13860   // top and a single exit at the bottom.
13861   // The point of exit cannot be a branch out of the structured block.
13862   // longjmp() and throw() must not violate the entry/exit criteria.
13863   CS->getCapturedDecl()->setNothrow();
13864   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_distribute_simd);
13865        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13866     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13867     // 1.2.2 OpenMP Language Terminology
13868     // Structured block - An executable statement with a single entry at the
13869     // top and a single exit at the bottom.
13870     // The point of exit cannot be a branch out of the structured block.
13871     // longjmp() and throw() must not violate the entry/exit criteria.
13872     CS->getCapturedDecl()->setNothrow();
13873   }
13874 
13875   OMPLoopBasedDirective::HelperExprs B;
13876   // In presence of clause 'collapse' with number of loops, it will
13877   // define the nested loops number.
13878   unsigned NestedLoopCount =
13879       checkOpenMPLoop(OMPD_distribute_simd, getCollapseNumberExpr(Clauses),
13880                       nullptr /*ordered not a clause on distribute*/, CS, *this,
13881                       *DSAStack, VarsWithImplicitDSA, B);
13882   if (NestedLoopCount == 0)
13883     return StmtError();
13884 
13885   assert((CurContext->isDependentContext() || B.builtAll()) &&
13886          "omp for loop exprs were not built");
13887 
13888   if (!CurContext->isDependentContext()) {
13889     // Finalize the clauses that need pre-built expressions for CodeGen.
13890     for (OMPClause *C : Clauses) {
13891       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13892         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13893                                      B.NumIterations, *this, CurScope,
13894                                      DSAStack))
13895           return StmtError();
13896     }
13897   }
13898 
13899   if (checkSimdlenSafelenSpecified(*this, Clauses))
13900     return StmtError();
13901 
13902   setFunctionHasBranchProtectedScope();
13903   return OMPDistributeSimdDirective::Create(Context, StartLoc, EndLoc,
13904                                             NestedLoopCount, Clauses, AStmt, B);
13905 }
13906 
13907 StmtResult Sema::ActOnOpenMPTargetParallelForSimdDirective(
13908     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13909     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13910   if (!AStmt)
13911     return StmtError();
13912 
13913   auto *CS = cast<CapturedStmt>(AStmt);
13914   // 1.2.2 OpenMP Language Terminology
13915   // Structured block - An executable statement with a single entry at the
13916   // top and a single exit at the bottom.
13917   // The point of exit cannot be a branch out of the structured block.
13918   // longjmp() and throw() must not violate the entry/exit criteria.
13919   CS->getCapturedDecl()->setNothrow();
13920   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_parallel_for);
13921        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13922     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13923     // 1.2.2 OpenMP Language Terminology
13924     // Structured block - An executable statement with a single entry at the
13925     // top and a single exit at the bottom.
13926     // The point of exit cannot be a branch out of the structured block.
13927     // longjmp() and throw() must not violate the entry/exit criteria.
13928     CS->getCapturedDecl()->setNothrow();
13929   }
13930 
13931   OMPLoopBasedDirective::HelperExprs B;
13932   // In presence of clause 'collapse' or 'ordered' with number of loops, it will
13933   // define the nested loops number.
13934   unsigned NestedLoopCount = checkOpenMPLoop(
13935       OMPD_target_parallel_for_simd, getCollapseNumberExpr(Clauses),
13936       getOrderedNumberExpr(Clauses), CS, *this, *DSAStack, VarsWithImplicitDSA,
13937       B);
13938   if (NestedLoopCount == 0)
13939     return StmtError();
13940 
13941   assert((CurContext->isDependentContext() || B.builtAll()) &&
13942          "omp target parallel for simd loop exprs were not built");
13943 
13944   if (!CurContext->isDependentContext()) {
13945     // Finalize the clauses that need pre-built expressions for CodeGen.
13946     for (OMPClause *C : Clauses) {
13947       if (auto *LC = dyn_cast<OMPLinearClause>(C))
13948         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
13949                                      B.NumIterations, *this, CurScope,
13950                                      DSAStack))
13951           return StmtError();
13952     }
13953   }
13954   if (checkSimdlenSafelenSpecified(*this, Clauses))
13955     return StmtError();
13956 
13957   setFunctionHasBranchProtectedScope();
13958   return OMPTargetParallelForSimdDirective::Create(
13959       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
13960 }
13961 
13962 StmtResult Sema::ActOnOpenMPTargetSimdDirective(
13963     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
13964     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
13965   if (!AStmt)
13966     return StmtError();
13967 
13968   auto *CS = cast<CapturedStmt>(AStmt);
13969   // 1.2.2 OpenMP Language Terminology
13970   // Structured block - An executable statement with a single entry at the
13971   // top and a single exit at the bottom.
13972   // The point of exit cannot be a branch out of the structured block.
13973   // longjmp() and throw() must not violate the entry/exit criteria.
13974   CS->getCapturedDecl()->setNothrow();
13975   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_simd);
13976        ThisCaptureLevel > 1; --ThisCaptureLevel) {
13977     CS = cast<CapturedStmt>(CS->getCapturedStmt());
13978     // 1.2.2 OpenMP Language Terminology
13979     // Structured block - An executable statement with a single entry at the
13980     // top and a single exit at the bottom.
13981     // The point of exit cannot be a branch out of the structured block.
13982     // longjmp() and throw() must not violate the entry/exit criteria.
13983     CS->getCapturedDecl()->setNothrow();
13984   }
13985 
13986   OMPLoopBasedDirective::HelperExprs B;
13987   // In presence of clause 'collapse' with number of loops, it will define the
13988   // nested loops number.
13989   unsigned NestedLoopCount =
13990       checkOpenMPLoop(OMPD_target_simd, getCollapseNumberExpr(Clauses),
13991                       getOrderedNumberExpr(Clauses), CS, *this, *DSAStack,
13992                       VarsWithImplicitDSA, B);
13993   if (NestedLoopCount == 0)
13994     return StmtError();
13995 
13996   assert((CurContext->isDependentContext() || B.builtAll()) &&
13997          "omp target simd loop exprs were not built");
13998 
13999   if (!CurContext->isDependentContext()) {
14000     // Finalize the clauses that need pre-built expressions for CodeGen.
14001     for (OMPClause *C : Clauses) {
14002       if (auto *LC = dyn_cast<OMPLinearClause>(C))
14003         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
14004                                      B.NumIterations, *this, CurScope,
14005                                      DSAStack))
14006           return StmtError();
14007     }
14008   }
14009 
14010   if (checkSimdlenSafelenSpecified(*this, Clauses))
14011     return StmtError();
14012 
14013   setFunctionHasBranchProtectedScope();
14014   return OMPTargetSimdDirective::Create(Context, StartLoc, EndLoc,
14015                                         NestedLoopCount, Clauses, AStmt, B);
14016 }
14017 
14018 StmtResult Sema::ActOnOpenMPTeamsDistributeDirective(
14019     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14020     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14021   if (!AStmt)
14022     return StmtError();
14023 
14024   auto *CS = cast<CapturedStmt>(AStmt);
14025   // 1.2.2 OpenMP Language Terminology
14026   // Structured block - An executable statement with a single entry at the
14027   // top and a single exit at the bottom.
14028   // The point of exit cannot be a branch out of the structured block.
14029   // longjmp() and throw() must not violate the entry/exit criteria.
14030   CS->getCapturedDecl()->setNothrow();
14031   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_teams_distribute);
14032        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14033     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14034     // 1.2.2 OpenMP Language Terminology
14035     // Structured block - An executable statement with a single entry at the
14036     // top and a single exit at the bottom.
14037     // The point of exit cannot be a branch out of the structured block.
14038     // longjmp() and throw() must not violate the entry/exit criteria.
14039     CS->getCapturedDecl()->setNothrow();
14040   }
14041 
14042   OMPLoopBasedDirective::HelperExprs B;
14043   // In presence of clause 'collapse' with number of loops, it will
14044   // define the nested loops number.
14045   unsigned NestedLoopCount =
14046       checkOpenMPLoop(OMPD_teams_distribute, getCollapseNumberExpr(Clauses),
14047                       nullptr /*ordered not a clause on distribute*/, CS, *this,
14048                       *DSAStack, VarsWithImplicitDSA, B);
14049   if (NestedLoopCount == 0)
14050     return StmtError();
14051 
14052   assert((CurContext->isDependentContext() || B.builtAll()) &&
14053          "omp teams distribute loop exprs were not built");
14054 
14055   setFunctionHasBranchProtectedScope();
14056 
14057   DSAStack->setParentTeamsRegionLoc(StartLoc);
14058 
14059   return OMPTeamsDistributeDirective::Create(
14060       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
14061 }
14062 
14063 StmtResult Sema::ActOnOpenMPTeamsDistributeSimdDirective(
14064     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14065     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14066   if (!AStmt)
14067     return StmtError();
14068 
14069   auto *CS = cast<CapturedStmt>(AStmt);
14070   // 1.2.2 OpenMP Language Terminology
14071   // Structured block - An executable statement with a single entry at the
14072   // top and a single exit at the bottom.
14073   // The point of exit cannot be a branch out of the structured block.
14074   // longjmp() and throw() must not violate the entry/exit criteria.
14075   CS->getCapturedDecl()->setNothrow();
14076   for (int ThisCaptureLevel =
14077            getOpenMPCaptureLevels(OMPD_teams_distribute_simd);
14078        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14079     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14080     // 1.2.2 OpenMP Language Terminology
14081     // Structured block - An executable statement with a single entry at the
14082     // top and a single exit at the bottom.
14083     // The point of exit cannot be a branch out of the structured block.
14084     // longjmp() and throw() must not violate the entry/exit criteria.
14085     CS->getCapturedDecl()->setNothrow();
14086   }
14087 
14088   OMPLoopBasedDirective::HelperExprs B;
14089   // In presence of clause 'collapse' with number of loops, it will
14090   // define the nested loops number.
14091   unsigned NestedLoopCount = checkOpenMPLoop(
14092       OMPD_teams_distribute_simd, getCollapseNumberExpr(Clauses),
14093       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
14094       VarsWithImplicitDSA, B);
14095 
14096   if (NestedLoopCount == 0)
14097     return StmtError();
14098 
14099   assert((CurContext->isDependentContext() || B.builtAll()) &&
14100          "omp teams distribute simd loop exprs were not built");
14101 
14102   if (!CurContext->isDependentContext()) {
14103     // Finalize the clauses that need pre-built expressions for CodeGen.
14104     for (OMPClause *C : Clauses) {
14105       if (auto *LC = dyn_cast<OMPLinearClause>(C))
14106         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
14107                                      B.NumIterations, *this, CurScope,
14108                                      DSAStack))
14109           return StmtError();
14110     }
14111   }
14112 
14113   if (checkSimdlenSafelenSpecified(*this, Clauses))
14114     return StmtError();
14115 
14116   setFunctionHasBranchProtectedScope();
14117 
14118   DSAStack->setParentTeamsRegionLoc(StartLoc);
14119 
14120   return OMPTeamsDistributeSimdDirective::Create(
14121       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
14122 }
14123 
14124 StmtResult Sema::ActOnOpenMPTeamsDistributeParallelForSimdDirective(
14125     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14126     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14127   if (!AStmt)
14128     return StmtError();
14129 
14130   auto *CS = cast<CapturedStmt>(AStmt);
14131   // 1.2.2 OpenMP Language Terminology
14132   // Structured block - An executable statement with a single entry at the
14133   // top and a single exit at the bottom.
14134   // The point of exit cannot be a branch out of the structured block.
14135   // longjmp() and throw() must not violate the entry/exit criteria.
14136   CS->getCapturedDecl()->setNothrow();
14137 
14138   for (int ThisCaptureLevel =
14139            getOpenMPCaptureLevels(OMPD_teams_distribute_parallel_for_simd);
14140        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14141     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14142     // 1.2.2 OpenMP Language Terminology
14143     // Structured block - An executable statement with a single entry at the
14144     // top and a single exit at the bottom.
14145     // The point of exit cannot be a branch out of the structured block.
14146     // longjmp() and throw() must not violate the entry/exit criteria.
14147     CS->getCapturedDecl()->setNothrow();
14148   }
14149 
14150   OMPLoopBasedDirective::HelperExprs B;
14151   // In presence of clause 'collapse' with number of loops, it will
14152   // define the nested loops number.
14153   unsigned NestedLoopCount = checkOpenMPLoop(
14154       OMPD_teams_distribute_parallel_for_simd, getCollapseNumberExpr(Clauses),
14155       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
14156       VarsWithImplicitDSA, B);
14157 
14158   if (NestedLoopCount == 0)
14159     return StmtError();
14160 
14161   assert((CurContext->isDependentContext() || B.builtAll()) &&
14162          "omp for loop exprs were not built");
14163 
14164   if (!CurContext->isDependentContext()) {
14165     // Finalize the clauses that need pre-built expressions for CodeGen.
14166     for (OMPClause *C : Clauses) {
14167       if (auto *LC = dyn_cast<OMPLinearClause>(C))
14168         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
14169                                      B.NumIterations, *this, CurScope,
14170                                      DSAStack))
14171           return StmtError();
14172     }
14173   }
14174 
14175   if (checkSimdlenSafelenSpecified(*this, Clauses))
14176     return StmtError();
14177 
14178   setFunctionHasBranchProtectedScope();
14179 
14180   DSAStack->setParentTeamsRegionLoc(StartLoc);
14181 
14182   return OMPTeamsDistributeParallelForSimdDirective::Create(
14183       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
14184 }
14185 
14186 StmtResult Sema::ActOnOpenMPTeamsDistributeParallelForDirective(
14187     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14188     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14189   if (!AStmt)
14190     return StmtError();
14191 
14192   auto *CS = cast<CapturedStmt>(AStmt);
14193   // 1.2.2 OpenMP Language Terminology
14194   // Structured block - An executable statement with a single entry at the
14195   // top and a single exit at the bottom.
14196   // The point of exit cannot be a branch out of the structured block.
14197   // longjmp() and throw() must not violate the entry/exit criteria.
14198   CS->getCapturedDecl()->setNothrow();
14199 
14200   for (int ThisCaptureLevel =
14201            getOpenMPCaptureLevels(OMPD_teams_distribute_parallel_for);
14202        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14203     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14204     // 1.2.2 OpenMP Language Terminology
14205     // Structured block - An executable statement with a single entry at the
14206     // top and a single exit at the bottom.
14207     // The point of exit cannot be a branch out of the structured block.
14208     // longjmp() and throw() must not violate the entry/exit criteria.
14209     CS->getCapturedDecl()->setNothrow();
14210   }
14211 
14212   OMPLoopBasedDirective::HelperExprs B;
14213   // In presence of clause 'collapse' with number of loops, it will
14214   // define the nested loops number.
14215   unsigned NestedLoopCount = checkOpenMPLoop(
14216       OMPD_teams_distribute_parallel_for, getCollapseNumberExpr(Clauses),
14217       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
14218       VarsWithImplicitDSA, B);
14219 
14220   if (NestedLoopCount == 0)
14221     return StmtError();
14222 
14223   assert((CurContext->isDependentContext() || B.builtAll()) &&
14224          "omp for loop exprs were not built");
14225 
14226   setFunctionHasBranchProtectedScope();
14227 
14228   DSAStack->setParentTeamsRegionLoc(StartLoc);
14229 
14230   return OMPTeamsDistributeParallelForDirective::Create(
14231       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
14232       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
14233 }
14234 
14235 StmtResult Sema::ActOnOpenMPTargetTeamsDirective(ArrayRef<OMPClause *> Clauses,
14236                                                  Stmt *AStmt,
14237                                                  SourceLocation StartLoc,
14238                                                  SourceLocation EndLoc) {
14239   if (!AStmt)
14240     return StmtError();
14241 
14242   auto *CS = cast<CapturedStmt>(AStmt);
14243   // 1.2.2 OpenMP Language Terminology
14244   // Structured block - An executable statement with a single entry at the
14245   // top and a single exit at the bottom.
14246   // The point of exit cannot be a branch out of the structured block.
14247   // longjmp() and throw() must not violate the entry/exit criteria.
14248   CS->getCapturedDecl()->setNothrow();
14249 
14250   for (int ThisCaptureLevel = getOpenMPCaptureLevels(OMPD_target_teams);
14251        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14252     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14253     // 1.2.2 OpenMP Language Terminology
14254     // Structured block - An executable statement with a single entry at the
14255     // top and a single exit at the bottom.
14256     // The point of exit cannot be a branch out of the structured block.
14257     // longjmp() and throw() must not violate the entry/exit criteria.
14258     CS->getCapturedDecl()->setNothrow();
14259   }
14260   setFunctionHasBranchProtectedScope();
14261 
14262   return OMPTargetTeamsDirective::Create(Context, StartLoc, EndLoc, Clauses,
14263                                          AStmt);
14264 }
14265 
14266 StmtResult Sema::ActOnOpenMPTargetTeamsDistributeDirective(
14267     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14268     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14269   if (!AStmt)
14270     return StmtError();
14271 
14272   auto *CS = cast<CapturedStmt>(AStmt);
14273   // 1.2.2 OpenMP Language Terminology
14274   // Structured block - An executable statement with a single entry at the
14275   // top and a single exit at the bottom.
14276   // The point of exit cannot be a branch out of the structured block.
14277   // longjmp() and throw() must not violate the entry/exit criteria.
14278   CS->getCapturedDecl()->setNothrow();
14279   for (int ThisCaptureLevel =
14280            getOpenMPCaptureLevels(OMPD_target_teams_distribute);
14281        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14282     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14283     // 1.2.2 OpenMP Language Terminology
14284     // Structured block - An executable statement with a single entry at the
14285     // top and a single exit at the bottom.
14286     // The point of exit cannot be a branch out of the structured block.
14287     // longjmp() and throw() must not violate the entry/exit criteria.
14288     CS->getCapturedDecl()->setNothrow();
14289   }
14290 
14291   OMPLoopBasedDirective::HelperExprs B;
14292   // In presence of clause 'collapse' with number of loops, it will
14293   // define the nested loops number.
14294   unsigned NestedLoopCount = checkOpenMPLoop(
14295       OMPD_target_teams_distribute, getCollapseNumberExpr(Clauses),
14296       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
14297       VarsWithImplicitDSA, B);
14298   if (NestedLoopCount == 0)
14299     return StmtError();
14300 
14301   assert((CurContext->isDependentContext() || B.builtAll()) &&
14302          "omp target teams distribute loop exprs were not built");
14303 
14304   setFunctionHasBranchProtectedScope();
14305   return OMPTargetTeamsDistributeDirective::Create(
14306       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
14307 }
14308 
14309 StmtResult Sema::ActOnOpenMPTargetTeamsDistributeParallelForDirective(
14310     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14311     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14312   if (!AStmt)
14313     return StmtError();
14314 
14315   auto *CS = cast<CapturedStmt>(AStmt);
14316   // 1.2.2 OpenMP Language Terminology
14317   // Structured block - An executable statement with a single entry at the
14318   // top and a single exit at the bottom.
14319   // The point of exit cannot be a branch out of the structured block.
14320   // longjmp() and throw() must not violate the entry/exit criteria.
14321   CS->getCapturedDecl()->setNothrow();
14322   for (int ThisCaptureLevel =
14323            getOpenMPCaptureLevels(OMPD_target_teams_distribute_parallel_for);
14324        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14325     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14326     // 1.2.2 OpenMP Language Terminology
14327     // Structured block - An executable statement with a single entry at the
14328     // top and a single exit at the bottom.
14329     // The point of exit cannot be a branch out of the structured block.
14330     // longjmp() and throw() must not violate the entry/exit criteria.
14331     CS->getCapturedDecl()->setNothrow();
14332   }
14333 
14334   OMPLoopBasedDirective::HelperExprs B;
14335   // In presence of clause 'collapse' with number of loops, it will
14336   // define the nested loops number.
14337   unsigned NestedLoopCount = checkOpenMPLoop(
14338       OMPD_target_teams_distribute_parallel_for, getCollapseNumberExpr(Clauses),
14339       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
14340       VarsWithImplicitDSA, B);
14341   if (NestedLoopCount == 0)
14342     return StmtError();
14343 
14344   assert((CurContext->isDependentContext() || B.builtAll()) &&
14345          "omp target teams distribute parallel for loop exprs were not built");
14346 
14347   if (!CurContext->isDependentContext()) {
14348     // Finalize the clauses that need pre-built expressions for CodeGen.
14349     for (OMPClause *C : Clauses) {
14350       if (auto *LC = dyn_cast<OMPLinearClause>(C))
14351         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
14352                                      B.NumIterations, *this, CurScope,
14353                                      DSAStack))
14354           return StmtError();
14355     }
14356   }
14357 
14358   setFunctionHasBranchProtectedScope();
14359   return OMPTargetTeamsDistributeParallelForDirective::Create(
14360       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B,
14361       DSAStack->getTaskgroupReductionRef(), DSAStack->isCancelRegion());
14362 }
14363 
14364 StmtResult Sema::ActOnOpenMPTargetTeamsDistributeParallelForSimdDirective(
14365     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14366     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14367   if (!AStmt)
14368     return StmtError();
14369 
14370   auto *CS = cast<CapturedStmt>(AStmt);
14371   // 1.2.2 OpenMP Language Terminology
14372   // Structured block - An executable statement with a single entry at the
14373   // top and a single exit at the bottom.
14374   // The point of exit cannot be a branch out of the structured block.
14375   // longjmp() and throw() must not violate the entry/exit criteria.
14376   CS->getCapturedDecl()->setNothrow();
14377   for (int ThisCaptureLevel = getOpenMPCaptureLevels(
14378            OMPD_target_teams_distribute_parallel_for_simd);
14379        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14380     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14381     // 1.2.2 OpenMP Language Terminology
14382     // Structured block - An executable statement with a single entry at the
14383     // top and a single exit at the bottom.
14384     // The point of exit cannot be a branch out of the structured block.
14385     // longjmp() and throw() must not violate the entry/exit criteria.
14386     CS->getCapturedDecl()->setNothrow();
14387   }
14388 
14389   OMPLoopBasedDirective::HelperExprs B;
14390   // In presence of clause 'collapse' with number of loops, it will
14391   // define the nested loops number.
14392   unsigned NestedLoopCount =
14393       checkOpenMPLoop(OMPD_target_teams_distribute_parallel_for_simd,
14394                       getCollapseNumberExpr(Clauses),
14395                       nullptr /*ordered not a clause on distribute*/, CS, *this,
14396                       *DSAStack, VarsWithImplicitDSA, B);
14397   if (NestedLoopCount == 0)
14398     return StmtError();
14399 
14400   assert((CurContext->isDependentContext() || B.builtAll()) &&
14401          "omp target teams distribute parallel for simd loop exprs were not "
14402          "built");
14403 
14404   if (!CurContext->isDependentContext()) {
14405     // Finalize the clauses that need pre-built expressions for CodeGen.
14406     for (OMPClause *C : Clauses) {
14407       if (auto *LC = dyn_cast<OMPLinearClause>(C))
14408         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
14409                                      B.NumIterations, *this, CurScope,
14410                                      DSAStack))
14411           return StmtError();
14412     }
14413   }
14414 
14415   if (checkSimdlenSafelenSpecified(*this, Clauses))
14416     return StmtError();
14417 
14418   setFunctionHasBranchProtectedScope();
14419   return OMPTargetTeamsDistributeParallelForSimdDirective::Create(
14420       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
14421 }
14422 
14423 StmtResult Sema::ActOnOpenMPTargetTeamsDistributeSimdDirective(
14424     ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc,
14425     SourceLocation EndLoc, VarsWithInheritedDSAType &VarsWithImplicitDSA) {
14426   if (!AStmt)
14427     return StmtError();
14428 
14429   auto *CS = cast<CapturedStmt>(AStmt);
14430   // 1.2.2 OpenMP Language Terminology
14431   // Structured block - An executable statement with a single entry at the
14432   // top and a single exit at the bottom.
14433   // The point of exit cannot be a branch out of the structured block.
14434   // longjmp() and throw() must not violate the entry/exit criteria.
14435   CS->getCapturedDecl()->setNothrow();
14436   for (int ThisCaptureLevel =
14437            getOpenMPCaptureLevels(OMPD_target_teams_distribute_simd);
14438        ThisCaptureLevel > 1; --ThisCaptureLevel) {
14439     CS = cast<CapturedStmt>(CS->getCapturedStmt());
14440     // 1.2.2 OpenMP Language Terminology
14441     // Structured block - An executable statement with a single entry at the
14442     // top and a single exit at the bottom.
14443     // The point of exit cannot be a branch out of the structured block.
14444     // longjmp() and throw() must not violate the entry/exit criteria.
14445     CS->getCapturedDecl()->setNothrow();
14446   }
14447 
14448   OMPLoopBasedDirective::HelperExprs B;
14449   // In presence of clause 'collapse' with number of loops, it will
14450   // define the nested loops number.
14451   unsigned NestedLoopCount = checkOpenMPLoop(
14452       OMPD_target_teams_distribute_simd, getCollapseNumberExpr(Clauses),
14453       nullptr /*ordered not a clause on distribute*/, CS, *this, *DSAStack,
14454       VarsWithImplicitDSA, B);
14455   if (NestedLoopCount == 0)
14456     return StmtError();
14457 
14458   assert((CurContext->isDependentContext() || B.builtAll()) &&
14459          "omp target teams distribute simd loop exprs were not built");
14460 
14461   if (!CurContext->isDependentContext()) {
14462     // Finalize the clauses that need pre-built expressions for CodeGen.
14463     for (OMPClause *C : Clauses) {
14464       if (auto *LC = dyn_cast<OMPLinearClause>(C))
14465         if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef),
14466                                      B.NumIterations, *this, CurScope,
14467                                      DSAStack))
14468           return StmtError();
14469     }
14470   }
14471 
14472   if (checkSimdlenSafelenSpecified(*this, Clauses))
14473     return StmtError();
14474 
14475   setFunctionHasBranchProtectedScope();
14476   return OMPTargetTeamsDistributeSimdDirective::Create(
14477       Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B);
14478 }
14479 
14480 bool Sema::checkTransformableLoopNest(
14481     OpenMPDirectiveKind Kind, Stmt *AStmt, int NumLoops,
14482     SmallVectorImpl<OMPLoopBasedDirective::HelperExprs> &LoopHelpers,
14483     Stmt *&Body,
14484     SmallVectorImpl<SmallVector<llvm::PointerUnion<Stmt *, Decl *>, 0>>
14485         &OriginalInits) {
14486   OriginalInits.emplace_back();
14487   bool Result = OMPLoopBasedDirective::doForAllLoops(
14488       AStmt->IgnoreContainers(), /*TryImperfectlyNestedLoops=*/false, NumLoops,
14489       [this, &LoopHelpers, &Body, &OriginalInits, Kind](unsigned Cnt,
14490                                                         Stmt *CurStmt) {
14491         VarsWithInheritedDSAType TmpDSA;
14492         unsigned SingleNumLoops =
14493             checkOpenMPLoop(Kind, nullptr, nullptr, CurStmt, *this, *DSAStack,
14494                             TmpDSA, LoopHelpers[Cnt]);
14495         if (SingleNumLoops == 0)
14496           return true;
14497         assert(SingleNumLoops == 1 && "Expect single loop iteration space");
14498         if (auto *For = dyn_cast<ForStmt>(CurStmt)) {
14499           OriginalInits.back().push_back(For->getInit());
14500           Body = For->getBody();
14501         } else {
14502           assert(isa<CXXForRangeStmt>(CurStmt) &&
14503                  "Expected canonical for or range-based for loops.");
14504           auto *CXXFor = cast<CXXForRangeStmt>(CurStmt);
14505           OriginalInits.back().push_back(CXXFor->getBeginStmt());
14506           Body = CXXFor->getBody();
14507         }
14508         OriginalInits.emplace_back();
14509         return false;
14510       },
14511       [&OriginalInits](OMPLoopBasedDirective *Transform) {
14512         Stmt *DependentPreInits;
14513         if (auto *Dir = dyn_cast<OMPTileDirective>(Transform))
14514           DependentPreInits = Dir->getPreInits();
14515         else if (auto *Dir = dyn_cast<OMPUnrollDirective>(Transform))
14516           DependentPreInits = Dir->getPreInits();
14517         else
14518           llvm_unreachable("Unhandled loop transformation");
14519         if (!DependentPreInits)
14520           return;
14521         llvm::append_range(OriginalInits.back(),
14522                            cast<DeclStmt>(DependentPreInits)->getDeclGroup());
14523       });
14524   assert(OriginalInits.back().empty() && "No preinit after innermost loop");
14525   OriginalInits.pop_back();
14526   return Result;
14527 }
14528 
14529 StmtResult Sema::ActOnOpenMPTileDirective(ArrayRef<OMPClause *> Clauses,
14530                                           Stmt *AStmt, SourceLocation StartLoc,
14531                                           SourceLocation EndLoc) {
14532   auto SizesClauses =
14533       OMPExecutableDirective::getClausesOfKind<OMPSizesClause>(Clauses);
14534   if (SizesClauses.empty()) {
14535     // A missing 'sizes' clause is already reported by the parser.
14536     return StmtError();
14537   }
14538   const OMPSizesClause *SizesClause = *SizesClauses.begin();
14539   unsigned NumLoops = SizesClause->getNumSizes();
14540 
14541   // Empty statement should only be possible if there already was an error.
14542   if (!AStmt)
14543     return StmtError();
14544 
14545   // Verify and diagnose loop nest.
14546   SmallVector<OMPLoopBasedDirective::HelperExprs, 4> LoopHelpers(NumLoops);
14547   Stmt *Body = nullptr;
14548   SmallVector<SmallVector<llvm::PointerUnion<Stmt *, Decl *>, 0>, 4>
14549       OriginalInits;
14550   if (!checkTransformableLoopNest(OMPD_tile, AStmt, NumLoops, LoopHelpers, Body,
14551                                   OriginalInits))
14552     return StmtError();
14553 
14554   // Delay tiling to when template is completely instantiated.
14555   if (CurContext->isDependentContext())
14556     return OMPTileDirective::Create(Context, StartLoc, EndLoc, Clauses,
14557                                     NumLoops, AStmt, nullptr, nullptr);
14558 
14559   SmallVector<Decl *, 4> PreInits;
14560 
14561   // Create iteration variables for the generated loops.
14562   SmallVector<VarDecl *, 4> FloorIndVars;
14563   SmallVector<VarDecl *, 4> TileIndVars;
14564   FloorIndVars.resize(NumLoops);
14565   TileIndVars.resize(NumLoops);
14566   for (unsigned I = 0; I < NumLoops; ++I) {
14567     OMPLoopBasedDirective::HelperExprs &LoopHelper = LoopHelpers[I];
14568 
14569     assert(LoopHelper.Counters.size() == 1 &&
14570            "Expect single-dimensional loop iteration space");
14571     auto *OrigCntVar = cast<DeclRefExpr>(LoopHelper.Counters.front());
14572     std::string OrigVarName = OrigCntVar->getNameInfo().getAsString();
14573     DeclRefExpr *IterVarRef = cast<DeclRefExpr>(LoopHelper.IterationVarRef);
14574     QualType CntTy = IterVarRef->getType();
14575 
14576     // Iteration variable for the floor (i.e. outer) loop.
14577     {
14578       std::string FloorCntName =
14579           (Twine(".floor_") + llvm::utostr(I) + ".iv." + OrigVarName).str();
14580       VarDecl *FloorCntDecl =
14581           buildVarDecl(*this, {}, CntTy, FloorCntName, nullptr, OrigCntVar);
14582       FloorIndVars[I] = FloorCntDecl;
14583     }
14584 
14585     // Iteration variable for the tile (i.e. inner) loop.
14586     {
14587       std::string TileCntName =
14588           (Twine(".tile_") + llvm::utostr(I) + ".iv." + OrigVarName).str();
14589 
14590       // Reuse the iteration variable created by checkOpenMPLoop. It is also
14591       // used by the expressions to derive the original iteration variable's
14592       // value from the logical iteration number.
14593       auto *TileCntDecl = cast<VarDecl>(IterVarRef->getDecl());
14594       TileCntDecl->setDeclName(&PP.getIdentifierTable().get(TileCntName));
14595       TileIndVars[I] = TileCntDecl;
14596     }
14597     for (auto &P : OriginalInits[I]) {
14598       if (auto *D = P.dyn_cast<Decl *>())
14599         PreInits.push_back(D);
14600       else if (auto *PI = dyn_cast_or_null<DeclStmt>(P.dyn_cast<Stmt *>()))
14601         PreInits.append(PI->decl_begin(), PI->decl_end());
14602     }
14603     if (auto *PI = cast_or_null<DeclStmt>(LoopHelper.PreInits))
14604       PreInits.append(PI->decl_begin(), PI->decl_end());
14605     // Gather declarations for the data members used as counters.
14606     for (Expr *CounterRef : LoopHelper.Counters) {
14607       auto *CounterDecl = cast<DeclRefExpr>(CounterRef)->getDecl();
14608       if (isa<OMPCapturedExprDecl>(CounterDecl))
14609         PreInits.push_back(CounterDecl);
14610     }
14611   }
14612 
14613   // Once the original iteration values are set, append the innermost body.
14614   Stmt *Inner = Body;
14615 
14616   // Create tile loops from the inside to the outside.
14617   for (int I = NumLoops - 1; I >= 0; --I) {
14618     OMPLoopBasedDirective::HelperExprs &LoopHelper = LoopHelpers[I];
14619     Expr *NumIterations = LoopHelper.NumIterations;
14620     auto *OrigCntVar = cast<DeclRefExpr>(LoopHelper.Counters[0]);
14621     QualType CntTy = OrigCntVar->getType();
14622     Expr *DimTileSize = SizesClause->getSizesRefs()[I];
14623     Scope *CurScope = getCurScope();
14624 
14625     // Commonly used variables.
14626     DeclRefExpr *TileIV = buildDeclRefExpr(*this, TileIndVars[I], CntTy,
14627                                            OrigCntVar->getExprLoc());
14628     DeclRefExpr *FloorIV = buildDeclRefExpr(*this, FloorIndVars[I], CntTy,
14629                                             OrigCntVar->getExprLoc());
14630 
14631     // For init-statement: auto .tile.iv = .floor.iv
14632     AddInitializerToDecl(TileIndVars[I], DefaultLvalueConversion(FloorIV).get(),
14633                          /*DirectInit=*/false);
14634     Decl *CounterDecl = TileIndVars[I];
14635     StmtResult InitStmt = new (Context)
14636         DeclStmt(DeclGroupRef::Create(Context, &CounterDecl, 1),
14637                  OrigCntVar->getBeginLoc(), OrigCntVar->getEndLoc());
14638     if (!InitStmt.isUsable())
14639       return StmtError();
14640 
14641     // For cond-expression: .tile.iv < min(.floor.iv + DimTileSize,
14642     // NumIterations)
14643     ExprResult EndOfTile = BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(),
14644                                       BO_Add, FloorIV, DimTileSize);
14645     if (!EndOfTile.isUsable())
14646       return StmtError();
14647     ExprResult IsPartialTile =
14648         BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(), BO_LT,
14649                    NumIterations, EndOfTile.get());
14650     if (!IsPartialTile.isUsable())
14651       return StmtError();
14652     ExprResult MinTileAndIterSpace = ActOnConditionalOp(
14653         LoopHelper.Cond->getBeginLoc(), LoopHelper.Cond->getEndLoc(),
14654         IsPartialTile.get(), NumIterations, EndOfTile.get());
14655     if (!MinTileAndIterSpace.isUsable())
14656       return StmtError();
14657     ExprResult CondExpr = BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(),
14658                                      BO_LT, TileIV, MinTileAndIterSpace.get());
14659     if (!CondExpr.isUsable())
14660       return StmtError();
14661 
14662     // For incr-statement: ++.tile.iv
14663     ExprResult IncrStmt =
14664         BuildUnaryOp(CurScope, LoopHelper.Inc->getExprLoc(), UO_PreInc, TileIV);
14665     if (!IncrStmt.isUsable())
14666       return StmtError();
14667 
14668     // Statements to set the original iteration variable's value from the
14669     // logical iteration number.
14670     // Generated for loop is:
14671     // Original_for_init;
14672     // for (auto .tile.iv = .floor.iv; .tile.iv < min(.floor.iv + DimTileSize,
14673     // NumIterations); ++.tile.iv) {
14674     //   Original_Body;
14675     //   Original_counter_update;
14676     // }
14677     // FIXME: If the innermost body is an loop itself, inserting these
14678     // statements stops it being recognized  as a perfectly nested loop (e.g.
14679     // for applying tiling again). If this is the case, sink the expressions
14680     // further into the inner loop.
14681     SmallVector<Stmt *, 4> BodyParts;
14682     BodyParts.append(LoopHelper.Updates.begin(), LoopHelper.Updates.end());
14683     BodyParts.push_back(Inner);
14684     Inner = CompoundStmt::Create(Context, BodyParts, FPOptionsOverride(),
14685                                  Inner->getBeginLoc(), Inner->getEndLoc());
14686     Inner = new (Context)
14687         ForStmt(Context, InitStmt.get(), CondExpr.get(), nullptr,
14688                 IncrStmt.get(), Inner, LoopHelper.Init->getBeginLoc(),
14689                 LoopHelper.Init->getBeginLoc(), LoopHelper.Inc->getEndLoc());
14690   }
14691 
14692   // Create floor loops from the inside to the outside.
14693   for (int I = NumLoops - 1; I >= 0; --I) {
14694     auto &LoopHelper = LoopHelpers[I];
14695     Expr *NumIterations = LoopHelper.NumIterations;
14696     DeclRefExpr *OrigCntVar = cast<DeclRefExpr>(LoopHelper.Counters[0]);
14697     QualType CntTy = OrigCntVar->getType();
14698     Expr *DimTileSize = SizesClause->getSizesRefs()[I];
14699     Scope *CurScope = getCurScope();
14700 
14701     // Commonly used variables.
14702     DeclRefExpr *FloorIV = buildDeclRefExpr(*this, FloorIndVars[I], CntTy,
14703                                             OrigCntVar->getExprLoc());
14704 
14705     // For init-statement: auto .floor.iv = 0
14706     AddInitializerToDecl(
14707         FloorIndVars[I],
14708         ActOnIntegerConstant(LoopHelper.Init->getExprLoc(), 0).get(),
14709         /*DirectInit=*/false);
14710     Decl *CounterDecl = FloorIndVars[I];
14711     StmtResult InitStmt = new (Context)
14712         DeclStmt(DeclGroupRef::Create(Context, &CounterDecl, 1),
14713                  OrigCntVar->getBeginLoc(), OrigCntVar->getEndLoc());
14714     if (!InitStmt.isUsable())
14715       return StmtError();
14716 
14717     // For cond-expression: .floor.iv < NumIterations
14718     ExprResult CondExpr = BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(),
14719                                      BO_LT, FloorIV, NumIterations);
14720     if (!CondExpr.isUsable())
14721       return StmtError();
14722 
14723     // For incr-statement: .floor.iv += DimTileSize
14724     ExprResult IncrStmt = BuildBinOp(CurScope, LoopHelper.Inc->getExprLoc(),
14725                                      BO_AddAssign, FloorIV, DimTileSize);
14726     if (!IncrStmt.isUsable())
14727       return StmtError();
14728 
14729     Inner = new (Context)
14730         ForStmt(Context, InitStmt.get(), CondExpr.get(), nullptr,
14731                 IncrStmt.get(), Inner, LoopHelper.Init->getBeginLoc(),
14732                 LoopHelper.Init->getBeginLoc(), LoopHelper.Inc->getEndLoc());
14733   }
14734 
14735   return OMPTileDirective::Create(Context, StartLoc, EndLoc, Clauses, NumLoops,
14736                                   AStmt, Inner,
14737                                   buildPreInits(Context, PreInits));
14738 }
14739 
14740 StmtResult Sema::ActOnOpenMPUnrollDirective(ArrayRef<OMPClause *> Clauses,
14741                                             Stmt *AStmt,
14742                                             SourceLocation StartLoc,
14743                                             SourceLocation EndLoc) {
14744   // Empty statement should only be possible if there already was an error.
14745   if (!AStmt)
14746     return StmtError();
14747 
14748   if (checkMutuallyExclusiveClauses(*this, Clauses, {OMPC_partial, OMPC_full}))
14749     return StmtError();
14750 
14751   const OMPFullClause *FullClause =
14752       OMPExecutableDirective::getSingleClause<OMPFullClause>(Clauses);
14753   const OMPPartialClause *PartialClause =
14754       OMPExecutableDirective::getSingleClause<OMPPartialClause>(Clauses);
14755   assert(!(FullClause && PartialClause) &&
14756          "mutual exclusivity must have been checked before");
14757 
14758   constexpr unsigned NumLoops = 1;
14759   Stmt *Body = nullptr;
14760   SmallVector<OMPLoopBasedDirective::HelperExprs, NumLoops> LoopHelpers(
14761       NumLoops);
14762   SmallVector<SmallVector<llvm::PointerUnion<Stmt *, Decl *>, 0>, NumLoops + 1>
14763       OriginalInits;
14764   if (!checkTransformableLoopNest(OMPD_unroll, AStmt, NumLoops, LoopHelpers,
14765                                   Body, OriginalInits))
14766     return StmtError();
14767 
14768   unsigned NumGeneratedLoops = PartialClause ? 1 : 0;
14769 
14770   // Delay unrolling to when template is completely instantiated.
14771   if (CurContext->isDependentContext())
14772     return OMPUnrollDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
14773                                       NumGeneratedLoops, nullptr, nullptr);
14774 
14775   OMPLoopBasedDirective::HelperExprs &LoopHelper = LoopHelpers.front();
14776 
14777   if (FullClause) {
14778     if (!VerifyPositiveIntegerConstantInClause(
14779              LoopHelper.NumIterations, OMPC_full, /*StrictlyPositive=*/false,
14780              /*SuppressExprDiags=*/true)
14781              .isUsable()) {
14782       Diag(AStmt->getBeginLoc(), diag::err_omp_unroll_full_variable_trip_count);
14783       Diag(FullClause->getBeginLoc(), diag::note_omp_directive_here)
14784           << "#pragma omp unroll full";
14785       return StmtError();
14786     }
14787   }
14788 
14789   // The generated loop may only be passed to other loop-associated directive
14790   // when a partial clause is specified. Without the requirement it is
14791   // sufficient to generate loop unroll metadata at code-generation.
14792   if (NumGeneratedLoops == 0)
14793     return OMPUnrollDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
14794                                       NumGeneratedLoops, nullptr, nullptr);
14795 
14796   // Otherwise, we need to provide a de-sugared/transformed AST that can be
14797   // associated with another loop directive.
14798   //
14799   // The canonical loop analysis return by checkTransformableLoopNest assumes
14800   // the following structure to be the same loop without transformations or
14801   // directives applied: \code OriginalInits; LoopHelper.PreInits;
14802   // LoopHelper.Counters;
14803   // for (; IV < LoopHelper.NumIterations; ++IV) {
14804   //   LoopHelper.Updates;
14805   //   Body;
14806   // }
14807   // \endcode
14808   // where IV is a variable declared and initialized to 0 in LoopHelper.PreInits
14809   // and referenced by LoopHelper.IterationVarRef.
14810   //
14811   // The unrolling directive transforms this into the following loop:
14812   // \code
14813   // OriginalInits;         \
14814   // LoopHelper.PreInits;    > NewPreInits
14815   // LoopHelper.Counters;   /
14816   // for (auto UIV = 0; UIV < LoopHelper.NumIterations; UIV+=Factor) {
14817   //   #pragma clang loop unroll_count(Factor)
14818   //   for (IV = UIV; IV < UIV + Factor && UIV < LoopHelper.NumIterations; ++IV)
14819   //   {
14820   //     LoopHelper.Updates;
14821   //     Body;
14822   //   }
14823   // }
14824   // \endcode
14825   // where UIV is a new logical iteration counter. IV must be the same VarDecl
14826   // as the original LoopHelper.IterationVarRef because LoopHelper.Updates
14827   // references it. If the partially unrolled loop is associated with another
14828   // loop directive (like an OMPForDirective), it will use checkOpenMPLoop to
14829   // analyze this loop, i.e. the outer loop must fulfill the constraints of an
14830   // OpenMP canonical loop. The inner loop is not an associable canonical loop
14831   // and only exists to defer its unrolling to LLVM's LoopUnroll instead of
14832   // doing it in the frontend (by adding loop metadata). NewPreInits becomes a
14833   // property of the OMPLoopBasedDirective instead of statements in
14834   // CompoundStatement. This is to allow the loop to become a non-outermost loop
14835   // of a canonical loop nest where these PreInits are emitted before the
14836   // outermost directive.
14837 
14838   // Determine the PreInit declarations.
14839   SmallVector<Decl *, 4> PreInits;
14840   assert(OriginalInits.size() == 1 &&
14841          "Expecting a single-dimensional loop iteration space");
14842   for (auto &P : OriginalInits[0]) {
14843     if (auto *D = P.dyn_cast<Decl *>())
14844       PreInits.push_back(D);
14845     else if (auto *PI = dyn_cast_or_null<DeclStmt>(P.dyn_cast<Stmt *>()))
14846       PreInits.append(PI->decl_begin(), PI->decl_end());
14847   }
14848   if (auto *PI = cast_or_null<DeclStmt>(LoopHelper.PreInits))
14849     PreInits.append(PI->decl_begin(), PI->decl_end());
14850   // Gather declarations for the data members used as counters.
14851   for (Expr *CounterRef : LoopHelper.Counters) {
14852     auto *CounterDecl = cast<DeclRefExpr>(CounterRef)->getDecl();
14853     if (isa<OMPCapturedExprDecl>(CounterDecl))
14854       PreInits.push_back(CounterDecl);
14855   }
14856 
14857   auto *IterationVarRef = cast<DeclRefExpr>(LoopHelper.IterationVarRef);
14858   QualType IVTy = IterationVarRef->getType();
14859   assert(LoopHelper.Counters.size() == 1 &&
14860          "Expecting a single-dimensional loop iteration space");
14861   auto *OrigVar = cast<DeclRefExpr>(LoopHelper.Counters.front());
14862 
14863   // Determine the unroll factor.
14864   uint64_t Factor;
14865   SourceLocation FactorLoc;
14866   if (Expr *FactorVal = PartialClause->getFactor()) {
14867     Factor = FactorVal->getIntegerConstantExpr(Context)->getZExtValue();
14868     FactorLoc = FactorVal->getExprLoc();
14869   } else {
14870     // TODO: Use a better profitability model.
14871     Factor = 2;
14872   }
14873   assert(Factor > 0 && "Expected positive unroll factor");
14874   auto MakeFactorExpr = [this, Factor, IVTy, FactorLoc]() {
14875     return IntegerLiteral::Create(
14876         Context, llvm::APInt(Context.getIntWidth(IVTy), Factor), IVTy,
14877         FactorLoc);
14878   };
14879 
14880   // Iteration variable SourceLocations.
14881   SourceLocation OrigVarLoc = OrigVar->getExprLoc();
14882   SourceLocation OrigVarLocBegin = OrigVar->getBeginLoc();
14883   SourceLocation OrigVarLocEnd = OrigVar->getEndLoc();
14884 
14885   // Internal variable names.
14886   std::string OrigVarName = OrigVar->getNameInfo().getAsString();
14887   std::string OuterIVName = (Twine(".unrolled.iv.") + OrigVarName).str();
14888   std::string InnerIVName = (Twine(".unroll_inner.iv.") + OrigVarName).str();
14889   std::string InnerTripCountName =
14890       (Twine(".unroll_inner.tripcount.") + OrigVarName).str();
14891 
14892   // Create the iteration variable for the unrolled loop.
14893   VarDecl *OuterIVDecl =
14894       buildVarDecl(*this, {}, IVTy, OuterIVName, nullptr, OrigVar);
14895   auto MakeOuterRef = [this, OuterIVDecl, IVTy, OrigVarLoc]() {
14896     return buildDeclRefExpr(*this, OuterIVDecl, IVTy, OrigVarLoc);
14897   };
14898 
14899   // Iteration variable for the inner loop: Reuse the iteration variable created
14900   // by checkOpenMPLoop.
14901   auto *InnerIVDecl = cast<VarDecl>(IterationVarRef->getDecl());
14902   InnerIVDecl->setDeclName(&PP.getIdentifierTable().get(InnerIVName));
14903   auto MakeInnerRef = [this, InnerIVDecl, IVTy, OrigVarLoc]() {
14904     return buildDeclRefExpr(*this, InnerIVDecl, IVTy, OrigVarLoc);
14905   };
14906 
14907   // Make a copy of the NumIterations expression for each use: By the AST
14908   // constraints, every expression object in a DeclContext must be unique.
14909   CaptureVars CopyTransformer(*this);
14910   auto MakeNumIterations = [&CopyTransformer, &LoopHelper]() -> Expr * {
14911     return AssertSuccess(
14912         CopyTransformer.TransformExpr(LoopHelper.NumIterations));
14913   };
14914 
14915   // Inner For init-statement: auto .unroll_inner.iv = .unrolled.iv
14916   ExprResult LValueConv = DefaultLvalueConversion(MakeOuterRef());
14917   AddInitializerToDecl(InnerIVDecl, LValueConv.get(), /*DirectInit=*/false);
14918   StmtResult InnerInit = new (Context)
14919       DeclStmt(DeclGroupRef(InnerIVDecl), OrigVarLocBegin, OrigVarLocEnd);
14920   if (!InnerInit.isUsable())
14921     return StmtError();
14922 
14923   // Inner For cond-expression:
14924   // \code
14925   //   .unroll_inner.iv < .unrolled.iv + Factor &&
14926   //   .unroll_inner.iv < NumIterations
14927   // \endcode
14928   // This conjunction of two conditions allows ScalarEvolution to derive the
14929   // maximum trip count of the inner loop.
14930   ExprResult EndOfTile = BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(),
14931                                     BO_Add, MakeOuterRef(), MakeFactorExpr());
14932   if (!EndOfTile.isUsable())
14933     return StmtError();
14934   ExprResult InnerCond1 = BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(),
14935                                      BO_LT, MakeInnerRef(), EndOfTile.get());
14936   if (!InnerCond1.isUsable())
14937     return StmtError();
14938   ExprResult InnerCond2 =
14939       BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(), BO_LT, MakeInnerRef(),
14940                  MakeNumIterations());
14941   if (!InnerCond2.isUsable())
14942     return StmtError();
14943   ExprResult InnerCond =
14944       BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(), BO_LAnd,
14945                  InnerCond1.get(), InnerCond2.get());
14946   if (!InnerCond.isUsable())
14947     return StmtError();
14948 
14949   // Inner For incr-statement: ++.unroll_inner.iv
14950   ExprResult InnerIncr = BuildUnaryOp(CurScope, LoopHelper.Inc->getExprLoc(),
14951                                       UO_PreInc, MakeInnerRef());
14952   if (!InnerIncr.isUsable())
14953     return StmtError();
14954 
14955   // Inner For statement.
14956   SmallVector<Stmt *> InnerBodyStmts;
14957   InnerBodyStmts.append(LoopHelper.Updates.begin(), LoopHelper.Updates.end());
14958   InnerBodyStmts.push_back(Body);
14959   CompoundStmt *InnerBody =
14960       CompoundStmt::Create(Context, InnerBodyStmts, FPOptionsOverride(),
14961                            Body->getBeginLoc(), Body->getEndLoc());
14962   ForStmt *InnerFor = new (Context)
14963       ForStmt(Context, InnerInit.get(), InnerCond.get(), nullptr,
14964               InnerIncr.get(), InnerBody, LoopHelper.Init->getBeginLoc(),
14965               LoopHelper.Init->getBeginLoc(), LoopHelper.Inc->getEndLoc());
14966 
14967   // Unroll metadata for the inner loop.
14968   // This needs to take into account the remainder portion of the unrolled loop,
14969   // hence `unroll(full)` does not apply here, even though the LoopUnroll pass
14970   // supports multiple loop exits. Instead, unroll using a factor equivalent to
14971   // the maximum trip count, which will also generate a remainder loop. Just
14972   // `unroll(enable)` (which could have been useful if the user has not
14973   // specified a concrete factor; even though the outer loop cannot be
14974   // influenced anymore, would avoid more code bloat than necessary) will refuse
14975   // the loop because "Won't unroll; remainder loop could not be generated when
14976   // assuming runtime trip count". Even if it did work, it must not choose a
14977   // larger unroll factor than the maximum loop length, or it would always just
14978   // execute the remainder loop.
14979   LoopHintAttr *UnrollHintAttr =
14980       LoopHintAttr::CreateImplicit(Context, LoopHintAttr::UnrollCount,
14981                                    LoopHintAttr::Numeric, MakeFactorExpr());
14982   AttributedStmt *InnerUnrolled =
14983       AttributedStmt::Create(Context, StartLoc, {UnrollHintAttr}, InnerFor);
14984 
14985   // Outer For init-statement: auto .unrolled.iv = 0
14986   AddInitializerToDecl(
14987       OuterIVDecl, ActOnIntegerConstant(LoopHelper.Init->getExprLoc(), 0).get(),
14988       /*DirectInit=*/false);
14989   StmtResult OuterInit = new (Context)
14990       DeclStmt(DeclGroupRef(OuterIVDecl), OrigVarLocBegin, OrigVarLocEnd);
14991   if (!OuterInit.isUsable())
14992     return StmtError();
14993 
14994   // Outer For cond-expression: .unrolled.iv < NumIterations
14995   ExprResult OuterConde =
14996       BuildBinOp(CurScope, LoopHelper.Cond->getExprLoc(), BO_LT, MakeOuterRef(),
14997                  MakeNumIterations());
14998   if (!OuterConde.isUsable())
14999     return StmtError();
15000 
15001   // Outer For incr-statement: .unrolled.iv += Factor
15002   ExprResult OuterIncr =
15003       BuildBinOp(CurScope, LoopHelper.Inc->getExprLoc(), BO_AddAssign,
15004                  MakeOuterRef(), MakeFactorExpr());
15005   if (!OuterIncr.isUsable())
15006     return StmtError();
15007 
15008   // Outer For statement.
15009   ForStmt *OuterFor = new (Context)
15010       ForStmt(Context, OuterInit.get(), OuterConde.get(), nullptr,
15011               OuterIncr.get(), InnerUnrolled, LoopHelper.Init->getBeginLoc(),
15012               LoopHelper.Init->getBeginLoc(), LoopHelper.Inc->getEndLoc());
15013 
15014   return OMPUnrollDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt,
15015                                     NumGeneratedLoops, OuterFor,
15016                                     buildPreInits(Context, PreInits));
15017 }
15018 
15019 OMPClause *Sema::ActOnOpenMPSingleExprClause(OpenMPClauseKind Kind, Expr *Expr,
15020                                              SourceLocation StartLoc,
15021                                              SourceLocation LParenLoc,
15022                                              SourceLocation EndLoc) {
15023   OMPClause *Res = nullptr;
15024   switch (Kind) {
15025   case OMPC_final:
15026     Res = ActOnOpenMPFinalClause(Expr, StartLoc, LParenLoc, EndLoc);
15027     break;
15028   case OMPC_num_threads:
15029     Res = ActOnOpenMPNumThreadsClause(Expr, StartLoc, LParenLoc, EndLoc);
15030     break;
15031   case OMPC_safelen:
15032     Res = ActOnOpenMPSafelenClause(Expr, StartLoc, LParenLoc, EndLoc);
15033     break;
15034   case OMPC_simdlen:
15035     Res = ActOnOpenMPSimdlenClause(Expr, StartLoc, LParenLoc, EndLoc);
15036     break;
15037   case OMPC_allocator:
15038     Res = ActOnOpenMPAllocatorClause(Expr, StartLoc, LParenLoc, EndLoc);
15039     break;
15040   case OMPC_collapse:
15041     Res = ActOnOpenMPCollapseClause(Expr, StartLoc, LParenLoc, EndLoc);
15042     break;
15043   case OMPC_ordered:
15044     Res = ActOnOpenMPOrderedClause(StartLoc, EndLoc, LParenLoc, Expr);
15045     break;
15046   case OMPC_num_teams:
15047     Res = ActOnOpenMPNumTeamsClause(Expr, StartLoc, LParenLoc, EndLoc);
15048     break;
15049   case OMPC_thread_limit:
15050     Res = ActOnOpenMPThreadLimitClause(Expr, StartLoc, LParenLoc, EndLoc);
15051     break;
15052   case OMPC_priority:
15053     Res = ActOnOpenMPPriorityClause(Expr, StartLoc, LParenLoc, EndLoc);
15054     break;
15055   case OMPC_grainsize:
15056     Res = ActOnOpenMPGrainsizeClause(Expr, StartLoc, LParenLoc, EndLoc);
15057     break;
15058   case OMPC_num_tasks:
15059     Res = ActOnOpenMPNumTasksClause(Expr, StartLoc, LParenLoc, EndLoc);
15060     break;
15061   case OMPC_hint:
15062     Res = ActOnOpenMPHintClause(Expr, StartLoc, LParenLoc, EndLoc);
15063     break;
15064   case OMPC_depobj:
15065     Res = ActOnOpenMPDepobjClause(Expr, StartLoc, LParenLoc, EndLoc);
15066     break;
15067   case OMPC_detach:
15068     Res = ActOnOpenMPDetachClause(Expr, StartLoc, LParenLoc, EndLoc);
15069     break;
15070   case OMPC_novariants:
15071     Res = ActOnOpenMPNovariantsClause(Expr, StartLoc, LParenLoc, EndLoc);
15072     break;
15073   case OMPC_nocontext:
15074     Res = ActOnOpenMPNocontextClause(Expr, StartLoc, LParenLoc, EndLoc);
15075     break;
15076   case OMPC_filter:
15077     Res = ActOnOpenMPFilterClause(Expr, StartLoc, LParenLoc, EndLoc);
15078     break;
15079   case OMPC_partial:
15080     Res = ActOnOpenMPPartialClause(Expr, StartLoc, LParenLoc, EndLoc);
15081     break;
15082   case OMPC_align:
15083     Res = ActOnOpenMPAlignClause(Expr, StartLoc, LParenLoc, EndLoc);
15084     break;
15085   case OMPC_device:
15086   case OMPC_if:
15087   case OMPC_default:
15088   case OMPC_proc_bind:
15089   case OMPC_schedule:
15090   case OMPC_private:
15091   case OMPC_firstprivate:
15092   case OMPC_lastprivate:
15093   case OMPC_shared:
15094   case OMPC_reduction:
15095   case OMPC_task_reduction:
15096   case OMPC_in_reduction:
15097   case OMPC_linear:
15098   case OMPC_aligned:
15099   case OMPC_copyin:
15100   case OMPC_copyprivate:
15101   case OMPC_nowait:
15102   case OMPC_untied:
15103   case OMPC_mergeable:
15104   case OMPC_threadprivate:
15105   case OMPC_sizes:
15106   case OMPC_allocate:
15107   case OMPC_flush:
15108   case OMPC_read:
15109   case OMPC_write:
15110   case OMPC_update:
15111   case OMPC_capture:
15112   case OMPC_compare:
15113   case OMPC_seq_cst:
15114   case OMPC_acq_rel:
15115   case OMPC_acquire:
15116   case OMPC_release:
15117   case OMPC_relaxed:
15118   case OMPC_depend:
15119   case OMPC_threads:
15120   case OMPC_simd:
15121   case OMPC_map:
15122   case OMPC_nogroup:
15123   case OMPC_dist_schedule:
15124   case OMPC_defaultmap:
15125   case OMPC_unknown:
15126   case OMPC_uniform:
15127   case OMPC_to:
15128   case OMPC_from:
15129   case OMPC_use_device_ptr:
15130   case OMPC_use_device_addr:
15131   case OMPC_is_device_ptr:
15132   case OMPC_unified_address:
15133   case OMPC_unified_shared_memory:
15134   case OMPC_reverse_offload:
15135   case OMPC_dynamic_allocators:
15136   case OMPC_atomic_default_mem_order:
15137   case OMPC_device_type:
15138   case OMPC_match:
15139   case OMPC_nontemporal:
15140   case OMPC_order:
15141   case OMPC_destroy:
15142   case OMPC_inclusive:
15143   case OMPC_exclusive:
15144   case OMPC_uses_allocators:
15145   case OMPC_affinity:
15146   case OMPC_when:
15147   case OMPC_bind:
15148   default:
15149     llvm_unreachable("Clause is not allowed.");
15150   }
15151   return Res;
15152 }
15153 
15154 // An OpenMP directive such as 'target parallel' has two captured regions:
15155 // for the 'target' and 'parallel' respectively.  This function returns
15156 // the region in which to capture expressions associated with a clause.
15157 // A return value of OMPD_unknown signifies that the expression should not
15158 // be captured.
15159 static OpenMPDirectiveKind getOpenMPCaptureRegionForClause(
15160     OpenMPDirectiveKind DKind, OpenMPClauseKind CKind, unsigned OpenMPVersion,
15161     OpenMPDirectiveKind NameModifier = OMPD_unknown) {
15162   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
15163   switch (CKind) {
15164   case OMPC_if:
15165     switch (DKind) {
15166     case OMPD_target_parallel_for_simd:
15167       if (OpenMPVersion >= 50 &&
15168           (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)) {
15169         CaptureRegion = OMPD_parallel;
15170         break;
15171       }
15172       LLVM_FALLTHROUGH;
15173     case OMPD_target_parallel:
15174     case OMPD_target_parallel_for:
15175     case OMPD_target_parallel_loop:
15176       // If this clause applies to the nested 'parallel' region, capture within
15177       // the 'target' region, otherwise do not capture.
15178       if (NameModifier == OMPD_unknown || NameModifier == OMPD_parallel)
15179         CaptureRegion = OMPD_target;
15180       break;
15181     case OMPD_target_teams_distribute_parallel_for_simd:
15182       if (OpenMPVersion >= 50 &&
15183           (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)) {
15184         CaptureRegion = OMPD_parallel;
15185         break;
15186       }
15187       LLVM_FALLTHROUGH;
15188     case OMPD_target_teams_distribute_parallel_for:
15189       // If this clause applies to the nested 'parallel' region, capture within
15190       // the 'teams' region, otherwise do not capture.
15191       if (NameModifier == OMPD_unknown || NameModifier == OMPD_parallel)
15192         CaptureRegion = OMPD_teams;
15193       break;
15194     case OMPD_teams_distribute_parallel_for_simd:
15195       if (OpenMPVersion >= 50 &&
15196           (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)) {
15197         CaptureRegion = OMPD_parallel;
15198         break;
15199       }
15200       LLVM_FALLTHROUGH;
15201     case OMPD_teams_distribute_parallel_for:
15202       CaptureRegion = OMPD_teams;
15203       break;
15204     case OMPD_target_update:
15205     case OMPD_target_enter_data:
15206     case OMPD_target_exit_data:
15207       CaptureRegion = OMPD_task;
15208       break;
15209     case OMPD_parallel_masked_taskloop:
15210       if (NameModifier == OMPD_unknown || NameModifier == OMPD_taskloop)
15211         CaptureRegion = OMPD_parallel;
15212       break;
15213     case OMPD_parallel_master_taskloop:
15214       if (NameModifier == OMPD_unknown || NameModifier == OMPD_taskloop)
15215         CaptureRegion = OMPD_parallel;
15216       break;
15217     case OMPD_parallel_masked_taskloop_simd:
15218       if ((OpenMPVersion <= 45 && NameModifier == OMPD_unknown) ||
15219           NameModifier == OMPD_taskloop) {
15220         CaptureRegion = OMPD_parallel;
15221         break;
15222       }
15223       if (OpenMPVersion <= 45)
15224         break;
15225       if (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)
15226         CaptureRegion = OMPD_taskloop;
15227       break;
15228     case OMPD_parallel_master_taskloop_simd:
15229       if ((OpenMPVersion <= 45 && NameModifier == OMPD_unknown) ||
15230           NameModifier == OMPD_taskloop) {
15231         CaptureRegion = OMPD_parallel;
15232         break;
15233       }
15234       if (OpenMPVersion <= 45)
15235         break;
15236       if (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)
15237         CaptureRegion = OMPD_taskloop;
15238       break;
15239     case OMPD_parallel_for_simd:
15240       if (OpenMPVersion <= 45)
15241         break;
15242       if (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)
15243         CaptureRegion = OMPD_parallel;
15244       break;
15245     case OMPD_taskloop_simd:
15246     case OMPD_master_taskloop_simd:
15247     case OMPD_masked_taskloop_simd:
15248       if (OpenMPVersion <= 45)
15249         break;
15250       if (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)
15251         CaptureRegion = OMPD_taskloop;
15252       break;
15253     case OMPD_distribute_parallel_for_simd:
15254       if (OpenMPVersion <= 45)
15255         break;
15256       if (NameModifier == OMPD_unknown || NameModifier == OMPD_simd)
15257         CaptureRegion = OMPD_parallel;
15258       break;
15259     case OMPD_target_simd:
15260       if (OpenMPVersion >= 50 &&
15261           (NameModifier == OMPD_unknown || NameModifier == OMPD_simd))
15262         CaptureRegion = OMPD_target;
15263       break;
15264     case OMPD_teams_distribute_simd:
15265     case OMPD_target_teams_distribute_simd:
15266       if (OpenMPVersion >= 50 &&
15267           (NameModifier == OMPD_unknown || NameModifier == OMPD_simd))
15268         CaptureRegion = OMPD_teams;
15269       break;
15270     case OMPD_cancel:
15271     case OMPD_parallel:
15272     case OMPD_parallel_master:
15273     case OMPD_parallel_masked:
15274     case OMPD_parallel_sections:
15275     case OMPD_parallel_for:
15276     case OMPD_parallel_loop:
15277     case OMPD_target:
15278     case OMPD_target_teams:
15279     case OMPD_target_teams_distribute:
15280     case OMPD_target_teams_loop:
15281     case OMPD_distribute_parallel_for:
15282     case OMPD_task:
15283     case OMPD_taskloop:
15284     case OMPD_master_taskloop:
15285     case OMPD_masked_taskloop:
15286     case OMPD_target_data:
15287     case OMPD_simd:
15288     case OMPD_for_simd:
15289     case OMPD_distribute_simd:
15290       // Do not capture if-clause expressions.
15291       break;
15292     case OMPD_threadprivate:
15293     case OMPD_allocate:
15294     case OMPD_taskyield:
15295     case OMPD_barrier:
15296     case OMPD_taskwait:
15297     case OMPD_cancellation_point:
15298     case OMPD_flush:
15299     case OMPD_depobj:
15300     case OMPD_scan:
15301     case OMPD_declare_reduction:
15302     case OMPD_declare_mapper:
15303     case OMPD_declare_simd:
15304     case OMPD_declare_variant:
15305     case OMPD_begin_declare_variant:
15306     case OMPD_end_declare_variant:
15307     case OMPD_declare_target:
15308     case OMPD_end_declare_target:
15309     case OMPD_loop:
15310     case OMPD_teams_loop:
15311     case OMPD_teams:
15312     case OMPD_tile:
15313     case OMPD_unroll:
15314     case OMPD_for:
15315     case OMPD_sections:
15316     case OMPD_section:
15317     case OMPD_single:
15318     case OMPD_master:
15319     case OMPD_masked:
15320     case OMPD_critical:
15321     case OMPD_taskgroup:
15322     case OMPD_distribute:
15323     case OMPD_ordered:
15324     case OMPD_atomic:
15325     case OMPD_teams_distribute:
15326     case OMPD_requires:
15327     case OMPD_metadirective:
15328       llvm_unreachable("Unexpected OpenMP directive with if-clause");
15329     case OMPD_unknown:
15330     default:
15331       llvm_unreachable("Unknown OpenMP directive");
15332     }
15333     break;
15334   case OMPC_num_threads:
15335     switch (DKind) {
15336     case OMPD_target_parallel:
15337     case OMPD_target_parallel_for:
15338     case OMPD_target_parallel_for_simd:
15339     case OMPD_target_parallel_loop:
15340       CaptureRegion = OMPD_target;
15341       break;
15342     case OMPD_teams_distribute_parallel_for:
15343     case OMPD_teams_distribute_parallel_for_simd:
15344     case OMPD_target_teams_distribute_parallel_for:
15345     case OMPD_target_teams_distribute_parallel_for_simd:
15346       CaptureRegion = OMPD_teams;
15347       break;
15348     case OMPD_parallel:
15349     case OMPD_parallel_master:
15350     case OMPD_parallel_masked:
15351     case OMPD_parallel_sections:
15352     case OMPD_parallel_for:
15353     case OMPD_parallel_for_simd:
15354     case OMPD_parallel_loop:
15355     case OMPD_distribute_parallel_for:
15356     case OMPD_distribute_parallel_for_simd:
15357     case OMPD_parallel_master_taskloop:
15358     case OMPD_parallel_masked_taskloop:
15359     case OMPD_parallel_master_taskloop_simd:
15360     case OMPD_parallel_masked_taskloop_simd:
15361       // Do not capture num_threads-clause expressions.
15362       break;
15363     case OMPD_target_data:
15364     case OMPD_target_enter_data:
15365     case OMPD_target_exit_data:
15366     case OMPD_target_update:
15367     case OMPD_target:
15368     case OMPD_target_simd:
15369     case OMPD_target_teams:
15370     case OMPD_target_teams_distribute:
15371     case OMPD_target_teams_distribute_simd:
15372     case OMPD_cancel:
15373     case OMPD_task:
15374     case OMPD_taskloop:
15375     case OMPD_taskloop_simd:
15376     case OMPD_master_taskloop:
15377     case OMPD_masked_taskloop:
15378     case OMPD_master_taskloop_simd:
15379     case OMPD_masked_taskloop_simd:
15380     case OMPD_threadprivate:
15381     case OMPD_allocate:
15382     case OMPD_taskyield:
15383     case OMPD_barrier:
15384     case OMPD_taskwait:
15385     case OMPD_cancellation_point:
15386     case OMPD_flush:
15387     case OMPD_depobj:
15388     case OMPD_scan:
15389     case OMPD_declare_reduction:
15390     case OMPD_declare_mapper:
15391     case OMPD_declare_simd:
15392     case OMPD_declare_variant:
15393     case OMPD_begin_declare_variant:
15394     case OMPD_end_declare_variant:
15395     case OMPD_declare_target:
15396     case OMPD_end_declare_target:
15397     case OMPD_loop:
15398     case OMPD_teams_loop:
15399     case OMPD_target_teams_loop:
15400     case OMPD_teams:
15401     case OMPD_simd:
15402     case OMPD_tile:
15403     case OMPD_unroll:
15404     case OMPD_for:
15405     case OMPD_for_simd:
15406     case OMPD_sections:
15407     case OMPD_section:
15408     case OMPD_single:
15409     case OMPD_master:
15410     case OMPD_masked:
15411     case OMPD_critical:
15412     case OMPD_taskgroup:
15413     case OMPD_distribute:
15414     case OMPD_ordered:
15415     case OMPD_atomic:
15416     case OMPD_distribute_simd:
15417     case OMPD_teams_distribute:
15418     case OMPD_teams_distribute_simd:
15419     case OMPD_requires:
15420     case OMPD_metadirective:
15421       llvm_unreachable("Unexpected OpenMP directive with num_threads-clause");
15422     case OMPD_unknown:
15423     default:
15424       llvm_unreachable("Unknown OpenMP directive");
15425     }
15426     break;
15427   case OMPC_num_teams:
15428     switch (DKind) {
15429     case OMPD_target_teams:
15430     case OMPD_target_teams_distribute:
15431     case OMPD_target_teams_distribute_simd:
15432     case OMPD_target_teams_distribute_parallel_for:
15433     case OMPD_target_teams_distribute_parallel_for_simd:
15434     case OMPD_target_teams_loop:
15435       CaptureRegion = OMPD_target;
15436       break;
15437     case OMPD_teams_distribute_parallel_for:
15438     case OMPD_teams_distribute_parallel_for_simd:
15439     case OMPD_teams:
15440     case OMPD_teams_distribute:
15441     case OMPD_teams_distribute_simd:
15442     case OMPD_teams_loop:
15443       // Do not capture num_teams-clause expressions.
15444       break;
15445     case OMPD_distribute_parallel_for:
15446     case OMPD_distribute_parallel_for_simd:
15447     case OMPD_task:
15448     case OMPD_taskloop:
15449     case OMPD_taskloop_simd:
15450     case OMPD_master_taskloop:
15451     case OMPD_masked_taskloop:
15452     case OMPD_master_taskloop_simd:
15453     case OMPD_masked_taskloop_simd:
15454     case OMPD_parallel_master_taskloop:
15455     case OMPD_parallel_masked_taskloop:
15456     case OMPD_parallel_master_taskloop_simd:
15457     case OMPD_parallel_masked_taskloop_simd:
15458     case OMPD_target_data:
15459     case OMPD_target_enter_data:
15460     case OMPD_target_exit_data:
15461     case OMPD_target_update:
15462     case OMPD_cancel:
15463     case OMPD_parallel:
15464     case OMPD_parallel_master:
15465     case OMPD_parallel_masked:
15466     case OMPD_parallel_sections:
15467     case OMPD_parallel_for:
15468     case OMPD_parallel_for_simd:
15469     case OMPD_parallel_loop:
15470     case OMPD_target:
15471     case OMPD_target_simd:
15472     case OMPD_target_parallel:
15473     case OMPD_target_parallel_for:
15474     case OMPD_target_parallel_for_simd:
15475     case OMPD_target_parallel_loop:
15476     case OMPD_threadprivate:
15477     case OMPD_allocate:
15478     case OMPD_taskyield:
15479     case OMPD_barrier:
15480     case OMPD_taskwait:
15481     case OMPD_cancellation_point:
15482     case OMPD_flush:
15483     case OMPD_depobj:
15484     case OMPD_scan:
15485     case OMPD_declare_reduction:
15486     case OMPD_declare_mapper:
15487     case OMPD_declare_simd:
15488     case OMPD_declare_variant:
15489     case OMPD_begin_declare_variant:
15490     case OMPD_end_declare_variant:
15491     case OMPD_declare_target:
15492     case OMPD_end_declare_target:
15493     case OMPD_loop:
15494     case OMPD_simd:
15495     case OMPD_tile:
15496     case OMPD_unroll:
15497     case OMPD_for:
15498     case OMPD_for_simd:
15499     case OMPD_sections:
15500     case OMPD_section:
15501     case OMPD_single:
15502     case OMPD_master:
15503     case OMPD_masked:
15504     case OMPD_critical:
15505     case OMPD_taskgroup:
15506     case OMPD_distribute:
15507     case OMPD_ordered:
15508     case OMPD_atomic:
15509     case OMPD_distribute_simd:
15510     case OMPD_requires:
15511     case OMPD_metadirective:
15512       llvm_unreachable("Unexpected OpenMP directive with num_teams-clause");
15513     case OMPD_unknown:
15514     default:
15515       llvm_unreachable("Unknown OpenMP directive");
15516     }
15517     break;
15518   case OMPC_thread_limit:
15519     switch (DKind) {
15520     case OMPD_target_teams:
15521     case OMPD_target_teams_distribute:
15522     case OMPD_target_teams_distribute_simd:
15523     case OMPD_target_teams_distribute_parallel_for:
15524     case OMPD_target_teams_distribute_parallel_for_simd:
15525     case OMPD_target_teams_loop:
15526       CaptureRegion = OMPD_target;
15527       break;
15528     case OMPD_teams_distribute_parallel_for:
15529     case OMPD_teams_distribute_parallel_for_simd:
15530     case OMPD_teams:
15531     case OMPD_teams_distribute:
15532     case OMPD_teams_distribute_simd:
15533     case OMPD_teams_loop:
15534       // Do not capture thread_limit-clause expressions.
15535       break;
15536     case OMPD_distribute_parallel_for:
15537     case OMPD_distribute_parallel_for_simd:
15538     case OMPD_task:
15539     case OMPD_taskloop:
15540     case OMPD_taskloop_simd:
15541     case OMPD_master_taskloop:
15542     case OMPD_masked_taskloop:
15543     case OMPD_master_taskloop_simd:
15544     case OMPD_masked_taskloop_simd:
15545     case OMPD_parallel_master_taskloop:
15546     case OMPD_parallel_masked_taskloop:
15547     case OMPD_parallel_master_taskloop_simd:
15548     case OMPD_parallel_masked_taskloop_simd:
15549     case OMPD_target_data:
15550     case OMPD_target_enter_data:
15551     case OMPD_target_exit_data:
15552     case OMPD_target_update:
15553     case OMPD_cancel:
15554     case OMPD_parallel:
15555     case OMPD_parallel_master:
15556     case OMPD_parallel_masked:
15557     case OMPD_parallel_sections:
15558     case OMPD_parallel_for:
15559     case OMPD_parallel_for_simd:
15560     case OMPD_parallel_loop:
15561     case OMPD_target:
15562     case OMPD_target_simd:
15563     case OMPD_target_parallel:
15564     case OMPD_target_parallel_for:
15565     case OMPD_target_parallel_for_simd:
15566     case OMPD_target_parallel_loop:
15567     case OMPD_threadprivate:
15568     case OMPD_allocate:
15569     case OMPD_taskyield:
15570     case OMPD_barrier:
15571     case OMPD_taskwait:
15572     case OMPD_cancellation_point:
15573     case OMPD_flush:
15574     case OMPD_depobj:
15575     case OMPD_scan:
15576     case OMPD_declare_reduction:
15577     case OMPD_declare_mapper:
15578     case OMPD_declare_simd:
15579     case OMPD_declare_variant:
15580     case OMPD_begin_declare_variant:
15581     case OMPD_end_declare_variant:
15582     case OMPD_declare_target:
15583     case OMPD_end_declare_target:
15584     case OMPD_loop:
15585     case OMPD_simd:
15586     case OMPD_tile:
15587     case OMPD_unroll:
15588     case OMPD_for:
15589     case OMPD_for_simd:
15590     case OMPD_sections:
15591     case OMPD_section:
15592     case OMPD_single:
15593     case OMPD_master:
15594     case OMPD_masked:
15595     case OMPD_critical:
15596     case OMPD_taskgroup:
15597     case OMPD_distribute:
15598     case OMPD_ordered:
15599     case OMPD_atomic:
15600     case OMPD_distribute_simd:
15601     case OMPD_requires:
15602     case OMPD_metadirective:
15603       llvm_unreachable("Unexpected OpenMP directive with thread_limit-clause");
15604     case OMPD_unknown:
15605     default:
15606       llvm_unreachable("Unknown OpenMP directive");
15607     }
15608     break;
15609   case OMPC_schedule:
15610     switch (DKind) {
15611     case OMPD_parallel_for:
15612     case OMPD_parallel_for_simd:
15613     case OMPD_distribute_parallel_for:
15614     case OMPD_distribute_parallel_for_simd:
15615     case OMPD_teams_distribute_parallel_for:
15616     case OMPD_teams_distribute_parallel_for_simd:
15617     case OMPD_target_parallel_for:
15618     case OMPD_target_parallel_for_simd:
15619     case OMPD_target_teams_distribute_parallel_for:
15620     case OMPD_target_teams_distribute_parallel_for_simd:
15621       CaptureRegion = OMPD_parallel;
15622       break;
15623     case OMPD_for:
15624     case OMPD_for_simd:
15625       // Do not capture schedule-clause expressions.
15626       break;
15627     case OMPD_task:
15628     case OMPD_taskloop:
15629     case OMPD_taskloop_simd:
15630     case OMPD_master_taskloop:
15631     case OMPD_masked_taskloop:
15632     case OMPD_master_taskloop_simd:
15633     case OMPD_masked_taskloop_simd:
15634     case OMPD_parallel_master_taskloop:
15635     case OMPD_parallel_masked_taskloop:
15636     case OMPD_parallel_master_taskloop_simd:
15637     case OMPD_parallel_masked_taskloop_simd:
15638     case OMPD_target_data:
15639     case OMPD_target_enter_data:
15640     case OMPD_target_exit_data:
15641     case OMPD_target_update:
15642     case OMPD_teams:
15643     case OMPD_teams_distribute:
15644     case OMPD_teams_distribute_simd:
15645     case OMPD_target_teams_distribute:
15646     case OMPD_target_teams_distribute_simd:
15647     case OMPD_target:
15648     case OMPD_target_simd:
15649     case OMPD_target_parallel:
15650     case OMPD_cancel:
15651     case OMPD_parallel:
15652     case OMPD_parallel_master:
15653     case OMPD_parallel_masked:
15654     case OMPD_parallel_sections:
15655     case OMPD_threadprivate:
15656     case OMPD_allocate:
15657     case OMPD_taskyield:
15658     case OMPD_barrier:
15659     case OMPD_taskwait:
15660     case OMPD_cancellation_point:
15661     case OMPD_flush:
15662     case OMPD_depobj:
15663     case OMPD_scan:
15664     case OMPD_declare_reduction:
15665     case OMPD_declare_mapper:
15666     case OMPD_declare_simd:
15667     case OMPD_declare_variant:
15668     case OMPD_begin_declare_variant:
15669     case OMPD_end_declare_variant:
15670     case OMPD_declare_target:
15671     case OMPD_end_declare_target:
15672     case OMPD_loop:
15673     case OMPD_teams_loop:
15674     case OMPD_target_teams_loop:
15675     case OMPD_parallel_loop:
15676     case OMPD_target_parallel_loop:
15677     case OMPD_simd:
15678     case OMPD_tile:
15679     case OMPD_unroll:
15680     case OMPD_sections:
15681     case OMPD_section:
15682     case OMPD_single:
15683     case OMPD_master:
15684     case OMPD_masked:
15685     case OMPD_critical:
15686     case OMPD_taskgroup:
15687     case OMPD_distribute:
15688     case OMPD_ordered:
15689     case OMPD_atomic:
15690     case OMPD_distribute_simd:
15691     case OMPD_target_teams:
15692     case OMPD_requires:
15693     case OMPD_metadirective:
15694       llvm_unreachable("Unexpected OpenMP directive with schedule clause");
15695     case OMPD_unknown:
15696     default:
15697       llvm_unreachable("Unknown OpenMP directive");
15698     }
15699     break;
15700   case OMPC_dist_schedule:
15701     switch (DKind) {
15702     case OMPD_teams_distribute_parallel_for:
15703     case OMPD_teams_distribute_parallel_for_simd:
15704     case OMPD_teams_distribute:
15705     case OMPD_teams_distribute_simd:
15706     case OMPD_target_teams_distribute_parallel_for:
15707     case OMPD_target_teams_distribute_parallel_for_simd:
15708     case OMPD_target_teams_distribute:
15709     case OMPD_target_teams_distribute_simd:
15710       CaptureRegion = OMPD_teams;
15711       break;
15712     case OMPD_distribute_parallel_for:
15713     case OMPD_distribute_parallel_for_simd:
15714     case OMPD_distribute:
15715     case OMPD_distribute_simd:
15716       // Do not capture dist_schedule-clause expressions.
15717       break;
15718     case OMPD_parallel_for:
15719     case OMPD_parallel_for_simd:
15720     case OMPD_target_parallel_for_simd:
15721     case OMPD_target_parallel_for:
15722     case OMPD_task:
15723     case OMPD_taskloop:
15724     case OMPD_taskloop_simd:
15725     case OMPD_master_taskloop:
15726     case OMPD_masked_taskloop:
15727     case OMPD_master_taskloop_simd:
15728     case OMPD_masked_taskloop_simd:
15729     case OMPD_parallel_master_taskloop:
15730     case OMPD_parallel_masked_taskloop:
15731     case OMPD_parallel_master_taskloop_simd:
15732     case OMPD_parallel_masked_taskloop_simd:
15733     case OMPD_target_data:
15734     case OMPD_target_enter_data:
15735     case OMPD_target_exit_data:
15736     case OMPD_target_update:
15737     case OMPD_teams:
15738     case OMPD_target:
15739     case OMPD_target_simd:
15740     case OMPD_target_parallel:
15741     case OMPD_cancel:
15742     case OMPD_parallel:
15743     case OMPD_parallel_master:
15744     case OMPD_parallel_masked:
15745     case OMPD_parallel_sections:
15746     case OMPD_threadprivate:
15747     case OMPD_allocate:
15748     case OMPD_taskyield:
15749     case OMPD_barrier:
15750     case OMPD_taskwait:
15751     case OMPD_cancellation_point:
15752     case OMPD_flush:
15753     case OMPD_depobj:
15754     case OMPD_scan:
15755     case OMPD_declare_reduction:
15756     case OMPD_declare_mapper:
15757     case OMPD_declare_simd:
15758     case OMPD_declare_variant:
15759     case OMPD_begin_declare_variant:
15760     case OMPD_end_declare_variant:
15761     case OMPD_declare_target:
15762     case OMPD_end_declare_target:
15763     case OMPD_loop:
15764     case OMPD_teams_loop:
15765     case OMPD_target_teams_loop:
15766     case OMPD_parallel_loop:
15767     case OMPD_target_parallel_loop:
15768     case OMPD_simd:
15769     case OMPD_tile:
15770     case OMPD_unroll:
15771     case OMPD_for:
15772     case OMPD_for_simd:
15773     case OMPD_sections:
15774     case OMPD_section:
15775     case OMPD_single:
15776     case OMPD_master:
15777     case OMPD_masked:
15778     case OMPD_critical:
15779     case OMPD_taskgroup:
15780     case OMPD_ordered:
15781     case OMPD_atomic:
15782     case OMPD_target_teams:
15783     case OMPD_requires:
15784     case OMPD_metadirective:
15785       llvm_unreachable("Unexpected OpenMP directive with dist_schedule clause");
15786     case OMPD_unknown:
15787     default:
15788       llvm_unreachable("Unknown OpenMP directive");
15789     }
15790     break;
15791   case OMPC_device:
15792     switch (DKind) {
15793     case OMPD_target_update:
15794     case OMPD_target_enter_data:
15795     case OMPD_target_exit_data:
15796     case OMPD_target:
15797     case OMPD_target_simd:
15798     case OMPD_target_teams:
15799     case OMPD_target_parallel:
15800     case OMPD_target_teams_distribute:
15801     case OMPD_target_teams_distribute_simd:
15802     case OMPD_target_parallel_for:
15803     case OMPD_target_parallel_for_simd:
15804     case OMPD_target_parallel_loop:
15805     case OMPD_target_teams_distribute_parallel_for:
15806     case OMPD_target_teams_distribute_parallel_for_simd:
15807     case OMPD_target_teams_loop:
15808     case OMPD_dispatch:
15809       CaptureRegion = OMPD_task;
15810       break;
15811     case OMPD_target_data:
15812     case OMPD_interop:
15813       // Do not capture device-clause expressions.
15814       break;
15815     case OMPD_teams_distribute_parallel_for:
15816     case OMPD_teams_distribute_parallel_for_simd:
15817     case OMPD_teams:
15818     case OMPD_teams_distribute:
15819     case OMPD_teams_distribute_simd:
15820     case OMPD_distribute_parallel_for:
15821     case OMPD_distribute_parallel_for_simd:
15822     case OMPD_task:
15823     case OMPD_taskloop:
15824     case OMPD_taskloop_simd:
15825     case OMPD_master_taskloop:
15826     case OMPD_masked_taskloop:
15827     case OMPD_master_taskloop_simd:
15828     case OMPD_masked_taskloop_simd:
15829     case OMPD_parallel_master_taskloop:
15830     case OMPD_parallel_masked_taskloop:
15831     case OMPD_parallel_master_taskloop_simd:
15832     case OMPD_parallel_masked_taskloop_simd:
15833     case OMPD_cancel:
15834     case OMPD_parallel:
15835     case OMPD_parallel_master:
15836     case OMPD_parallel_masked:
15837     case OMPD_parallel_sections:
15838     case OMPD_parallel_for:
15839     case OMPD_parallel_for_simd:
15840     case OMPD_threadprivate:
15841     case OMPD_allocate:
15842     case OMPD_taskyield:
15843     case OMPD_barrier:
15844     case OMPD_taskwait:
15845     case OMPD_cancellation_point:
15846     case OMPD_flush:
15847     case OMPD_depobj:
15848     case OMPD_scan:
15849     case OMPD_declare_reduction:
15850     case OMPD_declare_mapper:
15851     case OMPD_declare_simd:
15852     case OMPD_declare_variant:
15853     case OMPD_begin_declare_variant:
15854     case OMPD_end_declare_variant:
15855     case OMPD_declare_target:
15856     case OMPD_end_declare_target:
15857     case OMPD_loop:
15858     case OMPD_teams_loop:
15859     case OMPD_parallel_loop:
15860     case OMPD_simd:
15861     case OMPD_tile:
15862     case OMPD_unroll:
15863     case OMPD_for:
15864     case OMPD_for_simd:
15865     case OMPD_sections:
15866     case OMPD_section:
15867     case OMPD_single:
15868     case OMPD_master:
15869     case OMPD_masked:
15870     case OMPD_critical:
15871     case OMPD_taskgroup:
15872     case OMPD_distribute:
15873     case OMPD_ordered:
15874     case OMPD_atomic:
15875     case OMPD_distribute_simd:
15876     case OMPD_requires:
15877     case OMPD_metadirective:
15878       llvm_unreachable("Unexpected OpenMP directive with device-clause");
15879     case OMPD_unknown:
15880     default:
15881       llvm_unreachable("Unknown OpenMP directive");
15882     }
15883     break;
15884   case OMPC_grainsize:
15885   case OMPC_num_tasks:
15886   case OMPC_final:
15887   case OMPC_priority:
15888     switch (DKind) {
15889     case OMPD_task:
15890     case OMPD_taskloop:
15891     case OMPD_taskloop_simd:
15892     case OMPD_master_taskloop:
15893     case OMPD_masked_taskloop:
15894     case OMPD_master_taskloop_simd:
15895     case OMPD_masked_taskloop_simd:
15896       break;
15897     case OMPD_parallel_masked_taskloop:
15898     case OMPD_parallel_masked_taskloop_simd:
15899     case OMPD_parallel_master_taskloop:
15900     case OMPD_parallel_master_taskloop_simd:
15901       CaptureRegion = OMPD_parallel;
15902       break;
15903     case OMPD_target_update:
15904     case OMPD_target_enter_data:
15905     case OMPD_target_exit_data:
15906     case OMPD_target:
15907     case OMPD_target_simd:
15908     case OMPD_target_teams:
15909     case OMPD_target_parallel:
15910     case OMPD_target_teams_distribute:
15911     case OMPD_target_teams_distribute_simd:
15912     case OMPD_target_parallel_for:
15913     case OMPD_target_parallel_for_simd:
15914     case OMPD_target_teams_distribute_parallel_for:
15915     case OMPD_target_teams_distribute_parallel_for_simd:
15916     case OMPD_target_data:
15917     case OMPD_teams_distribute_parallel_for:
15918     case OMPD_teams_distribute_parallel_for_simd:
15919     case OMPD_teams:
15920     case OMPD_teams_distribute:
15921     case OMPD_teams_distribute_simd:
15922     case OMPD_distribute_parallel_for:
15923     case OMPD_distribute_parallel_for_simd:
15924     case OMPD_cancel:
15925     case OMPD_parallel:
15926     case OMPD_parallel_master:
15927     case OMPD_parallel_masked:
15928     case OMPD_parallel_sections:
15929     case OMPD_parallel_for:
15930     case OMPD_parallel_for_simd:
15931     case OMPD_threadprivate:
15932     case OMPD_allocate:
15933     case OMPD_taskyield:
15934     case OMPD_barrier:
15935     case OMPD_taskwait:
15936     case OMPD_cancellation_point:
15937     case OMPD_flush:
15938     case OMPD_depobj:
15939     case OMPD_scan:
15940     case OMPD_declare_reduction:
15941     case OMPD_declare_mapper:
15942     case OMPD_declare_simd:
15943     case OMPD_declare_variant:
15944     case OMPD_begin_declare_variant:
15945     case OMPD_end_declare_variant:
15946     case OMPD_declare_target:
15947     case OMPD_end_declare_target:
15948     case OMPD_loop:
15949     case OMPD_teams_loop:
15950     case OMPD_target_teams_loop:
15951     case OMPD_parallel_loop:
15952     case OMPD_target_parallel_loop:
15953     case OMPD_simd:
15954     case OMPD_tile:
15955     case OMPD_unroll:
15956     case OMPD_for:
15957     case OMPD_for_simd:
15958     case OMPD_sections:
15959     case OMPD_section:
15960     case OMPD_single:
15961     case OMPD_master:
15962     case OMPD_masked:
15963     case OMPD_critical:
15964     case OMPD_taskgroup:
15965     case OMPD_distribute:
15966     case OMPD_ordered:
15967     case OMPD_atomic:
15968     case OMPD_distribute_simd:
15969     case OMPD_requires:
15970     case OMPD_metadirective:
15971       llvm_unreachable("Unexpected OpenMP directive with grainsize-clause");
15972     case OMPD_unknown:
15973     default:
15974       llvm_unreachable("Unknown OpenMP directive");
15975     }
15976     break;
15977   case OMPC_novariants:
15978   case OMPC_nocontext:
15979     switch (DKind) {
15980     case OMPD_dispatch:
15981       CaptureRegion = OMPD_task;
15982       break;
15983     default:
15984       llvm_unreachable("Unexpected OpenMP directive");
15985     }
15986     break;
15987   case OMPC_filter:
15988     // Do not capture filter-clause expressions.
15989     break;
15990   case OMPC_when:
15991     if (DKind == OMPD_metadirective) {
15992       CaptureRegion = OMPD_metadirective;
15993     } else if (DKind == OMPD_unknown) {
15994       llvm_unreachable("Unknown OpenMP directive");
15995     } else {
15996       llvm_unreachable("Unexpected OpenMP directive with when clause");
15997     }
15998     break;
15999   case OMPC_firstprivate:
16000   case OMPC_lastprivate:
16001   case OMPC_reduction:
16002   case OMPC_task_reduction:
16003   case OMPC_in_reduction:
16004   case OMPC_linear:
16005   case OMPC_default:
16006   case OMPC_proc_bind:
16007   case OMPC_safelen:
16008   case OMPC_simdlen:
16009   case OMPC_sizes:
16010   case OMPC_allocator:
16011   case OMPC_collapse:
16012   case OMPC_private:
16013   case OMPC_shared:
16014   case OMPC_aligned:
16015   case OMPC_copyin:
16016   case OMPC_copyprivate:
16017   case OMPC_ordered:
16018   case OMPC_nowait:
16019   case OMPC_untied:
16020   case OMPC_mergeable:
16021   case OMPC_threadprivate:
16022   case OMPC_allocate:
16023   case OMPC_flush:
16024   case OMPC_depobj:
16025   case OMPC_read:
16026   case OMPC_write:
16027   case OMPC_update:
16028   case OMPC_capture:
16029   case OMPC_compare:
16030   case OMPC_seq_cst:
16031   case OMPC_acq_rel:
16032   case OMPC_acquire:
16033   case OMPC_release:
16034   case OMPC_relaxed:
16035   case OMPC_depend:
16036   case OMPC_threads:
16037   case OMPC_simd:
16038   case OMPC_map:
16039   case OMPC_nogroup:
16040   case OMPC_hint:
16041   case OMPC_defaultmap:
16042   case OMPC_unknown:
16043   case OMPC_uniform:
16044   case OMPC_to:
16045   case OMPC_from:
16046   case OMPC_use_device_ptr:
16047   case OMPC_use_device_addr:
16048   case OMPC_is_device_ptr:
16049   case OMPC_unified_address:
16050   case OMPC_unified_shared_memory:
16051   case OMPC_reverse_offload:
16052   case OMPC_dynamic_allocators:
16053   case OMPC_atomic_default_mem_order:
16054   case OMPC_device_type:
16055   case OMPC_match:
16056   case OMPC_nontemporal:
16057   case OMPC_order:
16058   case OMPC_destroy:
16059   case OMPC_detach:
16060   case OMPC_inclusive:
16061   case OMPC_exclusive:
16062   case OMPC_uses_allocators:
16063   case OMPC_affinity:
16064   case OMPC_bind:
16065   default:
16066     llvm_unreachable("Unexpected OpenMP clause.");
16067   }
16068   return CaptureRegion;
16069 }
16070 
16071 OMPClause *Sema::ActOnOpenMPIfClause(OpenMPDirectiveKind NameModifier,
16072                                      Expr *Condition, SourceLocation StartLoc,
16073                                      SourceLocation LParenLoc,
16074                                      SourceLocation NameModifierLoc,
16075                                      SourceLocation ColonLoc,
16076                                      SourceLocation EndLoc) {
16077   Expr *ValExpr = Condition;
16078   Stmt *HelperValStmt = nullptr;
16079   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
16080   if (!Condition->isValueDependent() && !Condition->isTypeDependent() &&
16081       !Condition->isInstantiationDependent() &&
16082       !Condition->containsUnexpandedParameterPack()) {
16083     ExprResult Val = CheckBooleanCondition(StartLoc, Condition);
16084     if (Val.isInvalid())
16085       return nullptr;
16086 
16087     ValExpr = Val.get();
16088 
16089     OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
16090     CaptureRegion = getOpenMPCaptureRegionForClause(
16091         DKind, OMPC_if, LangOpts.OpenMP, NameModifier);
16092     if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
16093       ValExpr = MakeFullExpr(ValExpr).get();
16094       llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
16095       ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
16096       HelperValStmt = buildPreInits(Context, Captures);
16097     }
16098   }
16099 
16100   return new (Context)
16101       OMPIfClause(NameModifier, ValExpr, HelperValStmt, CaptureRegion, StartLoc,
16102                   LParenLoc, NameModifierLoc, ColonLoc, EndLoc);
16103 }
16104 
16105 OMPClause *Sema::ActOnOpenMPFinalClause(Expr *Condition,
16106                                         SourceLocation StartLoc,
16107                                         SourceLocation LParenLoc,
16108                                         SourceLocation EndLoc) {
16109   Expr *ValExpr = Condition;
16110   Stmt *HelperValStmt = nullptr;
16111   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
16112   if (!Condition->isValueDependent() && !Condition->isTypeDependent() &&
16113       !Condition->isInstantiationDependent() &&
16114       !Condition->containsUnexpandedParameterPack()) {
16115     ExprResult Val = CheckBooleanCondition(StartLoc, Condition);
16116     if (Val.isInvalid())
16117       return nullptr;
16118 
16119     ValExpr = MakeFullExpr(Val.get()).get();
16120 
16121     OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
16122     CaptureRegion =
16123         getOpenMPCaptureRegionForClause(DKind, OMPC_final, LangOpts.OpenMP);
16124     if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
16125       ValExpr = MakeFullExpr(ValExpr).get();
16126       llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
16127       ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
16128       HelperValStmt = buildPreInits(Context, Captures);
16129     }
16130   }
16131 
16132   return new (Context) OMPFinalClause(ValExpr, HelperValStmt, CaptureRegion,
16133                                       StartLoc, LParenLoc, EndLoc);
16134 }
16135 
16136 ExprResult Sema::PerformOpenMPImplicitIntegerConversion(SourceLocation Loc,
16137                                                         Expr *Op) {
16138   if (!Op)
16139     return ExprError();
16140 
16141   class IntConvertDiagnoser : public ICEConvertDiagnoser {
16142   public:
16143     IntConvertDiagnoser()
16144         : ICEConvertDiagnoser(/*AllowScopedEnumerations*/ false, false, true) {}
16145     SemaDiagnosticBuilder diagnoseNotInt(Sema &S, SourceLocation Loc,
16146                                          QualType T) override {
16147       return S.Diag(Loc, diag::err_omp_not_integral) << T;
16148     }
16149     SemaDiagnosticBuilder diagnoseIncomplete(Sema &S, SourceLocation Loc,
16150                                              QualType T) override {
16151       return S.Diag(Loc, diag::err_omp_incomplete_type) << T;
16152     }
16153     SemaDiagnosticBuilder diagnoseExplicitConv(Sema &S, SourceLocation Loc,
16154                                                QualType T,
16155                                                QualType ConvTy) override {
16156       return S.Diag(Loc, diag::err_omp_explicit_conversion) << T << ConvTy;
16157     }
16158     SemaDiagnosticBuilder noteExplicitConv(Sema &S, CXXConversionDecl *Conv,
16159                                            QualType ConvTy) override {
16160       return S.Diag(Conv->getLocation(), diag::note_omp_conversion_here)
16161              << ConvTy->isEnumeralType() << ConvTy;
16162     }
16163     SemaDiagnosticBuilder diagnoseAmbiguous(Sema &S, SourceLocation Loc,
16164                                             QualType T) override {
16165       return S.Diag(Loc, diag::err_omp_ambiguous_conversion) << T;
16166     }
16167     SemaDiagnosticBuilder noteAmbiguous(Sema &S, CXXConversionDecl *Conv,
16168                                         QualType ConvTy) override {
16169       return S.Diag(Conv->getLocation(), diag::note_omp_conversion_here)
16170              << ConvTy->isEnumeralType() << ConvTy;
16171     }
16172     SemaDiagnosticBuilder diagnoseConversion(Sema &, SourceLocation, QualType,
16173                                              QualType) override {
16174       llvm_unreachable("conversion functions are permitted");
16175     }
16176   } ConvertDiagnoser;
16177   return PerformContextualImplicitConversion(Loc, Op, ConvertDiagnoser);
16178 }
16179 
16180 static bool
16181 isNonNegativeIntegerValue(Expr *&ValExpr, Sema &SemaRef, OpenMPClauseKind CKind,
16182                           bool StrictlyPositive, bool BuildCapture = false,
16183                           OpenMPDirectiveKind DKind = OMPD_unknown,
16184                           OpenMPDirectiveKind *CaptureRegion = nullptr,
16185                           Stmt **HelperValStmt = nullptr) {
16186   if (!ValExpr->isTypeDependent() && !ValExpr->isValueDependent() &&
16187       !ValExpr->isInstantiationDependent()) {
16188     SourceLocation Loc = ValExpr->getExprLoc();
16189     ExprResult Value =
16190         SemaRef.PerformOpenMPImplicitIntegerConversion(Loc, ValExpr);
16191     if (Value.isInvalid())
16192       return false;
16193 
16194     ValExpr = Value.get();
16195     // The expression must evaluate to a non-negative integer value.
16196     if (Optional<llvm::APSInt> Result =
16197             ValExpr->getIntegerConstantExpr(SemaRef.Context)) {
16198       if (Result->isSigned() &&
16199           !((!StrictlyPositive && Result->isNonNegative()) ||
16200             (StrictlyPositive && Result->isStrictlyPositive()))) {
16201         SemaRef.Diag(Loc, diag::err_omp_negative_expression_in_clause)
16202             << getOpenMPClauseName(CKind) << (StrictlyPositive ? 1 : 0)
16203             << ValExpr->getSourceRange();
16204         return false;
16205       }
16206     }
16207     if (!BuildCapture)
16208       return true;
16209     *CaptureRegion =
16210         getOpenMPCaptureRegionForClause(DKind, CKind, SemaRef.LangOpts.OpenMP);
16211     if (*CaptureRegion != OMPD_unknown &&
16212         !SemaRef.CurContext->isDependentContext()) {
16213       ValExpr = SemaRef.MakeFullExpr(ValExpr).get();
16214       llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
16215       ValExpr = tryBuildCapture(SemaRef, ValExpr, Captures).get();
16216       *HelperValStmt = buildPreInits(SemaRef.Context, Captures);
16217     }
16218   }
16219   return true;
16220 }
16221 
16222 OMPClause *Sema::ActOnOpenMPNumThreadsClause(Expr *NumThreads,
16223                                              SourceLocation StartLoc,
16224                                              SourceLocation LParenLoc,
16225                                              SourceLocation EndLoc) {
16226   Expr *ValExpr = NumThreads;
16227   Stmt *HelperValStmt = nullptr;
16228 
16229   // OpenMP [2.5, Restrictions]
16230   //  The num_threads expression must evaluate to a positive integer value.
16231   if (!isNonNegativeIntegerValue(ValExpr, *this, OMPC_num_threads,
16232                                  /*StrictlyPositive=*/true))
16233     return nullptr;
16234 
16235   OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
16236   OpenMPDirectiveKind CaptureRegion =
16237       getOpenMPCaptureRegionForClause(DKind, OMPC_num_threads, LangOpts.OpenMP);
16238   if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
16239     ValExpr = MakeFullExpr(ValExpr).get();
16240     llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
16241     ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
16242     HelperValStmt = buildPreInits(Context, Captures);
16243   }
16244 
16245   return new (Context) OMPNumThreadsClause(
16246       ValExpr, HelperValStmt, CaptureRegion, StartLoc, LParenLoc, EndLoc);
16247 }
16248 
16249 ExprResult Sema::VerifyPositiveIntegerConstantInClause(Expr *E,
16250                                                        OpenMPClauseKind CKind,
16251                                                        bool StrictlyPositive,
16252                                                        bool SuppressExprDiags) {
16253   if (!E)
16254     return ExprError();
16255   if (E->isValueDependent() || E->isTypeDependent() ||
16256       E->isInstantiationDependent() || E->containsUnexpandedParameterPack())
16257     return E;
16258 
16259   llvm::APSInt Result;
16260   ExprResult ICE;
16261   if (SuppressExprDiags) {
16262     // Use a custom diagnoser that suppresses 'note' diagnostics about the
16263     // expression.
16264     struct SuppressedDiagnoser : public Sema::VerifyICEDiagnoser {
16265       SuppressedDiagnoser() : VerifyICEDiagnoser(/*Suppress=*/true) {}
16266       Sema::SemaDiagnosticBuilder diagnoseNotICE(Sema &S,
16267                                                  SourceLocation Loc) override {
16268         llvm_unreachable("Diagnostic suppressed");
16269       }
16270     } Diagnoser;
16271     ICE = VerifyIntegerConstantExpression(E, &Result, Diagnoser, AllowFold);
16272   } else {
16273     ICE = VerifyIntegerConstantExpression(E, &Result, /*FIXME*/ AllowFold);
16274   }
16275   if (ICE.isInvalid())
16276     return ExprError();
16277 
16278   if ((StrictlyPositive && !Result.isStrictlyPositive()) ||
16279       (!StrictlyPositive && !Result.isNonNegative())) {
16280     Diag(E->getExprLoc(), diag::err_omp_negative_expression_in_clause)
16281         << getOpenMPClauseName(CKind) << (StrictlyPositive ? 1 : 0)
16282         << E->getSourceRange();
16283     return ExprError();
16284   }
16285   if ((CKind == OMPC_aligned || CKind == OMPC_align) && !Result.isPowerOf2()) {
16286     Diag(E->getExprLoc(), diag::warn_omp_alignment_not_power_of_two)
16287         << E->getSourceRange();
16288     return ExprError();
16289   }
16290   if (CKind == OMPC_collapse && DSAStack->getAssociatedLoops() == 1)
16291     DSAStack->setAssociatedLoops(Result.getExtValue());
16292   else if (CKind == OMPC_ordered)
16293     DSAStack->setAssociatedLoops(Result.getExtValue());
16294   return ICE;
16295 }
16296 
16297 OMPClause *Sema::ActOnOpenMPSafelenClause(Expr *Len, SourceLocation StartLoc,
16298                                           SourceLocation LParenLoc,
16299                                           SourceLocation EndLoc) {
16300   // OpenMP [2.8.1, simd construct, Description]
16301   // The parameter of the safelen clause must be a constant
16302   // positive integer expression.
16303   ExprResult Safelen = VerifyPositiveIntegerConstantInClause(Len, OMPC_safelen);
16304   if (Safelen.isInvalid())
16305     return nullptr;
16306   return new (Context)
16307       OMPSafelenClause(Safelen.get(), StartLoc, LParenLoc, EndLoc);
16308 }
16309 
16310 OMPClause *Sema::ActOnOpenMPSimdlenClause(Expr *Len, SourceLocation StartLoc,
16311                                           SourceLocation LParenLoc,
16312                                           SourceLocation EndLoc) {
16313   // OpenMP [2.8.1, simd construct, Description]
16314   // The parameter of the simdlen clause must be a constant
16315   // positive integer expression.
16316   ExprResult Simdlen = VerifyPositiveIntegerConstantInClause(Len, OMPC_simdlen);
16317   if (Simdlen.isInvalid())
16318     return nullptr;
16319   return new (Context)
16320       OMPSimdlenClause(Simdlen.get(), StartLoc, LParenLoc, EndLoc);
16321 }
16322 
16323 /// Tries to find omp_allocator_handle_t type.
16324 static bool findOMPAllocatorHandleT(Sema &S, SourceLocation Loc,
16325                                     DSAStackTy *Stack) {
16326   QualType OMPAllocatorHandleT = Stack->getOMPAllocatorHandleT();
16327   if (!OMPAllocatorHandleT.isNull())
16328     return true;
16329   // Build the predefined allocator expressions.
16330   bool ErrorFound = false;
16331   for (int I = 0; I < OMPAllocateDeclAttr::OMPUserDefinedMemAlloc; ++I) {
16332     auto AllocatorKind = static_cast<OMPAllocateDeclAttr::AllocatorTypeTy>(I);
16333     StringRef Allocator =
16334         OMPAllocateDeclAttr::ConvertAllocatorTypeTyToStr(AllocatorKind);
16335     DeclarationName AllocatorName = &S.getASTContext().Idents.get(Allocator);
16336     auto *VD = dyn_cast_or_null<ValueDecl>(
16337         S.LookupSingleName(S.TUScope, AllocatorName, Loc, Sema::LookupAnyName));
16338     if (!VD) {
16339       ErrorFound = true;
16340       break;
16341     }
16342     QualType AllocatorType =
16343         VD->getType().getNonLValueExprType(S.getASTContext());
16344     ExprResult Res = S.BuildDeclRefExpr(VD, AllocatorType, VK_LValue, Loc);
16345     if (!Res.isUsable()) {
16346       ErrorFound = true;
16347       break;
16348     }
16349     if (OMPAllocatorHandleT.isNull())
16350       OMPAllocatorHandleT = AllocatorType;
16351     if (!S.getASTContext().hasSameType(OMPAllocatorHandleT, AllocatorType)) {
16352       ErrorFound = true;
16353       break;
16354     }
16355     Stack->setAllocator(AllocatorKind, Res.get());
16356   }
16357   if (ErrorFound) {
16358     S.Diag(Loc, diag::err_omp_implied_type_not_found)
16359         << "omp_allocator_handle_t";
16360     return false;
16361   }
16362   OMPAllocatorHandleT.addConst();
16363   Stack->setOMPAllocatorHandleT(OMPAllocatorHandleT);
16364   return true;
16365 }
16366 
16367 OMPClause *Sema::ActOnOpenMPAllocatorClause(Expr *A, SourceLocation StartLoc,
16368                                             SourceLocation LParenLoc,
16369                                             SourceLocation EndLoc) {
16370   // OpenMP [2.11.3, allocate Directive, Description]
16371   // allocator is an expression of omp_allocator_handle_t type.
16372   if (!findOMPAllocatorHandleT(*this, A->getExprLoc(), DSAStack))
16373     return nullptr;
16374 
16375   ExprResult Allocator = DefaultLvalueConversion(A);
16376   if (Allocator.isInvalid())
16377     return nullptr;
16378   Allocator = PerformImplicitConversion(Allocator.get(),
16379                                         DSAStack->getOMPAllocatorHandleT(),
16380                                         Sema::AA_Initializing,
16381                                         /*AllowExplicit=*/true);
16382   if (Allocator.isInvalid())
16383     return nullptr;
16384   return new (Context)
16385       OMPAllocatorClause(Allocator.get(), StartLoc, LParenLoc, EndLoc);
16386 }
16387 
16388 OMPClause *Sema::ActOnOpenMPCollapseClause(Expr *NumForLoops,
16389                                            SourceLocation StartLoc,
16390                                            SourceLocation LParenLoc,
16391                                            SourceLocation EndLoc) {
16392   // OpenMP [2.7.1, loop construct, Description]
16393   // OpenMP [2.8.1, simd construct, Description]
16394   // OpenMP [2.9.6, distribute construct, Description]
16395   // The parameter of the collapse clause must be a constant
16396   // positive integer expression.
16397   ExprResult NumForLoopsResult =
16398       VerifyPositiveIntegerConstantInClause(NumForLoops, OMPC_collapse);
16399   if (NumForLoopsResult.isInvalid())
16400     return nullptr;
16401   return new (Context)
16402       OMPCollapseClause(NumForLoopsResult.get(), StartLoc, LParenLoc, EndLoc);
16403 }
16404 
16405 OMPClause *Sema::ActOnOpenMPOrderedClause(SourceLocation StartLoc,
16406                                           SourceLocation EndLoc,
16407                                           SourceLocation LParenLoc,
16408                                           Expr *NumForLoops) {
16409   // OpenMP [2.7.1, loop construct, Description]
16410   // OpenMP [2.8.1, simd construct, Description]
16411   // OpenMP [2.9.6, distribute construct, Description]
16412   // The parameter of the ordered clause must be a constant
16413   // positive integer expression if any.
16414   if (NumForLoops && LParenLoc.isValid()) {
16415     ExprResult NumForLoopsResult =
16416         VerifyPositiveIntegerConstantInClause(NumForLoops, OMPC_ordered);
16417     if (NumForLoopsResult.isInvalid())
16418       return nullptr;
16419     NumForLoops = NumForLoopsResult.get();
16420   } else {
16421     NumForLoops = nullptr;
16422   }
16423   auto *Clause = OMPOrderedClause::Create(
16424       Context, NumForLoops, NumForLoops ? DSAStack->getAssociatedLoops() : 0,
16425       StartLoc, LParenLoc, EndLoc);
16426   DSAStack->setOrderedRegion(/*IsOrdered=*/true, NumForLoops, Clause);
16427   return Clause;
16428 }
16429 
16430 OMPClause *Sema::ActOnOpenMPSimpleClause(
16431     OpenMPClauseKind Kind, unsigned Argument, SourceLocation ArgumentLoc,
16432     SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc) {
16433   OMPClause *Res = nullptr;
16434   switch (Kind) {
16435   case OMPC_default:
16436     Res = ActOnOpenMPDefaultClause(static_cast<DefaultKind>(Argument),
16437                                    ArgumentLoc, StartLoc, LParenLoc, EndLoc);
16438     break;
16439   case OMPC_proc_bind:
16440     Res = ActOnOpenMPProcBindClause(static_cast<ProcBindKind>(Argument),
16441                                     ArgumentLoc, StartLoc, LParenLoc, EndLoc);
16442     break;
16443   case OMPC_atomic_default_mem_order:
16444     Res = ActOnOpenMPAtomicDefaultMemOrderClause(
16445         static_cast<OpenMPAtomicDefaultMemOrderClauseKind>(Argument),
16446         ArgumentLoc, StartLoc, LParenLoc, EndLoc);
16447     break;
16448   case OMPC_order:
16449     Res = ActOnOpenMPOrderClause(static_cast<OpenMPOrderClauseKind>(Argument),
16450                                  ArgumentLoc, StartLoc, LParenLoc, EndLoc);
16451     break;
16452   case OMPC_update:
16453     Res = ActOnOpenMPUpdateClause(static_cast<OpenMPDependClauseKind>(Argument),
16454                                   ArgumentLoc, StartLoc, LParenLoc, EndLoc);
16455     break;
16456   case OMPC_bind:
16457     Res = ActOnOpenMPBindClause(static_cast<OpenMPBindClauseKind>(Argument),
16458                                 ArgumentLoc, StartLoc, LParenLoc, EndLoc);
16459     break;
16460   case OMPC_if:
16461   case OMPC_final:
16462   case OMPC_num_threads:
16463   case OMPC_safelen:
16464   case OMPC_simdlen:
16465   case OMPC_sizes:
16466   case OMPC_allocator:
16467   case OMPC_collapse:
16468   case OMPC_schedule:
16469   case OMPC_private:
16470   case OMPC_firstprivate:
16471   case OMPC_lastprivate:
16472   case OMPC_shared:
16473   case OMPC_reduction:
16474   case OMPC_task_reduction:
16475   case OMPC_in_reduction:
16476   case OMPC_linear:
16477   case OMPC_aligned:
16478   case OMPC_copyin:
16479   case OMPC_copyprivate:
16480   case OMPC_ordered:
16481   case OMPC_nowait:
16482   case OMPC_untied:
16483   case OMPC_mergeable:
16484   case OMPC_threadprivate:
16485   case OMPC_allocate:
16486   case OMPC_flush:
16487   case OMPC_depobj:
16488   case OMPC_read:
16489   case OMPC_write:
16490   case OMPC_capture:
16491   case OMPC_compare:
16492   case OMPC_seq_cst:
16493   case OMPC_acq_rel:
16494   case OMPC_acquire:
16495   case OMPC_release:
16496   case OMPC_relaxed:
16497   case OMPC_depend:
16498   case OMPC_device:
16499   case OMPC_threads:
16500   case OMPC_simd:
16501   case OMPC_map:
16502   case OMPC_num_teams:
16503   case OMPC_thread_limit:
16504   case OMPC_priority:
16505   case OMPC_grainsize:
16506   case OMPC_nogroup:
16507   case OMPC_num_tasks:
16508   case OMPC_hint:
16509   case OMPC_dist_schedule:
16510   case OMPC_defaultmap:
16511   case OMPC_unknown:
16512   case OMPC_uniform:
16513   case OMPC_to:
16514   case OMPC_from:
16515   case OMPC_use_device_ptr:
16516   case OMPC_use_device_addr:
16517   case OMPC_is_device_ptr:
16518   case OMPC_has_device_addr:
16519   case OMPC_unified_address:
16520   case OMPC_unified_shared_memory:
16521   case OMPC_reverse_offload:
16522   case OMPC_dynamic_allocators:
16523   case OMPC_device_type:
16524   case OMPC_match:
16525   case OMPC_nontemporal:
16526   case OMPC_destroy:
16527   case OMPC_novariants:
16528   case OMPC_nocontext:
16529   case OMPC_detach:
16530   case OMPC_inclusive:
16531   case OMPC_exclusive:
16532   case OMPC_uses_allocators:
16533   case OMPC_affinity:
16534   case OMPC_when:
16535   default:
16536     llvm_unreachable("Clause is not allowed.");
16537   }
16538   return Res;
16539 }
16540 
16541 static std::string
16542 getListOfPossibleValues(OpenMPClauseKind K, unsigned First, unsigned Last,
16543                         ArrayRef<unsigned> Exclude = llvm::None) {
16544   SmallString<256> Buffer;
16545   llvm::raw_svector_ostream Out(Buffer);
16546   unsigned Skipped = Exclude.size();
16547   auto S = Exclude.begin(), E = Exclude.end();
16548   for (unsigned I = First; I < Last; ++I) {
16549     if (std::find(S, E, I) != E) {
16550       --Skipped;
16551       continue;
16552     }
16553     Out << "'" << getOpenMPSimpleClauseTypeName(K, I) << "'";
16554     if (I + Skipped + 2 == Last)
16555       Out << " or ";
16556     else if (I + Skipped + 1 != Last)
16557       Out << ", ";
16558   }
16559   return std::string(Out.str());
16560 }
16561 
16562 OMPClause *Sema::ActOnOpenMPDefaultClause(DefaultKind Kind,
16563                                           SourceLocation KindKwLoc,
16564                                           SourceLocation StartLoc,
16565                                           SourceLocation LParenLoc,
16566                                           SourceLocation EndLoc) {
16567   if (Kind == OMP_DEFAULT_unknown) {
16568     Diag(KindKwLoc, diag::err_omp_unexpected_clause_value)
16569         << getListOfPossibleValues(OMPC_default, /*First=*/0,
16570                                    /*Last=*/unsigned(OMP_DEFAULT_unknown))
16571         << getOpenMPClauseName(OMPC_default);
16572     return nullptr;
16573   }
16574 
16575   switch (Kind) {
16576   case OMP_DEFAULT_none:
16577     DSAStack->setDefaultDSANone(KindKwLoc);
16578     break;
16579   case OMP_DEFAULT_shared:
16580     DSAStack->setDefaultDSAShared(KindKwLoc);
16581     break;
16582   case OMP_DEFAULT_firstprivate:
16583     DSAStack->setDefaultDSAFirstPrivate(KindKwLoc);
16584     break;
16585   case OMP_DEFAULT_private:
16586     DSAStack->setDefaultDSAPrivate(KindKwLoc);
16587     break;
16588   default:
16589     llvm_unreachable("DSA unexpected in OpenMP default clause");
16590   }
16591 
16592   return new (Context)
16593       OMPDefaultClause(Kind, KindKwLoc, StartLoc, LParenLoc, EndLoc);
16594 }
16595 
16596 OMPClause *Sema::ActOnOpenMPProcBindClause(ProcBindKind Kind,
16597                                            SourceLocation KindKwLoc,
16598                                            SourceLocation StartLoc,
16599                                            SourceLocation LParenLoc,
16600                                            SourceLocation EndLoc) {
16601   if (Kind == OMP_PROC_BIND_unknown) {
16602     Diag(KindKwLoc, diag::err_omp_unexpected_clause_value)
16603         << getListOfPossibleValues(OMPC_proc_bind,
16604                                    /*First=*/unsigned(OMP_PROC_BIND_master),
16605                                    /*Last=*/
16606                                    unsigned(LangOpts.OpenMP > 50
16607                                                 ? OMP_PROC_BIND_primary
16608                                                 : OMP_PROC_BIND_spread) +
16609                                        1)
16610         << getOpenMPClauseName(OMPC_proc_bind);
16611     return nullptr;
16612   }
16613   if (Kind == OMP_PROC_BIND_primary && LangOpts.OpenMP < 51)
16614     Diag(KindKwLoc, diag::err_omp_unexpected_clause_value)
16615         << getListOfPossibleValues(OMPC_proc_bind,
16616                                    /*First=*/unsigned(OMP_PROC_BIND_master),
16617                                    /*Last=*/
16618                                    unsigned(OMP_PROC_BIND_spread) + 1)
16619         << getOpenMPClauseName(OMPC_proc_bind);
16620   return new (Context)
16621       OMPProcBindClause(Kind, KindKwLoc, StartLoc, LParenLoc, EndLoc);
16622 }
16623 
16624 OMPClause *Sema::ActOnOpenMPAtomicDefaultMemOrderClause(
16625     OpenMPAtomicDefaultMemOrderClauseKind Kind, SourceLocation KindKwLoc,
16626     SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc) {
16627   if (Kind == OMPC_ATOMIC_DEFAULT_MEM_ORDER_unknown) {
16628     Diag(KindKwLoc, diag::err_omp_unexpected_clause_value)
16629         << getListOfPossibleValues(
16630                OMPC_atomic_default_mem_order, /*First=*/0,
16631                /*Last=*/OMPC_ATOMIC_DEFAULT_MEM_ORDER_unknown)
16632         << getOpenMPClauseName(OMPC_atomic_default_mem_order);
16633     return nullptr;
16634   }
16635   return new (Context) OMPAtomicDefaultMemOrderClause(Kind, KindKwLoc, StartLoc,
16636                                                       LParenLoc, EndLoc);
16637 }
16638 
16639 OMPClause *Sema::ActOnOpenMPOrderClause(OpenMPOrderClauseKind Kind,
16640                                         SourceLocation KindKwLoc,
16641                                         SourceLocation StartLoc,
16642                                         SourceLocation LParenLoc,
16643                                         SourceLocation EndLoc) {
16644   if (Kind == OMPC_ORDER_unknown) {
16645     static_assert(OMPC_ORDER_unknown > 0,
16646                   "OMPC_ORDER_unknown not greater than 0");
16647     Diag(KindKwLoc, diag::err_omp_unexpected_clause_value)
16648         << getListOfPossibleValues(OMPC_order, /*First=*/0,
16649                                    /*Last=*/OMPC_ORDER_unknown)
16650         << getOpenMPClauseName(OMPC_order);
16651     return nullptr;
16652   }
16653   return new (Context)
16654       OMPOrderClause(Kind, KindKwLoc, StartLoc, LParenLoc, EndLoc);
16655 }
16656 
16657 OMPClause *Sema::ActOnOpenMPUpdateClause(OpenMPDependClauseKind Kind,
16658                                          SourceLocation KindKwLoc,
16659                                          SourceLocation StartLoc,
16660                                          SourceLocation LParenLoc,
16661                                          SourceLocation EndLoc) {
16662   if (Kind == OMPC_DEPEND_unknown || Kind == OMPC_DEPEND_source ||
16663       Kind == OMPC_DEPEND_sink || Kind == OMPC_DEPEND_depobj) {
16664     SmallVector<unsigned> Except = {
16665         OMPC_DEPEND_source, OMPC_DEPEND_sink, OMPC_DEPEND_depobj,
16666         OMPC_DEPEND_outallmemory, OMPC_DEPEND_inoutallmemory};
16667     if (LangOpts.OpenMP < 51)
16668       Except.push_back(OMPC_DEPEND_inoutset);
16669     Diag(KindKwLoc, diag::err_omp_unexpected_clause_value)
16670         << getListOfPossibleValues(OMPC_depend, /*First=*/0,
16671                                    /*Last=*/OMPC_DEPEND_unknown, Except)
16672         << getOpenMPClauseName(OMPC_update);
16673     return nullptr;
16674   }
16675   return OMPUpdateClause::Create(Context, StartLoc, LParenLoc, KindKwLoc, Kind,
16676                                  EndLoc);
16677 }
16678 
16679 OMPClause *Sema::ActOnOpenMPSizesClause(ArrayRef<Expr *> SizeExprs,
16680                                         SourceLocation StartLoc,
16681                                         SourceLocation LParenLoc,
16682                                         SourceLocation EndLoc) {
16683   for (Expr *SizeExpr : SizeExprs) {
16684     ExprResult NumForLoopsResult = VerifyPositiveIntegerConstantInClause(
16685         SizeExpr, OMPC_sizes, /*StrictlyPositive=*/true);
16686     if (!NumForLoopsResult.isUsable())
16687       return nullptr;
16688   }
16689 
16690   DSAStack->setAssociatedLoops(SizeExprs.size());
16691   return OMPSizesClause::Create(Context, StartLoc, LParenLoc, EndLoc,
16692                                 SizeExprs);
16693 }
16694 
16695 OMPClause *Sema::ActOnOpenMPFullClause(SourceLocation StartLoc,
16696                                        SourceLocation EndLoc) {
16697   return OMPFullClause::Create(Context, StartLoc, EndLoc);
16698 }
16699 
16700 OMPClause *Sema::ActOnOpenMPPartialClause(Expr *FactorExpr,
16701                                           SourceLocation StartLoc,
16702                                           SourceLocation LParenLoc,
16703                                           SourceLocation EndLoc) {
16704   if (FactorExpr) {
16705     // If an argument is specified, it must be a constant (or an unevaluated
16706     // template expression).
16707     ExprResult FactorResult = VerifyPositiveIntegerConstantInClause(
16708         FactorExpr, OMPC_partial, /*StrictlyPositive=*/true);
16709     if (FactorResult.isInvalid())
16710       return nullptr;
16711     FactorExpr = FactorResult.get();
16712   }
16713 
16714   return OMPPartialClause::Create(Context, StartLoc, LParenLoc, EndLoc,
16715                                   FactorExpr);
16716 }
16717 
16718 OMPClause *Sema::ActOnOpenMPAlignClause(Expr *A, SourceLocation StartLoc,
16719                                         SourceLocation LParenLoc,
16720                                         SourceLocation EndLoc) {
16721   ExprResult AlignVal;
16722   AlignVal = VerifyPositiveIntegerConstantInClause(A, OMPC_align);
16723   if (AlignVal.isInvalid())
16724     return nullptr;
16725   return OMPAlignClause::Create(Context, AlignVal.get(), StartLoc, LParenLoc,
16726                                 EndLoc);
16727 }
16728 
16729 OMPClause *Sema::ActOnOpenMPSingleExprWithArgClause(
16730     OpenMPClauseKind Kind, ArrayRef<unsigned> Argument, Expr *Expr,
16731     SourceLocation StartLoc, SourceLocation LParenLoc,
16732     ArrayRef<SourceLocation> ArgumentLoc, SourceLocation DelimLoc,
16733     SourceLocation EndLoc) {
16734   OMPClause *Res = nullptr;
16735   switch (Kind) {
16736   case OMPC_schedule:
16737     enum { Modifier1, Modifier2, ScheduleKind, NumberOfElements };
16738     assert(Argument.size() == NumberOfElements &&
16739            ArgumentLoc.size() == NumberOfElements);
16740     Res = ActOnOpenMPScheduleClause(
16741         static_cast<OpenMPScheduleClauseModifier>(Argument[Modifier1]),
16742         static_cast<OpenMPScheduleClauseModifier>(Argument[Modifier2]),
16743         static_cast<OpenMPScheduleClauseKind>(Argument[ScheduleKind]), Expr,
16744         StartLoc, LParenLoc, ArgumentLoc[Modifier1], ArgumentLoc[Modifier2],
16745         ArgumentLoc[ScheduleKind], DelimLoc, EndLoc);
16746     break;
16747   case OMPC_if:
16748     assert(Argument.size() == 1 && ArgumentLoc.size() == 1);
16749     Res = ActOnOpenMPIfClause(static_cast<OpenMPDirectiveKind>(Argument.back()),
16750                               Expr, StartLoc, LParenLoc, ArgumentLoc.back(),
16751                               DelimLoc, EndLoc);
16752     break;
16753   case OMPC_dist_schedule:
16754     Res = ActOnOpenMPDistScheduleClause(
16755         static_cast<OpenMPDistScheduleClauseKind>(Argument.back()), Expr,
16756         StartLoc, LParenLoc, ArgumentLoc.back(), DelimLoc, EndLoc);
16757     break;
16758   case OMPC_defaultmap:
16759     enum { Modifier, DefaultmapKind };
16760     Res = ActOnOpenMPDefaultmapClause(
16761         static_cast<OpenMPDefaultmapClauseModifier>(Argument[Modifier]),
16762         static_cast<OpenMPDefaultmapClauseKind>(Argument[DefaultmapKind]),
16763         StartLoc, LParenLoc, ArgumentLoc[Modifier], ArgumentLoc[DefaultmapKind],
16764         EndLoc);
16765     break;
16766   case OMPC_device:
16767     assert(Argument.size() == 1 && ArgumentLoc.size() == 1);
16768     Res = ActOnOpenMPDeviceClause(
16769         static_cast<OpenMPDeviceClauseModifier>(Argument.back()), Expr,
16770         StartLoc, LParenLoc, ArgumentLoc.back(), EndLoc);
16771     break;
16772   case OMPC_final:
16773   case OMPC_num_threads:
16774   case OMPC_safelen:
16775   case OMPC_simdlen:
16776   case OMPC_sizes:
16777   case OMPC_allocator:
16778   case OMPC_collapse:
16779   case OMPC_default:
16780   case OMPC_proc_bind:
16781   case OMPC_private:
16782   case OMPC_firstprivate:
16783   case OMPC_lastprivate:
16784   case OMPC_shared:
16785   case OMPC_reduction:
16786   case OMPC_task_reduction:
16787   case OMPC_in_reduction:
16788   case OMPC_linear:
16789   case OMPC_aligned:
16790   case OMPC_copyin:
16791   case OMPC_copyprivate:
16792   case OMPC_ordered:
16793   case OMPC_nowait:
16794   case OMPC_untied:
16795   case OMPC_mergeable:
16796   case OMPC_threadprivate:
16797   case OMPC_allocate:
16798   case OMPC_flush:
16799   case OMPC_depobj:
16800   case OMPC_read:
16801   case OMPC_write:
16802   case OMPC_update:
16803   case OMPC_capture:
16804   case OMPC_compare:
16805   case OMPC_seq_cst:
16806   case OMPC_acq_rel:
16807   case OMPC_acquire:
16808   case OMPC_release:
16809   case OMPC_relaxed:
16810   case OMPC_depend:
16811   case OMPC_threads:
16812   case OMPC_simd:
16813   case OMPC_map:
16814   case OMPC_num_teams:
16815   case OMPC_thread_limit:
16816   case OMPC_priority:
16817   case OMPC_grainsize:
16818   case OMPC_nogroup:
16819   case OMPC_num_tasks:
16820   case OMPC_hint:
16821   case OMPC_unknown:
16822   case OMPC_uniform:
16823   case OMPC_to:
16824   case OMPC_from:
16825   case OMPC_use_device_ptr:
16826   case OMPC_use_device_addr:
16827   case OMPC_is_device_ptr:
16828   case OMPC_has_device_addr:
16829   case OMPC_unified_address:
16830   case OMPC_unified_shared_memory:
16831   case OMPC_reverse_offload:
16832   case OMPC_dynamic_allocators:
16833   case OMPC_atomic_default_mem_order:
16834   case OMPC_device_type:
16835   case OMPC_match:
16836   case OMPC_nontemporal:
16837   case OMPC_order:
16838   case OMPC_destroy:
16839   case OMPC_novariants:
16840   case OMPC_nocontext:
16841   case OMPC_detach:
16842   case OMPC_inclusive:
16843   case OMPC_exclusive:
16844   case OMPC_uses_allocators:
16845   case OMPC_affinity:
16846   case OMPC_when:
16847   case OMPC_bind:
16848   default:
16849     llvm_unreachable("Clause is not allowed.");
16850   }
16851   return Res;
16852 }
16853 
16854 static bool checkScheduleModifiers(Sema &S, OpenMPScheduleClauseModifier M1,
16855                                    OpenMPScheduleClauseModifier M2,
16856                                    SourceLocation M1Loc, SourceLocation M2Loc) {
16857   if (M1 == OMPC_SCHEDULE_MODIFIER_unknown && M1Loc.isValid()) {
16858     SmallVector<unsigned, 2> Excluded;
16859     if (M2 != OMPC_SCHEDULE_MODIFIER_unknown)
16860       Excluded.push_back(M2);
16861     if (M2 == OMPC_SCHEDULE_MODIFIER_nonmonotonic)
16862       Excluded.push_back(OMPC_SCHEDULE_MODIFIER_monotonic);
16863     if (M2 == OMPC_SCHEDULE_MODIFIER_monotonic)
16864       Excluded.push_back(OMPC_SCHEDULE_MODIFIER_nonmonotonic);
16865     S.Diag(M1Loc, diag::err_omp_unexpected_clause_value)
16866         << getListOfPossibleValues(OMPC_schedule,
16867                                    /*First=*/OMPC_SCHEDULE_MODIFIER_unknown + 1,
16868                                    /*Last=*/OMPC_SCHEDULE_MODIFIER_last,
16869                                    Excluded)
16870         << getOpenMPClauseName(OMPC_schedule);
16871     return true;
16872   }
16873   return false;
16874 }
16875 
16876 OMPClause *Sema::ActOnOpenMPScheduleClause(
16877     OpenMPScheduleClauseModifier M1, OpenMPScheduleClauseModifier M2,
16878     OpenMPScheduleClauseKind Kind, Expr *ChunkSize, SourceLocation StartLoc,
16879     SourceLocation LParenLoc, SourceLocation M1Loc, SourceLocation M2Loc,
16880     SourceLocation KindLoc, SourceLocation CommaLoc, SourceLocation EndLoc) {
16881   if (checkScheduleModifiers(*this, M1, M2, M1Loc, M2Loc) ||
16882       checkScheduleModifiers(*this, M2, M1, M2Loc, M1Loc))
16883     return nullptr;
16884   // OpenMP, 2.7.1, Loop Construct, Restrictions
16885   // Either the monotonic modifier or the nonmonotonic modifier can be specified
16886   // but not both.
16887   if ((M1 == M2 && M1 != OMPC_SCHEDULE_MODIFIER_unknown) ||
16888       (M1 == OMPC_SCHEDULE_MODIFIER_monotonic &&
16889        M2 == OMPC_SCHEDULE_MODIFIER_nonmonotonic) ||
16890       (M1 == OMPC_SCHEDULE_MODIFIER_nonmonotonic &&
16891        M2 == OMPC_SCHEDULE_MODIFIER_monotonic)) {
16892     Diag(M2Loc, diag::err_omp_unexpected_schedule_modifier)
16893         << getOpenMPSimpleClauseTypeName(OMPC_schedule, M2)
16894         << getOpenMPSimpleClauseTypeName(OMPC_schedule, M1);
16895     return nullptr;
16896   }
16897   if (Kind == OMPC_SCHEDULE_unknown) {
16898     std::string Values;
16899     if (M1Loc.isInvalid() && M2Loc.isInvalid()) {
16900       unsigned Exclude[] = {OMPC_SCHEDULE_unknown};
16901       Values = getListOfPossibleValues(OMPC_schedule, /*First=*/0,
16902                                        /*Last=*/OMPC_SCHEDULE_MODIFIER_last,
16903                                        Exclude);
16904     } else {
16905       Values = getListOfPossibleValues(OMPC_schedule, /*First=*/0,
16906                                        /*Last=*/OMPC_SCHEDULE_unknown);
16907     }
16908     Diag(KindLoc, diag::err_omp_unexpected_clause_value)
16909         << Values << getOpenMPClauseName(OMPC_schedule);
16910     return nullptr;
16911   }
16912   // OpenMP, 2.7.1, Loop Construct, Restrictions
16913   // The nonmonotonic modifier can only be specified with schedule(dynamic) or
16914   // schedule(guided).
16915   // OpenMP 5.0 does not have this restriction.
16916   if (LangOpts.OpenMP < 50 &&
16917       (M1 == OMPC_SCHEDULE_MODIFIER_nonmonotonic ||
16918        M2 == OMPC_SCHEDULE_MODIFIER_nonmonotonic) &&
16919       Kind != OMPC_SCHEDULE_dynamic && Kind != OMPC_SCHEDULE_guided) {
16920     Diag(M1 == OMPC_SCHEDULE_MODIFIER_nonmonotonic ? M1Loc : M2Loc,
16921          diag::err_omp_schedule_nonmonotonic_static);
16922     return nullptr;
16923   }
16924   Expr *ValExpr = ChunkSize;
16925   Stmt *HelperValStmt = nullptr;
16926   if (ChunkSize) {
16927     if (!ChunkSize->isValueDependent() && !ChunkSize->isTypeDependent() &&
16928         !ChunkSize->isInstantiationDependent() &&
16929         !ChunkSize->containsUnexpandedParameterPack()) {
16930       SourceLocation ChunkSizeLoc = ChunkSize->getBeginLoc();
16931       ExprResult Val =
16932           PerformOpenMPImplicitIntegerConversion(ChunkSizeLoc, ChunkSize);
16933       if (Val.isInvalid())
16934         return nullptr;
16935 
16936       ValExpr = Val.get();
16937 
16938       // OpenMP [2.7.1, Restrictions]
16939       //  chunk_size must be a loop invariant integer expression with a positive
16940       //  value.
16941       if (Optional<llvm::APSInt> Result =
16942               ValExpr->getIntegerConstantExpr(Context)) {
16943         if (Result->isSigned() && !Result->isStrictlyPositive()) {
16944           Diag(ChunkSizeLoc, diag::err_omp_negative_expression_in_clause)
16945               << "schedule" << 1 << ChunkSize->getSourceRange();
16946           return nullptr;
16947         }
16948       } else if (getOpenMPCaptureRegionForClause(
16949                      DSAStack->getCurrentDirective(), OMPC_schedule,
16950                      LangOpts.OpenMP) != OMPD_unknown &&
16951                  !CurContext->isDependentContext()) {
16952         ValExpr = MakeFullExpr(ValExpr).get();
16953         llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
16954         ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
16955         HelperValStmt = buildPreInits(Context, Captures);
16956       }
16957     }
16958   }
16959 
16960   return new (Context)
16961       OMPScheduleClause(StartLoc, LParenLoc, KindLoc, CommaLoc, EndLoc, Kind,
16962                         ValExpr, HelperValStmt, M1, M1Loc, M2, M2Loc);
16963 }
16964 
16965 OMPClause *Sema::ActOnOpenMPClause(OpenMPClauseKind Kind,
16966                                    SourceLocation StartLoc,
16967                                    SourceLocation EndLoc) {
16968   OMPClause *Res = nullptr;
16969   switch (Kind) {
16970   case OMPC_ordered:
16971     Res = ActOnOpenMPOrderedClause(StartLoc, EndLoc);
16972     break;
16973   case OMPC_nowait:
16974     Res = ActOnOpenMPNowaitClause(StartLoc, EndLoc);
16975     break;
16976   case OMPC_untied:
16977     Res = ActOnOpenMPUntiedClause(StartLoc, EndLoc);
16978     break;
16979   case OMPC_mergeable:
16980     Res = ActOnOpenMPMergeableClause(StartLoc, EndLoc);
16981     break;
16982   case OMPC_read:
16983     Res = ActOnOpenMPReadClause(StartLoc, EndLoc);
16984     break;
16985   case OMPC_write:
16986     Res = ActOnOpenMPWriteClause(StartLoc, EndLoc);
16987     break;
16988   case OMPC_update:
16989     Res = ActOnOpenMPUpdateClause(StartLoc, EndLoc);
16990     break;
16991   case OMPC_capture:
16992     Res = ActOnOpenMPCaptureClause(StartLoc, EndLoc);
16993     break;
16994   case OMPC_compare:
16995     Res = ActOnOpenMPCompareClause(StartLoc, EndLoc);
16996     break;
16997   case OMPC_seq_cst:
16998     Res = ActOnOpenMPSeqCstClause(StartLoc, EndLoc);
16999     break;
17000   case OMPC_acq_rel:
17001     Res = ActOnOpenMPAcqRelClause(StartLoc, EndLoc);
17002     break;
17003   case OMPC_acquire:
17004     Res = ActOnOpenMPAcquireClause(StartLoc, EndLoc);
17005     break;
17006   case OMPC_release:
17007     Res = ActOnOpenMPReleaseClause(StartLoc, EndLoc);
17008     break;
17009   case OMPC_relaxed:
17010     Res = ActOnOpenMPRelaxedClause(StartLoc, EndLoc);
17011     break;
17012   case OMPC_threads:
17013     Res = ActOnOpenMPThreadsClause(StartLoc, EndLoc);
17014     break;
17015   case OMPC_simd:
17016     Res = ActOnOpenMPSIMDClause(StartLoc, EndLoc);
17017     break;
17018   case OMPC_nogroup:
17019     Res = ActOnOpenMPNogroupClause(StartLoc, EndLoc);
17020     break;
17021   case OMPC_unified_address:
17022     Res = ActOnOpenMPUnifiedAddressClause(StartLoc, EndLoc);
17023     break;
17024   case OMPC_unified_shared_memory:
17025     Res = ActOnOpenMPUnifiedSharedMemoryClause(StartLoc, EndLoc);
17026     break;
17027   case OMPC_reverse_offload:
17028     Res = ActOnOpenMPReverseOffloadClause(StartLoc, EndLoc);
17029     break;
17030   case OMPC_dynamic_allocators:
17031     Res = ActOnOpenMPDynamicAllocatorsClause(StartLoc, EndLoc);
17032     break;
17033   case OMPC_destroy:
17034     Res = ActOnOpenMPDestroyClause(/*InteropVar=*/nullptr, StartLoc,
17035                                    /*LParenLoc=*/SourceLocation(),
17036                                    /*VarLoc=*/SourceLocation(), EndLoc);
17037     break;
17038   case OMPC_full:
17039     Res = ActOnOpenMPFullClause(StartLoc, EndLoc);
17040     break;
17041   case OMPC_partial:
17042     Res = ActOnOpenMPPartialClause(nullptr, StartLoc, /*LParenLoc=*/{}, EndLoc);
17043     break;
17044   case OMPC_if:
17045   case OMPC_final:
17046   case OMPC_num_threads:
17047   case OMPC_safelen:
17048   case OMPC_simdlen:
17049   case OMPC_sizes:
17050   case OMPC_allocator:
17051   case OMPC_collapse:
17052   case OMPC_schedule:
17053   case OMPC_private:
17054   case OMPC_firstprivate:
17055   case OMPC_lastprivate:
17056   case OMPC_shared:
17057   case OMPC_reduction:
17058   case OMPC_task_reduction:
17059   case OMPC_in_reduction:
17060   case OMPC_linear:
17061   case OMPC_aligned:
17062   case OMPC_copyin:
17063   case OMPC_copyprivate:
17064   case OMPC_default:
17065   case OMPC_proc_bind:
17066   case OMPC_threadprivate:
17067   case OMPC_allocate:
17068   case OMPC_flush:
17069   case OMPC_depobj:
17070   case OMPC_depend:
17071   case OMPC_device:
17072   case OMPC_map:
17073   case OMPC_num_teams:
17074   case OMPC_thread_limit:
17075   case OMPC_priority:
17076   case OMPC_grainsize:
17077   case OMPC_num_tasks:
17078   case OMPC_hint:
17079   case OMPC_dist_schedule:
17080   case OMPC_defaultmap:
17081   case OMPC_unknown:
17082   case OMPC_uniform:
17083   case OMPC_to:
17084   case OMPC_from:
17085   case OMPC_use_device_ptr:
17086   case OMPC_use_device_addr:
17087   case OMPC_is_device_ptr:
17088   case OMPC_has_device_addr:
17089   case OMPC_atomic_default_mem_order:
17090   case OMPC_device_type:
17091   case OMPC_match:
17092   case OMPC_nontemporal:
17093   case OMPC_order:
17094   case OMPC_novariants:
17095   case OMPC_nocontext:
17096   case OMPC_detach:
17097   case OMPC_inclusive:
17098   case OMPC_exclusive:
17099   case OMPC_uses_allocators:
17100   case OMPC_affinity:
17101   case OMPC_when:
17102   default:
17103     llvm_unreachable("Clause is not allowed.");
17104   }
17105   return Res;
17106 }
17107 
17108 OMPClause *Sema::ActOnOpenMPNowaitClause(SourceLocation StartLoc,
17109                                          SourceLocation EndLoc) {
17110   DSAStack->setNowaitRegion();
17111   return new (Context) OMPNowaitClause(StartLoc, EndLoc);
17112 }
17113 
17114 OMPClause *Sema::ActOnOpenMPUntiedClause(SourceLocation StartLoc,
17115                                          SourceLocation EndLoc) {
17116   DSAStack->setUntiedRegion();
17117   return new (Context) OMPUntiedClause(StartLoc, EndLoc);
17118 }
17119 
17120 OMPClause *Sema::ActOnOpenMPMergeableClause(SourceLocation StartLoc,
17121                                             SourceLocation EndLoc) {
17122   return new (Context) OMPMergeableClause(StartLoc, EndLoc);
17123 }
17124 
17125 OMPClause *Sema::ActOnOpenMPReadClause(SourceLocation StartLoc,
17126                                        SourceLocation EndLoc) {
17127   return new (Context) OMPReadClause(StartLoc, EndLoc);
17128 }
17129 
17130 OMPClause *Sema::ActOnOpenMPWriteClause(SourceLocation StartLoc,
17131                                         SourceLocation EndLoc) {
17132   return new (Context) OMPWriteClause(StartLoc, EndLoc);
17133 }
17134 
17135 OMPClause *Sema::ActOnOpenMPUpdateClause(SourceLocation StartLoc,
17136                                          SourceLocation EndLoc) {
17137   return OMPUpdateClause::Create(Context, StartLoc, EndLoc);
17138 }
17139 
17140 OMPClause *Sema::ActOnOpenMPCaptureClause(SourceLocation StartLoc,
17141                                           SourceLocation EndLoc) {
17142   return new (Context) OMPCaptureClause(StartLoc, EndLoc);
17143 }
17144 
17145 OMPClause *Sema::ActOnOpenMPCompareClause(SourceLocation StartLoc,
17146                                           SourceLocation EndLoc) {
17147   return new (Context) OMPCompareClause(StartLoc, EndLoc);
17148 }
17149 
17150 OMPClause *Sema::ActOnOpenMPSeqCstClause(SourceLocation StartLoc,
17151                                          SourceLocation EndLoc) {
17152   return new (Context) OMPSeqCstClause(StartLoc, EndLoc);
17153 }
17154 
17155 OMPClause *Sema::ActOnOpenMPAcqRelClause(SourceLocation StartLoc,
17156                                          SourceLocation EndLoc) {
17157   return new (Context) OMPAcqRelClause(StartLoc, EndLoc);
17158 }
17159 
17160 OMPClause *Sema::ActOnOpenMPAcquireClause(SourceLocation StartLoc,
17161                                           SourceLocation EndLoc) {
17162   return new (Context) OMPAcquireClause(StartLoc, EndLoc);
17163 }
17164 
17165 OMPClause *Sema::ActOnOpenMPReleaseClause(SourceLocation StartLoc,
17166                                           SourceLocation EndLoc) {
17167   return new (Context) OMPReleaseClause(StartLoc, EndLoc);
17168 }
17169 
17170 OMPClause *Sema::ActOnOpenMPRelaxedClause(SourceLocation StartLoc,
17171                                           SourceLocation EndLoc) {
17172   return new (Context) OMPRelaxedClause(StartLoc, EndLoc);
17173 }
17174 
17175 OMPClause *Sema::ActOnOpenMPThreadsClause(SourceLocation StartLoc,
17176                                           SourceLocation EndLoc) {
17177   return new (Context) OMPThreadsClause(StartLoc, EndLoc);
17178 }
17179 
17180 OMPClause *Sema::ActOnOpenMPSIMDClause(SourceLocation StartLoc,
17181                                        SourceLocation EndLoc) {
17182   return new (Context) OMPSIMDClause(StartLoc, EndLoc);
17183 }
17184 
17185 OMPClause *Sema::ActOnOpenMPNogroupClause(SourceLocation StartLoc,
17186                                           SourceLocation EndLoc) {
17187   return new (Context) OMPNogroupClause(StartLoc, EndLoc);
17188 }
17189 
17190 OMPClause *Sema::ActOnOpenMPUnifiedAddressClause(SourceLocation StartLoc,
17191                                                  SourceLocation EndLoc) {
17192   return new (Context) OMPUnifiedAddressClause(StartLoc, EndLoc);
17193 }
17194 
17195 OMPClause *Sema::ActOnOpenMPUnifiedSharedMemoryClause(SourceLocation StartLoc,
17196                                                       SourceLocation EndLoc) {
17197   return new (Context) OMPUnifiedSharedMemoryClause(StartLoc, EndLoc);
17198 }
17199 
17200 OMPClause *Sema::ActOnOpenMPReverseOffloadClause(SourceLocation StartLoc,
17201                                                  SourceLocation EndLoc) {
17202   return new (Context) OMPReverseOffloadClause(StartLoc, EndLoc);
17203 }
17204 
17205 OMPClause *Sema::ActOnOpenMPDynamicAllocatorsClause(SourceLocation StartLoc,
17206                                                     SourceLocation EndLoc) {
17207   return new (Context) OMPDynamicAllocatorsClause(StartLoc, EndLoc);
17208 }
17209 
17210 StmtResult Sema::ActOnOpenMPInteropDirective(ArrayRef<OMPClause *> Clauses,
17211                                              SourceLocation StartLoc,
17212                                              SourceLocation EndLoc) {
17213 
17214   // OpenMP 5.1 [2.15.1, interop Construct, Restrictions]
17215   // At least one action-clause must appear on a directive.
17216   if (!hasClauses(Clauses, OMPC_init, OMPC_use, OMPC_destroy, OMPC_nowait)) {
17217     StringRef Expected = "'init', 'use', 'destroy', or 'nowait'";
17218     Diag(StartLoc, diag::err_omp_no_clause_for_directive)
17219         << Expected << getOpenMPDirectiveName(OMPD_interop);
17220     return StmtError();
17221   }
17222 
17223   // OpenMP 5.1 [2.15.1, interop Construct, Restrictions]
17224   // A depend clause can only appear on the directive if a targetsync
17225   // interop-type is present or the interop-var was initialized with
17226   // the targetsync interop-type.
17227 
17228   // If there is any 'init' clause diagnose if there is no 'init' clause with
17229   // interop-type of 'targetsync'. Cases involving other directives cannot be
17230   // diagnosed.
17231   const OMPDependClause *DependClause = nullptr;
17232   bool HasInitClause = false;
17233   bool IsTargetSync = false;
17234   for (const OMPClause *C : Clauses) {
17235     if (IsTargetSync)
17236       break;
17237     if (const auto *InitClause = dyn_cast<OMPInitClause>(C)) {
17238       HasInitClause = true;
17239       if (InitClause->getIsTargetSync())
17240         IsTargetSync = true;
17241     } else if (const auto *DC = dyn_cast<OMPDependClause>(C)) {
17242       DependClause = DC;
17243     }
17244   }
17245   if (DependClause && HasInitClause && !IsTargetSync) {
17246     Diag(DependClause->getBeginLoc(), diag::err_omp_interop_bad_depend_clause);
17247     return StmtError();
17248   }
17249 
17250   // OpenMP 5.1 [2.15.1, interop Construct, Restrictions]
17251   // Each interop-var may be specified for at most one action-clause of each
17252   // interop construct.
17253   llvm::SmallPtrSet<const VarDecl *, 4> InteropVars;
17254   for (const OMPClause *C : Clauses) {
17255     OpenMPClauseKind ClauseKind = C->getClauseKind();
17256     const DeclRefExpr *DRE = nullptr;
17257     SourceLocation VarLoc;
17258 
17259     if (ClauseKind == OMPC_init) {
17260       const auto *IC = cast<OMPInitClause>(C);
17261       VarLoc = IC->getVarLoc();
17262       DRE = dyn_cast_or_null<DeclRefExpr>(IC->getInteropVar());
17263     } else if (ClauseKind == OMPC_use) {
17264       const auto *UC = cast<OMPUseClause>(C);
17265       VarLoc = UC->getVarLoc();
17266       DRE = dyn_cast_or_null<DeclRefExpr>(UC->getInteropVar());
17267     } else if (ClauseKind == OMPC_destroy) {
17268       const auto *DC = cast<OMPDestroyClause>(C);
17269       VarLoc = DC->getVarLoc();
17270       DRE = dyn_cast_or_null<DeclRefExpr>(DC->getInteropVar());
17271     }
17272 
17273     if (!DRE)
17274       continue;
17275 
17276     if (const auto *VD = dyn_cast<VarDecl>(DRE->getDecl())) {
17277       if (!InteropVars.insert(VD->getCanonicalDecl()).second) {
17278         Diag(VarLoc, diag::err_omp_interop_var_multiple_actions) << VD;
17279         return StmtError();
17280       }
17281     }
17282   }
17283 
17284   return OMPInteropDirective::Create(Context, StartLoc, EndLoc, Clauses);
17285 }
17286 
17287 static bool isValidInteropVariable(Sema &SemaRef, Expr *InteropVarExpr,
17288                                    SourceLocation VarLoc,
17289                                    OpenMPClauseKind Kind) {
17290   if (InteropVarExpr->isValueDependent() || InteropVarExpr->isTypeDependent() ||
17291       InteropVarExpr->isInstantiationDependent() ||
17292       InteropVarExpr->containsUnexpandedParameterPack())
17293     return true;
17294 
17295   const auto *DRE = dyn_cast<DeclRefExpr>(InteropVarExpr);
17296   if (!DRE || !isa<VarDecl>(DRE->getDecl())) {
17297     SemaRef.Diag(VarLoc, diag::err_omp_interop_variable_expected) << 0;
17298     return false;
17299   }
17300 
17301   // Interop variable should be of type omp_interop_t.
17302   bool HasError = false;
17303   QualType InteropType;
17304   LookupResult Result(SemaRef, &SemaRef.Context.Idents.get("omp_interop_t"),
17305                       VarLoc, Sema::LookupOrdinaryName);
17306   if (SemaRef.LookupName(Result, SemaRef.getCurScope())) {
17307     NamedDecl *ND = Result.getFoundDecl();
17308     if (const auto *TD = dyn_cast<TypeDecl>(ND)) {
17309       InteropType = QualType(TD->getTypeForDecl(), 0);
17310     } else {
17311       HasError = true;
17312     }
17313   } else {
17314     HasError = true;
17315   }
17316 
17317   if (HasError) {
17318     SemaRef.Diag(VarLoc, diag::err_omp_implied_type_not_found)
17319         << "omp_interop_t";
17320     return false;
17321   }
17322 
17323   QualType VarType = InteropVarExpr->getType().getUnqualifiedType();
17324   if (!SemaRef.Context.hasSameType(InteropType, VarType)) {
17325     SemaRef.Diag(VarLoc, diag::err_omp_interop_variable_wrong_type);
17326     return false;
17327   }
17328 
17329   // OpenMP 5.1 [2.15.1, interop Construct, Restrictions]
17330   // The interop-var passed to init or destroy must be non-const.
17331   if ((Kind == OMPC_init || Kind == OMPC_destroy) &&
17332       isConstNotMutableType(SemaRef, InteropVarExpr->getType())) {
17333     SemaRef.Diag(VarLoc, diag::err_omp_interop_variable_expected)
17334         << /*non-const*/ 1;
17335     return false;
17336   }
17337   return true;
17338 }
17339 
17340 OMPClause *
17341 Sema::ActOnOpenMPInitClause(Expr *InteropVar, ArrayRef<Expr *> PrefExprs,
17342                             bool IsTarget, bool IsTargetSync,
17343                             SourceLocation StartLoc, SourceLocation LParenLoc,
17344                             SourceLocation VarLoc, SourceLocation EndLoc) {
17345 
17346   if (!isValidInteropVariable(*this, InteropVar, VarLoc, OMPC_init))
17347     return nullptr;
17348 
17349   // Check prefer_type values.  These foreign-runtime-id values are either
17350   // string literals or constant integral expressions.
17351   for (const Expr *E : PrefExprs) {
17352     if (E->isValueDependent() || E->isTypeDependent() ||
17353         E->isInstantiationDependent() || E->containsUnexpandedParameterPack())
17354       continue;
17355     if (E->isIntegerConstantExpr(Context))
17356       continue;
17357     if (isa<StringLiteral>(E))
17358       continue;
17359     Diag(E->getExprLoc(), diag::err_omp_interop_prefer_type);
17360     return nullptr;
17361   }
17362 
17363   return OMPInitClause::Create(Context, InteropVar, PrefExprs, IsTarget,
17364                                IsTargetSync, StartLoc, LParenLoc, VarLoc,
17365                                EndLoc);
17366 }
17367 
17368 OMPClause *Sema::ActOnOpenMPUseClause(Expr *InteropVar, SourceLocation StartLoc,
17369                                       SourceLocation LParenLoc,
17370                                       SourceLocation VarLoc,
17371                                       SourceLocation EndLoc) {
17372 
17373   if (!isValidInteropVariable(*this, InteropVar, VarLoc, OMPC_use))
17374     return nullptr;
17375 
17376   return new (Context)
17377       OMPUseClause(InteropVar, StartLoc, LParenLoc, VarLoc, EndLoc);
17378 }
17379 
17380 OMPClause *Sema::ActOnOpenMPDestroyClause(Expr *InteropVar,
17381                                           SourceLocation StartLoc,
17382                                           SourceLocation LParenLoc,
17383                                           SourceLocation VarLoc,
17384                                           SourceLocation EndLoc) {
17385   if (InteropVar &&
17386       !isValidInteropVariable(*this, InteropVar, VarLoc, OMPC_destroy))
17387     return nullptr;
17388 
17389   return new (Context)
17390       OMPDestroyClause(InteropVar, StartLoc, LParenLoc, VarLoc, EndLoc);
17391 }
17392 
17393 OMPClause *Sema::ActOnOpenMPNovariantsClause(Expr *Condition,
17394                                              SourceLocation StartLoc,
17395                                              SourceLocation LParenLoc,
17396                                              SourceLocation EndLoc) {
17397   Expr *ValExpr = Condition;
17398   Stmt *HelperValStmt = nullptr;
17399   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
17400   if (!Condition->isValueDependent() && !Condition->isTypeDependent() &&
17401       !Condition->isInstantiationDependent() &&
17402       !Condition->containsUnexpandedParameterPack()) {
17403     ExprResult Val = CheckBooleanCondition(StartLoc, Condition);
17404     if (Val.isInvalid())
17405       return nullptr;
17406 
17407     ValExpr = MakeFullExpr(Val.get()).get();
17408 
17409     OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
17410     CaptureRegion = getOpenMPCaptureRegionForClause(DKind, OMPC_novariants,
17411                                                     LangOpts.OpenMP);
17412     if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
17413       ValExpr = MakeFullExpr(ValExpr).get();
17414       llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
17415       ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
17416       HelperValStmt = buildPreInits(Context, Captures);
17417     }
17418   }
17419 
17420   return new (Context) OMPNovariantsClause(
17421       ValExpr, HelperValStmt, CaptureRegion, StartLoc, LParenLoc, EndLoc);
17422 }
17423 
17424 OMPClause *Sema::ActOnOpenMPNocontextClause(Expr *Condition,
17425                                             SourceLocation StartLoc,
17426                                             SourceLocation LParenLoc,
17427                                             SourceLocation EndLoc) {
17428   Expr *ValExpr = Condition;
17429   Stmt *HelperValStmt = nullptr;
17430   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
17431   if (!Condition->isValueDependent() && !Condition->isTypeDependent() &&
17432       !Condition->isInstantiationDependent() &&
17433       !Condition->containsUnexpandedParameterPack()) {
17434     ExprResult Val = CheckBooleanCondition(StartLoc, Condition);
17435     if (Val.isInvalid())
17436       return nullptr;
17437 
17438     ValExpr = MakeFullExpr(Val.get()).get();
17439 
17440     OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
17441     CaptureRegion =
17442         getOpenMPCaptureRegionForClause(DKind, OMPC_nocontext, LangOpts.OpenMP);
17443     if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
17444       ValExpr = MakeFullExpr(ValExpr).get();
17445       llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
17446       ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
17447       HelperValStmt = buildPreInits(Context, Captures);
17448     }
17449   }
17450 
17451   return new (Context) OMPNocontextClause(ValExpr, HelperValStmt, CaptureRegion,
17452                                           StartLoc, LParenLoc, EndLoc);
17453 }
17454 
17455 OMPClause *Sema::ActOnOpenMPFilterClause(Expr *ThreadID,
17456                                          SourceLocation StartLoc,
17457                                          SourceLocation LParenLoc,
17458                                          SourceLocation EndLoc) {
17459   Expr *ValExpr = ThreadID;
17460   Stmt *HelperValStmt = nullptr;
17461 
17462   OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
17463   OpenMPDirectiveKind CaptureRegion =
17464       getOpenMPCaptureRegionForClause(DKind, OMPC_filter, LangOpts.OpenMP);
17465   if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
17466     ValExpr = MakeFullExpr(ValExpr).get();
17467     llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
17468     ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
17469     HelperValStmt = buildPreInits(Context, Captures);
17470   }
17471 
17472   return new (Context) OMPFilterClause(ValExpr, HelperValStmt, CaptureRegion,
17473                                        StartLoc, LParenLoc, EndLoc);
17474 }
17475 
17476 OMPClause *Sema::ActOnOpenMPVarListClause(OpenMPClauseKind Kind,
17477                                           ArrayRef<Expr *> VarList,
17478                                           const OMPVarListLocTy &Locs,
17479                                           OpenMPVarListDataTy &Data) {
17480   SourceLocation StartLoc = Locs.StartLoc;
17481   SourceLocation LParenLoc = Locs.LParenLoc;
17482   SourceLocation EndLoc = Locs.EndLoc;
17483   OMPClause *Res = nullptr;
17484   int ExtraModifier = Data.ExtraModifier;
17485   SourceLocation ExtraModifierLoc = Data.ExtraModifierLoc;
17486   SourceLocation ColonLoc = Data.ColonLoc;
17487   switch (Kind) {
17488   case OMPC_private:
17489     Res = ActOnOpenMPPrivateClause(VarList, StartLoc, LParenLoc, EndLoc);
17490     break;
17491   case OMPC_firstprivate:
17492     Res = ActOnOpenMPFirstprivateClause(VarList, StartLoc, LParenLoc, EndLoc);
17493     break;
17494   case OMPC_lastprivate:
17495     assert(0 <= ExtraModifier && ExtraModifier <= OMPC_LASTPRIVATE_unknown &&
17496            "Unexpected lastprivate modifier.");
17497     Res = ActOnOpenMPLastprivateClause(
17498         VarList, static_cast<OpenMPLastprivateModifier>(ExtraModifier),
17499         ExtraModifierLoc, ColonLoc, StartLoc, LParenLoc, EndLoc);
17500     break;
17501   case OMPC_shared:
17502     Res = ActOnOpenMPSharedClause(VarList, StartLoc, LParenLoc, EndLoc);
17503     break;
17504   case OMPC_reduction:
17505     assert(0 <= ExtraModifier && ExtraModifier <= OMPC_REDUCTION_unknown &&
17506            "Unexpected lastprivate modifier.");
17507     Res = ActOnOpenMPReductionClause(
17508         VarList, static_cast<OpenMPReductionClauseModifier>(ExtraModifier),
17509         StartLoc, LParenLoc, ExtraModifierLoc, ColonLoc, EndLoc,
17510         Data.ReductionOrMapperIdScopeSpec, Data.ReductionOrMapperId);
17511     break;
17512   case OMPC_task_reduction:
17513     Res = ActOnOpenMPTaskReductionClause(
17514         VarList, StartLoc, LParenLoc, ColonLoc, EndLoc,
17515         Data.ReductionOrMapperIdScopeSpec, Data.ReductionOrMapperId);
17516     break;
17517   case OMPC_in_reduction:
17518     Res = ActOnOpenMPInReductionClause(
17519         VarList, StartLoc, LParenLoc, ColonLoc, EndLoc,
17520         Data.ReductionOrMapperIdScopeSpec, Data.ReductionOrMapperId);
17521     break;
17522   case OMPC_linear:
17523     assert(0 <= ExtraModifier && ExtraModifier <= OMPC_LINEAR_unknown &&
17524            "Unexpected linear modifier.");
17525     Res = ActOnOpenMPLinearClause(
17526         VarList, Data.DepModOrTailExpr, StartLoc, LParenLoc,
17527         static_cast<OpenMPLinearClauseKind>(ExtraModifier), ExtraModifierLoc,
17528         ColonLoc, EndLoc);
17529     break;
17530   case OMPC_aligned:
17531     Res = ActOnOpenMPAlignedClause(VarList, Data.DepModOrTailExpr, StartLoc,
17532                                    LParenLoc, ColonLoc, EndLoc);
17533     break;
17534   case OMPC_copyin:
17535     Res = ActOnOpenMPCopyinClause(VarList, StartLoc, LParenLoc, EndLoc);
17536     break;
17537   case OMPC_copyprivate:
17538     Res = ActOnOpenMPCopyprivateClause(VarList, StartLoc, LParenLoc, EndLoc);
17539     break;
17540   case OMPC_flush:
17541     Res = ActOnOpenMPFlushClause(VarList, StartLoc, LParenLoc, EndLoc);
17542     break;
17543   case OMPC_depend:
17544     assert(0 <= ExtraModifier && ExtraModifier <= OMPC_DEPEND_unknown &&
17545            "Unexpected depend modifier.");
17546     Res = ActOnOpenMPDependClause(
17547         {static_cast<OpenMPDependClauseKind>(ExtraModifier), ExtraModifierLoc,
17548          ColonLoc, Data.OmpAllMemoryLoc},
17549         Data.DepModOrTailExpr, VarList, StartLoc, LParenLoc, EndLoc);
17550     break;
17551   case OMPC_map:
17552     assert(0 <= ExtraModifier && ExtraModifier <= OMPC_MAP_unknown &&
17553            "Unexpected map modifier.");
17554     Res = ActOnOpenMPMapClause(
17555         Data.MapTypeModifiers, Data.MapTypeModifiersLoc,
17556         Data.ReductionOrMapperIdScopeSpec, Data.ReductionOrMapperId,
17557         static_cast<OpenMPMapClauseKind>(ExtraModifier), Data.IsMapTypeImplicit,
17558         ExtraModifierLoc, ColonLoc, VarList, Locs);
17559     break;
17560   case OMPC_to:
17561     Res =
17562         ActOnOpenMPToClause(Data.MotionModifiers, Data.MotionModifiersLoc,
17563                             Data.ReductionOrMapperIdScopeSpec,
17564                             Data.ReductionOrMapperId, ColonLoc, VarList, Locs);
17565     break;
17566   case OMPC_from:
17567     Res = ActOnOpenMPFromClause(Data.MotionModifiers, Data.MotionModifiersLoc,
17568                                 Data.ReductionOrMapperIdScopeSpec,
17569                                 Data.ReductionOrMapperId, ColonLoc, VarList,
17570                                 Locs);
17571     break;
17572   case OMPC_use_device_ptr:
17573     Res = ActOnOpenMPUseDevicePtrClause(VarList, Locs);
17574     break;
17575   case OMPC_use_device_addr:
17576     Res = ActOnOpenMPUseDeviceAddrClause(VarList, Locs);
17577     break;
17578   case OMPC_is_device_ptr:
17579     Res = ActOnOpenMPIsDevicePtrClause(VarList, Locs);
17580     break;
17581   case OMPC_has_device_addr:
17582     Res = ActOnOpenMPHasDeviceAddrClause(VarList, Locs);
17583     break;
17584   case OMPC_allocate:
17585     Res = ActOnOpenMPAllocateClause(Data.DepModOrTailExpr, VarList, StartLoc,
17586                                     LParenLoc, ColonLoc, EndLoc);
17587     break;
17588   case OMPC_nontemporal:
17589     Res = ActOnOpenMPNontemporalClause(VarList, StartLoc, LParenLoc, EndLoc);
17590     break;
17591   case OMPC_inclusive:
17592     Res = ActOnOpenMPInclusiveClause(VarList, StartLoc, LParenLoc, EndLoc);
17593     break;
17594   case OMPC_exclusive:
17595     Res = ActOnOpenMPExclusiveClause(VarList, StartLoc, LParenLoc, EndLoc);
17596     break;
17597   case OMPC_affinity:
17598     Res = ActOnOpenMPAffinityClause(StartLoc, LParenLoc, ColonLoc, EndLoc,
17599                                     Data.DepModOrTailExpr, VarList);
17600     break;
17601   case OMPC_if:
17602   case OMPC_depobj:
17603   case OMPC_final:
17604   case OMPC_num_threads:
17605   case OMPC_safelen:
17606   case OMPC_simdlen:
17607   case OMPC_sizes:
17608   case OMPC_allocator:
17609   case OMPC_collapse:
17610   case OMPC_default:
17611   case OMPC_proc_bind:
17612   case OMPC_schedule:
17613   case OMPC_ordered:
17614   case OMPC_nowait:
17615   case OMPC_untied:
17616   case OMPC_mergeable:
17617   case OMPC_threadprivate:
17618   case OMPC_read:
17619   case OMPC_write:
17620   case OMPC_update:
17621   case OMPC_capture:
17622   case OMPC_compare:
17623   case OMPC_seq_cst:
17624   case OMPC_acq_rel:
17625   case OMPC_acquire:
17626   case OMPC_release:
17627   case OMPC_relaxed:
17628   case OMPC_device:
17629   case OMPC_threads:
17630   case OMPC_simd:
17631   case OMPC_num_teams:
17632   case OMPC_thread_limit:
17633   case OMPC_priority:
17634   case OMPC_grainsize:
17635   case OMPC_nogroup:
17636   case OMPC_num_tasks:
17637   case OMPC_hint:
17638   case OMPC_dist_schedule:
17639   case OMPC_defaultmap:
17640   case OMPC_unknown:
17641   case OMPC_uniform:
17642   case OMPC_unified_address:
17643   case OMPC_unified_shared_memory:
17644   case OMPC_reverse_offload:
17645   case OMPC_dynamic_allocators:
17646   case OMPC_atomic_default_mem_order:
17647   case OMPC_device_type:
17648   case OMPC_match:
17649   case OMPC_order:
17650   case OMPC_destroy:
17651   case OMPC_novariants:
17652   case OMPC_nocontext:
17653   case OMPC_detach:
17654   case OMPC_uses_allocators:
17655   case OMPC_when:
17656   case OMPC_bind:
17657   default:
17658     llvm_unreachable("Clause is not allowed.");
17659   }
17660   return Res;
17661 }
17662 
17663 ExprResult Sema::getOpenMPCapturedExpr(VarDecl *Capture, ExprValueKind VK,
17664                                        ExprObjectKind OK, SourceLocation Loc) {
17665   ExprResult Res = BuildDeclRefExpr(
17666       Capture, Capture->getType().getNonReferenceType(), VK_LValue, Loc);
17667   if (!Res.isUsable())
17668     return ExprError();
17669   if (OK == OK_Ordinary && !getLangOpts().CPlusPlus) {
17670     Res = CreateBuiltinUnaryOp(Loc, UO_Deref, Res.get());
17671     if (!Res.isUsable())
17672       return ExprError();
17673   }
17674   if (VK != VK_LValue && Res.get()->isGLValue()) {
17675     Res = DefaultLvalueConversion(Res.get());
17676     if (!Res.isUsable())
17677       return ExprError();
17678   }
17679   return Res;
17680 }
17681 
17682 OMPClause *Sema::ActOnOpenMPPrivateClause(ArrayRef<Expr *> VarList,
17683                                           SourceLocation StartLoc,
17684                                           SourceLocation LParenLoc,
17685                                           SourceLocation EndLoc) {
17686   SmallVector<Expr *, 8> Vars;
17687   SmallVector<Expr *, 8> PrivateCopies;
17688   bool IsImplicitClause =
17689       StartLoc.isInvalid() && LParenLoc.isInvalid() && EndLoc.isInvalid();
17690   for (Expr *RefExpr : VarList) {
17691     assert(RefExpr && "NULL expr in OpenMP private clause.");
17692     SourceLocation ELoc;
17693     SourceRange ERange;
17694     Expr *SimpleRefExpr = RefExpr;
17695     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
17696     if (Res.second) {
17697       // It will be analyzed later.
17698       Vars.push_back(RefExpr);
17699       PrivateCopies.push_back(nullptr);
17700     }
17701     ValueDecl *D = Res.first;
17702     if (!D)
17703       continue;
17704 
17705     QualType Type = D->getType();
17706     auto *VD = dyn_cast<VarDecl>(D);
17707 
17708     // OpenMP [2.9.3.3, Restrictions, C/C++, p.3]
17709     //  A variable that appears in a private clause must not have an incomplete
17710     //  type or a reference type.
17711     if (RequireCompleteType(ELoc, Type, diag::err_omp_private_incomplete_type))
17712       continue;
17713     Type = Type.getNonReferenceType();
17714 
17715     // OpenMP 5.0 [2.19.3, List Item Privatization, Restrictions]
17716     // A variable that is privatized must not have a const-qualified type
17717     // unless it is of class type with a mutable member. This restriction does
17718     // not apply to the firstprivate clause.
17719     //
17720     // OpenMP 3.1 [2.9.3.3, private clause, Restrictions]
17721     // A variable that appears in a private clause must not have a
17722     // const-qualified type unless it is of class type with a mutable member.
17723     if (rejectConstNotMutableType(*this, D, Type, OMPC_private, ELoc))
17724       continue;
17725 
17726     // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
17727     // in a Construct]
17728     //  Variables with the predetermined data-sharing attributes may not be
17729     //  listed in data-sharing attributes clauses, except for the cases
17730     //  listed below. For these exceptions only, listing a predetermined
17731     //  variable in a data-sharing attribute clause is allowed and overrides
17732     //  the variable's predetermined data-sharing attributes.
17733     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(D, /*FromParent=*/false);
17734     if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_private) {
17735       Diag(ELoc, diag::err_omp_wrong_dsa) << getOpenMPClauseName(DVar.CKind)
17736                                           << getOpenMPClauseName(OMPC_private);
17737       reportOriginalDsa(*this, DSAStack, D, DVar);
17738       continue;
17739     }
17740 
17741     OpenMPDirectiveKind CurrDir = DSAStack->getCurrentDirective();
17742     // Variably modified types are not supported for tasks.
17743     if (!Type->isAnyPointerType() && Type->isVariablyModifiedType() &&
17744         isOpenMPTaskingDirective(CurrDir)) {
17745       Diag(ELoc, diag::err_omp_variably_modified_type_not_supported)
17746           << getOpenMPClauseName(OMPC_private) << Type
17747           << getOpenMPDirectiveName(CurrDir);
17748       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
17749                                VarDecl::DeclarationOnly;
17750       Diag(D->getLocation(),
17751            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
17752           << D;
17753       continue;
17754     }
17755 
17756     // OpenMP 4.5 [2.15.5.1, Restrictions, p.3]
17757     // A list item cannot appear in both a map clause and a data-sharing
17758     // attribute clause on the same construct
17759     //
17760     // OpenMP 5.0 [2.19.7.1, Restrictions, p.7]
17761     // A list item cannot appear in both a map clause and a data-sharing
17762     // attribute clause on the same construct unless the construct is a
17763     // combined construct.
17764     if ((LangOpts.OpenMP <= 45 && isOpenMPTargetExecutionDirective(CurrDir)) ||
17765         CurrDir == OMPD_target) {
17766       OpenMPClauseKind ConflictKind;
17767       if (DSAStack->checkMappableExprComponentListsForDecl(
17768               VD, /*CurrentRegionOnly=*/true,
17769               [&](OMPClauseMappableExprCommon::MappableExprComponentListRef,
17770                   OpenMPClauseKind WhereFoundClauseKind) -> bool {
17771                 ConflictKind = WhereFoundClauseKind;
17772                 return true;
17773               })) {
17774         Diag(ELoc, diag::err_omp_variable_in_given_clause_and_dsa)
17775             << getOpenMPClauseName(OMPC_private)
17776             << getOpenMPClauseName(ConflictKind)
17777             << getOpenMPDirectiveName(CurrDir);
17778         reportOriginalDsa(*this, DSAStack, D, DVar);
17779         continue;
17780       }
17781     }
17782 
17783     // OpenMP [2.9.3.3, Restrictions, C/C++, p.1]
17784     //  A variable of class type (or array thereof) that appears in a private
17785     //  clause requires an accessible, unambiguous default constructor for the
17786     //  class type.
17787     // Generate helper private variable and initialize it with the default
17788     // value. The address of the original variable is replaced by the address of
17789     // the new private variable in CodeGen. This new variable is not added to
17790     // IdResolver, so the code in the OpenMP region uses original variable for
17791     // proper diagnostics.
17792     Type = Type.getUnqualifiedType();
17793     VarDecl *VDPrivate =
17794         buildVarDecl(*this, ELoc, Type, D->getName(),
17795                      D->hasAttrs() ? &D->getAttrs() : nullptr,
17796                      VD ? cast<DeclRefExpr>(SimpleRefExpr) : nullptr);
17797     ActOnUninitializedDecl(VDPrivate);
17798     if (VDPrivate->isInvalidDecl())
17799       continue;
17800     DeclRefExpr *VDPrivateRefExpr = buildDeclRefExpr(
17801         *this, VDPrivate, RefExpr->getType().getUnqualifiedType(), ELoc);
17802 
17803     DeclRefExpr *Ref = nullptr;
17804     if (!VD && !CurContext->isDependentContext()) {
17805       auto *FD = dyn_cast<FieldDecl>(D);
17806       VarDecl *VD = FD ? DSAStack->getImplicitFDCapExprDecl(FD) : nullptr;
17807       if (VD)
17808         Ref = buildDeclRefExpr(*this, VD, VD->getType().getNonReferenceType(),
17809                                RefExpr->getExprLoc());
17810       else
17811         Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/false);
17812     }
17813     if (!IsImplicitClause)
17814       DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_private, Ref);
17815     Vars.push_back((VD || CurContext->isDependentContext())
17816                        ? RefExpr->IgnoreParens()
17817                        : Ref);
17818     PrivateCopies.push_back(VDPrivateRefExpr);
17819   }
17820 
17821   if (Vars.empty())
17822     return nullptr;
17823 
17824   return OMPPrivateClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars,
17825                                   PrivateCopies);
17826 }
17827 
17828 OMPClause *Sema::ActOnOpenMPFirstprivateClause(ArrayRef<Expr *> VarList,
17829                                                SourceLocation StartLoc,
17830                                                SourceLocation LParenLoc,
17831                                                SourceLocation EndLoc) {
17832   SmallVector<Expr *, 8> Vars;
17833   SmallVector<Expr *, 8> PrivateCopies;
17834   SmallVector<Expr *, 8> Inits;
17835   SmallVector<Decl *, 4> ExprCaptures;
17836   bool IsImplicitClause =
17837       StartLoc.isInvalid() && LParenLoc.isInvalid() && EndLoc.isInvalid();
17838   SourceLocation ImplicitClauseLoc = DSAStack->getConstructLoc();
17839 
17840   for (Expr *RefExpr : VarList) {
17841     assert(RefExpr && "NULL expr in OpenMP firstprivate clause.");
17842     SourceLocation ELoc;
17843     SourceRange ERange;
17844     Expr *SimpleRefExpr = RefExpr;
17845     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
17846     if (Res.second) {
17847       // It will be analyzed later.
17848       Vars.push_back(RefExpr);
17849       PrivateCopies.push_back(nullptr);
17850       Inits.push_back(nullptr);
17851     }
17852     ValueDecl *D = Res.first;
17853     if (!D)
17854       continue;
17855 
17856     ELoc = IsImplicitClause ? ImplicitClauseLoc : ELoc;
17857     QualType Type = D->getType();
17858     auto *VD = dyn_cast<VarDecl>(D);
17859 
17860     // OpenMP [2.9.3.3, Restrictions, C/C++, p.3]
17861     //  A variable that appears in a private clause must not have an incomplete
17862     //  type or a reference type.
17863     if (RequireCompleteType(ELoc, Type,
17864                             diag::err_omp_firstprivate_incomplete_type))
17865       continue;
17866     Type = Type.getNonReferenceType();
17867 
17868     // OpenMP [2.9.3.4, Restrictions, C/C++, p.1]
17869     //  A variable of class type (or array thereof) that appears in a private
17870     //  clause requires an accessible, unambiguous copy constructor for the
17871     //  class type.
17872     QualType ElemType = Context.getBaseElementType(Type).getNonReferenceType();
17873 
17874     // If an implicit firstprivate variable found it was checked already.
17875     DSAStackTy::DSAVarData TopDVar;
17876     if (!IsImplicitClause) {
17877       DSAStackTy::DSAVarData DVar =
17878           DSAStack->getTopDSA(D, /*FromParent=*/false);
17879       TopDVar = DVar;
17880       OpenMPDirectiveKind CurrDir = DSAStack->getCurrentDirective();
17881       bool IsConstant = ElemType.isConstant(Context);
17882       // OpenMP [2.4.13, Data-sharing Attribute Clauses]
17883       //  A list item that specifies a given variable may not appear in more
17884       // than one clause on the same directive, except that a variable may be
17885       //  specified in both firstprivate and lastprivate clauses.
17886       // OpenMP 4.5 [2.10.8, Distribute Construct, p.3]
17887       // A list item may appear in a firstprivate or lastprivate clause but not
17888       // both.
17889       if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_firstprivate &&
17890           (isOpenMPDistributeDirective(CurrDir) ||
17891            DVar.CKind != OMPC_lastprivate) &&
17892           DVar.RefExpr) {
17893         Diag(ELoc, diag::err_omp_wrong_dsa)
17894             << getOpenMPClauseName(DVar.CKind)
17895             << getOpenMPClauseName(OMPC_firstprivate);
17896         reportOriginalDsa(*this, DSAStack, D, DVar);
17897         continue;
17898       }
17899 
17900       // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
17901       // in a Construct]
17902       //  Variables with the predetermined data-sharing attributes may not be
17903       //  listed in data-sharing attributes clauses, except for the cases
17904       //  listed below. For these exceptions only, listing a predetermined
17905       //  variable in a data-sharing attribute clause is allowed and overrides
17906       //  the variable's predetermined data-sharing attributes.
17907       // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
17908       // in a Construct, C/C++, p.2]
17909       //  Variables with const-qualified type having no mutable member may be
17910       //  listed in a firstprivate clause, even if they are static data members.
17911       if (!(IsConstant || (VD && VD->isStaticDataMember())) && !DVar.RefExpr &&
17912           DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_shared) {
17913         Diag(ELoc, diag::err_omp_wrong_dsa)
17914             << getOpenMPClauseName(DVar.CKind)
17915             << getOpenMPClauseName(OMPC_firstprivate);
17916         reportOriginalDsa(*this, DSAStack, D, DVar);
17917         continue;
17918       }
17919 
17920       // OpenMP [2.9.3.4, Restrictions, p.2]
17921       //  A list item that is private within a parallel region must not appear
17922       //  in a firstprivate clause on a worksharing construct if any of the
17923       //  worksharing regions arising from the worksharing construct ever bind
17924       //  to any of the parallel regions arising from the parallel construct.
17925       // OpenMP 4.5 [2.15.3.4, Restrictions, p.3]
17926       // A list item that is private within a teams region must not appear in a
17927       // firstprivate clause on a distribute construct if any of the distribute
17928       // regions arising from the distribute construct ever bind to any of the
17929       // teams regions arising from the teams construct.
17930       // OpenMP 4.5 [2.15.3.4, Restrictions, p.3]
17931       // A list item that appears in a reduction clause of a teams construct
17932       // must not appear in a firstprivate clause on a distribute construct if
17933       // any of the distribute regions arising from the distribute construct
17934       // ever bind to any of the teams regions arising from the teams construct.
17935       if ((isOpenMPWorksharingDirective(CurrDir) ||
17936            isOpenMPDistributeDirective(CurrDir)) &&
17937           !isOpenMPParallelDirective(CurrDir) &&
17938           !isOpenMPTeamsDirective(CurrDir)) {
17939         DVar = DSAStack->getImplicitDSA(D, true);
17940         if (DVar.CKind != OMPC_shared &&
17941             (isOpenMPParallelDirective(DVar.DKind) ||
17942              isOpenMPTeamsDirective(DVar.DKind) ||
17943              DVar.DKind == OMPD_unknown)) {
17944           Diag(ELoc, diag::err_omp_required_access)
17945               << getOpenMPClauseName(OMPC_firstprivate)
17946               << getOpenMPClauseName(OMPC_shared);
17947           reportOriginalDsa(*this, DSAStack, D, DVar);
17948           continue;
17949         }
17950       }
17951       // OpenMP [2.9.3.4, Restrictions, p.3]
17952       //  A list item that appears in a reduction clause of a parallel construct
17953       //  must not appear in a firstprivate clause on a worksharing or task
17954       //  construct if any of the worksharing or task regions arising from the
17955       //  worksharing or task construct ever bind to any of the parallel regions
17956       //  arising from the parallel construct.
17957       // OpenMP [2.9.3.4, Restrictions, p.4]
17958       //  A list item that appears in a reduction clause in worksharing
17959       //  construct must not appear in a firstprivate clause in a task construct
17960       //  encountered during execution of any of the worksharing regions arising
17961       //  from the worksharing construct.
17962       if (isOpenMPTaskingDirective(CurrDir)) {
17963         DVar = DSAStack->hasInnermostDSA(
17964             D,
17965             [](OpenMPClauseKind C, bool AppliedToPointee) {
17966               return C == OMPC_reduction && !AppliedToPointee;
17967             },
17968             [](OpenMPDirectiveKind K) {
17969               return isOpenMPParallelDirective(K) ||
17970                      isOpenMPWorksharingDirective(K) ||
17971                      isOpenMPTeamsDirective(K);
17972             },
17973             /*FromParent=*/true);
17974         if (DVar.CKind == OMPC_reduction &&
17975             (isOpenMPParallelDirective(DVar.DKind) ||
17976              isOpenMPWorksharingDirective(DVar.DKind) ||
17977              isOpenMPTeamsDirective(DVar.DKind))) {
17978           Diag(ELoc, diag::err_omp_parallel_reduction_in_task_firstprivate)
17979               << getOpenMPDirectiveName(DVar.DKind);
17980           reportOriginalDsa(*this, DSAStack, D, DVar);
17981           continue;
17982         }
17983       }
17984 
17985       // OpenMP 4.5 [2.15.5.1, Restrictions, p.3]
17986       // A list item cannot appear in both a map clause and a data-sharing
17987       // attribute clause on the same construct
17988       //
17989       // OpenMP 5.0 [2.19.7.1, Restrictions, p.7]
17990       // A list item cannot appear in both a map clause and a data-sharing
17991       // attribute clause on the same construct unless the construct is a
17992       // combined construct.
17993       if ((LangOpts.OpenMP <= 45 &&
17994            isOpenMPTargetExecutionDirective(CurrDir)) ||
17995           CurrDir == OMPD_target) {
17996         OpenMPClauseKind ConflictKind;
17997         if (DSAStack->checkMappableExprComponentListsForDecl(
17998                 VD, /*CurrentRegionOnly=*/true,
17999                 [&ConflictKind](
18000                     OMPClauseMappableExprCommon::MappableExprComponentListRef,
18001                     OpenMPClauseKind WhereFoundClauseKind) {
18002                   ConflictKind = WhereFoundClauseKind;
18003                   return true;
18004                 })) {
18005           Diag(ELoc, diag::err_omp_variable_in_given_clause_and_dsa)
18006               << getOpenMPClauseName(OMPC_firstprivate)
18007               << getOpenMPClauseName(ConflictKind)
18008               << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
18009           reportOriginalDsa(*this, DSAStack, D, DVar);
18010           continue;
18011         }
18012       }
18013     }
18014 
18015     // Variably modified types are not supported for tasks.
18016     if (!Type->isAnyPointerType() && Type->isVariablyModifiedType() &&
18017         isOpenMPTaskingDirective(DSAStack->getCurrentDirective())) {
18018       Diag(ELoc, diag::err_omp_variably_modified_type_not_supported)
18019           << getOpenMPClauseName(OMPC_firstprivate) << Type
18020           << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
18021       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
18022                                VarDecl::DeclarationOnly;
18023       Diag(D->getLocation(),
18024            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
18025           << D;
18026       continue;
18027     }
18028 
18029     Type = Type.getUnqualifiedType();
18030     VarDecl *VDPrivate =
18031         buildVarDecl(*this, ELoc, Type, D->getName(),
18032                      D->hasAttrs() ? &D->getAttrs() : nullptr,
18033                      VD ? cast<DeclRefExpr>(SimpleRefExpr) : nullptr);
18034     // Generate helper private variable and initialize it with the value of the
18035     // original variable. The address of the original variable is replaced by
18036     // the address of the new private variable in the CodeGen. This new variable
18037     // is not added to IdResolver, so the code in the OpenMP region uses
18038     // original variable for proper diagnostics and variable capturing.
18039     Expr *VDInitRefExpr = nullptr;
18040     // For arrays generate initializer for single element and replace it by the
18041     // original array element in CodeGen.
18042     if (Type->isArrayType()) {
18043       VarDecl *VDInit =
18044           buildVarDecl(*this, RefExpr->getExprLoc(), ElemType, D->getName());
18045       VDInitRefExpr = buildDeclRefExpr(*this, VDInit, ElemType, ELoc);
18046       Expr *Init = DefaultLvalueConversion(VDInitRefExpr).get();
18047       ElemType = ElemType.getUnqualifiedType();
18048       VarDecl *VDInitTemp = buildVarDecl(*this, RefExpr->getExprLoc(), ElemType,
18049                                          ".firstprivate.temp");
18050       InitializedEntity Entity =
18051           InitializedEntity::InitializeVariable(VDInitTemp);
18052       InitializationKind Kind = InitializationKind::CreateCopy(ELoc, ELoc);
18053 
18054       InitializationSequence InitSeq(*this, Entity, Kind, Init);
18055       ExprResult Result = InitSeq.Perform(*this, Entity, Kind, Init);
18056       if (Result.isInvalid())
18057         VDPrivate->setInvalidDecl();
18058       else
18059         VDPrivate->setInit(Result.getAs<Expr>());
18060       // Remove temp variable declaration.
18061       Context.Deallocate(VDInitTemp);
18062     } else {
18063       VarDecl *VDInit = buildVarDecl(*this, RefExpr->getExprLoc(), Type,
18064                                      ".firstprivate.temp");
18065       VDInitRefExpr = buildDeclRefExpr(*this, VDInit, RefExpr->getType(),
18066                                        RefExpr->getExprLoc());
18067       AddInitializerToDecl(VDPrivate,
18068                            DefaultLvalueConversion(VDInitRefExpr).get(),
18069                            /*DirectInit=*/false);
18070     }
18071     if (VDPrivate->isInvalidDecl()) {
18072       if (IsImplicitClause) {
18073         Diag(RefExpr->getExprLoc(),
18074              diag::note_omp_task_predetermined_firstprivate_here);
18075       }
18076       continue;
18077     }
18078     CurContext->addDecl(VDPrivate);
18079     DeclRefExpr *VDPrivateRefExpr = buildDeclRefExpr(
18080         *this, VDPrivate, RefExpr->getType().getUnqualifiedType(),
18081         RefExpr->getExprLoc());
18082     DeclRefExpr *Ref = nullptr;
18083     if (!VD && !CurContext->isDependentContext()) {
18084       if (TopDVar.CKind == OMPC_lastprivate) {
18085         Ref = TopDVar.PrivateCopy;
18086       } else {
18087         auto *FD = dyn_cast<FieldDecl>(D);
18088         VarDecl *VD = FD ? DSAStack->getImplicitFDCapExprDecl(FD) : nullptr;
18089         if (VD)
18090           Ref = buildDeclRefExpr(*this, VD, VD->getType().getNonReferenceType(),
18091                                  RefExpr->getExprLoc());
18092         else
18093           Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/true);
18094         if (VD || !isOpenMPCapturedDecl(D))
18095           ExprCaptures.push_back(Ref->getDecl());
18096       }
18097     }
18098     if (!IsImplicitClause)
18099       DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_firstprivate, Ref);
18100     Vars.push_back((VD || CurContext->isDependentContext())
18101                        ? RefExpr->IgnoreParens()
18102                        : Ref);
18103     PrivateCopies.push_back(VDPrivateRefExpr);
18104     Inits.push_back(VDInitRefExpr);
18105   }
18106 
18107   if (Vars.empty())
18108     return nullptr;
18109 
18110   return OMPFirstprivateClause::Create(Context, StartLoc, LParenLoc, EndLoc,
18111                                        Vars, PrivateCopies, Inits,
18112                                        buildPreInits(Context, ExprCaptures));
18113 }
18114 
18115 OMPClause *Sema::ActOnOpenMPLastprivateClause(
18116     ArrayRef<Expr *> VarList, OpenMPLastprivateModifier LPKind,
18117     SourceLocation LPKindLoc, SourceLocation ColonLoc, SourceLocation StartLoc,
18118     SourceLocation LParenLoc, SourceLocation EndLoc) {
18119   if (LPKind == OMPC_LASTPRIVATE_unknown && LPKindLoc.isValid()) {
18120     assert(ColonLoc.isValid() && "Colon location must be valid.");
18121     Diag(LPKindLoc, diag::err_omp_unexpected_clause_value)
18122         << getListOfPossibleValues(OMPC_lastprivate, /*First=*/0,
18123                                    /*Last=*/OMPC_LASTPRIVATE_unknown)
18124         << getOpenMPClauseName(OMPC_lastprivate);
18125     return nullptr;
18126   }
18127 
18128   SmallVector<Expr *, 8> Vars;
18129   SmallVector<Expr *, 8> SrcExprs;
18130   SmallVector<Expr *, 8> DstExprs;
18131   SmallVector<Expr *, 8> AssignmentOps;
18132   SmallVector<Decl *, 4> ExprCaptures;
18133   SmallVector<Expr *, 4> ExprPostUpdates;
18134   for (Expr *RefExpr : VarList) {
18135     assert(RefExpr && "NULL expr in OpenMP lastprivate clause.");
18136     SourceLocation ELoc;
18137     SourceRange ERange;
18138     Expr *SimpleRefExpr = RefExpr;
18139     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
18140     if (Res.second) {
18141       // It will be analyzed later.
18142       Vars.push_back(RefExpr);
18143       SrcExprs.push_back(nullptr);
18144       DstExprs.push_back(nullptr);
18145       AssignmentOps.push_back(nullptr);
18146     }
18147     ValueDecl *D = Res.first;
18148     if (!D)
18149       continue;
18150 
18151     QualType Type = D->getType();
18152     auto *VD = dyn_cast<VarDecl>(D);
18153 
18154     // OpenMP [2.14.3.5, Restrictions, C/C++, p.2]
18155     //  A variable that appears in a lastprivate clause must not have an
18156     //  incomplete type or a reference type.
18157     if (RequireCompleteType(ELoc, Type,
18158                             diag::err_omp_lastprivate_incomplete_type))
18159       continue;
18160     Type = Type.getNonReferenceType();
18161 
18162     // OpenMP 5.0 [2.19.3, List Item Privatization, Restrictions]
18163     // A variable that is privatized must not have a const-qualified type
18164     // unless it is of class type with a mutable member. This restriction does
18165     // not apply to the firstprivate clause.
18166     //
18167     // OpenMP 3.1 [2.9.3.5, lastprivate clause, Restrictions]
18168     // A variable that appears in a lastprivate clause must not have a
18169     // const-qualified type unless it is of class type with a mutable member.
18170     if (rejectConstNotMutableType(*this, D, Type, OMPC_lastprivate, ELoc))
18171       continue;
18172 
18173     // OpenMP 5.0 [2.19.4.5 lastprivate Clause, Restrictions]
18174     // A list item that appears in a lastprivate clause with the conditional
18175     // modifier must be a scalar variable.
18176     if (LPKind == OMPC_LASTPRIVATE_conditional && !Type->isScalarType()) {
18177       Diag(ELoc, diag::err_omp_lastprivate_conditional_non_scalar);
18178       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
18179                                VarDecl::DeclarationOnly;
18180       Diag(D->getLocation(),
18181            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
18182           << D;
18183       continue;
18184     }
18185 
18186     OpenMPDirectiveKind CurrDir = DSAStack->getCurrentDirective();
18187     // OpenMP [2.14.1.1, Data-sharing Attribute Rules for Variables Referenced
18188     // in a Construct]
18189     //  Variables with the predetermined data-sharing attributes may not be
18190     //  listed in data-sharing attributes clauses, except for the cases
18191     //  listed below.
18192     // OpenMP 4.5 [2.10.8, Distribute Construct, p.3]
18193     // A list item may appear in a firstprivate or lastprivate clause but not
18194     // both.
18195     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(D, /*FromParent=*/false);
18196     if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_lastprivate &&
18197         (isOpenMPDistributeDirective(CurrDir) ||
18198          DVar.CKind != OMPC_firstprivate) &&
18199         (DVar.CKind != OMPC_private || DVar.RefExpr != nullptr)) {
18200       Diag(ELoc, diag::err_omp_wrong_dsa)
18201           << getOpenMPClauseName(DVar.CKind)
18202           << getOpenMPClauseName(OMPC_lastprivate);
18203       reportOriginalDsa(*this, DSAStack, D, DVar);
18204       continue;
18205     }
18206 
18207     // OpenMP [2.14.3.5, Restrictions, p.2]
18208     // A list item that is private within a parallel region, or that appears in
18209     // the reduction clause of a parallel construct, must not appear in a
18210     // lastprivate clause on a worksharing construct if any of the corresponding
18211     // worksharing regions ever binds to any of the corresponding parallel
18212     // regions.
18213     DSAStackTy::DSAVarData TopDVar = DVar;
18214     if (isOpenMPWorksharingDirective(CurrDir) &&
18215         !isOpenMPParallelDirective(CurrDir) &&
18216         !isOpenMPTeamsDirective(CurrDir)) {
18217       DVar = DSAStack->getImplicitDSA(D, true);
18218       if (DVar.CKind != OMPC_shared) {
18219         Diag(ELoc, diag::err_omp_required_access)
18220             << getOpenMPClauseName(OMPC_lastprivate)
18221             << getOpenMPClauseName(OMPC_shared);
18222         reportOriginalDsa(*this, DSAStack, D, DVar);
18223         continue;
18224       }
18225     }
18226 
18227     // OpenMP [2.14.3.5, Restrictions, C++, p.1,2]
18228     //  A variable of class type (or array thereof) that appears in a
18229     //  lastprivate clause requires an accessible, unambiguous default
18230     //  constructor for the class type, unless the list item is also specified
18231     //  in a firstprivate clause.
18232     //  A variable of class type (or array thereof) that appears in a
18233     //  lastprivate clause requires an accessible, unambiguous copy assignment
18234     //  operator for the class type.
18235     Type = Context.getBaseElementType(Type).getNonReferenceType();
18236     VarDecl *SrcVD = buildVarDecl(*this, ERange.getBegin(),
18237                                   Type.getUnqualifiedType(), ".lastprivate.src",
18238                                   D->hasAttrs() ? &D->getAttrs() : nullptr);
18239     DeclRefExpr *PseudoSrcExpr =
18240         buildDeclRefExpr(*this, SrcVD, Type.getUnqualifiedType(), ELoc);
18241     VarDecl *DstVD =
18242         buildVarDecl(*this, ERange.getBegin(), Type, ".lastprivate.dst",
18243                      D->hasAttrs() ? &D->getAttrs() : nullptr);
18244     DeclRefExpr *PseudoDstExpr = buildDeclRefExpr(*this, DstVD, Type, ELoc);
18245     // For arrays generate assignment operation for single element and replace
18246     // it by the original array element in CodeGen.
18247     ExprResult AssignmentOp = BuildBinOp(/*S=*/nullptr, ELoc, BO_Assign,
18248                                          PseudoDstExpr, PseudoSrcExpr);
18249     if (AssignmentOp.isInvalid())
18250       continue;
18251     AssignmentOp =
18252         ActOnFinishFullExpr(AssignmentOp.get(), ELoc, /*DiscardedValue*/ false);
18253     if (AssignmentOp.isInvalid())
18254       continue;
18255 
18256     DeclRefExpr *Ref = nullptr;
18257     if (!VD && !CurContext->isDependentContext()) {
18258       if (TopDVar.CKind == OMPC_firstprivate) {
18259         Ref = TopDVar.PrivateCopy;
18260       } else {
18261         Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/false);
18262         if (!isOpenMPCapturedDecl(D))
18263           ExprCaptures.push_back(Ref->getDecl());
18264       }
18265       if ((TopDVar.CKind == OMPC_firstprivate && !TopDVar.PrivateCopy) ||
18266           (!isOpenMPCapturedDecl(D) &&
18267            Ref->getDecl()->hasAttr<OMPCaptureNoInitAttr>())) {
18268         ExprResult RefRes = DefaultLvalueConversion(Ref);
18269         if (!RefRes.isUsable())
18270           continue;
18271         ExprResult PostUpdateRes =
18272             BuildBinOp(DSAStack->getCurScope(), ELoc, BO_Assign, SimpleRefExpr,
18273                        RefRes.get());
18274         if (!PostUpdateRes.isUsable())
18275           continue;
18276         ExprPostUpdates.push_back(
18277             IgnoredValueConversions(PostUpdateRes.get()).get());
18278       }
18279     }
18280     DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_lastprivate, Ref);
18281     Vars.push_back((VD || CurContext->isDependentContext())
18282                        ? RefExpr->IgnoreParens()
18283                        : Ref);
18284     SrcExprs.push_back(PseudoSrcExpr);
18285     DstExprs.push_back(PseudoDstExpr);
18286     AssignmentOps.push_back(AssignmentOp.get());
18287   }
18288 
18289   if (Vars.empty())
18290     return nullptr;
18291 
18292   return OMPLastprivateClause::Create(Context, StartLoc, LParenLoc, EndLoc,
18293                                       Vars, SrcExprs, DstExprs, AssignmentOps,
18294                                       LPKind, LPKindLoc, ColonLoc,
18295                                       buildPreInits(Context, ExprCaptures),
18296                                       buildPostUpdate(*this, ExprPostUpdates));
18297 }
18298 
18299 OMPClause *Sema::ActOnOpenMPSharedClause(ArrayRef<Expr *> VarList,
18300                                          SourceLocation StartLoc,
18301                                          SourceLocation LParenLoc,
18302                                          SourceLocation EndLoc) {
18303   SmallVector<Expr *, 8> Vars;
18304   for (Expr *RefExpr : VarList) {
18305     assert(RefExpr && "NULL expr in OpenMP lastprivate clause.");
18306     SourceLocation ELoc;
18307     SourceRange ERange;
18308     Expr *SimpleRefExpr = RefExpr;
18309     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
18310     if (Res.second) {
18311       // It will be analyzed later.
18312       Vars.push_back(RefExpr);
18313     }
18314     ValueDecl *D = Res.first;
18315     if (!D)
18316       continue;
18317 
18318     auto *VD = dyn_cast<VarDecl>(D);
18319     // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced
18320     // in a Construct]
18321     //  Variables with the predetermined data-sharing attributes may not be
18322     //  listed in data-sharing attributes clauses, except for the cases
18323     //  listed below. For these exceptions only, listing a predetermined
18324     //  variable in a data-sharing attribute clause is allowed and overrides
18325     //  the variable's predetermined data-sharing attributes.
18326     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(D, /*FromParent=*/false);
18327     if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_shared &&
18328         DVar.RefExpr) {
18329       Diag(ELoc, diag::err_omp_wrong_dsa) << getOpenMPClauseName(DVar.CKind)
18330                                           << getOpenMPClauseName(OMPC_shared);
18331       reportOriginalDsa(*this, DSAStack, D, DVar);
18332       continue;
18333     }
18334 
18335     DeclRefExpr *Ref = nullptr;
18336     if (!VD && isOpenMPCapturedDecl(D) && !CurContext->isDependentContext())
18337       Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/true);
18338     DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_shared, Ref);
18339     Vars.push_back((VD || !Ref || CurContext->isDependentContext())
18340                        ? RefExpr->IgnoreParens()
18341                        : Ref);
18342   }
18343 
18344   if (Vars.empty())
18345     return nullptr;
18346 
18347   return OMPSharedClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars);
18348 }
18349 
18350 namespace {
18351 class DSARefChecker : public StmtVisitor<DSARefChecker, bool> {
18352   DSAStackTy *Stack;
18353 
18354 public:
18355   bool VisitDeclRefExpr(DeclRefExpr *E) {
18356     if (auto *VD = dyn_cast<VarDecl>(E->getDecl())) {
18357       DSAStackTy::DSAVarData DVar = Stack->getTopDSA(VD, /*FromParent=*/false);
18358       if (DVar.CKind == OMPC_shared && !DVar.RefExpr)
18359         return false;
18360       if (DVar.CKind != OMPC_unknown)
18361         return true;
18362       DSAStackTy::DSAVarData DVarPrivate = Stack->hasDSA(
18363           VD,
18364           [](OpenMPClauseKind C, bool AppliedToPointee, bool) {
18365             return isOpenMPPrivate(C) && !AppliedToPointee;
18366           },
18367           [](OpenMPDirectiveKind) { return true; },
18368           /*FromParent=*/true);
18369       return DVarPrivate.CKind != OMPC_unknown;
18370     }
18371     return false;
18372   }
18373   bool VisitStmt(Stmt *S) {
18374     for (Stmt *Child : S->children()) {
18375       if (Child && Visit(Child))
18376         return true;
18377     }
18378     return false;
18379   }
18380   explicit DSARefChecker(DSAStackTy *S) : Stack(S) {}
18381 };
18382 } // namespace
18383 
18384 namespace {
18385 // Transform MemberExpression for specified FieldDecl of current class to
18386 // DeclRefExpr to specified OMPCapturedExprDecl.
18387 class TransformExprToCaptures : public TreeTransform<TransformExprToCaptures> {
18388   typedef TreeTransform<TransformExprToCaptures> BaseTransform;
18389   ValueDecl *Field = nullptr;
18390   DeclRefExpr *CapturedExpr = nullptr;
18391 
18392 public:
18393   TransformExprToCaptures(Sema &SemaRef, ValueDecl *FieldDecl)
18394       : BaseTransform(SemaRef), Field(FieldDecl), CapturedExpr(nullptr) {}
18395 
18396   ExprResult TransformMemberExpr(MemberExpr *E) {
18397     if (isa<CXXThisExpr>(E->getBase()->IgnoreParenImpCasts()) &&
18398         E->getMemberDecl() == Field) {
18399       CapturedExpr = buildCapture(SemaRef, Field, E, /*WithInit=*/false);
18400       return CapturedExpr;
18401     }
18402     return BaseTransform::TransformMemberExpr(E);
18403   }
18404   DeclRefExpr *getCapturedExpr() { return CapturedExpr; }
18405 };
18406 } // namespace
18407 
18408 template <typename T, typename U>
18409 static T filterLookupForUDReductionAndMapper(
18410     SmallVectorImpl<U> &Lookups, const llvm::function_ref<T(ValueDecl *)> Gen) {
18411   for (U &Set : Lookups) {
18412     for (auto *D : Set) {
18413       if (T Res = Gen(cast<ValueDecl>(D)))
18414         return Res;
18415     }
18416   }
18417   return T();
18418 }
18419 
18420 static NamedDecl *findAcceptableDecl(Sema &SemaRef, NamedDecl *D) {
18421   assert(!LookupResult::isVisible(SemaRef, D) && "not in slow case");
18422 
18423   for (auto RD : D->redecls()) {
18424     // Don't bother with extra checks if we already know this one isn't visible.
18425     if (RD == D)
18426       continue;
18427 
18428     auto ND = cast<NamedDecl>(RD);
18429     if (LookupResult::isVisible(SemaRef, ND))
18430       return ND;
18431   }
18432 
18433   return nullptr;
18434 }
18435 
18436 static void
18437 argumentDependentLookup(Sema &SemaRef, const DeclarationNameInfo &Id,
18438                         SourceLocation Loc, QualType Ty,
18439                         SmallVectorImpl<UnresolvedSet<8>> &Lookups) {
18440   // Find all of the associated namespaces and classes based on the
18441   // arguments we have.
18442   Sema::AssociatedNamespaceSet AssociatedNamespaces;
18443   Sema::AssociatedClassSet AssociatedClasses;
18444   OpaqueValueExpr OVE(Loc, Ty, VK_LValue);
18445   SemaRef.FindAssociatedClassesAndNamespaces(Loc, &OVE, AssociatedNamespaces,
18446                                              AssociatedClasses);
18447 
18448   // C++ [basic.lookup.argdep]p3:
18449   //   Let X be the lookup set produced by unqualified lookup (3.4.1)
18450   //   and let Y be the lookup set produced by argument dependent
18451   //   lookup (defined as follows). If X contains [...] then Y is
18452   //   empty. Otherwise Y is the set of declarations found in the
18453   //   namespaces associated with the argument types as described
18454   //   below. The set of declarations found by the lookup of the name
18455   //   is the union of X and Y.
18456   //
18457   // Here, we compute Y and add its members to the overloaded
18458   // candidate set.
18459   for (auto *NS : AssociatedNamespaces) {
18460     //   When considering an associated namespace, the lookup is the
18461     //   same as the lookup performed when the associated namespace is
18462     //   used as a qualifier (3.4.3.2) except that:
18463     //
18464     //     -- Any using-directives in the associated namespace are
18465     //        ignored.
18466     //
18467     //     -- Any namespace-scope friend functions declared in
18468     //        associated classes are visible within their respective
18469     //        namespaces even if they are not visible during an ordinary
18470     //        lookup (11.4).
18471     DeclContext::lookup_result R = NS->lookup(Id.getName());
18472     for (auto *D : R) {
18473       auto *Underlying = D;
18474       if (auto *USD = dyn_cast<UsingShadowDecl>(D))
18475         Underlying = USD->getTargetDecl();
18476 
18477       if (!isa<OMPDeclareReductionDecl>(Underlying) &&
18478           !isa<OMPDeclareMapperDecl>(Underlying))
18479         continue;
18480 
18481       if (!SemaRef.isVisible(D)) {
18482         D = findAcceptableDecl(SemaRef, D);
18483         if (!D)
18484           continue;
18485         if (auto *USD = dyn_cast<UsingShadowDecl>(D))
18486           Underlying = USD->getTargetDecl();
18487       }
18488       Lookups.emplace_back();
18489       Lookups.back().addDecl(Underlying);
18490     }
18491   }
18492 }
18493 
18494 static ExprResult
18495 buildDeclareReductionRef(Sema &SemaRef, SourceLocation Loc, SourceRange Range,
18496                          Scope *S, CXXScopeSpec &ReductionIdScopeSpec,
18497                          const DeclarationNameInfo &ReductionId, QualType Ty,
18498                          CXXCastPath &BasePath, Expr *UnresolvedReduction) {
18499   if (ReductionIdScopeSpec.isInvalid())
18500     return ExprError();
18501   SmallVector<UnresolvedSet<8>, 4> Lookups;
18502   if (S) {
18503     LookupResult Lookup(SemaRef, ReductionId, Sema::LookupOMPReductionName);
18504     Lookup.suppressDiagnostics();
18505     while (S && SemaRef.LookupParsedName(Lookup, S, &ReductionIdScopeSpec)) {
18506       NamedDecl *D = Lookup.getRepresentativeDecl();
18507       do {
18508         S = S->getParent();
18509       } while (S && !S->isDeclScope(D));
18510       if (S)
18511         S = S->getParent();
18512       Lookups.emplace_back();
18513       Lookups.back().append(Lookup.begin(), Lookup.end());
18514       Lookup.clear();
18515     }
18516   } else if (auto *ULE =
18517                  cast_or_null<UnresolvedLookupExpr>(UnresolvedReduction)) {
18518     Lookups.push_back(UnresolvedSet<8>());
18519     Decl *PrevD = nullptr;
18520     for (NamedDecl *D : ULE->decls()) {
18521       if (D == PrevD)
18522         Lookups.push_back(UnresolvedSet<8>());
18523       else if (auto *DRD = dyn_cast<OMPDeclareReductionDecl>(D))
18524         Lookups.back().addDecl(DRD);
18525       PrevD = D;
18526     }
18527   }
18528   if (SemaRef.CurContext->isDependentContext() || Ty->isDependentType() ||
18529       Ty->isInstantiationDependentType() ||
18530       Ty->containsUnexpandedParameterPack() ||
18531       filterLookupForUDReductionAndMapper<bool>(Lookups, [](ValueDecl *D) {
18532         return !D->isInvalidDecl() &&
18533                (D->getType()->isDependentType() ||
18534                 D->getType()->isInstantiationDependentType() ||
18535                 D->getType()->containsUnexpandedParameterPack());
18536       })) {
18537     UnresolvedSet<8> ResSet;
18538     for (const UnresolvedSet<8> &Set : Lookups) {
18539       if (Set.empty())
18540         continue;
18541       ResSet.append(Set.begin(), Set.end());
18542       // The last item marks the end of all declarations at the specified scope.
18543       ResSet.addDecl(Set[Set.size() - 1]);
18544     }
18545     return UnresolvedLookupExpr::Create(
18546         SemaRef.Context, /*NamingClass=*/nullptr,
18547         ReductionIdScopeSpec.getWithLocInContext(SemaRef.Context), ReductionId,
18548         /*ADL=*/true, /*Overloaded=*/true, ResSet.begin(), ResSet.end());
18549   }
18550   // Lookup inside the classes.
18551   // C++ [over.match.oper]p3:
18552   //   For a unary operator @ with an operand of a type whose
18553   //   cv-unqualified version is T1, and for a binary operator @ with
18554   //   a left operand of a type whose cv-unqualified version is T1 and
18555   //   a right operand of a type whose cv-unqualified version is T2,
18556   //   three sets of candidate functions, designated member
18557   //   candidates, non-member candidates and built-in candidates, are
18558   //   constructed as follows:
18559   //     -- If T1 is a complete class type or a class currently being
18560   //        defined, the set of member candidates is the result of the
18561   //        qualified lookup of T1::operator@ (13.3.1.1.1); otherwise,
18562   //        the set of member candidates is empty.
18563   LookupResult Lookup(SemaRef, ReductionId, Sema::LookupOMPReductionName);
18564   Lookup.suppressDiagnostics();
18565   if (const auto *TyRec = Ty->getAs<RecordType>()) {
18566     // Complete the type if it can be completed.
18567     // If the type is neither complete nor being defined, bail out now.
18568     if (SemaRef.isCompleteType(Loc, Ty) || TyRec->isBeingDefined() ||
18569         TyRec->getDecl()->getDefinition()) {
18570       Lookup.clear();
18571       SemaRef.LookupQualifiedName(Lookup, TyRec->getDecl());
18572       if (Lookup.empty()) {
18573         Lookups.emplace_back();
18574         Lookups.back().append(Lookup.begin(), Lookup.end());
18575       }
18576     }
18577   }
18578   // Perform ADL.
18579   if (SemaRef.getLangOpts().CPlusPlus)
18580     argumentDependentLookup(SemaRef, ReductionId, Loc, Ty, Lookups);
18581   if (auto *VD = filterLookupForUDReductionAndMapper<ValueDecl *>(
18582           Lookups, [&SemaRef, Ty](ValueDecl *D) -> ValueDecl * {
18583             if (!D->isInvalidDecl() &&
18584                 SemaRef.Context.hasSameType(D->getType(), Ty))
18585               return D;
18586             return nullptr;
18587           }))
18588     return SemaRef.BuildDeclRefExpr(VD, VD->getType().getNonReferenceType(),
18589                                     VK_LValue, Loc);
18590   if (SemaRef.getLangOpts().CPlusPlus) {
18591     if (auto *VD = filterLookupForUDReductionAndMapper<ValueDecl *>(
18592             Lookups, [&SemaRef, Ty, Loc](ValueDecl *D) -> ValueDecl * {
18593               if (!D->isInvalidDecl() &&
18594                   SemaRef.IsDerivedFrom(Loc, Ty, D->getType()) &&
18595                   !Ty.isMoreQualifiedThan(D->getType()))
18596                 return D;
18597               return nullptr;
18598             })) {
18599       CXXBasePaths Paths(/*FindAmbiguities=*/true, /*RecordPaths=*/true,
18600                          /*DetectVirtual=*/false);
18601       if (SemaRef.IsDerivedFrom(Loc, Ty, VD->getType(), Paths)) {
18602         if (!Paths.isAmbiguous(SemaRef.Context.getCanonicalType(
18603                 VD->getType().getUnqualifiedType()))) {
18604           if (SemaRef.CheckBaseClassAccess(
18605                   Loc, VD->getType(), Ty, Paths.front(),
18606                   /*DiagID=*/0) != Sema::AR_inaccessible) {
18607             SemaRef.BuildBasePathArray(Paths, BasePath);
18608             return SemaRef.BuildDeclRefExpr(
18609                 VD, VD->getType().getNonReferenceType(), VK_LValue, Loc);
18610           }
18611         }
18612       }
18613     }
18614   }
18615   if (ReductionIdScopeSpec.isSet()) {
18616     SemaRef.Diag(Loc, diag::err_omp_not_resolved_reduction_identifier)
18617         << Ty << Range;
18618     return ExprError();
18619   }
18620   return ExprEmpty();
18621 }
18622 
18623 namespace {
18624 /// Data for the reduction-based clauses.
18625 struct ReductionData {
18626   /// List of original reduction items.
18627   SmallVector<Expr *, 8> Vars;
18628   /// List of private copies of the reduction items.
18629   SmallVector<Expr *, 8> Privates;
18630   /// LHS expressions for the reduction_op expressions.
18631   SmallVector<Expr *, 8> LHSs;
18632   /// RHS expressions for the reduction_op expressions.
18633   SmallVector<Expr *, 8> RHSs;
18634   /// Reduction operation expression.
18635   SmallVector<Expr *, 8> ReductionOps;
18636   /// inscan copy operation expressions.
18637   SmallVector<Expr *, 8> InscanCopyOps;
18638   /// inscan copy temp array expressions for prefix sums.
18639   SmallVector<Expr *, 8> InscanCopyArrayTemps;
18640   /// inscan copy temp array element expressions for prefix sums.
18641   SmallVector<Expr *, 8> InscanCopyArrayElems;
18642   /// Taskgroup descriptors for the corresponding reduction items in
18643   /// in_reduction clauses.
18644   SmallVector<Expr *, 8> TaskgroupDescriptors;
18645   /// List of captures for clause.
18646   SmallVector<Decl *, 4> ExprCaptures;
18647   /// List of postupdate expressions.
18648   SmallVector<Expr *, 4> ExprPostUpdates;
18649   /// Reduction modifier.
18650   unsigned RedModifier = 0;
18651   ReductionData() = delete;
18652   /// Reserves required memory for the reduction data.
18653   ReductionData(unsigned Size, unsigned Modifier = 0) : RedModifier(Modifier) {
18654     Vars.reserve(Size);
18655     Privates.reserve(Size);
18656     LHSs.reserve(Size);
18657     RHSs.reserve(Size);
18658     ReductionOps.reserve(Size);
18659     if (RedModifier == OMPC_REDUCTION_inscan) {
18660       InscanCopyOps.reserve(Size);
18661       InscanCopyArrayTemps.reserve(Size);
18662       InscanCopyArrayElems.reserve(Size);
18663     }
18664     TaskgroupDescriptors.reserve(Size);
18665     ExprCaptures.reserve(Size);
18666     ExprPostUpdates.reserve(Size);
18667   }
18668   /// Stores reduction item and reduction operation only (required for dependent
18669   /// reduction item).
18670   void push(Expr *Item, Expr *ReductionOp) {
18671     Vars.emplace_back(Item);
18672     Privates.emplace_back(nullptr);
18673     LHSs.emplace_back(nullptr);
18674     RHSs.emplace_back(nullptr);
18675     ReductionOps.emplace_back(ReductionOp);
18676     TaskgroupDescriptors.emplace_back(nullptr);
18677     if (RedModifier == OMPC_REDUCTION_inscan) {
18678       InscanCopyOps.push_back(nullptr);
18679       InscanCopyArrayTemps.push_back(nullptr);
18680       InscanCopyArrayElems.push_back(nullptr);
18681     }
18682   }
18683   /// Stores reduction data.
18684   void push(Expr *Item, Expr *Private, Expr *LHS, Expr *RHS, Expr *ReductionOp,
18685             Expr *TaskgroupDescriptor, Expr *CopyOp, Expr *CopyArrayTemp,
18686             Expr *CopyArrayElem) {
18687     Vars.emplace_back(Item);
18688     Privates.emplace_back(Private);
18689     LHSs.emplace_back(LHS);
18690     RHSs.emplace_back(RHS);
18691     ReductionOps.emplace_back(ReductionOp);
18692     TaskgroupDescriptors.emplace_back(TaskgroupDescriptor);
18693     if (RedModifier == OMPC_REDUCTION_inscan) {
18694       InscanCopyOps.push_back(CopyOp);
18695       InscanCopyArrayTemps.push_back(CopyArrayTemp);
18696       InscanCopyArrayElems.push_back(CopyArrayElem);
18697     } else {
18698       assert(CopyOp == nullptr && CopyArrayTemp == nullptr &&
18699              CopyArrayElem == nullptr &&
18700              "Copy operation must be used for inscan reductions only.");
18701     }
18702   }
18703 };
18704 } // namespace
18705 
18706 static bool checkOMPArraySectionConstantForReduction(
18707     ASTContext &Context, const OMPArraySectionExpr *OASE, bool &SingleElement,
18708     SmallVectorImpl<llvm::APSInt> &ArraySizes) {
18709   const Expr *Length = OASE->getLength();
18710   if (Length == nullptr) {
18711     // For array sections of the form [1:] or [:], we would need to analyze
18712     // the lower bound...
18713     if (OASE->getColonLocFirst().isValid())
18714       return false;
18715 
18716     // This is an array subscript which has implicit length 1!
18717     SingleElement = true;
18718     ArraySizes.push_back(llvm::APSInt::get(1));
18719   } else {
18720     Expr::EvalResult Result;
18721     if (!Length->EvaluateAsInt(Result, Context))
18722       return false;
18723 
18724     llvm::APSInt ConstantLengthValue = Result.Val.getInt();
18725     SingleElement = (ConstantLengthValue.getSExtValue() == 1);
18726     ArraySizes.push_back(ConstantLengthValue);
18727   }
18728 
18729   // Get the base of this array section and walk up from there.
18730   const Expr *Base = OASE->getBase()->IgnoreParenImpCasts();
18731 
18732   // We require length = 1 for all array sections except the right-most to
18733   // guarantee that the memory region is contiguous and has no holes in it.
18734   while (const auto *TempOASE = dyn_cast<OMPArraySectionExpr>(Base)) {
18735     Length = TempOASE->getLength();
18736     if (Length == nullptr) {
18737       // For array sections of the form [1:] or [:], we would need to analyze
18738       // the lower bound...
18739       if (OASE->getColonLocFirst().isValid())
18740         return false;
18741 
18742       // This is an array subscript which has implicit length 1!
18743       ArraySizes.push_back(llvm::APSInt::get(1));
18744     } else {
18745       Expr::EvalResult Result;
18746       if (!Length->EvaluateAsInt(Result, Context))
18747         return false;
18748 
18749       llvm::APSInt ConstantLengthValue = Result.Val.getInt();
18750       if (ConstantLengthValue.getSExtValue() != 1)
18751         return false;
18752 
18753       ArraySizes.push_back(ConstantLengthValue);
18754     }
18755     Base = TempOASE->getBase()->IgnoreParenImpCasts();
18756   }
18757 
18758   // If we have a single element, we don't need to add the implicit lengths.
18759   if (!SingleElement) {
18760     while (const auto *TempASE = dyn_cast<ArraySubscriptExpr>(Base)) {
18761       // Has implicit length 1!
18762       ArraySizes.push_back(llvm::APSInt::get(1));
18763       Base = TempASE->getBase()->IgnoreParenImpCasts();
18764     }
18765   }
18766 
18767   // This array section can be privatized as a single value or as a constant
18768   // sized array.
18769   return true;
18770 }
18771 
18772 static BinaryOperatorKind
18773 getRelatedCompoundReductionOp(BinaryOperatorKind BOK) {
18774   if (BOK == BO_Add)
18775     return BO_AddAssign;
18776   if (BOK == BO_Mul)
18777     return BO_MulAssign;
18778   if (BOK == BO_And)
18779     return BO_AndAssign;
18780   if (BOK == BO_Or)
18781     return BO_OrAssign;
18782   if (BOK == BO_Xor)
18783     return BO_XorAssign;
18784   return BOK;
18785 }
18786 
18787 static bool actOnOMPReductionKindClause(
18788     Sema &S, DSAStackTy *Stack, OpenMPClauseKind ClauseKind,
18789     ArrayRef<Expr *> VarList, SourceLocation StartLoc, SourceLocation LParenLoc,
18790     SourceLocation ColonLoc, SourceLocation EndLoc,
18791     CXXScopeSpec &ReductionIdScopeSpec, const DeclarationNameInfo &ReductionId,
18792     ArrayRef<Expr *> UnresolvedReductions, ReductionData &RD) {
18793   DeclarationName DN = ReductionId.getName();
18794   OverloadedOperatorKind OOK = DN.getCXXOverloadedOperator();
18795   BinaryOperatorKind BOK = BO_Comma;
18796 
18797   ASTContext &Context = S.Context;
18798   // OpenMP [2.14.3.6, reduction clause]
18799   // C
18800   // reduction-identifier is either an identifier or one of the following
18801   // operators: +, -, *,  &, |, ^, && and ||
18802   // C++
18803   // reduction-identifier is either an id-expression or one of the following
18804   // operators: +, -, *, &, |, ^, && and ||
18805   switch (OOK) {
18806   case OO_Plus:
18807   case OO_Minus:
18808     BOK = BO_Add;
18809     break;
18810   case OO_Star:
18811     BOK = BO_Mul;
18812     break;
18813   case OO_Amp:
18814     BOK = BO_And;
18815     break;
18816   case OO_Pipe:
18817     BOK = BO_Or;
18818     break;
18819   case OO_Caret:
18820     BOK = BO_Xor;
18821     break;
18822   case OO_AmpAmp:
18823     BOK = BO_LAnd;
18824     break;
18825   case OO_PipePipe:
18826     BOK = BO_LOr;
18827     break;
18828   case OO_New:
18829   case OO_Delete:
18830   case OO_Array_New:
18831   case OO_Array_Delete:
18832   case OO_Slash:
18833   case OO_Percent:
18834   case OO_Tilde:
18835   case OO_Exclaim:
18836   case OO_Equal:
18837   case OO_Less:
18838   case OO_Greater:
18839   case OO_LessEqual:
18840   case OO_GreaterEqual:
18841   case OO_PlusEqual:
18842   case OO_MinusEqual:
18843   case OO_StarEqual:
18844   case OO_SlashEqual:
18845   case OO_PercentEqual:
18846   case OO_CaretEqual:
18847   case OO_AmpEqual:
18848   case OO_PipeEqual:
18849   case OO_LessLess:
18850   case OO_GreaterGreater:
18851   case OO_LessLessEqual:
18852   case OO_GreaterGreaterEqual:
18853   case OO_EqualEqual:
18854   case OO_ExclaimEqual:
18855   case OO_Spaceship:
18856   case OO_PlusPlus:
18857   case OO_MinusMinus:
18858   case OO_Comma:
18859   case OO_ArrowStar:
18860   case OO_Arrow:
18861   case OO_Call:
18862   case OO_Subscript:
18863   case OO_Conditional:
18864   case OO_Coawait:
18865   case NUM_OVERLOADED_OPERATORS:
18866     llvm_unreachable("Unexpected reduction identifier");
18867   case OO_None:
18868     if (IdentifierInfo *II = DN.getAsIdentifierInfo()) {
18869       if (II->isStr("max"))
18870         BOK = BO_GT;
18871       else if (II->isStr("min"))
18872         BOK = BO_LT;
18873     }
18874     break;
18875   }
18876   SourceRange ReductionIdRange;
18877   if (ReductionIdScopeSpec.isValid())
18878     ReductionIdRange.setBegin(ReductionIdScopeSpec.getBeginLoc());
18879   else
18880     ReductionIdRange.setBegin(ReductionId.getBeginLoc());
18881   ReductionIdRange.setEnd(ReductionId.getEndLoc());
18882 
18883   auto IR = UnresolvedReductions.begin(), ER = UnresolvedReductions.end();
18884   bool FirstIter = true;
18885   for (Expr *RefExpr : VarList) {
18886     assert(RefExpr && "nullptr expr in OpenMP reduction clause.");
18887     // OpenMP [2.1, C/C++]
18888     //  A list item is a variable or array section, subject to the restrictions
18889     //  specified in Section 2.4 on page 42 and in each of the sections
18890     // describing clauses and directives for which a list appears.
18891     // OpenMP  [2.14.3.3, Restrictions, p.1]
18892     //  A variable that is part of another variable (as an array or
18893     //  structure element) cannot appear in a private clause.
18894     if (!FirstIter && IR != ER)
18895       ++IR;
18896     FirstIter = false;
18897     SourceLocation ELoc;
18898     SourceRange ERange;
18899     Expr *SimpleRefExpr = RefExpr;
18900     auto Res = getPrivateItem(S, SimpleRefExpr, ELoc, ERange,
18901                               /*AllowArraySection=*/true);
18902     if (Res.second) {
18903       // Try to find 'declare reduction' corresponding construct before using
18904       // builtin/overloaded operators.
18905       QualType Type = Context.DependentTy;
18906       CXXCastPath BasePath;
18907       ExprResult DeclareReductionRef = buildDeclareReductionRef(
18908           S, ELoc, ERange, Stack->getCurScope(), ReductionIdScopeSpec,
18909           ReductionId, Type, BasePath, IR == ER ? nullptr : *IR);
18910       Expr *ReductionOp = nullptr;
18911       if (S.CurContext->isDependentContext() &&
18912           (DeclareReductionRef.isUnset() ||
18913            isa<UnresolvedLookupExpr>(DeclareReductionRef.get())))
18914         ReductionOp = DeclareReductionRef.get();
18915       // It will be analyzed later.
18916       RD.push(RefExpr, ReductionOp);
18917     }
18918     ValueDecl *D = Res.first;
18919     if (!D)
18920       continue;
18921 
18922     Expr *TaskgroupDescriptor = nullptr;
18923     QualType Type;
18924     auto *ASE = dyn_cast<ArraySubscriptExpr>(RefExpr->IgnoreParens());
18925     auto *OASE = dyn_cast<OMPArraySectionExpr>(RefExpr->IgnoreParens());
18926     if (ASE) {
18927       Type = ASE->getType().getNonReferenceType();
18928     } else if (OASE) {
18929       QualType BaseType =
18930           OMPArraySectionExpr::getBaseOriginalType(OASE->getBase());
18931       if (const auto *ATy = BaseType->getAsArrayTypeUnsafe())
18932         Type = ATy->getElementType();
18933       else
18934         Type = BaseType->getPointeeType();
18935       Type = Type.getNonReferenceType();
18936     } else {
18937       Type = Context.getBaseElementType(D->getType().getNonReferenceType());
18938     }
18939     auto *VD = dyn_cast<VarDecl>(D);
18940 
18941     // OpenMP [2.9.3.3, Restrictions, C/C++, p.3]
18942     //  A variable that appears in a private clause must not have an incomplete
18943     //  type or a reference type.
18944     if (S.RequireCompleteType(ELoc, D->getType(),
18945                               diag::err_omp_reduction_incomplete_type))
18946       continue;
18947     // OpenMP [2.14.3.6, reduction clause, Restrictions]
18948     // A list item that appears in a reduction clause must not be
18949     // const-qualified.
18950     if (rejectConstNotMutableType(S, D, Type, ClauseKind, ELoc,
18951                                   /*AcceptIfMutable*/ false, ASE || OASE))
18952       continue;
18953 
18954     OpenMPDirectiveKind CurrDir = Stack->getCurrentDirective();
18955     // OpenMP [2.9.3.6, Restrictions, C/C++, p.4]
18956     //  If a list-item is a reference type then it must bind to the same object
18957     //  for all threads of the team.
18958     if (!ASE && !OASE) {
18959       if (VD) {
18960         VarDecl *VDDef = VD->getDefinition();
18961         if (VD->getType()->isReferenceType() && VDDef && VDDef->hasInit()) {
18962           DSARefChecker Check(Stack);
18963           if (Check.Visit(VDDef->getInit())) {
18964             S.Diag(ELoc, diag::err_omp_reduction_ref_type_arg)
18965                 << getOpenMPClauseName(ClauseKind) << ERange;
18966             S.Diag(VDDef->getLocation(), diag::note_defined_here) << VDDef;
18967             continue;
18968           }
18969         }
18970       }
18971 
18972       // OpenMP [2.14.1.1, Data-sharing Attribute Rules for Variables Referenced
18973       // in a Construct]
18974       //  Variables with the predetermined data-sharing attributes may not be
18975       //  listed in data-sharing attributes clauses, except for the cases
18976       //  listed below. For these exceptions only, listing a predetermined
18977       //  variable in a data-sharing attribute clause is allowed and overrides
18978       //  the variable's predetermined data-sharing attributes.
18979       // OpenMP [2.14.3.6, Restrictions, p.3]
18980       //  Any number of reduction clauses can be specified on the directive,
18981       //  but a list item can appear only once in the reduction clauses for that
18982       //  directive.
18983       DSAStackTy::DSAVarData DVar = Stack->getTopDSA(D, /*FromParent=*/false);
18984       if (DVar.CKind == OMPC_reduction) {
18985         S.Diag(ELoc, diag::err_omp_once_referenced)
18986             << getOpenMPClauseName(ClauseKind);
18987         if (DVar.RefExpr)
18988           S.Diag(DVar.RefExpr->getExprLoc(), diag::note_omp_referenced);
18989         continue;
18990       }
18991       if (DVar.CKind != OMPC_unknown) {
18992         S.Diag(ELoc, diag::err_omp_wrong_dsa)
18993             << getOpenMPClauseName(DVar.CKind)
18994             << getOpenMPClauseName(OMPC_reduction);
18995         reportOriginalDsa(S, Stack, D, DVar);
18996         continue;
18997       }
18998 
18999       // OpenMP [2.14.3.6, Restrictions, p.1]
19000       //  A list item that appears in a reduction clause of a worksharing
19001       //  construct must be shared in the parallel regions to which any of the
19002       //  worksharing regions arising from the worksharing construct bind.
19003       if (isOpenMPWorksharingDirective(CurrDir) &&
19004           !isOpenMPParallelDirective(CurrDir) &&
19005           !isOpenMPTeamsDirective(CurrDir)) {
19006         DVar = Stack->getImplicitDSA(D, true);
19007         if (DVar.CKind != OMPC_shared) {
19008           S.Diag(ELoc, diag::err_omp_required_access)
19009               << getOpenMPClauseName(OMPC_reduction)
19010               << getOpenMPClauseName(OMPC_shared);
19011           reportOriginalDsa(S, Stack, D, DVar);
19012           continue;
19013         }
19014       }
19015     } else {
19016       // Threadprivates cannot be shared between threads, so dignose if the base
19017       // is a threadprivate variable.
19018       DSAStackTy::DSAVarData DVar = Stack->getTopDSA(D, /*FromParent=*/false);
19019       if (DVar.CKind == OMPC_threadprivate) {
19020         S.Diag(ELoc, diag::err_omp_wrong_dsa)
19021             << getOpenMPClauseName(DVar.CKind)
19022             << getOpenMPClauseName(OMPC_reduction);
19023         reportOriginalDsa(S, Stack, D, DVar);
19024         continue;
19025       }
19026     }
19027 
19028     // Try to find 'declare reduction' corresponding construct before using
19029     // builtin/overloaded operators.
19030     CXXCastPath BasePath;
19031     ExprResult DeclareReductionRef = buildDeclareReductionRef(
19032         S, ELoc, ERange, Stack->getCurScope(), ReductionIdScopeSpec,
19033         ReductionId, Type, BasePath, IR == ER ? nullptr : *IR);
19034     if (DeclareReductionRef.isInvalid())
19035       continue;
19036     if (S.CurContext->isDependentContext() &&
19037         (DeclareReductionRef.isUnset() ||
19038          isa<UnresolvedLookupExpr>(DeclareReductionRef.get()))) {
19039       RD.push(RefExpr, DeclareReductionRef.get());
19040       continue;
19041     }
19042     if (BOK == BO_Comma && DeclareReductionRef.isUnset()) {
19043       // Not allowed reduction identifier is found.
19044       S.Diag(ReductionId.getBeginLoc(),
19045              diag::err_omp_unknown_reduction_identifier)
19046           << Type << ReductionIdRange;
19047       continue;
19048     }
19049 
19050     // OpenMP [2.14.3.6, reduction clause, Restrictions]
19051     // The type of a list item that appears in a reduction clause must be valid
19052     // for the reduction-identifier. For a max or min reduction in C, the type
19053     // of the list item must be an allowed arithmetic data type: char, int,
19054     // float, double, or _Bool, possibly modified with long, short, signed, or
19055     // unsigned. For a max or min reduction in C++, the type of the list item
19056     // must be an allowed arithmetic data type: char, wchar_t, int, float,
19057     // double, or bool, possibly modified with long, short, signed, or unsigned.
19058     if (DeclareReductionRef.isUnset()) {
19059       if ((BOK == BO_GT || BOK == BO_LT) &&
19060           !(Type->isScalarType() ||
19061             (S.getLangOpts().CPlusPlus && Type->isArithmeticType()))) {
19062         S.Diag(ELoc, diag::err_omp_clause_not_arithmetic_type_arg)
19063             << getOpenMPClauseName(ClauseKind) << S.getLangOpts().CPlusPlus;
19064         if (!ASE && !OASE) {
19065           bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
19066                                    VarDecl::DeclarationOnly;
19067           S.Diag(D->getLocation(),
19068                  IsDecl ? diag::note_previous_decl : diag::note_defined_here)
19069               << D;
19070         }
19071         continue;
19072       }
19073       if ((BOK == BO_OrAssign || BOK == BO_AndAssign || BOK == BO_XorAssign) &&
19074           !S.getLangOpts().CPlusPlus && Type->isFloatingType()) {
19075         S.Diag(ELoc, diag::err_omp_clause_floating_type_arg)
19076             << getOpenMPClauseName(ClauseKind);
19077         if (!ASE && !OASE) {
19078           bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
19079                                    VarDecl::DeclarationOnly;
19080           S.Diag(D->getLocation(),
19081                  IsDecl ? diag::note_previous_decl : diag::note_defined_here)
19082               << D;
19083         }
19084         continue;
19085       }
19086     }
19087 
19088     Type = Type.getNonLValueExprType(Context).getUnqualifiedType();
19089     VarDecl *LHSVD = buildVarDecl(S, ELoc, Type, ".reduction.lhs",
19090                                   D->hasAttrs() ? &D->getAttrs() : nullptr);
19091     VarDecl *RHSVD = buildVarDecl(S, ELoc, Type, D->getName(),
19092                                   D->hasAttrs() ? &D->getAttrs() : nullptr);
19093     QualType PrivateTy = Type;
19094 
19095     // Try if we can determine constant lengths for all array sections and avoid
19096     // the VLA.
19097     bool ConstantLengthOASE = false;
19098     if (OASE) {
19099       bool SingleElement;
19100       llvm::SmallVector<llvm::APSInt, 4> ArraySizes;
19101       ConstantLengthOASE = checkOMPArraySectionConstantForReduction(
19102           Context, OASE, SingleElement, ArraySizes);
19103 
19104       // If we don't have a single element, we must emit a constant array type.
19105       if (ConstantLengthOASE && !SingleElement) {
19106         for (llvm::APSInt &Size : ArraySizes)
19107           PrivateTy = Context.getConstantArrayType(PrivateTy, Size, nullptr,
19108                                                    ArrayType::Normal,
19109                                                    /*IndexTypeQuals=*/0);
19110       }
19111     }
19112 
19113     if ((OASE && !ConstantLengthOASE) ||
19114         (!OASE && !ASE &&
19115          D->getType().getNonReferenceType()->isVariablyModifiedType())) {
19116       if (!Context.getTargetInfo().isVLASupported()) {
19117         if (isOpenMPTargetExecutionDirective(Stack->getCurrentDirective())) {
19118           S.Diag(ELoc, diag::err_omp_reduction_vla_unsupported) << !!OASE;
19119           S.Diag(ELoc, diag::note_vla_unsupported);
19120           continue;
19121         } else {
19122           S.targetDiag(ELoc, diag::err_omp_reduction_vla_unsupported) << !!OASE;
19123           S.targetDiag(ELoc, diag::note_vla_unsupported);
19124         }
19125       }
19126       // For arrays/array sections only:
19127       // Create pseudo array type for private copy. The size for this array will
19128       // be generated during codegen.
19129       // For array subscripts or single variables Private Ty is the same as Type
19130       // (type of the variable or single array element).
19131       PrivateTy = Context.getVariableArrayType(
19132           Type,
19133           new (Context)
19134               OpaqueValueExpr(ELoc, Context.getSizeType(), VK_PRValue),
19135           ArrayType::Normal, /*IndexTypeQuals=*/0, SourceRange());
19136     } else if (!ASE && !OASE &&
19137                Context.getAsArrayType(D->getType().getNonReferenceType())) {
19138       PrivateTy = D->getType().getNonReferenceType();
19139     }
19140     // Private copy.
19141     VarDecl *PrivateVD =
19142         buildVarDecl(S, ELoc, PrivateTy, D->getName(),
19143                      D->hasAttrs() ? &D->getAttrs() : nullptr,
19144                      VD ? cast<DeclRefExpr>(SimpleRefExpr) : nullptr);
19145     // Add initializer for private variable.
19146     Expr *Init = nullptr;
19147     DeclRefExpr *LHSDRE = buildDeclRefExpr(S, LHSVD, Type, ELoc);
19148     DeclRefExpr *RHSDRE = buildDeclRefExpr(S, RHSVD, Type, ELoc);
19149     if (DeclareReductionRef.isUsable()) {
19150       auto *DRDRef = DeclareReductionRef.getAs<DeclRefExpr>();
19151       auto *DRD = cast<OMPDeclareReductionDecl>(DRDRef->getDecl());
19152       if (DRD->getInitializer()) {
19153         Init = DRDRef;
19154         RHSVD->setInit(DRDRef);
19155         RHSVD->setInitStyle(VarDecl::CallInit);
19156       }
19157     } else {
19158       switch (BOK) {
19159       case BO_Add:
19160       case BO_Xor:
19161       case BO_Or:
19162       case BO_LOr:
19163         // '+', '-', '^', '|', '||' reduction ops - initializer is '0'.
19164         if (Type->isScalarType() || Type->isAnyComplexType())
19165           Init = S.ActOnIntegerConstant(ELoc, /*Val=*/0).get();
19166         break;
19167       case BO_Mul:
19168       case BO_LAnd:
19169         if (Type->isScalarType() || Type->isAnyComplexType()) {
19170           // '*' and '&&' reduction ops - initializer is '1'.
19171           Init = S.ActOnIntegerConstant(ELoc, /*Val=*/1).get();
19172         }
19173         break;
19174       case BO_And: {
19175         // '&' reduction op - initializer is '~0'.
19176         QualType OrigType = Type;
19177         if (auto *ComplexTy = OrigType->getAs<ComplexType>())
19178           Type = ComplexTy->getElementType();
19179         if (Type->isRealFloatingType()) {
19180           llvm::APFloat InitValue = llvm::APFloat::getAllOnesValue(
19181               Context.getFloatTypeSemantics(Type));
19182           Init = FloatingLiteral::Create(Context, InitValue, /*isexact=*/true,
19183                                          Type, ELoc);
19184         } else if (Type->isScalarType()) {
19185           uint64_t Size = Context.getTypeSize(Type);
19186           QualType IntTy = Context.getIntTypeForBitwidth(Size, /*Signed=*/0);
19187           llvm::APInt InitValue = llvm::APInt::getAllOnes(Size);
19188           Init = IntegerLiteral::Create(Context, InitValue, IntTy, ELoc);
19189         }
19190         if (Init && OrigType->isAnyComplexType()) {
19191           // Init = 0xFFFF + 0xFFFFi;
19192           auto *Im = new (Context) ImaginaryLiteral(Init, OrigType);
19193           Init = S.CreateBuiltinBinOp(ELoc, BO_Add, Init, Im).get();
19194         }
19195         Type = OrigType;
19196         break;
19197       }
19198       case BO_LT:
19199       case BO_GT: {
19200         // 'min' reduction op - initializer is 'Largest representable number in
19201         // the reduction list item type'.
19202         // 'max' reduction op - initializer is 'Least representable number in
19203         // the reduction list item type'.
19204         if (Type->isIntegerType() || Type->isPointerType()) {
19205           bool IsSigned = Type->hasSignedIntegerRepresentation();
19206           uint64_t Size = Context.getTypeSize(Type);
19207           QualType IntTy =
19208               Context.getIntTypeForBitwidth(Size, /*Signed=*/IsSigned);
19209           llvm::APInt InitValue =
19210               (BOK != BO_LT) ? IsSigned ? llvm::APInt::getSignedMinValue(Size)
19211                                         : llvm::APInt::getMinValue(Size)
19212               : IsSigned ? llvm::APInt::getSignedMaxValue(Size)
19213                              : llvm::APInt::getMaxValue(Size);
19214           Init = IntegerLiteral::Create(Context, InitValue, IntTy, ELoc);
19215           if (Type->isPointerType()) {
19216             // Cast to pointer type.
19217             ExprResult CastExpr = S.BuildCStyleCastExpr(
19218                 ELoc, Context.getTrivialTypeSourceInfo(Type, ELoc), ELoc, Init);
19219             if (CastExpr.isInvalid())
19220               continue;
19221             Init = CastExpr.get();
19222           }
19223         } else if (Type->isRealFloatingType()) {
19224           llvm::APFloat InitValue = llvm::APFloat::getLargest(
19225               Context.getFloatTypeSemantics(Type), BOK != BO_LT);
19226           Init = FloatingLiteral::Create(Context, InitValue, /*isexact=*/true,
19227                                          Type, ELoc);
19228         }
19229         break;
19230       }
19231       case BO_PtrMemD:
19232       case BO_PtrMemI:
19233       case BO_MulAssign:
19234       case BO_Div:
19235       case BO_Rem:
19236       case BO_Sub:
19237       case BO_Shl:
19238       case BO_Shr:
19239       case BO_LE:
19240       case BO_GE:
19241       case BO_EQ:
19242       case BO_NE:
19243       case BO_Cmp:
19244       case BO_AndAssign:
19245       case BO_XorAssign:
19246       case BO_OrAssign:
19247       case BO_Assign:
19248       case BO_AddAssign:
19249       case BO_SubAssign:
19250       case BO_DivAssign:
19251       case BO_RemAssign:
19252       case BO_ShlAssign:
19253       case BO_ShrAssign:
19254       case BO_Comma:
19255         llvm_unreachable("Unexpected reduction operation");
19256       }
19257     }
19258     if (Init && DeclareReductionRef.isUnset()) {
19259       S.AddInitializerToDecl(RHSVD, Init, /*DirectInit=*/false);
19260       // Store initializer for single element in private copy. Will be used
19261       // during codegen.
19262       PrivateVD->setInit(RHSVD->getInit());
19263       PrivateVD->setInitStyle(RHSVD->getInitStyle());
19264     } else if (!Init) {
19265       S.ActOnUninitializedDecl(RHSVD);
19266       // Store initializer for single element in private copy. Will be used
19267       // during codegen.
19268       PrivateVD->setInit(RHSVD->getInit());
19269       PrivateVD->setInitStyle(RHSVD->getInitStyle());
19270     }
19271     if (RHSVD->isInvalidDecl())
19272       continue;
19273     if (!RHSVD->hasInit() && DeclareReductionRef.isUnset()) {
19274       S.Diag(ELoc, diag::err_omp_reduction_id_not_compatible)
19275           << Type << ReductionIdRange;
19276       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
19277                                VarDecl::DeclarationOnly;
19278       S.Diag(D->getLocation(),
19279              IsDecl ? diag::note_previous_decl : diag::note_defined_here)
19280           << D;
19281       continue;
19282     }
19283     DeclRefExpr *PrivateDRE = buildDeclRefExpr(S, PrivateVD, PrivateTy, ELoc);
19284     ExprResult ReductionOp;
19285     if (DeclareReductionRef.isUsable()) {
19286       QualType RedTy = DeclareReductionRef.get()->getType();
19287       QualType PtrRedTy = Context.getPointerType(RedTy);
19288       ExprResult LHS = S.CreateBuiltinUnaryOp(ELoc, UO_AddrOf, LHSDRE);
19289       ExprResult RHS = S.CreateBuiltinUnaryOp(ELoc, UO_AddrOf, RHSDRE);
19290       if (!BasePath.empty()) {
19291         LHS = S.DefaultLvalueConversion(LHS.get());
19292         RHS = S.DefaultLvalueConversion(RHS.get());
19293         LHS = ImplicitCastExpr::Create(
19294             Context, PtrRedTy, CK_UncheckedDerivedToBase, LHS.get(), &BasePath,
19295             LHS.get()->getValueKind(), FPOptionsOverride());
19296         RHS = ImplicitCastExpr::Create(
19297             Context, PtrRedTy, CK_UncheckedDerivedToBase, RHS.get(), &BasePath,
19298             RHS.get()->getValueKind(), FPOptionsOverride());
19299       }
19300       FunctionProtoType::ExtProtoInfo EPI;
19301       QualType Params[] = {PtrRedTy, PtrRedTy};
19302       QualType FnTy = Context.getFunctionType(Context.VoidTy, Params, EPI);
19303       auto *OVE = new (Context) OpaqueValueExpr(
19304           ELoc, Context.getPointerType(FnTy), VK_PRValue, OK_Ordinary,
19305           S.DefaultLvalueConversion(DeclareReductionRef.get()).get());
19306       Expr *Args[] = {LHS.get(), RHS.get()};
19307       ReductionOp =
19308           CallExpr::Create(Context, OVE, Args, Context.VoidTy, VK_PRValue, ELoc,
19309                            S.CurFPFeatureOverrides());
19310     } else {
19311       BinaryOperatorKind CombBOK = getRelatedCompoundReductionOp(BOK);
19312       if (Type->isRecordType() && CombBOK != BOK) {
19313         Sema::TentativeAnalysisScope Trap(S);
19314         ReductionOp =
19315             S.BuildBinOp(Stack->getCurScope(), ReductionId.getBeginLoc(),
19316                          CombBOK, LHSDRE, RHSDRE);
19317       }
19318       if (!ReductionOp.isUsable()) {
19319         ReductionOp =
19320             S.BuildBinOp(Stack->getCurScope(), ReductionId.getBeginLoc(), BOK,
19321                          LHSDRE, RHSDRE);
19322         if (ReductionOp.isUsable()) {
19323           if (BOK != BO_LT && BOK != BO_GT) {
19324             ReductionOp =
19325                 S.BuildBinOp(Stack->getCurScope(), ReductionId.getBeginLoc(),
19326                              BO_Assign, LHSDRE, ReductionOp.get());
19327           } else {
19328             auto *ConditionalOp = new (Context)
19329                 ConditionalOperator(ReductionOp.get(), ELoc, LHSDRE, ELoc,
19330                                     RHSDRE, Type, VK_LValue, OK_Ordinary);
19331             ReductionOp =
19332                 S.BuildBinOp(Stack->getCurScope(), ReductionId.getBeginLoc(),
19333                              BO_Assign, LHSDRE, ConditionalOp);
19334           }
19335         }
19336       }
19337       if (ReductionOp.isUsable())
19338         ReductionOp = S.ActOnFinishFullExpr(ReductionOp.get(),
19339                                             /*DiscardedValue*/ false);
19340       if (!ReductionOp.isUsable())
19341         continue;
19342     }
19343 
19344     // Add copy operations for inscan reductions.
19345     // LHS = RHS;
19346     ExprResult CopyOpRes, TempArrayRes, TempArrayElem;
19347     if (ClauseKind == OMPC_reduction &&
19348         RD.RedModifier == OMPC_REDUCTION_inscan) {
19349       ExprResult RHS = S.DefaultLvalueConversion(RHSDRE);
19350       CopyOpRes = S.BuildBinOp(Stack->getCurScope(), ELoc, BO_Assign, LHSDRE,
19351                                RHS.get());
19352       if (!CopyOpRes.isUsable())
19353         continue;
19354       CopyOpRes =
19355           S.ActOnFinishFullExpr(CopyOpRes.get(), /*DiscardedValue=*/true);
19356       if (!CopyOpRes.isUsable())
19357         continue;
19358       // For simd directive and simd-based directives in simd mode no need to
19359       // construct temp array, need just a single temp element.
19360       if (Stack->getCurrentDirective() == OMPD_simd ||
19361           (S.getLangOpts().OpenMPSimd &&
19362            isOpenMPSimdDirective(Stack->getCurrentDirective()))) {
19363         VarDecl *TempArrayVD =
19364             buildVarDecl(S, ELoc, PrivateTy, D->getName(),
19365                          D->hasAttrs() ? &D->getAttrs() : nullptr);
19366         // Add a constructor to the temp decl.
19367         S.ActOnUninitializedDecl(TempArrayVD);
19368         TempArrayRes = buildDeclRefExpr(S, TempArrayVD, PrivateTy, ELoc);
19369       } else {
19370         // Build temp array for prefix sum.
19371         auto *Dim = new (S.Context)
19372             OpaqueValueExpr(ELoc, S.Context.getSizeType(), VK_PRValue);
19373         QualType ArrayTy =
19374             S.Context.getVariableArrayType(PrivateTy, Dim, ArrayType::Normal,
19375                                            /*IndexTypeQuals=*/0, {ELoc, ELoc});
19376         VarDecl *TempArrayVD =
19377             buildVarDecl(S, ELoc, ArrayTy, D->getName(),
19378                          D->hasAttrs() ? &D->getAttrs() : nullptr);
19379         // Add a constructor to the temp decl.
19380         S.ActOnUninitializedDecl(TempArrayVD);
19381         TempArrayRes = buildDeclRefExpr(S, TempArrayVD, ArrayTy, ELoc);
19382         TempArrayElem =
19383             S.DefaultFunctionArrayLvalueConversion(TempArrayRes.get());
19384         auto *Idx = new (S.Context)
19385             OpaqueValueExpr(ELoc, S.Context.getSizeType(), VK_PRValue);
19386         TempArrayElem = S.CreateBuiltinArraySubscriptExpr(TempArrayElem.get(),
19387                                                           ELoc, Idx, ELoc);
19388       }
19389     }
19390 
19391     // OpenMP [2.15.4.6, Restrictions, p.2]
19392     // A list item that appears in an in_reduction clause of a task construct
19393     // must appear in a task_reduction clause of a construct associated with a
19394     // taskgroup region that includes the participating task in its taskgroup
19395     // set. The construct associated with the innermost region that meets this
19396     // condition must specify the same reduction-identifier as the in_reduction
19397     // clause.
19398     if (ClauseKind == OMPC_in_reduction) {
19399       SourceRange ParentSR;
19400       BinaryOperatorKind ParentBOK;
19401       const Expr *ParentReductionOp = nullptr;
19402       Expr *ParentBOKTD = nullptr, *ParentReductionOpTD = nullptr;
19403       DSAStackTy::DSAVarData ParentBOKDSA =
19404           Stack->getTopMostTaskgroupReductionData(D, ParentSR, ParentBOK,
19405                                                   ParentBOKTD);
19406       DSAStackTy::DSAVarData ParentReductionOpDSA =
19407           Stack->getTopMostTaskgroupReductionData(
19408               D, ParentSR, ParentReductionOp, ParentReductionOpTD);
19409       bool IsParentBOK = ParentBOKDSA.DKind != OMPD_unknown;
19410       bool IsParentReductionOp = ParentReductionOpDSA.DKind != OMPD_unknown;
19411       if ((DeclareReductionRef.isUnset() && IsParentReductionOp) ||
19412           (DeclareReductionRef.isUsable() && IsParentBOK) ||
19413           (IsParentBOK && BOK != ParentBOK) || IsParentReductionOp) {
19414         bool EmitError = true;
19415         if (IsParentReductionOp && DeclareReductionRef.isUsable()) {
19416           llvm::FoldingSetNodeID RedId, ParentRedId;
19417           ParentReductionOp->Profile(ParentRedId, Context, /*Canonical=*/true);
19418           DeclareReductionRef.get()->Profile(RedId, Context,
19419                                              /*Canonical=*/true);
19420           EmitError = RedId != ParentRedId;
19421         }
19422         if (EmitError) {
19423           S.Diag(ReductionId.getBeginLoc(),
19424                  diag::err_omp_reduction_identifier_mismatch)
19425               << ReductionIdRange << RefExpr->getSourceRange();
19426           S.Diag(ParentSR.getBegin(),
19427                  diag::note_omp_previous_reduction_identifier)
19428               << ParentSR
19429               << (IsParentBOK ? ParentBOKDSA.RefExpr
19430                               : ParentReductionOpDSA.RefExpr)
19431                      ->getSourceRange();
19432           continue;
19433         }
19434       }
19435       TaskgroupDescriptor = IsParentBOK ? ParentBOKTD : ParentReductionOpTD;
19436     }
19437 
19438     DeclRefExpr *Ref = nullptr;
19439     Expr *VarsExpr = RefExpr->IgnoreParens();
19440     if (!VD && !S.CurContext->isDependentContext()) {
19441       if (ASE || OASE) {
19442         TransformExprToCaptures RebuildToCapture(S, D);
19443         VarsExpr =
19444             RebuildToCapture.TransformExpr(RefExpr->IgnoreParens()).get();
19445         Ref = RebuildToCapture.getCapturedExpr();
19446       } else {
19447         VarsExpr = Ref = buildCapture(S, D, SimpleRefExpr, /*WithInit=*/false);
19448       }
19449       if (!S.isOpenMPCapturedDecl(D)) {
19450         RD.ExprCaptures.emplace_back(Ref->getDecl());
19451         if (Ref->getDecl()->hasAttr<OMPCaptureNoInitAttr>()) {
19452           ExprResult RefRes = S.DefaultLvalueConversion(Ref);
19453           if (!RefRes.isUsable())
19454             continue;
19455           ExprResult PostUpdateRes =
19456               S.BuildBinOp(Stack->getCurScope(), ELoc, BO_Assign, SimpleRefExpr,
19457                            RefRes.get());
19458           if (!PostUpdateRes.isUsable())
19459             continue;
19460           if (isOpenMPTaskingDirective(Stack->getCurrentDirective()) ||
19461               Stack->getCurrentDirective() == OMPD_taskgroup) {
19462             S.Diag(RefExpr->getExprLoc(),
19463                    diag::err_omp_reduction_non_addressable_expression)
19464                 << RefExpr->getSourceRange();
19465             continue;
19466           }
19467           RD.ExprPostUpdates.emplace_back(
19468               S.IgnoredValueConversions(PostUpdateRes.get()).get());
19469         }
19470       }
19471     }
19472     // All reduction items are still marked as reduction (to do not increase
19473     // code base size).
19474     unsigned Modifier = RD.RedModifier;
19475     // Consider task_reductions as reductions with task modifier. Required for
19476     // correct analysis of in_reduction clauses.
19477     if (CurrDir == OMPD_taskgroup && ClauseKind == OMPC_task_reduction)
19478       Modifier = OMPC_REDUCTION_task;
19479     Stack->addDSA(D, RefExpr->IgnoreParens(), OMPC_reduction, Ref, Modifier,
19480                   ASE || OASE);
19481     if (Modifier == OMPC_REDUCTION_task &&
19482         (CurrDir == OMPD_taskgroup ||
19483          ((isOpenMPParallelDirective(CurrDir) ||
19484            isOpenMPWorksharingDirective(CurrDir)) &&
19485           !isOpenMPSimdDirective(CurrDir)))) {
19486       if (DeclareReductionRef.isUsable())
19487         Stack->addTaskgroupReductionData(D, ReductionIdRange,
19488                                          DeclareReductionRef.get());
19489       else
19490         Stack->addTaskgroupReductionData(D, ReductionIdRange, BOK);
19491     }
19492     RD.push(VarsExpr, PrivateDRE, LHSDRE, RHSDRE, ReductionOp.get(),
19493             TaskgroupDescriptor, CopyOpRes.get(), TempArrayRes.get(),
19494             TempArrayElem.get());
19495   }
19496   return RD.Vars.empty();
19497 }
19498 
19499 OMPClause *Sema::ActOnOpenMPReductionClause(
19500     ArrayRef<Expr *> VarList, OpenMPReductionClauseModifier Modifier,
19501     SourceLocation StartLoc, SourceLocation LParenLoc,
19502     SourceLocation ModifierLoc, SourceLocation ColonLoc, SourceLocation EndLoc,
19503     CXXScopeSpec &ReductionIdScopeSpec, const DeclarationNameInfo &ReductionId,
19504     ArrayRef<Expr *> UnresolvedReductions) {
19505   if (ModifierLoc.isValid() && Modifier == OMPC_REDUCTION_unknown) {
19506     Diag(LParenLoc, diag::err_omp_unexpected_clause_value)
19507         << getListOfPossibleValues(OMPC_reduction, /*First=*/0,
19508                                    /*Last=*/OMPC_REDUCTION_unknown)
19509         << getOpenMPClauseName(OMPC_reduction);
19510     return nullptr;
19511   }
19512   // OpenMP 5.0, 2.19.5.4 reduction Clause, Restrictions
19513   // A reduction clause with the inscan reduction-modifier may only appear on a
19514   // worksharing-loop construct, a worksharing-loop SIMD construct, a simd
19515   // construct, a parallel worksharing-loop construct or a parallel
19516   // worksharing-loop SIMD construct.
19517   if (Modifier == OMPC_REDUCTION_inscan &&
19518       (DSAStack->getCurrentDirective() != OMPD_for &&
19519        DSAStack->getCurrentDirective() != OMPD_for_simd &&
19520        DSAStack->getCurrentDirective() != OMPD_simd &&
19521        DSAStack->getCurrentDirective() != OMPD_parallel_for &&
19522        DSAStack->getCurrentDirective() != OMPD_parallel_for_simd)) {
19523     Diag(ModifierLoc, diag::err_omp_wrong_inscan_reduction);
19524     return nullptr;
19525   }
19526 
19527   ReductionData RD(VarList.size(), Modifier);
19528   if (actOnOMPReductionKindClause(*this, DSAStack, OMPC_reduction, VarList,
19529                                   StartLoc, LParenLoc, ColonLoc, EndLoc,
19530                                   ReductionIdScopeSpec, ReductionId,
19531                                   UnresolvedReductions, RD))
19532     return nullptr;
19533 
19534   return OMPReductionClause::Create(
19535       Context, StartLoc, LParenLoc, ModifierLoc, ColonLoc, EndLoc, Modifier,
19536       RD.Vars, ReductionIdScopeSpec.getWithLocInContext(Context), ReductionId,
19537       RD.Privates, RD.LHSs, RD.RHSs, RD.ReductionOps, RD.InscanCopyOps,
19538       RD.InscanCopyArrayTemps, RD.InscanCopyArrayElems,
19539       buildPreInits(Context, RD.ExprCaptures),
19540       buildPostUpdate(*this, RD.ExprPostUpdates));
19541 }
19542 
19543 OMPClause *Sema::ActOnOpenMPTaskReductionClause(
19544     ArrayRef<Expr *> VarList, SourceLocation StartLoc, SourceLocation LParenLoc,
19545     SourceLocation ColonLoc, SourceLocation EndLoc,
19546     CXXScopeSpec &ReductionIdScopeSpec, const DeclarationNameInfo &ReductionId,
19547     ArrayRef<Expr *> UnresolvedReductions) {
19548   ReductionData RD(VarList.size());
19549   if (actOnOMPReductionKindClause(*this, DSAStack, OMPC_task_reduction, VarList,
19550                                   StartLoc, LParenLoc, ColonLoc, EndLoc,
19551                                   ReductionIdScopeSpec, ReductionId,
19552                                   UnresolvedReductions, RD))
19553     return nullptr;
19554 
19555   return OMPTaskReductionClause::Create(
19556       Context, StartLoc, LParenLoc, ColonLoc, EndLoc, RD.Vars,
19557       ReductionIdScopeSpec.getWithLocInContext(Context), ReductionId,
19558       RD.Privates, RD.LHSs, RD.RHSs, RD.ReductionOps,
19559       buildPreInits(Context, RD.ExprCaptures),
19560       buildPostUpdate(*this, RD.ExprPostUpdates));
19561 }
19562 
19563 OMPClause *Sema::ActOnOpenMPInReductionClause(
19564     ArrayRef<Expr *> VarList, SourceLocation StartLoc, SourceLocation LParenLoc,
19565     SourceLocation ColonLoc, SourceLocation EndLoc,
19566     CXXScopeSpec &ReductionIdScopeSpec, const DeclarationNameInfo &ReductionId,
19567     ArrayRef<Expr *> UnresolvedReductions) {
19568   ReductionData RD(VarList.size());
19569   if (actOnOMPReductionKindClause(*this, DSAStack, OMPC_in_reduction, VarList,
19570                                   StartLoc, LParenLoc, ColonLoc, EndLoc,
19571                                   ReductionIdScopeSpec, ReductionId,
19572                                   UnresolvedReductions, RD))
19573     return nullptr;
19574 
19575   return OMPInReductionClause::Create(
19576       Context, StartLoc, LParenLoc, ColonLoc, EndLoc, RD.Vars,
19577       ReductionIdScopeSpec.getWithLocInContext(Context), ReductionId,
19578       RD.Privates, RD.LHSs, RD.RHSs, RD.ReductionOps, RD.TaskgroupDescriptors,
19579       buildPreInits(Context, RD.ExprCaptures),
19580       buildPostUpdate(*this, RD.ExprPostUpdates));
19581 }
19582 
19583 bool Sema::CheckOpenMPLinearModifier(OpenMPLinearClauseKind LinKind,
19584                                      SourceLocation LinLoc) {
19585   if ((!LangOpts.CPlusPlus && LinKind != OMPC_LINEAR_val) ||
19586       LinKind == OMPC_LINEAR_unknown) {
19587     Diag(LinLoc, diag::err_omp_wrong_linear_modifier) << LangOpts.CPlusPlus;
19588     return true;
19589   }
19590   return false;
19591 }
19592 
19593 bool Sema::CheckOpenMPLinearDecl(const ValueDecl *D, SourceLocation ELoc,
19594                                  OpenMPLinearClauseKind LinKind, QualType Type,
19595                                  bool IsDeclareSimd) {
19596   const auto *VD = dyn_cast_or_null<VarDecl>(D);
19597   // A variable must not have an incomplete type or a reference type.
19598   if (RequireCompleteType(ELoc, Type, diag::err_omp_linear_incomplete_type))
19599     return true;
19600   if ((LinKind == OMPC_LINEAR_uval || LinKind == OMPC_LINEAR_ref) &&
19601       !Type->isReferenceType()) {
19602     Diag(ELoc, diag::err_omp_wrong_linear_modifier_non_reference)
19603         << Type << getOpenMPSimpleClauseTypeName(OMPC_linear, LinKind);
19604     return true;
19605   }
19606   Type = Type.getNonReferenceType();
19607 
19608   // OpenMP 5.0 [2.19.3, List Item Privatization, Restrictions]
19609   // A variable that is privatized must not have a const-qualified type
19610   // unless it is of class type with a mutable member. This restriction does
19611   // not apply to the firstprivate clause, nor to the linear clause on
19612   // declarative directives (like declare simd).
19613   if (!IsDeclareSimd &&
19614       rejectConstNotMutableType(*this, D, Type, OMPC_linear, ELoc))
19615     return true;
19616 
19617   // A list item must be of integral or pointer type.
19618   Type = Type.getUnqualifiedType().getCanonicalType();
19619   const auto *Ty = Type.getTypePtrOrNull();
19620   if (!Ty || (LinKind != OMPC_LINEAR_ref && !Ty->isDependentType() &&
19621               !Ty->isIntegralType(Context) && !Ty->isPointerType())) {
19622     Diag(ELoc, diag::err_omp_linear_expected_int_or_ptr) << Type;
19623     if (D) {
19624       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
19625                                VarDecl::DeclarationOnly;
19626       Diag(D->getLocation(),
19627            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
19628           << D;
19629     }
19630     return true;
19631   }
19632   return false;
19633 }
19634 
19635 OMPClause *Sema::ActOnOpenMPLinearClause(
19636     ArrayRef<Expr *> VarList, Expr *Step, SourceLocation StartLoc,
19637     SourceLocation LParenLoc, OpenMPLinearClauseKind LinKind,
19638     SourceLocation LinLoc, SourceLocation ColonLoc, SourceLocation EndLoc) {
19639   SmallVector<Expr *, 8> Vars;
19640   SmallVector<Expr *, 8> Privates;
19641   SmallVector<Expr *, 8> Inits;
19642   SmallVector<Decl *, 4> ExprCaptures;
19643   SmallVector<Expr *, 4> ExprPostUpdates;
19644   if (CheckOpenMPLinearModifier(LinKind, LinLoc))
19645     LinKind = OMPC_LINEAR_val;
19646   for (Expr *RefExpr : VarList) {
19647     assert(RefExpr && "NULL expr in OpenMP linear clause.");
19648     SourceLocation ELoc;
19649     SourceRange ERange;
19650     Expr *SimpleRefExpr = RefExpr;
19651     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
19652     if (Res.second) {
19653       // It will be analyzed later.
19654       Vars.push_back(RefExpr);
19655       Privates.push_back(nullptr);
19656       Inits.push_back(nullptr);
19657     }
19658     ValueDecl *D = Res.first;
19659     if (!D)
19660       continue;
19661 
19662     QualType Type = D->getType();
19663     auto *VD = dyn_cast<VarDecl>(D);
19664 
19665     // OpenMP [2.14.3.7, linear clause]
19666     //  A list-item cannot appear in more than one linear clause.
19667     //  A list-item that appears in a linear clause cannot appear in any
19668     //  other data-sharing attribute clause.
19669     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(D, /*FromParent=*/false);
19670     if (DVar.RefExpr) {
19671       Diag(ELoc, diag::err_omp_wrong_dsa) << getOpenMPClauseName(DVar.CKind)
19672                                           << getOpenMPClauseName(OMPC_linear);
19673       reportOriginalDsa(*this, DSAStack, D, DVar);
19674       continue;
19675     }
19676 
19677     if (CheckOpenMPLinearDecl(D, ELoc, LinKind, Type))
19678       continue;
19679     Type = Type.getNonReferenceType().getUnqualifiedType().getCanonicalType();
19680 
19681     // Build private copy of original var.
19682     VarDecl *Private =
19683         buildVarDecl(*this, ELoc, Type, D->getName(),
19684                      D->hasAttrs() ? &D->getAttrs() : nullptr,
19685                      VD ? cast<DeclRefExpr>(SimpleRefExpr) : nullptr);
19686     DeclRefExpr *PrivateRef = buildDeclRefExpr(*this, Private, Type, ELoc);
19687     // Build var to save initial value.
19688     VarDecl *Init = buildVarDecl(*this, ELoc, Type, ".linear.start");
19689     Expr *InitExpr;
19690     DeclRefExpr *Ref = nullptr;
19691     if (!VD && !CurContext->isDependentContext()) {
19692       Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/false);
19693       if (!isOpenMPCapturedDecl(D)) {
19694         ExprCaptures.push_back(Ref->getDecl());
19695         if (Ref->getDecl()->hasAttr<OMPCaptureNoInitAttr>()) {
19696           ExprResult RefRes = DefaultLvalueConversion(Ref);
19697           if (!RefRes.isUsable())
19698             continue;
19699           ExprResult PostUpdateRes =
19700               BuildBinOp(DSAStack->getCurScope(), ELoc, BO_Assign,
19701                          SimpleRefExpr, RefRes.get());
19702           if (!PostUpdateRes.isUsable())
19703             continue;
19704           ExprPostUpdates.push_back(
19705               IgnoredValueConversions(PostUpdateRes.get()).get());
19706         }
19707       }
19708     }
19709     if (LinKind == OMPC_LINEAR_uval)
19710       InitExpr = VD ? VD->getInit() : SimpleRefExpr;
19711     else
19712       InitExpr = VD ? SimpleRefExpr : Ref;
19713     AddInitializerToDecl(Init, DefaultLvalueConversion(InitExpr).get(),
19714                          /*DirectInit=*/false);
19715     DeclRefExpr *InitRef = buildDeclRefExpr(*this, Init, Type, ELoc);
19716 
19717     DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_linear, Ref);
19718     Vars.push_back((VD || CurContext->isDependentContext())
19719                        ? RefExpr->IgnoreParens()
19720                        : Ref);
19721     Privates.push_back(PrivateRef);
19722     Inits.push_back(InitRef);
19723   }
19724 
19725   if (Vars.empty())
19726     return nullptr;
19727 
19728   Expr *StepExpr = Step;
19729   Expr *CalcStepExpr = nullptr;
19730   if (Step && !Step->isValueDependent() && !Step->isTypeDependent() &&
19731       !Step->isInstantiationDependent() &&
19732       !Step->containsUnexpandedParameterPack()) {
19733     SourceLocation StepLoc = Step->getBeginLoc();
19734     ExprResult Val = PerformOpenMPImplicitIntegerConversion(StepLoc, Step);
19735     if (Val.isInvalid())
19736       return nullptr;
19737     StepExpr = Val.get();
19738 
19739     // Build var to save the step value.
19740     VarDecl *SaveVar =
19741         buildVarDecl(*this, StepLoc, StepExpr->getType(), ".linear.step");
19742     ExprResult SaveRef =
19743         buildDeclRefExpr(*this, SaveVar, StepExpr->getType(), StepLoc);
19744     ExprResult CalcStep =
19745         BuildBinOp(CurScope, StepLoc, BO_Assign, SaveRef.get(), StepExpr);
19746     CalcStep = ActOnFinishFullExpr(CalcStep.get(), /*DiscardedValue*/ false);
19747 
19748     // Warn about zero linear step (it would be probably better specified as
19749     // making corresponding variables 'const').
19750     if (Optional<llvm::APSInt> Result =
19751             StepExpr->getIntegerConstantExpr(Context)) {
19752       if (!Result->isNegative() && !Result->isStrictlyPositive())
19753         Diag(StepLoc, diag::warn_omp_linear_step_zero)
19754             << Vars[0] << (Vars.size() > 1);
19755     } else if (CalcStep.isUsable()) {
19756       // Calculate the step beforehand instead of doing this on each iteration.
19757       // (This is not used if the number of iterations may be kfold-ed).
19758       CalcStepExpr = CalcStep.get();
19759     }
19760   }
19761 
19762   return OMPLinearClause::Create(Context, StartLoc, LParenLoc, LinKind, LinLoc,
19763                                  ColonLoc, EndLoc, Vars, Privates, Inits,
19764                                  StepExpr, CalcStepExpr,
19765                                  buildPreInits(Context, ExprCaptures),
19766                                  buildPostUpdate(*this, ExprPostUpdates));
19767 }
19768 
19769 static bool FinishOpenMPLinearClause(OMPLinearClause &Clause, DeclRefExpr *IV,
19770                                      Expr *NumIterations, Sema &SemaRef,
19771                                      Scope *S, DSAStackTy *Stack) {
19772   // Walk the vars and build update/final expressions for the CodeGen.
19773   SmallVector<Expr *, 8> Updates;
19774   SmallVector<Expr *, 8> Finals;
19775   SmallVector<Expr *, 8> UsedExprs;
19776   Expr *Step = Clause.getStep();
19777   Expr *CalcStep = Clause.getCalcStep();
19778   // OpenMP [2.14.3.7, linear clause]
19779   // If linear-step is not specified it is assumed to be 1.
19780   if (!Step)
19781     Step = SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get();
19782   else if (CalcStep)
19783     Step = cast<BinaryOperator>(CalcStep)->getLHS();
19784   bool HasErrors = false;
19785   auto CurInit = Clause.inits().begin();
19786   auto CurPrivate = Clause.privates().begin();
19787   OpenMPLinearClauseKind LinKind = Clause.getModifier();
19788   for (Expr *RefExpr : Clause.varlists()) {
19789     SourceLocation ELoc;
19790     SourceRange ERange;
19791     Expr *SimpleRefExpr = RefExpr;
19792     auto Res = getPrivateItem(SemaRef, SimpleRefExpr, ELoc, ERange);
19793     ValueDecl *D = Res.first;
19794     if (Res.second || !D) {
19795       Updates.push_back(nullptr);
19796       Finals.push_back(nullptr);
19797       HasErrors = true;
19798       continue;
19799     }
19800     auto &&Info = Stack->isLoopControlVariable(D);
19801     // OpenMP [2.15.11, distribute simd Construct]
19802     // A list item may not appear in a linear clause, unless it is the loop
19803     // iteration variable.
19804     if (isOpenMPDistributeDirective(Stack->getCurrentDirective()) &&
19805         isOpenMPSimdDirective(Stack->getCurrentDirective()) && !Info.first) {
19806       SemaRef.Diag(ELoc,
19807                    diag::err_omp_linear_distribute_var_non_loop_iteration);
19808       Updates.push_back(nullptr);
19809       Finals.push_back(nullptr);
19810       HasErrors = true;
19811       continue;
19812     }
19813     Expr *InitExpr = *CurInit;
19814 
19815     // Build privatized reference to the current linear var.
19816     auto *DE = cast<DeclRefExpr>(SimpleRefExpr);
19817     Expr *CapturedRef;
19818     if (LinKind == OMPC_LINEAR_uval)
19819       CapturedRef = cast<VarDecl>(DE->getDecl())->getInit();
19820     else
19821       CapturedRef =
19822           buildDeclRefExpr(SemaRef, cast<VarDecl>(DE->getDecl()),
19823                            DE->getType().getUnqualifiedType(), DE->getExprLoc(),
19824                            /*RefersToCapture=*/true);
19825 
19826     // Build update: Var = InitExpr + IV * Step
19827     ExprResult Update;
19828     if (!Info.first)
19829       Update = buildCounterUpdate(
19830           SemaRef, S, RefExpr->getExprLoc(), *CurPrivate, InitExpr, IV, Step,
19831           /*Subtract=*/false, /*IsNonRectangularLB=*/false);
19832     else
19833       Update = *CurPrivate;
19834     Update = SemaRef.ActOnFinishFullExpr(Update.get(), DE->getBeginLoc(),
19835                                          /*DiscardedValue*/ false);
19836 
19837     // Build final: Var = PrivCopy;
19838     ExprResult Final;
19839     if (!Info.first)
19840       Final = SemaRef.BuildBinOp(
19841           S, RefExpr->getExprLoc(), BO_Assign, CapturedRef,
19842           SemaRef.DefaultLvalueConversion(*CurPrivate).get());
19843     else
19844       Final = *CurPrivate;
19845     Final = SemaRef.ActOnFinishFullExpr(Final.get(), DE->getBeginLoc(),
19846                                         /*DiscardedValue*/ false);
19847 
19848     if (!Update.isUsable() || !Final.isUsable()) {
19849       Updates.push_back(nullptr);
19850       Finals.push_back(nullptr);
19851       UsedExprs.push_back(nullptr);
19852       HasErrors = true;
19853     } else {
19854       Updates.push_back(Update.get());
19855       Finals.push_back(Final.get());
19856       if (!Info.first)
19857         UsedExprs.push_back(SimpleRefExpr);
19858     }
19859     ++CurInit;
19860     ++CurPrivate;
19861   }
19862   if (Expr *S = Clause.getStep())
19863     UsedExprs.push_back(S);
19864   // Fill the remaining part with the nullptr.
19865   UsedExprs.append(Clause.varlist_size() + 1 - UsedExprs.size(), nullptr);
19866   Clause.setUpdates(Updates);
19867   Clause.setFinals(Finals);
19868   Clause.setUsedExprs(UsedExprs);
19869   return HasErrors;
19870 }
19871 
19872 OMPClause *Sema::ActOnOpenMPAlignedClause(
19873     ArrayRef<Expr *> VarList, Expr *Alignment, SourceLocation StartLoc,
19874     SourceLocation LParenLoc, SourceLocation ColonLoc, SourceLocation EndLoc) {
19875   SmallVector<Expr *, 8> Vars;
19876   for (Expr *RefExpr : VarList) {
19877     assert(RefExpr && "NULL expr in OpenMP linear clause.");
19878     SourceLocation ELoc;
19879     SourceRange ERange;
19880     Expr *SimpleRefExpr = RefExpr;
19881     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
19882     if (Res.second) {
19883       // It will be analyzed later.
19884       Vars.push_back(RefExpr);
19885     }
19886     ValueDecl *D = Res.first;
19887     if (!D)
19888       continue;
19889 
19890     QualType QType = D->getType();
19891     auto *VD = dyn_cast<VarDecl>(D);
19892 
19893     // OpenMP  [2.8.1, simd construct, Restrictions]
19894     // The type of list items appearing in the aligned clause must be
19895     // array, pointer, reference to array, or reference to pointer.
19896     QType = QType.getNonReferenceType().getUnqualifiedType().getCanonicalType();
19897     const Type *Ty = QType.getTypePtrOrNull();
19898     if (!Ty || (!Ty->isArrayType() && !Ty->isPointerType())) {
19899       Diag(ELoc, diag::err_omp_aligned_expected_array_or_ptr)
19900           << QType << getLangOpts().CPlusPlus << ERange;
19901       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
19902                                VarDecl::DeclarationOnly;
19903       Diag(D->getLocation(),
19904            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
19905           << D;
19906       continue;
19907     }
19908 
19909     // OpenMP  [2.8.1, simd construct, Restrictions]
19910     // A list-item cannot appear in more than one aligned clause.
19911     if (const Expr *PrevRef = DSAStack->addUniqueAligned(D, SimpleRefExpr)) {
19912       Diag(ELoc, diag::err_omp_used_in_clause_twice)
19913           << 0 << getOpenMPClauseName(OMPC_aligned) << ERange;
19914       Diag(PrevRef->getExprLoc(), diag::note_omp_explicit_dsa)
19915           << getOpenMPClauseName(OMPC_aligned);
19916       continue;
19917     }
19918 
19919     DeclRefExpr *Ref = nullptr;
19920     if (!VD && isOpenMPCapturedDecl(D))
19921       Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/true);
19922     Vars.push_back(DefaultFunctionArrayConversion(
19923                        (VD || !Ref) ? RefExpr->IgnoreParens() : Ref)
19924                        .get());
19925   }
19926 
19927   // OpenMP [2.8.1, simd construct, Description]
19928   // The parameter of the aligned clause, alignment, must be a constant
19929   // positive integer expression.
19930   // If no optional parameter is specified, implementation-defined default
19931   // alignments for SIMD instructions on the target platforms are assumed.
19932   if (Alignment != nullptr) {
19933     ExprResult AlignResult =
19934         VerifyPositiveIntegerConstantInClause(Alignment, OMPC_aligned);
19935     if (AlignResult.isInvalid())
19936       return nullptr;
19937     Alignment = AlignResult.get();
19938   }
19939   if (Vars.empty())
19940     return nullptr;
19941 
19942   return OMPAlignedClause::Create(Context, StartLoc, LParenLoc, ColonLoc,
19943                                   EndLoc, Vars, Alignment);
19944 }
19945 
19946 OMPClause *Sema::ActOnOpenMPCopyinClause(ArrayRef<Expr *> VarList,
19947                                          SourceLocation StartLoc,
19948                                          SourceLocation LParenLoc,
19949                                          SourceLocation EndLoc) {
19950   SmallVector<Expr *, 8> Vars;
19951   SmallVector<Expr *, 8> SrcExprs;
19952   SmallVector<Expr *, 8> DstExprs;
19953   SmallVector<Expr *, 8> AssignmentOps;
19954   for (Expr *RefExpr : VarList) {
19955     assert(RefExpr && "NULL expr in OpenMP copyin clause.");
19956     if (isa<DependentScopeDeclRefExpr>(RefExpr)) {
19957       // It will be analyzed later.
19958       Vars.push_back(RefExpr);
19959       SrcExprs.push_back(nullptr);
19960       DstExprs.push_back(nullptr);
19961       AssignmentOps.push_back(nullptr);
19962       continue;
19963     }
19964 
19965     SourceLocation ELoc = RefExpr->getExprLoc();
19966     // OpenMP [2.1, C/C++]
19967     //  A list item is a variable name.
19968     // OpenMP  [2.14.4.1, Restrictions, p.1]
19969     //  A list item that appears in a copyin clause must be threadprivate.
19970     auto *DE = dyn_cast<DeclRefExpr>(RefExpr);
19971     if (!DE || !isa<VarDecl>(DE->getDecl())) {
19972       Diag(ELoc, diag::err_omp_expected_var_name_member_expr)
19973           << 0 << RefExpr->getSourceRange();
19974       continue;
19975     }
19976 
19977     Decl *D = DE->getDecl();
19978     auto *VD = cast<VarDecl>(D);
19979 
19980     QualType Type = VD->getType();
19981     if (Type->isDependentType() || Type->isInstantiationDependentType()) {
19982       // It will be analyzed later.
19983       Vars.push_back(DE);
19984       SrcExprs.push_back(nullptr);
19985       DstExprs.push_back(nullptr);
19986       AssignmentOps.push_back(nullptr);
19987       continue;
19988     }
19989 
19990     // OpenMP [2.14.4.1, Restrictions, C/C++, p.1]
19991     //  A list item that appears in a copyin clause must be threadprivate.
19992     if (!DSAStack->isThreadPrivate(VD)) {
19993       Diag(ELoc, diag::err_omp_required_access)
19994           << getOpenMPClauseName(OMPC_copyin)
19995           << getOpenMPDirectiveName(OMPD_threadprivate);
19996       continue;
19997     }
19998 
19999     // OpenMP [2.14.4.1, Restrictions, C/C++, p.2]
20000     //  A variable of class type (or array thereof) that appears in a
20001     //  copyin clause requires an accessible, unambiguous copy assignment
20002     //  operator for the class type.
20003     QualType ElemType = Context.getBaseElementType(Type).getNonReferenceType();
20004     VarDecl *SrcVD =
20005         buildVarDecl(*this, DE->getBeginLoc(), ElemType.getUnqualifiedType(),
20006                      ".copyin.src", VD->hasAttrs() ? &VD->getAttrs() : nullptr);
20007     DeclRefExpr *PseudoSrcExpr = buildDeclRefExpr(
20008         *this, SrcVD, ElemType.getUnqualifiedType(), DE->getExprLoc());
20009     VarDecl *DstVD =
20010         buildVarDecl(*this, DE->getBeginLoc(), ElemType, ".copyin.dst",
20011                      VD->hasAttrs() ? &VD->getAttrs() : nullptr);
20012     DeclRefExpr *PseudoDstExpr =
20013         buildDeclRefExpr(*this, DstVD, ElemType, DE->getExprLoc());
20014     // For arrays generate assignment operation for single element and replace
20015     // it by the original array element in CodeGen.
20016     ExprResult AssignmentOp =
20017         BuildBinOp(/*S=*/nullptr, DE->getExprLoc(), BO_Assign, PseudoDstExpr,
20018                    PseudoSrcExpr);
20019     if (AssignmentOp.isInvalid())
20020       continue;
20021     AssignmentOp = ActOnFinishFullExpr(AssignmentOp.get(), DE->getExprLoc(),
20022                                        /*DiscardedValue*/ false);
20023     if (AssignmentOp.isInvalid())
20024       continue;
20025 
20026     DSAStack->addDSA(VD, DE, OMPC_copyin);
20027     Vars.push_back(DE);
20028     SrcExprs.push_back(PseudoSrcExpr);
20029     DstExprs.push_back(PseudoDstExpr);
20030     AssignmentOps.push_back(AssignmentOp.get());
20031   }
20032 
20033   if (Vars.empty())
20034     return nullptr;
20035 
20036   return OMPCopyinClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars,
20037                                  SrcExprs, DstExprs, AssignmentOps);
20038 }
20039 
20040 OMPClause *Sema::ActOnOpenMPCopyprivateClause(ArrayRef<Expr *> VarList,
20041                                               SourceLocation StartLoc,
20042                                               SourceLocation LParenLoc,
20043                                               SourceLocation EndLoc) {
20044   SmallVector<Expr *, 8> Vars;
20045   SmallVector<Expr *, 8> SrcExprs;
20046   SmallVector<Expr *, 8> DstExprs;
20047   SmallVector<Expr *, 8> AssignmentOps;
20048   for (Expr *RefExpr : VarList) {
20049     assert(RefExpr && "NULL expr in OpenMP linear clause.");
20050     SourceLocation ELoc;
20051     SourceRange ERange;
20052     Expr *SimpleRefExpr = RefExpr;
20053     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
20054     if (Res.second) {
20055       // It will be analyzed later.
20056       Vars.push_back(RefExpr);
20057       SrcExprs.push_back(nullptr);
20058       DstExprs.push_back(nullptr);
20059       AssignmentOps.push_back(nullptr);
20060     }
20061     ValueDecl *D = Res.first;
20062     if (!D)
20063       continue;
20064 
20065     QualType Type = D->getType();
20066     auto *VD = dyn_cast<VarDecl>(D);
20067 
20068     // OpenMP [2.14.4.2, Restrictions, p.2]
20069     //  A list item that appears in a copyprivate clause may not appear in a
20070     //  private or firstprivate clause on the single construct.
20071     if (!VD || !DSAStack->isThreadPrivate(VD)) {
20072       DSAStackTy::DSAVarData DVar =
20073           DSAStack->getTopDSA(D, /*FromParent=*/false);
20074       if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_copyprivate &&
20075           DVar.RefExpr) {
20076         Diag(ELoc, diag::err_omp_wrong_dsa)
20077             << getOpenMPClauseName(DVar.CKind)
20078             << getOpenMPClauseName(OMPC_copyprivate);
20079         reportOriginalDsa(*this, DSAStack, D, DVar);
20080         continue;
20081       }
20082 
20083       // OpenMP [2.11.4.2, Restrictions, p.1]
20084       //  All list items that appear in a copyprivate clause must be either
20085       //  threadprivate or private in the enclosing context.
20086       if (DVar.CKind == OMPC_unknown) {
20087         DVar = DSAStack->getImplicitDSA(D, false);
20088         if (DVar.CKind == OMPC_shared) {
20089           Diag(ELoc, diag::err_omp_required_access)
20090               << getOpenMPClauseName(OMPC_copyprivate)
20091               << "threadprivate or private in the enclosing context";
20092           reportOriginalDsa(*this, DSAStack, D, DVar);
20093           continue;
20094         }
20095       }
20096     }
20097 
20098     // Variably modified types are not supported.
20099     if (!Type->isAnyPointerType() && Type->isVariablyModifiedType()) {
20100       Diag(ELoc, diag::err_omp_variably_modified_type_not_supported)
20101           << getOpenMPClauseName(OMPC_copyprivate) << Type
20102           << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
20103       bool IsDecl = !VD || VD->isThisDeclarationADefinition(Context) ==
20104                                VarDecl::DeclarationOnly;
20105       Diag(D->getLocation(),
20106            IsDecl ? diag::note_previous_decl : diag::note_defined_here)
20107           << D;
20108       continue;
20109     }
20110 
20111     // OpenMP [2.14.4.1, Restrictions, C/C++, p.2]
20112     //  A variable of class type (or array thereof) that appears in a
20113     //  copyin clause requires an accessible, unambiguous copy assignment
20114     //  operator for the class type.
20115     Type = Context.getBaseElementType(Type.getNonReferenceType())
20116                .getUnqualifiedType();
20117     VarDecl *SrcVD =
20118         buildVarDecl(*this, RefExpr->getBeginLoc(), Type, ".copyprivate.src",
20119                      D->hasAttrs() ? &D->getAttrs() : nullptr);
20120     DeclRefExpr *PseudoSrcExpr = buildDeclRefExpr(*this, SrcVD, Type, ELoc);
20121     VarDecl *DstVD =
20122         buildVarDecl(*this, RefExpr->getBeginLoc(), Type, ".copyprivate.dst",
20123                      D->hasAttrs() ? &D->getAttrs() : nullptr);
20124     DeclRefExpr *PseudoDstExpr = buildDeclRefExpr(*this, DstVD, Type, ELoc);
20125     ExprResult AssignmentOp = BuildBinOp(
20126         DSAStack->getCurScope(), ELoc, BO_Assign, PseudoDstExpr, PseudoSrcExpr);
20127     if (AssignmentOp.isInvalid())
20128       continue;
20129     AssignmentOp =
20130         ActOnFinishFullExpr(AssignmentOp.get(), ELoc, /*DiscardedValue*/ false);
20131     if (AssignmentOp.isInvalid())
20132       continue;
20133 
20134     // No need to mark vars as copyprivate, they are already threadprivate or
20135     // implicitly private.
20136     assert(VD || isOpenMPCapturedDecl(D));
20137     Vars.push_back(
20138         VD ? RefExpr->IgnoreParens()
20139            : buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/false));
20140     SrcExprs.push_back(PseudoSrcExpr);
20141     DstExprs.push_back(PseudoDstExpr);
20142     AssignmentOps.push_back(AssignmentOp.get());
20143   }
20144 
20145   if (Vars.empty())
20146     return nullptr;
20147 
20148   return OMPCopyprivateClause::Create(Context, StartLoc, LParenLoc, EndLoc,
20149                                       Vars, SrcExprs, DstExprs, AssignmentOps);
20150 }
20151 
20152 OMPClause *Sema::ActOnOpenMPFlushClause(ArrayRef<Expr *> VarList,
20153                                         SourceLocation StartLoc,
20154                                         SourceLocation LParenLoc,
20155                                         SourceLocation EndLoc) {
20156   if (VarList.empty())
20157     return nullptr;
20158 
20159   return OMPFlushClause::Create(Context, StartLoc, LParenLoc, EndLoc, VarList);
20160 }
20161 
20162 /// Tries to find omp_depend_t. type.
20163 static bool findOMPDependT(Sema &S, SourceLocation Loc, DSAStackTy *Stack,
20164                            bool Diagnose = true) {
20165   QualType OMPDependT = Stack->getOMPDependT();
20166   if (!OMPDependT.isNull())
20167     return true;
20168   IdentifierInfo *II = &S.PP.getIdentifierTable().get("omp_depend_t");
20169   ParsedType PT = S.getTypeName(*II, Loc, S.getCurScope());
20170   if (!PT.getAsOpaquePtr() || PT.get().isNull()) {
20171     if (Diagnose)
20172       S.Diag(Loc, diag::err_omp_implied_type_not_found) << "omp_depend_t";
20173     return false;
20174   }
20175   Stack->setOMPDependT(PT.get());
20176   return true;
20177 }
20178 
20179 OMPClause *Sema::ActOnOpenMPDepobjClause(Expr *Depobj, SourceLocation StartLoc,
20180                                          SourceLocation LParenLoc,
20181                                          SourceLocation EndLoc) {
20182   if (!Depobj)
20183     return nullptr;
20184 
20185   bool OMPDependTFound = findOMPDependT(*this, StartLoc, DSAStack);
20186 
20187   // OpenMP 5.0, 2.17.10.1 depobj Construct
20188   // depobj is an lvalue expression of type omp_depend_t.
20189   if (!Depobj->isTypeDependent() && !Depobj->isValueDependent() &&
20190       !Depobj->isInstantiationDependent() &&
20191       !Depobj->containsUnexpandedParameterPack() &&
20192       (OMPDependTFound &&
20193        !Context.typesAreCompatible(DSAStack->getOMPDependT(), Depobj->getType(),
20194                                    /*CompareUnqualified=*/true))) {
20195     Diag(Depobj->getExprLoc(), diag::err_omp_expected_omp_depend_t_lvalue)
20196         << 0 << Depobj->getType() << Depobj->getSourceRange();
20197   }
20198 
20199   if (!Depobj->isLValue()) {
20200     Diag(Depobj->getExprLoc(), diag::err_omp_expected_omp_depend_t_lvalue)
20201         << 1 << Depobj->getSourceRange();
20202   }
20203 
20204   return OMPDepobjClause::Create(Context, StartLoc, LParenLoc, EndLoc, Depobj);
20205 }
20206 
20207 OMPClause *
20208 Sema::ActOnOpenMPDependClause(const OMPDependClause::DependDataTy &Data,
20209                               Expr *DepModifier, ArrayRef<Expr *> VarList,
20210                               SourceLocation StartLoc, SourceLocation LParenLoc,
20211                               SourceLocation EndLoc) {
20212   OpenMPDependClauseKind DepKind = Data.DepKind;
20213   SourceLocation DepLoc = Data.DepLoc;
20214   if (DSAStack->getCurrentDirective() == OMPD_ordered &&
20215       DepKind != OMPC_DEPEND_source && DepKind != OMPC_DEPEND_sink) {
20216     Diag(DepLoc, diag::err_omp_unexpected_clause_value)
20217         << "'source' or 'sink'" << getOpenMPClauseName(OMPC_depend);
20218     return nullptr;
20219   }
20220   if (DSAStack->getCurrentDirective() == OMPD_taskwait &&
20221       DepKind == OMPC_DEPEND_mutexinoutset) {
20222     Diag(DepLoc, diag::err_omp_taskwait_depend_mutexinoutset_not_allowed);
20223     return nullptr;
20224   }
20225   if ((DSAStack->getCurrentDirective() != OMPD_ordered ||
20226        DSAStack->getCurrentDirective() == OMPD_depobj) &&
20227       (DepKind == OMPC_DEPEND_unknown || DepKind == OMPC_DEPEND_source ||
20228        DepKind == OMPC_DEPEND_sink ||
20229        ((LangOpts.OpenMP < 50 ||
20230          DSAStack->getCurrentDirective() == OMPD_depobj) &&
20231         DepKind == OMPC_DEPEND_depobj))) {
20232     SmallVector<unsigned, 6> Except = {OMPC_DEPEND_source, OMPC_DEPEND_sink,
20233                                        OMPC_DEPEND_outallmemory,
20234                                        OMPC_DEPEND_inoutallmemory};
20235     if (LangOpts.OpenMP < 50 || DSAStack->getCurrentDirective() == OMPD_depobj)
20236       Except.push_back(OMPC_DEPEND_depobj);
20237     if (LangOpts.OpenMP < 51)
20238       Except.push_back(OMPC_DEPEND_inoutset);
20239     std::string Expected = (LangOpts.OpenMP >= 50 && !DepModifier)
20240                                ? "depend modifier(iterator) or "
20241                                : "";
20242     Diag(DepLoc, diag::err_omp_unexpected_clause_value)
20243         << Expected + getListOfPossibleValues(OMPC_depend, /*First=*/0,
20244                                               /*Last=*/OMPC_DEPEND_unknown,
20245                                               Except)
20246         << getOpenMPClauseName(OMPC_depend);
20247     return nullptr;
20248   }
20249   if (DepModifier &&
20250       (DepKind == OMPC_DEPEND_source || DepKind == OMPC_DEPEND_sink)) {
20251     Diag(DepModifier->getExprLoc(),
20252          diag::err_omp_depend_sink_source_with_modifier);
20253     return nullptr;
20254   }
20255   if (DepModifier &&
20256       !DepModifier->getType()->isSpecificBuiltinType(BuiltinType::OMPIterator))
20257     Diag(DepModifier->getExprLoc(), diag::err_omp_depend_modifier_not_iterator);
20258 
20259   SmallVector<Expr *, 8> Vars;
20260   DSAStackTy::OperatorOffsetTy OpsOffs;
20261   llvm::APSInt DepCounter(/*BitWidth=*/32);
20262   llvm::APSInt TotalDepCount(/*BitWidth=*/32);
20263   if (DepKind == OMPC_DEPEND_sink || DepKind == OMPC_DEPEND_source) {
20264     if (const Expr *OrderedCountExpr =
20265             DSAStack->getParentOrderedRegionParam().first) {
20266       TotalDepCount = OrderedCountExpr->EvaluateKnownConstInt(Context);
20267       TotalDepCount.setIsUnsigned(/*Val=*/true);
20268     }
20269   }
20270   for (Expr *RefExpr : VarList) {
20271     assert(RefExpr && "NULL expr in OpenMP shared clause.");
20272     if (isa<DependentScopeDeclRefExpr>(RefExpr)) {
20273       // It will be analyzed later.
20274       Vars.push_back(RefExpr);
20275       continue;
20276     }
20277 
20278     SourceLocation ELoc = RefExpr->getExprLoc();
20279     Expr *SimpleExpr = RefExpr->IgnoreParenCasts();
20280     if (DepKind == OMPC_DEPEND_sink) {
20281       if (DSAStack->getParentOrderedRegionParam().first &&
20282           DepCounter >= TotalDepCount) {
20283         Diag(ELoc, diag::err_omp_depend_sink_unexpected_expr);
20284         continue;
20285       }
20286       ++DepCounter;
20287       // OpenMP  [2.13.9, Summary]
20288       // depend(dependence-type : vec), where dependence-type is:
20289       // 'sink' and where vec is the iteration vector, which has the form:
20290       //  x1 [+- d1], x2 [+- d2 ], . . . , xn [+- dn]
20291       // where n is the value specified by the ordered clause in the loop
20292       // directive, xi denotes the loop iteration variable of the i-th nested
20293       // loop associated with the loop directive, and di is a constant
20294       // non-negative integer.
20295       if (CurContext->isDependentContext()) {
20296         // It will be analyzed later.
20297         Vars.push_back(RefExpr);
20298         continue;
20299       }
20300       SimpleExpr = SimpleExpr->IgnoreImplicit();
20301       OverloadedOperatorKind OOK = OO_None;
20302       SourceLocation OOLoc;
20303       Expr *LHS = SimpleExpr;
20304       Expr *RHS = nullptr;
20305       if (auto *BO = dyn_cast<BinaryOperator>(SimpleExpr)) {
20306         OOK = BinaryOperator::getOverloadedOperator(BO->getOpcode());
20307         OOLoc = BO->getOperatorLoc();
20308         LHS = BO->getLHS()->IgnoreParenImpCasts();
20309         RHS = BO->getRHS()->IgnoreParenImpCasts();
20310       } else if (auto *OCE = dyn_cast<CXXOperatorCallExpr>(SimpleExpr)) {
20311         OOK = OCE->getOperator();
20312         OOLoc = OCE->getOperatorLoc();
20313         LHS = OCE->getArg(/*Arg=*/0)->IgnoreParenImpCasts();
20314         RHS = OCE->getArg(/*Arg=*/1)->IgnoreParenImpCasts();
20315       } else if (auto *MCE = dyn_cast<CXXMemberCallExpr>(SimpleExpr)) {
20316         OOK = MCE->getMethodDecl()
20317                   ->getNameInfo()
20318                   .getName()
20319                   .getCXXOverloadedOperator();
20320         OOLoc = MCE->getCallee()->getExprLoc();
20321         LHS = MCE->getImplicitObjectArgument()->IgnoreParenImpCasts();
20322         RHS = MCE->getArg(/*Arg=*/0)->IgnoreParenImpCasts();
20323       }
20324       SourceLocation ELoc;
20325       SourceRange ERange;
20326       auto Res = getPrivateItem(*this, LHS, ELoc, ERange);
20327       if (Res.second) {
20328         // It will be analyzed later.
20329         Vars.push_back(RefExpr);
20330       }
20331       ValueDecl *D = Res.first;
20332       if (!D)
20333         continue;
20334 
20335       if (OOK != OO_Plus && OOK != OO_Minus && (RHS || OOK != OO_None)) {
20336         Diag(OOLoc, diag::err_omp_depend_sink_expected_plus_minus);
20337         continue;
20338       }
20339       if (RHS) {
20340         ExprResult RHSRes = VerifyPositiveIntegerConstantInClause(
20341             RHS, OMPC_depend, /*StrictlyPositive=*/false);
20342         if (RHSRes.isInvalid())
20343           continue;
20344       }
20345       if (!CurContext->isDependentContext() &&
20346           DSAStack->getParentOrderedRegionParam().first &&
20347           DepCounter != DSAStack->isParentLoopControlVariable(D).first) {
20348         const ValueDecl *VD =
20349             DSAStack->getParentLoopControlVariable(DepCounter.getZExtValue());
20350         if (VD)
20351           Diag(ELoc, diag::err_omp_depend_sink_expected_loop_iteration)
20352               << 1 << VD;
20353         else
20354           Diag(ELoc, diag::err_omp_depend_sink_expected_loop_iteration) << 0;
20355         continue;
20356       }
20357       OpsOffs.emplace_back(RHS, OOK);
20358     } else {
20359       bool OMPDependTFound = LangOpts.OpenMP >= 50;
20360       if (OMPDependTFound)
20361         OMPDependTFound = findOMPDependT(*this, StartLoc, DSAStack,
20362                                          DepKind == OMPC_DEPEND_depobj);
20363       if (DepKind == OMPC_DEPEND_depobj) {
20364         // OpenMP 5.0, 2.17.11 depend Clause, Restrictions, C/C++
20365         // List items used in depend clauses with the depobj dependence type
20366         // must be expressions of the omp_depend_t type.
20367         if (!RefExpr->isValueDependent() && !RefExpr->isTypeDependent() &&
20368             !RefExpr->isInstantiationDependent() &&
20369             !RefExpr->containsUnexpandedParameterPack() &&
20370             (OMPDependTFound &&
20371              !Context.hasSameUnqualifiedType(DSAStack->getOMPDependT(),
20372                                              RefExpr->getType()))) {
20373           Diag(ELoc, diag::err_omp_expected_omp_depend_t_lvalue)
20374               << 0 << RefExpr->getType() << RefExpr->getSourceRange();
20375           continue;
20376         }
20377         if (!RefExpr->isLValue()) {
20378           Diag(ELoc, diag::err_omp_expected_omp_depend_t_lvalue)
20379               << 1 << RefExpr->getType() << RefExpr->getSourceRange();
20380           continue;
20381         }
20382       } else {
20383         // OpenMP 5.0 [2.17.11, Restrictions]
20384         // List items used in depend clauses cannot be zero-length array
20385         // sections.
20386         QualType ExprTy = RefExpr->getType().getNonReferenceType();
20387         const auto *OASE = dyn_cast<OMPArraySectionExpr>(SimpleExpr);
20388         if (OASE) {
20389           QualType BaseType =
20390               OMPArraySectionExpr::getBaseOriginalType(OASE->getBase());
20391           if (const auto *ATy = BaseType->getAsArrayTypeUnsafe())
20392             ExprTy = ATy->getElementType();
20393           else
20394             ExprTy = BaseType->getPointeeType();
20395           ExprTy = ExprTy.getNonReferenceType();
20396           const Expr *Length = OASE->getLength();
20397           Expr::EvalResult Result;
20398           if (Length && !Length->isValueDependent() &&
20399               Length->EvaluateAsInt(Result, Context) &&
20400               Result.Val.getInt().isZero()) {
20401             Diag(ELoc,
20402                  diag::err_omp_depend_zero_length_array_section_not_allowed)
20403                 << SimpleExpr->getSourceRange();
20404             continue;
20405           }
20406         }
20407 
20408         // OpenMP 5.0, 2.17.11 depend Clause, Restrictions, C/C++
20409         // List items used in depend clauses with the in, out, inout,
20410         // inoutset, or mutexinoutset dependence types cannot be
20411         // expressions of the omp_depend_t type.
20412         if (!RefExpr->isValueDependent() && !RefExpr->isTypeDependent() &&
20413             !RefExpr->isInstantiationDependent() &&
20414             !RefExpr->containsUnexpandedParameterPack() &&
20415             (!RefExpr->IgnoreParenImpCasts()->isLValue() ||
20416              (OMPDependTFound &&
20417               DSAStack->getOMPDependT().getTypePtr() == ExprTy.getTypePtr()))) {
20418           Diag(ELoc, diag::err_omp_expected_addressable_lvalue_or_array_item)
20419               << (LangOpts.OpenMP >= 50 ? 1 : 0)
20420               << (LangOpts.OpenMP >= 50 ? 1 : 0) << RefExpr->getSourceRange();
20421           continue;
20422         }
20423 
20424         auto *ASE = dyn_cast<ArraySubscriptExpr>(SimpleExpr);
20425         if (ASE && !ASE->getBase()->isTypeDependent() &&
20426             !ASE->getBase()->getType().getNonReferenceType()->isPointerType() &&
20427             !ASE->getBase()->getType().getNonReferenceType()->isArrayType()) {
20428           Diag(ELoc, diag::err_omp_expected_addressable_lvalue_or_array_item)
20429               << (LangOpts.OpenMP >= 50 ? 1 : 0)
20430               << (LangOpts.OpenMP >= 50 ? 1 : 0) << RefExpr->getSourceRange();
20431           continue;
20432         }
20433 
20434         ExprResult Res;
20435         {
20436           Sema::TentativeAnalysisScope Trap(*this);
20437           Res = CreateBuiltinUnaryOp(ELoc, UO_AddrOf,
20438                                      RefExpr->IgnoreParenImpCasts());
20439         }
20440         if (!Res.isUsable() && !isa<OMPArraySectionExpr>(SimpleExpr) &&
20441             !isa<OMPArrayShapingExpr>(SimpleExpr)) {
20442           Diag(ELoc, diag::err_omp_expected_addressable_lvalue_or_array_item)
20443               << (LangOpts.OpenMP >= 50 ? 1 : 0)
20444               << (LangOpts.OpenMP >= 50 ? 1 : 0) << RefExpr->getSourceRange();
20445           continue;
20446         }
20447       }
20448     }
20449     Vars.push_back(RefExpr->IgnoreParenImpCasts());
20450   }
20451 
20452   if (!CurContext->isDependentContext() && DepKind == OMPC_DEPEND_sink &&
20453       TotalDepCount > VarList.size() &&
20454       DSAStack->getParentOrderedRegionParam().first &&
20455       DSAStack->getParentLoopControlVariable(VarList.size() + 1)) {
20456     Diag(EndLoc, diag::err_omp_depend_sink_expected_loop_iteration)
20457         << 1 << DSAStack->getParentLoopControlVariable(VarList.size() + 1);
20458   }
20459   if (DepKind != OMPC_DEPEND_source && DepKind != OMPC_DEPEND_sink &&
20460       DepKind != OMPC_DEPEND_outallmemory &&
20461       DepKind != OMPC_DEPEND_inoutallmemory && Vars.empty())
20462     return nullptr;
20463 
20464   auto *C = OMPDependClause::Create(
20465       Context, StartLoc, LParenLoc, EndLoc,
20466       {DepKind, DepLoc, Data.ColonLoc, Data.OmpAllMemoryLoc}, DepModifier, Vars,
20467       TotalDepCount.getZExtValue());
20468   if ((DepKind == OMPC_DEPEND_sink || DepKind == OMPC_DEPEND_source) &&
20469       DSAStack->isParentOrderedRegion())
20470     DSAStack->addDoacrossDependClause(C, OpsOffs);
20471   return C;
20472 }
20473 
20474 OMPClause *Sema::ActOnOpenMPDeviceClause(OpenMPDeviceClauseModifier Modifier,
20475                                          Expr *Device, SourceLocation StartLoc,
20476                                          SourceLocation LParenLoc,
20477                                          SourceLocation ModifierLoc,
20478                                          SourceLocation EndLoc) {
20479   assert((ModifierLoc.isInvalid() || LangOpts.OpenMP >= 50) &&
20480          "Unexpected device modifier in OpenMP < 50.");
20481 
20482   bool ErrorFound = false;
20483   if (ModifierLoc.isValid() && Modifier == OMPC_DEVICE_unknown) {
20484     std::string Values =
20485         getListOfPossibleValues(OMPC_device, /*First=*/0, OMPC_DEVICE_unknown);
20486     Diag(ModifierLoc, diag::err_omp_unexpected_clause_value)
20487         << Values << getOpenMPClauseName(OMPC_device);
20488     ErrorFound = true;
20489   }
20490 
20491   Expr *ValExpr = Device;
20492   Stmt *HelperValStmt = nullptr;
20493 
20494   // OpenMP [2.9.1, Restrictions]
20495   // The device expression must evaluate to a non-negative integer value.
20496   ErrorFound = !isNonNegativeIntegerValue(ValExpr, *this, OMPC_device,
20497                                           /*StrictlyPositive=*/false) ||
20498                ErrorFound;
20499   if (ErrorFound)
20500     return nullptr;
20501 
20502   // OpenMP 5.0 [2.12.5, Restrictions]
20503   // In case of ancestor device-modifier, a requires directive with
20504   // the reverse_offload clause must be specified.
20505   if (Modifier == OMPC_DEVICE_ancestor) {
20506     if (!DSAStack->hasRequiresDeclWithClause<OMPReverseOffloadClause>()) {
20507       targetDiag(
20508           StartLoc,
20509           diag::err_omp_device_ancestor_without_requires_reverse_offload);
20510       ErrorFound = true;
20511     }
20512   }
20513 
20514   OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
20515   OpenMPDirectiveKind CaptureRegion =
20516       getOpenMPCaptureRegionForClause(DKind, OMPC_device, LangOpts.OpenMP);
20517   if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
20518     ValExpr = MakeFullExpr(ValExpr).get();
20519     llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
20520     ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
20521     HelperValStmt = buildPreInits(Context, Captures);
20522   }
20523 
20524   return new (Context)
20525       OMPDeviceClause(Modifier, ValExpr, HelperValStmt, CaptureRegion, StartLoc,
20526                       LParenLoc, ModifierLoc, EndLoc);
20527 }
20528 
20529 static bool checkTypeMappable(SourceLocation SL, SourceRange SR, Sema &SemaRef,
20530                               DSAStackTy *Stack, QualType QTy,
20531                               bool FullCheck = true) {
20532   if (SemaRef.RequireCompleteType(SL, QTy, diag::err_incomplete_type))
20533     return false;
20534   if (FullCheck && !SemaRef.CurContext->isDependentContext() &&
20535       !QTy.isTriviallyCopyableType(SemaRef.Context))
20536     SemaRef.Diag(SL, diag::warn_omp_non_trivial_type_mapped) << QTy << SR;
20537   return true;
20538 }
20539 
20540 /// Return true if it can be proven that the provided array expression
20541 /// (array section or array subscript) does NOT specify the whole size of the
20542 /// array whose base type is \a BaseQTy.
20543 static bool checkArrayExpressionDoesNotReferToWholeSize(Sema &SemaRef,
20544                                                         const Expr *E,
20545                                                         QualType BaseQTy) {
20546   const auto *OASE = dyn_cast<OMPArraySectionExpr>(E);
20547 
20548   // If this is an array subscript, it refers to the whole size if the size of
20549   // the dimension is constant and equals 1. Also, an array section assumes the
20550   // format of an array subscript if no colon is used.
20551   if (isa<ArraySubscriptExpr>(E) ||
20552       (OASE && OASE->getColonLocFirst().isInvalid())) {
20553     if (const auto *ATy = dyn_cast<ConstantArrayType>(BaseQTy.getTypePtr()))
20554       return ATy->getSize().getSExtValue() != 1;
20555     // Size can't be evaluated statically.
20556     return false;
20557   }
20558 
20559   assert(OASE && "Expecting array section if not an array subscript.");
20560   const Expr *LowerBound = OASE->getLowerBound();
20561   const Expr *Length = OASE->getLength();
20562 
20563   // If there is a lower bound that does not evaluates to zero, we are not
20564   // covering the whole dimension.
20565   if (LowerBound) {
20566     Expr::EvalResult Result;
20567     if (!LowerBound->EvaluateAsInt(Result, SemaRef.getASTContext()))
20568       return false; // Can't get the integer value as a constant.
20569 
20570     llvm::APSInt ConstLowerBound = Result.Val.getInt();
20571     if (ConstLowerBound.getSExtValue())
20572       return true;
20573   }
20574 
20575   // If we don't have a length we covering the whole dimension.
20576   if (!Length)
20577     return false;
20578 
20579   // If the base is a pointer, we don't have a way to get the size of the
20580   // pointee.
20581   if (BaseQTy->isPointerType())
20582     return false;
20583 
20584   // We can only check if the length is the same as the size of the dimension
20585   // if we have a constant array.
20586   const auto *CATy = dyn_cast<ConstantArrayType>(BaseQTy.getTypePtr());
20587   if (!CATy)
20588     return false;
20589 
20590   Expr::EvalResult Result;
20591   if (!Length->EvaluateAsInt(Result, SemaRef.getASTContext()))
20592     return false; // Can't get the integer value as a constant.
20593 
20594   llvm::APSInt ConstLength = Result.Val.getInt();
20595   return CATy->getSize().getSExtValue() != ConstLength.getSExtValue();
20596 }
20597 
20598 // Return true if it can be proven that the provided array expression (array
20599 // section or array subscript) does NOT specify a single element of the array
20600 // whose base type is \a BaseQTy.
20601 static bool checkArrayExpressionDoesNotReferToUnitySize(Sema &SemaRef,
20602                                                         const Expr *E,
20603                                                         QualType BaseQTy) {
20604   const auto *OASE = dyn_cast<OMPArraySectionExpr>(E);
20605 
20606   // An array subscript always refer to a single element. Also, an array section
20607   // assumes the format of an array subscript if no colon is used.
20608   if (isa<ArraySubscriptExpr>(E) ||
20609       (OASE && OASE->getColonLocFirst().isInvalid()))
20610     return false;
20611 
20612   assert(OASE && "Expecting array section if not an array subscript.");
20613   const Expr *Length = OASE->getLength();
20614 
20615   // If we don't have a length we have to check if the array has unitary size
20616   // for this dimension. Also, we should always expect a length if the base type
20617   // is pointer.
20618   if (!Length) {
20619     if (const auto *ATy = dyn_cast<ConstantArrayType>(BaseQTy.getTypePtr()))
20620       return ATy->getSize().getSExtValue() != 1;
20621     // We cannot assume anything.
20622     return false;
20623   }
20624 
20625   // Check if the length evaluates to 1.
20626   Expr::EvalResult Result;
20627   if (!Length->EvaluateAsInt(Result, SemaRef.getASTContext()))
20628     return false; // Can't get the integer value as a constant.
20629 
20630   llvm::APSInt ConstLength = Result.Val.getInt();
20631   return ConstLength.getSExtValue() != 1;
20632 }
20633 
20634 // The base of elements of list in a map clause have to be either:
20635 //  - a reference to variable or field.
20636 //  - a member expression.
20637 //  - an array expression.
20638 //
20639 // E.g. if we have the expression 'r.S.Arr[:12]', we want to retrieve the
20640 // reference to 'r'.
20641 //
20642 // If we have:
20643 //
20644 // struct SS {
20645 //   Bla S;
20646 //   foo() {
20647 //     #pragma omp target map (S.Arr[:12]);
20648 //   }
20649 // }
20650 //
20651 // We want to retrieve the member expression 'this->S';
20652 
20653 // OpenMP 5.0 [2.19.7.1, map Clause, Restrictions, p.2]
20654 //  If a list item is an array section, it must specify contiguous storage.
20655 //
20656 // For this restriction it is sufficient that we make sure only references
20657 // to variables or fields and array expressions, and that no array sections
20658 // exist except in the rightmost expression (unless they cover the whole
20659 // dimension of the array). E.g. these would be invalid:
20660 //
20661 //   r.ArrS[3:5].Arr[6:7]
20662 //
20663 //   r.ArrS[3:5].x
20664 //
20665 // but these would be valid:
20666 //   r.ArrS[3].Arr[6:7]
20667 //
20668 //   r.ArrS[3].x
20669 namespace {
20670 class MapBaseChecker final : public StmtVisitor<MapBaseChecker, bool> {
20671   Sema &SemaRef;
20672   OpenMPClauseKind CKind = OMPC_unknown;
20673   OpenMPDirectiveKind DKind = OMPD_unknown;
20674   OMPClauseMappableExprCommon::MappableExprComponentList &Components;
20675   bool IsNonContiguous = false;
20676   bool NoDiagnose = false;
20677   const Expr *RelevantExpr = nullptr;
20678   bool AllowUnitySizeArraySection = true;
20679   bool AllowWholeSizeArraySection = true;
20680   bool AllowAnotherPtr = true;
20681   SourceLocation ELoc;
20682   SourceRange ERange;
20683 
20684   void emitErrorMsg() {
20685     // If nothing else worked, this is not a valid map clause expression.
20686     if (SemaRef.getLangOpts().OpenMP < 50) {
20687       SemaRef.Diag(ELoc,
20688                    diag::err_omp_expected_named_var_member_or_array_expression)
20689           << ERange;
20690     } else {
20691       SemaRef.Diag(ELoc, diag::err_omp_non_lvalue_in_map_or_motion_clauses)
20692           << getOpenMPClauseName(CKind) << ERange;
20693     }
20694   }
20695 
20696 public:
20697   bool VisitDeclRefExpr(DeclRefExpr *DRE) {
20698     if (!isa<VarDecl>(DRE->getDecl())) {
20699       emitErrorMsg();
20700       return false;
20701     }
20702     assert(!RelevantExpr && "RelevantExpr is expected to be nullptr");
20703     RelevantExpr = DRE;
20704     // Record the component.
20705     Components.emplace_back(DRE, DRE->getDecl(), IsNonContiguous);
20706     return true;
20707   }
20708 
20709   bool VisitMemberExpr(MemberExpr *ME) {
20710     Expr *E = ME;
20711     Expr *BaseE = ME->getBase()->IgnoreParenCasts();
20712 
20713     if (isa<CXXThisExpr>(BaseE)) {
20714       assert(!RelevantExpr && "RelevantExpr is expected to be nullptr");
20715       // We found a base expression: this->Val.
20716       RelevantExpr = ME;
20717     } else {
20718       E = BaseE;
20719     }
20720 
20721     if (!isa<FieldDecl>(ME->getMemberDecl())) {
20722       if (!NoDiagnose) {
20723         SemaRef.Diag(ELoc, diag::err_omp_expected_access_to_data_field)
20724             << ME->getSourceRange();
20725         return false;
20726       }
20727       if (RelevantExpr)
20728         return false;
20729       return Visit(E);
20730     }
20731 
20732     auto *FD = cast<FieldDecl>(ME->getMemberDecl());
20733 
20734     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C/C++, p.3]
20735     //  A bit-field cannot appear in a map clause.
20736     //
20737     if (FD->isBitField()) {
20738       if (!NoDiagnose) {
20739         SemaRef.Diag(ELoc, diag::err_omp_bit_fields_forbidden_in_clause)
20740             << ME->getSourceRange() << getOpenMPClauseName(CKind);
20741         return false;
20742       }
20743       if (RelevantExpr)
20744         return false;
20745       return Visit(E);
20746     }
20747 
20748     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C++, p.1]
20749     //  If the type of a list item is a reference to a type T then the type
20750     //  will be considered to be T for all purposes of this clause.
20751     QualType CurType = BaseE->getType().getNonReferenceType();
20752 
20753     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C/C++, p.2]
20754     //  A list item cannot be a variable that is a member of a structure with
20755     //  a union type.
20756     //
20757     if (CurType->isUnionType()) {
20758       if (!NoDiagnose) {
20759         SemaRef.Diag(ELoc, diag::err_omp_union_type_not_allowed)
20760             << ME->getSourceRange();
20761         return false;
20762       }
20763       return RelevantExpr || Visit(E);
20764     }
20765 
20766     // If we got a member expression, we should not expect any array section
20767     // before that:
20768     //
20769     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.7]
20770     //  If a list item is an element of a structure, only the rightmost symbol
20771     //  of the variable reference can be an array section.
20772     //
20773     AllowUnitySizeArraySection = false;
20774     AllowWholeSizeArraySection = false;
20775 
20776     // Record the component.
20777     Components.emplace_back(ME, FD, IsNonContiguous);
20778     return RelevantExpr || Visit(E);
20779   }
20780 
20781   bool VisitArraySubscriptExpr(ArraySubscriptExpr *AE) {
20782     Expr *E = AE->getBase()->IgnoreParenImpCasts();
20783 
20784     if (!E->getType()->isAnyPointerType() && !E->getType()->isArrayType()) {
20785       if (!NoDiagnose) {
20786         SemaRef.Diag(ELoc, diag::err_omp_expected_base_var_name)
20787             << 0 << AE->getSourceRange();
20788         return false;
20789       }
20790       return RelevantExpr || Visit(E);
20791     }
20792 
20793     // If we got an array subscript that express the whole dimension we
20794     // can have any array expressions before. If it only expressing part of
20795     // the dimension, we can only have unitary-size array expressions.
20796     if (checkArrayExpressionDoesNotReferToWholeSize(SemaRef, AE, E->getType()))
20797       AllowWholeSizeArraySection = false;
20798 
20799     if (const auto *TE = dyn_cast<CXXThisExpr>(E->IgnoreParenCasts())) {
20800       Expr::EvalResult Result;
20801       if (!AE->getIdx()->isValueDependent() &&
20802           AE->getIdx()->EvaluateAsInt(Result, SemaRef.getASTContext()) &&
20803           !Result.Val.getInt().isZero()) {
20804         SemaRef.Diag(AE->getIdx()->getExprLoc(),
20805                      diag::err_omp_invalid_map_this_expr);
20806         SemaRef.Diag(AE->getIdx()->getExprLoc(),
20807                      diag::note_omp_invalid_subscript_on_this_ptr_map);
20808       }
20809       assert(!RelevantExpr && "RelevantExpr is expected to be nullptr");
20810       RelevantExpr = TE;
20811     }
20812 
20813     // Record the component - we don't have any declaration associated.
20814     Components.emplace_back(AE, nullptr, IsNonContiguous);
20815 
20816     return RelevantExpr || Visit(E);
20817   }
20818 
20819   bool VisitOMPArraySectionExpr(OMPArraySectionExpr *OASE) {
20820     // After OMP 5.0  Array section in reduction clause will be implicitly
20821     // mapped
20822     assert(!(SemaRef.getLangOpts().OpenMP < 50 && NoDiagnose) &&
20823            "Array sections cannot be implicitly mapped.");
20824     Expr *E = OASE->getBase()->IgnoreParenImpCasts();
20825     QualType CurType =
20826         OMPArraySectionExpr::getBaseOriginalType(E).getCanonicalType();
20827 
20828     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C++, p.1]
20829     //  If the type of a list item is a reference to a type T then the type
20830     //  will be considered to be T for all purposes of this clause.
20831     if (CurType->isReferenceType())
20832       CurType = CurType->getPointeeType();
20833 
20834     bool IsPointer = CurType->isAnyPointerType();
20835 
20836     if (!IsPointer && !CurType->isArrayType()) {
20837       SemaRef.Diag(ELoc, diag::err_omp_expected_base_var_name)
20838           << 0 << OASE->getSourceRange();
20839       return false;
20840     }
20841 
20842     bool NotWhole =
20843         checkArrayExpressionDoesNotReferToWholeSize(SemaRef, OASE, CurType);
20844     bool NotUnity =
20845         checkArrayExpressionDoesNotReferToUnitySize(SemaRef, OASE, CurType);
20846 
20847     if (AllowWholeSizeArraySection) {
20848       // Any array section is currently allowed. Allowing a whole size array
20849       // section implies allowing a unity array section as well.
20850       //
20851       // If this array section refers to the whole dimension we can still
20852       // accept other array sections before this one, except if the base is a
20853       // pointer. Otherwise, only unitary sections are accepted.
20854       if (NotWhole || IsPointer)
20855         AllowWholeSizeArraySection = false;
20856     } else if (DKind == OMPD_target_update &&
20857                SemaRef.getLangOpts().OpenMP >= 50) {
20858       if (IsPointer && !AllowAnotherPtr)
20859         SemaRef.Diag(ELoc, diag::err_omp_section_length_undefined)
20860             << /*array of unknown bound */ 1;
20861       else
20862         IsNonContiguous = true;
20863     } else if (AllowUnitySizeArraySection && NotUnity) {
20864       // A unity or whole array section is not allowed and that is not
20865       // compatible with the properties of the current array section.
20866       if (NoDiagnose)
20867         return false;
20868       SemaRef.Diag(ELoc,
20869                    diag::err_array_section_does_not_specify_contiguous_storage)
20870           << OASE->getSourceRange();
20871       return false;
20872     }
20873 
20874     if (IsPointer)
20875       AllowAnotherPtr = false;
20876 
20877     if (const auto *TE = dyn_cast<CXXThisExpr>(E)) {
20878       Expr::EvalResult ResultR;
20879       Expr::EvalResult ResultL;
20880       if (!OASE->getLength()->isValueDependent() &&
20881           OASE->getLength()->EvaluateAsInt(ResultR, SemaRef.getASTContext()) &&
20882           !ResultR.Val.getInt().isOne()) {
20883         SemaRef.Diag(OASE->getLength()->getExprLoc(),
20884                      diag::err_omp_invalid_map_this_expr);
20885         SemaRef.Diag(OASE->getLength()->getExprLoc(),
20886                      diag::note_omp_invalid_length_on_this_ptr_mapping);
20887       }
20888       if (OASE->getLowerBound() && !OASE->getLowerBound()->isValueDependent() &&
20889           OASE->getLowerBound()->EvaluateAsInt(ResultL,
20890                                                SemaRef.getASTContext()) &&
20891           !ResultL.Val.getInt().isZero()) {
20892         SemaRef.Diag(OASE->getLowerBound()->getExprLoc(),
20893                      diag::err_omp_invalid_map_this_expr);
20894         SemaRef.Diag(OASE->getLowerBound()->getExprLoc(),
20895                      diag::note_omp_invalid_lower_bound_on_this_ptr_mapping);
20896       }
20897       assert(!RelevantExpr && "RelevantExpr is expected to be nullptr");
20898       RelevantExpr = TE;
20899     }
20900 
20901     // Record the component - we don't have any declaration associated.
20902     Components.emplace_back(OASE, nullptr, /*IsNonContiguous=*/false);
20903     return RelevantExpr || Visit(E);
20904   }
20905   bool VisitOMPArrayShapingExpr(OMPArrayShapingExpr *E) {
20906     Expr *Base = E->getBase();
20907 
20908     // Record the component - we don't have any declaration associated.
20909     Components.emplace_back(E, nullptr, IsNonContiguous);
20910 
20911     return Visit(Base->IgnoreParenImpCasts());
20912   }
20913 
20914   bool VisitUnaryOperator(UnaryOperator *UO) {
20915     if (SemaRef.getLangOpts().OpenMP < 50 || !UO->isLValue() ||
20916         UO->getOpcode() != UO_Deref) {
20917       emitErrorMsg();
20918       return false;
20919     }
20920     if (!RelevantExpr) {
20921       // Record the component if haven't found base decl.
20922       Components.emplace_back(UO, nullptr, /*IsNonContiguous=*/false);
20923     }
20924     return RelevantExpr || Visit(UO->getSubExpr()->IgnoreParenImpCasts());
20925   }
20926   bool VisitBinaryOperator(BinaryOperator *BO) {
20927     if (SemaRef.getLangOpts().OpenMP < 50 || !BO->getType()->isPointerType()) {
20928       emitErrorMsg();
20929       return false;
20930     }
20931 
20932     // Pointer arithmetic is the only thing we expect to happen here so after we
20933     // make sure the binary operator is a pointer type, the we only thing need
20934     // to to is to visit the subtree that has the same type as root (so that we
20935     // know the other subtree is just an offset)
20936     Expr *LE = BO->getLHS()->IgnoreParenImpCasts();
20937     Expr *RE = BO->getRHS()->IgnoreParenImpCasts();
20938     Components.emplace_back(BO, nullptr, false);
20939     assert((LE->getType().getTypePtr() == BO->getType().getTypePtr() ||
20940             RE->getType().getTypePtr() == BO->getType().getTypePtr()) &&
20941            "Either LHS or RHS have base decl inside");
20942     if (BO->getType().getTypePtr() == LE->getType().getTypePtr())
20943       return RelevantExpr || Visit(LE);
20944     return RelevantExpr || Visit(RE);
20945   }
20946   bool VisitCXXThisExpr(CXXThisExpr *CTE) {
20947     assert(!RelevantExpr && "RelevantExpr is expected to be nullptr");
20948     RelevantExpr = CTE;
20949     Components.emplace_back(CTE, nullptr, IsNonContiguous);
20950     return true;
20951   }
20952   bool VisitCXXOperatorCallExpr(CXXOperatorCallExpr *COCE) {
20953     assert(!RelevantExpr && "RelevantExpr is expected to be nullptr");
20954     Components.emplace_back(COCE, nullptr, IsNonContiguous);
20955     return true;
20956   }
20957   bool VisitOpaqueValueExpr(OpaqueValueExpr *E) {
20958     Expr *Source = E->getSourceExpr();
20959     if (!Source) {
20960       emitErrorMsg();
20961       return false;
20962     }
20963     return Visit(Source);
20964   }
20965   bool VisitStmt(Stmt *) {
20966     emitErrorMsg();
20967     return false;
20968   }
20969   const Expr *getFoundBase() const { return RelevantExpr; }
20970   explicit MapBaseChecker(
20971       Sema &SemaRef, OpenMPClauseKind CKind, OpenMPDirectiveKind DKind,
20972       OMPClauseMappableExprCommon::MappableExprComponentList &Components,
20973       bool NoDiagnose, SourceLocation &ELoc, SourceRange &ERange)
20974       : SemaRef(SemaRef), CKind(CKind), DKind(DKind), Components(Components),
20975         NoDiagnose(NoDiagnose), ELoc(ELoc), ERange(ERange) {}
20976 };
20977 } // namespace
20978 
20979 /// Return the expression of the base of the mappable expression or null if it
20980 /// cannot be determined and do all the necessary checks to see if the
20981 /// expression is valid as a standalone mappable expression. In the process,
20982 /// record all the components of the expression.
20983 static const Expr *checkMapClauseExpressionBase(
20984     Sema &SemaRef, Expr *E,
20985     OMPClauseMappableExprCommon::MappableExprComponentList &CurComponents,
20986     OpenMPClauseKind CKind, OpenMPDirectiveKind DKind, bool NoDiagnose) {
20987   SourceLocation ELoc = E->getExprLoc();
20988   SourceRange ERange = E->getSourceRange();
20989   MapBaseChecker Checker(SemaRef, CKind, DKind, CurComponents, NoDiagnose, ELoc,
20990                          ERange);
20991   if (Checker.Visit(E->IgnoreParens())) {
20992     // Check if the highest dimension array section has length specified
20993     if (SemaRef.getLangOpts().OpenMP >= 50 && !CurComponents.empty() &&
20994         (CKind == OMPC_to || CKind == OMPC_from)) {
20995       auto CI = CurComponents.rbegin();
20996       auto CE = CurComponents.rend();
20997       for (; CI != CE; ++CI) {
20998         const auto *OASE =
20999             dyn_cast<OMPArraySectionExpr>(CI->getAssociatedExpression());
21000         if (!OASE)
21001           continue;
21002         if (OASE && OASE->getLength())
21003           break;
21004         SemaRef.Diag(ELoc, diag::err_array_section_does_not_specify_length)
21005             << ERange;
21006       }
21007     }
21008     return Checker.getFoundBase();
21009   }
21010   return nullptr;
21011 }
21012 
21013 // Return true if expression E associated with value VD has conflicts with other
21014 // map information.
21015 static bool checkMapConflicts(
21016     Sema &SemaRef, DSAStackTy *DSAS, const ValueDecl *VD, const Expr *E,
21017     bool CurrentRegionOnly,
21018     OMPClauseMappableExprCommon::MappableExprComponentListRef CurComponents,
21019     OpenMPClauseKind CKind) {
21020   assert(VD && E);
21021   SourceLocation ELoc = E->getExprLoc();
21022   SourceRange ERange = E->getSourceRange();
21023 
21024   // In order to easily check the conflicts we need to match each component of
21025   // the expression under test with the components of the expressions that are
21026   // already in the stack.
21027 
21028   assert(!CurComponents.empty() && "Map clause expression with no components!");
21029   assert(CurComponents.back().getAssociatedDeclaration() == VD &&
21030          "Map clause expression with unexpected base!");
21031 
21032   // Variables to help detecting enclosing problems in data environment nests.
21033   bool IsEnclosedByDataEnvironmentExpr = false;
21034   const Expr *EnclosingExpr = nullptr;
21035 
21036   bool FoundError = DSAS->checkMappableExprComponentListsForDecl(
21037       VD, CurrentRegionOnly,
21038       [&IsEnclosedByDataEnvironmentExpr, &SemaRef, VD, CurrentRegionOnly, ELoc,
21039        ERange, CKind, &EnclosingExpr,
21040        CurComponents](OMPClauseMappableExprCommon::MappableExprComponentListRef
21041                           StackComponents,
21042                       OpenMPClauseKind Kind) {
21043         if (CKind == Kind && SemaRef.LangOpts.OpenMP >= 50)
21044           return false;
21045         assert(!StackComponents.empty() &&
21046                "Map clause expression with no components!");
21047         assert(StackComponents.back().getAssociatedDeclaration() == VD &&
21048                "Map clause expression with unexpected base!");
21049         (void)VD;
21050 
21051         // The whole expression in the stack.
21052         const Expr *RE = StackComponents.front().getAssociatedExpression();
21053 
21054         // Expressions must start from the same base. Here we detect at which
21055         // point both expressions diverge from each other and see if we can
21056         // detect if the memory referred to both expressions is contiguous and
21057         // do not overlap.
21058         auto CI = CurComponents.rbegin();
21059         auto CE = CurComponents.rend();
21060         auto SI = StackComponents.rbegin();
21061         auto SE = StackComponents.rend();
21062         for (; CI != CE && SI != SE; ++CI, ++SI) {
21063 
21064           // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.3]
21065           //  At most one list item can be an array item derived from a given
21066           //  variable in map clauses of the same construct.
21067           if (CurrentRegionOnly &&
21068               (isa<ArraySubscriptExpr>(CI->getAssociatedExpression()) ||
21069                isa<OMPArraySectionExpr>(CI->getAssociatedExpression()) ||
21070                isa<OMPArrayShapingExpr>(CI->getAssociatedExpression())) &&
21071               (isa<ArraySubscriptExpr>(SI->getAssociatedExpression()) ||
21072                isa<OMPArraySectionExpr>(SI->getAssociatedExpression()) ||
21073                isa<OMPArrayShapingExpr>(SI->getAssociatedExpression()))) {
21074             SemaRef.Diag(CI->getAssociatedExpression()->getExprLoc(),
21075                          diag::err_omp_multiple_array_items_in_map_clause)
21076                 << CI->getAssociatedExpression()->getSourceRange();
21077             SemaRef.Diag(SI->getAssociatedExpression()->getExprLoc(),
21078                          diag::note_used_here)
21079                 << SI->getAssociatedExpression()->getSourceRange();
21080             return true;
21081           }
21082 
21083           // Do both expressions have the same kind?
21084           if (CI->getAssociatedExpression()->getStmtClass() !=
21085               SI->getAssociatedExpression()->getStmtClass())
21086             break;
21087 
21088           // Are we dealing with different variables/fields?
21089           if (CI->getAssociatedDeclaration() != SI->getAssociatedDeclaration())
21090             break;
21091         }
21092         // Check if the extra components of the expressions in the enclosing
21093         // data environment are redundant for the current base declaration.
21094         // If they are, the maps completely overlap, which is legal.
21095         for (; SI != SE; ++SI) {
21096           QualType Type;
21097           if (const auto *ASE =
21098                   dyn_cast<ArraySubscriptExpr>(SI->getAssociatedExpression())) {
21099             Type = ASE->getBase()->IgnoreParenImpCasts()->getType();
21100           } else if (const auto *OASE = dyn_cast<OMPArraySectionExpr>(
21101                          SI->getAssociatedExpression())) {
21102             const Expr *E = OASE->getBase()->IgnoreParenImpCasts();
21103             Type =
21104                 OMPArraySectionExpr::getBaseOriginalType(E).getCanonicalType();
21105           } else if (const auto *OASE = dyn_cast<OMPArrayShapingExpr>(
21106                          SI->getAssociatedExpression())) {
21107             Type = OASE->getBase()->getType()->getPointeeType();
21108           }
21109           if (Type.isNull() || Type->isAnyPointerType() ||
21110               checkArrayExpressionDoesNotReferToWholeSize(
21111                   SemaRef, SI->getAssociatedExpression(), Type))
21112             break;
21113         }
21114 
21115         // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.4]
21116         //  List items of map clauses in the same construct must not share
21117         //  original storage.
21118         //
21119         // If the expressions are exactly the same or one is a subset of the
21120         // other, it means they are sharing storage.
21121         if (CI == CE && SI == SE) {
21122           if (CurrentRegionOnly) {
21123             if (CKind == OMPC_map) {
21124               SemaRef.Diag(ELoc, diag::err_omp_map_shared_storage) << ERange;
21125             } else {
21126               assert(CKind == OMPC_to || CKind == OMPC_from);
21127               SemaRef.Diag(ELoc, diag::err_omp_once_referenced_in_target_update)
21128                   << ERange;
21129             }
21130             SemaRef.Diag(RE->getExprLoc(), diag::note_used_here)
21131                 << RE->getSourceRange();
21132             return true;
21133           }
21134           // If we find the same expression in the enclosing data environment,
21135           // that is legal.
21136           IsEnclosedByDataEnvironmentExpr = true;
21137           return false;
21138         }
21139 
21140         QualType DerivedType =
21141             std::prev(CI)->getAssociatedDeclaration()->getType();
21142         SourceLocation DerivedLoc =
21143             std::prev(CI)->getAssociatedExpression()->getExprLoc();
21144 
21145         // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C++, p.1]
21146         //  If the type of a list item is a reference to a type T then the type
21147         //  will be considered to be T for all purposes of this clause.
21148         DerivedType = DerivedType.getNonReferenceType();
21149 
21150         // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C/C++, p.1]
21151         //  A variable for which the type is pointer and an array section
21152         //  derived from that variable must not appear as list items of map
21153         //  clauses of the same construct.
21154         //
21155         // Also, cover one of the cases in:
21156         // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.5]
21157         //  If any part of the original storage of a list item has corresponding
21158         //  storage in the device data environment, all of the original storage
21159         //  must have corresponding storage in the device data environment.
21160         //
21161         if (DerivedType->isAnyPointerType()) {
21162           if (CI == CE || SI == SE) {
21163             SemaRef.Diag(
21164                 DerivedLoc,
21165                 diag::err_omp_pointer_mapped_along_with_derived_section)
21166                 << DerivedLoc;
21167             SemaRef.Diag(RE->getExprLoc(), diag::note_used_here)
21168                 << RE->getSourceRange();
21169             return true;
21170           }
21171           if (CI->getAssociatedExpression()->getStmtClass() !=
21172                   SI->getAssociatedExpression()->getStmtClass() ||
21173               CI->getAssociatedDeclaration()->getCanonicalDecl() ==
21174                   SI->getAssociatedDeclaration()->getCanonicalDecl()) {
21175             assert(CI != CE && SI != SE);
21176             SemaRef.Diag(DerivedLoc, diag::err_omp_same_pointer_dereferenced)
21177                 << DerivedLoc;
21178             SemaRef.Diag(RE->getExprLoc(), diag::note_used_here)
21179                 << RE->getSourceRange();
21180             return true;
21181           }
21182         }
21183 
21184         // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.4]
21185         //  List items of map clauses in the same construct must not share
21186         //  original storage.
21187         //
21188         // An expression is a subset of the other.
21189         if (CurrentRegionOnly && (CI == CE || SI == SE)) {
21190           if (CKind == OMPC_map) {
21191             if (CI != CE || SI != SE) {
21192               // Allow constructs like this: map(s, s.ptr[0:1]), where s.ptr is
21193               // a pointer.
21194               auto Begin =
21195                   CI != CE ? CurComponents.begin() : StackComponents.begin();
21196               auto End = CI != CE ? CurComponents.end() : StackComponents.end();
21197               auto It = Begin;
21198               while (It != End && !It->getAssociatedDeclaration())
21199                 std::advance(It, 1);
21200               assert(It != End &&
21201                      "Expected at least one component with the declaration.");
21202               if (It != Begin && It->getAssociatedDeclaration()
21203                                      ->getType()
21204                                      .getCanonicalType()
21205                                      ->isAnyPointerType()) {
21206                 IsEnclosedByDataEnvironmentExpr = false;
21207                 EnclosingExpr = nullptr;
21208                 return false;
21209               }
21210             }
21211             SemaRef.Diag(ELoc, diag::err_omp_map_shared_storage) << ERange;
21212           } else {
21213             assert(CKind == OMPC_to || CKind == OMPC_from);
21214             SemaRef.Diag(ELoc, diag::err_omp_once_referenced_in_target_update)
21215                 << ERange;
21216           }
21217           SemaRef.Diag(RE->getExprLoc(), diag::note_used_here)
21218               << RE->getSourceRange();
21219           return true;
21220         }
21221 
21222         // The current expression uses the same base as other expression in the
21223         // data environment but does not contain it completely.
21224         if (!CurrentRegionOnly && SI != SE)
21225           EnclosingExpr = RE;
21226 
21227         // The current expression is a subset of the expression in the data
21228         // environment.
21229         IsEnclosedByDataEnvironmentExpr |=
21230             (!CurrentRegionOnly && CI != CE && SI == SE);
21231 
21232         return false;
21233       });
21234 
21235   if (CurrentRegionOnly)
21236     return FoundError;
21237 
21238   // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.5]
21239   //  If any part of the original storage of a list item has corresponding
21240   //  storage in the device data environment, all of the original storage must
21241   //  have corresponding storage in the device data environment.
21242   // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.6]
21243   //  If a list item is an element of a structure, and a different element of
21244   //  the structure has a corresponding list item in the device data environment
21245   //  prior to a task encountering the construct associated with the map clause,
21246   //  then the list item must also have a corresponding list item in the device
21247   //  data environment prior to the task encountering the construct.
21248   //
21249   if (EnclosingExpr && !IsEnclosedByDataEnvironmentExpr) {
21250     SemaRef.Diag(ELoc,
21251                  diag::err_omp_original_storage_is_shared_and_does_not_contain)
21252         << ERange;
21253     SemaRef.Diag(EnclosingExpr->getExprLoc(), diag::note_used_here)
21254         << EnclosingExpr->getSourceRange();
21255     return true;
21256   }
21257 
21258   return FoundError;
21259 }
21260 
21261 // Look up the user-defined mapper given the mapper name and mapped type, and
21262 // build a reference to it.
21263 static ExprResult buildUserDefinedMapperRef(Sema &SemaRef, Scope *S,
21264                                             CXXScopeSpec &MapperIdScopeSpec,
21265                                             const DeclarationNameInfo &MapperId,
21266                                             QualType Type,
21267                                             Expr *UnresolvedMapper) {
21268   if (MapperIdScopeSpec.isInvalid())
21269     return ExprError();
21270   // Get the actual type for the array type.
21271   if (Type->isArrayType()) {
21272     assert(Type->getAsArrayTypeUnsafe() && "Expect to get a valid array type");
21273     Type = Type->getAsArrayTypeUnsafe()->getElementType().getCanonicalType();
21274   }
21275   // Find all user-defined mappers with the given MapperId.
21276   SmallVector<UnresolvedSet<8>, 4> Lookups;
21277   LookupResult Lookup(SemaRef, MapperId, Sema::LookupOMPMapperName);
21278   Lookup.suppressDiagnostics();
21279   if (S) {
21280     while (S && SemaRef.LookupParsedName(Lookup, S, &MapperIdScopeSpec)) {
21281       NamedDecl *D = Lookup.getRepresentativeDecl();
21282       while (S && !S->isDeclScope(D))
21283         S = S->getParent();
21284       if (S)
21285         S = S->getParent();
21286       Lookups.emplace_back();
21287       Lookups.back().append(Lookup.begin(), Lookup.end());
21288       Lookup.clear();
21289     }
21290   } else if (auto *ULE = cast_or_null<UnresolvedLookupExpr>(UnresolvedMapper)) {
21291     // Extract the user-defined mappers with the given MapperId.
21292     Lookups.push_back(UnresolvedSet<8>());
21293     for (NamedDecl *D : ULE->decls()) {
21294       auto *DMD = cast<OMPDeclareMapperDecl>(D);
21295       assert(DMD && "Expect valid OMPDeclareMapperDecl during instantiation.");
21296       Lookups.back().addDecl(DMD);
21297     }
21298   }
21299   // Defer the lookup for dependent types. The results will be passed through
21300   // UnresolvedMapper on instantiation.
21301   if (SemaRef.CurContext->isDependentContext() || Type->isDependentType() ||
21302       Type->isInstantiationDependentType() ||
21303       Type->containsUnexpandedParameterPack() ||
21304       filterLookupForUDReductionAndMapper<bool>(Lookups, [](ValueDecl *D) {
21305         return !D->isInvalidDecl() &&
21306                (D->getType()->isDependentType() ||
21307                 D->getType()->isInstantiationDependentType() ||
21308                 D->getType()->containsUnexpandedParameterPack());
21309       })) {
21310     UnresolvedSet<8> URS;
21311     for (const UnresolvedSet<8> &Set : Lookups) {
21312       if (Set.empty())
21313         continue;
21314       URS.append(Set.begin(), Set.end());
21315     }
21316     return UnresolvedLookupExpr::Create(
21317         SemaRef.Context, /*NamingClass=*/nullptr,
21318         MapperIdScopeSpec.getWithLocInContext(SemaRef.Context), MapperId,
21319         /*ADL=*/false, /*Overloaded=*/true, URS.begin(), URS.end());
21320   }
21321   SourceLocation Loc = MapperId.getLoc();
21322   // [OpenMP 5.0], 2.19.7.3 declare mapper Directive, Restrictions
21323   //  The type must be of struct, union or class type in C and C++
21324   if (!Type->isStructureOrClassType() && !Type->isUnionType() &&
21325       (MapperIdScopeSpec.isSet() || MapperId.getAsString() != "default")) {
21326     SemaRef.Diag(Loc, diag::err_omp_mapper_wrong_type);
21327     return ExprError();
21328   }
21329   // Perform argument dependent lookup.
21330   if (SemaRef.getLangOpts().CPlusPlus && !MapperIdScopeSpec.isSet())
21331     argumentDependentLookup(SemaRef, MapperId, Loc, Type, Lookups);
21332   // Return the first user-defined mapper with the desired type.
21333   if (auto *VD = filterLookupForUDReductionAndMapper<ValueDecl *>(
21334           Lookups, [&SemaRef, Type](ValueDecl *D) -> ValueDecl * {
21335             if (!D->isInvalidDecl() &&
21336                 SemaRef.Context.hasSameType(D->getType(), Type))
21337               return D;
21338             return nullptr;
21339           }))
21340     return SemaRef.BuildDeclRefExpr(VD, Type, VK_LValue, Loc);
21341   // Find the first user-defined mapper with a type derived from the desired
21342   // type.
21343   if (auto *VD = filterLookupForUDReductionAndMapper<ValueDecl *>(
21344           Lookups, [&SemaRef, Type, Loc](ValueDecl *D) -> ValueDecl * {
21345             if (!D->isInvalidDecl() &&
21346                 SemaRef.IsDerivedFrom(Loc, Type, D->getType()) &&
21347                 !Type.isMoreQualifiedThan(D->getType()))
21348               return D;
21349             return nullptr;
21350           })) {
21351     CXXBasePaths Paths(/*FindAmbiguities=*/true, /*RecordPaths=*/true,
21352                        /*DetectVirtual=*/false);
21353     if (SemaRef.IsDerivedFrom(Loc, Type, VD->getType(), Paths)) {
21354       if (!Paths.isAmbiguous(SemaRef.Context.getCanonicalType(
21355               VD->getType().getUnqualifiedType()))) {
21356         if (SemaRef.CheckBaseClassAccess(
21357                 Loc, VD->getType(), Type, Paths.front(),
21358                 /*DiagID=*/0) != Sema::AR_inaccessible) {
21359           return SemaRef.BuildDeclRefExpr(VD, Type, VK_LValue, Loc);
21360         }
21361       }
21362     }
21363   }
21364   // Report error if a mapper is specified, but cannot be found.
21365   if (MapperIdScopeSpec.isSet() || MapperId.getAsString() != "default") {
21366     SemaRef.Diag(Loc, diag::err_omp_invalid_mapper)
21367         << Type << MapperId.getName();
21368     return ExprError();
21369   }
21370   return ExprEmpty();
21371 }
21372 
21373 namespace {
21374 // Utility struct that gathers all the related lists associated with a mappable
21375 // expression.
21376 struct MappableVarListInfo {
21377   // The list of expressions.
21378   ArrayRef<Expr *> VarList;
21379   // The list of processed expressions.
21380   SmallVector<Expr *, 16> ProcessedVarList;
21381   // The mappble components for each expression.
21382   OMPClauseMappableExprCommon::MappableExprComponentLists VarComponents;
21383   // The base declaration of the variable.
21384   SmallVector<ValueDecl *, 16> VarBaseDeclarations;
21385   // The reference to the user-defined mapper associated with every expression.
21386   SmallVector<Expr *, 16> UDMapperList;
21387 
21388   MappableVarListInfo(ArrayRef<Expr *> VarList) : VarList(VarList) {
21389     // We have a list of components and base declarations for each entry in the
21390     // variable list.
21391     VarComponents.reserve(VarList.size());
21392     VarBaseDeclarations.reserve(VarList.size());
21393   }
21394 };
21395 } // namespace
21396 
21397 // Check the validity of the provided variable list for the provided clause kind
21398 // \a CKind. In the check process the valid expressions, mappable expression
21399 // components, variables, and user-defined mappers are extracted and used to
21400 // fill \a ProcessedVarList, \a VarComponents, \a VarBaseDeclarations, and \a
21401 // UDMapperList in MVLI. \a MapType, \a IsMapTypeImplicit, \a MapperIdScopeSpec,
21402 // and \a MapperId are expected to be valid if the clause kind is 'map'.
21403 static void checkMappableExpressionList(
21404     Sema &SemaRef, DSAStackTy *DSAS, OpenMPClauseKind CKind,
21405     MappableVarListInfo &MVLI, SourceLocation StartLoc,
21406     CXXScopeSpec &MapperIdScopeSpec, DeclarationNameInfo MapperId,
21407     ArrayRef<Expr *> UnresolvedMappers,
21408     OpenMPMapClauseKind MapType = OMPC_MAP_unknown,
21409     ArrayRef<OpenMPMapModifierKind> Modifiers = None,
21410     bool IsMapTypeImplicit = false, bool NoDiagnose = false) {
21411   // We only expect mappable expressions in 'to', 'from', and 'map' clauses.
21412   assert((CKind == OMPC_map || CKind == OMPC_to || CKind == OMPC_from) &&
21413          "Unexpected clause kind with mappable expressions!");
21414 
21415   // If the identifier of user-defined mapper is not specified, it is "default".
21416   // We do not change the actual name in this clause to distinguish whether a
21417   // mapper is specified explicitly, i.e., it is not explicitly specified when
21418   // MapperId.getName() is empty.
21419   if (!MapperId.getName() || MapperId.getName().isEmpty()) {
21420     auto &DeclNames = SemaRef.getASTContext().DeclarationNames;
21421     MapperId.setName(DeclNames.getIdentifier(
21422         &SemaRef.getASTContext().Idents.get("default")));
21423     MapperId.setLoc(StartLoc);
21424   }
21425 
21426   // Iterators to find the current unresolved mapper expression.
21427   auto UMIt = UnresolvedMappers.begin(), UMEnd = UnresolvedMappers.end();
21428   bool UpdateUMIt = false;
21429   Expr *UnresolvedMapper = nullptr;
21430 
21431   bool HasHoldModifier =
21432       llvm::is_contained(Modifiers, OMPC_MAP_MODIFIER_ompx_hold);
21433 
21434   // Keep track of the mappable components and base declarations in this clause.
21435   // Each entry in the list is going to have a list of components associated. We
21436   // record each set of the components so that we can build the clause later on.
21437   // In the end we should have the same amount of declarations and component
21438   // lists.
21439 
21440   for (Expr *RE : MVLI.VarList) {
21441     assert(RE && "Null expr in omp to/from/map clause");
21442     SourceLocation ELoc = RE->getExprLoc();
21443 
21444     // Find the current unresolved mapper expression.
21445     if (UpdateUMIt && UMIt != UMEnd) {
21446       UMIt++;
21447       assert(
21448           UMIt != UMEnd &&
21449           "Expect the size of UnresolvedMappers to match with that of VarList");
21450     }
21451     UpdateUMIt = true;
21452     if (UMIt != UMEnd)
21453       UnresolvedMapper = *UMIt;
21454 
21455     const Expr *VE = RE->IgnoreParenLValueCasts();
21456 
21457     if (VE->isValueDependent() || VE->isTypeDependent() ||
21458         VE->isInstantiationDependent() ||
21459         VE->containsUnexpandedParameterPack()) {
21460       // Try to find the associated user-defined mapper.
21461       ExprResult ER = buildUserDefinedMapperRef(
21462           SemaRef, DSAS->getCurScope(), MapperIdScopeSpec, MapperId,
21463           VE->getType().getCanonicalType(), UnresolvedMapper);
21464       if (ER.isInvalid())
21465         continue;
21466       MVLI.UDMapperList.push_back(ER.get());
21467       // We can only analyze this information once the missing information is
21468       // resolved.
21469       MVLI.ProcessedVarList.push_back(RE);
21470       continue;
21471     }
21472 
21473     Expr *SimpleExpr = RE->IgnoreParenCasts();
21474 
21475     if (!RE->isLValue()) {
21476       if (SemaRef.getLangOpts().OpenMP < 50) {
21477         SemaRef.Diag(
21478             ELoc, diag::err_omp_expected_named_var_member_or_array_expression)
21479             << RE->getSourceRange();
21480       } else {
21481         SemaRef.Diag(ELoc, diag::err_omp_non_lvalue_in_map_or_motion_clauses)
21482             << getOpenMPClauseName(CKind) << RE->getSourceRange();
21483       }
21484       continue;
21485     }
21486 
21487     OMPClauseMappableExprCommon::MappableExprComponentList CurComponents;
21488     ValueDecl *CurDeclaration = nullptr;
21489 
21490     // Obtain the array or member expression bases if required. Also, fill the
21491     // components array with all the components identified in the process.
21492     const Expr *BE =
21493         checkMapClauseExpressionBase(SemaRef, SimpleExpr, CurComponents, CKind,
21494                                      DSAS->getCurrentDirective(), NoDiagnose);
21495     if (!BE)
21496       continue;
21497 
21498     assert(!CurComponents.empty() &&
21499            "Invalid mappable expression information.");
21500 
21501     if (const auto *TE = dyn_cast<CXXThisExpr>(BE)) {
21502       // Add store "this" pointer to class in DSAStackTy for future checking
21503       DSAS->addMappedClassesQualTypes(TE->getType());
21504       // Try to find the associated user-defined mapper.
21505       ExprResult ER = buildUserDefinedMapperRef(
21506           SemaRef, DSAS->getCurScope(), MapperIdScopeSpec, MapperId,
21507           VE->getType().getCanonicalType(), UnresolvedMapper);
21508       if (ER.isInvalid())
21509         continue;
21510       MVLI.UDMapperList.push_back(ER.get());
21511       // Skip restriction checking for variable or field declarations
21512       MVLI.ProcessedVarList.push_back(RE);
21513       MVLI.VarComponents.resize(MVLI.VarComponents.size() + 1);
21514       MVLI.VarComponents.back().append(CurComponents.begin(),
21515                                        CurComponents.end());
21516       MVLI.VarBaseDeclarations.push_back(nullptr);
21517       continue;
21518     }
21519 
21520     // For the following checks, we rely on the base declaration which is
21521     // expected to be associated with the last component. The declaration is
21522     // expected to be a variable or a field (if 'this' is being mapped).
21523     CurDeclaration = CurComponents.back().getAssociatedDeclaration();
21524     assert(CurDeclaration && "Null decl on map clause.");
21525     assert(
21526         CurDeclaration->isCanonicalDecl() &&
21527         "Expecting components to have associated only canonical declarations.");
21528 
21529     auto *VD = dyn_cast<VarDecl>(CurDeclaration);
21530     const auto *FD = dyn_cast<FieldDecl>(CurDeclaration);
21531 
21532     assert((VD || FD) && "Only variables or fields are expected here!");
21533     (void)FD;
21534 
21535     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.10]
21536     // threadprivate variables cannot appear in a map clause.
21537     // OpenMP 4.5 [2.10.5, target update Construct]
21538     // threadprivate variables cannot appear in a from clause.
21539     if (VD && DSAS->isThreadPrivate(VD)) {
21540       if (NoDiagnose)
21541         continue;
21542       DSAStackTy::DSAVarData DVar = DSAS->getTopDSA(VD, /*FromParent=*/false);
21543       SemaRef.Diag(ELoc, diag::err_omp_threadprivate_in_clause)
21544           << getOpenMPClauseName(CKind);
21545       reportOriginalDsa(SemaRef, DSAS, VD, DVar);
21546       continue;
21547     }
21548 
21549     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.9]
21550     //  A list item cannot appear in both a map clause and a data-sharing
21551     //  attribute clause on the same construct.
21552 
21553     // Check conflicts with other map clause expressions. We check the conflicts
21554     // with the current construct separately from the enclosing data
21555     // environment, because the restrictions are different. We only have to
21556     // check conflicts across regions for the map clauses.
21557     if (checkMapConflicts(SemaRef, DSAS, CurDeclaration, SimpleExpr,
21558                           /*CurrentRegionOnly=*/true, CurComponents, CKind))
21559       break;
21560     if (CKind == OMPC_map &&
21561         (SemaRef.getLangOpts().OpenMP <= 45 || StartLoc.isValid()) &&
21562         checkMapConflicts(SemaRef, DSAS, CurDeclaration, SimpleExpr,
21563                           /*CurrentRegionOnly=*/false, CurComponents, CKind))
21564       break;
21565 
21566     // OpenMP 4.5 [2.10.5, target update Construct]
21567     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, C++, p.1]
21568     //  If the type of a list item is a reference to a type T then the type will
21569     //  be considered to be T for all purposes of this clause.
21570     auto I = llvm::find_if(
21571         CurComponents,
21572         [](const OMPClauseMappableExprCommon::MappableComponent &MC) {
21573           return MC.getAssociatedDeclaration();
21574         });
21575     assert(I != CurComponents.end() && "Null decl on map clause.");
21576     (void)I;
21577     QualType Type;
21578     auto *ASE = dyn_cast<ArraySubscriptExpr>(VE->IgnoreParens());
21579     auto *OASE = dyn_cast<OMPArraySectionExpr>(VE->IgnoreParens());
21580     auto *OAShE = dyn_cast<OMPArrayShapingExpr>(VE->IgnoreParens());
21581     if (ASE) {
21582       Type = ASE->getType().getNonReferenceType();
21583     } else if (OASE) {
21584       QualType BaseType =
21585           OMPArraySectionExpr::getBaseOriginalType(OASE->getBase());
21586       if (const auto *ATy = BaseType->getAsArrayTypeUnsafe())
21587         Type = ATy->getElementType();
21588       else
21589         Type = BaseType->getPointeeType();
21590       Type = Type.getNonReferenceType();
21591     } else if (OAShE) {
21592       Type = OAShE->getBase()->getType()->getPointeeType();
21593     } else {
21594       Type = VE->getType();
21595     }
21596 
21597     // OpenMP 4.5 [2.10.5, target update Construct, Restrictions, p.4]
21598     // A list item in a to or from clause must have a mappable type.
21599     // OpenMP 4.5 [2.15.5.1, map Clause, Restrictions, p.9]
21600     //  A list item must have a mappable type.
21601     if (!checkTypeMappable(VE->getExprLoc(), VE->getSourceRange(), SemaRef,
21602                            DSAS, Type, /*FullCheck=*/true))
21603       continue;
21604 
21605     if (CKind == OMPC_map) {
21606       // target enter data
21607       // OpenMP [2.10.2, Restrictions, p. 99]
21608       // A map-type must be specified in all map clauses and must be either
21609       // to or alloc.
21610       OpenMPDirectiveKind DKind = DSAS->getCurrentDirective();
21611       if (DKind == OMPD_target_enter_data &&
21612           !(MapType == OMPC_MAP_to || MapType == OMPC_MAP_alloc)) {
21613         SemaRef.Diag(StartLoc, diag::err_omp_invalid_map_type_for_directive)
21614             << (IsMapTypeImplicit ? 1 : 0)
21615             << getOpenMPSimpleClauseTypeName(OMPC_map, MapType)
21616             << getOpenMPDirectiveName(DKind);
21617         continue;
21618       }
21619 
21620       // target exit_data
21621       // OpenMP [2.10.3, Restrictions, p. 102]
21622       // A map-type must be specified in all map clauses and must be either
21623       // from, release, or delete.
21624       if (DKind == OMPD_target_exit_data &&
21625           !(MapType == OMPC_MAP_from || MapType == OMPC_MAP_release ||
21626             MapType == OMPC_MAP_delete)) {
21627         SemaRef.Diag(StartLoc, diag::err_omp_invalid_map_type_for_directive)
21628             << (IsMapTypeImplicit ? 1 : 0)
21629             << getOpenMPSimpleClauseTypeName(OMPC_map, MapType)
21630             << getOpenMPDirectiveName(DKind);
21631         continue;
21632       }
21633 
21634       // The 'ompx_hold' modifier is specifically intended to be used on a
21635       // 'target' or 'target data' directive to prevent data from being unmapped
21636       // during the associated statement.  It is not permitted on a 'target
21637       // enter data' or 'target exit data' directive, which have no associated
21638       // statement.
21639       if ((DKind == OMPD_target_enter_data || DKind == OMPD_target_exit_data) &&
21640           HasHoldModifier) {
21641         SemaRef.Diag(StartLoc,
21642                      diag::err_omp_invalid_map_type_modifier_for_directive)
21643             << getOpenMPSimpleClauseTypeName(OMPC_map,
21644                                              OMPC_MAP_MODIFIER_ompx_hold)
21645             << getOpenMPDirectiveName(DKind);
21646         continue;
21647       }
21648 
21649       // target, target data
21650       // OpenMP 5.0 [2.12.2, Restrictions, p. 163]
21651       // OpenMP 5.0 [2.12.5, Restrictions, p. 174]
21652       // A map-type in a map clause must be to, from, tofrom or alloc
21653       if ((DKind == OMPD_target_data ||
21654            isOpenMPTargetExecutionDirective(DKind)) &&
21655           !(MapType == OMPC_MAP_to || MapType == OMPC_MAP_from ||
21656             MapType == OMPC_MAP_tofrom || MapType == OMPC_MAP_alloc)) {
21657         SemaRef.Diag(StartLoc, diag::err_omp_invalid_map_type_for_directive)
21658             << (IsMapTypeImplicit ? 1 : 0)
21659             << getOpenMPSimpleClauseTypeName(OMPC_map, MapType)
21660             << getOpenMPDirectiveName(DKind);
21661         continue;
21662       }
21663 
21664       // OpenMP 4.5 [2.15.5.1, Restrictions, p.3]
21665       // A list item cannot appear in both a map clause and a data-sharing
21666       // attribute clause on the same construct
21667       //
21668       // OpenMP 5.0 [2.19.7.1, Restrictions, p.7]
21669       // A list item cannot appear in both a map clause and a data-sharing
21670       // attribute clause on the same construct unless the construct is a
21671       // combined construct.
21672       if (VD && ((SemaRef.LangOpts.OpenMP <= 45 &&
21673                   isOpenMPTargetExecutionDirective(DKind)) ||
21674                  DKind == OMPD_target)) {
21675         DSAStackTy::DSAVarData DVar = DSAS->getTopDSA(VD, /*FromParent=*/false);
21676         if (isOpenMPPrivate(DVar.CKind)) {
21677           SemaRef.Diag(ELoc, diag::err_omp_variable_in_given_clause_and_dsa)
21678               << getOpenMPClauseName(DVar.CKind)
21679               << getOpenMPClauseName(OMPC_map)
21680               << getOpenMPDirectiveName(DSAS->getCurrentDirective());
21681           reportOriginalDsa(SemaRef, DSAS, CurDeclaration, DVar);
21682           continue;
21683         }
21684       }
21685     }
21686 
21687     // Try to find the associated user-defined mapper.
21688     ExprResult ER = buildUserDefinedMapperRef(
21689         SemaRef, DSAS->getCurScope(), MapperIdScopeSpec, MapperId,
21690         Type.getCanonicalType(), UnresolvedMapper);
21691     if (ER.isInvalid())
21692       continue;
21693     MVLI.UDMapperList.push_back(ER.get());
21694 
21695     // Save the current expression.
21696     MVLI.ProcessedVarList.push_back(RE);
21697 
21698     // Store the components in the stack so that they can be used to check
21699     // against other clauses later on.
21700     DSAS->addMappableExpressionComponents(CurDeclaration, CurComponents,
21701                                           /*WhereFoundClauseKind=*/OMPC_map);
21702 
21703     // Save the components and declaration to create the clause. For purposes of
21704     // the clause creation, any component list that has has base 'this' uses
21705     // null as base declaration.
21706     MVLI.VarComponents.resize(MVLI.VarComponents.size() + 1);
21707     MVLI.VarComponents.back().append(CurComponents.begin(),
21708                                      CurComponents.end());
21709     MVLI.VarBaseDeclarations.push_back(isa<MemberExpr>(BE) ? nullptr
21710                                                            : CurDeclaration);
21711   }
21712 }
21713 
21714 OMPClause *Sema::ActOnOpenMPMapClause(
21715     ArrayRef<OpenMPMapModifierKind> MapTypeModifiers,
21716     ArrayRef<SourceLocation> MapTypeModifiersLoc,
21717     CXXScopeSpec &MapperIdScopeSpec, DeclarationNameInfo &MapperId,
21718     OpenMPMapClauseKind MapType, bool IsMapTypeImplicit, SourceLocation MapLoc,
21719     SourceLocation ColonLoc, ArrayRef<Expr *> VarList,
21720     const OMPVarListLocTy &Locs, bool NoDiagnose,
21721     ArrayRef<Expr *> UnresolvedMappers) {
21722   OpenMPMapModifierKind Modifiers[] = {
21723       OMPC_MAP_MODIFIER_unknown, OMPC_MAP_MODIFIER_unknown,
21724       OMPC_MAP_MODIFIER_unknown, OMPC_MAP_MODIFIER_unknown,
21725       OMPC_MAP_MODIFIER_unknown};
21726   SourceLocation ModifiersLoc[NumberOfOMPMapClauseModifiers];
21727 
21728   // Process map-type-modifiers, flag errors for duplicate modifiers.
21729   unsigned Count = 0;
21730   for (unsigned I = 0, E = MapTypeModifiers.size(); I < E; ++I) {
21731     if (MapTypeModifiers[I] != OMPC_MAP_MODIFIER_unknown &&
21732         llvm::is_contained(Modifiers, MapTypeModifiers[I])) {
21733       Diag(MapTypeModifiersLoc[I], diag::err_omp_duplicate_map_type_modifier);
21734       continue;
21735     }
21736     assert(Count < NumberOfOMPMapClauseModifiers &&
21737            "Modifiers exceed the allowed number of map type modifiers");
21738     Modifiers[Count] = MapTypeModifiers[I];
21739     ModifiersLoc[Count] = MapTypeModifiersLoc[I];
21740     ++Count;
21741   }
21742 
21743   MappableVarListInfo MVLI(VarList);
21744   checkMappableExpressionList(*this, DSAStack, OMPC_map, MVLI, Locs.StartLoc,
21745                               MapperIdScopeSpec, MapperId, UnresolvedMappers,
21746                               MapType, Modifiers, IsMapTypeImplicit,
21747                               NoDiagnose);
21748 
21749   // We need to produce a map clause even if we don't have variables so that
21750   // other diagnostics related with non-existing map clauses are accurate.
21751   return OMPMapClause::Create(Context, Locs, MVLI.ProcessedVarList,
21752                               MVLI.VarBaseDeclarations, MVLI.VarComponents,
21753                               MVLI.UDMapperList, Modifiers, ModifiersLoc,
21754                               MapperIdScopeSpec.getWithLocInContext(Context),
21755                               MapperId, MapType, IsMapTypeImplicit, MapLoc);
21756 }
21757 
21758 QualType Sema::ActOnOpenMPDeclareReductionType(SourceLocation TyLoc,
21759                                                TypeResult ParsedType) {
21760   assert(ParsedType.isUsable());
21761 
21762   QualType ReductionType = GetTypeFromParser(ParsedType.get());
21763   if (ReductionType.isNull())
21764     return QualType();
21765 
21766   // [OpenMP 4.0], 2.15 declare reduction Directive, Restrictions, C\C++
21767   // A type name in a declare reduction directive cannot be a function type, an
21768   // array type, a reference type, or a type qualified with const, volatile or
21769   // restrict.
21770   if (ReductionType.hasQualifiers()) {
21771     Diag(TyLoc, diag::err_omp_reduction_wrong_type) << 0;
21772     return QualType();
21773   }
21774 
21775   if (ReductionType->isFunctionType()) {
21776     Diag(TyLoc, diag::err_omp_reduction_wrong_type) << 1;
21777     return QualType();
21778   }
21779   if (ReductionType->isReferenceType()) {
21780     Diag(TyLoc, diag::err_omp_reduction_wrong_type) << 2;
21781     return QualType();
21782   }
21783   if (ReductionType->isArrayType()) {
21784     Diag(TyLoc, diag::err_omp_reduction_wrong_type) << 3;
21785     return QualType();
21786   }
21787   return ReductionType;
21788 }
21789 
21790 Sema::DeclGroupPtrTy Sema::ActOnOpenMPDeclareReductionDirectiveStart(
21791     Scope *S, DeclContext *DC, DeclarationName Name,
21792     ArrayRef<std::pair<QualType, SourceLocation>> ReductionTypes,
21793     AccessSpecifier AS, Decl *PrevDeclInScope) {
21794   SmallVector<Decl *, 8> Decls;
21795   Decls.reserve(ReductionTypes.size());
21796 
21797   LookupResult Lookup(*this, Name, SourceLocation(), LookupOMPReductionName,
21798                       forRedeclarationInCurContext());
21799   // [OpenMP 4.0], 2.15 declare reduction Directive, Restrictions
21800   // A reduction-identifier may not be re-declared in the current scope for the
21801   // same type or for a type that is compatible according to the base language
21802   // rules.
21803   llvm::DenseMap<QualType, SourceLocation> PreviousRedeclTypes;
21804   OMPDeclareReductionDecl *PrevDRD = nullptr;
21805   bool InCompoundScope = true;
21806   if (S != nullptr) {
21807     // Find previous declaration with the same name not referenced in other
21808     // declarations.
21809     FunctionScopeInfo *ParentFn = getEnclosingFunction();
21810     InCompoundScope =
21811         (ParentFn != nullptr) && !ParentFn->CompoundScopes.empty();
21812     LookupName(Lookup, S);
21813     FilterLookupForScope(Lookup, DC, S, /*ConsiderLinkage=*/false,
21814                          /*AllowInlineNamespace=*/false);
21815     llvm::DenseMap<OMPDeclareReductionDecl *, bool> UsedAsPrevious;
21816     LookupResult::Filter Filter = Lookup.makeFilter();
21817     while (Filter.hasNext()) {
21818       auto *PrevDecl = cast<OMPDeclareReductionDecl>(Filter.next());
21819       if (InCompoundScope) {
21820         auto I = UsedAsPrevious.find(PrevDecl);
21821         if (I == UsedAsPrevious.end())
21822           UsedAsPrevious[PrevDecl] = false;
21823         if (OMPDeclareReductionDecl *D = PrevDecl->getPrevDeclInScope())
21824           UsedAsPrevious[D] = true;
21825       }
21826       PreviousRedeclTypes[PrevDecl->getType().getCanonicalType()] =
21827           PrevDecl->getLocation();
21828     }
21829     Filter.done();
21830     if (InCompoundScope) {
21831       for (const auto &PrevData : UsedAsPrevious) {
21832         if (!PrevData.second) {
21833           PrevDRD = PrevData.first;
21834           break;
21835         }
21836       }
21837     }
21838   } else if (PrevDeclInScope != nullptr) {
21839     auto *PrevDRDInScope = PrevDRD =
21840         cast<OMPDeclareReductionDecl>(PrevDeclInScope);
21841     do {
21842       PreviousRedeclTypes[PrevDRDInScope->getType().getCanonicalType()] =
21843           PrevDRDInScope->getLocation();
21844       PrevDRDInScope = PrevDRDInScope->getPrevDeclInScope();
21845     } while (PrevDRDInScope != nullptr);
21846   }
21847   for (const auto &TyData : ReductionTypes) {
21848     const auto I = PreviousRedeclTypes.find(TyData.first.getCanonicalType());
21849     bool Invalid = false;
21850     if (I != PreviousRedeclTypes.end()) {
21851       Diag(TyData.second, diag::err_omp_declare_reduction_redefinition)
21852           << TyData.first;
21853       Diag(I->second, diag::note_previous_definition);
21854       Invalid = true;
21855     }
21856     PreviousRedeclTypes[TyData.first.getCanonicalType()] = TyData.second;
21857     auto *DRD = OMPDeclareReductionDecl::Create(Context, DC, TyData.second,
21858                                                 Name, TyData.first, PrevDRD);
21859     DC->addDecl(DRD);
21860     DRD->setAccess(AS);
21861     Decls.push_back(DRD);
21862     if (Invalid)
21863       DRD->setInvalidDecl();
21864     else
21865       PrevDRD = DRD;
21866   }
21867 
21868   return DeclGroupPtrTy::make(
21869       DeclGroupRef::Create(Context, Decls.begin(), Decls.size()));
21870 }
21871 
21872 void Sema::ActOnOpenMPDeclareReductionCombinerStart(Scope *S, Decl *D) {
21873   auto *DRD = cast<OMPDeclareReductionDecl>(D);
21874 
21875   // Enter new function scope.
21876   PushFunctionScope();
21877   setFunctionHasBranchProtectedScope();
21878   getCurFunction()->setHasOMPDeclareReductionCombiner();
21879 
21880   if (S != nullptr)
21881     PushDeclContext(S, DRD);
21882   else
21883     CurContext = DRD;
21884 
21885   PushExpressionEvaluationContext(
21886       ExpressionEvaluationContext::PotentiallyEvaluated);
21887 
21888   QualType ReductionType = DRD->getType();
21889   // Create 'T* omp_parm;T omp_in;'. All references to 'omp_in' will
21890   // be replaced by '*omp_parm' during codegen. This required because 'omp_in'
21891   // uses semantics of argument handles by value, but it should be passed by
21892   // reference. C lang does not support references, so pass all parameters as
21893   // pointers.
21894   // Create 'T omp_in;' variable.
21895   VarDecl *OmpInParm =
21896       buildVarDecl(*this, D->getLocation(), ReductionType, "omp_in");
21897   // Create 'T* omp_parm;T omp_out;'. All references to 'omp_out' will
21898   // be replaced by '*omp_parm' during codegen. This required because 'omp_out'
21899   // uses semantics of argument handles by value, but it should be passed by
21900   // reference. C lang does not support references, so pass all parameters as
21901   // pointers.
21902   // Create 'T omp_out;' variable.
21903   VarDecl *OmpOutParm =
21904       buildVarDecl(*this, D->getLocation(), ReductionType, "omp_out");
21905   if (S != nullptr) {
21906     PushOnScopeChains(OmpInParm, S);
21907     PushOnScopeChains(OmpOutParm, S);
21908   } else {
21909     DRD->addDecl(OmpInParm);
21910     DRD->addDecl(OmpOutParm);
21911   }
21912   Expr *InE =
21913       ::buildDeclRefExpr(*this, OmpInParm, ReductionType, D->getLocation());
21914   Expr *OutE =
21915       ::buildDeclRefExpr(*this, OmpOutParm, ReductionType, D->getLocation());
21916   DRD->setCombinerData(InE, OutE);
21917 }
21918 
21919 void Sema::ActOnOpenMPDeclareReductionCombinerEnd(Decl *D, Expr *Combiner) {
21920   auto *DRD = cast<OMPDeclareReductionDecl>(D);
21921   DiscardCleanupsInEvaluationContext();
21922   PopExpressionEvaluationContext();
21923 
21924   PopDeclContext();
21925   PopFunctionScopeInfo();
21926 
21927   if (Combiner != nullptr)
21928     DRD->setCombiner(Combiner);
21929   else
21930     DRD->setInvalidDecl();
21931 }
21932 
21933 VarDecl *Sema::ActOnOpenMPDeclareReductionInitializerStart(Scope *S, Decl *D) {
21934   auto *DRD = cast<OMPDeclareReductionDecl>(D);
21935 
21936   // Enter new function scope.
21937   PushFunctionScope();
21938   setFunctionHasBranchProtectedScope();
21939 
21940   if (S != nullptr)
21941     PushDeclContext(S, DRD);
21942   else
21943     CurContext = DRD;
21944 
21945   PushExpressionEvaluationContext(
21946       ExpressionEvaluationContext::PotentiallyEvaluated);
21947 
21948   QualType ReductionType = DRD->getType();
21949   // Create 'T* omp_parm;T omp_priv;'. All references to 'omp_priv' will
21950   // be replaced by '*omp_parm' during codegen. This required because 'omp_priv'
21951   // uses semantics of argument handles by value, but it should be passed by
21952   // reference. C lang does not support references, so pass all parameters as
21953   // pointers.
21954   // Create 'T omp_priv;' variable.
21955   VarDecl *OmpPrivParm =
21956       buildVarDecl(*this, D->getLocation(), ReductionType, "omp_priv");
21957   // Create 'T* omp_parm;T omp_orig;'. All references to 'omp_orig' will
21958   // be replaced by '*omp_parm' during codegen. This required because 'omp_orig'
21959   // uses semantics of argument handles by value, but it should be passed by
21960   // reference. C lang does not support references, so pass all parameters as
21961   // pointers.
21962   // Create 'T omp_orig;' variable.
21963   VarDecl *OmpOrigParm =
21964       buildVarDecl(*this, D->getLocation(), ReductionType, "omp_orig");
21965   if (S != nullptr) {
21966     PushOnScopeChains(OmpPrivParm, S);
21967     PushOnScopeChains(OmpOrigParm, S);
21968   } else {
21969     DRD->addDecl(OmpPrivParm);
21970     DRD->addDecl(OmpOrigParm);
21971   }
21972   Expr *OrigE =
21973       ::buildDeclRefExpr(*this, OmpOrigParm, ReductionType, D->getLocation());
21974   Expr *PrivE =
21975       ::buildDeclRefExpr(*this, OmpPrivParm, ReductionType, D->getLocation());
21976   DRD->setInitializerData(OrigE, PrivE);
21977   return OmpPrivParm;
21978 }
21979 
21980 void Sema::ActOnOpenMPDeclareReductionInitializerEnd(Decl *D, Expr *Initializer,
21981                                                      VarDecl *OmpPrivParm) {
21982   auto *DRD = cast<OMPDeclareReductionDecl>(D);
21983   DiscardCleanupsInEvaluationContext();
21984   PopExpressionEvaluationContext();
21985 
21986   PopDeclContext();
21987   PopFunctionScopeInfo();
21988 
21989   if (Initializer != nullptr) {
21990     DRD->setInitializer(Initializer, OMPDeclareReductionDecl::CallInit);
21991   } else if (OmpPrivParm->hasInit()) {
21992     DRD->setInitializer(OmpPrivParm->getInit(),
21993                         OmpPrivParm->isDirectInit()
21994                             ? OMPDeclareReductionDecl::DirectInit
21995                             : OMPDeclareReductionDecl::CopyInit);
21996   } else {
21997     DRD->setInvalidDecl();
21998   }
21999 }
22000 
22001 Sema::DeclGroupPtrTy Sema::ActOnOpenMPDeclareReductionDirectiveEnd(
22002     Scope *S, DeclGroupPtrTy DeclReductions, bool IsValid) {
22003   for (Decl *D : DeclReductions.get()) {
22004     if (IsValid) {
22005       if (S)
22006         PushOnScopeChains(cast<OMPDeclareReductionDecl>(D), S,
22007                           /*AddToContext=*/false);
22008     } else {
22009       D->setInvalidDecl();
22010     }
22011   }
22012   return DeclReductions;
22013 }
22014 
22015 TypeResult Sema::ActOnOpenMPDeclareMapperVarDecl(Scope *S, Declarator &D) {
22016   TypeSourceInfo *TInfo = GetTypeForDeclarator(D, S);
22017   QualType T = TInfo->getType();
22018   if (D.isInvalidType())
22019     return true;
22020 
22021   if (getLangOpts().CPlusPlus) {
22022     // Check that there are no default arguments (C++ only).
22023     CheckExtraCXXDefaultArguments(D);
22024   }
22025 
22026   return CreateParsedType(T, TInfo);
22027 }
22028 
22029 QualType Sema::ActOnOpenMPDeclareMapperType(SourceLocation TyLoc,
22030                                             TypeResult ParsedType) {
22031   assert(ParsedType.isUsable() && "Expect usable parsed mapper type");
22032 
22033   QualType MapperType = GetTypeFromParser(ParsedType.get());
22034   assert(!MapperType.isNull() && "Expect valid mapper type");
22035 
22036   // [OpenMP 5.0], 2.19.7.3 declare mapper Directive, Restrictions
22037   //  The type must be of struct, union or class type in C and C++
22038   if (!MapperType->isStructureOrClassType() && !MapperType->isUnionType()) {
22039     Diag(TyLoc, diag::err_omp_mapper_wrong_type);
22040     return QualType();
22041   }
22042   return MapperType;
22043 }
22044 
22045 Sema::DeclGroupPtrTy Sema::ActOnOpenMPDeclareMapperDirective(
22046     Scope *S, DeclContext *DC, DeclarationName Name, QualType MapperType,
22047     SourceLocation StartLoc, DeclarationName VN, AccessSpecifier AS,
22048     Expr *MapperVarRef, ArrayRef<OMPClause *> Clauses, Decl *PrevDeclInScope) {
22049   LookupResult Lookup(*this, Name, SourceLocation(), LookupOMPMapperName,
22050                       forRedeclarationInCurContext());
22051   // [OpenMP 5.0], 2.19.7.3 declare mapper Directive, Restrictions
22052   //  A mapper-identifier may not be redeclared in the current scope for the
22053   //  same type or for a type that is compatible according to the base language
22054   //  rules.
22055   llvm::DenseMap<QualType, SourceLocation> PreviousRedeclTypes;
22056   OMPDeclareMapperDecl *PrevDMD = nullptr;
22057   bool InCompoundScope = true;
22058   if (S != nullptr) {
22059     // Find previous declaration with the same name not referenced in other
22060     // declarations.
22061     FunctionScopeInfo *ParentFn = getEnclosingFunction();
22062     InCompoundScope =
22063         (ParentFn != nullptr) && !ParentFn->CompoundScopes.empty();
22064     LookupName(Lookup, S);
22065     FilterLookupForScope(Lookup, DC, S, /*ConsiderLinkage=*/false,
22066                          /*AllowInlineNamespace=*/false);
22067     llvm::DenseMap<OMPDeclareMapperDecl *, bool> UsedAsPrevious;
22068     LookupResult::Filter Filter = Lookup.makeFilter();
22069     while (Filter.hasNext()) {
22070       auto *PrevDecl = cast<OMPDeclareMapperDecl>(Filter.next());
22071       if (InCompoundScope) {
22072         auto I = UsedAsPrevious.find(PrevDecl);
22073         if (I == UsedAsPrevious.end())
22074           UsedAsPrevious[PrevDecl] = false;
22075         if (OMPDeclareMapperDecl *D = PrevDecl->getPrevDeclInScope())
22076           UsedAsPrevious[D] = true;
22077       }
22078       PreviousRedeclTypes[PrevDecl->getType().getCanonicalType()] =
22079           PrevDecl->getLocation();
22080     }
22081     Filter.done();
22082     if (InCompoundScope) {
22083       for (const auto &PrevData : UsedAsPrevious) {
22084         if (!PrevData.second) {
22085           PrevDMD = PrevData.first;
22086           break;
22087         }
22088       }
22089     }
22090   } else if (PrevDeclInScope) {
22091     auto *PrevDMDInScope = PrevDMD =
22092         cast<OMPDeclareMapperDecl>(PrevDeclInScope);
22093     do {
22094       PreviousRedeclTypes[PrevDMDInScope->getType().getCanonicalType()] =
22095           PrevDMDInScope->getLocation();
22096       PrevDMDInScope = PrevDMDInScope->getPrevDeclInScope();
22097     } while (PrevDMDInScope != nullptr);
22098   }
22099   const auto I = PreviousRedeclTypes.find(MapperType.getCanonicalType());
22100   bool Invalid = false;
22101   if (I != PreviousRedeclTypes.end()) {
22102     Diag(StartLoc, diag::err_omp_declare_mapper_redefinition)
22103         << MapperType << Name;
22104     Diag(I->second, diag::note_previous_definition);
22105     Invalid = true;
22106   }
22107   // Build expressions for implicit maps of data members with 'default'
22108   // mappers.
22109   SmallVector<OMPClause *, 4> ClausesWithImplicit(Clauses.begin(),
22110                                                   Clauses.end());
22111   if (LangOpts.OpenMP >= 50)
22112     processImplicitMapsWithDefaultMappers(*this, DSAStack, ClausesWithImplicit);
22113   auto *DMD =
22114       OMPDeclareMapperDecl::Create(Context, DC, StartLoc, Name, MapperType, VN,
22115                                    ClausesWithImplicit, PrevDMD);
22116   if (S)
22117     PushOnScopeChains(DMD, S);
22118   else
22119     DC->addDecl(DMD);
22120   DMD->setAccess(AS);
22121   if (Invalid)
22122     DMD->setInvalidDecl();
22123 
22124   auto *VD = cast<DeclRefExpr>(MapperVarRef)->getDecl();
22125   VD->setDeclContext(DMD);
22126   VD->setLexicalDeclContext(DMD);
22127   DMD->addDecl(VD);
22128   DMD->setMapperVarRef(MapperVarRef);
22129 
22130   return DeclGroupPtrTy::make(DeclGroupRef(DMD));
22131 }
22132 
22133 ExprResult
22134 Sema::ActOnOpenMPDeclareMapperDirectiveVarDecl(Scope *S, QualType MapperType,
22135                                                SourceLocation StartLoc,
22136                                                DeclarationName VN) {
22137   TypeSourceInfo *TInfo =
22138       Context.getTrivialTypeSourceInfo(MapperType, StartLoc);
22139   auto *VD = VarDecl::Create(Context, Context.getTranslationUnitDecl(),
22140                              StartLoc, StartLoc, VN.getAsIdentifierInfo(),
22141                              MapperType, TInfo, SC_None);
22142   if (S)
22143     PushOnScopeChains(VD, S, /*AddToContext=*/false);
22144   Expr *E = buildDeclRefExpr(*this, VD, MapperType, StartLoc);
22145   DSAStack->addDeclareMapperVarRef(E);
22146   return E;
22147 }
22148 
22149 bool Sema::isOpenMPDeclareMapperVarDeclAllowed(const VarDecl *VD) const {
22150   assert(LangOpts.OpenMP && "Expected OpenMP mode.");
22151   const Expr *Ref = DSAStack->getDeclareMapperVarRef();
22152   if (const auto *DRE = cast_or_null<DeclRefExpr>(Ref)) {
22153     if (VD->getCanonicalDecl() == DRE->getDecl()->getCanonicalDecl())
22154       return true;
22155     if (VD->isUsableInConstantExpressions(Context))
22156       return true;
22157     return false;
22158   }
22159   return true;
22160 }
22161 
22162 const ValueDecl *Sema::getOpenMPDeclareMapperVarName() const {
22163   assert(LangOpts.OpenMP && "Expected OpenMP mode.");
22164   return cast<DeclRefExpr>(DSAStack->getDeclareMapperVarRef())->getDecl();
22165 }
22166 
22167 OMPClause *Sema::ActOnOpenMPNumTeamsClause(Expr *NumTeams,
22168                                            SourceLocation StartLoc,
22169                                            SourceLocation LParenLoc,
22170                                            SourceLocation EndLoc) {
22171   Expr *ValExpr = NumTeams;
22172   Stmt *HelperValStmt = nullptr;
22173 
22174   // OpenMP [teams Constrcut, Restrictions]
22175   // The num_teams expression must evaluate to a positive integer value.
22176   if (!isNonNegativeIntegerValue(ValExpr, *this, OMPC_num_teams,
22177                                  /*StrictlyPositive=*/true))
22178     return nullptr;
22179 
22180   OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
22181   OpenMPDirectiveKind CaptureRegion =
22182       getOpenMPCaptureRegionForClause(DKind, OMPC_num_teams, LangOpts.OpenMP);
22183   if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
22184     ValExpr = MakeFullExpr(ValExpr).get();
22185     llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
22186     ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
22187     HelperValStmt = buildPreInits(Context, Captures);
22188   }
22189 
22190   return new (Context) OMPNumTeamsClause(ValExpr, HelperValStmt, CaptureRegion,
22191                                          StartLoc, LParenLoc, EndLoc);
22192 }
22193 
22194 OMPClause *Sema::ActOnOpenMPThreadLimitClause(Expr *ThreadLimit,
22195                                               SourceLocation StartLoc,
22196                                               SourceLocation LParenLoc,
22197                                               SourceLocation EndLoc) {
22198   Expr *ValExpr = ThreadLimit;
22199   Stmt *HelperValStmt = nullptr;
22200 
22201   // OpenMP [teams Constrcut, Restrictions]
22202   // The thread_limit expression must evaluate to a positive integer value.
22203   if (!isNonNegativeIntegerValue(ValExpr, *this, OMPC_thread_limit,
22204                                  /*StrictlyPositive=*/true))
22205     return nullptr;
22206 
22207   OpenMPDirectiveKind DKind = DSAStack->getCurrentDirective();
22208   OpenMPDirectiveKind CaptureRegion = getOpenMPCaptureRegionForClause(
22209       DKind, OMPC_thread_limit, LangOpts.OpenMP);
22210   if (CaptureRegion != OMPD_unknown && !CurContext->isDependentContext()) {
22211     ValExpr = MakeFullExpr(ValExpr).get();
22212     llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
22213     ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
22214     HelperValStmt = buildPreInits(Context, Captures);
22215   }
22216 
22217   return new (Context) OMPThreadLimitClause(
22218       ValExpr, HelperValStmt, CaptureRegion, StartLoc, LParenLoc, EndLoc);
22219 }
22220 
22221 OMPClause *Sema::ActOnOpenMPPriorityClause(Expr *Priority,
22222                                            SourceLocation StartLoc,
22223                                            SourceLocation LParenLoc,
22224                                            SourceLocation EndLoc) {
22225   Expr *ValExpr = Priority;
22226   Stmt *HelperValStmt = nullptr;
22227   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
22228 
22229   // OpenMP [2.9.1, task Constrcut]
22230   // The priority-value is a non-negative numerical scalar expression.
22231   if (!isNonNegativeIntegerValue(
22232           ValExpr, *this, OMPC_priority,
22233           /*StrictlyPositive=*/false, /*BuildCapture=*/true,
22234           DSAStack->getCurrentDirective(), &CaptureRegion, &HelperValStmt))
22235     return nullptr;
22236 
22237   return new (Context) OMPPriorityClause(ValExpr, HelperValStmt, CaptureRegion,
22238                                          StartLoc, LParenLoc, EndLoc);
22239 }
22240 
22241 OMPClause *Sema::ActOnOpenMPGrainsizeClause(Expr *Grainsize,
22242                                             SourceLocation StartLoc,
22243                                             SourceLocation LParenLoc,
22244                                             SourceLocation EndLoc) {
22245   Expr *ValExpr = Grainsize;
22246   Stmt *HelperValStmt = nullptr;
22247   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
22248 
22249   // OpenMP [2.9.2, taskloop Constrcut]
22250   // The parameter of the grainsize clause must be a positive integer
22251   // expression.
22252   if (!isNonNegativeIntegerValue(
22253           ValExpr, *this, OMPC_grainsize,
22254           /*StrictlyPositive=*/true, /*BuildCapture=*/true,
22255           DSAStack->getCurrentDirective(), &CaptureRegion, &HelperValStmt))
22256     return nullptr;
22257 
22258   return new (Context) OMPGrainsizeClause(ValExpr, HelperValStmt, CaptureRegion,
22259                                           StartLoc, LParenLoc, EndLoc);
22260 }
22261 
22262 OMPClause *Sema::ActOnOpenMPNumTasksClause(Expr *NumTasks,
22263                                            SourceLocation StartLoc,
22264                                            SourceLocation LParenLoc,
22265                                            SourceLocation EndLoc) {
22266   Expr *ValExpr = NumTasks;
22267   Stmt *HelperValStmt = nullptr;
22268   OpenMPDirectiveKind CaptureRegion = OMPD_unknown;
22269 
22270   // OpenMP [2.9.2, taskloop Constrcut]
22271   // The parameter of the num_tasks clause must be a positive integer
22272   // expression.
22273   if (!isNonNegativeIntegerValue(
22274           ValExpr, *this, OMPC_num_tasks,
22275           /*StrictlyPositive=*/true, /*BuildCapture=*/true,
22276           DSAStack->getCurrentDirective(), &CaptureRegion, &HelperValStmt))
22277     return nullptr;
22278 
22279   return new (Context) OMPNumTasksClause(ValExpr, HelperValStmt, CaptureRegion,
22280                                          StartLoc, LParenLoc, EndLoc);
22281 }
22282 
22283 OMPClause *Sema::ActOnOpenMPHintClause(Expr *Hint, SourceLocation StartLoc,
22284                                        SourceLocation LParenLoc,
22285                                        SourceLocation EndLoc) {
22286   // OpenMP [2.13.2, critical construct, Description]
22287   // ... where hint-expression is an integer constant expression that evaluates
22288   // to a valid lock hint.
22289   ExprResult HintExpr =
22290       VerifyPositiveIntegerConstantInClause(Hint, OMPC_hint, false);
22291   if (HintExpr.isInvalid())
22292     return nullptr;
22293   return new (Context)
22294       OMPHintClause(HintExpr.get(), StartLoc, LParenLoc, EndLoc);
22295 }
22296 
22297 /// Tries to find omp_event_handle_t type.
22298 static bool findOMPEventHandleT(Sema &S, SourceLocation Loc,
22299                                 DSAStackTy *Stack) {
22300   QualType OMPEventHandleT = Stack->getOMPEventHandleT();
22301   if (!OMPEventHandleT.isNull())
22302     return true;
22303   IdentifierInfo *II = &S.PP.getIdentifierTable().get("omp_event_handle_t");
22304   ParsedType PT = S.getTypeName(*II, Loc, S.getCurScope());
22305   if (!PT.getAsOpaquePtr() || PT.get().isNull()) {
22306     S.Diag(Loc, diag::err_omp_implied_type_not_found) << "omp_event_handle_t";
22307     return false;
22308   }
22309   Stack->setOMPEventHandleT(PT.get());
22310   return true;
22311 }
22312 
22313 OMPClause *Sema::ActOnOpenMPDetachClause(Expr *Evt, SourceLocation StartLoc,
22314                                          SourceLocation LParenLoc,
22315                                          SourceLocation EndLoc) {
22316   if (!Evt->isValueDependent() && !Evt->isTypeDependent() &&
22317       !Evt->isInstantiationDependent() &&
22318       !Evt->containsUnexpandedParameterPack()) {
22319     if (!findOMPEventHandleT(*this, Evt->getExprLoc(), DSAStack))
22320       return nullptr;
22321     // OpenMP 5.0, 2.10.1 task Construct.
22322     // event-handle is a variable of the omp_event_handle_t type.
22323     auto *Ref = dyn_cast<DeclRefExpr>(Evt->IgnoreParenImpCasts());
22324     if (!Ref) {
22325       Diag(Evt->getExprLoc(), diag::err_omp_var_expected)
22326           << "omp_event_handle_t" << 0 << Evt->getSourceRange();
22327       return nullptr;
22328     }
22329     auto *VD = dyn_cast_or_null<VarDecl>(Ref->getDecl());
22330     if (!VD) {
22331       Diag(Evt->getExprLoc(), diag::err_omp_var_expected)
22332           << "omp_event_handle_t" << 0 << Evt->getSourceRange();
22333       return nullptr;
22334     }
22335     if (!Context.hasSameUnqualifiedType(DSAStack->getOMPEventHandleT(),
22336                                         VD->getType()) ||
22337         VD->getType().isConstant(Context)) {
22338       Diag(Evt->getExprLoc(), diag::err_omp_var_expected)
22339           << "omp_event_handle_t" << 1 << VD->getType()
22340           << Evt->getSourceRange();
22341       return nullptr;
22342     }
22343     // OpenMP 5.0, 2.10.1 task Construct
22344     // [detach clause]... The event-handle will be considered as if it was
22345     // specified on a firstprivate clause.
22346     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(VD, /*FromParent=*/false);
22347     if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_firstprivate &&
22348         DVar.RefExpr) {
22349       Diag(Evt->getExprLoc(), diag::err_omp_wrong_dsa)
22350           << getOpenMPClauseName(DVar.CKind)
22351           << getOpenMPClauseName(OMPC_firstprivate);
22352       reportOriginalDsa(*this, DSAStack, VD, DVar);
22353       return nullptr;
22354     }
22355   }
22356 
22357   return new (Context) OMPDetachClause(Evt, StartLoc, LParenLoc, EndLoc);
22358 }
22359 
22360 OMPClause *Sema::ActOnOpenMPDistScheduleClause(
22361     OpenMPDistScheduleClauseKind Kind, Expr *ChunkSize, SourceLocation StartLoc,
22362     SourceLocation LParenLoc, SourceLocation KindLoc, SourceLocation CommaLoc,
22363     SourceLocation EndLoc) {
22364   if (Kind == OMPC_DIST_SCHEDULE_unknown) {
22365     std::string Values;
22366     Values += "'";
22367     Values += getOpenMPSimpleClauseTypeName(OMPC_dist_schedule, 0);
22368     Values += "'";
22369     Diag(KindLoc, diag::err_omp_unexpected_clause_value)
22370         << Values << getOpenMPClauseName(OMPC_dist_schedule);
22371     return nullptr;
22372   }
22373   Expr *ValExpr = ChunkSize;
22374   Stmt *HelperValStmt = nullptr;
22375   if (ChunkSize) {
22376     if (!ChunkSize->isValueDependent() && !ChunkSize->isTypeDependent() &&
22377         !ChunkSize->isInstantiationDependent() &&
22378         !ChunkSize->containsUnexpandedParameterPack()) {
22379       SourceLocation ChunkSizeLoc = ChunkSize->getBeginLoc();
22380       ExprResult Val =
22381           PerformOpenMPImplicitIntegerConversion(ChunkSizeLoc, ChunkSize);
22382       if (Val.isInvalid())
22383         return nullptr;
22384 
22385       ValExpr = Val.get();
22386 
22387       // OpenMP [2.7.1, Restrictions]
22388       //  chunk_size must be a loop invariant integer expression with a positive
22389       //  value.
22390       if (Optional<llvm::APSInt> Result =
22391               ValExpr->getIntegerConstantExpr(Context)) {
22392         if (Result->isSigned() && !Result->isStrictlyPositive()) {
22393           Diag(ChunkSizeLoc, diag::err_omp_negative_expression_in_clause)
22394               << "dist_schedule" << ChunkSize->getSourceRange();
22395           return nullptr;
22396         }
22397       } else if (getOpenMPCaptureRegionForClause(
22398                      DSAStack->getCurrentDirective(), OMPC_dist_schedule,
22399                      LangOpts.OpenMP) != OMPD_unknown &&
22400                  !CurContext->isDependentContext()) {
22401         ValExpr = MakeFullExpr(ValExpr).get();
22402         llvm::MapVector<const Expr *, DeclRefExpr *> Captures;
22403         ValExpr = tryBuildCapture(*this, ValExpr, Captures).get();
22404         HelperValStmt = buildPreInits(Context, Captures);
22405       }
22406     }
22407   }
22408 
22409   return new (Context)
22410       OMPDistScheduleClause(StartLoc, LParenLoc, KindLoc, CommaLoc, EndLoc,
22411                             Kind, ValExpr, HelperValStmt);
22412 }
22413 
22414 OMPClause *Sema::ActOnOpenMPDefaultmapClause(
22415     OpenMPDefaultmapClauseModifier M, OpenMPDefaultmapClauseKind Kind,
22416     SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation MLoc,
22417     SourceLocation KindLoc, SourceLocation EndLoc) {
22418   if (getLangOpts().OpenMP < 50) {
22419     if (M != OMPC_DEFAULTMAP_MODIFIER_tofrom ||
22420         Kind != OMPC_DEFAULTMAP_scalar) {
22421       std::string Value;
22422       SourceLocation Loc;
22423       Value += "'";
22424       if (M != OMPC_DEFAULTMAP_MODIFIER_tofrom) {
22425         Value += getOpenMPSimpleClauseTypeName(OMPC_defaultmap,
22426                                                OMPC_DEFAULTMAP_MODIFIER_tofrom);
22427         Loc = MLoc;
22428       } else {
22429         Value += getOpenMPSimpleClauseTypeName(OMPC_defaultmap,
22430                                                OMPC_DEFAULTMAP_scalar);
22431         Loc = KindLoc;
22432       }
22433       Value += "'";
22434       Diag(Loc, diag::err_omp_unexpected_clause_value)
22435           << Value << getOpenMPClauseName(OMPC_defaultmap);
22436       return nullptr;
22437     }
22438   } else {
22439     bool isDefaultmapModifier = (M != OMPC_DEFAULTMAP_MODIFIER_unknown);
22440     bool isDefaultmapKind = (Kind != OMPC_DEFAULTMAP_unknown) ||
22441                             (LangOpts.OpenMP >= 50 && KindLoc.isInvalid());
22442     if (!isDefaultmapKind || !isDefaultmapModifier) {
22443       StringRef KindValue = "'scalar', 'aggregate', 'pointer'";
22444       if (LangOpts.OpenMP == 50) {
22445         StringRef ModifierValue = "'alloc', 'from', 'to', 'tofrom', "
22446                                   "'firstprivate', 'none', 'default'";
22447         if (!isDefaultmapKind && isDefaultmapModifier) {
22448           Diag(KindLoc, diag::err_omp_unexpected_clause_value)
22449               << KindValue << getOpenMPClauseName(OMPC_defaultmap);
22450         } else if (isDefaultmapKind && !isDefaultmapModifier) {
22451           Diag(MLoc, diag::err_omp_unexpected_clause_value)
22452               << ModifierValue << getOpenMPClauseName(OMPC_defaultmap);
22453         } else {
22454           Diag(MLoc, diag::err_omp_unexpected_clause_value)
22455               << ModifierValue << getOpenMPClauseName(OMPC_defaultmap);
22456           Diag(KindLoc, diag::err_omp_unexpected_clause_value)
22457               << KindValue << getOpenMPClauseName(OMPC_defaultmap);
22458         }
22459       } else {
22460         StringRef ModifierValue =
22461             "'alloc', 'from', 'to', 'tofrom', "
22462             "'firstprivate', 'none', 'default', 'present'";
22463         if (!isDefaultmapKind && isDefaultmapModifier) {
22464           Diag(KindLoc, diag::err_omp_unexpected_clause_value)
22465               << KindValue << getOpenMPClauseName(OMPC_defaultmap);
22466         } else if (isDefaultmapKind && !isDefaultmapModifier) {
22467           Diag(MLoc, diag::err_omp_unexpected_clause_value)
22468               << ModifierValue << getOpenMPClauseName(OMPC_defaultmap);
22469         } else {
22470           Diag(MLoc, diag::err_omp_unexpected_clause_value)
22471               << ModifierValue << getOpenMPClauseName(OMPC_defaultmap);
22472           Diag(KindLoc, diag::err_omp_unexpected_clause_value)
22473               << KindValue << getOpenMPClauseName(OMPC_defaultmap);
22474         }
22475       }
22476       return nullptr;
22477     }
22478 
22479     // OpenMP [5.0, 2.12.5, Restrictions, p. 174]
22480     //  At most one defaultmap clause for each category can appear on the
22481     //  directive.
22482     if (DSAStack->checkDefaultmapCategory(Kind)) {
22483       Diag(StartLoc, diag::err_omp_one_defaultmap_each_category);
22484       return nullptr;
22485     }
22486   }
22487   if (Kind == OMPC_DEFAULTMAP_unknown) {
22488     // Variable category is not specified - mark all categories.
22489     DSAStack->setDefaultDMAAttr(M, OMPC_DEFAULTMAP_aggregate, StartLoc);
22490     DSAStack->setDefaultDMAAttr(M, OMPC_DEFAULTMAP_scalar, StartLoc);
22491     DSAStack->setDefaultDMAAttr(M, OMPC_DEFAULTMAP_pointer, StartLoc);
22492   } else {
22493     DSAStack->setDefaultDMAAttr(M, Kind, StartLoc);
22494   }
22495 
22496   return new (Context)
22497       OMPDefaultmapClause(StartLoc, LParenLoc, MLoc, KindLoc, EndLoc, Kind, M);
22498 }
22499 
22500 bool Sema::ActOnStartOpenMPDeclareTargetContext(
22501     DeclareTargetContextInfo &DTCI) {
22502   DeclContext *CurLexicalContext = getCurLexicalContext();
22503   if (!CurLexicalContext->isFileContext() &&
22504       !CurLexicalContext->isExternCContext() &&
22505       !CurLexicalContext->isExternCXXContext() &&
22506       !isa<CXXRecordDecl>(CurLexicalContext) &&
22507       !isa<ClassTemplateDecl>(CurLexicalContext) &&
22508       !isa<ClassTemplatePartialSpecializationDecl>(CurLexicalContext) &&
22509       !isa<ClassTemplateSpecializationDecl>(CurLexicalContext)) {
22510     Diag(DTCI.Loc, diag::err_omp_region_not_file_context);
22511     return false;
22512   }
22513   DeclareTargetNesting.push_back(DTCI);
22514   return true;
22515 }
22516 
22517 const Sema::DeclareTargetContextInfo
22518 Sema::ActOnOpenMPEndDeclareTargetDirective() {
22519   assert(!DeclareTargetNesting.empty() &&
22520          "check isInOpenMPDeclareTargetContext() first!");
22521   return DeclareTargetNesting.pop_back_val();
22522 }
22523 
22524 void Sema::ActOnFinishedOpenMPDeclareTargetContext(
22525     DeclareTargetContextInfo &DTCI) {
22526   for (auto &It : DTCI.ExplicitlyMapped)
22527     ActOnOpenMPDeclareTargetName(It.first, It.second.Loc, It.second.MT, DTCI);
22528 }
22529 
22530 void Sema::DiagnoseUnterminatedOpenMPDeclareTarget() {
22531   if (DeclareTargetNesting.empty())
22532     return;
22533   DeclareTargetContextInfo &DTCI = DeclareTargetNesting.back();
22534   Diag(DTCI.Loc, diag::warn_omp_unterminated_declare_target)
22535       << getOpenMPDirectiveName(DTCI.Kind);
22536 }
22537 
22538 NamedDecl *Sema::lookupOpenMPDeclareTargetName(Scope *CurScope,
22539                                                CXXScopeSpec &ScopeSpec,
22540                                                const DeclarationNameInfo &Id) {
22541   LookupResult Lookup(*this, Id, LookupOrdinaryName);
22542   LookupParsedName(Lookup, CurScope, &ScopeSpec, true);
22543 
22544   if (Lookup.isAmbiguous())
22545     return nullptr;
22546   Lookup.suppressDiagnostics();
22547 
22548   if (!Lookup.isSingleResult()) {
22549     VarOrFuncDeclFilterCCC CCC(*this);
22550     if (TypoCorrection Corrected =
22551             CorrectTypo(Id, LookupOrdinaryName, CurScope, nullptr, CCC,
22552                         CTK_ErrorRecovery)) {
22553       diagnoseTypo(Corrected, PDiag(diag::err_undeclared_var_use_suggest)
22554                                   << Id.getName());
22555       checkDeclIsAllowedInOpenMPTarget(nullptr, Corrected.getCorrectionDecl());
22556       return nullptr;
22557     }
22558 
22559     Diag(Id.getLoc(), diag::err_undeclared_var_use) << Id.getName();
22560     return nullptr;
22561   }
22562 
22563   NamedDecl *ND = Lookup.getAsSingle<NamedDecl>();
22564   if (!isa<VarDecl>(ND) && !isa<FunctionDecl>(ND) &&
22565       !isa<FunctionTemplateDecl>(ND)) {
22566     Diag(Id.getLoc(), diag::err_omp_invalid_target_decl) << Id.getName();
22567     return nullptr;
22568   }
22569   return ND;
22570 }
22571 
22572 void Sema::ActOnOpenMPDeclareTargetName(NamedDecl *ND, SourceLocation Loc,
22573                                         OMPDeclareTargetDeclAttr::MapTypeTy MT,
22574                                         DeclareTargetContextInfo &DTCI) {
22575   assert((isa<VarDecl>(ND) || isa<FunctionDecl>(ND) ||
22576           isa<FunctionTemplateDecl>(ND)) &&
22577          "Expected variable, function or function template.");
22578 
22579   // Diagnose marking after use as it may lead to incorrect diagnosis and
22580   // codegen.
22581   if (LangOpts.OpenMP >= 50 &&
22582       (ND->isUsed(/*CheckUsedAttr=*/false) || ND->isReferenced()))
22583     Diag(Loc, diag::warn_omp_declare_target_after_first_use);
22584 
22585   // Explicit declare target lists have precedence.
22586   const unsigned Level = -1;
22587 
22588   auto *VD = cast<ValueDecl>(ND);
22589   llvm::Optional<OMPDeclareTargetDeclAttr *> ActiveAttr =
22590       OMPDeclareTargetDeclAttr::getActiveAttr(VD);
22591   if (ActiveAttr && ActiveAttr.value()->getDevType() != DTCI.DT &&
22592       ActiveAttr.value()->getLevel() == Level) {
22593     Diag(Loc, diag::err_omp_device_type_mismatch)
22594         << OMPDeclareTargetDeclAttr::ConvertDevTypeTyToStr(DTCI.DT)
22595         << OMPDeclareTargetDeclAttr::ConvertDevTypeTyToStr(
22596                ActiveAttr.value()->getDevType());
22597     return;
22598   }
22599   if (ActiveAttr && ActiveAttr.value()->getMapType() != MT &&
22600       ActiveAttr.value()->getLevel() == Level) {
22601     Diag(Loc, diag::err_omp_declare_target_to_and_link) << ND;
22602     return;
22603   }
22604 
22605   if (ActiveAttr && ActiveAttr.value()->getLevel() == Level)
22606     return;
22607 
22608   Expr *IndirectE = nullptr;
22609   bool IsIndirect = false;
22610   if (DTCI.Indirect) {
22611     IndirectE = DTCI.Indirect.value();
22612     if (!IndirectE)
22613       IsIndirect = true;
22614   }
22615   auto *A = OMPDeclareTargetDeclAttr::CreateImplicit(
22616       Context, MT, DTCI.DT, IndirectE, IsIndirect, Level,
22617       SourceRange(Loc, Loc));
22618   ND->addAttr(A);
22619   if (ASTMutationListener *ML = Context.getASTMutationListener())
22620     ML->DeclarationMarkedOpenMPDeclareTarget(ND, A);
22621   checkDeclIsAllowedInOpenMPTarget(nullptr, ND, Loc);
22622 }
22623 
22624 static void checkDeclInTargetContext(SourceLocation SL, SourceRange SR,
22625                                      Sema &SemaRef, Decl *D) {
22626   if (!D || !isa<VarDecl>(D))
22627     return;
22628   auto *VD = cast<VarDecl>(D);
22629   Optional<OMPDeclareTargetDeclAttr::MapTypeTy> MapTy =
22630       OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(VD);
22631   if (SemaRef.LangOpts.OpenMP >= 50 &&
22632       (SemaRef.getCurLambda(/*IgnoreNonLambdaCapturingScope=*/true) ||
22633        SemaRef.getCurBlock() || SemaRef.getCurCapturedRegion()) &&
22634       VD->hasGlobalStorage()) {
22635     if (!MapTy || *MapTy != OMPDeclareTargetDeclAttr::MT_To) {
22636       // OpenMP 5.0, 2.12.7 declare target Directive, Restrictions
22637       // If a lambda declaration and definition appears between a
22638       // declare target directive and the matching end declare target
22639       // directive, all variables that are captured by the lambda
22640       // expression must also appear in a to clause.
22641       SemaRef.Diag(VD->getLocation(),
22642                    diag::err_omp_lambda_capture_in_declare_target_not_to);
22643       SemaRef.Diag(SL, diag::note_var_explicitly_captured_here)
22644           << VD << 0 << SR;
22645       return;
22646     }
22647   }
22648   if (MapTy)
22649     return;
22650   SemaRef.Diag(VD->getLocation(), diag::warn_omp_not_in_target_context);
22651   SemaRef.Diag(SL, diag::note_used_here) << SR;
22652 }
22653 
22654 static bool checkValueDeclInTarget(SourceLocation SL, SourceRange SR,
22655                                    Sema &SemaRef, DSAStackTy *Stack,
22656                                    ValueDecl *VD) {
22657   return OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(VD) ||
22658          checkTypeMappable(SL, SR, SemaRef, Stack, VD->getType(),
22659                            /*FullCheck=*/false);
22660 }
22661 
22662 void Sema::checkDeclIsAllowedInOpenMPTarget(Expr *E, Decl *D,
22663                                             SourceLocation IdLoc) {
22664   if (!D || D->isInvalidDecl())
22665     return;
22666   SourceRange SR = E ? E->getSourceRange() : D->getSourceRange();
22667   SourceLocation SL = E ? E->getBeginLoc() : D->getLocation();
22668   if (auto *VD = dyn_cast<VarDecl>(D)) {
22669     // Only global variables can be marked as declare target.
22670     if (!VD->isFileVarDecl() && !VD->isStaticLocal() &&
22671         !VD->isStaticDataMember())
22672       return;
22673     // 2.10.6: threadprivate variable cannot appear in a declare target
22674     // directive.
22675     if (DSAStack->isThreadPrivate(VD)) {
22676       Diag(SL, diag::err_omp_threadprivate_in_target);
22677       reportOriginalDsa(*this, DSAStack, VD, DSAStack->getTopDSA(VD, false));
22678       return;
22679     }
22680   }
22681   if (const auto *FTD = dyn_cast<FunctionTemplateDecl>(D))
22682     D = FTD->getTemplatedDecl();
22683   if (auto *FD = dyn_cast<FunctionDecl>(D)) {
22684     llvm::Optional<OMPDeclareTargetDeclAttr::MapTypeTy> Res =
22685         OMPDeclareTargetDeclAttr::isDeclareTargetDeclaration(FD);
22686     if (IdLoc.isValid() && Res && *Res == OMPDeclareTargetDeclAttr::MT_Link) {
22687       Diag(IdLoc, diag::err_omp_function_in_link_clause);
22688       Diag(FD->getLocation(), diag::note_defined_here) << FD;
22689       return;
22690     }
22691   }
22692   if (auto *VD = dyn_cast<ValueDecl>(D)) {
22693     // Problem if any with var declared with incomplete type will be reported
22694     // as normal, so no need to check it here.
22695     if ((E || !VD->getType()->isIncompleteType()) &&
22696         !checkValueDeclInTarget(SL, SR, *this, DSAStack, VD))
22697       return;
22698     if (!E && isInOpenMPDeclareTargetContext()) {
22699       // Checking declaration inside declare target region.
22700       if (isa<VarDecl>(D) || isa<FunctionDecl>(D) ||
22701           isa<FunctionTemplateDecl>(D)) {
22702         llvm::Optional<OMPDeclareTargetDeclAttr *> ActiveAttr =
22703             OMPDeclareTargetDeclAttr::getActiveAttr(VD);
22704         unsigned Level = DeclareTargetNesting.size();
22705         if (ActiveAttr && ActiveAttr.value()->getLevel() >= Level)
22706           return;
22707         DeclareTargetContextInfo &DTCI = DeclareTargetNesting.back();
22708         Expr *IndirectE = nullptr;
22709         bool IsIndirect = false;
22710         if (DTCI.Indirect) {
22711           IndirectE = DTCI.Indirect.value();
22712           if (!IndirectE)
22713             IsIndirect = true;
22714         }
22715         auto *A = OMPDeclareTargetDeclAttr::CreateImplicit(
22716             Context, OMPDeclareTargetDeclAttr::MT_To, DTCI.DT, IndirectE,
22717             IsIndirect, Level, SourceRange(DTCI.Loc, DTCI.Loc));
22718         D->addAttr(A);
22719         if (ASTMutationListener *ML = Context.getASTMutationListener())
22720           ML->DeclarationMarkedOpenMPDeclareTarget(D, A);
22721       }
22722       return;
22723     }
22724   }
22725   if (!E)
22726     return;
22727   checkDeclInTargetContext(E->getExprLoc(), E->getSourceRange(), *this, D);
22728 }
22729 
22730 OMPClause *Sema::ActOnOpenMPToClause(
22731     ArrayRef<OpenMPMotionModifierKind> MotionModifiers,
22732     ArrayRef<SourceLocation> MotionModifiersLoc,
22733     CXXScopeSpec &MapperIdScopeSpec, DeclarationNameInfo &MapperId,
22734     SourceLocation ColonLoc, ArrayRef<Expr *> VarList,
22735     const OMPVarListLocTy &Locs, ArrayRef<Expr *> UnresolvedMappers) {
22736   OpenMPMotionModifierKind Modifiers[] = {OMPC_MOTION_MODIFIER_unknown,
22737                                           OMPC_MOTION_MODIFIER_unknown};
22738   SourceLocation ModifiersLoc[NumberOfOMPMotionModifiers];
22739 
22740   // Process motion-modifiers, flag errors for duplicate modifiers.
22741   unsigned Count = 0;
22742   for (unsigned I = 0, E = MotionModifiers.size(); I < E; ++I) {
22743     if (MotionModifiers[I] != OMPC_MOTION_MODIFIER_unknown &&
22744         llvm::is_contained(Modifiers, MotionModifiers[I])) {
22745       Diag(MotionModifiersLoc[I], diag::err_omp_duplicate_motion_modifier);
22746       continue;
22747     }
22748     assert(Count < NumberOfOMPMotionModifiers &&
22749            "Modifiers exceed the allowed number of motion modifiers");
22750     Modifiers[Count] = MotionModifiers[I];
22751     ModifiersLoc[Count] = MotionModifiersLoc[I];
22752     ++Count;
22753   }
22754 
22755   MappableVarListInfo MVLI(VarList);
22756   checkMappableExpressionList(*this, DSAStack, OMPC_to, MVLI, Locs.StartLoc,
22757                               MapperIdScopeSpec, MapperId, UnresolvedMappers);
22758   if (MVLI.ProcessedVarList.empty())
22759     return nullptr;
22760 
22761   return OMPToClause::Create(
22762       Context, Locs, MVLI.ProcessedVarList, MVLI.VarBaseDeclarations,
22763       MVLI.VarComponents, MVLI.UDMapperList, Modifiers, ModifiersLoc,
22764       MapperIdScopeSpec.getWithLocInContext(Context), MapperId);
22765 }
22766 
22767 OMPClause *Sema::ActOnOpenMPFromClause(
22768     ArrayRef<OpenMPMotionModifierKind> MotionModifiers,
22769     ArrayRef<SourceLocation> MotionModifiersLoc,
22770     CXXScopeSpec &MapperIdScopeSpec, DeclarationNameInfo &MapperId,
22771     SourceLocation ColonLoc, ArrayRef<Expr *> VarList,
22772     const OMPVarListLocTy &Locs, ArrayRef<Expr *> UnresolvedMappers) {
22773   OpenMPMotionModifierKind Modifiers[] = {OMPC_MOTION_MODIFIER_unknown,
22774                                           OMPC_MOTION_MODIFIER_unknown};
22775   SourceLocation ModifiersLoc[NumberOfOMPMotionModifiers];
22776 
22777   // Process motion-modifiers, flag errors for duplicate modifiers.
22778   unsigned Count = 0;
22779   for (unsigned I = 0, E = MotionModifiers.size(); I < E; ++I) {
22780     if (MotionModifiers[I] != OMPC_MOTION_MODIFIER_unknown &&
22781         llvm::is_contained(Modifiers, MotionModifiers[I])) {
22782       Diag(MotionModifiersLoc[I], diag::err_omp_duplicate_motion_modifier);
22783       continue;
22784     }
22785     assert(Count < NumberOfOMPMotionModifiers &&
22786            "Modifiers exceed the allowed number of motion modifiers");
22787     Modifiers[Count] = MotionModifiers[I];
22788     ModifiersLoc[Count] = MotionModifiersLoc[I];
22789     ++Count;
22790   }
22791 
22792   MappableVarListInfo MVLI(VarList);
22793   checkMappableExpressionList(*this, DSAStack, OMPC_from, MVLI, Locs.StartLoc,
22794                               MapperIdScopeSpec, MapperId, UnresolvedMappers);
22795   if (MVLI.ProcessedVarList.empty())
22796     return nullptr;
22797 
22798   return OMPFromClause::Create(
22799       Context, Locs, MVLI.ProcessedVarList, MVLI.VarBaseDeclarations,
22800       MVLI.VarComponents, MVLI.UDMapperList, Modifiers, ModifiersLoc,
22801       MapperIdScopeSpec.getWithLocInContext(Context), MapperId);
22802 }
22803 
22804 OMPClause *Sema::ActOnOpenMPUseDevicePtrClause(ArrayRef<Expr *> VarList,
22805                                                const OMPVarListLocTy &Locs) {
22806   MappableVarListInfo MVLI(VarList);
22807   SmallVector<Expr *, 8> PrivateCopies;
22808   SmallVector<Expr *, 8> Inits;
22809 
22810   for (Expr *RefExpr : VarList) {
22811     assert(RefExpr && "NULL expr in OpenMP use_device_ptr clause.");
22812     SourceLocation ELoc;
22813     SourceRange ERange;
22814     Expr *SimpleRefExpr = RefExpr;
22815     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
22816     if (Res.second) {
22817       // It will be analyzed later.
22818       MVLI.ProcessedVarList.push_back(RefExpr);
22819       PrivateCopies.push_back(nullptr);
22820       Inits.push_back(nullptr);
22821     }
22822     ValueDecl *D = Res.first;
22823     if (!D)
22824       continue;
22825 
22826     QualType Type = D->getType();
22827     Type = Type.getNonReferenceType().getUnqualifiedType();
22828 
22829     auto *VD = dyn_cast<VarDecl>(D);
22830 
22831     // Item should be a pointer or reference to pointer.
22832     if (!Type->isPointerType()) {
22833       Diag(ELoc, diag::err_omp_usedeviceptr_not_a_pointer)
22834           << 0 << RefExpr->getSourceRange();
22835       continue;
22836     }
22837 
22838     // Build the private variable and the expression that refers to it.
22839     auto VDPrivate =
22840         buildVarDecl(*this, ELoc, Type, D->getName(),
22841                      D->hasAttrs() ? &D->getAttrs() : nullptr,
22842                      VD ? cast<DeclRefExpr>(SimpleRefExpr) : nullptr);
22843     if (VDPrivate->isInvalidDecl())
22844       continue;
22845 
22846     CurContext->addDecl(VDPrivate);
22847     DeclRefExpr *VDPrivateRefExpr = buildDeclRefExpr(
22848         *this, VDPrivate, RefExpr->getType().getUnqualifiedType(), ELoc);
22849 
22850     // Add temporary variable to initialize the private copy of the pointer.
22851     VarDecl *VDInit =
22852         buildVarDecl(*this, RefExpr->getExprLoc(), Type, ".devptr.temp");
22853     DeclRefExpr *VDInitRefExpr = buildDeclRefExpr(
22854         *this, VDInit, RefExpr->getType(), RefExpr->getExprLoc());
22855     AddInitializerToDecl(VDPrivate,
22856                          DefaultLvalueConversion(VDInitRefExpr).get(),
22857                          /*DirectInit=*/false);
22858 
22859     // If required, build a capture to implement the privatization initialized
22860     // with the current list item value.
22861     DeclRefExpr *Ref = nullptr;
22862     if (!VD)
22863       Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/true);
22864     MVLI.ProcessedVarList.push_back(VD ? RefExpr->IgnoreParens() : Ref);
22865     PrivateCopies.push_back(VDPrivateRefExpr);
22866     Inits.push_back(VDInitRefExpr);
22867 
22868     // We need to add a data sharing attribute for this variable to make sure it
22869     // is correctly captured. A variable that shows up in a use_device_ptr has
22870     // similar properties of a first private variable.
22871     DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_firstprivate, Ref);
22872 
22873     // Create a mappable component for the list item. List items in this clause
22874     // only need a component.
22875     MVLI.VarBaseDeclarations.push_back(D);
22876     MVLI.VarComponents.resize(MVLI.VarComponents.size() + 1);
22877     MVLI.VarComponents.back().emplace_back(SimpleRefExpr, D,
22878                                            /*IsNonContiguous=*/false);
22879   }
22880 
22881   if (MVLI.ProcessedVarList.empty())
22882     return nullptr;
22883 
22884   return OMPUseDevicePtrClause::Create(
22885       Context, Locs, MVLI.ProcessedVarList, PrivateCopies, Inits,
22886       MVLI.VarBaseDeclarations, MVLI.VarComponents);
22887 }
22888 
22889 OMPClause *Sema::ActOnOpenMPUseDeviceAddrClause(ArrayRef<Expr *> VarList,
22890                                                 const OMPVarListLocTy &Locs) {
22891   MappableVarListInfo MVLI(VarList);
22892 
22893   for (Expr *RefExpr : VarList) {
22894     assert(RefExpr && "NULL expr in OpenMP use_device_addr clause.");
22895     SourceLocation ELoc;
22896     SourceRange ERange;
22897     Expr *SimpleRefExpr = RefExpr;
22898     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange,
22899                               /*AllowArraySection=*/true);
22900     if (Res.second) {
22901       // It will be analyzed later.
22902       MVLI.ProcessedVarList.push_back(RefExpr);
22903     }
22904     ValueDecl *D = Res.first;
22905     if (!D)
22906       continue;
22907     auto *VD = dyn_cast<VarDecl>(D);
22908 
22909     // If required, build a capture to implement the privatization initialized
22910     // with the current list item value.
22911     DeclRefExpr *Ref = nullptr;
22912     if (!VD)
22913       Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/true);
22914     MVLI.ProcessedVarList.push_back(VD ? RefExpr->IgnoreParens() : Ref);
22915 
22916     // We need to add a data sharing attribute for this variable to make sure it
22917     // is correctly captured. A variable that shows up in a use_device_addr has
22918     // similar properties of a first private variable.
22919     DSAStack->addDSA(D, RefExpr->IgnoreParens(), OMPC_firstprivate, Ref);
22920 
22921     // Create a mappable component for the list item. List items in this clause
22922     // only need a component.
22923     MVLI.VarBaseDeclarations.push_back(D);
22924     MVLI.VarComponents.emplace_back();
22925     Expr *Component = SimpleRefExpr;
22926     if (VD && (isa<OMPArraySectionExpr>(RefExpr->IgnoreParenImpCasts()) ||
22927                isa<ArraySubscriptExpr>(RefExpr->IgnoreParenImpCasts())))
22928       Component = DefaultFunctionArrayLvalueConversion(SimpleRefExpr).get();
22929     MVLI.VarComponents.back().emplace_back(Component, D,
22930                                            /*IsNonContiguous=*/false);
22931   }
22932 
22933   if (MVLI.ProcessedVarList.empty())
22934     return nullptr;
22935 
22936   return OMPUseDeviceAddrClause::Create(Context, Locs, MVLI.ProcessedVarList,
22937                                         MVLI.VarBaseDeclarations,
22938                                         MVLI.VarComponents);
22939 }
22940 
22941 OMPClause *Sema::ActOnOpenMPIsDevicePtrClause(ArrayRef<Expr *> VarList,
22942                                               const OMPVarListLocTy &Locs) {
22943   MappableVarListInfo MVLI(VarList);
22944   for (Expr *RefExpr : VarList) {
22945     assert(RefExpr && "NULL expr in OpenMP is_device_ptr clause.");
22946     SourceLocation ELoc;
22947     SourceRange ERange;
22948     Expr *SimpleRefExpr = RefExpr;
22949     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
22950     if (Res.second) {
22951       // It will be analyzed later.
22952       MVLI.ProcessedVarList.push_back(RefExpr);
22953     }
22954     ValueDecl *D = Res.first;
22955     if (!D)
22956       continue;
22957 
22958     QualType Type = D->getType();
22959     // item should be a pointer or array or reference to pointer or array
22960     if (!Type.getNonReferenceType()->isPointerType() &&
22961         !Type.getNonReferenceType()->isArrayType()) {
22962       Diag(ELoc, diag::err_omp_argument_type_isdeviceptr)
22963           << 0 << RefExpr->getSourceRange();
22964       continue;
22965     }
22966 
22967     // Check if the declaration in the clause does not show up in any data
22968     // sharing attribute.
22969     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(D, /*FromParent=*/false);
22970     if (isOpenMPPrivate(DVar.CKind)) {
22971       Diag(ELoc, diag::err_omp_variable_in_given_clause_and_dsa)
22972           << getOpenMPClauseName(DVar.CKind)
22973           << getOpenMPClauseName(OMPC_is_device_ptr)
22974           << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
22975       reportOriginalDsa(*this, DSAStack, D, DVar);
22976       continue;
22977     }
22978 
22979     const Expr *ConflictExpr;
22980     if (DSAStack->checkMappableExprComponentListsForDecl(
22981             D, /*CurrentRegionOnly=*/true,
22982             [&ConflictExpr](
22983                 OMPClauseMappableExprCommon::MappableExprComponentListRef R,
22984                 OpenMPClauseKind) -> bool {
22985               ConflictExpr = R.front().getAssociatedExpression();
22986               return true;
22987             })) {
22988       Diag(ELoc, diag::err_omp_map_shared_storage) << RefExpr->getSourceRange();
22989       Diag(ConflictExpr->getExprLoc(), diag::note_used_here)
22990           << ConflictExpr->getSourceRange();
22991       continue;
22992     }
22993 
22994     // Store the components in the stack so that they can be used to check
22995     // against other clauses later on.
22996     OMPClauseMappableExprCommon::MappableComponent MC(
22997         SimpleRefExpr, D, /*IsNonContiguous=*/false);
22998     DSAStack->addMappableExpressionComponents(
22999         D, MC, /*WhereFoundClauseKind=*/OMPC_is_device_ptr);
23000 
23001     // Record the expression we've just processed.
23002     MVLI.ProcessedVarList.push_back(SimpleRefExpr);
23003 
23004     // Create a mappable component for the list item. List items in this clause
23005     // only need a component. We use a null declaration to signal fields in
23006     // 'this'.
23007     assert((isa<DeclRefExpr>(SimpleRefExpr) ||
23008             isa<CXXThisExpr>(cast<MemberExpr>(SimpleRefExpr)->getBase())) &&
23009            "Unexpected device pointer expression!");
23010     MVLI.VarBaseDeclarations.push_back(
23011         isa<DeclRefExpr>(SimpleRefExpr) ? D : nullptr);
23012     MVLI.VarComponents.resize(MVLI.VarComponents.size() + 1);
23013     MVLI.VarComponents.back().push_back(MC);
23014   }
23015 
23016   if (MVLI.ProcessedVarList.empty())
23017     return nullptr;
23018 
23019   return OMPIsDevicePtrClause::Create(Context, Locs, MVLI.ProcessedVarList,
23020                                       MVLI.VarBaseDeclarations,
23021                                       MVLI.VarComponents);
23022 }
23023 
23024 OMPClause *Sema::ActOnOpenMPHasDeviceAddrClause(ArrayRef<Expr *> VarList,
23025                                                 const OMPVarListLocTy &Locs) {
23026   MappableVarListInfo MVLI(VarList);
23027   for (Expr *RefExpr : VarList) {
23028     assert(RefExpr && "NULL expr in OpenMP has_device_addr clause.");
23029     SourceLocation ELoc;
23030     SourceRange ERange;
23031     Expr *SimpleRefExpr = RefExpr;
23032     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange,
23033                               /*AllowArraySection=*/true);
23034     if (Res.second) {
23035       // It will be analyzed later.
23036       MVLI.ProcessedVarList.push_back(RefExpr);
23037     }
23038     ValueDecl *D = Res.first;
23039     if (!D)
23040       continue;
23041 
23042     // Check if the declaration in the clause does not show up in any data
23043     // sharing attribute.
23044     DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(D, /*FromParent=*/false);
23045     if (isOpenMPPrivate(DVar.CKind)) {
23046       Diag(ELoc, diag::err_omp_variable_in_given_clause_and_dsa)
23047           << getOpenMPClauseName(DVar.CKind)
23048           << getOpenMPClauseName(OMPC_has_device_addr)
23049           << getOpenMPDirectiveName(DSAStack->getCurrentDirective());
23050       reportOriginalDsa(*this, DSAStack, D, DVar);
23051       continue;
23052     }
23053 
23054     const Expr *ConflictExpr;
23055     if (DSAStack->checkMappableExprComponentListsForDecl(
23056             D, /*CurrentRegionOnly=*/true,
23057             [&ConflictExpr](
23058                 OMPClauseMappableExprCommon::MappableExprComponentListRef R,
23059                 OpenMPClauseKind) -> bool {
23060               ConflictExpr = R.front().getAssociatedExpression();
23061               return true;
23062             })) {
23063       Diag(ELoc, diag::err_omp_map_shared_storage) << RefExpr->getSourceRange();
23064       Diag(ConflictExpr->getExprLoc(), diag::note_used_here)
23065           << ConflictExpr->getSourceRange();
23066       continue;
23067     }
23068 
23069     // Store the components in the stack so that they can be used to check
23070     // against other clauses later on.
23071     OMPClauseMappableExprCommon::MappableComponent MC(
23072         SimpleRefExpr, D, /*IsNonContiguous=*/false);
23073     DSAStack->addMappableExpressionComponents(
23074         D, MC, /*WhereFoundClauseKind=*/OMPC_has_device_addr);
23075 
23076     // Record the expression we've just processed.
23077     auto *VD = dyn_cast<VarDecl>(D);
23078     if (!VD && !CurContext->isDependentContext()) {
23079       DeclRefExpr *Ref =
23080           buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/true);
23081       assert(Ref && "has_device_addr capture failed");
23082       MVLI.ProcessedVarList.push_back(Ref);
23083     } else
23084       MVLI.ProcessedVarList.push_back(RefExpr->IgnoreParens());
23085 
23086     // Create a mappable component for the list item. List items in this clause
23087     // only need a component. We use a null declaration to signal fields in
23088     // 'this'.
23089     assert((isa<DeclRefExpr>(SimpleRefExpr) ||
23090             isa<CXXThisExpr>(cast<MemberExpr>(SimpleRefExpr)->getBase())) &&
23091            "Unexpected device pointer expression!");
23092     MVLI.VarBaseDeclarations.push_back(
23093         isa<DeclRefExpr>(SimpleRefExpr) ? D : nullptr);
23094     MVLI.VarComponents.resize(MVLI.VarComponents.size() + 1);
23095     MVLI.VarComponents.back().push_back(MC);
23096   }
23097 
23098   if (MVLI.ProcessedVarList.empty())
23099     return nullptr;
23100 
23101   return OMPHasDeviceAddrClause::Create(Context, Locs, MVLI.ProcessedVarList,
23102                                         MVLI.VarBaseDeclarations,
23103                                         MVLI.VarComponents);
23104 }
23105 
23106 OMPClause *Sema::ActOnOpenMPAllocateClause(
23107     Expr *Allocator, ArrayRef<Expr *> VarList, SourceLocation StartLoc,
23108     SourceLocation ColonLoc, SourceLocation LParenLoc, SourceLocation EndLoc) {
23109   if (Allocator) {
23110     // OpenMP [2.11.4 allocate Clause, Description]
23111     // allocator is an expression of omp_allocator_handle_t type.
23112     if (!findOMPAllocatorHandleT(*this, Allocator->getExprLoc(), DSAStack))
23113       return nullptr;
23114 
23115     ExprResult AllocatorRes = DefaultLvalueConversion(Allocator);
23116     if (AllocatorRes.isInvalid())
23117       return nullptr;
23118     AllocatorRes = PerformImplicitConversion(AllocatorRes.get(),
23119                                              DSAStack->getOMPAllocatorHandleT(),
23120                                              Sema::AA_Initializing,
23121                                              /*AllowExplicit=*/true);
23122     if (AllocatorRes.isInvalid())
23123       return nullptr;
23124     Allocator = AllocatorRes.get();
23125   } else {
23126     // OpenMP 5.0, 2.11.4 allocate Clause, Restrictions.
23127     // allocate clauses that appear on a target construct or on constructs in a
23128     // target region must specify an allocator expression unless a requires
23129     // directive with the dynamic_allocators clause is present in the same
23130     // compilation unit.
23131     if (LangOpts.OpenMPIsDevice &&
23132         !DSAStack->hasRequiresDeclWithClause<OMPDynamicAllocatorsClause>())
23133       targetDiag(StartLoc, diag::err_expected_allocator_expression);
23134   }
23135   // Analyze and build list of variables.
23136   SmallVector<Expr *, 8> Vars;
23137   for (Expr *RefExpr : VarList) {
23138     assert(RefExpr && "NULL expr in OpenMP private clause.");
23139     SourceLocation ELoc;
23140     SourceRange ERange;
23141     Expr *SimpleRefExpr = RefExpr;
23142     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
23143     if (Res.second) {
23144       // It will be analyzed later.
23145       Vars.push_back(RefExpr);
23146     }
23147     ValueDecl *D = Res.first;
23148     if (!D)
23149       continue;
23150 
23151     auto *VD = dyn_cast<VarDecl>(D);
23152     DeclRefExpr *Ref = nullptr;
23153     if (!VD && !CurContext->isDependentContext())
23154       Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/false);
23155     Vars.push_back((VD || CurContext->isDependentContext())
23156                        ? RefExpr->IgnoreParens()
23157                        : Ref);
23158   }
23159 
23160   if (Vars.empty())
23161     return nullptr;
23162 
23163   if (Allocator)
23164     DSAStack->addInnerAllocatorExpr(Allocator);
23165   return OMPAllocateClause::Create(Context, StartLoc, LParenLoc, Allocator,
23166                                    ColonLoc, EndLoc, Vars);
23167 }
23168 
23169 OMPClause *Sema::ActOnOpenMPNontemporalClause(ArrayRef<Expr *> VarList,
23170                                               SourceLocation StartLoc,
23171                                               SourceLocation LParenLoc,
23172                                               SourceLocation EndLoc) {
23173   SmallVector<Expr *, 8> Vars;
23174   for (Expr *RefExpr : VarList) {
23175     assert(RefExpr && "NULL expr in OpenMP nontemporal clause.");
23176     SourceLocation ELoc;
23177     SourceRange ERange;
23178     Expr *SimpleRefExpr = RefExpr;
23179     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange);
23180     if (Res.second)
23181       // It will be analyzed later.
23182       Vars.push_back(RefExpr);
23183     ValueDecl *D = Res.first;
23184     if (!D)
23185       continue;
23186 
23187     // OpenMP 5.0, 2.9.3.1 simd Construct, Restrictions.
23188     // A list-item cannot appear in more than one nontemporal clause.
23189     if (const Expr *PrevRef =
23190             DSAStack->addUniqueNontemporal(D, SimpleRefExpr)) {
23191       Diag(ELoc, diag::err_omp_used_in_clause_twice)
23192           << 0 << getOpenMPClauseName(OMPC_nontemporal) << ERange;
23193       Diag(PrevRef->getExprLoc(), diag::note_omp_explicit_dsa)
23194           << getOpenMPClauseName(OMPC_nontemporal);
23195       continue;
23196     }
23197 
23198     Vars.push_back(RefExpr);
23199   }
23200 
23201   if (Vars.empty())
23202     return nullptr;
23203 
23204   return OMPNontemporalClause::Create(Context, StartLoc, LParenLoc, EndLoc,
23205                                       Vars);
23206 }
23207 
23208 OMPClause *Sema::ActOnOpenMPInclusiveClause(ArrayRef<Expr *> VarList,
23209                                             SourceLocation StartLoc,
23210                                             SourceLocation LParenLoc,
23211                                             SourceLocation EndLoc) {
23212   SmallVector<Expr *, 8> Vars;
23213   for (Expr *RefExpr : VarList) {
23214     assert(RefExpr && "NULL expr in OpenMP nontemporal clause.");
23215     SourceLocation ELoc;
23216     SourceRange ERange;
23217     Expr *SimpleRefExpr = RefExpr;
23218     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange,
23219                               /*AllowArraySection=*/true);
23220     if (Res.second)
23221       // It will be analyzed later.
23222       Vars.push_back(RefExpr);
23223     ValueDecl *D = Res.first;
23224     if (!D)
23225       continue;
23226 
23227     const DSAStackTy::DSAVarData DVar =
23228         DSAStack->getTopDSA(D, /*FromParent=*/true);
23229     // OpenMP 5.0, 2.9.6, scan Directive, Restrictions.
23230     // A list item that appears in the inclusive or exclusive clause must appear
23231     // in a reduction clause with the inscan modifier on the enclosing
23232     // worksharing-loop, worksharing-loop SIMD, or simd construct.
23233     if (DVar.CKind != OMPC_reduction || DVar.Modifier != OMPC_REDUCTION_inscan)
23234       Diag(ELoc, diag::err_omp_inclusive_exclusive_not_reduction)
23235           << RefExpr->getSourceRange();
23236 
23237     if (DSAStack->getParentDirective() != OMPD_unknown)
23238       DSAStack->markDeclAsUsedInScanDirective(D);
23239     Vars.push_back(RefExpr);
23240   }
23241 
23242   if (Vars.empty())
23243     return nullptr;
23244 
23245   return OMPInclusiveClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars);
23246 }
23247 
23248 OMPClause *Sema::ActOnOpenMPExclusiveClause(ArrayRef<Expr *> VarList,
23249                                             SourceLocation StartLoc,
23250                                             SourceLocation LParenLoc,
23251                                             SourceLocation EndLoc) {
23252   SmallVector<Expr *, 8> Vars;
23253   for (Expr *RefExpr : VarList) {
23254     assert(RefExpr && "NULL expr in OpenMP nontemporal clause.");
23255     SourceLocation ELoc;
23256     SourceRange ERange;
23257     Expr *SimpleRefExpr = RefExpr;
23258     auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange,
23259                               /*AllowArraySection=*/true);
23260     if (Res.second)
23261       // It will be analyzed later.
23262       Vars.push_back(RefExpr);
23263     ValueDecl *D = Res.first;
23264     if (!D)
23265       continue;
23266 
23267     OpenMPDirectiveKind ParentDirective = DSAStack->getParentDirective();
23268     DSAStackTy::DSAVarData DVar;
23269     if (ParentDirective != OMPD_unknown)
23270       DVar = DSAStack->getTopDSA(D, /*FromParent=*/true);
23271     // OpenMP 5.0, 2.9.6, scan Directive, Restrictions.
23272     // A list item that appears in the inclusive or exclusive clause must appear
23273     // in a reduction clause with the inscan modifier on the enclosing
23274     // worksharing-loop, worksharing-loop SIMD, or simd construct.
23275     if (ParentDirective == OMPD_unknown || DVar.CKind != OMPC_reduction ||
23276         DVar.Modifier != OMPC_REDUCTION_inscan) {
23277       Diag(ELoc, diag::err_omp_inclusive_exclusive_not_reduction)
23278           << RefExpr->getSourceRange();
23279     } else {
23280       DSAStack->markDeclAsUsedInScanDirective(D);
23281     }
23282     Vars.push_back(RefExpr);
23283   }
23284 
23285   if (Vars.empty())
23286     return nullptr;
23287 
23288   return OMPExclusiveClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars);
23289 }
23290 
23291 /// Tries to find omp_alloctrait_t type.
23292 static bool findOMPAlloctraitT(Sema &S, SourceLocation Loc, DSAStackTy *Stack) {
23293   QualType OMPAlloctraitT = Stack->getOMPAlloctraitT();
23294   if (!OMPAlloctraitT.isNull())
23295     return true;
23296   IdentifierInfo &II = S.PP.getIdentifierTable().get("omp_alloctrait_t");
23297   ParsedType PT = S.getTypeName(II, Loc, S.getCurScope());
23298   if (!PT.getAsOpaquePtr() || PT.get().isNull()) {
23299     S.Diag(Loc, diag::err_omp_implied_type_not_found) << "omp_alloctrait_t";
23300     return false;
23301   }
23302   Stack->setOMPAlloctraitT(PT.get());
23303   return true;
23304 }
23305 
23306 OMPClause *Sema::ActOnOpenMPUsesAllocatorClause(
23307     SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc,
23308     ArrayRef<UsesAllocatorsData> Data) {
23309   // OpenMP [2.12.5, target Construct]
23310   // allocator is an identifier of omp_allocator_handle_t type.
23311   if (!findOMPAllocatorHandleT(*this, StartLoc, DSAStack))
23312     return nullptr;
23313   // OpenMP [2.12.5, target Construct]
23314   // allocator-traits-array is an identifier of const omp_alloctrait_t * type.
23315   if (llvm::any_of(
23316           Data,
23317           [](const UsesAllocatorsData &D) { return D.AllocatorTraits; }) &&
23318       !findOMPAlloctraitT(*this, StartLoc, DSAStack))
23319     return nullptr;
23320   llvm::SmallPtrSet<CanonicalDeclPtr<Decl>, 4> PredefinedAllocators;
23321   for (int I = 0; I < OMPAllocateDeclAttr::OMPUserDefinedMemAlloc; ++I) {
23322     auto AllocatorKind = static_cast<OMPAllocateDeclAttr::AllocatorTypeTy>(I);
23323     StringRef Allocator =
23324         OMPAllocateDeclAttr::ConvertAllocatorTypeTyToStr(AllocatorKind);
23325     DeclarationName AllocatorName = &Context.Idents.get(Allocator);
23326     PredefinedAllocators.insert(LookupSingleName(
23327         TUScope, AllocatorName, StartLoc, Sema::LookupAnyName));
23328   }
23329 
23330   SmallVector<OMPUsesAllocatorsClause::Data, 4> NewData;
23331   for (const UsesAllocatorsData &D : Data) {
23332     Expr *AllocatorExpr = nullptr;
23333     // Check allocator expression.
23334     if (D.Allocator->isTypeDependent()) {
23335       AllocatorExpr = D.Allocator;
23336     } else {
23337       // Traits were specified - need to assign new allocator to the specified
23338       // allocator, so it must be an lvalue.
23339       AllocatorExpr = D.Allocator->IgnoreParenImpCasts();
23340       auto *DRE = dyn_cast<DeclRefExpr>(AllocatorExpr);
23341       bool IsPredefinedAllocator = false;
23342       if (DRE)
23343         IsPredefinedAllocator = PredefinedAllocators.count(DRE->getDecl());
23344       if (!DRE ||
23345           !(Context.hasSameUnqualifiedType(
23346                 AllocatorExpr->getType(), DSAStack->getOMPAllocatorHandleT()) ||
23347             Context.typesAreCompatible(AllocatorExpr->getType(),
23348                                        DSAStack->getOMPAllocatorHandleT(),
23349                                        /*CompareUnqualified=*/true)) ||
23350           (!IsPredefinedAllocator &&
23351            (AllocatorExpr->getType().isConstant(Context) ||
23352             !AllocatorExpr->isLValue()))) {
23353         Diag(D.Allocator->getExprLoc(), diag::err_omp_var_expected)
23354             << "omp_allocator_handle_t" << (DRE ? 1 : 0)
23355             << AllocatorExpr->getType() << D.Allocator->getSourceRange();
23356         continue;
23357       }
23358       // OpenMP [2.12.5, target Construct]
23359       // Predefined allocators appearing in a uses_allocators clause cannot have
23360       // traits specified.
23361       if (IsPredefinedAllocator && D.AllocatorTraits) {
23362         Diag(D.AllocatorTraits->getExprLoc(),
23363              diag::err_omp_predefined_allocator_with_traits)
23364             << D.AllocatorTraits->getSourceRange();
23365         Diag(D.Allocator->getExprLoc(), diag::note_omp_predefined_allocator)
23366             << cast<NamedDecl>(DRE->getDecl())->getName()
23367             << D.Allocator->getSourceRange();
23368         continue;
23369       }
23370       // OpenMP [2.12.5, target Construct]
23371       // Non-predefined allocators appearing in a uses_allocators clause must
23372       // have traits specified.
23373       if (!IsPredefinedAllocator && !D.AllocatorTraits) {
23374         Diag(D.Allocator->getExprLoc(),
23375              diag::err_omp_nonpredefined_allocator_without_traits);
23376         continue;
23377       }
23378       // No allocator traits - just convert it to rvalue.
23379       if (!D.AllocatorTraits)
23380         AllocatorExpr = DefaultLvalueConversion(AllocatorExpr).get();
23381       DSAStack->addUsesAllocatorsDecl(
23382           DRE->getDecl(),
23383           IsPredefinedAllocator
23384               ? DSAStackTy::UsesAllocatorsDeclKind::PredefinedAllocator
23385               : DSAStackTy::UsesAllocatorsDeclKind::UserDefinedAllocator);
23386     }
23387     Expr *AllocatorTraitsExpr = nullptr;
23388     if (D.AllocatorTraits) {
23389       if (D.AllocatorTraits->isTypeDependent()) {
23390         AllocatorTraitsExpr = D.AllocatorTraits;
23391       } else {
23392         // OpenMP [2.12.5, target Construct]
23393         // Arrays that contain allocator traits that appear in a uses_allocators
23394         // clause must be constant arrays, have constant values and be defined
23395         // in the same scope as the construct in which the clause appears.
23396         AllocatorTraitsExpr = D.AllocatorTraits->IgnoreParenImpCasts();
23397         // Check that traits expr is a constant array.
23398         QualType TraitTy;
23399         if (const ArrayType *Ty =
23400                 AllocatorTraitsExpr->getType()->getAsArrayTypeUnsafe())
23401           if (const auto *ConstArrayTy = dyn_cast<ConstantArrayType>(Ty))
23402             TraitTy = ConstArrayTy->getElementType();
23403         if (TraitTy.isNull() ||
23404             !(Context.hasSameUnqualifiedType(TraitTy,
23405                                              DSAStack->getOMPAlloctraitT()) ||
23406               Context.typesAreCompatible(TraitTy, DSAStack->getOMPAlloctraitT(),
23407                                          /*CompareUnqualified=*/true))) {
23408           Diag(D.AllocatorTraits->getExprLoc(),
23409                diag::err_omp_expected_array_alloctraits)
23410               << AllocatorTraitsExpr->getType();
23411           continue;
23412         }
23413         // Do not map by default allocator traits if it is a standalone
23414         // variable.
23415         if (auto *DRE = dyn_cast<DeclRefExpr>(AllocatorTraitsExpr))
23416           DSAStack->addUsesAllocatorsDecl(
23417               DRE->getDecl(),
23418               DSAStackTy::UsesAllocatorsDeclKind::AllocatorTrait);
23419       }
23420     }
23421     OMPUsesAllocatorsClause::Data &NewD = NewData.emplace_back();
23422     NewD.Allocator = AllocatorExpr;
23423     NewD.AllocatorTraits = AllocatorTraitsExpr;
23424     NewD.LParenLoc = D.LParenLoc;
23425     NewD.RParenLoc = D.RParenLoc;
23426   }
23427   return OMPUsesAllocatorsClause::Create(Context, StartLoc, LParenLoc, EndLoc,
23428                                          NewData);
23429 }
23430 
23431 OMPClause *Sema::ActOnOpenMPAffinityClause(
23432     SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation ColonLoc,
23433     SourceLocation EndLoc, Expr *Modifier, ArrayRef<Expr *> Locators) {
23434   SmallVector<Expr *, 8> Vars;
23435   for (Expr *RefExpr : Locators) {
23436     assert(RefExpr && "NULL expr in OpenMP shared clause.");
23437     if (isa<DependentScopeDeclRefExpr>(RefExpr) || RefExpr->isTypeDependent()) {
23438       // It will be analyzed later.
23439       Vars.push_back(RefExpr);
23440       continue;
23441     }
23442 
23443     SourceLocation ELoc = RefExpr->getExprLoc();
23444     Expr *SimpleExpr = RefExpr->IgnoreParenImpCasts();
23445 
23446     if (!SimpleExpr->isLValue()) {
23447       Diag(ELoc, diag::err_omp_expected_addressable_lvalue_or_array_item)
23448           << 1 << 0 << RefExpr->getSourceRange();
23449       continue;
23450     }
23451 
23452     ExprResult Res;
23453     {
23454       Sema::TentativeAnalysisScope Trap(*this);
23455       Res = CreateBuiltinUnaryOp(ELoc, UO_AddrOf, SimpleExpr);
23456     }
23457     if (!Res.isUsable() && !isa<OMPArraySectionExpr>(SimpleExpr) &&
23458         !isa<OMPArrayShapingExpr>(SimpleExpr)) {
23459       Diag(ELoc, diag::err_omp_expected_addressable_lvalue_or_array_item)
23460           << 1 << 0 << RefExpr->getSourceRange();
23461       continue;
23462     }
23463     Vars.push_back(SimpleExpr);
23464   }
23465 
23466   return OMPAffinityClause::Create(Context, StartLoc, LParenLoc, ColonLoc,
23467                                    EndLoc, Modifier, Vars);
23468 }
23469 
23470 OMPClause *Sema::ActOnOpenMPBindClause(OpenMPBindClauseKind Kind,
23471                                        SourceLocation KindLoc,
23472                                        SourceLocation StartLoc,
23473                                        SourceLocation LParenLoc,
23474                                        SourceLocation EndLoc) {
23475   if (Kind == OMPC_BIND_unknown) {
23476     Diag(KindLoc, diag::err_omp_unexpected_clause_value)
23477         << getListOfPossibleValues(OMPC_bind, /*First=*/0,
23478                                    /*Last=*/unsigned(OMPC_BIND_unknown))
23479         << getOpenMPClauseName(OMPC_bind);
23480     return nullptr;
23481   }
23482 
23483   return OMPBindClause::Create(Context, Kind, KindLoc, StartLoc, LParenLoc,
23484                                EndLoc);
23485 }
23486