1 //===--- SemaOpenMP.cpp - Semantic Analysis for OpenMP constructs ---------===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 /// \file 10 /// \brief This file implements semantic analysis for OpenMP directives and 11 /// clauses. 12 /// 13 //===----------------------------------------------------------------------===// 14 15 #include "TreeTransform.h" 16 #include "clang/AST/ASTContext.h" 17 #include "clang/AST/ASTMutationListener.h" 18 #include "clang/AST/Decl.h" 19 #include "clang/AST/DeclCXX.h" 20 #include "clang/AST/DeclOpenMP.h" 21 #include "clang/AST/StmtCXX.h" 22 #include "clang/AST/StmtOpenMP.h" 23 #include "clang/AST/StmtVisitor.h" 24 #include "clang/Basic/OpenMPKinds.h" 25 #include "clang/Basic/TargetInfo.h" 26 #include "clang/Lex/Preprocessor.h" 27 #include "clang/Sema/Initialization.h" 28 #include "clang/Sema/Lookup.h" 29 #include "clang/Sema/Scope.h" 30 #include "clang/Sema/ScopeInfo.h" 31 #include "clang/Sema/SemaInternal.h" 32 using namespace clang; 33 34 //===----------------------------------------------------------------------===// 35 // Stack of data-sharing attributes for variables 36 //===----------------------------------------------------------------------===// 37 38 namespace { 39 /// \brief Default data sharing attributes, which can be applied to directive. 40 enum DefaultDataSharingAttributes { 41 DSA_unspecified = 0, /// \brief Data sharing attribute not specified. 42 DSA_none = 1 << 0, /// \brief Default data sharing attribute 'none'. 43 DSA_shared = 1 << 1 /// \brief Default data sharing attribute 'shared'. 44 }; 45 46 template <class T> struct MatchesAny { 47 explicit MatchesAny(ArrayRef<T> Arr) : Arr(std::move(Arr)) {} 48 bool operator()(T Kind) { 49 for (auto KindEl : Arr) 50 if (KindEl == Kind) 51 return true; 52 return false; 53 } 54 55 private: 56 ArrayRef<T> Arr; 57 }; 58 struct MatchesAlways { 59 MatchesAlways() {} 60 template <class T> bool operator()(T) { return true; } 61 }; 62 63 typedef MatchesAny<OpenMPClauseKind> MatchesAnyClause; 64 typedef MatchesAny<OpenMPDirectiveKind> MatchesAnyDirective; 65 66 /// \brief 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; 72 OpenMPClauseKind CKind; 73 DeclRefExpr *RefExpr; 74 SourceLocation ImplicitDSALoc; 75 DSAVarData() 76 : DKind(OMPD_unknown), CKind(OMPC_unknown), RefExpr(nullptr), 77 ImplicitDSALoc() {} 78 }; 79 80 public: 81 struct MapInfo { 82 Expr *RefExpr; 83 }; 84 85 private: 86 struct DSAInfo { 87 OpenMPClauseKind Attributes; 88 DeclRefExpr *RefExpr; 89 }; 90 typedef llvm::SmallDenseMap<VarDecl *, DSAInfo, 64> DeclSAMapTy; 91 typedef llvm::SmallDenseMap<VarDecl *, DeclRefExpr *, 64> AlignedMapTy; 92 typedef llvm::DenseMap<VarDecl *, unsigned> LoopControlVariablesMapTy; 93 typedef llvm::SmallDenseMap<VarDecl *, MapInfo, 64> MappedDeclsTy; 94 typedef llvm::StringMap<std::pair<OMPCriticalDirective *, llvm::APSInt>> 95 CriticalsWithHintsTy; 96 97 struct SharingMapTy { 98 DeclSAMapTy SharingMap; 99 AlignedMapTy AlignedMap; 100 MappedDeclsTy MappedDecls; 101 LoopControlVariablesMapTy LCVMap; 102 DefaultDataSharingAttributes DefaultAttr; 103 SourceLocation DefaultAttrLoc; 104 OpenMPDirectiveKind Directive; 105 DeclarationNameInfo DirectiveName; 106 Scope *CurScope; 107 SourceLocation ConstructLoc; 108 /// \brief first argument (Expr *) contains optional argument of the 109 /// 'ordered' clause, the second one is true if the regions has 'ordered' 110 /// clause, false otherwise. 111 llvm::PointerIntPair<Expr *, 1, bool> OrderedRegion; 112 bool NowaitRegion; 113 bool CancelRegion; 114 unsigned AssociatedLoops; 115 SourceLocation InnerTeamsRegionLoc; 116 SharingMapTy(OpenMPDirectiveKind DKind, DeclarationNameInfo Name, 117 Scope *CurScope, SourceLocation Loc) 118 : SharingMap(), AlignedMap(), LCVMap(), DefaultAttr(DSA_unspecified), 119 Directive(DKind), DirectiveName(std::move(Name)), CurScope(CurScope), 120 ConstructLoc(Loc), OrderedRegion(), NowaitRegion(false), 121 CancelRegion(false), AssociatedLoops(1), InnerTeamsRegionLoc() {} 122 SharingMapTy() 123 : SharingMap(), AlignedMap(), LCVMap(), DefaultAttr(DSA_unspecified), 124 Directive(OMPD_unknown), DirectiveName(), CurScope(nullptr), 125 ConstructLoc(), OrderedRegion(), NowaitRegion(false), 126 CancelRegion(false), AssociatedLoops(1), InnerTeamsRegionLoc() {} 127 }; 128 129 typedef SmallVector<SharingMapTy, 64> StackTy; 130 131 /// \brief Stack of used declaration and their data-sharing attributes. 132 StackTy Stack; 133 /// \brief true, if check for DSA must be from parent directive, false, if 134 /// from current directive. 135 OpenMPClauseKind ClauseKindMode; 136 Sema &SemaRef; 137 bool ForceCapturing; 138 CriticalsWithHintsTy Criticals; 139 140 typedef SmallVector<SharingMapTy, 8>::reverse_iterator reverse_iterator; 141 142 DSAVarData getDSA(StackTy::reverse_iterator Iter, VarDecl *D); 143 144 /// \brief Checks if the variable is a local for OpenMP region. 145 bool isOpenMPLocal(VarDecl *D, StackTy::reverse_iterator Iter); 146 147 public: 148 explicit DSAStackTy(Sema &S) 149 : Stack(1), ClauseKindMode(OMPC_unknown), SemaRef(S), 150 ForceCapturing(false) {} 151 152 bool isClauseParsingMode() const { return ClauseKindMode != OMPC_unknown; } 153 void setClauseParsingMode(OpenMPClauseKind K) { ClauseKindMode = K; } 154 155 bool isForceVarCapturing() const { return ForceCapturing; } 156 void setForceVarCapturing(bool V) { ForceCapturing = V; } 157 158 void push(OpenMPDirectiveKind DKind, const DeclarationNameInfo &DirName, 159 Scope *CurScope, SourceLocation Loc) { 160 Stack.push_back(SharingMapTy(DKind, DirName, CurScope, Loc)); 161 Stack.back().DefaultAttrLoc = Loc; 162 } 163 164 void pop() { 165 assert(Stack.size() > 1 && "Data-sharing attributes stack is empty!"); 166 Stack.pop_back(); 167 } 168 169 void addCriticalWithHint(OMPCriticalDirective *D, llvm::APSInt Hint) { 170 Criticals[D->getDirectiveName().getAsString()] = std::make_pair(D, Hint); 171 } 172 const std::pair<OMPCriticalDirective *, llvm::APSInt> 173 getCriticalWithHint(const DeclarationNameInfo &Name) const { 174 auto I = Criticals.find(Name.getAsString()); 175 if (I != Criticals.end()) 176 return I->second; 177 return std::make_pair(nullptr, llvm::APSInt()); 178 } 179 /// \brief If 'aligned' declaration for given variable \a D was not seen yet, 180 /// add it and return NULL; otherwise return previous occurrence's expression 181 /// for diagnostics. 182 DeclRefExpr *addUniqueAligned(VarDecl *D, DeclRefExpr *NewDE); 183 184 /// \brief Register specified variable as loop control variable. 185 void addLoopControlVariable(VarDecl *D); 186 /// \brief Check if the specified variable is a loop control variable for 187 /// current region. 188 /// \return The index of the loop control variable in the list of associated 189 /// for-loops (from outer to inner). 190 unsigned isLoopControlVariable(VarDecl *D); 191 /// \brief Check if the specified variable is a loop control variable for 192 /// parent region. 193 /// \return The index of the loop control variable in the list of associated 194 /// for-loops (from outer to inner). 195 unsigned isParentLoopControlVariable(VarDecl *D); 196 /// \brief Get the loop control variable for the I-th loop (or nullptr) in 197 /// parent directive. 198 VarDecl *getParentLoopControlVariable(unsigned I); 199 200 /// \brief Adds explicit data sharing attribute to the specified declaration. 201 void addDSA(VarDecl *D, DeclRefExpr *E, OpenMPClauseKind A); 202 203 /// \brief Returns data sharing attributes from top of the stack for the 204 /// specified declaration. 205 DSAVarData getTopDSA(VarDecl *D, bool FromParent); 206 /// \brief Returns data-sharing attributes for the specified declaration. 207 DSAVarData getImplicitDSA(VarDecl *D, bool FromParent); 208 /// \brief Checks if the specified variables has data-sharing attributes which 209 /// match specified \a CPred predicate in any directive which matches \a DPred 210 /// predicate. 211 template <class ClausesPredicate, class DirectivesPredicate> 212 DSAVarData hasDSA(VarDecl *D, ClausesPredicate CPred, 213 DirectivesPredicate DPred, bool FromParent); 214 /// \brief Checks if the specified variables has data-sharing attributes which 215 /// match specified \a CPred predicate in any innermost directive which 216 /// matches \a DPred predicate. 217 template <class ClausesPredicate, class DirectivesPredicate> 218 DSAVarData hasInnermostDSA(VarDecl *D, ClausesPredicate CPred, 219 DirectivesPredicate DPred, 220 bool FromParent); 221 /// \brief Checks if the specified variables has explicit data-sharing 222 /// attributes which match specified \a CPred predicate at the specified 223 /// OpenMP region. 224 bool hasExplicitDSA(VarDecl *D, 225 const llvm::function_ref<bool(OpenMPClauseKind)> &CPred, 226 unsigned Level); 227 228 /// \brief Returns true if the directive at level \Level matches in the 229 /// specified \a DPred predicate. 230 bool hasExplicitDirective( 231 const llvm::function_ref<bool(OpenMPDirectiveKind)> &DPred, 232 unsigned Level); 233 234 /// \brief Finds a directive which matches specified \a DPred predicate. 235 template <class NamedDirectivesPredicate> 236 bool hasDirective(NamedDirectivesPredicate DPred, bool FromParent); 237 238 /// \brief Returns currently analyzed directive. 239 OpenMPDirectiveKind getCurrentDirective() const { 240 return Stack.back().Directive; 241 } 242 /// \brief Returns parent directive. 243 OpenMPDirectiveKind getParentDirective() const { 244 if (Stack.size() > 2) 245 return Stack[Stack.size() - 2].Directive; 246 return OMPD_unknown; 247 } 248 /// \brief Return the directive associated with the provided scope. 249 OpenMPDirectiveKind getDirectiveForScope(const Scope *S) const; 250 251 /// \brief Set default data sharing attribute to none. 252 void setDefaultDSANone(SourceLocation Loc) { 253 Stack.back().DefaultAttr = DSA_none; 254 Stack.back().DefaultAttrLoc = Loc; 255 } 256 /// \brief Set default data sharing attribute to shared. 257 void setDefaultDSAShared(SourceLocation Loc) { 258 Stack.back().DefaultAttr = DSA_shared; 259 Stack.back().DefaultAttrLoc = Loc; 260 } 261 262 DefaultDataSharingAttributes getDefaultDSA() const { 263 return Stack.back().DefaultAttr; 264 } 265 SourceLocation getDefaultDSALocation() const { 266 return Stack.back().DefaultAttrLoc; 267 } 268 269 /// \brief Checks if the specified variable is a threadprivate. 270 bool isThreadPrivate(VarDecl *D) { 271 DSAVarData DVar = getTopDSA(D, false); 272 return isOpenMPThreadPrivate(DVar.CKind); 273 } 274 275 /// \brief Marks current region as ordered (it has an 'ordered' clause). 276 void setOrderedRegion(bool IsOrdered, Expr *Param) { 277 Stack.back().OrderedRegion.setInt(IsOrdered); 278 Stack.back().OrderedRegion.setPointer(Param); 279 } 280 /// \brief Returns true, if parent region is ordered (has associated 281 /// 'ordered' clause), false - otherwise. 282 bool isParentOrderedRegion() const { 283 if (Stack.size() > 2) 284 return Stack[Stack.size() - 2].OrderedRegion.getInt(); 285 return false; 286 } 287 /// \brief Returns optional parameter for the ordered region. 288 Expr *getParentOrderedRegionParam() const { 289 if (Stack.size() > 2) 290 return Stack[Stack.size() - 2].OrderedRegion.getPointer(); 291 return nullptr; 292 } 293 /// \brief Marks current region as nowait (it has a 'nowait' clause). 294 void setNowaitRegion(bool IsNowait = true) { 295 Stack.back().NowaitRegion = IsNowait; 296 } 297 /// \brief Returns true, if parent region is nowait (has associated 298 /// 'nowait' clause), false - otherwise. 299 bool isParentNowaitRegion() const { 300 if (Stack.size() > 2) 301 return Stack[Stack.size() - 2].NowaitRegion; 302 return false; 303 } 304 /// \brief Marks parent region as cancel region. 305 void setParentCancelRegion(bool Cancel = true) { 306 if (Stack.size() > 2) 307 Stack[Stack.size() - 2].CancelRegion = 308 Stack[Stack.size() - 2].CancelRegion || Cancel; 309 } 310 /// \brief Return true if current region has inner cancel construct. 311 bool isCancelRegion() const { 312 return Stack.back().CancelRegion; 313 } 314 315 /// \brief Set collapse value for the region. 316 void setAssociatedLoops(unsigned Val) { Stack.back().AssociatedLoops = Val; } 317 /// \brief Return collapse value for region. 318 unsigned getAssociatedLoops() const { return Stack.back().AssociatedLoops; } 319 320 /// \brief Marks current target region as one with closely nested teams 321 /// region. 322 void setParentTeamsRegionLoc(SourceLocation TeamsRegionLoc) { 323 if (Stack.size() > 2) 324 Stack[Stack.size() - 2].InnerTeamsRegionLoc = TeamsRegionLoc; 325 } 326 /// \brief Returns true, if current region has closely nested teams region. 327 bool hasInnerTeamsRegion() const { 328 return getInnerTeamsRegionLoc().isValid(); 329 } 330 /// \brief Returns location of the nested teams region (if any). 331 SourceLocation getInnerTeamsRegionLoc() const { 332 if (Stack.size() > 1) 333 return Stack.back().InnerTeamsRegionLoc; 334 return SourceLocation(); 335 } 336 337 Scope *getCurScope() const { return Stack.back().CurScope; } 338 Scope *getCurScope() { return Stack.back().CurScope; } 339 SourceLocation getConstructLoc() { return Stack.back().ConstructLoc; } 340 341 MapInfo getMapInfoForVar(VarDecl *VD) { 342 MapInfo VarMI = {0}; 343 for (auto Cnt = Stack.size() - 1; Cnt > 0; --Cnt) { 344 if (Stack[Cnt].MappedDecls.count(VD)) { 345 VarMI = Stack[Cnt].MappedDecls[VD]; 346 break; 347 } 348 } 349 return VarMI; 350 } 351 352 void addMapInfoForVar(VarDecl *VD, MapInfo MI) { 353 if (Stack.size() > 1) { 354 Stack.back().MappedDecls[VD] = MI; 355 } 356 } 357 358 MapInfo IsMappedInCurrentRegion(VarDecl *VD) { 359 assert(Stack.size() > 1 && "Target level is 0"); 360 MapInfo VarMI = {0}; 361 if (Stack.size() > 1 && Stack.back().MappedDecls.count(VD)) { 362 VarMI = Stack.back().MappedDecls[VD]; 363 } 364 return VarMI; 365 } 366 }; 367 bool isParallelOrTaskRegion(OpenMPDirectiveKind DKind) { 368 return isOpenMPParallelDirective(DKind) || DKind == OMPD_task || 369 isOpenMPTeamsDirective(DKind) || DKind == OMPD_unknown || 370 isOpenMPTaskLoopDirective(DKind); 371 } 372 } // namespace 373 374 DSAStackTy::DSAVarData DSAStackTy::getDSA(StackTy::reverse_iterator Iter, 375 VarDecl *D) { 376 D = D->getCanonicalDecl(); 377 DSAVarData DVar; 378 if (Iter == std::prev(Stack.rend())) { 379 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 380 // in a region but not in construct] 381 // File-scope or namespace-scope variables referenced in called routines 382 // in the region are shared unless they appear in a threadprivate 383 // directive. 384 if (!D->isFunctionOrMethodVarDecl() && !isa<ParmVarDecl>(D)) 385 DVar.CKind = OMPC_shared; 386 387 // OpenMP [2.9.1.2, Data-sharing Attribute Rules for Variables Referenced 388 // in a region but not in construct] 389 // Variables with static storage duration that are declared in called 390 // routines in the region are shared. 391 if (D->hasGlobalStorage()) 392 DVar.CKind = OMPC_shared; 393 394 return DVar; 395 } 396 397 DVar.DKind = Iter->Directive; 398 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 399 // in a Construct, C/C++, predetermined, p.1] 400 // Variables with automatic storage duration that are declared in a scope 401 // inside the construct are private. 402 if (isOpenMPLocal(D, Iter) && D->isLocalVarDecl() && 403 (D->getStorageClass() == SC_Auto || D->getStorageClass() == SC_None)) { 404 DVar.CKind = OMPC_private; 405 return DVar; 406 } 407 408 // Explicitly specified attributes and local variables with predetermined 409 // attributes. 410 if (Iter->SharingMap.count(D)) { 411 DVar.RefExpr = Iter->SharingMap[D].RefExpr; 412 DVar.CKind = Iter->SharingMap[D].Attributes; 413 DVar.ImplicitDSALoc = Iter->DefaultAttrLoc; 414 return DVar; 415 } 416 417 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 418 // in a Construct, C/C++, implicitly determined, p.1] 419 // In a parallel or task construct, the data-sharing attributes of these 420 // variables are determined by the default clause, if present. 421 switch (Iter->DefaultAttr) { 422 case DSA_shared: 423 DVar.CKind = OMPC_shared; 424 DVar.ImplicitDSALoc = Iter->DefaultAttrLoc; 425 return DVar; 426 case DSA_none: 427 return DVar; 428 case DSA_unspecified: 429 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 430 // in a Construct, implicitly determined, p.2] 431 // In a parallel construct, if no default clause is present, these 432 // variables are shared. 433 DVar.ImplicitDSALoc = Iter->DefaultAttrLoc; 434 if (isOpenMPParallelDirective(DVar.DKind) || 435 isOpenMPTeamsDirective(DVar.DKind)) { 436 DVar.CKind = OMPC_shared; 437 return DVar; 438 } 439 440 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 441 // in a Construct, implicitly determined, p.4] 442 // In a task construct, if no default clause is present, a variable that in 443 // the enclosing context is determined to be shared by all implicit tasks 444 // bound to the current team is shared. 445 if (DVar.DKind == OMPD_task) { 446 DSAVarData DVarTemp; 447 for (StackTy::reverse_iterator I = std::next(Iter), EE = Stack.rend(); 448 I != EE; ++I) { 449 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables 450 // Referenced 451 // in a Construct, implicitly determined, p.6] 452 // In a task construct, if no default clause is present, a variable 453 // whose data-sharing attribute is not determined by the rules above is 454 // firstprivate. 455 DVarTemp = getDSA(I, D); 456 if (DVarTemp.CKind != OMPC_shared) { 457 DVar.RefExpr = nullptr; 458 DVar.DKind = OMPD_task; 459 DVar.CKind = OMPC_firstprivate; 460 return DVar; 461 } 462 if (isParallelOrTaskRegion(I->Directive)) 463 break; 464 } 465 DVar.DKind = OMPD_task; 466 DVar.CKind = 467 (DVarTemp.CKind == OMPC_unknown) ? OMPC_firstprivate : OMPC_shared; 468 return DVar; 469 } 470 } 471 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 472 // in a Construct, implicitly determined, p.3] 473 // For constructs other than task, if no default clause is present, these 474 // variables inherit their data-sharing attributes from the enclosing 475 // context. 476 return getDSA(std::next(Iter), D); 477 } 478 479 DeclRefExpr *DSAStackTy::addUniqueAligned(VarDecl *D, DeclRefExpr *NewDE) { 480 assert(Stack.size() > 1 && "Data sharing attributes stack is empty"); 481 D = D->getCanonicalDecl(); 482 auto It = Stack.back().AlignedMap.find(D); 483 if (It == Stack.back().AlignedMap.end()) { 484 assert(NewDE && "Unexpected nullptr expr to be added into aligned map"); 485 Stack.back().AlignedMap[D] = NewDE; 486 return nullptr; 487 } else { 488 assert(It->second && "Unexpected nullptr expr in the aligned map"); 489 return It->second; 490 } 491 return nullptr; 492 } 493 494 void DSAStackTy::addLoopControlVariable(VarDecl *D) { 495 assert(Stack.size() > 1 && "Data-sharing attributes stack is empty"); 496 D = D->getCanonicalDecl(); 497 Stack.back().LCVMap.insert(std::make_pair(D, Stack.back().LCVMap.size() + 1)); 498 } 499 500 unsigned DSAStackTy::isLoopControlVariable(VarDecl *D) { 501 assert(Stack.size() > 1 && "Data-sharing attributes stack is empty"); 502 D = D->getCanonicalDecl(); 503 return Stack.back().LCVMap.count(D) > 0 ? Stack.back().LCVMap[D] : 0; 504 } 505 506 unsigned DSAStackTy::isParentLoopControlVariable(VarDecl *D) { 507 assert(Stack.size() > 2 && "Data-sharing attributes stack is empty"); 508 D = D->getCanonicalDecl(); 509 return Stack[Stack.size() - 2].LCVMap.count(D) > 0 510 ? Stack[Stack.size() - 2].LCVMap[D] 511 : 0; 512 } 513 514 VarDecl *DSAStackTy::getParentLoopControlVariable(unsigned I) { 515 assert(Stack.size() > 2 && "Data-sharing attributes stack is empty"); 516 if (Stack[Stack.size() - 2].LCVMap.size() < I) 517 return nullptr; 518 for (auto &Pair : Stack[Stack.size() - 2].LCVMap) { 519 if (Pair.second == I) 520 return Pair.first; 521 } 522 return nullptr; 523 } 524 525 void DSAStackTy::addDSA(VarDecl *D, DeclRefExpr *E, OpenMPClauseKind A) { 526 D = D->getCanonicalDecl(); 527 if (A == OMPC_threadprivate) { 528 Stack[0].SharingMap[D].Attributes = A; 529 Stack[0].SharingMap[D].RefExpr = E; 530 } else { 531 assert(Stack.size() > 1 && "Data-sharing attributes stack is empty"); 532 Stack.back().SharingMap[D].Attributes = A; 533 Stack.back().SharingMap[D].RefExpr = E; 534 } 535 } 536 537 bool DSAStackTy::isOpenMPLocal(VarDecl *D, StackTy::reverse_iterator Iter) { 538 D = D->getCanonicalDecl(); 539 if (Stack.size() > 2) { 540 reverse_iterator I = Iter, E = std::prev(Stack.rend()); 541 Scope *TopScope = nullptr; 542 while (I != E && !isParallelOrTaskRegion(I->Directive)) { 543 ++I; 544 } 545 if (I == E) 546 return false; 547 TopScope = I->CurScope ? I->CurScope->getParent() : nullptr; 548 Scope *CurScope = getCurScope(); 549 while (CurScope != TopScope && !CurScope->isDeclScope(D)) { 550 CurScope = CurScope->getParent(); 551 } 552 return CurScope != TopScope; 553 } 554 return false; 555 } 556 557 /// \brief Build a variable declaration for OpenMP loop iteration variable. 558 static VarDecl *buildVarDecl(Sema &SemaRef, SourceLocation Loc, QualType Type, 559 StringRef Name, const AttrVec *Attrs = nullptr) { 560 DeclContext *DC = SemaRef.CurContext; 561 IdentifierInfo *II = &SemaRef.PP.getIdentifierTable().get(Name); 562 TypeSourceInfo *TInfo = SemaRef.Context.getTrivialTypeSourceInfo(Type, Loc); 563 VarDecl *Decl = 564 VarDecl::Create(SemaRef.Context, DC, Loc, Loc, II, Type, TInfo, SC_None); 565 if (Attrs) { 566 for (specific_attr_iterator<AlignedAttr> I(Attrs->begin()), E(Attrs->end()); 567 I != E; ++I) 568 Decl->addAttr(*I); 569 } 570 Decl->setImplicit(); 571 return Decl; 572 } 573 574 static DeclRefExpr *buildDeclRefExpr(Sema &S, VarDecl *D, QualType Ty, 575 SourceLocation Loc, 576 bool RefersToCapture = false) { 577 D->setReferenced(); 578 D->markUsed(S.Context); 579 return DeclRefExpr::Create(S.getASTContext(), NestedNameSpecifierLoc(), 580 SourceLocation(), D, RefersToCapture, Loc, Ty, 581 VK_LValue); 582 } 583 584 DSAStackTy::DSAVarData DSAStackTy::getTopDSA(VarDecl *D, bool FromParent) { 585 D = D->getCanonicalDecl(); 586 DSAVarData DVar; 587 588 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 589 // in a Construct, C/C++, predetermined, p.1] 590 // Variables appearing in threadprivate directives are threadprivate. 591 if ((D->getTLSKind() != VarDecl::TLS_None && 592 !(D->hasAttr<OMPThreadPrivateDeclAttr>() && 593 SemaRef.getLangOpts().OpenMPUseTLS && 594 SemaRef.getASTContext().getTargetInfo().isTLSSupported())) || 595 (D->getStorageClass() == SC_Register && D->hasAttr<AsmLabelAttr>() && 596 !D->isLocalVarDecl())) { 597 addDSA(D, buildDeclRefExpr(SemaRef, D, D->getType().getNonReferenceType(), 598 D->getLocation()), 599 OMPC_threadprivate); 600 } 601 if (Stack[0].SharingMap.count(D)) { 602 DVar.RefExpr = Stack[0].SharingMap[D].RefExpr; 603 DVar.CKind = OMPC_threadprivate; 604 return DVar; 605 } 606 607 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 608 // in a Construct, C/C++, predetermined, p.4] 609 // Static data members are shared. 610 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 611 // in a Construct, C/C++, predetermined, p.7] 612 // Variables with static storage duration that are declared in a scope 613 // inside the construct are shared. 614 if (D->isStaticDataMember()) { 615 DSAVarData DVarTemp = 616 hasDSA(D, isOpenMPPrivate, MatchesAlways(), FromParent); 617 if (DVarTemp.CKind != OMPC_unknown && DVarTemp.RefExpr) 618 return DVar; 619 620 DVar.CKind = OMPC_shared; 621 return DVar; 622 } 623 624 QualType Type = D->getType().getNonReferenceType().getCanonicalType(); 625 bool IsConstant = Type.isConstant(SemaRef.getASTContext()); 626 Type = SemaRef.getASTContext().getBaseElementType(Type); 627 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 628 // in a Construct, C/C++, predetermined, p.6] 629 // Variables with const qualified type having no mutable member are 630 // shared. 631 CXXRecordDecl *RD = 632 SemaRef.getLangOpts().CPlusPlus ? Type->getAsCXXRecordDecl() : nullptr; 633 if (auto *CTSD = dyn_cast_or_null<ClassTemplateSpecializationDecl>(RD)) 634 if (auto *CTD = CTSD->getSpecializedTemplate()) 635 RD = CTD->getTemplatedDecl(); 636 if (IsConstant && 637 !(SemaRef.getLangOpts().CPlusPlus && RD && RD->hasDefinition() && 638 RD->hasMutableFields())) { 639 // Variables with const-qualified type having no mutable member may be 640 // listed in a firstprivate clause, even if they are static data members. 641 DSAVarData DVarTemp = hasDSA(D, MatchesAnyClause(OMPC_firstprivate), 642 MatchesAlways(), FromParent); 643 if (DVarTemp.CKind == OMPC_firstprivate && DVarTemp.RefExpr) 644 return DVar; 645 646 DVar.CKind = OMPC_shared; 647 return DVar; 648 } 649 650 // Explicitly specified attributes and local variables with predetermined 651 // attributes. 652 auto StartI = std::next(Stack.rbegin()); 653 auto EndI = std::prev(Stack.rend()); 654 if (FromParent && StartI != EndI) { 655 StartI = std::next(StartI); 656 } 657 auto I = std::prev(StartI); 658 if (I->SharingMap.count(D)) { 659 DVar.RefExpr = I->SharingMap[D].RefExpr; 660 DVar.CKind = I->SharingMap[D].Attributes; 661 DVar.ImplicitDSALoc = I->DefaultAttrLoc; 662 } 663 664 return DVar; 665 } 666 667 DSAStackTy::DSAVarData DSAStackTy::getImplicitDSA(VarDecl *D, bool FromParent) { 668 D = D->getCanonicalDecl(); 669 auto StartI = Stack.rbegin(); 670 auto EndI = std::prev(Stack.rend()); 671 if (FromParent && StartI != EndI) { 672 StartI = std::next(StartI); 673 } 674 return getDSA(StartI, D); 675 } 676 677 template <class ClausesPredicate, class DirectivesPredicate> 678 DSAStackTy::DSAVarData DSAStackTy::hasDSA(VarDecl *D, ClausesPredicate CPred, 679 DirectivesPredicate DPred, 680 bool FromParent) { 681 D = D->getCanonicalDecl(); 682 auto StartI = std::next(Stack.rbegin()); 683 auto EndI = std::prev(Stack.rend()); 684 if (FromParent && StartI != EndI) { 685 StartI = std::next(StartI); 686 } 687 for (auto I = StartI, EE = EndI; I != EE; ++I) { 688 if (!DPred(I->Directive) && !isParallelOrTaskRegion(I->Directive)) 689 continue; 690 DSAVarData DVar = getDSA(I, D); 691 if (CPred(DVar.CKind)) 692 return DVar; 693 } 694 return DSAVarData(); 695 } 696 697 template <class ClausesPredicate, class DirectivesPredicate> 698 DSAStackTy::DSAVarData 699 DSAStackTy::hasInnermostDSA(VarDecl *D, ClausesPredicate CPred, 700 DirectivesPredicate DPred, bool FromParent) { 701 D = D->getCanonicalDecl(); 702 auto StartI = std::next(Stack.rbegin()); 703 auto EndI = std::prev(Stack.rend()); 704 if (FromParent && StartI != EndI) { 705 StartI = std::next(StartI); 706 } 707 for (auto I = StartI, EE = EndI; I != EE; ++I) { 708 if (!DPred(I->Directive)) 709 break; 710 DSAVarData DVar = getDSA(I, D); 711 if (CPred(DVar.CKind)) 712 return DVar; 713 return DSAVarData(); 714 } 715 return DSAVarData(); 716 } 717 718 bool DSAStackTy::hasExplicitDSA( 719 VarDecl *D, const llvm::function_ref<bool(OpenMPClauseKind)> &CPred, 720 unsigned Level) { 721 if (CPred(ClauseKindMode)) 722 return true; 723 if (isClauseParsingMode()) 724 ++Level; 725 D = D->getCanonicalDecl(); 726 auto StartI = Stack.rbegin(); 727 auto EndI = std::prev(Stack.rend()); 728 if (std::distance(StartI, EndI) <= (int)Level) 729 return false; 730 std::advance(StartI, Level); 731 return (StartI->SharingMap.count(D) > 0) && StartI->SharingMap[D].RefExpr && 732 CPred(StartI->SharingMap[D].Attributes); 733 } 734 735 bool DSAStackTy::hasExplicitDirective( 736 const llvm::function_ref<bool(OpenMPDirectiveKind)> &DPred, 737 unsigned Level) { 738 if (isClauseParsingMode()) 739 ++Level; 740 auto StartI = Stack.rbegin(); 741 auto EndI = std::prev(Stack.rend()); 742 if (std::distance(StartI, EndI) <= (int)Level) 743 return false; 744 std::advance(StartI, Level); 745 return DPred(StartI->Directive); 746 } 747 748 template <class NamedDirectivesPredicate> 749 bool DSAStackTy::hasDirective(NamedDirectivesPredicate DPred, bool FromParent) { 750 auto StartI = std::next(Stack.rbegin()); 751 auto EndI = std::prev(Stack.rend()); 752 if (FromParent && StartI != EndI) { 753 StartI = std::next(StartI); 754 } 755 for (auto I = StartI, EE = EndI; I != EE; ++I) { 756 if (DPred(I->Directive, I->DirectiveName, I->ConstructLoc)) 757 return true; 758 } 759 return false; 760 } 761 762 OpenMPDirectiveKind DSAStackTy::getDirectiveForScope(const Scope *S) const { 763 for (auto I = Stack.rbegin(), EE = Stack.rend(); I != EE; ++I) 764 if (I->CurScope == S) 765 return I->Directive; 766 return OMPD_unknown; 767 } 768 769 void Sema::InitDataSharingAttributesStack() { 770 VarDataSharingAttributesStack = new DSAStackTy(*this); 771 } 772 773 #define DSAStack static_cast<DSAStackTy *>(VarDataSharingAttributesStack) 774 775 bool Sema::IsOpenMPCapturedByRef(VarDecl *VD, 776 const CapturedRegionScopeInfo *RSI) { 777 assert(LangOpts.OpenMP && "OpenMP is not allowed"); 778 779 auto &Ctx = getASTContext(); 780 bool IsByRef = true; 781 782 // Find the directive that is associated with the provided scope. 783 auto DKind = DSAStack->getDirectiveForScope(RSI->TheScope); 784 auto Ty = VD->getType(); 785 786 if (isOpenMPTargetDirective(DKind)) { 787 // This table summarizes how a given variable should be passed to the device 788 // given its type and the clauses where it appears. This table is based on 789 // the description in OpenMP 4.5 [2.10.4, target Construct] and 790 // OpenMP 4.5 [2.15.5, Data-mapping Attribute Rules and Clauses]. 791 // 792 // ========================================================================= 793 // | type | defaultmap | pvt | first | is_device_ptr | map | res. | 794 // | |(tofrom:scalar)| | pvt | | | | 795 // ========================================================================= 796 // | scl | | | | - | | bycopy| 797 // | scl | | - | x | - | - | bycopy| 798 // | scl | | x | - | - | - | null | 799 // | scl | x | | | - | | byref | 800 // | scl | x | - | x | - | - | bycopy| 801 // | scl | x | x | - | - | - | null | 802 // | scl | | - | - | - | x | byref | 803 // | scl | x | - | - | - | x | byref | 804 // 805 // | agg | n.a. | | | - | | byref | 806 // | agg | n.a. | - | x | - | - | byref | 807 // | agg | n.a. | x | - | - | - | null | 808 // | agg | n.a. | - | - | - | x | byref | 809 // | agg | n.a. | - | - | - | x[] | byref | 810 // 811 // | ptr | n.a. | | | - | | bycopy| 812 // | ptr | n.a. | - | x | - | - | bycopy| 813 // | ptr | n.a. | x | - | - | - | null | 814 // | ptr | n.a. | - | - | - | x | byref | 815 // | ptr | n.a. | - | - | - | x[] | bycopy| 816 // | ptr | n.a. | - | - | x | | bycopy| 817 // | ptr | n.a. | - | - | x | x | bycopy| 818 // | ptr | n.a. | - | - | x | x[] | bycopy| 819 // ========================================================================= 820 // Legend: 821 // scl - scalar 822 // ptr - pointer 823 // agg - aggregate 824 // x - applies 825 // - - invalid in this combination 826 // [] - mapped with an array section 827 // byref - should be mapped by reference 828 // byval - should be mapped by value 829 // null - initialize a local variable to null on the device 830 // 831 // Observations: 832 // - All scalar declarations that show up in a map clause have to be passed 833 // by reference, because they may have been mapped in the enclosing data 834 // environment. 835 // - If the scalar value does not fit the size of uintptr, it has to be 836 // passed by reference, regardless the result in the table above. 837 // - For pointers mapped by value that have either an implicit map or an 838 // array section, the runtime library may pass the NULL value to the 839 // device instead of the value passed to it by the compiler. 840 841 // FIXME: Right now, only implicit maps are implemented. Properly mapping 842 // values requires having the map, private, and firstprivate clauses SEMA 843 // and parsing in place, which we don't yet. 844 845 if (Ty->isReferenceType()) 846 Ty = Ty->castAs<ReferenceType>()->getPointeeType(); 847 IsByRef = !Ty->isScalarType(); 848 } 849 850 // When passing data by value, we need to make sure it fits the uintptr size 851 // and alignment, because the runtime library only deals with uintptr types. 852 // If it does not fit the uintptr size, we need to pass the data by reference 853 // instead. 854 if (!IsByRef && 855 (Ctx.getTypeSizeInChars(Ty) > 856 Ctx.getTypeSizeInChars(Ctx.getUIntPtrType()) || 857 Ctx.getDeclAlign(VD) > Ctx.getTypeAlignInChars(Ctx.getUIntPtrType()))) 858 IsByRef = true; 859 860 return IsByRef; 861 } 862 863 bool Sema::IsOpenMPCapturedVar(VarDecl *VD) { 864 assert(LangOpts.OpenMP && "OpenMP is not allowed"); 865 VD = VD->getCanonicalDecl(); 866 867 // If we are attempting to capture a global variable in a directive with 868 // 'target' we return true so that this global is also mapped to the device. 869 // 870 // FIXME: If the declaration is enclosed in a 'declare target' directive, 871 // then it should not be captured. Therefore, an extra check has to be 872 // inserted here once support for 'declare target' is added. 873 // 874 if (!VD->hasLocalStorage()) { 875 if (DSAStack->getCurrentDirective() == OMPD_target && 876 !DSAStack->isClauseParsingMode()) { 877 return true; 878 } 879 if (DSAStack->getCurScope() && 880 DSAStack->hasDirective( 881 [](OpenMPDirectiveKind K, const DeclarationNameInfo &DNI, 882 SourceLocation Loc) -> bool { 883 return isOpenMPTargetDirective(K); 884 }, 885 false)) { 886 return true; 887 } 888 } 889 890 if (DSAStack->getCurrentDirective() != OMPD_unknown && 891 (!DSAStack->isClauseParsingMode() || 892 DSAStack->getParentDirective() != OMPD_unknown)) { 893 if (DSAStack->isLoopControlVariable(VD) || 894 (VD->hasLocalStorage() && 895 isParallelOrTaskRegion(DSAStack->getCurrentDirective())) || 896 DSAStack->isForceVarCapturing()) 897 return true; 898 auto DVarPrivate = DSAStack->getTopDSA(VD, DSAStack->isClauseParsingMode()); 899 if (DVarPrivate.CKind != OMPC_unknown && isOpenMPPrivate(DVarPrivate.CKind)) 900 return true; 901 DVarPrivate = DSAStack->hasDSA(VD, isOpenMPPrivate, MatchesAlways(), 902 DSAStack->isClauseParsingMode()); 903 return DVarPrivate.CKind != OMPC_unknown; 904 } 905 return false; 906 } 907 908 bool Sema::isOpenMPPrivateVar(VarDecl *VD, unsigned Level) { 909 assert(LangOpts.OpenMP && "OpenMP is not allowed"); 910 return DSAStack->hasExplicitDSA( 911 VD, [](OpenMPClauseKind K) -> bool { return K == OMPC_private; }, Level); 912 } 913 914 bool Sema::isOpenMPTargetCapturedVar(VarDecl *VD, unsigned Level) { 915 assert(LangOpts.OpenMP && "OpenMP is not allowed"); 916 // Return true if the current level is no longer enclosed in a target region. 917 918 return !VD->hasLocalStorage() && 919 DSAStack->hasExplicitDirective(isOpenMPTargetDirective, Level); 920 } 921 922 void Sema::DestroyDataSharingAttributesStack() { delete DSAStack; } 923 924 void Sema::StartOpenMPDSABlock(OpenMPDirectiveKind DKind, 925 const DeclarationNameInfo &DirName, 926 Scope *CurScope, SourceLocation Loc) { 927 DSAStack->push(DKind, DirName, CurScope, Loc); 928 PushExpressionEvaluationContext(PotentiallyEvaluated); 929 } 930 931 void Sema::StartOpenMPClause(OpenMPClauseKind K) { 932 DSAStack->setClauseParsingMode(K); 933 } 934 935 void Sema::EndOpenMPClause() { 936 DSAStack->setClauseParsingMode(/*K=*/OMPC_unknown); 937 } 938 939 void Sema::EndOpenMPDSABlock(Stmt *CurDirective) { 940 // OpenMP [2.14.3.5, Restrictions, C/C++, p.1] 941 // A variable of class type (or array thereof) that appears in a lastprivate 942 // clause requires an accessible, unambiguous default constructor for the 943 // class type, unless the list item is also specified in a firstprivate 944 // clause. 945 if (auto D = dyn_cast_or_null<OMPExecutableDirective>(CurDirective)) { 946 for (auto *C : D->clauses()) { 947 if (auto *Clause = dyn_cast<OMPLastprivateClause>(C)) { 948 SmallVector<Expr *, 8> PrivateCopies; 949 for (auto *DE : Clause->varlists()) { 950 if (DE->isValueDependent() || DE->isTypeDependent()) { 951 PrivateCopies.push_back(nullptr); 952 continue; 953 } 954 auto *VD = cast<VarDecl>(cast<DeclRefExpr>(DE)->getDecl()); 955 QualType Type = VD->getType().getNonReferenceType(); 956 auto DVar = DSAStack->getTopDSA(VD, false); 957 if (DVar.CKind == OMPC_lastprivate) { 958 // Generate helper private variable and initialize it with the 959 // default value. The address of the original variable is replaced 960 // by the address of the new private variable in CodeGen. This new 961 // variable is not added to IdResolver, so the code in the OpenMP 962 // region uses original variable for proper diagnostics. 963 auto *VDPrivate = buildVarDecl( 964 *this, DE->getExprLoc(), Type.getUnqualifiedType(), 965 VD->getName(), VD->hasAttrs() ? &VD->getAttrs() : nullptr); 966 ActOnUninitializedDecl(VDPrivate, /*TypeMayContainAuto=*/false); 967 if (VDPrivate->isInvalidDecl()) 968 continue; 969 PrivateCopies.push_back(buildDeclRefExpr( 970 *this, VDPrivate, DE->getType(), DE->getExprLoc())); 971 } else { 972 // The variable is also a firstprivate, so initialization sequence 973 // for private copy is generated already. 974 PrivateCopies.push_back(nullptr); 975 } 976 } 977 // Set initializers to private copies if no errors were found. 978 if (PrivateCopies.size() == Clause->varlist_size()) { 979 Clause->setPrivateCopies(PrivateCopies); 980 } 981 } 982 } 983 } 984 985 DSAStack->pop(); 986 DiscardCleanupsInEvaluationContext(); 987 PopExpressionEvaluationContext(); 988 } 989 990 static bool FinishOpenMPLinearClause(OMPLinearClause &Clause, DeclRefExpr *IV, 991 Expr *NumIterations, Sema &SemaRef, 992 Scope *S); 993 994 namespace { 995 996 class VarDeclFilterCCC : public CorrectionCandidateCallback { 997 private: 998 Sema &SemaRef; 999 1000 public: 1001 explicit VarDeclFilterCCC(Sema &S) : SemaRef(S) {} 1002 bool ValidateCandidate(const TypoCorrection &Candidate) override { 1003 NamedDecl *ND = Candidate.getCorrectionDecl(); 1004 if (VarDecl *VD = dyn_cast_or_null<VarDecl>(ND)) { 1005 return VD->hasGlobalStorage() && 1006 SemaRef.isDeclInScope(ND, SemaRef.getCurLexicalContext(), 1007 SemaRef.getCurScope()); 1008 } 1009 return false; 1010 } 1011 }; 1012 } // namespace 1013 1014 ExprResult Sema::ActOnOpenMPIdExpression(Scope *CurScope, 1015 CXXScopeSpec &ScopeSpec, 1016 const DeclarationNameInfo &Id) { 1017 LookupResult Lookup(*this, Id, LookupOrdinaryName); 1018 LookupParsedName(Lookup, CurScope, &ScopeSpec, true); 1019 1020 if (Lookup.isAmbiguous()) 1021 return ExprError(); 1022 1023 VarDecl *VD; 1024 if (!Lookup.isSingleResult()) { 1025 if (TypoCorrection Corrected = CorrectTypo( 1026 Id, LookupOrdinaryName, CurScope, nullptr, 1027 llvm::make_unique<VarDeclFilterCCC>(*this), CTK_ErrorRecovery)) { 1028 diagnoseTypo(Corrected, 1029 PDiag(Lookup.empty() 1030 ? diag::err_undeclared_var_use_suggest 1031 : diag::err_omp_expected_var_arg_suggest) 1032 << Id.getName()); 1033 VD = Corrected.getCorrectionDeclAs<VarDecl>(); 1034 } else { 1035 Diag(Id.getLoc(), Lookup.empty() ? diag::err_undeclared_var_use 1036 : diag::err_omp_expected_var_arg) 1037 << Id.getName(); 1038 return ExprError(); 1039 } 1040 } else { 1041 if (!(VD = Lookup.getAsSingle<VarDecl>())) { 1042 Diag(Id.getLoc(), diag::err_omp_expected_var_arg) << Id.getName(); 1043 Diag(Lookup.getFoundDecl()->getLocation(), diag::note_declared_at); 1044 return ExprError(); 1045 } 1046 } 1047 Lookup.suppressDiagnostics(); 1048 1049 // OpenMP [2.9.2, Syntax, C/C++] 1050 // Variables must be file-scope, namespace-scope, or static block-scope. 1051 if (!VD->hasGlobalStorage()) { 1052 Diag(Id.getLoc(), diag::err_omp_global_var_arg) 1053 << getOpenMPDirectiveName(OMPD_threadprivate) << !VD->isStaticLocal(); 1054 bool IsDecl = 1055 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 1056 Diag(VD->getLocation(), 1057 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 1058 << VD; 1059 return ExprError(); 1060 } 1061 1062 VarDecl *CanonicalVD = VD->getCanonicalDecl(); 1063 NamedDecl *ND = cast<NamedDecl>(CanonicalVD); 1064 // OpenMP [2.9.2, Restrictions, C/C++, p.2] 1065 // A threadprivate directive for file-scope variables must appear outside 1066 // any definition or declaration. 1067 if (CanonicalVD->getDeclContext()->isTranslationUnit() && 1068 !getCurLexicalContext()->isTranslationUnit()) { 1069 Diag(Id.getLoc(), diag::err_omp_var_scope) 1070 << getOpenMPDirectiveName(OMPD_threadprivate) << VD; 1071 bool IsDecl = 1072 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 1073 Diag(VD->getLocation(), 1074 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 1075 << VD; 1076 return ExprError(); 1077 } 1078 // OpenMP [2.9.2, Restrictions, C/C++, p.3] 1079 // A threadprivate directive for static class member variables must appear 1080 // in the class definition, in the same scope in which the member 1081 // variables are declared. 1082 if (CanonicalVD->isStaticDataMember() && 1083 !CanonicalVD->getDeclContext()->Equals(getCurLexicalContext())) { 1084 Diag(Id.getLoc(), diag::err_omp_var_scope) 1085 << getOpenMPDirectiveName(OMPD_threadprivate) << VD; 1086 bool IsDecl = 1087 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 1088 Diag(VD->getLocation(), 1089 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 1090 << VD; 1091 return ExprError(); 1092 } 1093 // OpenMP [2.9.2, Restrictions, C/C++, p.4] 1094 // A threadprivate directive for namespace-scope variables must appear 1095 // outside any definition or declaration other than the namespace 1096 // definition itself. 1097 if (CanonicalVD->getDeclContext()->isNamespace() && 1098 (!getCurLexicalContext()->isFileContext() || 1099 !getCurLexicalContext()->Encloses(CanonicalVD->getDeclContext()))) { 1100 Diag(Id.getLoc(), diag::err_omp_var_scope) 1101 << getOpenMPDirectiveName(OMPD_threadprivate) << VD; 1102 bool IsDecl = 1103 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 1104 Diag(VD->getLocation(), 1105 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 1106 << VD; 1107 return ExprError(); 1108 } 1109 // OpenMP [2.9.2, Restrictions, C/C++, p.6] 1110 // A threadprivate directive for static block-scope variables must appear 1111 // in the scope of the variable and not in a nested scope. 1112 if (CanonicalVD->isStaticLocal() && CurScope && 1113 !isDeclInScope(ND, getCurLexicalContext(), CurScope)) { 1114 Diag(Id.getLoc(), diag::err_omp_var_scope) 1115 << getOpenMPDirectiveName(OMPD_threadprivate) << VD; 1116 bool IsDecl = 1117 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 1118 Diag(VD->getLocation(), 1119 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 1120 << VD; 1121 return ExprError(); 1122 } 1123 1124 // OpenMP [2.9.2, Restrictions, C/C++, p.2-6] 1125 // A threadprivate directive must lexically precede all references to any 1126 // of the variables in its list. 1127 if (VD->isUsed() && !DSAStack->isThreadPrivate(VD)) { 1128 Diag(Id.getLoc(), diag::err_omp_var_used) 1129 << getOpenMPDirectiveName(OMPD_threadprivate) << VD; 1130 return ExprError(); 1131 } 1132 1133 QualType ExprType = VD->getType().getNonReferenceType(); 1134 ExprResult DE = buildDeclRefExpr(*this, VD, ExprType, Id.getLoc()); 1135 return DE; 1136 } 1137 1138 Sema::DeclGroupPtrTy 1139 Sema::ActOnOpenMPThreadprivateDirective(SourceLocation Loc, 1140 ArrayRef<Expr *> VarList) { 1141 if (OMPThreadPrivateDecl *D = CheckOMPThreadPrivateDecl(Loc, VarList)) { 1142 CurContext->addDecl(D); 1143 return DeclGroupPtrTy::make(DeclGroupRef(D)); 1144 } 1145 return DeclGroupPtrTy(); 1146 } 1147 1148 namespace { 1149 class LocalVarRefChecker : public ConstStmtVisitor<LocalVarRefChecker, bool> { 1150 Sema &SemaRef; 1151 1152 public: 1153 bool VisitDeclRefExpr(const DeclRefExpr *E) { 1154 if (auto VD = dyn_cast<VarDecl>(E->getDecl())) { 1155 if (VD->hasLocalStorage()) { 1156 SemaRef.Diag(E->getLocStart(), 1157 diag::err_omp_local_var_in_threadprivate_init) 1158 << E->getSourceRange(); 1159 SemaRef.Diag(VD->getLocation(), diag::note_defined_here) 1160 << VD << VD->getSourceRange(); 1161 return true; 1162 } 1163 } 1164 return false; 1165 } 1166 bool VisitStmt(const Stmt *S) { 1167 for (auto Child : S->children()) { 1168 if (Child && Visit(Child)) 1169 return true; 1170 } 1171 return false; 1172 } 1173 explicit LocalVarRefChecker(Sema &SemaRef) : SemaRef(SemaRef) {} 1174 }; 1175 } // namespace 1176 1177 OMPThreadPrivateDecl * 1178 Sema::CheckOMPThreadPrivateDecl(SourceLocation Loc, ArrayRef<Expr *> VarList) { 1179 SmallVector<Expr *, 8> Vars; 1180 for (auto &RefExpr : VarList) { 1181 DeclRefExpr *DE = cast<DeclRefExpr>(RefExpr); 1182 VarDecl *VD = cast<VarDecl>(DE->getDecl()); 1183 SourceLocation ILoc = DE->getExprLoc(); 1184 1185 QualType QType = VD->getType(); 1186 if (QType->isDependentType() || QType->isInstantiationDependentType()) { 1187 // It will be analyzed later. 1188 Vars.push_back(DE); 1189 continue; 1190 } 1191 1192 // OpenMP [2.9.2, Restrictions, C/C++, p.10] 1193 // A threadprivate variable must not have an incomplete type. 1194 if (RequireCompleteType(ILoc, VD->getType(), 1195 diag::err_omp_threadprivate_incomplete_type)) { 1196 continue; 1197 } 1198 1199 // OpenMP [2.9.2, Restrictions, C/C++, p.10] 1200 // A threadprivate variable must not have a reference type. 1201 if (VD->getType()->isReferenceType()) { 1202 Diag(ILoc, diag::err_omp_ref_type_arg) 1203 << getOpenMPDirectiveName(OMPD_threadprivate) << VD->getType(); 1204 bool IsDecl = 1205 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 1206 Diag(VD->getLocation(), 1207 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 1208 << VD; 1209 continue; 1210 } 1211 1212 // Check if this is a TLS variable. If TLS is not being supported, produce 1213 // the corresponding diagnostic. 1214 if ((VD->getTLSKind() != VarDecl::TLS_None && 1215 !(VD->hasAttr<OMPThreadPrivateDeclAttr>() && 1216 getLangOpts().OpenMPUseTLS && 1217 getASTContext().getTargetInfo().isTLSSupported())) || 1218 (VD->getStorageClass() == SC_Register && VD->hasAttr<AsmLabelAttr>() && 1219 !VD->isLocalVarDecl())) { 1220 Diag(ILoc, diag::err_omp_var_thread_local) 1221 << VD << ((VD->getTLSKind() != VarDecl::TLS_None) ? 0 : 1); 1222 bool IsDecl = 1223 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 1224 Diag(VD->getLocation(), 1225 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 1226 << VD; 1227 continue; 1228 } 1229 1230 // Check if initial value of threadprivate variable reference variable with 1231 // local storage (it is not supported by runtime). 1232 if (auto Init = VD->getAnyInitializer()) { 1233 LocalVarRefChecker Checker(*this); 1234 if (Checker.Visit(Init)) 1235 continue; 1236 } 1237 1238 Vars.push_back(RefExpr); 1239 DSAStack->addDSA(VD, DE, OMPC_threadprivate); 1240 VD->addAttr(OMPThreadPrivateDeclAttr::CreateImplicit( 1241 Context, SourceRange(Loc, Loc))); 1242 if (auto *ML = Context.getASTMutationListener()) 1243 ML->DeclarationMarkedOpenMPThreadPrivate(VD); 1244 } 1245 OMPThreadPrivateDecl *D = nullptr; 1246 if (!Vars.empty()) { 1247 D = OMPThreadPrivateDecl::Create(Context, getCurLexicalContext(), Loc, 1248 Vars); 1249 D->setAccess(AS_public); 1250 } 1251 return D; 1252 } 1253 1254 static void ReportOriginalDSA(Sema &SemaRef, DSAStackTy *Stack, 1255 const VarDecl *VD, DSAStackTy::DSAVarData DVar, 1256 bool IsLoopIterVar = false) { 1257 if (DVar.RefExpr) { 1258 SemaRef.Diag(DVar.RefExpr->getExprLoc(), diag::note_omp_explicit_dsa) 1259 << getOpenMPClauseName(DVar.CKind); 1260 return; 1261 } 1262 enum { 1263 PDSA_StaticMemberShared, 1264 PDSA_StaticLocalVarShared, 1265 PDSA_LoopIterVarPrivate, 1266 PDSA_LoopIterVarLinear, 1267 PDSA_LoopIterVarLastprivate, 1268 PDSA_ConstVarShared, 1269 PDSA_GlobalVarShared, 1270 PDSA_TaskVarFirstprivate, 1271 PDSA_LocalVarPrivate, 1272 PDSA_Implicit 1273 } Reason = PDSA_Implicit; 1274 bool ReportHint = false; 1275 auto ReportLoc = VD->getLocation(); 1276 if (IsLoopIterVar) { 1277 if (DVar.CKind == OMPC_private) 1278 Reason = PDSA_LoopIterVarPrivate; 1279 else if (DVar.CKind == OMPC_lastprivate) 1280 Reason = PDSA_LoopIterVarLastprivate; 1281 else 1282 Reason = PDSA_LoopIterVarLinear; 1283 } else if (DVar.DKind == OMPD_task && DVar.CKind == OMPC_firstprivate) { 1284 Reason = PDSA_TaskVarFirstprivate; 1285 ReportLoc = DVar.ImplicitDSALoc; 1286 } else if (VD->isStaticLocal()) 1287 Reason = PDSA_StaticLocalVarShared; 1288 else if (VD->isStaticDataMember()) 1289 Reason = PDSA_StaticMemberShared; 1290 else if (VD->isFileVarDecl()) 1291 Reason = PDSA_GlobalVarShared; 1292 else if (VD->getType().isConstant(SemaRef.getASTContext())) 1293 Reason = PDSA_ConstVarShared; 1294 else if (VD->isLocalVarDecl() && DVar.CKind == OMPC_private) { 1295 ReportHint = true; 1296 Reason = PDSA_LocalVarPrivate; 1297 } 1298 if (Reason != PDSA_Implicit) { 1299 SemaRef.Diag(ReportLoc, diag::note_omp_predetermined_dsa) 1300 << Reason << ReportHint 1301 << getOpenMPDirectiveName(Stack->getCurrentDirective()); 1302 } else if (DVar.ImplicitDSALoc.isValid()) { 1303 SemaRef.Diag(DVar.ImplicitDSALoc, diag::note_omp_implicit_dsa) 1304 << getOpenMPClauseName(DVar.CKind); 1305 } 1306 } 1307 1308 namespace { 1309 class DSAAttrChecker : public StmtVisitor<DSAAttrChecker, void> { 1310 DSAStackTy *Stack; 1311 Sema &SemaRef; 1312 bool ErrorFound; 1313 CapturedStmt *CS; 1314 llvm::SmallVector<Expr *, 8> ImplicitFirstprivate; 1315 llvm::DenseMap<VarDecl *, Expr *> VarsWithInheritedDSA; 1316 1317 public: 1318 void VisitDeclRefExpr(DeclRefExpr *E) { 1319 if (auto *VD = dyn_cast<VarDecl>(E->getDecl())) { 1320 // Skip internally declared variables. 1321 if (VD->isLocalVarDecl() && !CS->capturesVariable(VD)) 1322 return; 1323 1324 auto DVar = Stack->getTopDSA(VD, false); 1325 // Check if the variable has explicit DSA set and stop analysis if it so. 1326 if (DVar.RefExpr) return; 1327 1328 auto ELoc = E->getExprLoc(); 1329 auto DKind = Stack->getCurrentDirective(); 1330 // The default(none) clause requires that each variable that is referenced 1331 // in the construct, and does not have a predetermined data-sharing 1332 // attribute, must have its data-sharing attribute explicitly determined 1333 // by being listed in a data-sharing attribute clause. 1334 if (DVar.CKind == OMPC_unknown && Stack->getDefaultDSA() == DSA_none && 1335 isParallelOrTaskRegion(DKind) && 1336 VarsWithInheritedDSA.count(VD) == 0) { 1337 VarsWithInheritedDSA[VD] = E; 1338 return; 1339 } 1340 1341 // OpenMP [2.9.3.6, Restrictions, p.2] 1342 // A list item that appears in a reduction clause of the innermost 1343 // enclosing worksharing or parallel construct may not be accessed in an 1344 // explicit task. 1345 DVar = Stack->hasInnermostDSA(VD, MatchesAnyClause(OMPC_reduction), 1346 [](OpenMPDirectiveKind K) -> bool { 1347 return isOpenMPParallelDirective(K) || 1348 isOpenMPWorksharingDirective(K) || 1349 isOpenMPTeamsDirective(K); 1350 }, 1351 false); 1352 if (DKind == OMPD_task && DVar.CKind == OMPC_reduction) { 1353 ErrorFound = true; 1354 SemaRef.Diag(ELoc, diag::err_omp_reduction_in_task); 1355 ReportOriginalDSA(SemaRef, Stack, VD, DVar); 1356 return; 1357 } 1358 1359 // Define implicit data-sharing attributes for task. 1360 DVar = Stack->getImplicitDSA(VD, false); 1361 if (DKind == OMPD_task && DVar.CKind != OMPC_shared) 1362 ImplicitFirstprivate.push_back(E); 1363 } 1364 } 1365 void VisitOMPExecutableDirective(OMPExecutableDirective *S) { 1366 for (auto *C : S->clauses()) { 1367 // Skip analysis of arguments of implicitly defined firstprivate clause 1368 // for task directives. 1369 if (C && (!isa<OMPFirstprivateClause>(C) || C->getLocStart().isValid())) 1370 for (auto *CC : C->children()) { 1371 if (CC) 1372 Visit(CC); 1373 } 1374 } 1375 } 1376 void VisitStmt(Stmt *S) { 1377 for (auto *C : S->children()) { 1378 if (C && !isa<OMPExecutableDirective>(C)) 1379 Visit(C); 1380 } 1381 } 1382 1383 bool isErrorFound() { return ErrorFound; } 1384 ArrayRef<Expr *> getImplicitFirstprivate() { return ImplicitFirstprivate; } 1385 llvm::DenseMap<VarDecl *, Expr *> &getVarsWithInheritedDSA() { 1386 return VarsWithInheritedDSA; 1387 } 1388 1389 DSAAttrChecker(DSAStackTy *S, Sema &SemaRef, CapturedStmt *CS) 1390 : Stack(S), SemaRef(SemaRef), ErrorFound(false), CS(CS) {} 1391 }; 1392 } // namespace 1393 1394 void Sema::ActOnOpenMPRegionStart(OpenMPDirectiveKind DKind, Scope *CurScope) { 1395 switch (DKind) { 1396 case OMPD_parallel: { 1397 QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1); 1398 QualType KmpInt32PtrTy = 1399 Context.getPointerType(KmpInt32Ty).withConst().withRestrict(); 1400 Sema::CapturedParamNameType Params[] = { 1401 std::make_pair(".global_tid.", KmpInt32PtrTy), 1402 std::make_pair(".bound_tid.", KmpInt32PtrTy), 1403 std::make_pair(StringRef(), QualType()) // __context with shared vars 1404 }; 1405 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1406 Params); 1407 break; 1408 } 1409 case OMPD_simd: { 1410 Sema::CapturedParamNameType Params[] = { 1411 std::make_pair(StringRef(), QualType()) // __context with shared vars 1412 }; 1413 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1414 Params); 1415 break; 1416 } 1417 case OMPD_for: { 1418 Sema::CapturedParamNameType Params[] = { 1419 std::make_pair(StringRef(), QualType()) // __context with shared vars 1420 }; 1421 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1422 Params); 1423 break; 1424 } 1425 case OMPD_for_simd: { 1426 Sema::CapturedParamNameType Params[] = { 1427 std::make_pair(StringRef(), QualType()) // __context with shared vars 1428 }; 1429 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1430 Params); 1431 break; 1432 } 1433 case OMPD_sections: { 1434 Sema::CapturedParamNameType Params[] = { 1435 std::make_pair(StringRef(), QualType()) // __context with shared vars 1436 }; 1437 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1438 Params); 1439 break; 1440 } 1441 case OMPD_section: { 1442 Sema::CapturedParamNameType Params[] = { 1443 std::make_pair(StringRef(), QualType()) // __context with shared vars 1444 }; 1445 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1446 Params); 1447 break; 1448 } 1449 case OMPD_single: { 1450 Sema::CapturedParamNameType Params[] = { 1451 std::make_pair(StringRef(), QualType()) // __context with shared vars 1452 }; 1453 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1454 Params); 1455 break; 1456 } 1457 case OMPD_master: { 1458 Sema::CapturedParamNameType Params[] = { 1459 std::make_pair(StringRef(), QualType()) // __context with shared vars 1460 }; 1461 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1462 Params); 1463 break; 1464 } 1465 case OMPD_critical: { 1466 Sema::CapturedParamNameType Params[] = { 1467 std::make_pair(StringRef(), QualType()) // __context with shared vars 1468 }; 1469 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1470 Params); 1471 break; 1472 } 1473 case OMPD_parallel_for: { 1474 QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1); 1475 QualType KmpInt32PtrTy = 1476 Context.getPointerType(KmpInt32Ty).withConst().withRestrict(); 1477 Sema::CapturedParamNameType Params[] = { 1478 std::make_pair(".global_tid.", KmpInt32PtrTy), 1479 std::make_pair(".bound_tid.", KmpInt32PtrTy), 1480 std::make_pair(StringRef(), QualType()) // __context with shared vars 1481 }; 1482 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1483 Params); 1484 break; 1485 } 1486 case OMPD_parallel_for_simd: { 1487 QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1); 1488 QualType KmpInt32PtrTy = 1489 Context.getPointerType(KmpInt32Ty).withConst().withRestrict(); 1490 Sema::CapturedParamNameType Params[] = { 1491 std::make_pair(".global_tid.", KmpInt32PtrTy), 1492 std::make_pair(".bound_tid.", KmpInt32PtrTy), 1493 std::make_pair(StringRef(), QualType()) // __context with shared vars 1494 }; 1495 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1496 Params); 1497 break; 1498 } 1499 case OMPD_parallel_sections: { 1500 QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1); 1501 QualType KmpInt32PtrTy = 1502 Context.getPointerType(KmpInt32Ty).withConst().withRestrict(); 1503 Sema::CapturedParamNameType Params[] = { 1504 std::make_pair(".global_tid.", KmpInt32PtrTy), 1505 std::make_pair(".bound_tid.", KmpInt32PtrTy), 1506 std::make_pair(StringRef(), QualType()) // __context with shared vars 1507 }; 1508 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1509 Params); 1510 break; 1511 } 1512 case OMPD_task: { 1513 QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1); 1514 QualType Args[] = {Context.VoidPtrTy.withConst().withRestrict()}; 1515 FunctionProtoType::ExtProtoInfo EPI; 1516 EPI.Variadic = true; 1517 QualType CopyFnType = Context.getFunctionType(Context.VoidTy, Args, EPI); 1518 Sema::CapturedParamNameType Params[] = { 1519 std::make_pair(".global_tid.", KmpInt32Ty), 1520 std::make_pair(".part_id.", KmpInt32Ty), 1521 std::make_pair(".privates.", 1522 Context.VoidPtrTy.withConst().withRestrict()), 1523 std::make_pair( 1524 ".copy_fn.", 1525 Context.getPointerType(CopyFnType).withConst().withRestrict()), 1526 std::make_pair(StringRef(), QualType()) // __context with shared vars 1527 }; 1528 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1529 Params); 1530 // Mark this captured region as inlined, because we don't use outlined 1531 // function directly. 1532 getCurCapturedRegion()->TheCapturedDecl->addAttr( 1533 AlwaysInlineAttr::CreateImplicit( 1534 Context, AlwaysInlineAttr::Keyword_forceinline, SourceRange())); 1535 break; 1536 } 1537 case OMPD_ordered: { 1538 Sema::CapturedParamNameType Params[] = { 1539 std::make_pair(StringRef(), QualType()) // __context with shared vars 1540 }; 1541 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1542 Params); 1543 break; 1544 } 1545 case OMPD_atomic: { 1546 Sema::CapturedParamNameType Params[] = { 1547 std::make_pair(StringRef(), QualType()) // __context with shared vars 1548 }; 1549 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1550 Params); 1551 break; 1552 } 1553 case OMPD_target_data: 1554 case OMPD_target: { 1555 Sema::CapturedParamNameType Params[] = { 1556 std::make_pair(StringRef(), QualType()) // __context with shared vars 1557 }; 1558 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1559 Params); 1560 break; 1561 } 1562 case OMPD_teams: { 1563 QualType KmpInt32Ty = Context.getIntTypeForBitwidth(32, 1); 1564 QualType KmpInt32PtrTy = 1565 Context.getPointerType(KmpInt32Ty).withConst().withRestrict(); 1566 Sema::CapturedParamNameType Params[] = { 1567 std::make_pair(".global_tid.", KmpInt32PtrTy), 1568 std::make_pair(".bound_tid.", KmpInt32PtrTy), 1569 std::make_pair(StringRef(), QualType()) // __context with shared vars 1570 }; 1571 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1572 Params); 1573 break; 1574 } 1575 case OMPD_taskgroup: { 1576 Sema::CapturedParamNameType Params[] = { 1577 std::make_pair(StringRef(), QualType()) // __context with shared vars 1578 }; 1579 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1580 Params); 1581 break; 1582 } 1583 case OMPD_taskloop: { 1584 Sema::CapturedParamNameType Params[] = { 1585 std::make_pair(StringRef(), QualType()) // __context with shared vars 1586 }; 1587 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1588 Params); 1589 break; 1590 } 1591 case OMPD_taskloop_simd: { 1592 Sema::CapturedParamNameType Params[] = { 1593 std::make_pair(StringRef(), QualType()) // __context with shared vars 1594 }; 1595 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1596 Params); 1597 break; 1598 } 1599 case OMPD_distribute: { 1600 Sema::CapturedParamNameType Params[] = { 1601 std::make_pair(StringRef(), QualType()) // __context with shared vars 1602 }; 1603 ActOnCapturedRegionStart(DSAStack->getConstructLoc(), CurScope, CR_OpenMP, 1604 Params); 1605 break; 1606 } 1607 case OMPD_threadprivate: 1608 case OMPD_taskyield: 1609 case OMPD_barrier: 1610 case OMPD_taskwait: 1611 case OMPD_cancellation_point: 1612 case OMPD_cancel: 1613 case OMPD_flush: 1614 llvm_unreachable("OpenMP Directive is not allowed"); 1615 case OMPD_unknown: 1616 llvm_unreachable("Unknown OpenMP directive"); 1617 } 1618 } 1619 1620 StmtResult Sema::ActOnOpenMPRegionEnd(StmtResult S, 1621 ArrayRef<OMPClause *> Clauses) { 1622 if (!S.isUsable()) { 1623 ActOnCapturedRegionError(); 1624 return StmtError(); 1625 } 1626 1627 OMPOrderedClause *OC = nullptr; 1628 OMPScheduleClause *SC = nullptr; 1629 SmallVector<OMPLinearClause *, 4> LCs; 1630 // This is required for proper codegen. 1631 for (auto *Clause : Clauses) { 1632 if (isOpenMPPrivate(Clause->getClauseKind()) || 1633 Clause->getClauseKind() == OMPC_copyprivate || 1634 (getLangOpts().OpenMPUseTLS && 1635 getASTContext().getTargetInfo().isTLSSupported() && 1636 Clause->getClauseKind() == OMPC_copyin)) { 1637 DSAStack->setForceVarCapturing(Clause->getClauseKind() == OMPC_copyin); 1638 // Mark all variables in private list clauses as used in inner region. 1639 for (auto *VarRef : Clause->children()) { 1640 if (auto *E = cast_or_null<Expr>(VarRef)) { 1641 MarkDeclarationsReferencedInExpr(E); 1642 } 1643 } 1644 DSAStack->setForceVarCapturing(/*V=*/false); 1645 } else if (isParallelOrTaskRegion(DSAStack->getCurrentDirective()) && 1646 Clause->getClauseKind() == OMPC_schedule) { 1647 // Mark all variables in private list clauses as used in inner region. 1648 // Required for proper codegen of combined directives. 1649 // TODO: add processing for other clauses. 1650 if (auto *E = cast_or_null<Expr>( 1651 cast<OMPScheduleClause>(Clause)->getHelperChunkSize())) 1652 MarkDeclarationsReferencedInExpr(E); 1653 } 1654 if (Clause->getClauseKind() == OMPC_schedule) 1655 SC = cast<OMPScheduleClause>(Clause); 1656 else if (Clause->getClauseKind() == OMPC_ordered) 1657 OC = cast<OMPOrderedClause>(Clause); 1658 else if (Clause->getClauseKind() == OMPC_linear) 1659 LCs.push_back(cast<OMPLinearClause>(Clause)); 1660 } 1661 bool ErrorFound = false; 1662 // OpenMP, 2.7.1 Loop Construct, Restrictions 1663 // The nonmonotonic modifier cannot be specified if an ordered clause is 1664 // specified. 1665 if (SC && 1666 (SC->getFirstScheduleModifier() == OMPC_SCHEDULE_MODIFIER_nonmonotonic || 1667 SC->getSecondScheduleModifier() == 1668 OMPC_SCHEDULE_MODIFIER_nonmonotonic) && 1669 OC) { 1670 Diag(SC->getFirstScheduleModifier() == OMPC_SCHEDULE_MODIFIER_nonmonotonic 1671 ? SC->getFirstScheduleModifierLoc() 1672 : SC->getSecondScheduleModifierLoc(), 1673 diag::err_omp_schedule_nonmonotonic_ordered) 1674 << SourceRange(OC->getLocStart(), OC->getLocEnd()); 1675 ErrorFound = true; 1676 } 1677 if (!LCs.empty() && OC && OC->getNumForLoops()) { 1678 for (auto *C : LCs) { 1679 Diag(C->getLocStart(), diag::err_omp_linear_ordered) 1680 << SourceRange(OC->getLocStart(), OC->getLocEnd()); 1681 } 1682 ErrorFound = true; 1683 } 1684 if (isOpenMPWorksharingDirective(DSAStack->getCurrentDirective()) && 1685 isOpenMPSimdDirective(DSAStack->getCurrentDirective()) && OC && 1686 OC->getNumForLoops()) { 1687 Diag(OC->getLocStart(), diag::err_omp_ordered_simd) 1688 << getOpenMPDirectiveName(DSAStack->getCurrentDirective()); 1689 ErrorFound = true; 1690 } 1691 if (ErrorFound) { 1692 ActOnCapturedRegionError(); 1693 return StmtError(); 1694 } 1695 return ActOnCapturedRegionEnd(S.get()); 1696 } 1697 1698 static bool CheckNestingOfRegions(Sema &SemaRef, DSAStackTy *Stack, 1699 OpenMPDirectiveKind CurrentRegion, 1700 const DeclarationNameInfo &CurrentName, 1701 OpenMPDirectiveKind CancelRegion, 1702 SourceLocation StartLoc) { 1703 // Allowed nesting of constructs 1704 // +------------------+-----------------+------------------------------------+ 1705 // | Parent directive | Child directive | Closely (!), No-Closely(+), Both(*)| 1706 // +------------------+-----------------+------------------------------------+ 1707 // | parallel | parallel | * | 1708 // | parallel | for | * | 1709 // | parallel | for simd | * | 1710 // | parallel | master | * | 1711 // | parallel | critical | * | 1712 // | parallel | simd | * | 1713 // | parallel | sections | * | 1714 // | parallel | section | + | 1715 // | parallel | single | * | 1716 // | parallel | parallel for | * | 1717 // | parallel |parallel for simd| * | 1718 // | parallel |parallel sections| * | 1719 // | parallel | task | * | 1720 // | parallel | taskyield | * | 1721 // | parallel | barrier | * | 1722 // | parallel | taskwait | * | 1723 // | parallel | taskgroup | * | 1724 // | parallel | flush | * | 1725 // | parallel | ordered | + | 1726 // | parallel | atomic | * | 1727 // | parallel | target | * | 1728 // | parallel | teams | + | 1729 // | parallel | cancellation | | 1730 // | | point | ! | 1731 // | parallel | cancel | ! | 1732 // | parallel | taskloop | * | 1733 // | parallel | taskloop simd | * | 1734 // | parallel | distribute | | 1735 // +------------------+-----------------+------------------------------------+ 1736 // | for | parallel | * | 1737 // | for | for | + | 1738 // | for | for simd | + | 1739 // | for | master | + | 1740 // | for | critical | * | 1741 // | for | simd | * | 1742 // | for | sections | + | 1743 // | for | section | + | 1744 // | for | single | + | 1745 // | for | parallel for | * | 1746 // | for |parallel for simd| * | 1747 // | for |parallel sections| * | 1748 // | for | task | * | 1749 // | for | taskyield | * | 1750 // | for | barrier | + | 1751 // | for | taskwait | * | 1752 // | for | taskgroup | * | 1753 // | for | flush | * | 1754 // | for | ordered | * (if construct is ordered) | 1755 // | for | atomic | * | 1756 // | for | target | * | 1757 // | for | teams | + | 1758 // | for | cancellation | | 1759 // | | point | ! | 1760 // | for | cancel | ! | 1761 // | for | taskloop | * | 1762 // | for | taskloop simd | * | 1763 // | for | distribute | | 1764 // +------------------+-----------------+------------------------------------+ 1765 // | master | parallel | * | 1766 // | master | for | + | 1767 // | master | for simd | + | 1768 // | master | master | * | 1769 // | master | critical | * | 1770 // | master | simd | * | 1771 // | master | sections | + | 1772 // | master | section | + | 1773 // | master | single | + | 1774 // | master | parallel for | * | 1775 // | master |parallel for simd| * | 1776 // | master |parallel sections| * | 1777 // | master | task | * | 1778 // | master | taskyield | * | 1779 // | master | barrier | + | 1780 // | master | taskwait | * | 1781 // | master | taskgroup | * | 1782 // | master | flush | * | 1783 // | master | ordered | + | 1784 // | master | atomic | * | 1785 // | master | target | * | 1786 // | master | teams | + | 1787 // | master | cancellation | | 1788 // | | point | | 1789 // | master | cancel | | 1790 // | master | taskloop | * | 1791 // | master | taskloop simd | * | 1792 // | master | distribute | | 1793 // +------------------+-----------------+------------------------------------+ 1794 // | critical | parallel | * | 1795 // | critical | for | + | 1796 // | critical | for simd | + | 1797 // | critical | master | * | 1798 // | critical | critical | * (should have different names) | 1799 // | critical | simd | * | 1800 // | critical | sections | + | 1801 // | critical | section | + | 1802 // | critical | single | + | 1803 // | critical | parallel for | * | 1804 // | critical |parallel for simd| * | 1805 // | critical |parallel sections| * | 1806 // | critical | task | * | 1807 // | critical | taskyield | * | 1808 // | critical | barrier | + | 1809 // | critical | taskwait | * | 1810 // | critical | taskgroup | * | 1811 // | critical | ordered | + | 1812 // | critical | atomic | * | 1813 // | critical | target | * | 1814 // | critical | teams | + | 1815 // | critical | cancellation | | 1816 // | | point | | 1817 // | critical | cancel | | 1818 // | critical | taskloop | * | 1819 // | critical | taskloop simd | * | 1820 // | critical | distribute | | 1821 // +------------------+-----------------+------------------------------------+ 1822 // | simd | parallel | | 1823 // | simd | for | | 1824 // | simd | for simd | | 1825 // | simd | master | | 1826 // | simd | critical | | 1827 // | simd | simd | | 1828 // | simd | sections | | 1829 // | simd | section | | 1830 // | simd | single | | 1831 // | simd | parallel for | | 1832 // | simd |parallel for simd| | 1833 // | simd |parallel sections| | 1834 // | simd | task | | 1835 // | simd | taskyield | | 1836 // | simd | barrier | | 1837 // | simd | taskwait | | 1838 // | simd | taskgroup | | 1839 // | simd | flush | | 1840 // | simd | ordered | + (with simd clause) | 1841 // | simd | atomic | | 1842 // | simd | target | | 1843 // | simd | teams | | 1844 // | simd | cancellation | | 1845 // | | point | | 1846 // | simd | cancel | | 1847 // | simd | taskloop | | 1848 // | simd | taskloop simd | | 1849 // | simd | distribute | | 1850 // +------------------+-----------------+------------------------------------+ 1851 // | for simd | parallel | | 1852 // | for simd | for | | 1853 // | for simd | for simd | | 1854 // | for simd | master | | 1855 // | for simd | critical | | 1856 // | for simd | simd | | 1857 // | for simd | sections | | 1858 // | for simd | section | | 1859 // | for simd | single | | 1860 // | for simd | parallel for | | 1861 // | for simd |parallel for simd| | 1862 // | for simd |parallel sections| | 1863 // | for simd | task | | 1864 // | for simd | taskyield | | 1865 // | for simd | barrier | | 1866 // | for simd | taskwait | | 1867 // | for simd | taskgroup | | 1868 // | for simd | flush | | 1869 // | for simd | ordered | + (with simd clause) | 1870 // | for simd | atomic | | 1871 // | for simd | target | | 1872 // | for simd | teams | | 1873 // | for simd | cancellation | | 1874 // | | point | | 1875 // | for simd | cancel | | 1876 // | for simd | taskloop | | 1877 // | for simd | taskloop simd | | 1878 // | for simd | distribute | | 1879 // +------------------+-----------------+------------------------------------+ 1880 // | parallel for simd| parallel | | 1881 // | parallel for simd| for | | 1882 // | parallel for simd| for simd | | 1883 // | parallel for simd| master | | 1884 // | parallel for simd| critical | | 1885 // | parallel for simd| simd | | 1886 // | parallel for simd| sections | | 1887 // | parallel for simd| section | | 1888 // | parallel for simd| single | | 1889 // | parallel for simd| parallel for | | 1890 // | parallel for simd|parallel for simd| | 1891 // | parallel for simd|parallel sections| | 1892 // | parallel for simd| task | | 1893 // | parallel for simd| taskyield | | 1894 // | parallel for simd| barrier | | 1895 // | parallel for simd| taskwait | | 1896 // | parallel for simd| taskgroup | | 1897 // | parallel for simd| flush | | 1898 // | parallel for simd| ordered | + (with simd clause) | 1899 // | parallel for simd| atomic | | 1900 // | parallel for simd| target | | 1901 // | parallel for simd| teams | | 1902 // | parallel for simd| cancellation | | 1903 // | | point | | 1904 // | parallel for simd| cancel | | 1905 // | parallel for simd| taskloop | | 1906 // | parallel for simd| taskloop simd | | 1907 // | parallel for simd| distribute | | 1908 // +------------------+-----------------+------------------------------------+ 1909 // | sections | parallel | * | 1910 // | sections | for | + | 1911 // | sections | for simd | + | 1912 // | sections | master | + | 1913 // | sections | critical | * | 1914 // | sections | simd | * | 1915 // | sections | sections | + | 1916 // | sections | section | * | 1917 // | sections | single | + | 1918 // | sections | parallel for | * | 1919 // | sections |parallel for simd| * | 1920 // | sections |parallel sections| * | 1921 // | sections | task | * | 1922 // | sections | taskyield | * | 1923 // | sections | barrier | + | 1924 // | sections | taskwait | * | 1925 // | sections | taskgroup | * | 1926 // | sections | flush | * | 1927 // | sections | ordered | + | 1928 // | sections | atomic | * | 1929 // | sections | target | * | 1930 // | sections | teams | + | 1931 // | sections | cancellation | | 1932 // | | point | ! | 1933 // | sections | cancel | ! | 1934 // | sections | taskloop | * | 1935 // | sections | taskloop simd | * | 1936 // | sections | distribute | | 1937 // +------------------+-----------------+------------------------------------+ 1938 // | section | parallel | * | 1939 // | section | for | + | 1940 // | section | for simd | + | 1941 // | section | master | + | 1942 // | section | critical | * | 1943 // | section | simd | * | 1944 // | section | sections | + | 1945 // | section | section | + | 1946 // | section | single | + | 1947 // | section | parallel for | * | 1948 // | section |parallel for simd| * | 1949 // | section |parallel sections| * | 1950 // | section | task | * | 1951 // | section | taskyield | * | 1952 // | section | barrier | + | 1953 // | section | taskwait | * | 1954 // | section | taskgroup | * | 1955 // | section | flush | * | 1956 // | section | ordered | + | 1957 // | section | atomic | * | 1958 // | section | target | * | 1959 // | section | teams | + | 1960 // | section | cancellation | | 1961 // | | point | ! | 1962 // | section | cancel | ! | 1963 // | section | taskloop | * | 1964 // | section | taskloop simd | * | 1965 // | section | distribute | | 1966 // +------------------+-----------------+------------------------------------+ 1967 // | single | parallel | * | 1968 // | single | for | + | 1969 // | single | for simd | + | 1970 // | single | master | + | 1971 // | single | critical | * | 1972 // | single | simd | * | 1973 // | single | sections | + | 1974 // | single | section | + | 1975 // | single | single | + | 1976 // | single | parallel for | * | 1977 // | single |parallel for simd| * | 1978 // | single |parallel sections| * | 1979 // | single | task | * | 1980 // | single | taskyield | * | 1981 // | single | barrier | + | 1982 // | single | taskwait | * | 1983 // | single | taskgroup | * | 1984 // | single | flush | * | 1985 // | single | ordered | + | 1986 // | single | atomic | * | 1987 // | single | target | * | 1988 // | single | teams | + | 1989 // | single | cancellation | | 1990 // | | point | | 1991 // | single | cancel | | 1992 // | single | taskloop | * | 1993 // | single | taskloop simd | * | 1994 // | single | distribute | | 1995 // +------------------+-----------------+------------------------------------+ 1996 // | parallel for | parallel | * | 1997 // | parallel for | for | + | 1998 // | parallel for | for simd | + | 1999 // | parallel for | master | + | 2000 // | parallel for | critical | * | 2001 // | parallel for | simd | * | 2002 // | parallel for | sections | + | 2003 // | parallel for | section | + | 2004 // | parallel for | single | + | 2005 // | parallel for | parallel for | * | 2006 // | parallel for |parallel for simd| * | 2007 // | parallel for |parallel sections| * | 2008 // | parallel for | task | * | 2009 // | parallel for | taskyield | * | 2010 // | parallel for | barrier | + | 2011 // | parallel for | taskwait | * | 2012 // | parallel for | taskgroup | * | 2013 // | parallel for | flush | * | 2014 // | parallel for | ordered | * (if construct is ordered) | 2015 // | parallel for | atomic | * | 2016 // | parallel for | target | * | 2017 // | parallel for | teams | + | 2018 // | parallel for | cancellation | | 2019 // | | point | ! | 2020 // | parallel for | cancel | ! | 2021 // | parallel for | taskloop | * | 2022 // | parallel for | taskloop simd | * | 2023 // | parallel for | distribute | | 2024 // +------------------+-----------------+------------------------------------+ 2025 // | parallel sections| parallel | * | 2026 // | parallel sections| for | + | 2027 // | parallel sections| for simd | + | 2028 // | parallel sections| master | + | 2029 // | parallel sections| critical | + | 2030 // | parallel sections| simd | * | 2031 // | parallel sections| sections | + | 2032 // | parallel sections| section | * | 2033 // | parallel sections| single | + | 2034 // | parallel sections| parallel for | * | 2035 // | parallel sections|parallel for simd| * | 2036 // | parallel sections|parallel sections| * | 2037 // | parallel sections| task | * | 2038 // | parallel sections| taskyield | * | 2039 // | parallel sections| barrier | + | 2040 // | parallel sections| taskwait | * | 2041 // | parallel sections| taskgroup | * | 2042 // | parallel sections| flush | * | 2043 // | parallel sections| ordered | + | 2044 // | parallel sections| atomic | * | 2045 // | parallel sections| target | * | 2046 // | parallel sections| teams | + | 2047 // | parallel sections| cancellation | | 2048 // | | point | ! | 2049 // | parallel sections| cancel | ! | 2050 // | parallel sections| taskloop | * | 2051 // | parallel sections| taskloop simd | * | 2052 // | parallel sections| distribute | | 2053 // +------------------+-----------------+------------------------------------+ 2054 // | task | parallel | * | 2055 // | task | for | + | 2056 // | task | for simd | + | 2057 // | task | master | + | 2058 // | task | critical | * | 2059 // | task | simd | * | 2060 // | task | sections | + | 2061 // | task | section | + | 2062 // | task | single | + | 2063 // | task | parallel for | * | 2064 // | task |parallel for simd| * | 2065 // | task |parallel sections| * | 2066 // | task | task | * | 2067 // | task | taskyield | * | 2068 // | task | barrier | + | 2069 // | task | taskwait | * | 2070 // | task | taskgroup | * | 2071 // | task | flush | * | 2072 // | task | ordered | + | 2073 // | task | atomic | * | 2074 // | task | target | * | 2075 // | task | teams | + | 2076 // | task | cancellation | | 2077 // | | point | ! | 2078 // | task | cancel | ! | 2079 // | task | taskloop | * | 2080 // | task | taskloop simd | * | 2081 // | task | distribute | | 2082 // +------------------+-----------------+------------------------------------+ 2083 // | ordered | parallel | * | 2084 // | ordered | for | + | 2085 // | ordered | for simd | + | 2086 // | ordered | master | * | 2087 // | ordered | critical | * | 2088 // | ordered | simd | * | 2089 // | ordered | sections | + | 2090 // | ordered | section | + | 2091 // | ordered | single | + | 2092 // | ordered | parallel for | * | 2093 // | ordered |parallel for simd| * | 2094 // | ordered |parallel sections| * | 2095 // | ordered | task | * | 2096 // | ordered | taskyield | * | 2097 // | ordered | barrier | + | 2098 // | ordered | taskwait | * | 2099 // | ordered | taskgroup | * | 2100 // | ordered | flush | * | 2101 // | ordered | ordered | + | 2102 // | ordered | atomic | * | 2103 // | ordered | target | * | 2104 // | ordered | teams | + | 2105 // | ordered | cancellation | | 2106 // | | point | | 2107 // | ordered | cancel | | 2108 // | ordered | taskloop | * | 2109 // | ordered | taskloop simd | * | 2110 // | ordered | distribute | | 2111 // +------------------+-----------------+------------------------------------+ 2112 // | atomic | parallel | | 2113 // | atomic | for | | 2114 // | atomic | for simd | | 2115 // | atomic | master | | 2116 // | atomic | critical | | 2117 // | atomic | simd | | 2118 // | atomic | sections | | 2119 // | atomic | section | | 2120 // | atomic | single | | 2121 // | atomic | parallel for | | 2122 // | atomic |parallel for simd| | 2123 // | atomic |parallel sections| | 2124 // | atomic | task | | 2125 // | atomic | taskyield | | 2126 // | atomic | barrier | | 2127 // | atomic | taskwait | | 2128 // | atomic | taskgroup | | 2129 // | atomic | flush | | 2130 // | atomic | ordered | | 2131 // | atomic | atomic | | 2132 // | atomic | target | | 2133 // | atomic | teams | | 2134 // | atomic | cancellation | | 2135 // | | point | | 2136 // | atomic | cancel | | 2137 // | atomic | taskloop | | 2138 // | atomic | taskloop simd | | 2139 // | atomic | distribute | | 2140 // +------------------+-----------------+------------------------------------+ 2141 // | target | parallel | * | 2142 // | target | for | * | 2143 // | target | for simd | * | 2144 // | target | master | * | 2145 // | target | critical | * | 2146 // | target | simd | * | 2147 // | target | sections | * | 2148 // | target | section | * | 2149 // | target | single | * | 2150 // | target | parallel for | * | 2151 // | target |parallel for simd| * | 2152 // | target |parallel sections| * | 2153 // | target | task | * | 2154 // | target | taskyield | * | 2155 // | target | barrier | * | 2156 // | target | taskwait | * | 2157 // | target | taskgroup | * | 2158 // | target | flush | * | 2159 // | target | ordered | * | 2160 // | target | atomic | * | 2161 // | target | target | * | 2162 // | target | teams | * | 2163 // | target | cancellation | | 2164 // | | point | | 2165 // | target | cancel | | 2166 // | target | taskloop | * | 2167 // | target | taskloop simd | * | 2168 // | target | distribute | | 2169 // +------------------+-----------------+------------------------------------+ 2170 // | teams | parallel | * | 2171 // | teams | for | + | 2172 // | teams | for simd | + | 2173 // | teams | master | + | 2174 // | teams | critical | + | 2175 // | teams | simd | + | 2176 // | teams | sections | + | 2177 // | teams | section | + | 2178 // | teams | single | + | 2179 // | teams | parallel for | * | 2180 // | teams |parallel for simd| * | 2181 // | teams |parallel sections| * | 2182 // | teams | task | + | 2183 // | teams | taskyield | + | 2184 // | teams | barrier | + | 2185 // | teams | taskwait | + | 2186 // | teams | taskgroup | + | 2187 // | teams | flush | + | 2188 // | teams | ordered | + | 2189 // | teams | atomic | + | 2190 // | teams | target | + | 2191 // | teams | teams | + | 2192 // | teams | cancellation | | 2193 // | | point | | 2194 // | teams | cancel | | 2195 // | teams | taskloop | + | 2196 // | teams | taskloop simd | + | 2197 // | teams | distribute | ! | 2198 // +------------------+-----------------+------------------------------------+ 2199 // | taskloop | parallel | * | 2200 // | taskloop | for | + | 2201 // | taskloop | for simd | + | 2202 // | taskloop | master | + | 2203 // | taskloop | critical | * | 2204 // | taskloop | simd | * | 2205 // | taskloop | sections | + | 2206 // | taskloop | section | + | 2207 // | taskloop | single | + | 2208 // | taskloop | parallel for | * | 2209 // | taskloop |parallel for simd| * | 2210 // | taskloop |parallel sections| * | 2211 // | taskloop | task | * | 2212 // | taskloop | taskyield | * | 2213 // | taskloop | barrier | + | 2214 // | taskloop | taskwait | * | 2215 // | taskloop | taskgroup | * | 2216 // | taskloop | flush | * | 2217 // | taskloop | ordered | + | 2218 // | taskloop | atomic | * | 2219 // | taskloop | target | * | 2220 // | taskloop | teams | + | 2221 // | taskloop | cancellation | | 2222 // | | point | | 2223 // | taskloop | cancel | | 2224 // | taskloop | taskloop | * | 2225 // | taskloop | distribute | | 2226 // +------------------+-----------------+------------------------------------+ 2227 // | taskloop simd | parallel | | 2228 // | taskloop simd | for | | 2229 // | taskloop simd | for simd | | 2230 // | taskloop simd | master | | 2231 // | taskloop simd | critical | | 2232 // | taskloop simd | simd | | 2233 // | taskloop simd | sections | | 2234 // | taskloop simd | section | | 2235 // | taskloop simd | single | | 2236 // | taskloop simd | parallel for | | 2237 // | taskloop simd |parallel for simd| | 2238 // | taskloop simd |parallel sections| | 2239 // | taskloop simd | task | | 2240 // | taskloop simd | taskyield | | 2241 // | taskloop simd | barrier | | 2242 // | taskloop simd | taskwait | | 2243 // | taskloop simd | taskgroup | | 2244 // | taskloop simd | flush | | 2245 // | taskloop simd | ordered | + (with simd clause) | 2246 // | taskloop simd | atomic | | 2247 // | taskloop simd | target | | 2248 // | taskloop simd | teams | | 2249 // | taskloop simd | cancellation | | 2250 // | | point | | 2251 // | taskloop simd | cancel | | 2252 // | taskloop simd | taskloop | | 2253 // | taskloop simd | taskloop simd | | 2254 // | taskloop simd | distribute | | 2255 // +------------------+-----------------+------------------------------------+ 2256 // | distribute | parallel | * | 2257 // | distribute | for | * | 2258 // | distribute | for simd | * | 2259 // | distribute | master | * | 2260 // | distribute | critical | * | 2261 // | distribute | simd | * | 2262 // | distribute | sections | * | 2263 // | distribute | section | * | 2264 // | distribute | single | * | 2265 // | distribute | parallel for | * | 2266 // | distribute |parallel for simd| * | 2267 // | distribute |parallel sections| * | 2268 // | distribute | task | * | 2269 // | distribute | taskyield | * | 2270 // | distribute | barrier | * | 2271 // | distribute | taskwait | * | 2272 // | distribute | taskgroup | * | 2273 // | distribute | flush | * | 2274 // | distribute | ordered | + | 2275 // | distribute | atomic | * | 2276 // | distribute | target | | 2277 // | distribute | teams | | 2278 // | distribute | cancellation | + | 2279 // | | point | | 2280 // | distribute | cancel | + | 2281 // | distribute | taskloop | * | 2282 // | distribute | taskloop simd | * | 2283 // | distribute | distribute | | 2284 // +------------------+-----------------+------------------------------------+ 2285 if (Stack->getCurScope()) { 2286 auto ParentRegion = Stack->getParentDirective(); 2287 bool NestingProhibited = false; 2288 bool CloseNesting = true; 2289 enum { 2290 NoRecommend, 2291 ShouldBeInParallelRegion, 2292 ShouldBeInOrderedRegion, 2293 ShouldBeInTargetRegion, 2294 ShouldBeInTeamsRegion 2295 } Recommend = NoRecommend; 2296 if (isOpenMPSimdDirective(ParentRegion) && CurrentRegion != OMPD_ordered) { 2297 // OpenMP [2.16, Nesting of Regions] 2298 // OpenMP constructs may not be nested inside a simd region. 2299 // OpenMP [2.8.1,simd Construct, Restrictions] 2300 // An ordered construct with the simd clause is the only OpenMP construct 2301 // that can appear in the simd region. 2302 SemaRef.Diag(StartLoc, diag::err_omp_prohibited_region_simd); 2303 return true; 2304 } 2305 if (ParentRegion == OMPD_atomic) { 2306 // OpenMP [2.16, Nesting of Regions] 2307 // OpenMP constructs may not be nested inside an atomic region. 2308 SemaRef.Diag(StartLoc, diag::err_omp_prohibited_region_atomic); 2309 return true; 2310 } 2311 if (CurrentRegion == OMPD_section) { 2312 // OpenMP [2.7.2, sections Construct, Restrictions] 2313 // Orphaned section directives are prohibited. That is, the section 2314 // directives must appear within the sections construct and must not be 2315 // encountered elsewhere in the sections region. 2316 if (ParentRegion != OMPD_sections && 2317 ParentRegion != OMPD_parallel_sections) { 2318 SemaRef.Diag(StartLoc, diag::err_omp_orphaned_section_directive) 2319 << (ParentRegion != OMPD_unknown) 2320 << getOpenMPDirectiveName(ParentRegion); 2321 return true; 2322 } 2323 return false; 2324 } 2325 // Allow some constructs to be orphaned (they could be used in functions, 2326 // called from OpenMP regions with the required preconditions). 2327 if (ParentRegion == OMPD_unknown) 2328 return false; 2329 if (CurrentRegion == OMPD_cancellation_point || 2330 CurrentRegion == OMPD_cancel) { 2331 // OpenMP [2.16, Nesting of Regions] 2332 // A cancellation point construct for which construct-type-clause is 2333 // taskgroup must be nested inside a task construct. A cancellation 2334 // point construct for which construct-type-clause is not taskgroup must 2335 // be closely nested inside an OpenMP construct that matches the type 2336 // specified in construct-type-clause. 2337 // A cancel construct for which construct-type-clause is taskgroup must be 2338 // nested inside a task construct. A cancel construct for which 2339 // construct-type-clause is not taskgroup must be closely nested inside an 2340 // OpenMP construct that matches the type specified in 2341 // construct-type-clause. 2342 NestingProhibited = 2343 !((CancelRegion == OMPD_parallel && ParentRegion == OMPD_parallel) || 2344 (CancelRegion == OMPD_for && 2345 (ParentRegion == OMPD_for || ParentRegion == OMPD_parallel_for)) || 2346 (CancelRegion == OMPD_taskgroup && ParentRegion == OMPD_task) || 2347 (CancelRegion == OMPD_sections && 2348 (ParentRegion == OMPD_section || ParentRegion == OMPD_sections || 2349 ParentRegion == OMPD_parallel_sections))); 2350 } else if (CurrentRegion == OMPD_master) { 2351 // OpenMP [2.16, Nesting of Regions] 2352 // A master region may not be closely nested inside a worksharing, 2353 // atomic, or explicit task region. 2354 NestingProhibited = isOpenMPWorksharingDirective(ParentRegion) || 2355 ParentRegion == OMPD_task || 2356 isOpenMPTaskLoopDirective(ParentRegion); 2357 } else if (CurrentRegion == OMPD_critical && CurrentName.getName()) { 2358 // OpenMP [2.16, Nesting of Regions] 2359 // A critical region may not be nested (closely or otherwise) inside a 2360 // critical region with the same name. Note that this restriction is not 2361 // sufficient to prevent deadlock. 2362 SourceLocation PreviousCriticalLoc; 2363 bool DeadLock = 2364 Stack->hasDirective([CurrentName, &PreviousCriticalLoc]( 2365 OpenMPDirectiveKind K, 2366 const DeclarationNameInfo &DNI, 2367 SourceLocation Loc) 2368 ->bool { 2369 if (K == OMPD_critical && 2370 DNI.getName() == CurrentName.getName()) { 2371 PreviousCriticalLoc = Loc; 2372 return true; 2373 } else 2374 return false; 2375 }, 2376 false /* skip top directive */); 2377 if (DeadLock) { 2378 SemaRef.Diag(StartLoc, 2379 diag::err_omp_prohibited_region_critical_same_name) 2380 << CurrentName.getName(); 2381 if (PreviousCriticalLoc.isValid()) 2382 SemaRef.Diag(PreviousCriticalLoc, 2383 diag::note_omp_previous_critical_region); 2384 return true; 2385 } 2386 } else if (CurrentRegion == OMPD_barrier) { 2387 // OpenMP [2.16, Nesting of Regions] 2388 // A barrier region may not be closely nested inside a worksharing, 2389 // explicit task, critical, ordered, atomic, or master region. 2390 NestingProhibited = 2391 isOpenMPWorksharingDirective(ParentRegion) || 2392 ParentRegion == OMPD_task || ParentRegion == OMPD_master || 2393 ParentRegion == OMPD_critical || ParentRegion == OMPD_ordered || 2394 isOpenMPTaskLoopDirective(ParentRegion); 2395 } else if (isOpenMPWorksharingDirective(CurrentRegion) && 2396 !isOpenMPParallelDirective(CurrentRegion)) { 2397 // OpenMP [2.16, Nesting of Regions] 2398 // A worksharing region may not be closely nested inside a worksharing, 2399 // explicit task, critical, ordered, atomic, or master region. 2400 NestingProhibited = 2401 isOpenMPWorksharingDirective(ParentRegion) || 2402 ParentRegion == OMPD_task || ParentRegion == OMPD_master || 2403 ParentRegion == OMPD_critical || ParentRegion == OMPD_ordered || 2404 isOpenMPTaskLoopDirective(ParentRegion); 2405 Recommend = ShouldBeInParallelRegion; 2406 } else if (CurrentRegion == OMPD_ordered) { 2407 // OpenMP [2.16, Nesting of Regions] 2408 // An ordered region may not be closely nested inside a critical, 2409 // atomic, or explicit task region. 2410 // An ordered region must be closely nested inside a loop region (or 2411 // parallel loop region) with an ordered clause. 2412 // OpenMP [2.8.1,simd Construct, Restrictions] 2413 // An ordered construct with the simd clause is the only OpenMP construct 2414 // that can appear in the simd region. 2415 NestingProhibited = ParentRegion == OMPD_critical || 2416 ParentRegion == OMPD_task || 2417 isOpenMPTaskLoopDirective(ParentRegion) || 2418 !(isOpenMPSimdDirective(ParentRegion) || 2419 Stack->isParentOrderedRegion()); 2420 Recommend = ShouldBeInOrderedRegion; 2421 } else if (isOpenMPTeamsDirective(CurrentRegion)) { 2422 // OpenMP [2.16, Nesting of Regions] 2423 // If specified, a teams construct must be contained within a target 2424 // construct. 2425 NestingProhibited = ParentRegion != OMPD_target; 2426 Recommend = ShouldBeInTargetRegion; 2427 Stack->setParentTeamsRegionLoc(Stack->getConstructLoc()); 2428 } 2429 if (!NestingProhibited && isOpenMPTeamsDirective(ParentRegion)) { 2430 // OpenMP [2.16, Nesting of Regions] 2431 // distribute, parallel, parallel sections, parallel workshare, and the 2432 // parallel loop and parallel loop SIMD constructs are the only OpenMP 2433 // constructs that can be closely nested in the teams region. 2434 NestingProhibited = !isOpenMPParallelDirective(CurrentRegion) && 2435 !isOpenMPDistributeDirective(CurrentRegion); 2436 Recommend = ShouldBeInParallelRegion; 2437 } 2438 if (!NestingProhibited && isOpenMPDistributeDirective(CurrentRegion)) { 2439 // OpenMP 4.5 [2.17 Nesting of Regions] 2440 // The region associated with the distribute construct must be strictly 2441 // nested inside a teams region 2442 NestingProhibited = !isOpenMPTeamsDirective(ParentRegion); 2443 Recommend = ShouldBeInTeamsRegion; 2444 } 2445 if (NestingProhibited) { 2446 SemaRef.Diag(StartLoc, diag::err_omp_prohibited_region) 2447 << CloseNesting << getOpenMPDirectiveName(ParentRegion) << Recommend 2448 << getOpenMPDirectiveName(CurrentRegion); 2449 return true; 2450 } 2451 } 2452 return false; 2453 } 2454 2455 static bool checkIfClauses(Sema &S, OpenMPDirectiveKind Kind, 2456 ArrayRef<OMPClause *> Clauses, 2457 ArrayRef<OpenMPDirectiveKind> AllowedNameModifiers) { 2458 bool ErrorFound = false; 2459 unsigned NamedModifiersNumber = 0; 2460 SmallVector<const OMPIfClause *, OMPC_unknown + 1> FoundNameModifiers( 2461 OMPD_unknown + 1); 2462 SmallVector<SourceLocation, 4> NameModifierLoc; 2463 for (const auto *C : Clauses) { 2464 if (const auto *IC = dyn_cast_or_null<OMPIfClause>(C)) { 2465 // At most one if clause without a directive-name-modifier can appear on 2466 // the directive. 2467 OpenMPDirectiveKind CurNM = IC->getNameModifier(); 2468 if (FoundNameModifiers[CurNM]) { 2469 S.Diag(C->getLocStart(), diag::err_omp_more_one_clause) 2470 << getOpenMPDirectiveName(Kind) << getOpenMPClauseName(OMPC_if) 2471 << (CurNM != OMPD_unknown) << getOpenMPDirectiveName(CurNM); 2472 ErrorFound = true; 2473 } else if (CurNM != OMPD_unknown) { 2474 NameModifierLoc.push_back(IC->getNameModifierLoc()); 2475 ++NamedModifiersNumber; 2476 } 2477 FoundNameModifiers[CurNM] = IC; 2478 if (CurNM == OMPD_unknown) 2479 continue; 2480 // Check if the specified name modifier is allowed for the current 2481 // directive. 2482 // At most one if clause with the particular directive-name-modifier can 2483 // appear on the directive. 2484 bool MatchFound = false; 2485 for (auto NM : AllowedNameModifiers) { 2486 if (CurNM == NM) { 2487 MatchFound = true; 2488 break; 2489 } 2490 } 2491 if (!MatchFound) { 2492 S.Diag(IC->getNameModifierLoc(), 2493 diag::err_omp_wrong_if_directive_name_modifier) 2494 << getOpenMPDirectiveName(CurNM) << getOpenMPDirectiveName(Kind); 2495 ErrorFound = true; 2496 } 2497 } 2498 } 2499 // If any if clause on the directive includes a directive-name-modifier then 2500 // all if clauses on the directive must include a directive-name-modifier. 2501 if (FoundNameModifiers[OMPD_unknown] && NamedModifiersNumber > 0) { 2502 if (NamedModifiersNumber == AllowedNameModifiers.size()) { 2503 S.Diag(FoundNameModifiers[OMPD_unknown]->getLocStart(), 2504 diag::err_omp_no_more_if_clause); 2505 } else { 2506 std::string Values; 2507 std::string Sep(", "); 2508 unsigned AllowedCnt = 0; 2509 unsigned TotalAllowedNum = 2510 AllowedNameModifiers.size() - NamedModifiersNumber; 2511 for (unsigned Cnt = 0, End = AllowedNameModifiers.size(); Cnt < End; 2512 ++Cnt) { 2513 OpenMPDirectiveKind NM = AllowedNameModifiers[Cnt]; 2514 if (!FoundNameModifiers[NM]) { 2515 Values += "'"; 2516 Values += getOpenMPDirectiveName(NM); 2517 Values += "'"; 2518 if (AllowedCnt + 2 == TotalAllowedNum) 2519 Values += " or "; 2520 else if (AllowedCnt + 1 != TotalAllowedNum) 2521 Values += Sep; 2522 ++AllowedCnt; 2523 } 2524 } 2525 S.Diag(FoundNameModifiers[OMPD_unknown]->getCondition()->getLocStart(), 2526 diag::err_omp_unnamed_if_clause) 2527 << (TotalAllowedNum > 1) << Values; 2528 } 2529 for (auto Loc : NameModifierLoc) { 2530 S.Diag(Loc, diag::note_omp_previous_named_if_clause); 2531 } 2532 ErrorFound = true; 2533 } 2534 return ErrorFound; 2535 } 2536 2537 StmtResult Sema::ActOnOpenMPExecutableDirective( 2538 OpenMPDirectiveKind Kind, const DeclarationNameInfo &DirName, 2539 OpenMPDirectiveKind CancelRegion, ArrayRef<OMPClause *> Clauses, 2540 Stmt *AStmt, SourceLocation StartLoc, SourceLocation EndLoc) { 2541 StmtResult Res = StmtError(); 2542 if (CheckNestingOfRegions(*this, DSAStack, Kind, DirName, CancelRegion, 2543 StartLoc)) 2544 return StmtError(); 2545 2546 llvm::SmallVector<OMPClause *, 8> ClausesWithImplicit; 2547 llvm::DenseMap<VarDecl *, Expr *> VarsWithInheritedDSA; 2548 bool ErrorFound = false; 2549 ClausesWithImplicit.append(Clauses.begin(), Clauses.end()); 2550 if (AStmt) { 2551 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 2552 2553 // Check default data sharing attributes for referenced variables. 2554 DSAAttrChecker DSAChecker(DSAStack, *this, cast<CapturedStmt>(AStmt)); 2555 DSAChecker.Visit(cast<CapturedStmt>(AStmt)->getCapturedStmt()); 2556 if (DSAChecker.isErrorFound()) 2557 return StmtError(); 2558 // Generate list of implicitly defined firstprivate variables. 2559 VarsWithInheritedDSA = DSAChecker.getVarsWithInheritedDSA(); 2560 2561 if (!DSAChecker.getImplicitFirstprivate().empty()) { 2562 if (OMPClause *Implicit = ActOnOpenMPFirstprivateClause( 2563 DSAChecker.getImplicitFirstprivate(), SourceLocation(), 2564 SourceLocation(), SourceLocation())) { 2565 ClausesWithImplicit.push_back(Implicit); 2566 ErrorFound = cast<OMPFirstprivateClause>(Implicit)->varlist_size() != 2567 DSAChecker.getImplicitFirstprivate().size(); 2568 } else 2569 ErrorFound = true; 2570 } 2571 } 2572 2573 llvm::SmallVector<OpenMPDirectiveKind, 4> AllowedNameModifiers; 2574 switch (Kind) { 2575 case OMPD_parallel: 2576 Res = ActOnOpenMPParallelDirective(ClausesWithImplicit, AStmt, StartLoc, 2577 EndLoc); 2578 AllowedNameModifiers.push_back(OMPD_parallel); 2579 break; 2580 case OMPD_simd: 2581 Res = ActOnOpenMPSimdDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc, 2582 VarsWithInheritedDSA); 2583 break; 2584 case OMPD_for: 2585 Res = ActOnOpenMPForDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc, 2586 VarsWithInheritedDSA); 2587 break; 2588 case OMPD_for_simd: 2589 Res = ActOnOpenMPForSimdDirective(ClausesWithImplicit, AStmt, StartLoc, 2590 EndLoc, VarsWithInheritedDSA); 2591 break; 2592 case OMPD_sections: 2593 Res = ActOnOpenMPSectionsDirective(ClausesWithImplicit, AStmt, StartLoc, 2594 EndLoc); 2595 break; 2596 case OMPD_section: 2597 assert(ClausesWithImplicit.empty() && 2598 "No clauses are allowed for 'omp section' directive"); 2599 Res = ActOnOpenMPSectionDirective(AStmt, StartLoc, EndLoc); 2600 break; 2601 case OMPD_single: 2602 Res = ActOnOpenMPSingleDirective(ClausesWithImplicit, AStmt, StartLoc, 2603 EndLoc); 2604 break; 2605 case OMPD_master: 2606 assert(ClausesWithImplicit.empty() && 2607 "No clauses are allowed for 'omp master' directive"); 2608 Res = ActOnOpenMPMasterDirective(AStmt, StartLoc, EndLoc); 2609 break; 2610 case OMPD_critical: 2611 Res = ActOnOpenMPCriticalDirective(DirName, ClausesWithImplicit, AStmt, 2612 StartLoc, EndLoc); 2613 break; 2614 case OMPD_parallel_for: 2615 Res = ActOnOpenMPParallelForDirective(ClausesWithImplicit, AStmt, StartLoc, 2616 EndLoc, VarsWithInheritedDSA); 2617 AllowedNameModifiers.push_back(OMPD_parallel); 2618 break; 2619 case OMPD_parallel_for_simd: 2620 Res = ActOnOpenMPParallelForSimdDirective( 2621 ClausesWithImplicit, AStmt, StartLoc, EndLoc, VarsWithInheritedDSA); 2622 AllowedNameModifiers.push_back(OMPD_parallel); 2623 break; 2624 case OMPD_parallel_sections: 2625 Res = ActOnOpenMPParallelSectionsDirective(ClausesWithImplicit, AStmt, 2626 StartLoc, EndLoc); 2627 AllowedNameModifiers.push_back(OMPD_parallel); 2628 break; 2629 case OMPD_task: 2630 Res = 2631 ActOnOpenMPTaskDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc); 2632 AllowedNameModifiers.push_back(OMPD_task); 2633 break; 2634 case OMPD_taskyield: 2635 assert(ClausesWithImplicit.empty() && 2636 "No clauses are allowed for 'omp taskyield' directive"); 2637 assert(AStmt == nullptr && 2638 "No associated statement allowed for 'omp taskyield' directive"); 2639 Res = ActOnOpenMPTaskyieldDirective(StartLoc, EndLoc); 2640 break; 2641 case OMPD_barrier: 2642 assert(ClausesWithImplicit.empty() && 2643 "No clauses are allowed for 'omp barrier' directive"); 2644 assert(AStmt == nullptr && 2645 "No associated statement allowed for 'omp barrier' directive"); 2646 Res = ActOnOpenMPBarrierDirective(StartLoc, EndLoc); 2647 break; 2648 case OMPD_taskwait: 2649 assert(ClausesWithImplicit.empty() && 2650 "No clauses are allowed for 'omp taskwait' directive"); 2651 assert(AStmt == nullptr && 2652 "No associated statement allowed for 'omp taskwait' directive"); 2653 Res = ActOnOpenMPTaskwaitDirective(StartLoc, EndLoc); 2654 break; 2655 case OMPD_taskgroup: 2656 assert(ClausesWithImplicit.empty() && 2657 "No clauses are allowed for 'omp taskgroup' directive"); 2658 Res = ActOnOpenMPTaskgroupDirective(AStmt, StartLoc, EndLoc); 2659 break; 2660 case OMPD_flush: 2661 assert(AStmt == nullptr && 2662 "No associated statement allowed for 'omp flush' directive"); 2663 Res = ActOnOpenMPFlushDirective(ClausesWithImplicit, StartLoc, EndLoc); 2664 break; 2665 case OMPD_ordered: 2666 Res = ActOnOpenMPOrderedDirective(ClausesWithImplicit, AStmt, StartLoc, 2667 EndLoc); 2668 break; 2669 case OMPD_atomic: 2670 Res = ActOnOpenMPAtomicDirective(ClausesWithImplicit, AStmt, StartLoc, 2671 EndLoc); 2672 break; 2673 case OMPD_teams: 2674 Res = 2675 ActOnOpenMPTeamsDirective(ClausesWithImplicit, AStmt, StartLoc, EndLoc); 2676 break; 2677 case OMPD_target: 2678 Res = ActOnOpenMPTargetDirective(ClausesWithImplicit, AStmt, StartLoc, 2679 EndLoc); 2680 AllowedNameModifiers.push_back(OMPD_target); 2681 break; 2682 case OMPD_cancellation_point: 2683 assert(ClausesWithImplicit.empty() && 2684 "No clauses are allowed for 'omp cancellation point' directive"); 2685 assert(AStmt == nullptr && "No associated statement allowed for 'omp " 2686 "cancellation point' directive"); 2687 Res = ActOnOpenMPCancellationPointDirective(StartLoc, EndLoc, CancelRegion); 2688 break; 2689 case OMPD_cancel: 2690 assert(AStmt == nullptr && 2691 "No associated statement allowed for 'omp cancel' directive"); 2692 Res = ActOnOpenMPCancelDirective(ClausesWithImplicit, StartLoc, EndLoc, 2693 CancelRegion); 2694 AllowedNameModifiers.push_back(OMPD_cancel); 2695 break; 2696 case OMPD_target_data: 2697 Res = ActOnOpenMPTargetDataDirective(ClausesWithImplicit, AStmt, StartLoc, 2698 EndLoc); 2699 AllowedNameModifiers.push_back(OMPD_target_data); 2700 break; 2701 case OMPD_taskloop: 2702 Res = ActOnOpenMPTaskLoopDirective(ClausesWithImplicit, AStmt, StartLoc, 2703 EndLoc, VarsWithInheritedDSA); 2704 AllowedNameModifiers.push_back(OMPD_taskloop); 2705 break; 2706 case OMPD_taskloop_simd: 2707 Res = ActOnOpenMPTaskLoopSimdDirective(ClausesWithImplicit, AStmt, StartLoc, 2708 EndLoc, VarsWithInheritedDSA); 2709 AllowedNameModifiers.push_back(OMPD_taskloop); 2710 break; 2711 case OMPD_distribute: 2712 Res = ActOnOpenMPDistributeDirective(ClausesWithImplicit, AStmt, StartLoc, 2713 EndLoc, VarsWithInheritedDSA); 2714 break; 2715 case OMPD_threadprivate: 2716 llvm_unreachable("OpenMP Directive is not allowed"); 2717 case OMPD_unknown: 2718 llvm_unreachable("Unknown OpenMP directive"); 2719 } 2720 2721 for (auto P : VarsWithInheritedDSA) { 2722 Diag(P.second->getExprLoc(), diag::err_omp_no_dsa_for_variable) 2723 << P.first << P.second->getSourceRange(); 2724 } 2725 ErrorFound = !VarsWithInheritedDSA.empty() || ErrorFound; 2726 2727 if (!AllowedNameModifiers.empty()) 2728 ErrorFound = checkIfClauses(*this, Kind, Clauses, AllowedNameModifiers) || 2729 ErrorFound; 2730 2731 if (ErrorFound) 2732 return StmtError(); 2733 return Res; 2734 } 2735 2736 StmtResult Sema::ActOnOpenMPParallelDirective(ArrayRef<OMPClause *> Clauses, 2737 Stmt *AStmt, 2738 SourceLocation StartLoc, 2739 SourceLocation EndLoc) { 2740 if (!AStmt) 2741 return StmtError(); 2742 2743 CapturedStmt *CS = cast<CapturedStmt>(AStmt); 2744 // 1.2.2 OpenMP Language Terminology 2745 // Structured block - An executable statement with a single entry at the 2746 // top and a single exit at the bottom. 2747 // The point of exit cannot be a branch out of the structured block. 2748 // longjmp() and throw() must not violate the entry/exit criteria. 2749 CS->getCapturedDecl()->setNothrow(); 2750 2751 getCurFunction()->setHasBranchProtectedScope(); 2752 2753 return OMPParallelDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt, 2754 DSAStack->isCancelRegion()); 2755 } 2756 2757 namespace { 2758 /// \brief Helper class for checking canonical form of the OpenMP loops and 2759 /// extracting iteration space of each loop in the loop nest, that will be used 2760 /// for IR generation. 2761 class OpenMPIterationSpaceChecker { 2762 /// \brief Reference to Sema. 2763 Sema &SemaRef; 2764 /// \brief A location for diagnostics (when there is no some better location). 2765 SourceLocation DefaultLoc; 2766 /// \brief A location for diagnostics (when increment is not compatible). 2767 SourceLocation ConditionLoc; 2768 /// \brief A source location for referring to loop init later. 2769 SourceRange InitSrcRange; 2770 /// \brief A source location for referring to condition later. 2771 SourceRange ConditionSrcRange; 2772 /// \brief A source location for referring to increment later. 2773 SourceRange IncrementSrcRange; 2774 /// \brief Loop variable. 2775 VarDecl *Var; 2776 /// \brief Reference to loop variable. 2777 DeclRefExpr *VarRef; 2778 /// \brief Lower bound (initializer for the var). 2779 Expr *LB; 2780 /// \brief Upper bound. 2781 Expr *UB; 2782 /// \brief Loop step (increment). 2783 Expr *Step; 2784 /// \brief This flag is true when condition is one of: 2785 /// Var < UB 2786 /// Var <= UB 2787 /// UB > Var 2788 /// UB >= Var 2789 bool TestIsLessOp; 2790 /// \brief This flag is true when condition is strict ( < or > ). 2791 bool TestIsStrictOp; 2792 /// \brief This flag is true when step is subtracted on each iteration. 2793 bool SubtractStep; 2794 2795 public: 2796 OpenMPIterationSpaceChecker(Sema &SemaRef, SourceLocation DefaultLoc) 2797 : SemaRef(SemaRef), DefaultLoc(DefaultLoc), ConditionLoc(DefaultLoc), 2798 InitSrcRange(SourceRange()), ConditionSrcRange(SourceRange()), 2799 IncrementSrcRange(SourceRange()), Var(nullptr), VarRef(nullptr), 2800 LB(nullptr), UB(nullptr), Step(nullptr), TestIsLessOp(false), 2801 TestIsStrictOp(false), SubtractStep(false) {} 2802 /// \brief Check init-expr for canonical loop form and save loop counter 2803 /// variable - #Var and its initialization value - #LB. 2804 bool CheckInit(Stmt *S, bool EmitDiags = true); 2805 /// \brief Check test-expr for canonical form, save upper-bound (#UB), flags 2806 /// for less/greater and for strict/non-strict comparison. 2807 bool CheckCond(Expr *S); 2808 /// \brief Check incr-expr for canonical loop form and return true if it 2809 /// does not conform, otherwise save loop step (#Step). 2810 bool CheckInc(Expr *S); 2811 /// \brief Return the loop counter variable. 2812 VarDecl *GetLoopVar() const { return Var; } 2813 /// \brief Return the reference expression to loop counter variable. 2814 DeclRefExpr *GetLoopVarRefExpr() const { return VarRef; } 2815 /// \brief Source range of the loop init. 2816 SourceRange GetInitSrcRange() const { return InitSrcRange; } 2817 /// \brief Source range of the loop condition. 2818 SourceRange GetConditionSrcRange() const { return ConditionSrcRange; } 2819 /// \brief Source range of the loop increment. 2820 SourceRange GetIncrementSrcRange() const { return IncrementSrcRange; } 2821 /// \brief True if the step should be subtracted. 2822 bool ShouldSubtractStep() const { return SubtractStep; } 2823 /// \brief Build the expression to calculate the number of iterations. 2824 Expr *BuildNumIterations(Scope *S, const bool LimitedType) const; 2825 /// \brief Build the precondition expression for the loops. 2826 Expr *BuildPreCond(Scope *S, Expr *Cond) const; 2827 /// \brief Build reference expression to the counter be used for codegen. 2828 Expr *BuildCounterVar() const; 2829 /// \brief Build reference expression to the private counter be used for 2830 /// codegen. 2831 Expr *BuildPrivateCounterVar() const; 2832 /// \brief Build initization of the counter be used for codegen. 2833 Expr *BuildCounterInit() const; 2834 /// \brief Build step of the counter be used for codegen. 2835 Expr *BuildCounterStep() const; 2836 /// \brief Return true if any expression is dependent. 2837 bool Dependent() const; 2838 2839 private: 2840 /// \brief Check the right-hand side of an assignment in the increment 2841 /// expression. 2842 bool CheckIncRHS(Expr *RHS); 2843 /// \brief Helper to set loop counter variable and its initializer. 2844 bool SetVarAndLB(VarDecl *NewVar, DeclRefExpr *NewVarRefExpr, Expr *NewLB); 2845 /// \brief Helper to set upper bound. 2846 bool SetUB(Expr *NewUB, bool LessOp, bool StrictOp, SourceRange SR, 2847 SourceLocation SL); 2848 /// \brief Helper to set loop increment. 2849 bool SetStep(Expr *NewStep, bool Subtract); 2850 }; 2851 2852 bool OpenMPIterationSpaceChecker::Dependent() const { 2853 if (!Var) { 2854 assert(!LB && !UB && !Step); 2855 return false; 2856 } 2857 return Var->getType()->isDependentType() || (LB && LB->isValueDependent()) || 2858 (UB && UB->isValueDependent()) || (Step && Step->isValueDependent()); 2859 } 2860 2861 template <typename T> 2862 static T *getExprAsWritten(T *E) { 2863 if (auto *ExprTemp = dyn_cast<ExprWithCleanups>(E)) 2864 E = ExprTemp->getSubExpr(); 2865 2866 if (auto *MTE = dyn_cast<MaterializeTemporaryExpr>(E)) 2867 E = MTE->GetTemporaryExpr(); 2868 2869 while (auto *Binder = dyn_cast<CXXBindTemporaryExpr>(E)) 2870 E = Binder->getSubExpr(); 2871 2872 if (auto *ICE = dyn_cast<ImplicitCastExpr>(E)) 2873 E = ICE->getSubExprAsWritten(); 2874 return E->IgnoreParens(); 2875 } 2876 2877 bool OpenMPIterationSpaceChecker::SetVarAndLB(VarDecl *NewVar, 2878 DeclRefExpr *NewVarRefExpr, 2879 Expr *NewLB) { 2880 // State consistency checking to ensure correct usage. 2881 assert(Var == nullptr && LB == nullptr && VarRef == nullptr && 2882 UB == nullptr && Step == nullptr && !TestIsLessOp && !TestIsStrictOp); 2883 if (!NewVar || !NewLB) 2884 return true; 2885 Var = NewVar; 2886 VarRef = NewVarRefExpr; 2887 if (auto *CE = dyn_cast_or_null<CXXConstructExpr>(NewLB)) 2888 if (const CXXConstructorDecl *Ctor = CE->getConstructor()) 2889 if ((Ctor->isCopyOrMoveConstructor() || 2890 Ctor->isConvertingConstructor(/*AllowExplicit=*/false)) && 2891 CE->getNumArgs() > 0 && CE->getArg(0) != nullptr) 2892 NewLB = CE->getArg(0)->IgnoreParenImpCasts(); 2893 LB = NewLB; 2894 return false; 2895 } 2896 2897 bool OpenMPIterationSpaceChecker::SetUB(Expr *NewUB, bool LessOp, bool StrictOp, 2898 SourceRange SR, SourceLocation SL) { 2899 // State consistency checking to ensure correct usage. 2900 assert(Var != nullptr && LB != nullptr && UB == nullptr && Step == nullptr && 2901 !TestIsLessOp && !TestIsStrictOp); 2902 if (!NewUB) 2903 return true; 2904 UB = NewUB; 2905 TestIsLessOp = LessOp; 2906 TestIsStrictOp = StrictOp; 2907 ConditionSrcRange = SR; 2908 ConditionLoc = SL; 2909 return false; 2910 } 2911 2912 bool OpenMPIterationSpaceChecker::SetStep(Expr *NewStep, bool Subtract) { 2913 // State consistency checking to ensure correct usage. 2914 assert(Var != nullptr && LB != nullptr && Step == nullptr); 2915 if (!NewStep) 2916 return true; 2917 if (!NewStep->isValueDependent()) { 2918 // Check that the step is integer expression. 2919 SourceLocation StepLoc = NewStep->getLocStart(); 2920 ExprResult Val = 2921 SemaRef.PerformOpenMPImplicitIntegerConversion(StepLoc, NewStep); 2922 if (Val.isInvalid()) 2923 return true; 2924 NewStep = Val.get(); 2925 2926 // OpenMP [2.6, Canonical Loop Form, Restrictions] 2927 // If test-expr is of form var relational-op b and relational-op is < or 2928 // <= then incr-expr must cause var to increase on each iteration of the 2929 // loop. If test-expr is of form var relational-op b and relational-op is 2930 // > or >= then incr-expr must cause var to decrease on each iteration of 2931 // the loop. 2932 // If test-expr is of form b relational-op var and relational-op is < or 2933 // <= then incr-expr must cause var to decrease on each iteration of the 2934 // loop. If test-expr is of form b relational-op var and relational-op is 2935 // > or >= then incr-expr must cause var to increase on each iteration of 2936 // the loop. 2937 llvm::APSInt Result; 2938 bool IsConstant = NewStep->isIntegerConstantExpr(Result, SemaRef.Context); 2939 bool IsUnsigned = !NewStep->getType()->hasSignedIntegerRepresentation(); 2940 bool IsConstNeg = 2941 IsConstant && Result.isSigned() && (Subtract != Result.isNegative()); 2942 bool IsConstPos = 2943 IsConstant && Result.isSigned() && (Subtract == Result.isNegative()); 2944 bool IsConstZero = IsConstant && !Result.getBoolValue(); 2945 if (UB && (IsConstZero || 2946 (TestIsLessOp ? (IsConstNeg || (IsUnsigned && Subtract)) 2947 : (IsConstPos || (IsUnsigned && !Subtract))))) { 2948 SemaRef.Diag(NewStep->getExprLoc(), 2949 diag::err_omp_loop_incr_not_compatible) 2950 << Var << TestIsLessOp << NewStep->getSourceRange(); 2951 SemaRef.Diag(ConditionLoc, 2952 diag::note_omp_loop_cond_requres_compatible_incr) 2953 << TestIsLessOp << ConditionSrcRange; 2954 return true; 2955 } 2956 if (TestIsLessOp == Subtract) { 2957 NewStep = SemaRef.CreateBuiltinUnaryOp(NewStep->getExprLoc(), UO_Minus, 2958 NewStep).get(); 2959 Subtract = !Subtract; 2960 } 2961 } 2962 2963 Step = NewStep; 2964 SubtractStep = Subtract; 2965 return false; 2966 } 2967 2968 bool OpenMPIterationSpaceChecker::CheckInit(Stmt *S, bool EmitDiags) { 2969 // Check init-expr for canonical loop form and save loop counter 2970 // variable - #Var and its initialization value - #LB. 2971 // OpenMP [2.6] Canonical loop form. init-expr may be one of the following: 2972 // var = lb 2973 // integer-type var = lb 2974 // random-access-iterator-type var = lb 2975 // pointer-type var = lb 2976 // 2977 if (!S) { 2978 if (EmitDiags) { 2979 SemaRef.Diag(DefaultLoc, diag::err_omp_loop_not_canonical_init); 2980 } 2981 return true; 2982 } 2983 InitSrcRange = S->getSourceRange(); 2984 if (Expr *E = dyn_cast<Expr>(S)) 2985 S = E->IgnoreParens(); 2986 if (auto BO = dyn_cast<BinaryOperator>(S)) { 2987 if (BO->getOpcode() == BO_Assign) 2988 if (auto DRE = dyn_cast<DeclRefExpr>(BO->getLHS()->IgnoreParens())) 2989 return SetVarAndLB(dyn_cast<VarDecl>(DRE->getDecl()), DRE, 2990 BO->getRHS()); 2991 } else if (auto DS = dyn_cast<DeclStmt>(S)) { 2992 if (DS->isSingleDecl()) { 2993 if (auto Var = dyn_cast_or_null<VarDecl>(DS->getSingleDecl())) { 2994 if (Var->hasInit() && !Var->getType()->isReferenceType()) { 2995 // Accept non-canonical init form here but emit ext. warning. 2996 if (Var->getInitStyle() != VarDecl::CInit && EmitDiags) 2997 SemaRef.Diag(S->getLocStart(), 2998 diag::ext_omp_loop_not_canonical_init) 2999 << S->getSourceRange(); 3000 return SetVarAndLB(Var, nullptr, Var->getInit()); 3001 } 3002 } 3003 } 3004 } else if (auto CE = dyn_cast<CXXOperatorCallExpr>(S)) 3005 if (CE->getOperator() == OO_Equal) 3006 if (auto DRE = dyn_cast<DeclRefExpr>(CE->getArg(0))) 3007 return SetVarAndLB(dyn_cast<VarDecl>(DRE->getDecl()), DRE, 3008 CE->getArg(1)); 3009 3010 if (EmitDiags) { 3011 SemaRef.Diag(S->getLocStart(), diag::err_omp_loop_not_canonical_init) 3012 << S->getSourceRange(); 3013 } 3014 return true; 3015 } 3016 3017 /// \brief Ignore parenthesizes, implicit casts, copy constructor and return the 3018 /// variable (which may be the loop variable) if possible. 3019 static const VarDecl *GetInitVarDecl(const Expr *E) { 3020 if (!E) 3021 return nullptr; 3022 E = getExprAsWritten(E); 3023 if (auto *CE = dyn_cast_or_null<CXXConstructExpr>(E)) 3024 if (const CXXConstructorDecl *Ctor = CE->getConstructor()) 3025 if ((Ctor->isCopyOrMoveConstructor() || 3026 Ctor->isConvertingConstructor(/*AllowExplicit=*/false)) && 3027 CE->getNumArgs() > 0 && CE->getArg(0) != nullptr) 3028 E = CE->getArg(0)->IgnoreParenImpCasts(); 3029 auto DRE = dyn_cast_or_null<DeclRefExpr>(E); 3030 if (!DRE) 3031 return nullptr; 3032 return dyn_cast<VarDecl>(DRE->getDecl()); 3033 } 3034 3035 bool OpenMPIterationSpaceChecker::CheckCond(Expr *S) { 3036 // Check test-expr for canonical form, save upper-bound UB, flags for 3037 // less/greater and for strict/non-strict comparison. 3038 // OpenMP [2.6] Canonical loop form. Test-expr may be one of the following: 3039 // var relational-op b 3040 // b relational-op var 3041 // 3042 if (!S) { 3043 SemaRef.Diag(DefaultLoc, diag::err_omp_loop_not_canonical_cond) << Var; 3044 return true; 3045 } 3046 S = getExprAsWritten(S); 3047 SourceLocation CondLoc = S->getLocStart(); 3048 if (auto BO = dyn_cast<BinaryOperator>(S)) { 3049 if (BO->isRelationalOp()) { 3050 if (GetInitVarDecl(BO->getLHS()) == Var) 3051 return SetUB(BO->getRHS(), 3052 (BO->getOpcode() == BO_LT || BO->getOpcode() == BO_LE), 3053 (BO->getOpcode() == BO_LT || BO->getOpcode() == BO_GT), 3054 BO->getSourceRange(), BO->getOperatorLoc()); 3055 if (GetInitVarDecl(BO->getRHS()) == Var) 3056 return SetUB(BO->getLHS(), 3057 (BO->getOpcode() == BO_GT || BO->getOpcode() == BO_GE), 3058 (BO->getOpcode() == BO_LT || BO->getOpcode() == BO_GT), 3059 BO->getSourceRange(), BO->getOperatorLoc()); 3060 } 3061 } else if (auto CE = dyn_cast<CXXOperatorCallExpr>(S)) { 3062 if (CE->getNumArgs() == 2) { 3063 auto Op = CE->getOperator(); 3064 switch (Op) { 3065 case OO_Greater: 3066 case OO_GreaterEqual: 3067 case OO_Less: 3068 case OO_LessEqual: 3069 if (GetInitVarDecl(CE->getArg(0)) == Var) 3070 return SetUB(CE->getArg(1), Op == OO_Less || Op == OO_LessEqual, 3071 Op == OO_Less || Op == OO_Greater, CE->getSourceRange(), 3072 CE->getOperatorLoc()); 3073 if (GetInitVarDecl(CE->getArg(1)) == Var) 3074 return SetUB(CE->getArg(0), Op == OO_Greater || Op == OO_GreaterEqual, 3075 Op == OO_Less || Op == OO_Greater, CE->getSourceRange(), 3076 CE->getOperatorLoc()); 3077 break; 3078 default: 3079 break; 3080 } 3081 } 3082 } 3083 SemaRef.Diag(CondLoc, diag::err_omp_loop_not_canonical_cond) 3084 << S->getSourceRange() << Var; 3085 return true; 3086 } 3087 3088 bool OpenMPIterationSpaceChecker::CheckIncRHS(Expr *RHS) { 3089 // RHS of canonical loop form increment can be: 3090 // var + incr 3091 // incr + var 3092 // var - incr 3093 // 3094 RHS = RHS->IgnoreParenImpCasts(); 3095 if (auto BO = dyn_cast<BinaryOperator>(RHS)) { 3096 if (BO->isAdditiveOp()) { 3097 bool IsAdd = BO->getOpcode() == BO_Add; 3098 if (GetInitVarDecl(BO->getLHS()) == Var) 3099 return SetStep(BO->getRHS(), !IsAdd); 3100 if (IsAdd && GetInitVarDecl(BO->getRHS()) == Var) 3101 return SetStep(BO->getLHS(), false); 3102 } 3103 } else if (auto CE = dyn_cast<CXXOperatorCallExpr>(RHS)) { 3104 bool IsAdd = CE->getOperator() == OO_Plus; 3105 if ((IsAdd || CE->getOperator() == OO_Minus) && CE->getNumArgs() == 2) { 3106 if (GetInitVarDecl(CE->getArg(0)) == Var) 3107 return SetStep(CE->getArg(1), !IsAdd); 3108 if (IsAdd && GetInitVarDecl(CE->getArg(1)) == Var) 3109 return SetStep(CE->getArg(0), false); 3110 } 3111 } 3112 SemaRef.Diag(RHS->getLocStart(), diag::err_omp_loop_not_canonical_incr) 3113 << RHS->getSourceRange() << Var; 3114 return true; 3115 } 3116 3117 bool OpenMPIterationSpaceChecker::CheckInc(Expr *S) { 3118 // Check incr-expr for canonical loop form and return true if it 3119 // does not conform. 3120 // OpenMP [2.6] Canonical loop form. Test-expr may be one of the following: 3121 // ++var 3122 // var++ 3123 // --var 3124 // var-- 3125 // var += incr 3126 // var -= incr 3127 // var = var + incr 3128 // var = incr + var 3129 // var = var - incr 3130 // 3131 if (!S) { 3132 SemaRef.Diag(DefaultLoc, diag::err_omp_loop_not_canonical_incr) << Var; 3133 return true; 3134 } 3135 IncrementSrcRange = S->getSourceRange(); 3136 S = S->IgnoreParens(); 3137 if (auto UO = dyn_cast<UnaryOperator>(S)) { 3138 if (UO->isIncrementDecrementOp() && GetInitVarDecl(UO->getSubExpr()) == Var) 3139 return SetStep( 3140 SemaRef.ActOnIntegerConstant(UO->getLocStart(), 3141 (UO->isDecrementOp() ? -1 : 1)).get(), 3142 false); 3143 } else if (auto BO = dyn_cast<BinaryOperator>(S)) { 3144 switch (BO->getOpcode()) { 3145 case BO_AddAssign: 3146 case BO_SubAssign: 3147 if (GetInitVarDecl(BO->getLHS()) == Var) 3148 return SetStep(BO->getRHS(), BO->getOpcode() == BO_SubAssign); 3149 break; 3150 case BO_Assign: 3151 if (GetInitVarDecl(BO->getLHS()) == Var) 3152 return CheckIncRHS(BO->getRHS()); 3153 break; 3154 default: 3155 break; 3156 } 3157 } else if (auto CE = dyn_cast<CXXOperatorCallExpr>(S)) { 3158 switch (CE->getOperator()) { 3159 case OO_PlusPlus: 3160 case OO_MinusMinus: 3161 if (GetInitVarDecl(CE->getArg(0)) == Var) 3162 return SetStep( 3163 SemaRef.ActOnIntegerConstant( 3164 CE->getLocStart(), 3165 ((CE->getOperator() == OO_MinusMinus) ? -1 : 1)).get(), 3166 false); 3167 break; 3168 case OO_PlusEqual: 3169 case OO_MinusEqual: 3170 if (GetInitVarDecl(CE->getArg(0)) == Var) 3171 return SetStep(CE->getArg(1), CE->getOperator() == OO_MinusEqual); 3172 break; 3173 case OO_Equal: 3174 if (GetInitVarDecl(CE->getArg(0)) == Var) 3175 return CheckIncRHS(CE->getArg(1)); 3176 break; 3177 default: 3178 break; 3179 } 3180 } 3181 SemaRef.Diag(S->getLocStart(), diag::err_omp_loop_not_canonical_incr) 3182 << S->getSourceRange() << Var; 3183 return true; 3184 } 3185 3186 namespace { 3187 // Transform variables declared in GNU statement expressions to new ones to 3188 // avoid crash on codegen. 3189 class TransformToNewDefs : public TreeTransform<TransformToNewDefs> { 3190 typedef TreeTransform<TransformToNewDefs> BaseTransform; 3191 3192 public: 3193 TransformToNewDefs(Sema &SemaRef) : BaseTransform(SemaRef) {} 3194 3195 Decl *TransformDefinition(SourceLocation Loc, Decl *D) { 3196 if (auto *VD = cast<VarDecl>(D)) 3197 if (!isa<ParmVarDecl>(D) && !isa<VarTemplateSpecializationDecl>(D) && 3198 !isa<ImplicitParamDecl>(D)) { 3199 auto *NewVD = VarDecl::Create( 3200 SemaRef.Context, VD->getDeclContext(), VD->getLocStart(), 3201 VD->getLocation(), VD->getIdentifier(), VD->getType(), 3202 VD->getTypeSourceInfo(), VD->getStorageClass()); 3203 NewVD->setTSCSpec(VD->getTSCSpec()); 3204 NewVD->setInit(VD->getInit()); 3205 NewVD->setInitStyle(VD->getInitStyle()); 3206 NewVD->setExceptionVariable(VD->isExceptionVariable()); 3207 NewVD->setNRVOVariable(VD->isNRVOVariable()); 3208 NewVD->setCXXForRangeDecl(VD->isCXXForRangeDecl()); 3209 NewVD->setConstexpr(VD->isConstexpr()); 3210 NewVD->setInitCapture(VD->isInitCapture()); 3211 NewVD->setPreviousDeclInSameBlockScope( 3212 VD->isPreviousDeclInSameBlockScope()); 3213 VD->getDeclContext()->addHiddenDecl(NewVD); 3214 if (VD->hasAttrs()) 3215 NewVD->setAttrs(VD->getAttrs()); 3216 transformedLocalDecl(VD, NewVD); 3217 return NewVD; 3218 } 3219 return BaseTransform::TransformDefinition(Loc, D); 3220 } 3221 3222 ExprResult TransformDeclRefExpr(DeclRefExpr *E) { 3223 if (auto *NewD = TransformDecl(E->getExprLoc(), E->getDecl())) 3224 if (E->getDecl() != NewD) { 3225 NewD->setReferenced(); 3226 NewD->markUsed(SemaRef.Context); 3227 return DeclRefExpr::Create( 3228 SemaRef.Context, E->getQualifierLoc(), E->getTemplateKeywordLoc(), 3229 cast<ValueDecl>(NewD), E->refersToEnclosingVariableOrCapture(), 3230 E->getNameInfo(), E->getType(), E->getValueKind()); 3231 } 3232 return BaseTransform::TransformDeclRefExpr(E); 3233 } 3234 }; 3235 } 3236 3237 /// \brief Build the expression to calculate the number of iterations. 3238 Expr * 3239 OpenMPIterationSpaceChecker::BuildNumIterations(Scope *S, 3240 const bool LimitedType) const { 3241 TransformToNewDefs Transform(SemaRef); 3242 ExprResult Diff; 3243 auto VarType = Var->getType().getNonReferenceType(); 3244 if (VarType->isIntegerType() || VarType->isPointerType() || 3245 SemaRef.getLangOpts().CPlusPlus) { 3246 // Upper - Lower 3247 auto *UBExpr = TestIsLessOp ? UB : LB; 3248 auto *LBExpr = TestIsLessOp ? LB : UB; 3249 Expr *Upper = Transform.TransformExpr(UBExpr).get(); 3250 Expr *Lower = Transform.TransformExpr(LBExpr).get(); 3251 if (!Upper || !Lower) 3252 return nullptr; 3253 if (!SemaRef.Context.hasSameType(Upper->getType(), UBExpr->getType())) { 3254 Upper = SemaRef 3255 .PerformImplicitConversion(Upper, UBExpr->getType(), 3256 Sema::AA_Converting, 3257 /*AllowExplicit=*/true) 3258 .get(); 3259 } 3260 if (!SemaRef.Context.hasSameType(Lower->getType(), LBExpr->getType())) { 3261 Lower = SemaRef 3262 .PerformImplicitConversion(Lower, LBExpr->getType(), 3263 Sema::AA_Converting, 3264 /*AllowExplicit=*/true) 3265 .get(); 3266 } 3267 if (!Upper || !Lower) 3268 return nullptr; 3269 3270 Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Sub, Upper, Lower); 3271 3272 if (!Diff.isUsable() && VarType->getAsCXXRecordDecl()) { 3273 // BuildBinOp already emitted error, this one is to point user to upper 3274 // and lower bound, and to tell what is passed to 'operator-'. 3275 SemaRef.Diag(Upper->getLocStart(), diag::err_omp_loop_diff_cxx) 3276 << Upper->getSourceRange() << Lower->getSourceRange(); 3277 return nullptr; 3278 } 3279 } 3280 3281 if (!Diff.isUsable()) 3282 return nullptr; 3283 3284 // Upper - Lower [- 1] 3285 if (TestIsStrictOp) 3286 Diff = SemaRef.BuildBinOp( 3287 S, DefaultLoc, BO_Sub, Diff.get(), 3288 SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get()); 3289 if (!Diff.isUsable()) 3290 return nullptr; 3291 3292 // Upper - Lower [- 1] + Step 3293 auto *StepNoImp = Step->IgnoreImplicit(); 3294 auto NewStep = Transform.TransformExpr(StepNoImp); 3295 if (NewStep.isInvalid()) 3296 return nullptr; 3297 if (!SemaRef.Context.hasSameType(NewStep.get()->getType(), 3298 StepNoImp->getType())) { 3299 NewStep = SemaRef.PerformImplicitConversion( 3300 NewStep.get(), StepNoImp->getType(), Sema::AA_Converting, 3301 /*AllowExplicit=*/true); 3302 if (NewStep.isInvalid()) 3303 return nullptr; 3304 } 3305 Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Add, Diff.get(), NewStep.get()); 3306 if (!Diff.isUsable()) 3307 return nullptr; 3308 3309 // Parentheses (for dumping/debugging purposes only). 3310 Diff = SemaRef.ActOnParenExpr(DefaultLoc, DefaultLoc, Diff.get()); 3311 if (!Diff.isUsable()) 3312 return nullptr; 3313 3314 // (Upper - Lower [- 1] + Step) / Step 3315 NewStep = Transform.TransformExpr(StepNoImp); 3316 if (NewStep.isInvalid()) 3317 return nullptr; 3318 if (!SemaRef.Context.hasSameType(NewStep.get()->getType(), 3319 StepNoImp->getType())) { 3320 NewStep = SemaRef.PerformImplicitConversion( 3321 NewStep.get(), StepNoImp->getType(), Sema::AA_Converting, 3322 /*AllowExplicit=*/true); 3323 if (NewStep.isInvalid()) 3324 return nullptr; 3325 } 3326 Diff = SemaRef.BuildBinOp(S, DefaultLoc, BO_Div, Diff.get(), NewStep.get()); 3327 if (!Diff.isUsable()) 3328 return nullptr; 3329 3330 // OpenMP runtime requires 32-bit or 64-bit loop variables. 3331 QualType Type = Diff.get()->getType(); 3332 auto &C = SemaRef.Context; 3333 bool UseVarType = VarType->hasIntegerRepresentation() && 3334 C.getTypeSize(Type) > C.getTypeSize(VarType); 3335 if (!Type->isIntegerType() || UseVarType) { 3336 unsigned NewSize = 3337 UseVarType ? C.getTypeSize(VarType) : C.getTypeSize(Type); 3338 bool IsSigned = UseVarType ? VarType->hasSignedIntegerRepresentation() 3339 : Type->hasSignedIntegerRepresentation(); 3340 Type = C.getIntTypeForBitwidth(NewSize, IsSigned); 3341 if (!SemaRef.Context.hasSameType(Diff.get()->getType(), Type)) { 3342 Diff = SemaRef.PerformImplicitConversion( 3343 Diff.get(), Type, Sema::AA_Converting, /*AllowExplicit=*/true); 3344 if (!Diff.isUsable()) 3345 return nullptr; 3346 } 3347 } 3348 if (LimitedType) { 3349 unsigned NewSize = (C.getTypeSize(Type) > 32) ? 64 : 32; 3350 if (NewSize != C.getTypeSize(Type)) { 3351 if (NewSize < C.getTypeSize(Type)) { 3352 assert(NewSize == 64 && "incorrect loop var size"); 3353 SemaRef.Diag(DefaultLoc, diag::warn_omp_loop_64_bit_var) 3354 << InitSrcRange << ConditionSrcRange; 3355 } 3356 QualType NewType = C.getIntTypeForBitwidth( 3357 NewSize, Type->hasSignedIntegerRepresentation() || 3358 C.getTypeSize(Type) < NewSize); 3359 if (!SemaRef.Context.hasSameType(Diff.get()->getType(), NewType)) { 3360 Diff = SemaRef.PerformImplicitConversion(Diff.get(), NewType, 3361 Sema::AA_Converting, true); 3362 if (!Diff.isUsable()) 3363 return nullptr; 3364 } 3365 } 3366 } 3367 3368 return Diff.get(); 3369 } 3370 3371 Expr *OpenMPIterationSpaceChecker::BuildPreCond(Scope *S, Expr *Cond) const { 3372 // Try to build LB <op> UB, where <op> is <, >, <=, or >=. 3373 bool Suppress = SemaRef.getDiagnostics().getSuppressAllDiagnostics(); 3374 SemaRef.getDiagnostics().setSuppressAllDiagnostics(/*Val=*/true); 3375 TransformToNewDefs Transform(SemaRef); 3376 3377 auto NewLB = Transform.TransformExpr(LB); 3378 auto NewUB = Transform.TransformExpr(UB); 3379 if (NewLB.isInvalid() || NewUB.isInvalid()) 3380 return Cond; 3381 if (!SemaRef.Context.hasSameType(NewLB.get()->getType(), LB->getType())) { 3382 NewLB = SemaRef.PerformImplicitConversion(NewLB.get(), LB->getType(), 3383 Sema::AA_Converting, 3384 /*AllowExplicit=*/true); 3385 } 3386 if (!SemaRef.Context.hasSameType(NewUB.get()->getType(), UB->getType())) { 3387 NewUB = SemaRef.PerformImplicitConversion(NewUB.get(), UB->getType(), 3388 Sema::AA_Converting, 3389 /*AllowExplicit=*/true); 3390 } 3391 if (NewLB.isInvalid() || NewUB.isInvalid()) 3392 return Cond; 3393 auto CondExpr = SemaRef.BuildBinOp( 3394 S, DefaultLoc, TestIsLessOp ? (TestIsStrictOp ? BO_LT : BO_LE) 3395 : (TestIsStrictOp ? BO_GT : BO_GE), 3396 NewLB.get(), NewUB.get()); 3397 if (CondExpr.isUsable()) { 3398 if (!SemaRef.Context.hasSameType(CondExpr.get()->getType(), 3399 SemaRef.Context.BoolTy)) 3400 CondExpr = SemaRef.PerformImplicitConversion( 3401 CondExpr.get(), SemaRef.Context.BoolTy, /*Action=*/Sema::AA_Casting, 3402 /*AllowExplicit=*/true); 3403 } 3404 SemaRef.getDiagnostics().setSuppressAllDiagnostics(Suppress); 3405 // Otherwise use original loop conditon and evaluate it in runtime. 3406 return CondExpr.isUsable() ? CondExpr.get() : Cond; 3407 } 3408 3409 /// \brief Build reference expression to the counter be used for codegen. 3410 Expr *OpenMPIterationSpaceChecker::BuildCounterVar() const { 3411 return buildDeclRefExpr(SemaRef, Var, Var->getType().getNonReferenceType(), 3412 DefaultLoc); 3413 } 3414 3415 Expr *OpenMPIterationSpaceChecker::BuildPrivateCounterVar() const { 3416 if (Var && !Var->isInvalidDecl()) { 3417 auto Type = Var->getType().getNonReferenceType(); 3418 auto *PrivateVar = 3419 buildVarDecl(SemaRef, DefaultLoc, Type, Var->getName(), 3420 Var->hasAttrs() ? &Var->getAttrs() : nullptr); 3421 if (PrivateVar->isInvalidDecl()) 3422 return nullptr; 3423 return buildDeclRefExpr(SemaRef, PrivateVar, Type, DefaultLoc); 3424 } 3425 return nullptr; 3426 } 3427 3428 /// \brief Build initization of the counter be used for codegen. 3429 Expr *OpenMPIterationSpaceChecker::BuildCounterInit() const { return LB; } 3430 3431 /// \brief Build step of the counter be used for codegen. 3432 Expr *OpenMPIterationSpaceChecker::BuildCounterStep() const { return Step; } 3433 3434 /// \brief Iteration space of a single for loop. 3435 struct LoopIterationSpace { 3436 /// \brief Condition of the loop. 3437 Expr *PreCond; 3438 /// \brief This expression calculates the number of iterations in the loop. 3439 /// It is always possible to calculate it before starting the loop. 3440 Expr *NumIterations; 3441 /// \brief The loop counter variable. 3442 Expr *CounterVar; 3443 /// \brief Private loop counter variable. 3444 Expr *PrivateCounterVar; 3445 /// \brief This is initializer for the initial value of #CounterVar. 3446 Expr *CounterInit; 3447 /// \brief This is step for the #CounterVar used to generate its update: 3448 /// #CounterVar = #CounterInit + #CounterStep * CurrentIteration. 3449 Expr *CounterStep; 3450 /// \brief Should step be subtracted? 3451 bool Subtract; 3452 /// \brief Source range of the loop init. 3453 SourceRange InitSrcRange; 3454 /// \brief Source range of the loop condition. 3455 SourceRange CondSrcRange; 3456 /// \brief Source range of the loop increment. 3457 SourceRange IncSrcRange; 3458 }; 3459 3460 } // namespace 3461 3462 void Sema::ActOnOpenMPLoopInitialization(SourceLocation ForLoc, Stmt *Init) { 3463 assert(getLangOpts().OpenMP && "OpenMP is not active."); 3464 assert(Init && "Expected loop in canonical form."); 3465 unsigned AssociatedLoops = DSAStack->getAssociatedLoops(); 3466 if (AssociatedLoops > 0 && 3467 isOpenMPLoopDirective(DSAStack->getCurrentDirective())) { 3468 OpenMPIterationSpaceChecker ISC(*this, ForLoc); 3469 if (!ISC.CheckInit(Init, /*EmitDiags=*/false)) 3470 DSAStack->addLoopControlVariable(ISC.GetLoopVar()); 3471 DSAStack->setAssociatedLoops(AssociatedLoops - 1); 3472 } 3473 } 3474 3475 /// \brief Called on a for stmt to check and extract its iteration space 3476 /// for further processing (such as collapsing). 3477 static bool CheckOpenMPIterationSpace( 3478 OpenMPDirectiveKind DKind, Stmt *S, Sema &SemaRef, DSAStackTy &DSA, 3479 unsigned CurrentNestedLoopCount, unsigned NestedLoopCount, 3480 Expr *CollapseLoopCountExpr, Expr *OrderedLoopCountExpr, 3481 llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA, 3482 LoopIterationSpace &ResultIterSpace) { 3483 // OpenMP [2.6, Canonical Loop Form] 3484 // for (init-expr; test-expr; incr-expr) structured-block 3485 auto For = dyn_cast_or_null<ForStmt>(S); 3486 if (!For) { 3487 SemaRef.Diag(S->getLocStart(), diag::err_omp_not_for) 3488 << (CollapseLoopCountExpr != nullptr || OrderedLoopCountExpr != nullptr) 3489 << getOpenMPDirectiveName(DKind) << NestedLoopCount 3490 << (CurrentNestedLoopCount > 0) << CurrentNestedLoopCount; 3491 if (NestedLoopCount > 1) { 3492 if (CollapseLoopCountExpr && OrderedLoopCountExpr) 3493 SemaRef.Diag(DSA.getConstructLoc(), 3494 diag::note_omp_collapse_ordered_expr) 3495 << 2 << CollapseLoopCountExpr->getSourceRange() 3496 << OrderedLoopCountExpr->getSourceRange(); 3497 else if (CollapseLoopCountExpr) 3498 SemaRef.Diag(CollapseLoopCountExpr->getExprLoc(), 3499 diag::note_omp_collapse_ordered_expr) 3500 << 0 << CollapseLoopCountExpr->getSourceRange(); 3501 else 3502 SemaRef.Diag(OrderedLoopCountExpr->getExprLoc(), 3503 diag::note_omp_collapse_ordered_expr) 3504 << 1 << OrderedLoopCountExpr->getSourceRange(); 3505 } 3506 return true; 3507 } 3508 assert(For->getBody()); 3509 3510 OpenMPIterationSpaceChecker ISC(SemaRef, For->getForLoc()); 3511 3512 // Check init. 3513 auto Init = For->getInit(); 3514 if (ISC.CheckInit(Init)) { 3515 return true; 3516 } 3517 3518 bool HasErrors = false; 3519 3520 // Check loop variable's type. 3521 auto Var = ISC.GetLoopVar(); 3522 3523 // OpenMP [2.6, Canonical Loop Form] 3524 // Var is one of the following: 3525 // A variable of signed or unsigned integer type. 3526 // For C++, a variable of a random access iterator type. 3527 // For C, a variable of a pointer type. 3528 auto VarType = Var->getType().getNonReferenceType(); 3529 if (!VarType->isDependentType() && !VarType->isIntegerType() && 3530 !VarType->isPointerType() && 3531 !(SemaRef.getLangOpts().CPlusPlus && VarType->isOverloadableType())) { 3532 SemaRef.Diag(Init->getLocStart(), diag::err_omp_loop_variable_type) 3533 << SemaRef.getLangOpts().CPlusPlus; 3534 HasErrors = true; 3535 } 3536 3537 // OpenMP, 2.14.1.1 Data-sharing Attribute Rules for Variables Referenced in a 3538 // Construct 3539 // The loop iteration variable(s) in the associated for-loop(s) of a for or 3540 // parallel for construct is (are) private. 3541 // The loop iteration variable in the associated for-loop of a simd construct 3542 // with just one associated for-loop is linear with a constant-linear-step 3543 // that is the increment of the associated for-loop. 3544 // Exclude loop var from the list of variables with implicitly defined data 3545 // sharing attributes. 3546 VarsWithImplicitDSA.erase(Var); 3547 3548 // OpenMP [2.14.1.1, Data-sharing Attribute Rules for Variables Referenced in 3549 // a Construct, C/C++]. 3550 // The loop iteration variable in the associated for-loop of a simd construct 3551 // with just one associated for-loop may be listed in a linear clause with a 3552 // constant-linear-step that is the increment of the associated for-loop. 3553 // The loop iteration variable(s) in the associated for-loop(s) of a for or 3554 // parallel for construct may be listed in a private or lastprivate clause. 3555 DSAStackTy::DSAVarData DVar = DSA.getTopDSA(Var, false); 3556 auto LoopVarRefExpr = ISC.GetLoopVarRefExpr(); 3557 // If LoopVarRefExpr is nullptr it means the corresponding loop variable is 3558 // declared in the loop and it is predetermined as a private. 3559 auto PredeterminedCKind = 3560 isOpenMPSimdDirective(DKind) 3561 ? ((NestedLoopCount == 1) ? OMPC_linear : OMPC_lastprivate) 3562 : OMPC_private; 3563 if (((isOpenMPSimdDirective(DKind) && DVar.CKind != OMPC_unknown && 3564 DVar.CKind != PredeterminedCKind) || 3565 ((isOpenMPWorksharingDirective(DKind) || DKind == OMPD_taskloop || 3566 isOpenMPDistributeDirective(DKind)) && 3567 !isOpenMPSimdDirective(DKind) && DVar.CKind != OMPC_unknown && 3568 DVar.CKind != OMPC_private && DVar.CKind != OMPC_lastprivate)) && 3569 (DVar.CKind != OMPC_private || DVar.RefExpr != nullptr)) { 3570 SemaRef.Diag(Init->getLocStart(), diag::err_omp_loop_var_dsa) 3571 << getOpenMPClauseName(DVar.CKind) << getOpenMPDirectiveName(DKind) 3572 << getOpenMPClauseName(PredeterminedCKind); 3573 if (DVar.RefExpr == nullptr) 3574 DVar.CKind = PredeterminedCKind; 3575 ReportOriginalDSA(SemaRef, &DSA, Var, DVar, /*IsLoopIterVar=*/true); 3576 HasErrors = true; 3577 } else if (LoopVarRefExpr != nullptr) { 3578 // Make the loop iteration variable private (for worksharing constructs), 3579 // linear (for simd directives with the only one associated loop) or 3580 // lastprivate (for simd directives with several collapsed or ordered 3581 // loops). 3582 if (DVar.CKind == OMPC_unknown) 3583 DVar = DSA.hasDSA(Var, isOpenMPPrivate, MatchesAlways(), 3584 /*FromParent=*/false); 3585 DSA.addDSA(Var, LoopVarRefExpr, PredeterminedCKind); 3586 } 3587 3588 assert(isOpenMPLoopDirective(DKind) && "DSA for non-loop vars"); 3589 3590 // Check test-expr. 3591 HasErrors |= ISC.CheckCond(For->getCond()); 3592 3593 // Check incr-expr. 3594 HasErrors |= ISC.CheckInc(For->getInc()); 3595 3596 if (ISC.Dependent() || SemaRef.CurContext->isDependentContext() || HasErrors) 3597 return HasErrors; 3598 3599 // Build the loop's iteration space representation. 3600 ResultIterSpace.PreCond = ISC.BuildPreCond(DSA.getCurScope(), For->getCond()); 3601 ResultIterSpace.NumIterations = ISC.BuildNumIterations( 3602 DSA.getCurScope(), (isOpenMPWorksharingDirective(DKind) || 3603 isOpenMPTaskLoopDirective(DKind) || 3604 isOpenMPDistributeDirective(DKind))); 3605 ResultIterSpace.CounterVar = ISC.BuildCounterVar(); 3606 ResultIterSpace.PrivateCounterVar = ISC.BuildPrivateCounterVar(); 3607 ResultIterSpace.CounterInit = ISC.BuildCounterInit(); 3608 ResultIterSpace.CounterStep = ISC.BuildCounterStep(); 3609 ResultIterSpace.InitSrcRange = ISC.GetInitSrcRange(); 3610 ResultIterSpace.CondSrcRange = ISC.GetConditionSrcRange(); 3611 ResultIterSpace.IncSrcRange = ISC.GetIncrementSrcRange(); 3612 ResultIterSpace.Subtract = ISC.ShouldSubtractStep(); 3613 3614 HasErrors |= (ResultIterSpace.PreCond == nullptr || 3615 ResultIterSpace.NumIterations == nullptr || 3616 ResultIterSpace.CounterVar == nullptr || 3617 ResultIterSpace.PrivateCounterVar == nullptr || 3618 ResultIterSpace.CounterInit == nullptr || 3619 ResultIterSpace.CounterStep == nullptr); 3620 3621 return HasErrors; 3622 } 3623 3624 /// \brief Build 'VarRef = Start. 3625 static ExprResult BuildCounterInit(Sema &SemaRef, Scope *S, SourceLocation Loc, 3626 ExprResult VarRef, ExprResult Start) { 3627 TransformToNewDefs Transform(SemaRef); 3628 // Build 'VarRef = Start. 3629 auto *StartNoImp = Start.get()->IgnoreImplicit(); 3630 auto NewStart = Transform.TransformExpr(StartNoImp); 3631 if (NewStart.isInvalid()) 3632 return ExprError(); 3633 if (!SemaRef.Context.hasSameType(NewStart.get()->getType(), 3634 StartNoImp->getType())) { 3635 NewStart = SemaRef.PerformImplicitConversion( 3636 NewStart.get(), StartNoImp->getType(), Sema::AA_Converting, 3637 /*AllowExplicit=*/true); 3638 if (NewStart.isInvalid()) 3639 return ExprError(); 3640 } 3641 if (!SemaRef.Context.hasSameType(NewStart.get()->getType(), 3642 VarRef.get()->getType())) { 3643 NewStart = SemaRef.PerformImplicitConversion( 3644 NewStart.get(), VarRef.get()->getType(), Sema::AA_Converting, 3645 /*AllowExplicit=*/true); 3646 if (!NewStart.isUsable()) 3647 return ExprError(); 3648 } 3649 3650 auto Init = 3651 SemaRef.BuildBinOp(S, Loc, BO_Assign, VarRef.get(), NewStart.get()); 3652 return Init; 3653 } 3654 3655 /// \brief Build 'VarRef = Start + Iter * Step'. 3656 static ExprResult BuildCounterUpdate(Sema &SemaRef, Scope *S, 3657 SourceLocation Loc, ExprResult VarRef, 3658 ExprResult Start, ExprResult Iter, 3659 ExprResult Step, bool Subtract) { 3660 // Add parentheses (for debugging purposes only). 3661 Iter = SemaRef.ActOnParenExpr(Loc, Loc, Iter.get()); 3662 if (!VarRef.isUsable() || !Start.isUsable() || !Iter.isUsable() || 3663 !Step.isUsable()) 3664 return ExprError(); 3665 3666 auto *StepNoImp = Step.get()->IgnoreImplicit(); 3667 TransformToNewDefs Transform(SemaRef); 3668 auto NewStep = Transform.TransformExpr(StepNoImp); 3669 if (NewStep.isInvalid()) 3670 return ExprError(); 3671 if (!SemaRef.Context.hasSameType(NewStep.get()->getType(), 3672 StepNoImp->getType())) { 3673 NewStep = SemaRef.PerformImplicitConversion( 3674 NewStep.get(), StepNoImp->getType(), Sema::AA_Converting, 3675 /*AllowExplicit=*/true); 3676 if (NewStep.isInvalid()) 3677 return ExprError(); 3678 } 3679 ExprResult Update = 3680 SemaRef.BuildBinOp(S, Loc, BO_Mul, Iter.get(), NewStep.get()); 3681 if (!Update.isUsable()) 3682 return ExprError(); 3683 3684 // Build 'VarRef = Start + Iter * Step'. 3685 auto *StartNoImp = Start.get()->IgnoreImplicit(); 3686 auto NewStart = Transform.TransformExpr(StartNoImp); 3687 if (NewStart.isInvalid()) 3688 return ExprError(); 3689 if (!SemaRef.Context.hasSameType(NewStart.get()->getType(), 3690 StartNoImp->getType())) { 3691 NewStart = SemaRef.PerformImplicitConversion( 3692 NewStart.get(), StartNoImp->getType(), Sema::AA_Converting, 3693 /*AllowExplicit=*/true); 3694 if (NewStart.isInvalid()) 3695 return ExprError(); 3696 } 3697 Update = SemaRef.BuildBinOp(S, Loc, (Subtract ? BO_Sub : BO_Add), 3698 NewStart.get(), Update.get()); 3699 if (!Update.isUsable()) 3700 return ExprError(); 3701 3702 Update = SemaRef.PerformImplicitConversion( 3703 Update.get(), VarRef.get()->getType(), Sema::AA_Converting, true); 3704 if (!Update.isUsable()) 3705 return ExprError(); 3706 3707 Update = SemaRef.BuildBinOp(S, Loc, BO_Assign, VarRef.get(), Update.get()); 3708 return Update; 3709 } 3710 3711 /// \brief Convert integer expression \a E to make it have at least \a Bits 3712 /// bits. 3713 static ExprResult WidenIterationCount(unsigned Bits, Expr *E, 3714 Sema &SemaRef) { 3715 if (E == nullptr) 3716 return ExprError(); 3717 auto &C = SemaRef.Context; 3718 QualType OldType = E->getType(); 3719 unsigned HasBits = C.getTypeSize(OldType); 3720 if (HasBits >= Bits) 3721 return ExprResult(E); 3722 // OK to convert to signed, because new type has more bits than old. 3723 QualType NewType = C.getIntTypeForBitwidth(Bits, /* Signed */ true); 3724 return SemaRef.PerformImplicitConversion(E, NewType, Sema::AA_Converting, 3725 true); 3726 } 3727 3728 /// \brief Check if the given expression \a E is a constant integer that fits 3729 /// into \a Bits bits. 3730 static bool FitsInto(unsigned Bits, bool Signed, Expr *E, Sema &SemaRef) { 3731 if (E == nullptr) 3732 return false; 3733 llvm::APSInt Result; 3734 if (E->isIntegerConstantExpr(Result, SemaRef.Context)) 3735 return Signed ? Result.isSignedIntN(Bits) : Result.isIntN(Bits); 3736 return false; 3737 } 3738 3739 /// \brief Called on a for stmt to check itself and nested loops (if any). 3740 /// \return Returns 0 if one of the collapsed stmts is not canonical for loop, 3741 /// number of collapsed loops otherwise. 3742 static unsigned 3743 CheckOpenMPLoop(OpenMPDirectiveKind DKind, Expr *CollapseLoopCountExpr, 3744 Expr *OrderedLoopCountExpr, Stmt *AStmt, Sema &SemaRef, 3745 DSAStackTy &DSA, 3746 llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA, 3747 OMPLoopDirective::HelperExprs &Built) { 3748 unsigned NestedLoopCount = 1; 3749 if (CollapseLoopCountExpr) { 3750 // Found 'collapse' clause - calculate collapse number. 3751 llvm::APSInt Result; 3752 if (CollapseLoopCountExpr->EvaluateAsInt(Result, SemaRef.getASTContext())) 3753 NestedLoopCount = Result.getLimitedValue(); 3754 } 3755 if (OrderedLoopCountExpr) { 3756 // Found 'ordered' clause - calculate collapse number. 3757 llvm::APSInt Result; 3758 if (OrderedLoopCountExpr->EvaluateAsInt(Result, SemaRef.getASTContext())) { 3759 if (Result.getLimitedValue() < NestedLoopCount) { 3760 SemaRef.Diag(OrderedLoopCountExpr->getExprLoc(), 3761 diag::err_omp_wrong_ordered_loop_count) 3762 << OrderedLoopCountExpr->getSourceRange(); 3763 SemaRef.Diag(CollapseLoopCountExpr->getExprLoc(), 3764 diag::note_collapse_loop_count) 3765 << CollapseLoopCountExpr->getSourceRange(); 3766 } 3767 NestedLoopCount = Result.getLimitedValue(); 3768 } 3769 } 3770 // This is helper routine for loop directives (e.g., 'for', 'simd', 3771 // 'for simd', etc.). 3772 SmallVector<LoopIterationSpace, 4> IterSpaces; 3773 IterSpaces.resize(NestedLoopCount); 3774 Stmt *CurStmt = AStmt->IgnoreContainers(/* IgnoreCaptured */ true); 3775 for (unsigned Cnt = 0; Cnt < NestedLoopCount; ++Cnt) { 3776 if (CheckOpenMPIterationSpace(DKind, CurStmt, SemaRef, DSA, Cnt, 3777 NestedLoopCount, CollapseLoopCountExpr, 3778 OrderedLoopCountExpr, VarsWithImplicitDSA, 3779 IterSpaces[Cnt])) 3780 return 0; 3781 // Move on to the next nested for loop, or to the loop body. 3782 // OpenMP [2.8.1, simd construct, Restrictions] 3783 // All loops associated with the construct must be perfectly nested; that 3784 // is, there must be no intervening code nor any OpenMP directive between 3785 // any two loops. 3786 CurStmt = cast<ForStmt>(CurStmt)->getBody()->IgnoreContainers(); 3787 } 3788 3789 Built.clear(/* size */ NestedLoopCount); 3790 3791 if (SemaRef.CurContext->isDependentContext()) 3792 return NestedLoopCount; 3793 3794 // An example of what is generated for the following code: 3795 // 3796 // #pragma omp simd collapse(2) ordered(2) 3797 // for (i = 0; i < NI; ++i) 3798 // for (k = 0; k < NK; ++k) 3799 // for (j = J0; j < NJ; j+=2) { 3800 // <loop body> 3801 // } 3802 // 3803 // We generate the code below. 3804 // Note: the loop body may be outlined in CodeGen. 3805 // Note: some counters may be C++ classes, operator- is used to find number of 3806 // iterations and operator+= to calculate counter value. 3807 // Note: decltype(NumIterations) must be integer type (in 'omp for', only i32 3808 // or i64 is currently supported). 3809 // 3810 // #define NumIterations (NI * ((NJ - J0 - 1 + 2) / 2)) 3811 // for (int[32|64]_t IV = 0; IV < NumIterations; ++IV ) { 3812 // .local.i = IV / ((NJ - J0 - 1 + 2) / 2); 3813 // .local.j = J0 + (IV % ((NJ - J0 - 1 + 2) / 2)) * 2; 3814 // // similar updates for vars in clauses (e.g. 'linear') 3815 // <loop body (using local i and j)> 3816 // } 3817 // i = NI; // assign final values of counters 3818 // j = NJ; 3819 // 3820 3821 // Last iteration number is (I1 * I2 * ... In) - 1, where I1, I2 ... In are 3822 // the iteration counts of the collapsed for loops. 3823 // Precondition tests if there is at least one iteration (all conditions are 3824 // true). 3825 auto PreCond = ExprResult(IterSpaces[0].PreCond); 3826 auto N0 = IterSpaces[0].NumIterations; 3827 ExprResult LastIteration32 = WidenIterationCount( 3828 32 /* Bits */, SemaRef.PerformImplicitConversion( 3829 N0->IgnoreImpCasts(), N0->getType(), 3830 Sema::AA_Converting, /*AllowExplicit=*/true) 3831 .get(), 3832 SemaRef); 3833 ExprResult LastIteration64 = WidenIterationCount( 3834 64 /* Bits */, SemaRef.PerformImplicitConversion( 3835 N0->IgnoreImpCasts(), N0->getType(), 3836 Sema::AA_Converting, /*AllowExplicit=*/true) 3837 .get(), 3838 SemaRef); 3839 3840 if (!LastIteration32.isUsable() || !LastIteration64.isUsable()) 3841 return NestedLoopCount; 3842 3843 auto &C = SemaRef.Context; 3844 bool AllCountsNeedLessThan32Bits = C.getTypeSize(N0->getType()) < 32; 3845 3846 Scope *CurScope = DSA.getCurScope(); 3847 for (unsigned Cnt = 1; Cnt < NestedLoopCount; ++Cnt) { 3848 if (PreCond.isUsable()) { 3849 PreCond = SemaRef.BuildBinOp(CurScope, SourceLocation(), BO_LAnd, 3850 PreCond.get(), IterSpaces[Cnt].PreCond); 3851 } 3852 auto N = IterSpaces[Cnt].NumIterations; 3853 AllCountsNeedLessThan32Bits &= C.getTypeSize(N->getType()) < 32; 3854 if (LastIteration32.isUsable()) 3855 LastIteration32 = SemaRef.BuildBinOp( 3856 CurScope, SourceLocation(), BO_Mul, LastIteration32.get(), 3857 SemaRef.PerformImplicitConversion(N->IgnoreImpCasts(), N->getType(), 3858 Sema::AA_Converting, 3859 /*AllowExplicit=*/true) 3860 .get()); 3861 if (LastIteration64.isUsable()) 3862 LastIteration64 = SemaRef.BuildBinOp( 3863 CurScope, SourceLocation(), BO_Mul, LastIteration64.get(), 3864 SemaRef.PerformImplicitConversion(N->IgnoreImpCasts(), N->getType(), 3865 Sema::AA_Converting, 3866 /*AllowExplicit=*/true) 3867 .get()); 3868 } 3869 3870 // Choose either the 32-bit or 64-bit version. 3871 ExprResult LastIteration = LastIteration64; 3872 if (LastIteration32.isUsable() && 3873 C.getTypeSize(LastIteration32.get()->getType()) == 32 && 3874 (AllCountsNeedLessThan32Bits || NestedLoopCount == 1 || 3875 FitsInto( 3876 32 /* Bits */, 3877 LastIteration32.get()->getType()->hasSignedIntegerRepresentation(), 3878 LastIteration64.get(), SemaRef))) 3879 LastIteration = LastIteration32; 3880 3881 if (!LastIteration.isUsable()) 3882 return 0; 3883 3884 // Save the number of iterations. 3885 ExprResult NumIterations = LastIteration; 3886 { 3887 LastIteration = SemaRef.BuildBinOp( 3888 CurScope, SourceLocation(), BO_Sub, LastIteration.get(), 3889 SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get()); 3890 if (!LastIteration.isUsable()) 3891 return 0; 3892 } 3893 3894 // Calculate the last iteration number beforehand instead of doing this on 3895 // each iteration. Do not do this if the number of iterations may be kfold-ed. 3896 llvm::APSInt Result; 3897 bool IsConstant = 3898 LastIteration.get()->isIntegerConstantExpr(Result, SemaRef.Context); 3899 ExprResult CalcLastIteration; 3900 if (!IsConstant) { 3901 SourceLocation SaveLoc; 3902 VarDecl *SaveVar = 3903 buildVarDecl(SemaRef, SaveLoc, LastIteration.get()->getType(), 3904 ".omp.last.iteration"); 3905 ExprResult SaveRef = buildDeclRefExpr( 3906 SemaRef, SaveVar, LastIteration.get()->getType(), SaveLoc); 3907 CalcLastIteration = SemaRef.BuildBinOp(CurScope, SaveLoc, BO_Assign, 3908 SaveRef.get(), LastIteration.get()); 3909 LastIteration = SaveRef; 3910 3911 // Prepare SaveRef + 1. 3912 NumIterations = SemaRef.BuildBinOp( 3913 CurScope, SaveLoc, BO_Add, SaveRef.get(), 3914 SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get()); 3915 if (!NumIterations.isUsable()) 3916 return 0; 3917 } 3918 3919 SourceLocation InitLoc = IterSpaces[0].InitSrcRange.getBegin(); 3920 3921 QualType VType = LastIteration.get()->getType(); 3922 // Build variables passed into runtime, nesessary for worksharing directives. 3923 ExprResult LB, UB, IL, ST, EUB; 3924 if (isOpenMPWorksharingDirective(DKind) || isOpenMPTaskLoopDirective(DKind) || 3925 isOpenMPDistributeDirective(DKind)) { 3926 // Lower bound variable, initialized with zero. 3927 VarDecl *LBDecl = buildVarDecl(SemaRef, InitLoc, VType, ".omp.lb"); 3928 LB = buildDeclRefExpr(SemaRef, LBDecl, VType, InitLoc); 3929 SemaRef.AddInitializerToDecl( 3930 LBDecl, SemaRef.ActOnIntegerConstant(InitLoc, 0).get(), 3931 /*DirectInit*/ false, /*TypeMayContainAuto*/ false); 3932 3933 // Upper bound variable, initialized with last iteration number. 3934 VarDecl *UBDecl = buildVarDecl(SemaRef, InitLoc, VType, ".omp.ub"); 3935 UB = buildDeclRefExpr(SemaRef, UBDecl, VType, InitLoc); 3936 SemaRef.AddInitializerToDecl(UBDecl, LastIteration.get(), 3937 /*DirectInit*/ false, 3938 /*TypeMayContainAuto*/ false); 3939 3940 // A 32-bit variable-flag where runtime returns 1 for the last iteration. 3941 // This will be used to implement clause 'lastprivate'. 3942 QualType Int32Ty = SemaRef.Context.getIntTypeForBitwidth(32, true); 3943 VarDecl *ILDecl = buildVarDecl(SemaRef, InitLoc, Int32Ty, ".omp.is_last"); 3944 IL = buildDeclRefExpr(SemaRef, ILDecl, Int32Ty, InitLoc); 3945 SemaRef.AddInitializerToDecl( 3946 ILDecl, SemaRef.ActOnIntegerConstant(InitLoc, 0).get(), 3947 /*DirectInit*/ false, /*TypeMayContainAuto*/ false); 3948 3949 // Stride variable returned by runtime (we initialize it to 1 by default). 3950 VarDecl *STDecl = buildVarDecl(SemaRef, InitLoc, VType, ".omp.stride"); 3951 ST = buildDeclRefExpr(SemaRef, STDecl, VType, InitLoc); 3952 SemaRef.AddInitializerToDecl( 3953 STDecl, SemaRef.ActOnIntegerConstant(InitLoc, 1).get(), 3954 /*DirectInit*/ false, /*TypeMayContainAuto*/ false); 3955 3956 // Build expression: UB = min(UB, LastIteration) 3957 // It is nesessary for CodeGen of directives with static scheduling. 3958 ExprResult IsUBGreater = SemaRef.BuildBinOp(CurScope, InitLoc, BO_GT, 3959 UB.get(), LastIteration.get()); 3960 ExprResult CondOp = SemaRef.ActOnConditionalOp( 3961 InitLoc, InitLoc, IsUBGreater.get(), LastIteration.get(), UB.get()); 3962 EUB = SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, UB.get(), 3963 CondOp.get()); 3964 EUB = SemaRef.ActOnFinishFullExpr(EUB.get()); 3965 } 3966 3967 // Build the iteration variable and its initialization before loop. 3968 ExprResult IV; 3969 ExprResult Init; 3970 { 3971 VarDecl *IVDecl = buildVarDecl(SemaRef, InitLoc, VType, ".omp.iv"); 3972 IV = buildDeclRefExpr(SemaRef, IVDecl, VType, InitLoc); 3973 Expr *RHS = (isOpenMPWorksharingDirective(DKind) || 3974 isOpenMPTaskLoopDirective(DKind) || 3975 isOpenMPDistributeDirective(DKind)) 3976 ? LB.get() 3977 : SemaRef.ActOnIntegerConstant(SourceLocation(), 0).get(); 3978 Init = SemaRef.BuildBinOp(CurScope, InitLoc, BO_Assign, IV.get(), RHS); 3979 Init = SemaRef.ActOnFinishFullExpr(Init.get()); 3980 } 3981 3982 // Loop condition (IV < NumIterations) or (IV <= UB) for worksharing loops. 3983 SourceLocation CondLoc; 3984 ExprResult Cond = 3985 (isOpenMPWorksharingDirective(DKind) || 3986 isOpenMPTaskLoopDirective(DKind) || isOpenMPDistributeDirective(DKind)) 3987 ? SemaRef.BuildBinOp(CurScope, CondLoc, BO_LE, IV.get(), UB.get()) 3988 : SemaRef.BuildBinOp(CurScope, CondLoc, BO_LT, IV.get(), 3989 NumIterations.get()); 3990 3991 // Loop increment (IV = IV + 1) 3992 SourceLocation IncLoc; 3993 ExprResult Inc = 3994 SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, IV.get(), 3995 SemaRef.ActOnIntegerConstant(IncLoc, 1).get()); 3996 if (!Inc.isUsable()) 3997 return 0; 3998 Inc = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, IV.get(), Inc.get()); 3999 Inc = SemaRef.ActOnFinishFullExpr(Inc.get()); 4000 if (!Inc.isUsable()) 4001 return 0; 4002 4003 // Increments for worksharing loops (LB = LB + ST; UB = UB + ST). 4004 // Used for directives with static scheduling. 4005 ExprResult NextLB, NextUB; 4006 if (isOpenMPWorksharingDirective(DKind) || isOpenMPTaskLoopDirective(DKind) || 4007 isOpenMPDistributeDirective(DKind)) { 4008 // LB + ST 4009 NextLB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, LB.get(), ST.get()); 4010 if (!NextLB.isUsable()) 4011 return 0; 4012 // LB = LB + ST 4013 NextLB = 4014 SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, LB.get(), NextLB.get()); 4015 NextLB = SemaRef.ActOnFinishFullExpr(NextLB.get()); 4016 if (!NextLB.isUsable()) 4017 return 0; 4018 // UB + ST 4019 NextUB = SemaRef.BuildBinOp(CurScope, IncLoc, BO_Add, UB.get(), ST.get()); 4020 if (!NextUB.isUsable()) 4021 return 0; 4022 // UB = UB + ST 4023 NextUB = 4024 SemaRef.BuildBinOp(CurScope, IncLoc, BO_Assign, UB.get(), NextUB.get()); 4025 NextUB = SemaRef.ActOnFinishFullExpr(NextUB.get()); 4026 if (!NextUB.isUsable()) 4027 return 0; 4028 } 4029 4030 // Build updates and final values of the loop counters. 4031 bool HasErrors = false; 4032 Built.Counters.resize(NestedLoopCount); 4033 Built.Inits.resize(NestedLoopCount); 4034 Built.Updates.resize(NestedLoopCount); 4035 Built.Finals.resize(NestedLoopCount); 4036 { 4037 ExprResult Div; 4038 // Go from inner nested loop to outer. 4039 for (int Cnt = NestedLoopCount - 1; Cnt >= 0; --Cnt) { 4040 LoopIterationSpace &IS = IterSpaces[Cnt]; 4041 SourceLocation UpdLoc = IS.IncSrcRange.getBegin(); 4042 // Build: Iter = (IV / Div) % IS.NumIters 4043 // where Div is product of previous iterations' IS.NumIters. 4044 ExprResult Iter; 4045 if (Div.isUsable()) { 4046 Iter = 4047 SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Div, IV.get(), Div.get()); 4048 } else { 4049 Iter = IV; 4050 assert((Cnt == (int)NestedLoopCount - 1) && 4051 "unusable div expected on first iteration only"); 4052 } 4053 4054 if (Cnt != 0 && Iter.isUsable()) 4055 Iter = SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Rem, Iter.get(), 4056 IS.NumIterations); 4057 if (!Iter.isUsable()) { 4058 HasErrors = true; 4059 break; 4060 } 4061 4062 // Build update: IS.CounterVar(Private) = IS.Start + Iter * IS.Step 4063 auto *CounterVar = buildDeclRefExpr( 4064 SemaRef, cast<VarDecl>(cast<DeclRefExpr>(IS.CounterVar)->getDecl()), 4065 IS.CounterVar->getType(), IS.CounterVar->getExprLoc(), 4066 /*RefersToCapture=*/true); 4067 ExprResult Init = BuildCounterInit(SemaRef, CurScope, UpdLoc, CounterVar, 4068 IS.CounterInit); 4069 if (!Init.isUsable()) { 4070 HasErrors = true; 4071 break; 4072 } 4073 ExprResult Update = 4074 BuildCounterUpdate(SemaRef, CurScope, UpdLoc, CounterVar, 4075 IS.CounterInit, Iter, IS.CounterStep, IS.Subtract); 4076 if (!Update.isUsable()) { 4077 HasErrors = true; 4078 break; 4079 } 4080 4081 // Build final: IS.CounterVar = IS.Start + IS.NumIters * IS.Step 4082 ExprResult Final = BuildCounterUpdate( 4083 SemaRef, CurScope, UpdLoc, CounterVar, IS.CounterInit, 4084 IS.NumIterations, IS.CounterStep, IS.Subtract); 4085 if (!Final.isUsable()) { 4086 HasErrors = true; 4087 break; 4088 } 4089 4090 // Build Div for the next iteration: Div <- Div * IS.NumIters 4091 if (Cnt != 0) { 4092 if (Div.isUnset()) 4093 Div = IS.NumIterations; 4094 else 4095 Div = SemaRef.BuildBinOp(CurScope, UpdLoc, BO_Mul, Div.get(), 4096 IS.NumIterations); 4097 4098 // Add parentheses (for debugging purposes only). 4099 if (Div.isUsable()) 4100 Div = SemaRef.ActOnParenExpr(UpdLoc, UpdLoc, Div.get()); 4101 if (!Div.isUsable()) { 4102 HasErrors = true; 4103 break; 4104 } 4105 } 4106 if (!Update.isUsable() || !Final.isUsable()) { 4107 HasErrors = true; 4108 break; 4109 } 4110 // Save results 4111 Built.Counters[Cnt] = IS.CounterVar; 4112 Built.PrivateCounters[Cnt] = IS.PrivateCounterVar; 4113 Built.Inits[Cnt] = Init.get(); 4114 Built.Updates[Cnt] = Update.get(); 4115 Built.Finals[Cnt] = Final.get(); 4116 } 4117 } 4118 4119 if (HasErrors) 4120 return 0; 4121 4122 // Save results 4123 Built.IterationVarRef = IV.get(); 4124 Built.LastIteration = LastIteration.get(); 4125 Built.NumIterations = NumIterations.get(); 4126 Built.CalcLastIteration = 4127 SemaRef.ActOnFinishFullExpr(CalcLastIteration.get()).get(); 4128 Built.PreCond = PreCond.get(); 4129 Built.Cond = Cond.get(); 4130 Built.Init = Init.get(); 4131 Built.Inc = Inc.get(); 4132 Built.LB = LB.get(); 4133 Built.UB = UB.get(); 4134 Built.IL = IL.get(); 4135 Built.ST = ST.get(); 4136 Built.EUB = EUB.get(); 4137 Built.NLB = NextLB.get(); 4138 Built.NUB = NextUB.get(); 4139 4140 return NestedLoopCount; 4141 } 4142 4143 static Expr *getCollapseNumberExpr(ArrayRef<OMPClause *> Clauses) { 4144 auto CollapseClauses = 4145 OMPExecutableDirective::getClausesOfKind<OMPCollapseClause>(Clauses); 4146 if (CollapseClauses.begin() != CollapseClauses.end()) 4147 return (*CollapseClauses.begin())->getNumForLoops(); 4148 return nullptr; 4149 } 4150 4151 static Expr *getOrderedNumberExpr(ArrayRef<OMPClause *> Clauses) { 4152 auto OrderedClauses = 4153 OMPExecutableDirective::getClausesOfKind<OMPOrderedClause>(Clauses); 4154 if (OrderedClauses.begin() != OrderedClauses.end()) 4155 return (*OrderedClauses.begin())->getNumForLoops(); 4156 return nullptr; 4157 } 4158 4159 static bool checkSimdlenSafelenValues(Sema &S, const Expr *Simdlen, 4160 const Expr *Safelen) { 4161 llvm::APSInt SimdlenRes, SafelenRes; 4162 if (Simdlen->isValueDependent() || Simdlen->isTypeDependent() || 4163 Simdlen->isInstantiationDependent() || 4164 Simdlen->containsUnexpandedParameterPack()) 4165 return false; 4166 if (Safelen->isValueDependent() || Safelen->isTypeDependent() || 4167 Safelen->isInstantiationDependent() || 4168 Safelen->containsUnexpandedParameterPack()) 4169 return false; 4170 Simdlen->EvaluateAsInt(SimdlenRes, S.Context); 4171 Safelen->EvaluateAsInt(SafelenRes, S.Context); 4172 // OpenMP 4.1 [2.8.1, simd Construct, Restrictions] 4173 // If both simdlen and safelen clauses are specified, the value of the simdlen 4174 // parameter must be less than or equal to the value of the safelen parameter. 4175 if (SimdlenRes > SafelenRes) { 4176 S.Diag(Simdlen->getExprLoc(), diag::err_omp_wrong_simdlen_safelen_values) 4177 << Simdlen->getSourceRange() << Safelen->getSourceRange(); 4178 return true; 4179 } 4180 return false; 4181 } 4182 4183 StmtResult Sema::ActOnOpenMPSimdDirective( 4184 ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc, 4185 SourceLocation EndLoc, 4186 llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA) { 4187 if (!AStmt) 4188 return StmtError(); 4189 4190 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 4191 OMPLoopDirective::HelperExprs B; 4192 // In presence of clause 'collapse' or 'ordered' with number of loops, it will 4193 // define the nested loops number. 4194 unsigned NestedLoopCount = CheckOpenMPLoop( 4195 OMPD_simd, getCollapseNumberExpr(Clauses), getOrderedNumberExpr(Clauses), 4196 AStmt, *this, *DSAStack, VarsWithImplicitDSA, B); 4197 if (NestedLoopCount == 0) 4198 return StmtError(); 4199 4200 assert((CurContext->isDependentContext() || B.builtAll()) && 4201 "omp simd loop exprs were not built"); 4202 4203 if (!CurContext->isDependentContext()) { 4204 // Finalize the clauses that need pre-built expressions for CodeGen. 4205 for (auto C : Clauses) { 4206 if (auto LC = dyn_cast<OMPLinearClause>(C)) 4207 if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef), 4208 B.NumIterations, *this, CurScope)) 4209 return StmtError(); 4210 } 4211 } 4212 4213 // OpenMP 4.1 [2.8.1, simd Construct, Restrictions] 4214 // If both simdlen and safelen clauses are specified, the value of the simdlen 4215 // parameter must be less than or equal to the value of the safelen parameter. 4216 OMPSafelenClause *Safelen = nullptr; 4217 OMPSimdlenClause *Simdlen = nullptr; 4218 for (auto *Clause : Clauses) { 4219 if (Clause->getClauseKind() == OMPC_safelen) 4220 Safelen = cast<OMPSafelenClause>(Clause); 4221 else if (Clause->getClauseKind() == OMPC_simdlen) 4222 Simdlen = cast<OMPSimdlenClause>(Clause); 4223 if (Safelen && Simdlen) 4224 break; 4225 } 4226 if (Simdlen && Safelen && 4227 checkSimdlenSafelenValues(*this, Simdlen->getSimdlen(), 4228 Safelen->getSafelen())) 4229 return StmtError(); 4230 4231 getCurFunction()->setHasBranchProtectedScope(); 4232 return OMPSimdDirective::Create(Context, StartLoc, EndLoc, NestedLoopCount, 4233 Clauses, AStmt, B); 4234 } 4235 4236 StmtResult Sema::ActOnOpenMPForDirective( 4237 ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc, 4238 SourceLocation EndLoc, 4239 llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA) { 4240 if (!AStmt) 4241 return StmtError(); 4242 4243 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 4244 OMPLoopDirective::HelperExprs B; 4245 // In presence of clause 'collapse' or 'ordered' with number of loops, it will 4246 // define the nested loops number. 4247 unsigned NestedLoopCount = CheckOpenMPLoop( 4248 OMPD_for, getCollapseNumberExpr(Clauses), getOrderedNumberExpr(Clauses), 4249 AStmt, *this, *DSAStack, VarsWithImplicitDSA, B); 4250 if (NestedLoopCount == 0) 4251 return StmtError(); 4252 4253 assert((CurContext->isDependentContext() || B.builtAll()) && 4254 "omp for loop exprs were not built"); 4255 4256 if (!CurContext->isDependentContext()) { 4257 // Finalize the clauses that need pre-built expressions for CodeGen. 4258 for (auto C : Clauses) { 4259 if (auto LC = dyn_cast<OMPLinearClause>(C)) 4260 if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef), 4261 B.NumIterations, *this, CurScope)) 4262 return StmtError(); 4263 } 4264 } 4265 4266 getCurFunction()->setHasBranchProtectedScope(); 4267 return OMPForDirective::Create(Context, StartLoc, EndLoc, NestedLoopCount, 4268 Clauses, AStmt, B, DSAStack->isCancelRegion()); 4269 } 4270 4271 StmtResult Sema::ActOnOpenMPForSimdDirective( 4272 ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc, 4273 SourceLocation EndLoc, 4274 llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA) { 4275 if (!AStmt) 4276 return StmtError(); 4277 4278 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 4279 OMPLoopDirective::HelperExprs B; 4280 // In presence of clause 'collapse' or 'ordered' with number of loops, it will 4281 // define the nested loops number. 4282 unsigned NestedLoopCount = 4283 CheckOpenMPLoop(OMPD_for_simd, getCollapseNumberExpr(Clauses), 4284 getOrderedNumberExpr(Clauses), AStmt, *this, *DSAStack, 4285 VarsWithImplicitDSA, B); 4286 if (NestedLoopCount == 0) 4287 return StmtError(); 4288 4289 assert((CurContext->isDependentContext() || B.builtAll()) && 4290 "omp for simd loop exprs were not built"); 4291 4292 if (!CurContext->isDependentContext()) { 4293 // Finalize the clauses that need pre-built expressions for CodeGen. 4294 for (auto C : Clauses) { 4295 if (auto LC = dyn_cast<OMPLinearClause>(C)) 4296 if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef), 4297 B.NumIterations, *this, CurScope)) 4298 return StmtError(); 4299 } 4300 } 4301 4302 // OpenMP 4.1 [2.8.1, simd Construct, Restrictions] 4303 // If both simdlen and safelen clauses are specified, the value of the simdlen 4304 // parameter must be less than or equal to the value of the safelen parameter. 4305 OMPSafelenClause *Safelen = nullptr; 4306 OMPSimdlenClause *Simdlen = nullptr; 4307 for (auto *Clause : Clauses) { 4308 if (Clause->getClauseKind() == OMPC_safelen) 4309 Safelen = cast<OMPSafelenClause>(Clause); 4310 else if (Clause->getClauseKind() == OMPC_simdlen) 4311 Simdlen = cast<OMPSimdlenClause>(Clause); 4312 if (Safelen && Simdlen) 4313 break; 4314 } 4315 if (Simdlen && Safelen && 4316 checkSimdlenSafelenValues(*this, Simdlen->getSimdlen(), 4317 Safelen->getSafelen())) 4318 return StmtError(); 4319 4320 getCurFunction()->setHasBranchProtectedScope(); 4321 return OMPForSimdDirective::Create(Context, StartLoc, EndLoc, NestedLoopCount, 4322 Clauses, AStmt, B); 4323 } 4324 4325 StmtResult Sema::ActOnOpenMPSectionsDirective(ArrayRef<OMPClause *> Clauses, 4326 Stmt *AStmt, 4327 SourceLocation StartLoc, 4328 SourceLocation EndLoc) { 4329 if (!AStmt) 4330 return StmtError(); 4331 4332 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 4333 auto BaseStmt = AStmt; 4334 while (CapturedStmt *CS = dyn_cast_or_null<CapturedStmt>(BaseStmt)) 4335 BaseStmt = CS->getCapturedStmt(); 4336 if (auto C = dyn_cast_or_null<CompoundStmt>(BaseStmt)) { 4337 auto S = C->children(); 4338 if (S.begin() == S.end()) 4339 return StmtError(); 4340 // All associated statements must be '#pragma omp section' except for 4341 // the first one. 4342 for (Stmt *SectionStmt : llvm::make_range(std::next(S.begin()), S.end())) { 4343 if (!SectionStmt || !isa<OMPSectionDirective>(SectionStmt)) { 4344 if (SectionStmt) 4345 Diag(SectionStmt->getLocStart(), 4346 diag::err_omp_sections_substmt_not_section); 4347 return StmtError(); 4348 } 4349 cast<OMPSectionDirective>(SectionStmt) 4350 ->setHasCancel(DSAStack->isCancelRegion()); 4351 } 4352 } else { 4353 Diag(AStmt->getLocStart(), diag::err_omp_sections_not_compound_stmt); 4354 return StmtError(); 4355 } 4356 4357 getCurFunction()->setHasBranchProtectedScope(); 4358 4359 return OMPSectionsDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt, 4360 DSAStack->isCancelRegion()); 4361 } 4362 4363 StmtResult Sema::ActOnOpenMPSectionDirective(Stmt *AStmt, 4364 SourceLocation StartLoc, 4365 SourceLocation EndLoc) { 4366 if (!AStmt) 4367 return StmtError(); 4368 4369 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 4370 4371 getCurFunction()->setHasBranchProtectedScope(); 4372 DSAStack->setParentCancelRegion(DSAStack->isCancelRegion()); 4373 4374 return OMPSectionDirective::Create(Context, StartLoc, EndLoc, AStmt, 4375 DSAStack->isCancelRegion()); 4376 } 4377 4378 StmtResult Sema::ActOnOpenMPSingleDirective(ArrayRef<OMPClause *> Clauses, 4379 Stmt *AStmt, 4380 SourceLocation StartLoc, 4381 SourceLocation EndLoc) { 4382 if (!AStmt) 4383 return StmtError(); 4384 4385 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 4386 4387 getCurFunction()->setHasBranchProtectedScope(); 4388 4389 // OpenMP [2.7.3, single Construct, Restrictions] 4390 // The copyprivate clause must not be used with the nowait clause. 4391 OMPClause *Nowait = nullptr; 4392 OMPClause *Copyprivate = nullptr; 4393 for (auto *Clause : Clauses) { 4394 if (Clause->getClauseKind() == OMPC_nowait) 4395 Nowait = Clause; 4396 else if (Clause->getClauseKind() == OMPC_copyprivate) 4397 Copyprivate = Clause; 4398 if (Copyprivate && Nowait) { 4399 Diag(Copyprivate->getLocStart(), 4400 diag::err_omp_single_copyprivate_with_nowait); 4401 Diag(Nowait->getLocStart(), diag::note_omp_nowait_clause_here); 4402 return StmtError(); 4403 } 4404 } 4405 4406 return OMPSingleDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt); 4407 } 4408 4409 StmtResult Sema::ActOnOpenMPMasterDirective(Stmt *AStmt, 4410 SourceLocation StartLoc, 4411 SourceLocation EndLoc) { 4412 if (!AStmt) 4413 return StmtError(); 4414 4415 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 4416 4417 getCurFunction()->setHasBranchProtectedScope(); 4418 4419 return OMPMasterDirective::Create(Context, StartLoc, EndLoc, AStmt); 4420 } 4421 4422 StmtResult Sema::ActOnOpenMPCriticalDirective( 4423 const DeclarationNameInfo &DirName, ArrayRef<OMPClause *> Clauses, 4424 Stmt *AStmt, SourceLocation StartLoc, SourceLocation EndLoc) { 4425 if (!AStmt) 4426 return StmtError(); 4427 4428 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 4429 4430 bool ErrorFound = false; 4431 llvm::APSInt Hint; 4432 SourceLocation HintLoc; 4433 bool DependentHint = false; 4434 for (auto *C : Clauses) { 4435 if (C->getClauseKind() == OMPC_hint) { 4436 if (!DirName.getName()) { 4437 Diag(C->getLocStart(), diag::err_omp_hint_clause_no_name); 4438 ErrorFound = true; 4439 } 4440 Expr *E = cast<OMPHintClause>(C)->getHint(); 4441 if (E->isTypeDependent() || E->isValueDependent() || 4442 E->isInstantiationDependent()) 4443 DependentHint = true; 4444 else { 4445 Hint = E->EvaluateKnownConstInt(Context); 4446 HintLoc = C->getLocStart(); 4447 } 4448 } 4449 } 4450 if (ErrorFound) 4451 return StmtError(); 4452 auto Pair = DSAStack->getCriticalWithHint(DirName); 4453 if (Pair.first && DirName.getName() && !DependentHint) { 4454 if (llvm::APSInt::compareValues(Hint, Pair.second) != 0) { 4455 Diag(StartLoc, diag::err_omp_critical_with_hint); 4456 if (HintLoc.isValid()) { 4457 Diag(HintLoc, diag::note_omp_critical_hint_here) 4458 << 0 << Hint.toString(/*Radix=*/10, /*Signed=*/false); 4459 } else 4460 Diag(StartLoc, diag::note_omp_critical_no_hint) << 0; 4461 if (auto *C = Pair.first->getSingleClause<OMPHintClause>()) { 4462 Diag(C->getLocStart(), diag::note_omp_critical_hint_here) 4463 << 1 4464 << C->getHint()->EvaluateKnownConstInt(Context).toString( 4465 /*Radix=*/10, /*Signed=*/false); 4466 } else 4467 Diag(Pair.first->getLocStart(), diag::note_omp_critical_no_hint) << 1; 4468 } 4469 } 4470 4471 getCurFunction()->setHasBranchProtectedScope(); 4472 4473 auto *Dir = OMPCriticalDirective::Create(Context, DirName, StartLoc, EndLoc, 4474 Clauses, AStmt); 4475 if (!Pair.first && DirName.getName() && !DependentHint) 4476 DSAStack->addCriticalWithHint(Dir, Hint); 4477 return Dir; 4478 } 4479 4480 StmtResult Sema::ActOnOpenMPParallelForDirective( 4481 ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc, 4482 SourceLocation EndLoc, 4483 llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA) { 4484 if (!AStmt) 4485 return StmtError(); 4486 4487 CapturedStmt *CS = cast<CapturedStmt>(AStmt); 4488 // 1.2.2 OpenMP Language Terminology 4489 // Structured block - An executable statement with a single entry at the 4490 // top and a single exit at the bottom. 4491 // The point of exit cannot be a branch out of the structured block. 4492 // longjmp() and throw() must not violate the entry/exit criteria. 4493 CS->getCapturedDecl()->setNothrow(); 4494 4495 OMPLoopDirective::HelperExprs B; 4496 // In presence of clause 'collapse' or 'ordered' with number of loops, it will 4497 // define the nested loops number. 4498 unsigned NestedLoopCount = 4499 CheckOpenMPLoop(OMPD_parallel_for, getCollapseNumberExpr(Clauses), 4500 getOrderedNumberExpr(Clauses), AStmt, *this, *DSAStack, 4501 VarsWithImplicitDSA, B); 4502 if (NestedLoopCount == 0) 4503 return StmtError(); 4504 4505 assert((CurContext->isDependentContext() || B.builtAll()) && 4506 "omp parallel for loop exprs were not built"); 4507 4508 if (!CurContext->isDependentContext()) { 4509 // Finalize the clauses that need pre-built expressions for CodeGen. 4510 for (auto C : Clauses) { 4511 if (auto LC = dyn_cast<OMPLinearClause>(C)) 4512 if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef), 4513 B.NumIterations, *this, CurScope)) 4514 return StmtError(); 4515 } 4516 } 4517 4518 getCurFunction()->setHasBranchProtectedScope(); 4519 return OMPParallelForDirective::Create(Context, StartLoc, EndLoc, 4520 NestedLoopCount, Clauses, AStmt, B, 4521 DSAStack->isCancelRegion()); 4522 } 4523 4524 StmtResult Sema::ActOnOpenMPParallelForSimdDirective( 4525 ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc, 4526 SourceLocation EndLoc, 4527 llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA) { 4528 if (!AStmt) 4529 return StmtError(); 4530 4531 CapturedStmt *CS = cast<CapturedStmt>(AStmt); 4532 // 1.2.2 OpenMP Language Terminology 4533 // Structured block - An executable statement with a single entry at the 4534 // top and a single exit at the bottom. 4535 // The point of exit cannot be a branch out of the structured block. 4536 // longjmp() and throw() must not violate the entry/exit criteria. 4537 CS->getCapturedDecl()->setNothrow(); 4538 4539 OMPLoopDirective::HelperExprs B; 4540 // In presence of clause 'collapse' or 'ordered' with number of loops, it will 4541 // define the nested loops number. 4542 unsigned NestedLoopCount = 4543 CheckOpenMPLoop(OMPD_parallel_for_simd, getCollapseNumberExpr(Clauses), 4544 getOrderedNumberExpr(Clauses), AStmt, *this, *DSAStack, 4545 VarsWithImplicitDSA, B); 4546 if (NestedLoopCount == 0) 4547 return StmtError(); 4548 4549 if (!CurContext->isDependentContext()) { 4550 // Finalize the clauses that need pre-built expressions for CodeGen. 4551 for (auto C : Clauses) { 4552 if (auto LC = dyn_cast<OMPLinearClause>(C)) 4553 if (FinishOpenMPLinearClause(*LC, cast<DeclRefExpr>(B.IterationVarRef), 4554 B.NumIterations, *this, CurScope)) 4555 return StmtError(); 4556 } 4557 } 4558 4559 // OpenMP 4.1 [2.8.1, simd Construct, Restrictions] 4560 // If both simdlen and safelen clauses are specified, the value of the simdlen 4561 // parameter must be less than or equal to the value of the safelen parameter. 4562 OMPSafelenClause *Safelen = nullptr; 4563 OMPSimdlenClause *Simdlen = nullptr; 4564 for (auto *Clause : Clauses) { 4565 if (Clause->getClauseKind() == OMPC_safelen) 4566 Safelen = cast<OMPSafelenClause>(Clause); 4567 else if (Clause->getClauseKind() == OMPC_simdlen) 4568 Simdlen = cast<OMPSimdlenClause>(Clause); 4569 if (Safelen && Simdlen) 4570 break; 4571 } 4572 if (Simdlen && Safelen && 4573 checkSimdlenSafelenValues(*this, Simdlen->getSimdlen(), 4574 Safelen->getSafelen())) 4575 return StmtError(); 4576 4577 getCurFunction()->setHasBranchProtectedScope(); 4578 return OMPParallelForSimdDirective::Create( 4579 Context, StartLoc, EndLoc, NestedLoopCount, Clauses, AStmt, B); 4580 } 4581 4582 StmtResult 4583 Sema::ActOnOpenMPParallelSectionsDirective(ArrayRef<OMPClause *> Clauses, 4584 Stmt *AStmt, SourceLocation StartLoc, 4585 SourceLocation EndLoc) { 4586 if (!AStmt) 4587 return StmtError(); 4588 4589 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 4590 auto BaseStmt = AStmt; 4591 while (CapturedStmt *CS = dyn_cast_or_null<CapturedStmt>(BaseStmt)) 4592 BaseStmt = CS->getCapturedStmt(); 4593 if (auto C = dyn_cast_or_null<CompoundStmt>(BaseStmt)) { 4594 auto S = C->children(); 4595 if (S.begin() == S.end()) 4596 return StmtError(); 4597 // All associated statements must be '#pragma omp section' except for 4598 // the first one. 4599 for (Stmt *SectionStmt : llvm::make_range(std::next(S.begin()), S.end())) { 4600 if (!SectionStmt || !isa<OMPSectionDirective>(SectionStmt)) { 4601 if (SectionStmt) 4602 Diag(SectionStmt->getLocStart(), 4603 diag::err_omp_parallel_sections_substmt_not_section); 4604 return StmtError(); 4605 } 4606 cast<OMPSectionDirective>(SectionStmt) 4607 ->setHasCancel(DSAStack->isCancelRegion()); 4608 } 4609 } else { 4610 Diag(AStmt->getLocStart(), 4611 diag::err_omp_parallel_sections_not_compound_stmt); 4612 return StmtError(); 4613 } 4614 4615 getCurFunction()->setHasBranchProtectedScope(); 4616 4617 return OMPParallelSectionsDirective::Create( 4618 Context, StartLoc, EndLoc, Clauses, AStmt, DSAStack->isCancelRegion()); 4619 } 4620 4621 StmtResult Sema::ActOnOpenMPTaskDirective(ArrayRef<OMPClause *> Clauses, 4622 Stmt *AStmt, SourceLocation StartLoc, 4623 SourceLocation EndLoc) { 4624 if (!AStmt) 4625 return StmtError(); 4626 4627 CapturedStmt *CS = cast<CapturedStmt>(AStmt); 4628 // 1.2.2 OpenMP Language Terminology 4629 // Structured block - An executable statement with a single entry at the 4630 // top and a single exit at the bottom. 4631 // The point of exit cannot be a branch out of the structured block. 4632 // longjmp() and throw() must not violate the entry/exit criteria. 4633 CS->getCapturedDecl()->setNothrow(); 4634 4635 getCurFunction()->setHasBranchProtectedScope(); 4636 4637 return OMPTaskDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt, 4638 DSAStack->isCancelRegion()); 4639 } 4640 4641 StmtResult Sema::ActOnOpenMPTaskyieldDirective(SourceLocation StartLoc, 4642 SourceLocation EndLoc) { 4643 return OMPTaskyieldDirective::Create(Context, StartLoc, EndLoc); 4644 } 4645 4646 StmtResult Sema::ActOnOpenMPBarrierDirective(SourceLocation StartLoc, 4647 SourceLocation EndLoc) { 4648 return OMPBarrierDirective::Create(Context, StartLoc, EndLoc); 4649 } 4650 4651 StmtResult Sema::ActOnOpenMPTaskwaitDirective(SourceLocation StartLoc, 4652 SourceLocation EndLoc) { 4653 return OMPTaskwaitDirective::Create(Context, StartLoc, EndLoc); 4654 } 4655 4656 StmtResult Sema::ActOnOpenMPTaskgroupDirective(Stmt *AStmt, 4657 SourceLocation StartLoc, 4658 SourceLocation EndLoc) { 4659 if (!AStmt) 4660 return StmtError(); 4661 4662 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 4663 4664 getCurFunction()->setHasBranchProtectedScope(); 4665 4666 return OMPTaskgroupDirective::Create(Context, StartLoc, EndLoc, AStmt); 4667 } 4668 4669 StmtResult Sema::ActOnOpenMPFlushDirective(ArrayRef<OMPClause *> Clauses, 4670 SourceLocation StartLoc, 4671 SourceLocation EndLoc) { 4672 assert(Clauses.size() <= 1 && "Extra clauses in flush directive"); 4673 return OMPFlushDirective::Create(Context, StartLoc, EndLoc, Clauses); 4674 } 4675 4676 StmtResult Sema::ActOnOpenMPOrderedDirective(ArrayRef<OMPClause *> Clauses, 4677 Stmt *AStmt, 4678 SourceLocation StartLoc, 4679 SourceLocation EndLoc) { 4680 OMPClause *DependFound = nullptr; 4681 OMPClause *DependSourceClause = nullptr; 4682 OMPClause *DependSinkClause = nullptr; 4683 bool ErrorFound = false; 4684 OMPThreadsClause *TC = nullptr; 4685 OMPSIMDClause *SC = nullptr; 4686 for (auto *C : Clauses) { 4687 if (auto *DC = dyn_cast<OMPDependClause>(C)) { 4688 DependFound = C; 4689 if (DC->getDependencyKind() == OMPC_DEPEND_source) { 4690 if (DependSourceClause) { 4691 Diag(C->getLocStart(), diag::err_omp_more_one_clause) 4692 << getOpenMPDirectiveName(OMPD_ordered) 4693 << getOpenMPClauseName(OMPC_depend) << 2; 4694 ErrorFound = true; 4695 } else 4696 DependSourceClause = C; 4697 if (DependSinkClause) { 4698 Diag(C->getLocStart(), diag::err_omp_depend_sink_source_not_allowed) 4699 << 0; 4700 ErrorFound = true; 4701 } 4702 } else if (DC->getDependencyKind() == OMPC_DEPEND_sink) { 4703 if (DependSourceClause) { 4704 Diag(C->getLocStart(), diag::err_omp_depend_sink_source_not_allowed) 4705 << 1; 4706 ErrorFound = true; 4707 } 4708 DependSinkClause = C; 4709 } 4710 } else if (C->getClauseKind() == OMPC_threads) 4711 TC = cast<OMPThreadsClause>(C); 4712 else if (C->getClauseKind() == OMPC_simd) 4713 SC = cast<OMPSIMDClause>(C); 4714 } 4715 if (!ErrorFound && !SC && 4716 isOpenMPSimdDirective(DSAStack->getParentDirective())) { 4717 // OpenMP [2.8.1,simd Construct, Restrictions] 4718 // An ordered construct with the simd clause is the only OpenMP construct 4719 // that can appear in the simd region. 4720 Diag(StartLoc, diag::err_omp_prohibited_region_simd); 4721 ErrorFound = true; 4722 } else if (DependFound && (TC || SC)) { 4723 Diag(DependFound->getLocStart(), diag::err_omp_depend_clause_thread_simd) 4724 << getOpenMPClauseName(TC ? TC->getClauseKind() : SC->getClauseKind()); 4725 ErrorFound = true; 4726 } else if (DependFound && !DSAStack->getParentOrderedRegionParam()) { 4727 Diag(DependFound->getLocStart(), 4728 diag::err_omp_ordered_directive_without_param); 4729 ErrorFound = true; 4730 } else if (TC || Clauses.empty()) { 4731 if (auto *Param = DSAStack->getParentOrderedRegionParam()) { 4732 SourceLocation ErrLoc = TC ? TC->getLocStart() : StartLoc; 4733 Diag(ErrLoc, diag::err_omp_ordered_directive_with_param) 4734 << (TC != nullptr); 4735 Diag(Param->getLocStart(), diag::note_omp_ordered_param); 4736 ErrorFound = true; 4737 } 4738 } 4739 if ((!AStmt && !DependFound) || ErrorFound) 4740 return StmtError(); 4741 4742 if (AStmt) { 4743 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 4744 4745 getCurFunction()->setHasBranchProtectedScope(); 4746 } 4747 4748 return OMPOrderedDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt); 4749 } 4750 4751 namespace { 4752 /// \brief Helper class for checking expression in 'omp atomic [update]' 4753 /// construct. 4754 class OpenMPAtomicUpdateChecker { 4755 /// \brief Error results for atomic update expressions. 4756 enum ExprAnalysisErrorCode { 4757 /// \brief A statement is not an expression statement. 4758 NotAnExpression, 4759 /// \brief Expression is not builtin binary or unary operation. 4760 NotABinaryOrUnaryExpression, 4761 /// \brief Unary operation is not post-/pre- increment/decrement operation. 4762 NotAnUnaryIncDecExpression, 4763 /// \brief An expression is not of scalar type. 4764 NotAScalarType, 4765 /// \brief A binary operation is not an assignment operation. 4766 NotAnAssignmentOp, 4767 /// \brief RHS part of the binary operation is not a binary expression. 4768 NotABinaryExpression, 4769 /// \brief RHS part is not additive/multiplicative/shift/biwise binary 4770 /// expression. 4771 NotABinaryOperator, 4772 /// \brief RHS binary operation does not have reference to the updated LHS 4773 /// part. 4774 NotAnUpdateExpression, 4775 /// \brief No errors is found. 4776 NoError 4777 }; 4778 /// \brief Reference to Sema. 4779 Sema &SemaRef; 4780 /// \brief A location for note diagnostics (when error is found). 4781 SourceLocation NoteLoc; 4782 /// \brief 'x' lvalue part of the source atomic expression. 4783 Expr *X; 4784 /// \brief 'expr' rvalue part of the source atomic expression. 4785 Expr *E; 4786 /// \brief Helper expression of the form 4787 /// 'OpaqueValueExpr(x) binop OpaqueValueExpr(expr)' or 4788 /// 'OpaqueValueExpr(expr) binop OpaqueValueExpr(x)'. 4789 Expr *UpdateExpr; 4790 /// \brief Is 'x' a LHS in a RHS part of full update expression. It is 4791 /// important for non-associative operations. 4792 bool IsXLHSInRHSPart; 4793 BinaryOperatorKind Op; 4794 SourceLocation OpLoc; 4795 /// \brief true if the source expression is a postfix unary operation, false 4796 /// if it is a prefix unary operation. 4797 bool IsPostfixUpdate; 4798 4799 public: 4800 OpenMPAtomicUpdateChecker(Sema &SemaRef) 4801 : SemaRef(SemaRef), X(nullptr), E(nullptr), UpdateExpr(nullptr), 4802 IsXLHSInRHSPart(false), Op(BO_PtrMemD), IsPostfixUpdate(false) {} 4803 /// \brief Check specified statement that it is suitable for 'atomic update' 4804 /// constructs and extract 'x', 'expr' and Operation from the original 4805 /// expression. If DiagId and NoteId == 0, then only check is performed 4806 /// without error notification. 4807 /// \param DiagId Diagnostic which should be emitted if error is found. 4808 /// \param NoteId Diagnostic note for the main error message. 4809 /// \return true if statement is not an update expression, false otherwise. 4810 bool checkStatement(Stmt *S, unsigned DiagId = 0, unsigned NoteId = 0); 4811 /// \brief Return the 'x' lvalue part of the source atomic expression. 4812 Expr *getX() const { return X; } 4813 /// \brief Return the 'expr' rvalue part of the source atomic expression. 4814 Expr *getExpr() const { return E; } 4815 /// \brief Return the update expression used in calculation of the updated 4816 /// value. Always has form 'OpaqueValueExpr(x) binop OpaqueValueExpr(expr)' or 4817 /// 'OpaqueValueExpr(expr) binop OpaqueValueExpr(x)'. 4818 Expr *getUpdateExpr() const { return UpdateExpr; } 4819 /// \brief Return true if 'x' is LHS in RHS part of full update expression, 4820 /// false otherwise. 4821 bool isXLHSInRHSPart() const { return IsXLHSInRHSPart; } 4822 4823 /// \brief true if the source expression is a postfix unary operation, false 4824 /// if it is a prefix unary operation. 4825 bool isPostfixUpdate() const { return IsPostfixUpdate; } 4826 4827 private: 4828 bool checkBinaryOperation(BinaryOperator *AtomicBinOp, unsigned DiagId = 0, 4829 unsigned NoteId = 0); 4830 }; 4831 } // namespace 4832 4833 bool OpenMPAtomicUpdateChecker::checkBinaryOperation( 4834 BinaryOperator *AtomicBinOp, unsigned DiagId, unsigned NoteId) { 4835 ExprAnalysisErrorCode ErrorFound = NoError; 4836 SourceLocation ErrorLoc, NoteLoc; 4837 SourceRange ErrorRange, NoteRange; 4838 // Allowed constructs are: 4839 // x = x binop expr; 4840 // x = expr binop x; 4841 if (AtomicBinOp->getOpcode() == BO_Assign) { 4842 X = AtomicBinOp->getLHS(); 4843 if (auto *AtomicInnerBinOp = dyn_cast<BinaryOperator>( 4844 AtomicBinOp->getRHS()->IgnoreParenImpCasts())) { 4845 if (AtomicInnerBinOp->isMultiplicativeOp() || 4846 AtomicInnerBinOp->isAdditiveOp() || AtomicInnerBinOp->isShiftOp() || 4847 AtomicInnerBinOp->isBitwiseOp()) { 4848 Op = AtomicInnerBinOp->getOpcode(); 4849 OpLoc = AtomicInnerBinOp->getOperatorLoc(); 4850 auto *LHS = AtomicInnerBinOp->getLHS(); 4851 auto *RHS = AtomicInnerBinOp->getRHS(); 4852 llvm::FoldingSetNodeID XId, LHSId, RHSId; 4853 X->IgnoreParenImpCasts()->Profile(XId, SemaRef.getASTContext(), 4854 /*Canonical=*/true); 4855 LHS->IgnoreParenImpCasts()->Profile(LHSId, SemaRef.getASTContext(), 4856 /*Canonical=*/true); 4857 RHS->IgnoreParenImpCasts()->Profile(RHSId, SemaRef.getASTContext(), 4858 /*Canonical=*/true); 4859 if (XId == LHSId) { 4860 E = RHS; 4861 IsXLHSInRHSPart = true; 4862 } else if (XId == RHSId) { 4863 E = LHS; 4864 IsXLHSInRHSPart = false; 4865 } else { 4866 ErrorLoc = AtomicInnerBinOp->getExprLoc(); 4867 ErrorRange = AtomicInnerBinOp->getSourceRange(); 4868 NoteLoc = X->getExprLoc(); 4869 NoteRange = X->getSourceRange(); 4870 ErrorFound = NotAnUpdateExpression; 4871 } 4872 } else { 4873 ErrorLoc = AtomicInnerBinOp->getExprLoc(); 4874 ErrorRange = AtomicInnerBinOp->getSourceRange(); 4875 NoteLoc = AtomicInnerBinOp->getOperatorLoc(); 4876 NoteRange = SourceRange(NoteLoc, NoteLoc); 4877 ErrorFound = NotABinaryOperator; 4878 } 4879 } else { 4880 NoteLoc = ErrorLoc = AtomicBinOp->getRHS()->getExprLoc(); 4881 NoteRange = ErrorRange = AtomicBinOp->getRHS()->getSourceRange(); 4882 ErrorFound = NotABinaryExpression; 4883 } 4884 } else { 4885 ErrorLoc = AtomicBinOp->getExprLoc(); 4886 ErrorRange = AtomicBinOp->getSourceRange(); 4887 NoteLoc = AtomicBinOp->getOperatorLoc(); 4888 NoteRange = SourceRange(NoteLoc, NoteLoc); 4889 ErrorFound = NotAnAssignmentOp; 4890 } 4891 if (ErrorFound != NoError && DiagId != 0 && NoteId != 0) { 4892 SemaRef.Diag(ErrorLoc, DiagId) << ErrorRange; 4893 SemaRef.Diag(NoteLoc, NoteId) << ErrorFound << NoteRange; 4894 return true; 4895 } else if (SemaRef.CurContext->isDependentContext()) 4896 E = X = UpdateExpr = nullptr; 4897 return ErrorFound != NoError; 4898 } 4899 4900 bool OpenMPAtomicUpdateChecker::checkStatement(Stmt *S, unsigned DiagId, 4901 unsigned NoteId) { 4902 ExprAnalysisErrorCode ErrorFound = NoError; 4903 SourceLocation ErrorLoc, NoteLoc; 4904 SourceRange ErrorRange, NoteRange; 4905 // Allowed constructs are: 4906 // x++; 4907 // x--; 4908 // ++x; 4909 // --x; 4910 // x binop= expr; 4911 // x = x binop expr; 4912 // x = expr binop x; 4913 if (auto *AtomicBody = dyn_cast<Expr>(S)) { 4914 AtomicBody = AtomicBody->IgnoreParenImpCasts(); 4915 if (AtomicBody->getType()->isScalarType() || 4916 AtomicBody->isInstantiationDependent()) { 4917 if (auto *AtomicCompAssignOp = dyn_cast<CompoundAssignOperator>( 4918 AtomicBody->IgnoreParenImpCasts())) { 4919 // Check for Compound Assignment Operation 4920 Op = BinaryOperator::getOpForCompoundAssignment( 4921 AtomicCompAssignOp->getOpcode()); 4922 OpLoc = AtomicCompAssignOp->getOperatorLoc(); 4923 E = AtomicCompAssignOp->getRHS(); 4924 X = AtomicCompAssignOp->getLHS(); 4925 IsXLHSInRHSPart = true; 4926 } else if (auto *AtomicBinOp = dyn_cast<BinaryOperator>( 4927 AtomicBody->IgnoreParenImpCasts())) { 4928 // Check for Binary Operation 4929 if(checkBinaryOperation(AtomicBinOp, DiagId, NoteId)) 4930 return true; 4931 } else if (auto *AtomicUnaryOp = 4932 dyn_cast<UnaryOperator>(AtomicBody->IgnoreParenImpCasts())) { 4933 // Check for Unary Operation 4934 if (AtomicUnaryOp->isIncrementDecrementOp()) { 4935 IsPostfixUpdate = AtomicUnaryOp->isPostfix(); 4936 Op = AtomicUnaryOp->isIncrementOp() ? BO_Add : BO_Sub; 4937 OpLoc = AtomicUnaryOp->getOperatorLoc(); 4938 X = AtomicUnaryOp->getSubExpr(); 4939 E = SemaRef.ActOnIntegerConstant(OpLoc, /*uint64_t Val=*/1).get(); 4940 IsXLHSInRHSPart = true; 4941 } else { 4942 ErrorFound = NotAnUnaryIncDecExpression; 4943 ErrorLoc = AtomicUnaryOp->getExprLoc(); 4944 ErrorRange = AtomicUnaryOp->getSourceRange(); 4945 NoteLoc = AtomicUnaryOp->getOperatorLoc(); 4946 NoteRange = SourceRange(NoteLoc, NoteLoc); 4947 } 4948 } else if (!AtomicBody->isInstantiationDependent()) { 4949 ErrorFound = NotABinaryOrUnaryExpression; 4950 NoteLoc = ErrorLoc = AtomicBody->getExprLoc(); 4951 NoteRange = ErrorRange = AtomicBody->getSourceRange(); 4952 } 4953 } else { 4954 ErrorFound = NotAScalarType; 4955 NoteLoc = ErrorLoc = AtomicBody->getLocStart(); 4956 NoteRange = ErrorRange = SourceRange(NoteLoc, NoteLoc); 4957 } 4958 } else { 4959 ErrorFound = NotAnExpression; 4960 NoteLoc = ErrorLoc = S->getLocStart(); 4961 NoteRange = ErrorRange = SourceRange(NoteLoc, NoteLoc); 4962 } 4963 if (ErrorFound != NoError && DiagId != 0 && NoteId != 0) { 4964 SemaRef.Diag(ErrorLoc, DiagId) << ErrorRange; 4965 SemaRef.Diag(NoteLoc, NoteId) << ErrorFound << NoteRange; 4966 return true; 4967 } else if (SemaRef.CurContext->isDependentContext()) 4968 E = X = UpdateExpr = nullptr; 4969 if (ErrorFound == NoError && E && X) { 4970 // Build an update expression of form 'OpaqueValueExpr(x) binop 4971 // OpaqueValueExpr(expr)' or 'OpaqueValueExpr(expr) binop 4972 // OpaqueValueExpr(x)' and then cast it to the type of the 'x' expression. 4973 auto *OVEX = new (SemaRef.getASTContext()) 4974 OpaqueValueExpr(X->getExprLoc(), X->getType(), VK_RValue); 4975 auto *OVEExpr = new (SemaRef.getASTContext()) 4976 OpaqueValueExpr(E->getExprLoc(), E->getType(), VK_RValue); 4977 auto Update = 4978 SemaRef.CreateBuiltinBinOp(OpLoc, Op, IsXLHSInRHSPart ? OVEX : OVEExpr, 4979 IsXLHSInRHSPart ? OVEExpr : OVEX); 4980 if (Update.isInvalid()) 4981 return true; 4982 Update = SemaRef.PerformImplicitConversion(Update.get(), X->getType(), 4983 Sema::AA_Casting); 4984 if (Update.isInvalid()) 4985 return true; 4986 UpdateExpr = Update.get(); 4987 } 4988 return ErrorFound != NoError; 4989 } 4990 4991 StmtResult Sema::ActOnOpenMPAtomicDirective(ArrayRef<OMPClause *> Clauses, 4992 Stmt *AStmt, 4993 SourceLocation StartLoc, 4994 SourceLocation EndLoc) { 4995 if (!AStmt) 4996 return StmtError(); 4997 4998 auto CS = cast<CapturedStmt>(AStmt); 4999 // 1.2.2 OpenMP Language Terminology 5000 // Structured block - An executable statement with a single entry at the 5001 // top and a single exit at the bottom. 5002 // The point of exit cannot be a branch out of the structured block. 5003 // longjmp() and throw() must not violate the entry/exit criteria. 5004 OpenMPClauseKind AtomicKind = OMPC_unknown; 5005 SourceLocation AtomicKindLoc; 5006 for (auto *C : Clauses) { 5007 if (C->getClauseKind() == OMPC_read || C->getClauseKind() == OMPC_write || 5008 C->getClauseKind() == OMPC_update || 5009 C->getClauseKind() == OMPC_capture) { 5010 if (AtomicKind != OMPC_unknown) { 5011 Diag(C->getLocStart(), diag::err_omp_atomic_several_clauses) 5012 << SourceRange(C->getLocStart(), C->getLocEnd()); 5013 Diag(AtomicKindLoc, diag::note_omp_atomic_previous_clause) 5014 << getOpenMPClauseName(AtomicKind); 5015 } else { 5016 AtomicKind = C->getClauseKind(); 5017 AtomicKindLoc = C->getLocStart(); 5018 } 5019 } 5020 } 5021 5022 auto Body = CS->getCapturedStmt(); 5023 if (auto *EWC = dyn_cast<ExprWithCleanups>(Body)) 5024 Body = EWC->getSubExpr(); 5025 5026 Expr *X = nullptr; 5027 Expr *V = nullptr; 5028 Expr *E = nullptr; 5029 Expr *UE = nullptr; 5030 bool IsXLHSInRHSPart = false; 5031 bool IsPostfixUpdate = false; 5032 // OpenMP [2.12.6, atomic Construct] 5033 // In the next expressions: 5034 // * x and v (as applicable) are both l-value expressions with scalar type. 5035 // * During the execution of an atomic region, multiple syntactic 5036 // occurrences of x must designate the same storage location. 5037 // * Neither of v and expr (as applicable) may access the storage location 5038 // designated by x. 5039 // * Neither of x and expr (as applicable) may access the storage location 5040 // designated by v. 5041 // * expr is an expression with scalar type. 5042 // * binop is one of +, *, -, /, &, ^, |, <<, or >>. 5043 // * binop, binop=, ++, and -- are not overloaded operators. 5044 // * The expression x binop expr must be numerically equivalent to x binop 5045 // (expr). This requirement is satisfied if the operators in expr have 5046 // precedence greater than binop, or by using parentheses around expr or 5047 // subexpressions of expr. 5048 // * The expression expr binop x must be numerically equivalent to (expr) 5049 // binop x. This requirement is satisfied if the operators in expr have 5050 // precedence equal to or greater than binop, or by using parentheses around 5051 // expr or subexpressions of expr. 5052 // * For forms that allow multiple occurrences of x, the number of times 5053 // that x is evaluated is unspecified. 5054 if (AtomicKind == OMPC_read) { 5055 enum { 5056 NotAnExpression, 5057 NotAnAssignmentOp, 5058 NotAScalarType, 5059 NotAnLValue, 5060 NoError 5061 } ErrorFound = NoError; 5062 SourceLocation ErrorLoc, NoteLoc; 5063 SourceRange ErrorRange, NoteRange; 5064 // If clause is read: 5065 // v = x; 5066 if (auto AtomicBody = dyn_cast<Expr>(Body)) { 5067 auto AtomicBinOp = 5068 dyn_cast<BinaryOperator>(AtomicBody->IgnoreParenImpCasts()); 5069 if (AtomicBinOp && AtomicBinOp->getOpcode() == BO_Assign) { 5070 X = AtomicBinOp->getRHS()->IgnoreParenImpCasts(); 5071 V = AtomicBinOp->getLHS()->IgnoreParenImpCasts(); 5072 if ((X->isInstantiationDependent() || X->getType()->isScalarType()) && 5073 (V->isInstantiationDependent() || V->getType()->isScalarType())) { 5074 if (!X->isLValue() || !V->isLValue()) { 5075 auto NotLValueExpr = X->isLValue() ? V : X; 5076 ErrorFound = NotAnLValue; 5077 ErrorLoc = AtomicBinOp->getExprLoc(); 5078 ErrorRange = AtomicBinOp->getSourceRange(); 5079 NoteLoc = NotLValueExpr->getExprLoc(); 5080 NoteRange = NotLValueExpr->getSourceRange(); 5081 } 5082 } else if (!X->isInstantiationDependent() || 5083 !V->isInstantiationDependent()) { 5084 auto NotScalarExpr = 5085 (X->isInstantiationDependent() || X->getType()->isScalarType()) 5086 ? V 5087 : X; 5088 ErrorFound = NotAScalarType; 5089 ErrorLoc = AtomicBinOp->getExprLoc(); 5090 ErrorRange = AtomicBinOp->getSourceRange(); 5091 NoteLoc = NotScalarExpr->getExprLoc(); 5092 NoteRange = NotScalarExpr->getSourceRange(); 5093 } 5094 } else if (!AtomicBody->isInstantiationDependent()) { 5095 ErrorFound = NotAnAssignmentOp; 5096 ErrorLoc = AtomicBody->getExprLoc(); 5097 ErrorRange = AtomicBody->getSourceRange(); 5098 NoteLoc = AtomicBinOp ? AtomicBinOp->getOperatorLoc() 5099 : AtomicBody->getExprLoc(); 5100 NoteRange = AtomicBinOp ? AtomicBinOp->getSourceRange() 5101 : AtomicBody->getSourceRange(); 5102 } 5103 } else { 5104 ErrorFound = NotAnExpression; 5105 NoteLoc = ErrorLoc = Body->getLocStart(); 5106 NoteRange = ErrorRange = SourceRange(NoteLoc, NoteLoc); 5107 } 5108 if (ErrorFound != NoError) { 5109 Diag(ErrorLoc, diag::err_omp_atomic_read_not_expression_statement) 5110 << ErrorRange; 5111 Diag(NoteLoc, diag::note_omp_atomic_read_write) << ErrorFound 5112 << NoteRange; 5113 return StmtError(); 5114 } else if (CurContext->isDependentContext()) 5115 V = X = nullptr; 5116 } else if (AtomicKind == OMPC_write) { 5117 enum { 5118 NotAnExpression, 5119 NotAnAssignmentOp, 5120 NotAScalarType, 5121 NotAnLValue, 5122 NoError 5123 } ErrorFound = NoError; 5124 SourceLocation ErrorLoc, NoteLoc; 5125 SourceRange ErrorRange, NoteRange; 5126 // If clause is write: 5127 // x = expr; 5128 if (auto AtomicBody = dyn_cast<Expr>(Body)) { 5129 auto AtomicBinOp = 5130 dyn_cast<BinaryOperator>(AtomicBody->IgnoreParenImpCasts()); 5131 if (AtomicBinOp && AtomicBinOp->getOpcode() == BO_Assign) { 5132 X = AtomicBinOp->getLHS(); 5133 E = AtomicBinOp->getRHS(); 5134 if ((X->isInstantiationDependent() || X->getType()->isScalarType()) && 5135 (E->isInstantiationDependent() || E->getType()->isScalarType())) { 5136 if (!X->isLValue()) { 5137 ErrorFound = NotAnLValue; 5138 ErrorLoc = AtomicBinOp->getExprLoc(); 5139 ErrorRange = AtomicBinOp->getSourceRange(); 5140 NoteLoc = X->getExprLoc(); 5141 NoteRange = X->getSourceRange(); 5142 } 5143 } else if (!X->isInstantiationDependent() || 5144 !E->isInstantiationDependent()) { 5145 auto NotScalarExpr = 5146 (X->isInstantiationDependent() || X->getType()->isScalarType()) 5147 ? E 5148 : X; 5149 ErrorFound = NotAScalarType; 5150 ErrorLoc = AtomicBinOp->getExprLoc(); 5151 ErrorRange = AtomicBinOp->getSourceRange(); 5152 NoteLoc = NotScalarExpr->getExprLoc(); 5153 NoteRange = NotScalarExpr->getSourceRange(); 5154 } 5155 } else if (!AtomicBody->isInstantiationDependent()) { 5156 ErrorFound = NotAnAssignmentOp; 5157 ErrorLoc = AtomicBody->getExprLoc(); 5158 ErrorRange = AtomicBody->getSourceRange(); 5159 NoteLoc = AtomicBinOp ? AtomicBinOp->getOperatorLoc() 5160 : AtomicBody->getExprLoc(); 5161 NoteRange = AtomicBinOp ? AtomicBinOp->getSourceRange() 5162 : AtomicBody->getSourceRange(); 5163 } 5164 } else { 5165 ErrorFound = NotAnExpression; 5166 NoteLoc = ErrorLoc = Body->getLocStart(); 5167 NoteRange = ErrorRange = SourceRange(NoteLoc, NoteLoc); 5168 } 5169 if (ErrorFound != NoError) { 5170 Diag(ErrorLoc, diag::err_omp_atomic_write_not_expression_statement) 5171 << ErrorRange; 5172 Diag(NoteLoc, diag::note_omp_atomic_read_write) << ErrorFound 5173 << NoteRange; 5174 return StmtError(); 5175 } else if (CurContext->isDependentContext()) 5176 E = X = nullptr; 5177 } else if (AtomicKind == OMPC_update || AtomicKind == OMPC_unknown) { 5178 // If clause is update: 5179 // x++; 5180 // x--; 5181 // ++x; 5182 // --x; 5183 // x binop= expr; 5184 // x = x binop expr; 5185 // x = expr binop x; 5186 OpenMPAtomicUpdateChecker Checker(*this); 5187 if (Checker.checkStatement( 5188 Body, (AtomicKind == OMPC_update) 5189 ? diag::err_omp_atomic_update_not_expression_statement 5190 : diag::err_omp_atomic_not_expression_statement, 5191 diag::note_omp_atomic_update)) 5192 return StmtError(); 5193 if (!CurContext->isDependentContext()) { 5194 E = Checker.getExpr(); 5195 X = Checker.getX(); 5196 UE = Checker.getUpdateExpr(); 5197 IsXLHSInRHSPart = Checker.isXLHSInRHSPart(); 5198 } 5199 } else if (AtomicKind == OMPC_capture) { 5200 enum { 5201 NotAnAssignmentOp, 5202 NotACompoundStatement, 5203 NotTwoSubstatements, 5204 NotASpecificExpression, 5205 NoError 5206 } ErrorFound = NoError; 5207 SourceLocation ErrorLoc, NoteLoc; 5208 SourceRange ErrorRange, NoteRange; 5209 if (auto *AtomicBody = dyn_cast<Expr>(Body)) { 5210 // If clause is a capture: 5211 // v = x++; 5212 // v = x--; 5213 // v = ++x; 5214 // v = --x; 5215 // v = x binop= expr; 5216 // v = x = x binop expr; 5217 // v = x = expr binop x; 5218 auto *AtomicBinOp = 5219 dyn_cast<BinaryOperator>(AtomicBody->IgnoreParenImpCasts()); 5220 if (AtomicBinOp && AtomicBinOp->getOpcode() == BO_Assign) { 5221 V = AtomicBinOp->getLHS(); 5222 Body = AtomicBinOp->getRHS()->IgnoreParenImpCasts(); 5223 OpenMPAtomicUpdateChecker Checker(*this); 5224 if (Checker.checkStatement( 5225 Body, diag::err_omp_atomic_capture_not_expression_statement, 5226 diag::note_omp_atomic_update)) 5227 return StmtError(); 5228 E = Checker.getExpr(); 5229 X = Checker.getX(); 5230 UE = Checker.getUpdateExpr(); 5231 IsXLHSInRHSPart = Checker.isXLHSInRHSPart(); 5232 IsPostfixUpdate = Checker.isPostfixUpdate(); 5233 } else if (!AtomicBody->isInstantiationDependent()) { 5234 ErrorLoc = AtomicBody->getExprLoc(); 5235 ErrorRange = AtomicBody->getSourceRange(); 5236 NoteLoc = AtomicBinOp ? AtomicBinOp->getOperatorLoc() 5237 : AtomicBody->getExprLoc(); 5238 NoteRange = AtomicBinOp ? AtomicBinOp->getSourceRange() 5239 : AtomicBody->getSourceRange(); 5240 ErrorFound = NotAnAssignmentOp; 5241 } 5242 if (ErrorFound != NoError) { 5243 Diag(ErrorLoc, diag::err_omp_atomic_capture_not_expression_statement) 5244 << ErrorRange; 5245 Diag(NoteLoc, diag::note_omp_atomic_capture) << ErrorFound << NoteRange; 5246 return StmtError(); 5247 } else if (CurContext->isDependentContext()) { 5248 UE = V = E = X = nullptr; 5249 } 5250 } else { 5251 // If clause is a capture: 5252 // { v = x; x = expr; } 5253 // { v = x; x++; } 5254 // { v = x; x--; } 5255 // { v = x; ++x; } 5256 // { v = x; --x; } 5257 // { v = x; x binop= expr; } 5258 // { v = x; x = x binop expr; } 5259 // { v = x; x = expr binop x; } 5260 // { x++; v = x; } 5261 // { x--; v = x; } 5262 // { ++x; v = x; } 5263 // { --x; v = x; } 5264 // { x binop= expr; v = x; } 5265 // { x = x binop expr; v = x; } 5266 // { x = expr binop x; v = x; } 5267 if (auto *CS = dyn_cast<CompoundStmt>(Body)) { 5268 // Check that this is { expr1; expr2; } 5269 if (CS->size() == 2) { 5270 auto *First = CS->body_front(); 5271 auto *Second = CS->body_back(); 5272 if (auto *EWC = dyn_cast<ExprWithCleanups>(First)) 5273 First = EWC->getSubExpr()->IgnoreParenImpCasts(); 5274 if (auto *EWC = dyn_cast<ExprWithCleanups>(Second)) 5275 Second = EWC->getSubExpr()->IgnoreParenImpCasts(); 5276 // Need to find what subexpression is 'v' and what is 'x'. 5277 OpenMPAtomicUpdateChecker Checker(*this); 5278 bool IsUpdateExprFound = !Checker.checkStatement(Second); 5279 BinaryOperator *BinOp = nullptr; 5280 if (IsUpdateExprFound) { 5281 BinOp = dyn_cast<BinaryOperator>(First); 5282 IsUpdateExprFound = BinOp && BinOp->getOpcode() == BO_Assign; 5283 } 5284 if (IsUpdateExprFound && !CurContext->isDependentContext()) { 5285 // { v = x; x++; } 5286 // { v = x; x--; } 5287 // { v = x; ++x; } 5288 // { v = x; --x; } 5289 // { v = x; x binop= expr; } 5290 // { v = x; x = x binop expr; } 5291 // { v = x; x = expr binop x; } 5292 // Check that the first expression has form v = x. 5293 auto *PossibleX = BinOp->getRHS()->IgnoreParenImpCasts(); 5294 llvm::FoldingSetNodeID XId, PossibleXId; 5295 Checker.getX()->Profile(XId, Context, /*Canonical=*/true); 5296 PossibleX->Profile(PossibleXId, Context, /*Canonical=*/true); 5297 IsUpdateExprFound = XId == PossibleXId; 5298 if (IsUpdateExprFound) { 5299 V = BinOp->getLHS(); 5300 X = Checker.getX(); 5301 E = Checker.getExpr(); 5302 UE = Checker.getUpdateExpr(); 5303 IsXLHSInRHSPart = Checker.isXLHSInRHSPart(); 5304 IsPostfixUpdate = true; 5305 } 5306 } 5307 if (!IsUpdateExprFound) { 5308 IsUpdateExprFound = !Checker.checkStatement(First); 5309 BinOp = nullptr; 5310 if (IsUpdateExprFound) { 5311 BinOp = dyn_cast<BinaryOperator>(Second); 5312 IsUpdateExprFound = BinOp && BinOp->getOpcode() == BO_Assign; 5313 } 5314 if (IsUpdateExprFound && !CurContext->isDependentContext()) { 5315 // { x++; v = x; } 5316 // { x--; v = x; } 5317 // { ++x; v = x; } 5318 // { --x; v = x; } 5319 // { x binop= expr; v = x; } 5320 // { x = x binop expr; v = x; } 5321 // { x = expr binop x; v = x; } 5322 // Check that the second expression has form v = x. 5323 auto *PossibleX = BinOp->getRHS()->IgnoreParenImpCasts(); 5324 llvm::FoldingSetNodeID XId, PossibleXId; 5325 Checker.getX()->Profile(XId, Context, /*Canonical=*/true); 5326 PossibleX->Profile(PossibleXId, Context, /*Canonical=*/true); 5327 IsUpdateExprFound = XId == PossibleXId; 5328 if (IsUpdateExprFound) { 5329 V = BinOp->getLHS(); 5330 X = Checker.getX(); 5331 E = Checker.getExpr(); 5332 UE = Checker.getUpdateExpr(); 5333 IsXLHSInRHSPart = Checker.isXLHSInRHSPart(); 5334 IsPostfixUpdate = false; 5335 } 5336 } 5337 } 5338 if (!IsUpdateExprFound) { 5339 // { v = x; x = expr; } 5340 auto *FirstExpr = dyn_cast<Expr>(First); 5341 auto *SecondExpr = dyn_cast<Expr>(Second); 5342 if (!FirstExpr || !SecondExpr || 5343 !(FirstExpr->isInstantiationDependent() || 5344 SecondExpr->isInstantiationDependent())) { 5345 auto *FirstBinOp = dyn_cast<BinaryOperator>(First); 5346 if (!FirstBinOp || FirstBinOp->getOpcode() != BO_Assign) { 5347 ErrorFound = NotAnAssignmentOp; 5348 NoteLoc = ErrorLoc = FirstBinOp ? FirstBinOp->getOperatorLoc() 5349 : First->getLocStart(); 5350 NoteRange = ErrorRange = FirstBinOp 5351 ? FirstBinOp->getSourceRange() 5352 : SourceRange(ErrorLoc, ErrorLoc); 5353 } else { 5354 auto *SecondBinOp = dyn_cast<BinaryOperator>(Second); 5355 if (!SecondBinOp || SecondBinOp->getOpcode() != BO_Assign) { 5356 ErrorFound = NotAnAssignmentOp; 5357 NoteLoc = ErrorLoc = SecondBinOp 5358 ? SecondBinOp->getOperatorLoc() 5359 : Second->getLocStart(); 5360 NoteRange = ErrorRange = 5361 SecondBinOp ? SecondBinOp->getSourceRange() 5362 : SourceRange(ErrorLoc, ErrorLoc); 5363 } else { 5364 auto *PossibleXRHSInFirst = 5365 FirstBinOp->getRHS()->IgnoreParenImpCasts(); 5366 auto *PossibleXLHSInSecond = 5367 SecondBinOp->getLHS()->IgnoreParenImpCasts(); 5368 llvm::FoldingSetNodeID X1Id, X2Id; 5369 PossibleXRHSInFirst->Profile(X1Id, Context, 5370 /*Canonical=*/true); 5371 PossibleXLHSInSecond->Profile(X2Id, Context, 5372 /*Canonical=*/true); 5373 IsUpdateExprFound = X1Id == X2Id; 5374 if (IsUpdateExprFound) { 5375 V = FirstBinOp->getLHS(); 5376 X = SecondBinOp->getLHS(); 5377 E = SecondBinOp->getRHS(); 5378 UE = nullptr; 5379 IsXLHSInRHSPart = false; 5380 IsPostfixUpdate = true; 5381 } else { 5382 ErrorFound = NotASpecificExpression; 5383 ErrorLoc = FirstBinOp->getExprLoc(); 5384 ErrorRange = FirstBinOp->getSourceRange(); 5385 NoteLoc = SecondBinOp->getLHS()->getExprLoc(); 5386 NoteRange = SecondBinOp->getRHS()->getSourceRange(); 5387 } 5388 } 5389 } 5390 } 5391 } 5392 } else { 5393 NoteLoc = ErrorLoc = Body->getLocStart(); 5394 NoteRange = ErrorRange = 5395 SourceRange(Body->getLocStart(), Body->getLocStart()); 5396 ErrorFound = NotTwoSubstatements; 5397 } 5398 } else { 5399 NoteLoc = ErrorLoc = Body->getLocStart(); 5400 NoteRange = ErrorRange = 5401 SourceRange(Body->getLocStart(), Body->getLocStart()); 5402 ErrorFound = NotACompoundStatement; 5403 } 5404 if (ErrorFound != NoError) { 5405 Diag(ErrorLoc, diag::err_omp_atomic_capture_not_compound_statement) 5406 << ErrorRange; 5407 Diag(NoteLoc, diag::note_omp_atomic_capture) << ErrorFound << NoteRange; 5408 return StmtError(); 5409 } else if (CurContext->isDependentContext()) { 5410 UE = V = E = X = nullptr; 5411 } 5412 } 5413 } 5414 5415 getCurFunction()->setHasBranchProtectedScope(); 5416 5417 return OMPAtomicDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt, 5418 X, V, E, UE, IsXLHSInRHSPart, 5419 IsPostfixUpdate); 5420 } 5421 5422 StmtResult Sema::ActOnOpenMPTargetDirective(ArrayRef<OMPClause *> Clauses, 5423 Stmt *AStmt, 5424 SourceLocation StartLoc, 5425 SourceLocation EndLoc) { 5426 if (!AStmt) 5427 return StmtError(); 5428 5429 CapturedStmt *CS = cast<CapturedStmt>(AStmt); 5430 // 1.2.2 OpenMP Language Terminology 5431 // Structured block - An executable statement with a single entry at the 5432 // top and a single exit at the bottom. 5433 // The point of exit cannot be a branch out of the structured block. 5434 // longjmp() and throw() must not violate the entry/exit criteria. 5435 CS->getCapturedDecl()->setNothrow(); 5436 5437 // OpenMP [2.16, Nesting of Regions] 5438 // If specified, a teams construct must be contained within a target 5439 // construct. That target construct must contain no statements or directives 5440 // outside of the teams construct. 5441 if (DSAStack->hasInnerTeamsRegion()) { 5442 auto S = AStmt->IgnoreContainers(/*IgnoreCaptured*/ true); 5443 bool OMPTeamsFound = true; 5444 if (auto *CS = dyn_cast<CompoundStmt>(S)) { 5445 auto I = CS->body_begin(); 5446 while (I != CS->body_end()) { 5447 auto OED = dyn_cast<OMPExecutableDirective>(*I); 5448 if (!OED || !isOpenMPTeamsDirective(OED->getDirectiveKind())) { 5449 OMPTeamsFound = false; 5450 break; 5451 } 5452 ++I; 5453 } 5454 assert(I != CS->body_end() && "Not found statement"); 5455 S = *I; 5456 } 5457 if (!OMPTeamsFound) { 5458 Diag(StartLoc, diag::err_omp_target_contains_not_only_teams); 5459 Diag(DSAStack->getInnerTeamsRegionLoc(), 5460 diag::note_omp_nested_teams_construct_here); 5461 Diag(S->getLocStart(), diag::note_omp_nested_statement_here) 5462 << isa<OMPExecutableDirective>(S); 5463 return StmtError(); 5464 } 5465 } 5466 5467 getCurFunction()->setHasBranchProtectedScope(); 5468 5469 return OMPTargetDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt); 5470 } 5471 5472 StmtResult Sema::ActOnOpenMPTargetDataDirective(ArrayRef<OMPClause *> Clauses, 5473 Stmt *AStmt, 5474 SourceLocation StartLoc, 5475 SourceLocation EndLoc) { 5476 if (!AStmt) 5477 return StmtError(); 5478 5479 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 5480 5481 getCurFunction()->setHasBranchProtectedScope(); 5482 5483 return OMPTargetDataDirective::Create(Context, StartLoc, EndLoc, Clauses, 5484 AStmt); 5485 } 5486 5487 StmtResult Sema::ActOnOpenMPTeamsDirective(ArrayRef<OMPClause *> Clauses, 5488 Stmt *AStmt, SourceLocation StartLoc, 5489 SourceLocation EndLoc) { 5490 if (!AStmt) 5491 return StmtError(); 5492 5493 CapturedStmt *CS = cast<CapturedStmt>(AStmt); 5494 // 1.2.2 OpenMP Language Terminology 5495 // Structured block - An executable statement with a single entry at the 5496 // top and a single exit at the bottom. 5497 // The point of exit cannot be a branch out of the structured block. 5498 // longjmp() and throw() must not violate the entry/exit criteria. 5499 CS->getCapturedDecl()->setNothrow(); 5500 5501 getCurFunction()->setHasBranchProtectedScope(); 5502 5503 return OMPTeamsDirective::Create(Context, StartLoc, EndLoc, Clauses, AStmt); 5504 } 5505 5506 StmtResult 5507 Sema::ActOnOpenMPCancellationPointDirective(SourceLocation StartLoc, 5508 SourceLocation EndLoc, 5509 OpenMPDirectiveKind CancelRegion) { 5510 if (CancelRegion != OMPD_parallel && CancelRegion != OMPD_for && 5511 CancelRegion != OMPD_sections && CancelRegion != OMPD_taskgroup) { 5512 Diag(StartLoc, diag::err_omp_wrong_cancel_region) 5513 << getOpenMPDirectiveName(CancelRegion); 5514 return StmtError(); 5515 } 5516 if (DSAStack->isParentNowaitRegion()) { 5517 Diag(StartLoc, diag::err_omp_parent_cancel_region_nowait) << 0; 5518 return StmtError(); 5519 } 5520 if (DSAStack->isParentOrderedRegion()) { 5521 Diag(StartLoc, diag::err_omp_parent_cancel_region_ordered) << 0; 5522 return StmtError(); 5523 } 5524 return OMPCancellationPointDirective::Create(Context, StartLoc, EndLoc, 5525 CancelRegion); 5526 } 5527 5528 StmtResult Sema::ActOnOpenMPCancelDirective(ArrayRef<OMPClause *> Clauses, 5529 SourceLocation StartLoc, 5530 SourceLocation EndLoc, 5531 OpenMPDirectiveKind CancelRegion) { 5532 if (CancelRegion != OMPD_parallel && CancelRegion != OMPD_for && 5533 CancelRegion != OMPD_sections && CancelRegion != OMPD_taskgroup) { 5534 Diag(StartLoc, diag::err_omp_wrong_cancel_region) 5535 << getOpenMPDirectiveName(CancelRegion); 5536 return StmtError(); 5537 } 5538 if (DSAStack->isParentNowaitRegion()) { 5539 Diag(StartLoc, diag::err_omp_parent_cancel_region_nowait) << 1; 5540 return StmtError(); 5541 } 5542 if (DSAStack->isParentOrderedRegion()) { 5543 Diag(StartLoc, diag::err_omp_parent_cancel_region_ordered) << 1; 5544 return StmtError(); 5545 } 5546 DSAStack->setParentCancelRegion(/*Cancel=*/true); 5547 return OMPCancelDirective::Create(Context, StartLoc, EndLoc, Clauses, 5548 CancelRegion); 5549 } 5550 5551 static bool checkGrainsizeNumTasksClauses(Sema &S, 5552 ArrayRef<OMPClause *> Clauses) { 5553 OMPClause *PrevClause = nullptr; 5554 bool ErrorFound = false; 5555 for (auto *C : Clauses) { 5556 if (C->getClauseKind() == OMPC_grainsize || 5557 C->getClauseKind() == OMPC_num_tasks) { 5558 if (!PrevClause) 5559 PrevClause = C; 5560 else if (PrevClause->getClauseKind() != C->getClauseKind()) { 5561 S.Diag(C->getLocStart(), 5562 diag::err_omp_grainsize_num_tasks_mutually_exclusive) 5563 << getOpenMPClauseName(C->getClauseKind()) 5564 << getOpenMPClauseName(PrevClause->getClauseKind()); 5565 S.Diag(PrevClause->getLocStart(), 5566 diag::note_omp_previous_grainsize_num_tasks) 5567 << getOpenMPClauseName(PrevClause->getClauseKind()); 5568 ErrorFound = true; 5569 } 5570 } 5571 } 5572 return ErrorFound; 5573 } 5574 5575 StmtResult Sema::ActOnOpenMPTaskLoopDirective( 5576 ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc, 5577 SourceLocation EndLoc, 5578 llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA) { 5579 if (!AStmt) 5580 return StmtError(); 5581 5582 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 5583 OMPLoopDirective::HelperExprs B; 5584 // In presence of clause 'collapse' or 'ordered' with number of loops, it will 5585 // define the nested loops number. 5586 unsigned NestedLoopCount = 5587 CheckOpenMPLoop(OMPD_taskloop, getCollapseNumberExpr(Clauses), 5588 /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack, 5589 VarsWithImplicitDSA, B); 5590 if (NestedLoopCount == 0) 5591 return StmtError(); 5592 5593 assert((CurContext->isDependentContext() || B.builtAll()) && 5594 "omp for loop exprs were not built"); 5595 5596 // OpenMP, [2.9.2 taskloop Construct, Restrictions] 5597 // The grainsize clause and num_tasks clause are mutually exclusive and may 5598 // not appear on the same taskloop directive. 5599 if (checkGrainsizeNumTasksClauses(*this, Clauses)) 5600 return StmtError(); 5601 5602 getCurFunction()->setHasBranchProtectedScope(); 5603 return OMPTaskLoopDirective::Create(Context, StartLoc, EndLoc, 5604 NestedLoopCount, Clauses, AStmt, B); 5605 } 5606 5607 StmtResult Sema::ActOnOpenMPTaskLoopSimdDirective( 5608 ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc, 5609 SourceLocation EndLoc, 5610 llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA) { 5611 if (!AStmt) 5612 return StmtError(); 5613 5614 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 5615 OMPLoopDirective::HelperExprs B; 5616 // In presence of clause 'collapse' or 'ordered' with number of loops, it will 5617 // define the nested loops number. 5618 unsigned NestedLoopCount = 5619 CheckOpenMPLoop(OMPD_taskloop_simd, getCollapseNumberExpr(Clauses), 5620 /*OrderedLoopCountExpr=*/nullptr, AStmt, *this, *DSAStack, 5621 VarsWithImplicitDSA, B); 5622 if (NestedLoopCount == 0) 5623 return StmtError(); 5624 5625 assert((CurContext->isDependentContext() || B.builtAll()) && 5626 "omp for loop exprs were not built"); 5627 5628 // OpenMP, [2.9.2 taskloop Construct, Restrictions] 5629 // The grainsize clause and num_tasks clause are mutually exclusive and may 5630 // not appear on the same taskloop directive. 5631 if (checkGrainsizeNumTasksClauses(*this, Clauses)) 5632 return StmtError(); 5633 5634 getCurFunction()->setHasBranchProtectedScope(); 5635 return OMPTaskLoopSimdDirective::Create(Context, StartLoc, EndLoc, 5636 NestedLoopCount, Clauses, AStmt, B); 5637 } 5638 5639 StmtResult Sema::ActOnOpenMPDistributeDirective( 5640 ArrayRef<OMPClause *> Clauses, Stmt *AStmt, SourceLocation StartLoc, 5641 SourceLocation EndLoc, 5642 llvm::DenseMap<VarDecl *, Expr *> &VarsWithImplicitDSA) { 5643 if (!AStmt) 5644 return StmtError(); 5645 5646 assert(isa<CapturedStmt>(AStmt) && "Captured statement expected"); 5647 OMPLoopDirective::HelperExprs B; 5648 // In presence of clause 'collapse' with number of loops, it will 5649 // define the nested loops number. 5650 unsigned NestedLoopCount = 5651 CheckOpenMPLoop(OMPD_distribute, getCollapseNumberExpr(Clauses), 5652 nullptr /*ordered not a clause on distribute*/, AStmt, 5653 *this, *DSAStack, VarsWithImplicitDSA, B); 5654 if (NestedLoopCount == 0) 5655 return StmtError(); 5656 5657 assert((CurContext->isDependentContext() || B.builtAll()) && 5658 "omp for loop exprs were not built"); 5659 5660 getCurFunction()->setHasBranchProtectedScope(); 5661 return OMPDistributeDirective::Create(Context, StartLoc, EndLoc, 5662 NestedLoopCount, Clauses, AStmt, B); 5663 } 5664 5665 OMPClause *Sema::ActOnOpenMPSingleExprClause(OpenMPClauseKind Kind, Expr *Expr, 5666 SourceLocation StartLoc, 5667 SourceLocation LParenLoc, 5668 SourceLocation EndLoc) { 5669 OMPClause *Res = nullptr; 5670 switch (Kind) { 5671 case OMPC_final: 5672 Res = ActOnOpenMPFinalClause(Expr, StartLoc, LParenLoc, EndLoc); 5673 break; 5674 case OMPC_num_threads: 5675 Res = ActOnOpenMPNumThreadsClause(Expr, StartLoc, LParenLoc, EndLoc); 5676 break; 5677 case OMPC_safelen: 5678 Res = ActOnOpenMPSafelenClause(Expr, StartLoc, LParenLoc, EndLoc); 5679 break; 5680 case OMPC_simdlen: 5681 Res = ActOnOpenMPSimdlenClause(Expr, StartLoc, LParenLoc, EndLoc); 5682 break; 5683 case OMPC_collapse: 5684 Res = ActOnOpenMPCollapseClause(Expr, StartLoc, LParenLoc, EndLoc); 5685 break; 5686 case OMPC_ordered: 5687 Res = ActOnOpenMPOrderedClause(StartLoc, EndLoc, LParenLoc, Expr); 5688 break; 5689 case OMPC_device: 5690 Res = ActOnOpenMPDeviceClause(Expr, StartLoc, LParenLoc, EndLoc); 5691 break; 5692 case OMPC_num_teams: 5693 Res = ActOnOpenMPNumTeamsClause(Expr, StartLoc, LParenLoc, EndLoc); 5694 break; 5695 case OMPC_thread_limit: 5696 Res = ActOnOpenMPThreadLimitClause(Expr, StartLoc, LParenLoc, EndLoc); 5697 break; 5698 case OMPC_priority: 5699 Res = ActOnOpenMPPriorityClause(Expr, StartLoc, LParenLoc, EndLoc); 5700 break; 5701 case OMPC_grainsize: 5702 Res = ActOnOpenMPGrainsizeClause(Expr, StartLoc, LParenLoc, EndLoc); 5703 break; 5704 case OMPC_num_tasks: 5705 Res = ActOnOpenMPNumTasksClause(Expr, StartLoc, LParenLoc, EndLoc); 5706 break; 5707 case OMPC_hint: 5708 Res = ActOnOpenMPHintClause(Expr, StartLoc, LParenLoc, EndLoc); 5709 break; 5710 case OMPC_if: 5711 case OMPC_default: 5712 case OMPC_proc_bind: 5713 case OMPC_schedule: 5714 case OMPC_private: 5715 case OMPC_firstprivate: 5716 case OMPC_lastprivate: 5717 case OMPC_shared: 5718 case OMPC_reduction: 5719 case OMPC_linear: 5720 case OMPC_aligned: 5721 case OMPC_copyin: 5722 case OMPC_copyprivate: 5723 case OMPC_nowait: 5724 case OMPC_untied: 5725 case OMPC_mergeable: 5726 case OMPC_threadprivate: 5727 case OMPC_flush: 5728 case OMPC_read: 5729 case OMPC_write: 5730 case OMPC_update: 5731 case OMPC_capture: 5732 case OMPC_seq_cst: 5733 case OMPC_depend: 5734 case OMPC_threads: 5735 case OMPC_simd: 5736 case OMPC_map: 5737 case OMPC_nogroup: 5738 case OMPC_unknown: 5739 llvm_unreachable("Clause is not allowed."); 5740 } 5741 return Res; 5742 } 5743 5744 OMPClause *Sema::ActOnOpenMPIfClause(OpenMPDirectiveKind NameModifier, 5745 Expr *Condition, SourceLocation StartLoc, 5746 SourceLocation LParenLoc, 5747 SourceLocation NameModifierLoc, 5748 SourceLocation ColonLoc, 5749 SourceLocation EndLoc) { 5750 Expr *ValExpr = Condition; 5751 if (!Condition->isValueDependent() && !Condition->isTypeDependent() && 5752 !Condition->isInstantiationDependent() && 5753 !Condition->containsUnexpandedParameterPack()) { 5754 ExprResult Val = ActOnBooleanCondition(DSAStack->getCurScope(), 5755 Condition->getExprLoc(), Condition); 5756 if (Val.isInvalid()) 5757 return nullptr; 5758 5759 ValExpr = Val.get(); 5760 } 5761 5762 return new (Context) OMPIfClause(NameModifier, ValExpr, StartLoc, LParenLoc, 5763 NameModifierLoc, ColonLoc, EndLoc); 5764 } 5765 5766 OMPClause *Sema::ActOnOpenMPFinalClause(Expr *Condition, 5767 SourceLocation StartLoc, 5768 SourceLocation LParenLoc, 5769 SourceLocation EndLoc) { 5770 Expr *ValExpr = Condition; 5771 if (!Condition->isValueDependent() && !Condition->isTypeDependent() && 5772 !Condition->isInstantiationDependent() && 5773 !Condition->containsUnexpandedParameterPack()) { 5774 ExprResult Val = ActOnBooleanCondition(DSAStack->getCurScope(), 5775 Condition->getExprLoc(), Condition); 5776 if (Val.isInvalid()) 5777 return nullptr; 5778 5779 ValExpr = Val.get(); 5780 } 5781 5782 return new (Context) OMPFinalClause(ValExpr, StartLoc, LParenLoc, EndLoc); 5783 } 5784 ExprResult Sema::PerformOpenMPImplicitIntegerConversion(SourceLocation Loc, 5785 Expr *Op) { 5786 if (!Op) 5787 return ExprError(); 5788 5789 class IntConvertDiagnoser : public ICEConvertDiagnoser { 5790 public: 5791 IntConvertDiagnoser() 5792 : ICEConvertDiagnoser(/*AllowScopedEnumerations*/ false, false, true) {} 5793 SemaDiagnosticBuilder diagnoseNotInt(Sema &S, SourceLocation Loc, 5794 QualType T) override { 5795 return S.Diag(Loc, diag::err_omp_not_integral) << T; 5796 } 5797 SemaDiagnosticBuilder diagnoseIncomplete(Sema &S, SourceLocation Loc, 5798 QualType T) override { 5799 return S.Diag(Loc, diag::err_omp_incomplete_type) << T; 5800 } 5801 SemaDiagnosticBuilder diagnoseExplicitConv(Sema &S, SourceLocation Loc, 5802 QualType T, 5803 QualType ConvTy) override { 5804 return S.Diag(Loc, diag::err_omp_explicit_conversion) << T << ConvTy; 5805 } 5806 SemaDiagnosticBuilder noteExplicitConv(Sema &S, CXXConversionDecl *Conv, 5807 QualType ConvTy) override { 5808 return S.Diag(Conv->getLocation(), diag::note_omp_conversion_here) 5809 << ConvTy->isEnumeralType() << ConvTy; 5810 } 5811 SemaDiagnosticBuilder diagnoseAmbiguous(Sema &S, SourceLocation Loc, 5812 QualType T) override { 5813 return S.Diag(Loc, diag::err_omp_ambiguous_conversion) << T; 5814 } 5815 SemaDiagnosticBuilder noteAmbiguous(Sema &S, CXXConversionDecl *Conv, 5816 QualType ConvTy) override { 5817 return S.Diag(Conv->getLocation(), diag::note_omp_conversion_here) 5818 << ConvTy->isEnumeralType() << ConvTy; 5819 } 5820 SemaDiagnosticBuilder diagnoseConversion(Sema &, SourceLocation, QualType, 5821 QualType) override { 5822 llvm_unreachable("conversion functions are permitted"); 5823 } 5824 } ConvertDiagnoser; 5825 return PerformContextualImplicitConversion(Loc, Op, ConvertDiagnoser); 5826 } 5827 5828 static bool IsNonNegativeIntegerValue(Expr *&ValExpr, Sema &SemaRef, 5829 OpenMPClauseKind CKind, 5830 bool StrictlyPositive) { 5831 if (!ValExpr->isTypeDependent() && !ValExpr->isValueDependent() && 5832 !ValExpr->isInstantiationDependent()) { 5833 SourceLocation Loc = ValExpr->getExprLoc(); 5834 ExprResult Value = 5835 SemaRef.PerformOpenMPImplicitIntegerConversion(Loc, ValExpr); 5836 if (Value.isInvalid()) 5837 return false; 5838 5839 ValExpr = Value.get(); 5840 // The expression must evaluate to a non-negative integer value. 5841 llvm::APSInt Result; 5842 if (ValExpr->isIntegerConstantExpr(Result, SemaRef.Context) && 5843 Result.isSigned() && 5844 !((!StrictlyPositive && Result.isNonNegative()) || 5845 (StrictlyPositive && Result.isStrictlyPositive()))) { 5846 SemaRef.Diag(Loc, diag::err_omp_negative_expression_in_clause) 5847 << getOpenMPClauseName(CKind) << (StrictlyPositive ? 1 : 0) 5848 << ValExpr->getSourceRange(); 5849 return false; 5850 } 5851 } 5852 return true; 5853 } 5854 5855 OMPClause *Sema::ActOnOpenMPNumThreadsClause(Expr *NumThreads, 5856 SourceLocation StartLoc, 5857 SourceLocation LParenLoc, 5858 SourceLocation EndLoc) { 5859 Expr *ValExpr = NumThreads; 5860 5861 // OpenMP [2.5, Restrictions] 5862 // The num_threads expression must evaluate to a positive integer value. 5863 if (!IsNonNegativeIntegerValue(ValExpr, *this, OMPC_num_threads, 5864 /*StrictlyPositive=*/true)) 5865 return nullptr; 5866 5867 return new (Context) 5868 OMPNumThreadsClause(ValExpr, StartLoc, LParenLoc, EndLoc); 5869 } 5870 5871 ExprResult Sema::VerifyPositiveIntegerConstantInClause(Expr *E, 5872 OpenMPClauseKind CKind, 5873 bool StrictlyPositive) { 5874 if (!E) 5875 return ExprError(); 5876 if (E->isValueDependent() || E->isTypeDependent() || 5877 E->isInstantiationDependent() || E->containsUnexpandedParameterPack()) 5878 return E; 5879 llvm::APSInt Result; 5880 ExprResult ICE = VerifyIntegerConstantExpression(E, &Result); 5881 if (ICE.isInvalid()) 5882 return ExprError(); 5883 if ((StrictlyPositive && !Result.isStrictlyPositive()) || 5884 (!StrictlyPositive && !Result.isNonNegative())) { 5885 Diag(E->getExprLoc(), diag::err_omp_negative_expression_in_clause) 5886 << getOpenMPClauseName(CKind) << (StrictlyPositive ? 1 : 0) 5887 << E->getSourceRange(); 5888 return ExprError(); 5889 } 5890 if (CKind == OMPC_aligned && !Result.isPowerOf2()) { 5891 Diag(E->getExprLoc(), diag::warn_omp_alignment_not_power_of_two) 5892 << E->getSourceRange(); 5893 return ExprError(); 5894 } 5895 if (CKind == OMPC_collapse && DSAStack->getAssociatedLoops() == 1) 5896 DSAStack->setAssociatedLoops(Result.getExtValue()); 5897 else if (CKind == OMPC_ordered) 5898 DSAStack->setAssociatedLoops(Result.getExtValue()); 5899 return ICE; 5900 } 5901 5902 OMPClause *Sema::ActOnOpenMPSafelenClause(Expr *Len, SourceLocation StartLoc, 5903 SourceLocation LParenLoc, 5904 SourceLocation EndLoc) { 5905 // OpenMP [2.8.1, simd construct, Description] 5906 // The parameter of the safelen clause must be a constant 5907 // positive integer expression. 5908 ExprResult Safelen = VerifyPositiveIntegerConstantInClause(Len, OMPC_safelen); 5909 if (Safelen.isInvalid()) 5910 return nullptr; 5911 return new (Context) 5912 OMPSafelenClause(Safelen.get(), StartLoc, LParenLoc, EndLoc); 5913 } 5914 5915 OMPClause *Sema::ActOnOpenMPSimdlenClause(Expr *Len, SourceLocation StartLoc, 5916 SourceLocation LParenLoc, 5917 SourceLocation EndLoc) { 5918 // OpenMP [2.8.1, simd construct, Description] 5919 // The parameter of the simdlen clause must be a constant 5920 // positive integer expression. 5921 ExprResult Simdlen = VerifyPositiveIntegerConstantInClause(Len, OMPC_simdlen); 5922 if (Simdlen.isInvalid()) 5923 return nullptr; 5924 return new (Context) 5925 OMPSimdlenClause(Simdlen.get(), StartLoc, LParenLoc, EndLoc); 5926 } 5927 5928 OMPClause *Sema::ActOnOpenMPCollapseClause(Expr *NumForLoops, 5929 SourceLocation StartLoc, 5930 SourceLocation LParenLoc, 5931 SourceLocation EndLoc) { 5932 // OpenMP [2.7.1, loop construct, Description] 5933 // OpenMP [2.8.1, simd construct, Description] 5934 // OpenMP [2.9.6, distribute construct, Description] 5935 // The parameter of the collapse clause must be a constant 5936 // positive integer expression. 5937 ExprResult NumForLoopsResult = 5938 VerifyPositiveIntegerConstantInClause(NumForLoops, OMPC_collapse); 5939 if (NumForLoopsResult.isInvalid()) 5940 return nullptr; 5941 return new (Context) 5942 OMPCollapseClause(NumForLoopsResult.get(), StartLoc, LParenLoc, EndLoc); 5943 } 5944 5945 OMPClause *Sema::ActOnOpenMPOrderedClause(SourceLocation StartLoc, 5946 SourceLocation EndLoc, 5947 SourceLocation LParenLoc, 5948 Expr *NumForLoops) { 5949 // OpenMP [2.7.1, loop construct, Description] 5950 // OpenMP [2.8.1, simd construct, Description] 5951 // OpenMP [2.9.6, distribute construct, Description] 5952 // The parameter of the ordered clause must be a constant 5953 // positive integer expression if any. 5954 if (NumForLoops && LParenLoc.isValid()) { 5955 ExprResult NumForLoopsResult = 5956 VerifyPositiveIntegerConstantInClause(NumForLoops, OMPC_ordered); 5957 if (NumForLoopsResult.isInvalid()) 5958 return nullptr; 5959 NumForLoops = NumForLoopsResult.get(); 5960 } else 5961 NumForLoops = nullptr; 5962 DSAStack->setOrderedRegion(/*IsOrdered=*/true, NumForLoops); 5963 return new (Context) 5964 OMPOrderedClause(NumForLoops, StartLoc, LParenLoc, EndLoc); 5965 } 5966 5967 OMPClause *Sema::ActOnOpenMPSimpleClause( 5968 OpenMPClauseKind Kind, unsigned Argument, SourceLocation ArgumentLoc, 5969 SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc) { 5970 OMPClause *Res = nullptr; 5971 switch (Kind) { 5972 case OMPC_default: 5973 Res = 5974 ActOnOpenMPDefaultClause(static_cast<OpenMPDefaultClauseKind>(Argument), 5975 ArgumentLoc, StartLoc, LParenLoc, EndLoc); 5976 break; 5977 case OMPC_proc_bind: 5978 Res = ActOnOpenMPProcBindClause( 5979 static_cast<OpenMPProcBindClauseKind>(Argument), ArgumentLoc, StartLoc, 5980 LParenLoc, EndLoc); 5981 break; 5982 case OMPC_if: 5983 case OMPC_final: 5984 case OMPC_num_threads: 5985 case OMPC_safelen: 5986 case OMPC_simdlen: 5987 case OMPC_collapse: 5988 case OMPC_schedule: 5989 case OMPC_private: 5990 case OMPC_firstprivate: 5991 case OMPC_lastprivate: 5992 case OMPC_shared: 5993 case OMPC_reduction: 5994 case OMPC_linear: 5995 case OMPC_aligned: 5996 case OMPC_copyin: 5997 case OMPC_copyprivate: 5998 case OMPC_ordered: 5999 case OMPC_nowait: 6000 case OMPC_untied: 6001 case OMPC_mergeable: 6002 case OMPC_threadprivate: 6003 case OMPC_flush: 6004 case OMPC_read: 6005 case OMPC_write: 6006 case OMPC_update: 6007 case OMPC_capture: 6008 case OMPC_seq_cst: 6009 case OMPC_depend: 6010 case OMPC_device: 6011 case OMPC_threads: 6012 case OMPC_simd: 6013 case OMPC_map: 6014 case OMPC_num_teams: 6015 case OMPC_thread_limit: 6016 case OMPC_priority: 6017 case OMPC_grainsize: 6018 case OMPC_nogroup: 6019 case OMPC_num_tasks: 6020 case OMPC_hint: 6021 case OMPC_unknown: 6022 llvm_unreachable("Clause is not allowed."); 6023 } 6024 return Res; 6025 } 6026 6027 static std::string 6028 getListOfPossibleValues(OpenMPClauseKind K, unsigned First, unsigned Last, 6029 ArrayRef<unsigned> Exclude = llvm::None) { 6030 std::string Values; 6031 unsigned Bound = Last >= 2 ? Last - 2 : 0; 6032 unsigned Skipped = Exclude.size(); 6033 auto S = Exclude.begin(), E = Exclude.end(); 6034 for (unsigned i = First; i < Last; ++i) { 6035 if (std::find(S, E, i) != E) { 6036 --Skipped; 6037 continue; 6038 } 6039 Values += "'"; 6040 Values += getOpenMPSimpleClauseTypeName(K, i); 6041 Values += "'"; 6042 if (i == Bound - Skipped) 6043 Values += " or "; 6044 else if (i != Bound + 1 - Skipped) 6045 Values += ", "; 6046 } 6047 return Values; 6048 } 6049 6050 OMPClause *Sema::ActOnOpenMPDefaultClause(OpenMPDefaultClauseKind Kind, 6051 SourceLocation KindKwLoc, 6052 SourceLocation StartLoc, 6053 SourceLocation LParenLoc, 6054 SourceLocation EndLoc) { 6055 if (Kind == OMPC_DEFAULT_unknown) { 6056 static_assert(OMPC_DEFAULT_unknown > 0, 6057 "OMPC_DEFAULT_unknown not greater than 0"); 6058 Diag(KindKwLoc, diag::err_omp_unexpected_clause_value) 6059 << getListOfPossibleValues(OMPC_default, /*First=*/0, 6060 /*Last=*/OMPC_DEFAULT_unknown) 6061 << getOpenMPClauseName(OMPC_default); 6062 return nullptr; 6063 } 6064 switch (Kind) { 6065 case OMPC_DEFAULT_none: 6066 DSAStack->setDefaultDSANone(KindKwLoc); 6067 break; 6068 case OMPC_DEFAULT_shared: 6069 DSAStack->setDefaultDSAShared(KindKwLoc); 6070 break; 6071 case OMPC_DEFAULT_unknown: 6072 llvm_unreachable("Clause kind is not allowed."); 6073 break; 6074 } 6075 return new (Context) 6076 OMPDefaultClause(Kind, KindKwLoc, StartLoc, LParenLoc, EndLoc); 6077 } 6078 6079 OMPClause *Sema::ActOnOpenMPProcBindClause(OpenMPProcBindClauseKind Kind, 6080 SourceLocation KindKwLoc, 6081 SourceLocation StartLoc, 6082 SourceLocation LParenLoc, 6083 SourceLocation EndLoc) { 6084 if (Kind == OMPC_PROC_BIND_unknown) { 6085 Diag(KindKwLoc, diag::err_omp_unexpected_clause_value) 6086 << getListOfPossibleValues(OMPC_proc_bind, /*First=*/0, 6087 /*Last=*/OMPC_PROC_BIND_unknown) 6088 << getOpenMPClauseName(OMPC_proc_bind); 6089 return nullptr; 6090 } 6091 return new (Context) 6092 OMPProcBindClause(Kind, KindKwLoc, StartLoc, LParenLoc, EndLoc); 6093 } 6094 6095 OMPClause *Sema::ActOnOpenMPSingleExprWithArgClause( 6096 OpenMPClauseKind Kind, ArrayRef<unsigned> Argument, Expr *Expr, 6097 SourceLocation StartLoc, SourceLocation LParenLoc, 6098 ArrayRef<SourceLocation> ArgumentLoc, SourceLocation DelimLoc, 6099 SourceLocation EndLoc) { 6100 OMPClause *Res = nullptr; 6101 switch (Kind) { 6102 case OMPC_schedule: 6103 enum { Modifier1, Modifier2, ScheduleKind, NumberOfElements }; 6104 assert(Argument.size() == NumberOfElements && 6105 ArgumentLoc.size() == NumberOfElements); 6106 Res = ActOnOpenMPScheduleClause( 6107 static_cast<OpenMPScheduleClauseModifier>(Argument[Modifier1]), 6108 static_cast<OpenMPScheduleClauseModifier>(Argument[Modifier2]), 6109 static_cast<OpenMPScheduleClauseKind>(Argument[ScheduleKind]), Expr, 6110 StartLoc, LParenLoc, ArgumentLoc[Modifier1], ArgumentLoc[Modifier2], 6111 ArgumentLoc[ScheduleKind], DelimLoc, EndLoc); 6112 break; 6113 case OMPC_if: 6114 assert(Argument.size() == 1 && ArgumentLoc.size() == 1); 6115 Res = ActOnOpenMPIfClause(static_cast<OpenMPDirectiveKind>(Argument.back()), 6116 Expr, StartLoc, LParenLoc, ArgumentLoc.back(), 6117 DelimLoc, EndLoc); 6118 break; 6119 case OMPC_final: 6120 case OMPC_num_threads: 6121 case OMPC_safelen: 6122 case OMPC_simdlen: 6123 case OMPC_collapse: 6124 case OMPC_default: 6125 case OMPC_proc_bind: 6126 case OMPC_private: 6127 case OMPC_firstprivate: 6128 case OMPC_lastprivate: 6129 case OMPC_shared: 6130 case OMPC_reduction: 6131 case OMPC_linear: 6132 case OMPC_aligned: 6133 case OMPC_copyin: 6134 case OMPC_copyprivate: 6135 case OMPC_ordered: 6136 case OMPC_nowait: 6137 case OMPC_untied: 6138 case OMPC_mergeable: 6139 case OMPC_threadprivate: 6140 case OMPC_flush: 6141 case OMPC_read: 6142 case OMPC_write: 6143 case OMPC_update: 6144 case OMPC_capture: 6145 case OMPC_seq_cst: 6146 case OMPC_depend: 6147 case OMPC_device: 6148 case OMPC_threads: 6149 case OMPC_simd: 6150 case OMPC_map: 6151 case OMPC_num_teams: 6152 case OMPC_thread_limit: 6153 case OMPC_priority: 6154 case OMPC_grainsize: 6155 case OMPC_nogroup: 6156 case OMPC_num_tasks: 6157 case OMPC_hint: 6158 case OMPC_unknown: 6159 llvm_unreachable("Clause is not allowed."); 6160 } 6161 return Res; 6162 } 6163 6164 static bool checkScheduleModifiers(Sema &S, OpenMPScheduleClauseModifier M1, 6165 OpenMPScheduleClauseModifier M2, 6166 SourceLocation M1Loc, SourceLocation M2Loc) { 6167 if (M1 == OMPC_SCHEDULE_MODIFIER_unknown && M1Loc.isValid()) { 6168 SmallVector<unsigned, 2> Excluded; 6169 if (M2 != OMPC_SCHEDULE_MODIFIER_unknown) 6170 Excluded.push_back(M2); 6171 if (M2 == OMPC_SCHEDULE_MODIFIER_nonmonotonic) 6172 Excluded.push_back(OMPC_SCHEDULE_MODIFIER_monotonic); 6173 if (M2 == OMPC_SCHEDULE_MODIFIER_monotonic) 6174 Excluded.push_back(OMPC_SCHEDULE_MODIFIER_nonmonotonic); 6175 S.Diag(M1Loc, diag::err_omp_unexpected_clause_value) 6176 << getListOfPossibleValues(OMPC_schedule, 6177 /*First=*/OMPC_SCHEDULE_MODIFIER_unknown + 1, 6178 /*Last=*/OMPC_SCHEDULE_MODIFIER_last, 6179 Excluded) 6180 << getOpenMPClauseName(OMPC_schedule); 6181 return true; 6182 } 6183 return false; 6184 } 6185 6186 OMPClause *Sema::ActOnOpenMPScheduleClause( 6187 OpenMPScheduleClauseModifier M1, OpenMPScheduleClauseModifier M2, 6188 OpenMPScheduleClauseKind Kind, Expr *ChunkSize, SourceLocation StartLoc, 6189 SourceLocation LParenLoc, SourceLocation M1Loc, SourceLocation M2Loc, 6190 SourceLocation KindLoc, SourceLocation CommaLoc, SourceLocation EndLoc) { 6191 if (checkScheduleModifiers(*this, M1, M2, M1Loc, M2Loc) || 6192 checkScheduleModifiers(*this, M2, M1, M2Loc, M1Loc)) 6193 return nullptr; 6194 // OpenMP, 2.7.1, Loop Construct, Restrictions 6195 // Either the monotonic modifier or the nonmonotonic modifier can be specified 6196 // but not both. 6197 if ((M1 == M2 && M1 != OMPC_SCHEDULE_MODIFIER_unknown) || 6198 (M1 == OMPC_SCHEDULE_MODIFIER_monotonic && 6199 M2 == OMPC_SCHEDULE_MODIFIER_nonmonotonic) || 6200 (M1 == OMPC_SCHEDULE_MODIFIER_nonmonotonic && 6201 M2 == OMPC_SCHEDULE_MODIFIER_monotonic)) { 6202 Diag(M2Loc, diag::err_omp_unexpected_schedule_modifier) 6203 << getOpenMPSimpleClauseTypeName(OMPC_schedule, M2) 6204 << getOpenMPSimpleClauseTypeName(OMPC_schedule, M1); 6205 return nullptr; 6206 } 6207 if (Kind == OMPC_SCHEDULE_unknown) { 6208 std::string Values; 6209 if (M1Loc.isInvalid() && M2Loc.isInvalid()) { 6210 unsigned Exclude[] = {OMPC_SCHEDULE_unknown}; 6211 Values = getListOfPossibleValues(OMPC_schedule, /*First=*/0, 6212 /*Last=*/OMPC_SCHEDULE_MODIFIER_last, 6213 Exclude); 6214 } else { 6215 Values = getListOfPossibleValues(OMPC_schedule, /*First=*/0, 6216 /*Last=*/OMPC_SCHEDULE_unknown); 6217 } 6218 Diag(KindLoc, diag::err_omp_unexpected_clause_value) 6219 << Values << getOpenMPClauseName(OMPC_schedule); 6220 return nullptr; 6221 } 6222 // OpenMP, 2.7.1, Loop Construct, Restrictions 6223 // The nonmonotonic modifier can only be specified with schedule(dynamic) or 6224 // schedule(guided). 6225 if ((M1 == OMPC_SCHEDULE_MODIFIER_nonmonotonic || 6226 M2 == OMPC_SCHEDULE_MODIFIER_nonmonotonic) && 6227 Kind != OMPC_SCHEDULE_dynamic && Kind != OMPC_SCHEDULE_guided) { 6228 Diag(M1 == OMPC_SCHEDULE_MODIFIER_nonmonotonic ? M1Loc : M2Loc, 6229 diag::err_omp_schedule_nonmonotonic_static); 6230 return nullptr; 6231 } 6232 Expr *ValExpr = ChunkSize; 6233 Expr *HelperValExpr = nullptr; 6234 if (ChunkSize) { 6235 if (!ChunkSize->isValueDependent() && !ChunkSize->isTypeDependent() && 6236 !ChunkSize->isInstantiationDependent() && 6237 !ChunkSize->containsUnexpandedParameterPack()) { 6238 SourceLocation ChunkSizeLoc = ChunkSize->getLocStart(); 6239 ExprResult Val = 6240 PerformOpenMPImplicitIntegerConversion(ChunkSizeLoc, ChunkSize); 6241 if (Val.isInvalid()) 6242 return nullptr; 6243 6244 ValExpr = Val.get(); 6245 6246 // OpenMP [2.7.1, Restrictions] 6247 // chunk_size must be a loop invariant integer expression with a positive 6248 // value. 6249 llvm::APSInt Result; 6250 if (ValExpr->isIntegerConstantExpr(Result, Context)) { 6251 if (Result.isSigned() && !Result.isStrictlyPositive()) { 6252 Diag(ChunkSizeLoc, diag::err_omp_negative_expression_in_clause) 6253 << "schedule" << 1 << ChunkSize->getSourceRange(); 6254 return nullptr; 6255 } 6256 } else if (isParallelOrTaskRegion(DSAStack->getCurrentDirective())) { 6257 auto *ImpVar = buildVarDecl(*this, ChunkSize->getExprLoc(), 6258 ChunkSize->getType(), ".chunk."); 6259 auto *ImpVarRef = buildDeclRefExpr(*this, ImpVar, ChunkSize->getType(), 6260 ChunkSize->getExprLoc(), 6261 /*RefersToCapture=*/true); 6262 HelperValExpr = ImpVarRef; 6263 } 6264 } 6265 } 6266 6267 return new (Context) 6268 OMPScheduleClause(StartLoc, LParenLoc, KindLoc, CommaLoc, EndLoc, Kind, 6269 ValExpr, HelperValExpr, M1, M1Loc, M2, M2Loc); 6270 } 6271 6272 OMPClause *Sema::ActOnOpenMPClause(OpenMPClauseKind Kind, 6273 SourceLocation StartLoc, 6274 SourceLocation EndLoc) { 6275 OMPClause *Res = nullptr; 6276 switch (Kind) { 6277 case OMPC_ordered: 6278 Res = ActOnOpenMPOrderedClause(StartLoc, EndLoc); 6279 break; 6280 case OMPC_nowait: 6281 Res = ActOnOpenMPNowaitClause(StartLoc, EndLoc); 6282 break; 6283 case OMPC_untied: 6284 Res = ActOnOpenMPUntiedClause(StartLoc, EndLoc); 6285 break; 6286 case OMPC_mergeable: 6287 Res = ActOnOpenMPMergeableClause(StartLoc, EndLoc); 6288 break; 6289 case OMPC_read: 6290 Res = ActOnOpenMPReadClause(StartLoc, EndLoc); 6291 break; 6292 case OMPC_write: 6293 Res = ActOnOpenMPWriteClause(StartLoc, EndLoc); 6294 break; 6295 case OMPC_update: 6296 Res = ActOnOpenMPUpdateClause(StartLoc, EndLoc); 6297 break; 6298 case OMPC_capture: 6299 Res = ActOnOpenMPCaptureClause(StartLoc, EndLoc); 6300 break; 6301 case OMPC_seq_cst: 6302 Res = ActOnOpenMPSeqCstClause(StartLoc, EndLoc); 6303 break; 6304 case OMPC_threads: 6305 Res = ActOnOpenMPThreadsClause(StartLoc, EndLoc); 6306 break; 6307 case OMPC_simd: 6308 Res = ActOnOpenMPSIMDClause(StartLoc, EndLoc); 6309 break; 6310 case OMPC_nogroup: 6311 Res = ActOnOpenMPNogroupClause(StartLoc, EndLoc); 6312 break; 6313 case OMPC_if: 6314 case OMPC_final: 6315 case OMPC_num_threads: 6316 case OMPC_safelen: 6317 case OMPC_simdlen: 6318 case OMPC_collapse: 6319 case OMPC_schedule: 6320 case OMPC_private: 6321 case OMPC_firstprivate: 6322 case OMPC_lastprivate: 6323 case OMPC_shared: 6324 case OMPC_reduction: 6325 case OMPC_linear: 6326 case OMPC_aligned: 6327 case OMPC_copyin: 6328 case OMPC_copyprivate: 6329 case OMPC_default: 6330 case OMPC_proc_bind: 6331 case OMPC_threadprivate: 6332 case OMPC_flush: 6333 case OMPC_depend: 6334 case OMPC_device: 6335 case OMPC_map: 6336 case OMPC_num_teams: 6337 case OMPC_thread_limit: 6338 case OMPC_priority: 6339 case OMPC_grainsize: 6340 case OMPC_num_tasks: 6341 case OMPC_hint: 6342 case OMPC_unknown: 6343 llvm_unreachable("Clause is not allowed."); 6344 } 6345 return Res; 6346 } 6347 6348 OMPClause *Sema::ActOnOpenMPNowaitClause(SourceLocation StartLoc, 6349 SourceLocation EndLoc) { 6350 DSAStack->setNowaitRegion(); 6351 return new (Context) OMPNowaitClause(StartLoc, EndLoc); 6352 } 6353 6354 OMPClause *Sema::ActOnOpenMPUntiedClause(SourceLocation StartLoc, 6355 SourceLocation EndLoc) { 6356 return new (Context) OMPUntiedClause(StartLoc, EndLoc); 6357 } 6358 6359 OMPClause *Sema::ActOnOpenMPMergeableClause(SourceLocation StartLoc, 6360 SourceLocation EndLoc) { 6361 return new (Context) OMPMergeableClause(StartLoc, EndLoc); 6362 } 6363 6364 OMPClause *Sema::ActOnOpenMPReadClause(SourceLocation StartLoc, 6365 SourceLocation EndLoc) { 6366 return new (Context) OMPReadClause(StartLoc, EndLoc); 6367 } 6368 6369 OMPClause *Sema::ActOnOpenMPWriteClause(SourceLocation StartLoc, 6370 SourceLocation EndLoc) { 6371 return new (Context) OMPWriteClause(StartLoc, EndLoc); 6372 } 6373 6374 OMPClause *Sema::ActOnOpenMPUpdateClause(SourceLocation StartLoc, 6375 SourceLocation EndLoc) { 6376 return new (Context) OMPUpdateClause(StartLoc, EndLoc); 6377 } 6378 6379 OMPClause *Sema::ActOnOpenMPCaptureClause(SourceLocation StartLoc, 6380 SourceLocation EndLoc) { 6381 return new (Context) OMPCaptureClause(StartLoc, EndLoc); 6382 } 6383 6384 OMPClause *Sema::ActOnOpenMPSeqCstClause(SourceLocation StartLoc, 6385 SourceLocation EndLoc) { 6386 return new (Context) OMPSeqCstClause(StartLoc, EndLoc); 6387 } 6388 6389 OMPClause *Sema::ActOnOpenMPThreadsClause(SourceLocation StartLoc, 6390 SourceLocation EndLoc) { 6391 return new (Context) OMPThreadsClause(StartLoc, EndLoc); 6392 } 6393 6394 OMPClause *Sema::ActOnOpenMPSIMDClause(SourceLocation StartLoc, 6395 SourceLocation EndLoc) { 6396 return new (Context) OMPSIMDClause(StartLoc, EndLoc); 6397 } 6398 6399 OMPClause *Sema::ActOnOpenMPNogroupClause(SourceLocation StartLoc, 6400 SourceLocation EndLoc) { 6401 return new (Context) OMPNogroupClause(StartLoc, EndLoc); 6402 } 6403 6404 OMPClause *Sema::ActOnOpenMPVarListClause( 6405 OpenMPClauseKind Kind, ArrayRef<Expr *> VarList, Expr *TailExpr, 6406 SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation ColonLoc, 6407 SourceLocation EndLoc, CXXScopeSpec &ReductionIdScopeSpec, 6408 const DeclarationNameInfo &ReductionId, OpenMPDependClauseKind DepKind, 6409 OpenMPLinearClauseKind LinKind, OpenMPMapClauseKind MapTypeModifier, 6410 OpenMPMapClauseKind MapType, SourceLocation DepLinMapLoc) { 6411 OMPClause *Res = nullptr; 6412 switch (Kind) { 6413 case OMPC_private: 6414 Res = ActOnOpenMPPrivateClause(VarList, StartLoc, LParenLoc, EndLoc); 6415 break; 6416 case OMPC_firstprivate: 6417 Res = ActOnOpenMPFirstprivateClause(VarList, StartLoc, LParenLoc, EndLoc); 6418 break; 6419 case OMPC_lastprivate: 6420 Res = ActOnOpenMPLastprivateClause(VarList, StartLoc, LParenLoc, EndLoc); 6421 break; 6422 case OMPC_shared: 6423 Res = ActOnOpenMPSharedClause(VarList, StartLoc, LParenLoc, EndLoc); 6424 break; 6425 case OMPC_reduction: 6426 Res = ActOnOpenMPReductionClause(VarList, StartLoc, LParenLoc, ColonLoc, 6427 EndLoc, ReductionIdScopeSpec, ReductionId); 6428 break; 6429 case OMPC_linear: 6430 Res = ActOnOpenMPLinearClause(VarList, TailExpr, StartLoc, LParenLoc, 6431 LinKind, DepLinMapLoc, ColonLoc, EndLoc); 6432 break; 6433 case OMPC_aligned: 6434 Res = ActOnOpenMPAlignedClause(VarList, TailExpr, StartLoc, LParenLoc, 6435 ColonLoc, EndLoc); 6436 break; 6437 case OMPC_copyin: 6438 Res = ActOnOpenMPCopyinClause(VarList, StartLoc, LParenLoc, EndLoc); 6439 break; 6440 case OMPC_copyprivate: 6441 Res = ActOnOpenMPCopyprivateClause(VarList, StartLoc, LParenLoc, EndLoc); 6442 break; 6443 case OMPC_flush: 6444 Res = ActOnOpenMPFlushClause(VarList, StartLoc, LParenLoc, EndLoc); 6445 break; 6446 case OMPC_depend: 6447 Res = ActOnOpenMPDependClause(DepKind, DepLinMapLoc, ColonLoc, VarList, 6448 StartLoc, LParenLoc, EndLoc); 6449 break; 6450 case OMPC_map: 6451 Res = ActOnOpenMPMapClause(MapTypeModifier, MapType, DepLinMapLoc, ColonLoc, 6452 VarList, StartLoc, LParenLoc, EndLoc); 6453 break; 6454 case OMPC_if: 6455 case OMPC_final: 6456 case OMPC_num_threads: 6457 case OMPC_safelen: 6458 case OMPC_simdlen: 6459 case OMPC_collapse: 6460 case OMPC_default: 6461 case OMPC_proc_bind: 6462 case OMPC_schedule: 6463 case OMPC_ordered: 6464 case OMPC_nowait: 6465 case OMPC_untied: 6466 case OMPC_mergeable: 6467 case OMPC_threadprivate: 6468 case OMPC_read: 6469 case OMPC_write: 6470 case OMPC_update: 6471 case OMPC_capture: 6472 case OMPC_seq_cst: 6473 case OMPC_device: 6474 case OMPC_threads: 6475 case OMPC_simd: 6476 case OMPC_num_teams: 6477 case OMPC_thread_limit: 6478 case OMPC_priority: 6479 case OMPC_grainsize: 6480 case OMPC_nogroup: 6481 case OMPC_num_tasks: 6482 case OMPC_hint: 6483 case OMPC_unknown: 6484 llvm_unreachable("Clause is not allowed."); 6485 } 6486 return Res; 6487 } 6488 6489 OMPClause *Sema::ActOnOpenMPPrivateClause(ArrayRef<Expr *> VarList, 6490 SourceLocation StartLoc, 6491 SourceLocation LParenLoc, 6492 SourceLocation EndLoc) { 6493 SmallVector<Expr *, 8> Vars; 6494 SmallVector<Expr *, 8> PrivateCopies; 6495 for (auto &RefExpr : VarList) { 6496 assert(RefExpr && "NULL expr in OpenMP private clause."); 6497 if (isa<DependentScopeDeclRefExpr>(RefExpr)) { 6498 // It will be analyzed later. 6499 Vars.push_back(RefExpr); 6500 PrivateCopies.push_back(nullptr); 6501 continue; 6502 } 6503 6504 SourceLocation ELoc = RefExpr->getExprLoc(); 6505 // OpenMP [2.1, C/C++] 6506 // A list item is a variable name. 6507 // OpenMP [2.9.3.3, Restrictions, p.1] 6508 // A variable that is part of another variable (as an array or 6509 // structure element) cannot appear in a private clause. 6510 DeclRefExpr *DE = dyn_cast_or_null<DeclRefExpr>(RefExpr); 6511 if (!DE || !isa<VarDecl>(DE->getDecl())) { 6512 Diag(ELoc, diag::err_omp_expected_var_name) << RefExpr->getSourceRange(); 6513 continue; 6514 } 6515 Decl *D = DE->getDecl(); 6516 VarDecl *VD = cast<VarDecl>(D); 6517 6518 QualType Type = VD->getType(); 6519 if (Type->isDependentType() || Type->isInstantiationDependentType()) { 6520 // It will be analyzed later. 6521 Vars.push_back(DE); 6522 PrivateCopies.push_back(nullptr); 6523 continue; 6524 } 6525 6526 // OpenMP [2.9.3.3, Restrictions, C/C++, p.3] 6527 // A variable that appears in a private clause must not have an incomplete 6528 // type or a reference type. 6529 if (RequireCompleteType(ELoc, Type, 6530 diag::err_omp_private_incomplete_type)) { 6531 continue; 6532 } 6533 Type = Type.getNonReferenceType(); 6534 6535 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 6536 // in a Construct] 6537 // Variables with the predetermined data-sharing attributes may not be 6538 // listed in data-sharing attributes clauses, except for the cases 6539 // listed below. For these exceptions only, listing a predetermined 6540 // variable in a data-sharing attribute clause is allowed and overrides 6541 // the variable's predetermined data-sharing attributes. 6542 DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(VD, false); 6543 if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_private) { 6544 Diag(ELoc, diag::err_omp_wrong_dsa) << getOpenMPClauseName(DVar.CKind) 6545 << getOpenMPClauseName(OMPC_private); 6546 ReportOriginalDSA(*this, DSAStack, VD, DVar); 6547 continue; 6548 } 6549 6550 // Variably modified types are not supported for tasks. 6551 if (!Type->isAnyPointerType() && Type->isVariablyModifiedType() && 6552 DSAStack->getCurrentDirective() == OMPD_task) { 6553 Diag(ELoc, diag::err_omp_variably_modified_type_not_supported) 6554 << getOpenMPClauseName(OMPC_private) << Type 6555 << getOpenMPDirectiveName(DSAStack->getCurrentDirective()); 6556 bool IsDecl = 6557 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 6558 Diag(VD->getLocation(), 6559 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 6560 << VD; 6561 continue; 6562 } 6563 6564 // OpenMP [2.9.3.3, Restrictions, C/C++, p.1] 6565 // A variable of class type (or array thereof) that appears in a private 6566 // clause requires an accessible, unambiguous default constructor for the 6567 // class type. 6568 // Generate helper private variable and initialize it with the default 6569 // value. The address of the original variable is replaced by the address of 6570 // the new private variable in CodeGen. This new variable is not added to 6571 // IdResolver, so the code in the OpenMP region uses original variable for 6572 // proper diagnostics. 6573 Type = Type.getUnqualifiedType(); 6574 auto VDPrivate = buildVarDecl(*this, DE->getExprLoc(), Type, VD->getName(), 6575 VD->hasAttrs() ? &VD->getAttrs() : nullptr); 6576 ActOnUninitializedDecl(VDPrivate, /*TypeMayContainAuto=*/false); 6577 if (VDPrivate->isInvalidDecl()) 6578 continue; 6579 auto VDPrivateRefExpr = buildDeclRefExpr( 6580 *this, VDPrivate, DE->getType().getUnqualifiedType(), DE->getExprLoc()); 6581 6582 DSAStack->addDSA(VD, DE, OMPC_private); 6583 Vars.push_back(DE); 6584 PrivateCopies.push_back(VDPrivateRefExpr); 6585 } 6586 6587 if (Vars.empty()) 6588 return nullptr; 6589 6590 return OMPPrivateClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars, 6591 PrivateCopies); 6592 } 6593 6594 namespace { 6595 class DiagsUninitializedSeveretyRAII { 6596 private: 6597 DiagnosticsEngine &Diags; 6598 SourceLocation SavedLoc; 6599 bool IsIgnored; 6600 6601 public: 6602 DiagsUninitializedSeveretyRAII(DiagnosticsEngine &Diags, SourceLocation Loc, 6603 bool IsIgnored) 6604 : Diags(Diags), SavedLoc(Loc), IsIgnored(IsIgnored) { 6605 if (!IsIgnored) { 6606 Diags.setSeverity(/*Diag*/ diag::warn_uninit_self_reference_in_init, 6607 /*Map*/ diag::Severity::Ignored, Loc); 6608 } 6609 } 6610 ~DiagsUninitializedSeveretyRAII() { 6611 if (!IsIgnored) 6612 Diags.popMappings(SavedLoc); 6613 } 6614 }; 6615 } 6616 6617 OMPClause *Sema::ActOnOpenMPFirstprivateClause(ArrayRef<Expr *> VarList, 6618 SourceLocation StartLoc, 6619 SourceLocation LParenLoc, 6620 SourceLocation EndLoc) { 6621 SmallVector<Expr *, 8> Vars; 6622 SmallVector<Expr *, 8> PrivateCopies; 6623 SmallVector<Expr *, 8> Inits; 6624 bool IsImplicitClause = 6625 StartLoc.isInvalid() && LParenLoc.isInvalid() && EndLoc.isInvalid(); 6626 auto ImplicitClauseLoc = DSAStack->getConstructLoc(); 6627 6628 for (auto &RefExpr : VarList) { 6629 assert(RefExpr && "NULL expr in OpenMP firstprivate clause."); 6630 if (isa<DependentScopeDeclRefExpr>(RefExpr)) { 6631 // It will be analyzed later. 6632 Vars.push_back(RefExpr); 6633 PrivateCopies.push_back(nullptr); 6634 Inits.push_back(nullptr); 6635 continue; 6636 } 6637 6638 SourceLocation ELoc = 6639 IsImplicitClause ? ImplicitClauseLoc : RefExpr->getExprLoc(); 6640 // OpenMP [2.1, C/C++] 6641 // A list item is a variable name. 6642 // OpenMP [2.9.3.3, Restrictions, p.1] 6643 // A variable that is part of another variable (as an array or 6644 // structure element) cannot appear in a private clause. 6645 DeclRefExpr *DE = dyn_cast_or_null<DeclRefExpr>(RefExpr); 6646 if (!DE || !isa<VarDecl>(DE->getDecl())) { 6647 Diag(ELoc, diag::err_omp_expected_var_name) << RefExpr->getSourceRange(); 6648 continue; 6649 } 6650 Decl *D = DE->getDecl(); 6651 VarDecl *VD = cast<VarDecl>(D); 6652 6653 QualType Type = VD->getType(); 6654 if (Type->isDependentType() || Type->isInstantiationDependentType()) { 6655 // It will be analyzed later. 6656 Vars.push_back(DE); 6657 PrivateCopies.push_back(nullptr); 6658 Inits.push_back(nullptr); 6659 continue; 6660 } 6661 6662 // OpenMP [2.9.3.3, Restrictions, C/C++, p.3] 6663 // A variable that appears in a private clause must not have an incomplete 6664 // type or a reference type. 6665 if (RequireCompleteType(ELoc, Type, 6666 diag::err_omp_firstprivate_incomplete_type)) { 6667 continue; 6668 } 6669 Type = Type.getNonReferenceType(); 6670 6671 // OpenMP [2.9.3.4, Restrictions, C/C++, p.1] 6672 // A variable of class type (or array thereof) that appears in a private 6673 // clause requires an accessible, unambiguous copy constructor for the 6674 // class type. 6675 auto ElemType = Context.getBaseElementType(Type).getNonReferenceType(); 6676 6677 // If an implicit firstprivate variable found it was checked already. 6678 if (!IsImplicitClause) { 6679 DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(VD, false); 6680 bool IsConstant = ElemType.isConstant(Context); 6681 // OpenMP [2.4.13, Data-sharing Attribute Clauses] 6682 // A list item that specifies a given variable may not appear in more 6683 // than one clause on the same directive, except that a variable may be 6684 // specified in both firstprivate and lastprivate clauses. 6685 if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_firstprivate && 6686 DVar.CKind != OMPC_lastprivate && DVar.RefExpr) { 6687 Diag(ELoc, diag::err_omp_wrong_dsa) 6688 << getOpenMPClauseName(DVar.CKind) 6689 << getOpenMPClauseName(OMPC_firstprivate); 6690 ReportOriginalDSA(*this, DSAStack, VD, DVar); 6691 continue; 6692 } 6693 6694 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 6695 // in a Construct] 6696 // Variables with the predetermined data-sharing attributes may not be 6697 // listed in data-sharing attributes clauses, except for the cases 6698 // listed below. For these exceptions only, listing a predetermined 6699 // variable in a data-sharing attribute clause is allowed and overrides 6700 // the variable's predetermined data-sharing attributes. 6701 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 6702 // in a Construct, C/C++, p.2] 6703 // Variables with const-qualified type having no mutable member may be 6704 // listed in a firstprivate clause, even if they are static data members. 6705 if (!(IsConstant || VD->isStaticDataMember()) && !DVar.RefExpr && 6706 DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_shared) { 6707 Diag(ELoc, diag::err_omp_wrong_dsa) 6708 << getOpenMPClauseName(DVar.CKind) 6709 << getOpenMPClauseName(OMPC_firstprivate); 6710 ReportOriginalDSA(*this, DSAStack, VD, DVar); 6711 continue; 6712 } 6713 6714 OpenMPDirectiveKind CurrDir = DSAStack->getCurrentDirective(); 6715 // OpenMP [2.9.3.4, Restrictions, p.2] 6716 // A list item that is private within a parallel region must not appear 6717 // in a firstprivate clause on a worksharing construct if any of the 6718 // worksharing regions arising from the worksharing construct ever bind 6719 // to any of the parallel regions arising from the parallel construct. 6720 if (isOpenMPWorksharingDirective(CurrDir) && 6721 !isOpenMPParallelDirective(CurrDir)) { 6722 DVar = DSAStack->getImplicitDSA(VD, true); 6723 if (DVar.CKind != OMPC_shared && 6724 (isOpenMPParallelDirective(DVar.DKind) || 6725 DVar.DKind == OMPD_unknown)) { 6726 Diag(ELoc, diag::err_omp_required_access) 6727 << getOpenMPClauseName(OMPC_firstprivate) 6728 << getOpenMPClauseName(OMPC_shared); 6729 ReportOriginalDSA(*this, DSAStack, VD, DVar); 6730 continue; 6731 } 6732 } 6733 // OpenMP [2.9.3.4, Restrictions, p.3] 6734 // A list item that appears in a reduction clause of a parallel construct 6735 // must not appear in a firstprivate clause on a worksharing or task 6736 // construct if any of the worksharing or task regions arising from the 6737 // worksharing or task construct ever bind to any of the parallel regions 6738 // arising from the parallel construct. 6739 // OpenMP [2.9.3.4, Restrictions, p.4] 6740 // A list item that appears in a reduction clause in worksharing 6741 // construct must not appear in a firstprivate clause in a task construct 6742 // encountered during execution of any of the worksharing regions arising 6743 // from the worksharing construct. 6744 if (CurrDir == OMPD_task) { 6745 DVar = 6746 DSAStack->hasInnermostDSA(VD, MatchesAnyClause(OMPC_reduction), 6747 [](OpenMPDirectiveKind K) -> bool { 6748 return isOpenMPParallelDirective(K) || 6749 isOpenMPWorksharingDirective(K); 6750 }, 6751 false); 6752 if (DVar.CKind == OMPC_reduction && 6753 (isOpenMPParallelDirective(DVar.DKind) || 6754 isOpenMPWorksharingDirective(DVar.DKind))) { 6755 Diag(ELoc, diag::err_omp_parallel_reduction_in_task_firstprivate) 6756 << getOpenMPDirectiveName(DVar.DKind); 6757 ReportOriginalDSA(*this, DSAStack, VD, DVar); 6758 continue; 6759 } 6760 } 6761 6762 // OpenMP 4.5 [2.15.3.4, Restrictions, p.3] 6763 // A list item that is private within a teams region must not appear in a 6764 // firstprivate clause on a distribute construct if any of the distribute 6765 // regions arising from the distribute construct ever bind to any of the 6766 // teams regions arising from the teams construct. 6767 // OpenMP 4.5 [2.15.3.4, Restrictions, p.3] 6768 // A list item that appears in a reduction clause of a teams construct 6769 // must not appear in a firstprivate clause on a distribute construct if 6770 // any of the distribute regions arising from the distribute construct 6771 // ever bind to any of the teams regions arising from the teams construct. 6772 // OpenMP 4.5 [2.10.8, Distribute Construct, p.3] 6773 // A list item may appear in a firstprivate or lastprivate clause but not 6774 // both. 6775 if (CurrDir == OMPD_distribute) { 6776 DVar = DSAStack->hasInnermostDSA(VD, MatchesAnyClause(OMPC_private), 6777 [](OpenMPDirectiveKind K) -> bool { 6778 return isOpenMPTeamsDirective(K); 6779 }, 6780 false); 6781 if (DVar.CKind == OMPC_private && isOpenMPTeamsDirective(DVar.DKind)) { 6782 Diag(ELoc, diag::err_omp_firstprivate_distribute_private_teams); 6783 ReportOriginalDSA(*this, DSAStack, VD, DVar); 6784 continue; 6785 } 6786 DVar = DSAStack->hasInnermostDSA(VD, MatchesAnyClause(OMPC_reduction), 6787 [](OpenMPDirectiveKind K) -> bool { 6788 return isOpenMPTeamsDirective(K); 6789 }, 6790 false); 6791 if (DVar.CKind == OMPC_reduction && 6792 isOpenMPTeamsDirective(DVar.DKind)) { 6793 Diag(ELoc, diag::err_omp_firstprivate_distribute_in_teams_reduction); 6794 ReportOriginalDSA(*this, DSAStack, VD, DVar); 6795 continue; 6796 } 6797 DVar = DSAStack->getTopDSA(VD, false); 6798 if (DVar.CKind == OMPC_lastprivate) { 6799 Diag(ELoc, diag::err_omp_firstprivate_and_lastprivate_in_distribute); 6800 ReportOriginalDSA(*this, DSAStack, VD, DVar); 6801 continue; 6802 } 6803 } 6804 } 6805 6806 // Variably modified types are not supported for tasks. 6807 if (!Type->isAnyPointerType() && Type->isVariablyModifiedType() && 6808 DSAStack->getCurrentDirective() == OMPD_task) { 6809 Diag(ELoc, diag::err_omp_variably_modified_type_not_supported) 6810 << getOpenMPClauseName(OMPC_firstprivate) << Type 6811 << getOpenMPDirectiveName(DSAStack->getCurrentDirective()); 6812 bool IsDecl = 6813 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 6814 Diag(VD->getLocation(), 6815 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 6816 << VD; 6817 continue; 6818 } 6819 6820 Type = Type.getUnqualifiedType(); 6821 auto VDPrivate = buildVarDecl(*this, ELoc, Type, VD->getName(), 6822 VD->hasAttrs() ? &VD->getAttrs() : nullptr); 6823 // Generate helper private variable and initialize it with the value of the 6824 // original variable. The address of the original variable is replaced by 6825 // the address of the new private variable in the CodeGen. This new variable 6826 // is not added to IdResolver, so the code in the OpenMP region uses 6827 // original variable for proper diagnostics and variable capturing. 6828 Expr *VDInitRefExpr = nullptr; 6829 // For arrays generate initializer for single element and replace it by the 6830 // original array element in CodeGen. 6831 if (Type->isArrayType()) { 6832 auto VDInit = 6833 buildVarDecl(*this, DE->getExprLoc(), ElemType, VD->getName()); 6834 VDInitRefExpr = buildDeclRefExpr(*this, VDInit, ElemType, ELoc); 6835 auto Init = DefaultLvalueConversion(VDInitRefExpr).get(); 6836 ElemType = ElemType.getUnqualifiedType(); 6837 auto *VDInitTemp = buildVarDecl(*this, DE->getLocStart(), ElemType, 6838 ".firstprivate.temp"); 6839 InitializedEntity Entity = 6840 InitializedEntity::InitializeVariable(VDInitTemp); 6841 InitializationKind Kind = InitializationKind::CreateCopy(ELoc, ELoc); 6842 6843 InitializationSequence InitSeq(*this, Entity, Kind, Init); 6844 ExprResult Result = InitSeq.Perform(*this, Entity, Kind, Init); 6845 if (Result.isInvalid()) 6846 VDPrivate->setInvalidDecl(); 6847 else 6848 VDPrivate->setInit(Result.getAs<Expr>()); 6849 // Remove temp variable declaration. 6850 Context.Deallocate(VDInitTemp); 6851 } else { 6852 auto *VDInit = 6853 buildVarDecl(*this, DE->getLocStart(), Type, ".firstprivate.temp"); 6854 VDInitRefExpr = 6855 buildDeclRefExpr(*this, VDInit, DE->getType(), DE->getExprLoc()); 6856 AddInitializerToDecl(VDPrivate, 6857 DefaultLvalueConversion(VDInitRefExpr).get(), 6858 /*DirectInit=*/false, /*TypeMayContainAuto=*/false); 6859 } 6860 if (VDPrivate->isInvalidDecl()) { 6861 if (IsImplicitClause) { 6862 Diag(DE->getExprLoc(), 6863 diag::note_omp_task_predetermined_firstprivate_here); 6864 } 6865 continue; 6866 } 6867 CurContext->addDecl(VDPrivate); 6868 auto VDPrivateRefExpr = buildDeclRefExpr( 6869 *this, VDPrivate, DE->getType().getUnqualifiedType(), DE->getExprLoc()); 6870 DSAStack->addDSA(VD, DE, OMPC_firstprivate); 6871 Vars.push_back(DE); 6872 PrivateCopies.push_back(VDPrivateRefExpr); 6873 Inits.push_back(VDInitRefExpr); 6874 } 6875 6876 if (Vars.empty()) 6877 return nullptr; 6878 6879 return OMPFirstprivateClause::Create(Context, StartLoc, LParenLoc, EndLoc, 6880 Vars, PrivateCopies, Inits); 6881 } 6882 6883 OMPClause *Sema::ActOnOpenMPLastprivateClause(ArrayRef<Expr *> VarList, 6884 SourceLocation StartLoc, 6885 SourceLocation LParenLoc, 6886 SourceLocation EndLoc) { 6887 SmallVector<Expr *, 8> Vars; 6888 SmallVector<Expr *, 8> SrcExprs; 6889 SmallVector<Expr *, 8> DstExprs; 6890 SmallVector<Expr *, 8> AssignmentOps; 6891 for (auto &RefExpr : VarList) { 6892 assert(RefExpr && "NULL expr in OpenMP lastprivate clause."); 6893 if (isa<DependentScopeDeclRefExpr>(RefExpr)) { 6894 // It will be analyzed later. 6895 Vars.push_back(RefExpr); 6896 SrcExprs.push_back(nullptr); 6897 DstExprs.push_back(nullptr); 6898 AssignmentOps.push_back(nullptr); 6899 continue; 6900 } 6901 6902 SourceLocation ELoc = RefExpr->getExprLoc(); 6903 // OpenMP [2.1, C/C++] 6904 // A list item is a variable name. 6905 // OpenMP [2.14.3.5, Restrictions, p.1] 6906 // A variable that is part of another variable (as an array or structure 6907 // element) cannot appear in a lastprivate clause. 6908 DeclRefExpr *DE = dyn_cast_or_null<DeclRefExpr>(RefExpr); 6909 if (!DE || !isa<VarDecl>(DE->getDecl())) { 6910 Diag(ELoc, diag::err_omp_expected_var_name) << RefExpr->getSourceRange(); 6911 continue; 6912 } 6913 Decl *D = DE->getDecl(); 6914 VarDecl *VD = cast<VarDecl>(D); 6915 6916 QualType Type = VD->getType(); 6917 if (Type->isDependentType() || Type->isInstantiationDependentType()) { 6918 // It will be analyzed later. 6919 Vars.push_back(DE); 6920 SrcExprs.push_back(nullptr); 6921 DstExprs.push_back(nullptr); 6922 AssignmentOps.push_back(nullptr); 6923 continue; 6924 } 6925 6926 // OpenMP [2.14.3.5, Restrictions, C/C++, p.2] 6927 // A variable that appears in a lastprivate clause must not have an 6928 // incomplete type or a reference type. 6929 if (RequireCompleteType(ELoc, Type, 6930 diag::err_omp_lastprivate_incomplete_type)) { 6931 continue; 6932 } 6933 Type = Type.getNonReferenceType(); 6934 6935 // OpenMP [2.14.1.1, Data-sharing Attribute Rules for Variables Referenced 6936 // in a Construct] 6937 // Variables with the predetermined data-sharing attributes may not be 6938 // listed in data-sharing attributes clauses, except for the cases 6939 // listed below. 6940 DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(VD, false); 6941 if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_lastprivate && 6942 DVar.CKind != OMPC_firstprivate && 6943 (DVar.CKind != OMPC_private || DVar.RefExpr != nullptr)) { 6944 Diag(ELoc, diag::err_omp_wrong_dsa) 6945 << getOpenMPClauseName(DVar.CKind) 6946 << getOpenMPClauseName(OMPC_lastprivate); 6947 ReportOriginalDSA(*this, DSAStack, VD, DVar); 6948 continue; 6949 } 6950 6951 OpenMPDirectiveKind CurrDir = DSAStack->getCurrentDirective(); 6952 // OpenMP [2.14.3.5, Restrictions, p.2] 6953 // A list item that is private within a parallel region, or that appears in 6954 // the reduction clause of a parallel construct, must not appear in a 6955 // lastprivate clause on a worksharing construct if any of the corresponding 6956 // worksharing regions ever binds to any of the corresponding parallel 6957 // regions. 6958 DSAStackTy::DSAVarData TopDVar = DVar; 6959 if (isOpenMPWorksharingDirective(CurrDir) && 6960 !isOpenMPParallelDirective(CurrDir)) { 6961 DVar = DSAStack->getImplicitDSA(VD, true); 6962 if (DVar.CKind != OMPC_shared) { 6963 Diag(ELoc, diag::err_omp_required_access) 6964 << getOpenMPClauseName(OMPC_lastprivate) 6965 << getOpenMPClauseName(OMPC_shared); 6966 ReportOriginalDSA(*this, DSAStack, VD, DVar); 6967 continue; 6968 } 6969 } 6970 // OpenMP [2.14.3.5, Restrictions, C++, p.1,2] 6971 // A variable of class type (or array thereof) that appears in a 6972 // lastprivate clause requires an accessible, unambiguous default 6973 // constructor for the class type, unless the list item is also specified 6974 // in a firstprivate clause. 6975 // A variable of class type (or array thereof) that appears in a 6976 // lastprivate clause requires an accessible, unambiguous copy assignment 6977 // operator for the class type. 6978 Type = Context.getBaseElementType(Type).getNonReferenceType(); 6979 auto *SrcVD = buildVarDecl(*this, DE->getLocStart(), 6980 Type.getUnqualifiedType(), ".lastprivate.src", 6981 VD->hasAttrs() ? &VD->getAttrs() : nullptr); 6982 auto *PseudoSrcExpr = buildDeclRefExpr( 6983 *this, SrcVD, Type.getUnqualifiedType(), DE->getExprLoc()); 6984 auto *DstVD = 6985 buildVarDecl(*this, DE->getLocStart(), Type, ".lastprivate.dst", 6986 VD->hasAttrs() ? &VD->getAttrs() : nullptr); 6987 auto *PseudoDstExpr = 6988 buildDeclRefExpr(*this, DstVD, Type, DE->getExprLoc()); 6989 // For arrays generate assignment operation for single element and replace 6990 // it by the original array element in CodeGen. 6991 auto AssignmentOp = BuildBinOp(/*S=*/nullptr, DE->getExprLoc(), BO_Assign, 6992 PseudoDstExpr, PseudoSrcExpr); 6993 if (AssignmentOp.isInvalid()) 6994 continue; 6995 AssignmentOp = ActOnFinishFullExpr(AssignmentOp.get(), DE->getExprLoc(), 6996 /*DiscardedValue=*/true); 6997 if (AssignmentOp.isInvalid()) 6998 continue; 6999 7000 // OpenMP 4.5 [2.10.8, Distribute Construct, p.3] 7001 // A list item may appear in a firstprivate or lastprivate clause but not 7002 // both. 7003 if (CurrDir == OMPD_distribute) { 7004 DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(VD, false); 7005 if (DVar.CKind == OMPC_firstprivate) { 7006 Diag(ELoc, diag::err_omp_firstprivate_and_lastprivate_in_distribute); 7007 ReportOriginalDSA(*this, DSAStack, VD, DVar); 7008 continue; 7009 } 7010 } 7011 7012 if (TopDVar.CKind != OMPC_firstprivate) 7013 DSAStack->addDSA(VD, DE, OMPC_lastprivate); 7014 Vars.push_back(DE); 7015 SrcExprs.push_back(PseudoSrcExpr); 7016 DstExprs.push_back(PseudoDstExpr); 7017 AssignmentOps.push_back(AssignmentOp.get()); 7018 } 7019 7020 if (Vars.empty()) 7021 return nullptr; 7022 7023 return OMPLastprivateClause::Create(Context, StartLoc, LParenLoc, EndLoc, 7024 Vars, SrcExprs, DstExprs, AssignmentOps); 7025 } 7026 7027 OMPClause *Sema::ActOnOpenMPSharedClause(ArrayRef<Expr *> VarList, 7028 SourceLocation StartLoc, 7029 SourceLocation LParenLoc, 7030 SourceLocation EndLoc) { 7031 SmallVector<Expr *, 8> Vars; 7032 for (auto &RefExpr : VarList) { 7033 assert(RefExpr && "NULL expr in OpenMP shared clause."); 7034 if (isa<DependentScopeDeclRefExpr>(RefExpr)) { 7035 // It will be analyzed later. 7036 Vars.push_back(RefExpr); 7037 continue; 7038 } 7039 7040 SourceLocation ELoc = RefExpr->getExprLoc(); 7041 // OpenMP [2.1, C/C++] 7042 // A list item is a variable name. 7043 // OpenMP [2.14.3.2, Restrictions, p.1] 7044 // A variable that is part of another variable (as an array or structure 7045 // element) cannot appear in a shared unless it is a static data member 7046 // of a C++ class. 7047 DeclRefExpr *DE = dyn_cast<DeclRefExpr>(RefExpr); 7048 if (!DE || !isa<VarDecl>(DE->getDecl())) { 7049 Diag(ELoc, diag::err_omp_expected_var_name) << RefExpr->getSourceRange(); 7050 continue; 7051 } 7052 Decl *D = DE->getDecl(); 7053 VarDecl *VD = cast<VarDecl>(D); 7054 7055 QualType Type = VD->getType(); 7056 if (Type->isDependentType() || Type->isInstantiationDependentType()) { 7057 // It will be analyzed later. 7058 Vars.push_back(DE); 7059 continue; 7060 } 7061 7062 // OpenMP [2.9.1.1, Data-sharing Attribute Rules for Variables Referenced 7063 // in a Construct] 7064 // Variables with the predetermined data-sharing attributes may not be 7065 // listed in data-sharing attributes clauses, except for the cases 7066 // listed below. For these exceptions only, listing a predetermined 7067 // variable in a data-sharing attribute clause is allowed and overrides 7068 // the variable's predetermined data-sharing attributes. 7069 DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(VD, false); 7070 if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_shared && 7071 DVar.RefExpr) { 7072 Diag(ELoc, diag::err_omp_wrong_dsa) << getOpenMPClauseName(DVar.CKind) 7073 << getOpenMPClauseName(OMPC_shared); 7074 ReportOriginalDSA(*this, DSAStack, VD, DVar); 7075 continue; 7076 } 7077 7078 DSAStack->addDSA(VD, DE, OMPC_shared); 7079 Vars.push_back(DE); 7080 } 7081 7082 if (Vars.empty()) 7083 return nullptr; 7084 7085 return OMPSharedClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars); 7086 } 7087 7088 namespace { 7089 class DSARefChecker : public StmtVisitor<DSARefChecker, bool> { 7090 DSAStackTy *Stack; 7091 7092 public: 7093 bool VisitDeclRefExpr(DeclRefExpr *E) { 7094 if (VarDecl *VD = dyn_cast<VarDecl>(E->getDecl())) { 7095 DSAStackTy::DSAVarData DVar = Stack->getTopDSA(VD, false); 7096 if (DVar.CKind == OMPC_shared && !DVar.RefExpr) 7097 return false; 7098 if (DVar.CKind != OMPC_unknown) 7099 return true; 7100 DSAStackTy::DSAVarData DVarPrivate = 7101 Stack->hasDSA(VD, isOpenMPPrivate, MatchesAlways(), false); 7102 if (DVarPrivate.CKind != OMPC_unknown) 7103 return true; 7104 return false; 7105 } 7106 return false; 7107 } 7108 bool VisitStmt(Stmt *S) { 7109 for (auto Child : S->children()) { 7110 if (Child && Visit(Child)) 7111 return true; 7112 } 7113 return false; 7114 } 7115 explicit DSARefChecker(DSAStackTy *S) : Stack(S) {} 7116 }; 7117 } // namespace 7118 7119 OMPClause *Sema::ActOnOpenMPReductionClause( 7120 ArrayRef<Expr *> VarList, SourceLocation StartLoc, SourceLocation LParenLoc, 7121 SourceLocation ColonLoc, SourceLocation EndLoc, 7122 CXXScopeSpec &ReductionIdScopeSpec, 7123 const DeclarationNameInfo &ReductionId) { 7124 // TODO: Allow scope specification search when 'declare reduction' is 7125 // supported. 7126 assert(ReductionIdScopeSpec.isEmpty() && 7127 "No support for scoped reduction identifiers yet."); 7128 7129 auto DN = ReductionId.getName(); 7130 auto OOK = DN.getCXXOverloadedOperator(); 7131 BinaryOperatorKind BOK = BO_Comma; 7132 7133 // OpenMP [2.14.3.6, reduction clause] 7134 // C 7135 // reduction-identifier is either an identifier or one of the following 7136 // operators: +, -, *, &, |, ^, && and || 7137 // C++ 7138 // reduction-identifier is either an id-expression or one of the following 7139 // operators: +, -, *, &, |, ^, && and || 7140 // FIXME: Only 'min' and 'max' identifiers are supported for now. 7141 switch (OOK) { 7142 case OO_Plus: 7143 case OO_Minus: 7144 BOK = BO_Add; 7145 break; 7146 case OO_Star: 7147 BOK = BO_Mul; 7148 break; 7149 case OO_Amp: 7150 BOK = BO_And; 7151 break; 7152 case OO_Pipe: 7153 BOK = BO_Or; 7154 break; 7155 case OO_Caret: 7156 BOK = BO_Xor; 7157 break; 7158 case OO_AmpAmp: 7159 BOK = BO_LAnd; 7160 break; 7161 case OO_PipePipe: 7162 BOK = BO_LOr; 7163 break; 7164 case OO_New: 7165 case OO_Delete: 7166 case OO_Array_New: 7167 case OO_Array_Delete: 7168 case OO_Slash: 7169 case OO_Percent: 7170 case OO_Tilde: 7171 case OO_Exclaim: 7172 case OO_Equal: 7173 case OO_Less: 7174 case OO_Greater: 7175 case OO_LessEqual: 7176 case OO_GreaterEqual: 7177 case OO_PlusEqual: 7178 case OO_MinusEqual: 7179 case OO_StarEqual: 7180 case OO_SlashEqual: 7181 case OO_PercentEqual: 7182 case OO_CaretEqual: 7183 case OO_AmpEqual: 7184 case OO_PipeEqual: 7185 case OO_LessLess: 7186 case OO_GreaterGreater: 7187 case OO_LessLessEqual: 7188 case OO_GreaterGreaterEqual: 7189 case OO_EqualEqual: 7190 case OO_ExclaimEqual: 7191 case OO_PlusPlus: 7192 case OO_MinusMinus: 7193 case OO_Comma: 7194 case OO_ArrowStar: 7195 case OO_Arrow: 7196 case OO_Call: 7197 case OO_Subscript: 7198 case OO_Conditional: 7199 case OO_Coawait: 7200 case NUM_OVERLOADED_OPERATORS: 7201 llvm_unreachable("Unexpected reduction identifier"); 7202 case OO_None: 7203 if (auto II = DN.getAsIdentifierInfo()) { 7204 if (II->isStr("max")) 7205 BOK = BO_GT; 7206 else if (II->isStr("min")) 7207 BOK = BO_LT; 7208 } 7209 break; 7210 } 7211 SourceRange ReductionIdRange; 7212 if (ReductionIdScopeSpec.isValid()) { 7213 ReductionIdRange.setBegin(ReductionIdScopeSpec.getBeginLoc()); 7214 } 7215 ReductionIdRange.setEnd(ReductionId.getEndLoc()); 7216 if (BOK == BO_Comma) { 7217 // Not allowed reduction identifier is found. 7218 Diag(ReductionId.getLocStart(), diag::err_omp_unknown_reduction_identifier) 7219 << ReductionIdRange; 7220 return nullptr; 7221 } 7222 7223 SmallVector<Expr *, 8> Vars; 7224 SmallVector<Expr *, 8> Privates; 7225 SmallVector<Expr *, 8> LHSs; 7226 SmallVector<Expr *, 8> RHSs; 7227 SmallVector<Expr *, 8> ReductionOps; 7228 for (auto RefExpr : VarList) { 7229 assert(RefExpr && "nullptr expr in OpenMP reduction clause."); 7230 if (isa<DependentScopeDeclRefExpr>(RefExpr)) { 7231 // It will be analyzed later. 7232 Vars.push_back(RefExpr); 7233 Privates.push_back(nullptr); 7234 LHSs.push_back(nullptr); 7235 RHSs.push_back(nullptr); 7236 ReductionOps.push_back(nullptr); 7237 continue; 7238 } 7239 7240 if (RefExpr->isTypeDependent() || RefExpr->isValueDependent() || 7241 RefExpr->isInstantiationDependent() || 7242 RefExpr->containsUnexpandedParameterPack()) { 7243 // It will be analyzed later. 7244 Vars.push_back(RefExpr); 7245 Privates.push_back(nullptr); 7246 LHSs.push_back(nullptr); 7247 RHSs.push_back(nullptr); 7248 ReductionOps.push_back(nullptr); 7249 continue; 7250 } 7251 7252 auto ELoc = RefExpr->getExprLoc(); 7253 auto ERange = RefExpr->getSourceRange(); 7254 // OpenMP [2.1, C/C++] 7255 // A list item is a variable or array section, subject to the restrictions 7256 // specified in Section 2.4 on page 42 and in each of the sections 7257 // describing clauses and directives for which a list appears. 7258 // OpenMP [2.14.3.3, Restrictions, p.1] 7259 // A variable that is part of another variable (as an array or 7260 // structure element) cannot appear in a private clause. 7261 auto *DE = dyn_cast<DeclRefExpr>(RefExpr); 7262 auto *ASE = dyn_cast<ArraySubscriptExpr>(RefExpr); 7263 auto *OASE = dyn_cast<OMPArraySectionExpr>(RefExpr); 7264 if (!ASE && !OASE && (!DE || !isa<VarDecl>(DE->getDecl()))) { 7265 Diag(ELoc, diag::err_omp_expected_var_name_or_array_item) << ERange; 7266 continue; 7267 } 7268 QualType Type; 7269 VarDecl *VD = nullptr; 7270 if (DE) { 7271 auto D = DE->getDecl(); 7272 VD = cast<VarDecl>(D); 7273 Type = VD->getType(); 7274 } else if (ASE) { 7275 Type = ASE->getType(); 7276 auto *Base = ASE->getBase()->IgnoreParenImpCasts(); 7277 while (auto *TempASE = dyn_cast<ArraySubscriptExpr>(Base)) 7278 Base = TempASE->getBase()->IgnoreParenImpCasts(); 7279 DE = dyn_cast<DeclRefExpr>(Base); 7280 if (DE) 7281 VD = dyn_cast<VarDecl>(DE->getDecl()); 7282 if (!VD) { 7283 Diag(Base->getExprLoc(), diag::err_omp_expected_base_var_name) 7284 << 0 << Base->getSourceRange(); 7285 continue; 7286 } 7287 } else if (OASE) { 7288 auto BaseType = OMPArraySectionExpr::getBaseOriginalType(OASE->getBase()); 7289 if (auto *ATy = BaseType->getAsArrayTypeUnsafe()) 7290 Type = ATy->getElementType(); 7291 else 7292 Type = BaseType->getPointeeType(); 7293 auto *Base = OASE->getBase()->IgnoreParenImpCasts(); 7294 while (auto *TempOASE = dyn_cast<OMPArraySectionExpr>(Base)) 7295 Base = TempOASE->getBase()->IgnoreParenImpCasts(); 7296 while (auto *TempASE = dyn_cast<ArraySubscriptExpr>(Base)) 7297 Base = TempASE->getBase()->IgnoreParenImpCasts(); 7298 DE = dyn_cast<DeclRefExpr>(Base); 7299 if (DE) 7300 VD = dyn_cast<VarDecl>(DE->getDecl()); 7301 if (!VD) { 7302 Diag(Base->getExprLoc(), diag::err_omp_expected_base_var_name) 7303 << 1 << Base->getSourceRange(); 7304 continue; 7305 } 7306 } 7307 7308 // OpenMP [2.9.3.3, Restrictions, C/C++, p.3] 7309 // A variable that appears in a private clause must not have an incomplete 7310 // type or a reference type. 7311 if (RequireCompleteType(ELoc, Type, 7312 diag::err_omp_reduction_incomplete_type)) 7313 continue; 7314 // OpenMP [2.14.3.6, reduction clause, Restrictions] 7315 // Arrays may not appear in a reduction clause. 7316 if (Type.getNonReferenceType()->isArrayType()) { 7317 Diag(ELoc, diag::err_omp_reduction_type_array) << Type << ERange; 7318 if (!ASE && !OASE) { 7319 bool IsDecl = VD->isThisDeclarationADefinition(Context) == 7320 VarDecl::DeclarationOnly; 7321 Diag(VD->getLocation(), 7322 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 7323 << VD; 7324 } 7325 continue; 7326 } 7327 // OpenMP [2.14.3.6, reduction clause, Restrictions] 7328 // A list item that appears in a reduction clause must not be 7329 // const-qualified. 7330 if (Type.getNonReferenceType().isConstant(Context)) { 7331 Diag(ELoc, diag::err_omp_const_reduction_list_item) 7332 << getOpenMPClauseName(OMPC_reduction) << Type << ERange; 7333 if (!ASE && !OASE) { 7334 bool IsDecl = VD->isThisDeclarationADefinition(Context) == 7335 VarDecl::DeclarationOnly; 7336 Diag(VD->getLocation(), 7337 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 7338 << VD; 7339 } 7340 continue; 7341 } 7342 // OpenMP [2.9.3.6, Restrictions, C/C++, p.4] 7343 // If a list-item is a reference type then it must bind to the same object 7344 // for all threads of the team. 7345 if (!ASE && !OASE) { 7346 VarDecl *VDDef = VD->getDefinition(); 7347 if (Type->isReferenceType() && VDDef) { 7348 DSARefChecker Check(DSAStack); 7349 if (Check.Visit(VDDef->getInit())) { 7350 Diag(ELoc, diag::err_omp_reduction_ref_type_arg) << ERange; 7351 Diag(VDDef->getLocation(), diag::note_defined_here) << VDDef; 7352 continue; 7353 } 7354 } 7355 } 7356 // OpenMP [2.14.3.6, reduction clause, Restrictions] 7357 // The type of a list item that appears in a reduction clause must be valid 7358 // for the reduction-identifier. For a max or min reduction in C, the type 7359 // of the list item must be an allowed arithmetic data type: char, int, 7360 // float, double, or _Bool, possibly modified with long, short, signed, or 7361 // unsigned. For a max or min reduction in C++, the type of the list item 7362 // must be an allowed arithmetic data type: char, wchar_t, int, float, 7363 // double, or bool, possibly modified with long, short, signed, or unsigned. 7364 if ((BOK == BO_GT || BOK == BO_LT) && 7365 !(Type->isScalarType() || 7366 (getLangOpts().CPlusPlus && Type->isArithmeticType()))) { 7367 Diag(ELoc, diag::err_omp_clause_not_arithmetic_type_arg) 7368 << getLangOpts().CPlusPlus; 7369 if (!ASE && !OASE) { 7370 bool IsDecl = VD->isThisDeclarationADefinition(Context) == 7371 VarDecl::DeclarationOnly; 7372 Diag(VD->getLocation(), 7373 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 7374 << VD; 7375 } 7376 continue; 7377 } 7378 if ((BOK == BO_OrAssign || BOK == BO_AndAssign || BOK == BO_XorAssign) && 7379 !getLangOpts().CPlusPlus && Type->isFloatingType()) { 7380 Diag(ELoc, diag::err_omp_clause_floating_type_arg); 7381 if (!ASE && !OASE) { 7382 bool IsDecl = VD->isThisDeclarationADefinition(Context) == 7383 VarDecl::DeclarationOnly; 7384 Diag(VD->getLocation(), 7385 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 7386 << VD; 7387 } 7388 continue; 7389 } 7390 // OpenMP [2.14.1.1, Data-sharing Attribute Rules for Variables Referenced 7391 // in a Construct] 7392 // Variables with the predetermined data-sharing attributes may not be 7393 // listed in data-sharing attributes clauses, except for the cases 7394 // listed below. For these exceptions only, listing a predetermined 7395 // variable in a data-sharing attribute clause is allowed and overrides 7396 // the variable's predetermined data-sharing attributes. 7397 // OpenMP [2.14.3.6, Restrictions, p.3] 7398 // Any number of reduction clauses can be specified on the directive, 7399 // but a list item can appear only once in the reduction clauses for that 7400 // directive. 7401 DSAStackTy::DSAVarData DVar; 7402 DVar = DSAStack->getTopDSA(VD, false); 7403 if (DVar.CKind == OMPC_reduction) { 7404 Diag(ELoc, diag::err_omp_once_referenced) 7405 << getOpenMPClauseName(OMPC_reduction); 7406 if (DVar.RefExpr) { 7407 Diag(DVar.RefExpr->getExprLoc(), diag::note_omp_referenced); 7408 } 7409 } else if (DVar.CKind != OMPC_unknown) { 7410 Diag(ELoc, diag::err_omp_wrong_dsa) 7411 << getOpenMPClauseName(DVar.CKind) 7412 << getOpenMPClauseName(OMPC_reduction); 7413 ReportOriginalDSA(*this, DSAStack, VD, DVar); 7414 continue; 7415 } 7416 7417 // OpenMP [2.14.3.6, Restrictions, p.1] 7418 // A list item that appears in a reduction clause of a worksharing 7419 // construct must be shared in the parallel regions to which any of the 7420 // worksharing regions arising from the worksharing construct bind. 7421 OpenMPDirectiveKind CurrDir = DSAStack->getCurrentDirective(); 7422 if (isOpenMPWorksharingDirective(CurrDir) && 7423 !isOpenMPParallelDirective(CurrDir)) { 7424 DVar = DSAStack->getImplicitDSA(VD, true); 7425 if (DVar.CKind != OMPC_shared) { 7426 Diag(ELoc, diag::err_omp_required_access) 7427 << getOpenMPClauseName(OMPC_reduction) 7428 << getOpenMPClauseName(OMPC_shared); 7429 ReportOriginalDSA(*this, DSAStack, VD, DVar); 7430 continue; 7431 } 7432 } 7433 7434 Type = Type.getNonLValueExprType(Context).getUnqualifiedType(); 7435 auto *LHSVD = buildVarDecl(*this, ELoc, Type, ".reduction.lhs", 7436 VD->hasAttrs() ? &VD->getAttrs() : nullptr); 7437 auto *RHSVD = buildVarDecl(*this, ELoc, Type, VD->getName(), 7438 VD->hasAttrs() ? &VD->getAttrs() : nullptr); 7439 auto PrivateTy = Type; 7440 if (OASE) { 7441 // For array sections only: 7442 // Create pseudo array type for private copy. The size for this array will 7443 // be generated during codegen. 7444 // For array subscripts or single variables Private Ty is the same as Type 7445 // (type of the variable or single array element). 7446 PrivateTy = Context.getVariableArrayType( 7447 Type, new (Context) OpaqueValueExpr(SourceLocation(), 7448 Context.getSizeType(), VK_RValue), 7449 ArrayType::Normal, /*IndexTypeQuals=*/0, SourceRange()); 7450 } 7451 // Private copy. 7452 auto *PrivateVD = buildVarDecl(*this, ELoc, PrivateTy, VD->getName(), 7453 VD->hasAttrs() ? &VD->getAttrs() : nullptr); 7454 // Add initializer for private variable. 7455 Expr *Init = nullptr; 7456 switch (BOK) { 7457 case BO_Add: 7458 case BO_Xor: 7459 case BO_Or: 7460 case BO_LOr: 7461 // '+', '-', '^', '|', '||' reduction ops - initializer is '0'. 7462 if (Type->isScalarType() || Type->isAnyComplexType()) { 7463 Init = ActOnIntegerConstant(ELoc, /*Val=*/0).get(); 7464 } 7465 break; 7466 case BO_Mul: 7467 case BO_LAnd: 7468 if (Type->isScalarType() || Type->isAnyComplexType()) { 7469 // '*' and '&&' reduction ops - initializer is '1'. 7470 Init = ActOnIntegerConstant(ELoc, /*Val=*/1).get(); 7471 } 7472 break; 7473 case BO_And: { 7474 // '&' reduction op - initializer is '~0'. 7475 QualType OrigType = Type; 7476 if (auto *ComplexTy = OrigType->getAs<ComplexType>()) { 7477 Type = ComplexTy->getElementType(); 7478 } 7479 if (Type->isRealFloatingType()) { 7480 llvm::APFloat InitValue = 7481 llvm::APFloat::getAllOnesValue(Context.getTypeSize(Type), 7482 /*isIEEE=*/true); 7483 Init = FloatingLiteral::Create(Context, InitValue, /*isexact=*/true, 7484 Type, ELoc); 7485 } else if (Type->isScalarType()) { 7486 auto Size = Context.getTypeSize(Type); 7487 QualType IntTy = Context.getIntTypeForBitwidth(Size, /*Signed=*/0); 7488 llvm::APInt InitValue = llvm::APInt::getAllOnesValue(Size); 7489 Init = IntegerLiteral::Create(Context, InitValue, IntTy, ELoc); 7490 } 7491 if (Init && OrigType->isAnyComplexType()) { 7492 // Init = 0xFFFF + 0xFFFFi; 7493 auto *Im = new (Context) ImaginaryLiteral(Init, OrigType); 7494 Init = CreateBuiltinBinOp(ELoc, BO_Add, Init, Im).get(); 7495 } 7496 Type = OrigType; 7497 break; 7498 } 7499 case BO_LT: 7500 case BO_GT: { 7501 // 'min' reduction op - initializer is 'Largest representable number in 7502 // the reduction list item type'. 7503 // 'max' reduction op - initializer is 'Least representable number in 7504 // the reduction list item type'. 7505 if (Type->isIntegerType() || Type->isPointerType()) { 7506 bool IsSigned = Type->hasSignedIntegerRepresentation(); 7507 auto Size = Context.getTypeSize(Type); 7508 QualType IntTy = 7509 Context.getIntTypeForBitwidth(Size, /*Signed=*/IsSigned); 7510 llvm::APInt InitValue = 7511 (BOK != BO_LT) 7512 ? IsSigned ? llvm::APInt::getSignedMinValue(Size) 7513 : llvm::APInt::getMinValue(Size) 7514 : IsSigned ? llvm::APInt::getSignedMaxValue(Size) 7515 : llvm::APInt::getMaxValue(Size); 7516 Init = IntegerLiteral::Create(Context, InitValue, IntTy, ELoc); 7517 if (Type->isPointerType()) { 7518 // Cast to pointer type. 7519 auto CastExpr = BuildCStyleCastExpr( 7520 SourceLocation(), Context.getTrivialTypeSourceInfo(Type, ELoc), 7521 SourceLocation(), Init); 7522 if (CastExpr.isInvalid()) 7523 continue; 7524 Init = CastExpr.get(); 7525 } 7526 } else if (Type->isRealFloatingType()) { 7527 llvm::APFloat InitValue = llvm::APFloat::getLargest( 7528 Context.getFloatTypeSemantics(Type), BOK != BO_LT); 7529 Init = FloatingLiteral::Create(Context, InitValue, /*isexact=*/true, 7530 Type, ELoc); 7531 } 7532 break; 7533 } 7534 case BO_PtrMemD: 7535 case BO_PtrMemI: 7536 case BO_MulAssign: 7537 case BO_Div: 7538 case BO_Rem: 7539 case BO_Sub: 7540 case BO_Shl: 7541 case BO_Shr: 7542 case BO_LE: 7543 case BO_GE: 7544 case BO_EQ: 7545 case BO_NE: 7546 case BO_AndAssign: 7547 case BO_XorAssign: 7548 case BO_OrAssign: 7549 case BO_Assign: 7550 case BO_AddAssign: 7551 case BO_SubAssign: 7552 case BO_DivAssign: 7553 case BO_RemAssign: 7554 case BO_ShlAssign: 7555 case BO_ShrAssign: 7556 case BO_Comma: 7557 llvm_unreachable("Unexpected reduction operation"); 7558 } 7559 if (Init) { 7560 AddInitializerToDecl(RHSVD, Init, /*DirectInit=*/false, 7561 /*TypeMayContainAuto=*/false); 7562 } else 7563 ActOnUninitializedDecl(RHSVD, /*TypeMayContainAuto=*/false); 7564 if (!RHSVD->hasInit()) { 7565 Diag(ELoc, diag::err_omp_reduction_id_not_compatible) << Type 7566 << ReductionIdRange; 7567 if (VD) { 7568 bool IsDecl = VD->isThisDeclarationADefinition(Context) == 7569 VarDecl::DeclarationOnly; 7570 Diag(VD->getLocation(), 7571 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 7572 << VD; 7573 } 7574 continue; 7575 } 7576 // Store initializer for single element in private copy. Will be used during 7577 // codegen. 7578 PrivateVD->setInit(RHSVD->getInit()); 7579 PrivateVD->setInitStyle(RHSVD->getInitStyle()); 7580 auto *LHSDRE = buildDeclRefExpr(*this, LHSVD, Type, ELoc); 7581 auto *RHSDRE = buildDeclRefExpr(*this, RHSVD, Type, ELoc); 7582 auto *PrivateDRE = buildDeclRefExpr(*this, PrivateVD, PrivateTy, ELoc); 7583 ExprResult ReductionOp = 7584 BuildBinOp(DSAStack->getCurScope(), ReductionId.getLocStart(), BOK, 7585 LHSDRE, RHSDRE); 7586 if (ReductionOp.isUsable()) { 7587 if (BOK != BO_LT && BOK != BO_GT) { 7588 ReductionOp = 7589 BuildBinOp(DSAStack->getCurScope(), ReductionId.getLocStart(), 7590 BO_Assign, LHSDRE, ReductionOp.get()); 7591 } else { 7592 auto *ConditionalOp = new (Context) ConditionalOperator( 7593 ReductionOp.get(), SourceLocation(), LHSDRE, SourceLocation(), 7594 RHSDRE, Type, VK_LValue, OK_Ordinary); 7595 ReductionOp = 7596 BuildBinOp(DSAStack->getCurScope(), ReductionId.getLocStart(), 7597 BO_Assign, LHSDRE, ConditionalOp); 7598 } 7599 ReductionOp = ActOnFinishFullExpr(ReductionOp.get()); 7600 } 7601 if (ReductionOp.isInvalid()) 7602 continue; 7603 7604 DSAStack->addDSA(VD, DE, OMPC_reduction); 7605 Vars.push_back(RefExpr); 7606 Privates.push_back(PrivateDRE); 7607 LHSs.push_back(LHSDRE); 7608 RHSs.push_back(RHSDRE); 7609 ReductionOps.push_back(ReductionOp.get()); 7610 } 7611 7612 if (Vars.empty()) 7613 return nullptr; 7614 7615 return OMPReductionClause::Create( 7616 Context, StartLoc, LParenLoc, ColonLoc, EndLoc, Vars, 7617 ReductionIdScopeSpec.getWithLocInContext(Context), ReductionId, Privates, 7618 LHSs, RHSs, ReductionOps); 7619 } 7620 7621 OMPClause *Sema::ActOnOpenMPLinearClause( 7622 ArrayRef<Expr *> VarList, Expr *Step, SourceLocation StartLoc, 7623 SourceLocation LParenLoc, OpenMPLinearClauseKind LinKind, 7624 SourceLocation LinLoc, SourceLocation ColonLoc, SourceLocation EndLoc) { 7625 SmallVector<Expr *, 8> Vars; 7626 SmallVector<Expr *, 8> Privates; 7627 SmallVector<Expr *, 8> Inits; 7628 if ((!LangOpts.CPlusPlus && LinKind != OMPC_LINEAR_val) || 7629 LinKind == OMPC_LINEAR_unknown) { 7630 Diag(LinLoc, diag::err_omp_wrong_linear_modifier) << LangOpts.CPlusPlus; 7631 LinKind = OMPC_LINEAR_val; 7632 } 7633 for (auto &RefExpr : VarList) { 7634 assert(RefExpr && "NULL expr in OpenMP linear clause."); 7635 if (isa<DependentScopeDeclRefExpr>(RefExpr)) { 7636 // It will be analyzed later. 7637 Vars.push_back(RefExpr); 7638 Privates.push_back(nullptr); 7639 Inits.push_back(nullptr); 7640 continue; 7641 } 7642 7643 // OpenMP [2.14.3.7, linear clause] 7644 // A list item that appears in a linear clause is subject to the private 7645 // clause semantics described in Section 2.14.3.3 on page 159 except as 7646 // noted. In addition, the value of the new list item on each iteration 7647 // of the associated loop(s) corresponds to the value of the original 7648 // list item before entering the construct plus the logical number of 7649 // the iteration times linear-step. 7650 7651 SourceLocation ELoc = RefExpr->getExprLoc(); 7652 // OpenMP [2.1, C/C++] 7653 // A list item is a variable name. 7654 // OpenMP [2.14.3.3, Restrictions, p.1] 7655 // A variable that is part of another variable (as an array or 7656 // structure element) cannot appear in a private clause. 7657 DeclRefExpr *DE = dyn_cast<DeclRefExpr>(RefExpr); 7658 if (!DE || !isa<VarDecl>(DE->getDecl())) { 7659 Diag(ELoc, diag::err_omp_expected_var_name) << RefExpr->getSourceRange(); 7660 continue; 7661 } 7662 7663 VarDecl *VD = cast<VarDecl>(DE->getDecl()); 7664 7665 // OpenMP [2.14.3.7, linear clause] 7666 // A list-item cannot appear in more than one linear clause. 7667 // A list-item that appears in a linear clause cannot appear in any 7668 // other data-sharing attribute clause. 7669 DSAStackTy::DSAVarData DVar = DSAStack->getTopDSA(VD, false); 7670 if (DVar.RefExpr) { 7671 Diag(ELoc, diag::err_omp_wrong_dsa) << getOpenMPClauseName(DVar.CKind) 7672 << getOpenMPClauseName(OMPC_linear); 7673 ReportOriginalDSA(*this, DSAStack, VD, DVar); 7674 continue; 7675 } 7676 7677 QualType QType = VD->getType(); 7678 if (QType->isDependentType() || QType->isInstantiationDependentType()) { 7679 // It will be analyzed later. 7680 Vars.push_back(DE); 7681 Privates.push_back(nullptr); 7682 Inits.push_back(nullptr); 7683 continue; 7684 } 7685 7686 // A variable must not have an incomplete type or a reference type. 7687 if (RequireCompleteType(ELoc, QType, 7688 diag::err_omp_linear_incomplete_type)) { 7689 continue; 7690 } 7691 if ((LinKind == OMPC_LINEAR_uval || LinKind == OMPC_LINEAR_ref) && 7692 !QType->isReferenceType()) { 7693 Diag(ELoc, diag::err_omp_wrong_linear_modifier_non_reference) 7694 << QType << getOpenMPSimpleClauseTypeName(OMPC_linear, LinKind); 7695 continue; 7696 } 7697 QType = QType.getNonReferenceType(); 7698 7699 // A list item must not be const-qualified. 7700 if (QType.isConstant(Context)) { 7701 Diag(ELoc, diag::err_omp_const_variable) 7702 << getOpenMPClauseName(OMPC_linear); 7703 bool IsDecl = 7704 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 7705 Diag(VD->getLocation(), 7706 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 7707 << VD; 7708 continue; 7709 } 7710 7711 // A list item must be of integral or pointer type. 7712 QType = QType.getUnqualifiedType().getCanonicalType(); 7713 const Type *Ty = QType.getTypePtrOrNull(); 7714 if (!Ty || (!Ty->isDependentType() && !Ty->isIntegralType(Context) && 7715 !Ty->isPointerType())) { 7716 Diag(ELoc, diag::err_omp_linear_expected_int_or_ptr) << QType; 7717 bool IsDecl = 7718 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 7719 Diag(VD->getLocation(), 7720 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 7721 << VD; 7722 continue; 7723 } 7724 7725 // Build private copy of original var. 7726 auto *Private = buildVarDecl(*this, ELoc, QType, VD->getName(), 7727 VD->hasAttrs() ? &VD->getAttrs() : nullptr); 7728 auto *PrivateRef = buildDeclRefExpr( 7729 *this, Private, DE->getType().getUnqualifiedType(), DE->getExprLoc()); 7730 // Build var to save initial value. 7731 VarDecl *Init = buildVarDecl(*this, ELoc, QType, ".linear.start"); 7732 Expr *InitExpr; 7733 if (LinKind == OMPC_LINEAR_uval) 7734 InitExpr = VD->getInit(); 7735 else 7736 InitExpr = DE; 7737 AddInitializerToDecl(Init, DefaultLvalueConversion(InitExpr).get(), 7738 /*DirectInit*/ false, /*TypeMayContainAuto*/ false); 7739 auto InitRef = buildDeclRefExpr( 7740 *this, Init, DE->getType().getUnqualifiedType(), DE->getExprLoc()); 7741 DSAStack->addDSA(VD, DE, OMPC_linear); 7742 Vars.push_back(DE); 7743 Privates.push_back(PrivateRef); 7744 Inits.push_back(InitRef); 7745 } 7746 7747 if (Vars.empty()) 7748 return nullptr; 7749 7750 Expr *StepExpr = Step; 7751 Expr *CalcStepExpr = nullptr; 7752 if (Step && !Step->isValueDependent() && !Step->isTypeDependent() && 7753 !Step->isInstantiationDependent() && 7754 !Step->containsUnexpandedParameterPack()) { 7755 SourceLocation StepLoc = Step->getLocStart(); 7756 ExprResult Val = PerformOpenMPImplicitIntegerConversion(StepLoc, Step); 7757 if (Val.isInvalid()) 7758 return nullptr; 7759 StepExpr = Val.get(); 7760 7761 // Build var to save the step value. 7762 VarDecl *SaveVar = 7763 buildVarDecl(*this, StepLoc, StepExpr->getType(), ".linear.step"); 7764 ExprResult SaveRef = 7765 buildDeclRefExpr(*this, SaveVar, StepExpr->getType(), StepLoc); 7766 ExprResult CalcStep = 7767 BuildBinOp(CurScope, StepLoc, BO_Assign, SaveRef.get(), StepExpr); 7768 CalcStep = ActOnFinishFullExpr(CalcStep.get()); 7769 7770 // Warn about zero linear step (it would be probably better specified as 7771 // making corresponding variables 'const'). 7772 llvm::APSInt Result; 7773 bool IsConstant = StepExpr->isIntegerConstantExpr(Result, Context); 7774 if (IsConstant && !Result.isNegative() && !Result.isStrictlyPositive()) 7775 Diag(StepLoc, diag::warn_omp_linear_step_zero) << Vars[0] 7776 << (Vars.size() > 1); 7777 if (!IsConstant && CalcStep.isUsable()) { 7778 // Calculate the step beforehand instead of doing this on each iteration. 7779 // (This is not used if the number of iterations may be kfold-ed). 7780 CalcStepExpr = CalcStep.get(); 7781 } 7782 } 7783 7784 return OMPLinearClause::Create(Context, StartLoc, LParenLoc, LinKind, LinLoc, 7785 ColonLoc, EndLoc, Vars, Privates, Inits, 7786 StepExpr, CalcStepExpr); 7787 } 7788 7789 static bool FinishOpenMPLinearClause(OMPLinearClause &Clause, DeclRefExpr *IV, 7790 Expr *NumIterations, Sema &SemaRef, 7791 Scope *S) { 7792 // Walk the vars and build update/final expressions for the CodeGen. 7793 SmallVector<Expr *, 8> Updates; 7794 SmallVector<Expr *, 8> Finals; 7795 Expr *Step = Clause.getStep(); 7796 Expr *CalcStep = Clause.getCalcStep(); 7797 // OpenMP [2.14.3.7, linear clause] 7798 // If linear-step is not specified it is assumed to be 1. 7799 if (Step == nullptr) 7800 Step = SemaRef.ActOnIntegerConstant(SourceLocation(), 1).get(); 7801 else if (CalcStep) 7802 Step = cast<BinaryOperator>(CalcStep)->getLHS(); 7803 bool HasErrors = false; 7804 auto CurInit = Clause.inits().begin(); 7805 auto CurPrivate = Clause.privates().begin(); 7806 auto LinKind = Clause.getModifier(); 7807 for (auto &RefExpr : Clause.varlists()) { 7808 Expr *InitExpr = *CurInit; 7809 7810 // Build privatized reference to the current linear var. 7811 auto DE = cast<DeclRefExpr>(RefExpr); 7812 Expr *CapturedRef; 7813 if (LinKind == OMPC_LINEAR_uval) 7814 CapturedRef = cast<VarDecl>(DE->getDecl())->getInit(); 7815 else 7816 CapturedRef = 7817 buildDeclRefExpr(SemaRef, cast<VarDecl>(DE->getDecl()), 7818 DE->getType().getUnqualifiedType(), DE->getExprLoc(), 7819 /*RefersToCapture=*/true); 7820 7821 // Build update: Var = InitExpr + IV * Step 7822 ExprResult Update = 7823 BuildCounterUpdate(SemaRef, S, RefExpr->getExprLoc(), *CurPrivate, 7824 InitExpr, IV, Step, /* Subtract */ false); 7825 Update = SemaRef.ActOnFinishFullExpr(Update.get(), DE->getLocStart(), 7826 /*DiscardedValue=*/true); 7827 7828 // Build final: Var = InitExpr + NumIterations * Step 7829 ExprResult Final = 7830 BuildCounterUpdate(SemaRef, S, RefExpr->getExprLoc(), CapturedRef, 7831 InitExpr, NumIterations, Step, /* Subtract */ false); 7832 Final = SemaRef.ActOnFinishFullExpr(Final.get(), DE->getLocStart(), 7833 /*DiscardedValue=*/true); 7834 if (!Update.isUsable() || !Final.isUsable()) { 7835 Updates.push_back(nullptr); 7836 Finals.push_back(nullptr); 7837 HasErrors = true; 7838 } else { 7839 Updates.push_back(Update.get()); 7840 Finals.push_back(Final.get()); 7841 } 7842 ++CurInit, ++CurPrivate; 7843 } 7844 Clause.setUpdates(Updates); 7845 Clause.setFinals(Finals); 7846 return HasErrors; 7847 } 7848 7849 OMPClause *Sema::ActOnOpenMPAlignedClause( 7850 ArrayRef<Expr *> VarList, Expr *Alignment, SourceLocation StartLoc, 7851 SourceLocation LParenLoc, SourceLocation ColonLoc, SourceLocation EndLoc) { 7852 7853 SmallVector<Expr *, 8> Vars; 7854 for (auto &RefExpr : VarList) { 7855 assert(RefExpr && "NULL expr in OpenMP aligned clause."); 7856 if (isa<DependentScopeDeclRefExpr>(RefExpr)) { 7857 // It will be analyzed later. 7858 Vars.push_back(RefExpr); 7859 continue; 7860 } 7861 7862 SourceLocation ELoc = RefExpr->getExprLoc(); 7863 // OpenMP [2.1, C/C++] 7864 // A list item is a variable name. 7865 DeclRefExpr *DE = dyn_cast<DeclRefExpr>(RefExpr); 7866 if (!DE || !isa<VarDecl>(DE->getDecl())) { 7867 Diag(ELoc, diag::err_omp_expected_var_name) << RefExpr->getSourceRange(); 7868 continue; 7869 } 7870 7871 VarDecl *VD = cast<VarDecl>(DE->getDecl()); 7872 7873 // OpenMP [2.8.1, simd construct, Restrictions] 7874 // The type of list items appearing in the aligned clause must be 7875 // array, pointer, reference to array, or reference to pointer. 7876 QualType QType = VD->getType(); 7877 QType = QType.getNonReferenceType().getUnqualifiedType().getCanonicalType(); 7878 const Type *Ty = QType.getTypePtrOrNull(); 7879 if (!Ty || (!Ty->isDependentType() && !Ty->isArrayType() && 7880 !Ty->isPointerType())) { 7881 Diag(ELoc, diag::err_omp_aligned_expected_array_or_ptr) 7882 << QType << getLangOpts().CPlusPlus << RefExpr->getSourceRange(); 7883 bool IsDecl = 7884 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 7885 Diag(VD->getLocation(), 7886 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 7887 << VD; 7888 continue; 7889 } 7890 7891 // OpenMP [2.8.1, simd construct, Restrictions] 7892 // A list-item cannot appear in more than one aligned clause. 7893 if (DeclRefExpr *PrevRef = DSAStack->addUniqueAligned(VD, DE)) { 7894 Diag(ELoc, diag::err_omp_aligned_twice) << RefExpr->getSourceRange(); 7895 Diag(PrevRef->getExprLoc(), diag::note_omp_explicit_dsa) 7896 << getOpenMPClauseName(OMPC_aligned); 7897 continue; 7898 } 7899 7900 Vars.push_back(DE); 7901 } 7902 7903 // OpenMP [2.8.1, simd construct, Description] 7904 // The parameter of the aligned clause, alignment, must be a constant 7905 // positive integer expression. 7906 // If no optional parameter is specified, implementation-defined default 7907 // alignments for SIMD instructions on the target platforms are assumed. 7908 if (Alignment != nullptr) { 7909 ExprResult AlignResult = 7910 VerifyPositiveIntegerConstantInClause(Alignment, OMPC_aligned); 7911 if (AlignResult.isInvalid()) 7912 return nullptr; 7913 Alignment = AlignResult.get(); 7914 } 7915 if (Vars.empty()) 7916 return nullptr; 7917 7918 return OMPAlignedClause::Create(Context, StartLoc, LParenLoc, ColonLoc, 7919 EndLoc, Vars, Alignment); 7920 } 7921 7922 OMPClause *Sema::ActOnOpenMPCopyinClause(ArrayRef<Expr *> VarList, 7923 SourceLocation StartLoc, 7924 SourceLocation LParenLoc, 7925 SourceLocation EndLoc) { 7926 SmallVector<Expr *, 8> Vars; 7927 SmallVector<Expr *, 8> SrcExprs; 7928 SmallVector<Expr *, 8> DstExprs; 7929 SmallVector<Expr *, 8> AssignmentOps; 7930 for (auto &RefExpr : VarList) { 7931 assert(RefExpr && "NULL expr in OpenMP copyin clause."); 7932 if (isa<DependentScopeDeclRefExpr>(RefExpr)) { 7933 // It will be analyzed later. 7934 Vars.push_back(RefExpr); 7935 SrcExprs.push_back(nullptr); 7936 DstExprs.push_back(nullptr); 7937 AssignmentOps.push_back(nullptr); 7938 continue; 7939 } 7940 7941 SourceLocation ELoc = RefExpr->getExprLoc(); 7942 // OpenMP [2.1, C/C++] 7943 // A list item is a variable name. 7944 // OpenMP [2.14.4.1, Restrictions, p.1] 7945 // A list item that appears in a copyin clause must be threadprivate. 7946 DeclRefExpr *DE = dyn_cast<DeclRefExpr>(RefExpr); 7947 if (!DE || !isa<VarDecl>(DE->getDecl())) { 7948 Diag(ELoc, diag::err_omp_expected_var_name) << RefExpr->getSourceRange(); 7949 continue; 7950 } 7951 7952 Decl *D = DE->getDecl(); 7953 VarDecl *VD = cast<VarDecl>(D); 7954 7955 QualType Type = VD->getType(); 7956 if (Type->isDependentType() || Type->isInstantiationDependentType()) { 7957 // It will be analyzed later. 7958 Vars.push_back(DE); 7959 SrcExprs.push_back(nullptr); 7960 DstExprs.push_back(nullptr); 7961 AssignmentOps.push_back(nullptr); 7962 continue; 7963 } 7964 7965 // OpenMP [2.14.4.1, Restrictions, C/C++, p.1] 7966 // A list item that appears in a copyin clause must be threadprivate. 7967 if (!DSAStack->isThreadPrivate(VD)) { 7968 Diag(ELoc, diag::err_omp_required_access) 7969 << getOpenMPClauseName(OMPC_copyin) 7970 << getOpenMPDirectiveName(OMPD_threadprivate); 7971 continue; 7972 } 7973 7974 // OpenMP [2.14.4.1, Restrictions, C/C++, p.2] 7975 // A variable of class type (or array thereof) that appears in a 7976 // copyin clause requires an accessible, unambiguous copy assignment 7977 // operator for the class type. 7978 auto ElemType = Context.getBaseElementType(Type).getNonReferenceType(); 7979 auto *SrcVD = 7980 buildVarDecl(*this, DE->getLocStart(), ElemType.getUnqualifiedType(), 7981 ".copyin.src", VD->hasAttrs() ? &VD->getAttrs() : nullptr); 7982 auto *PseudoSrcExpr = buildDeclRefExpr( 7983 *this, SrcVD, ElemType.getUnqualifiedType(), DE->getExprLoc()); 7984 auto *DstVD = 7985 buildVarDecl(*this, DE->getLocStart(), ElemType, ".copyin.dst", 7986 VD->hasAttrs() ? &VD->getAttrs() : nullptr); 7987 auto *PseudoDstExpr = 7988 buildDeclRefExpr(*this, DstVD, ElemType, DE->getExprLoc()); 7989 // For arrays generate assignment operation for single element and replace 7990 // it by the original array element in CodeGen. 7991 auto AssignmentOp = BuildBinOp(/*S=*/nullptr, DE->getExprLoc(), BO_Assign, 7992 PseudoDstExpr, PseudoSrcExpr); 7993 if (AssignmentOp.isInvalid()) 7994 continue; 7995 AssignmentOp = ActOnFinishFullExpr(AssignmentOp.get(), DE->getExprLoc(), 7996 /*DiscardedValue=*/true); 7997 if (AssignmentOp.isInvalid()) 7998 continue; 7999 8000 DSAStack->addDSA(VD, DE, OMPC_copyin); 8001 Vars.push_back(DE); 8002 SrcExprs.push_back(PseudoSrcExpr); 8003 DstExprs.push_back(PseudoDstExpr); 8004 AssignmentOps.push_back(AssignmentOp.get()); 8005 } 8006 8007 if (Vars.empty()) 8008 return nullptr; 8009 8010 return OMPCopyinClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars, 8011 SrcExprs, DstExprs, AssignmentOps); 8012 } 8013 8014 OMPClause *Sema::ActOnOpenMPCopyprivateClause(ArrayRef<Expr *> VarList, 8015 SourceLocation StartLoc, 8016 SourceLocation LParenLoc, 8017 SourceLocation EndLoc) { 8018 SmallVector<Expr *, 8> Vars; 8019 SmallVector<Expr *, 8> SrcExprs; 8020 SmallVector<Expr *, 8> DstExprs; 8021 SmallVector<Expr *, 8> AssignmentOps; 8022 for (auto &RefExpr : VarList) { 8023 assert(RefExpr && "NULL expr in OpenMP copyprivate clause."); 8024 if (isa<DependentScopeDeclRefExpr>(RefExpr)) { 8025 // It will be analyzed later. 8026 Vars.push_back(RefExpr); 8027 SrcExprs.push_back(nullptr); 8028 DstExprs.push_back(nullptr); 8029 AssignmentOps.push_back(nullptr); 8030 continue; 8031 } 8032 8033 SourceLocation ELoc = RefExpr->getExprLoc(); 8034 // OpenMP [2.1, C/C++] 8035 // A list item is a variable name. 8036 // OpenMP [2.14.4.1, Restrictions, p.1] 8037 // A list item that appears in a copyin clause must be threadprivate. 8038 DeclRefExpr *DE = dyn_cast<DeclRefExpr>(RefExpr); 8039 if (!DE || !isa<VarDecl>(DE->getDecl())) { 8040 Diag(ELoc, diag::err_omp_expected_var_name) << RefExpr->getSourceRange(); 8041 continue; 8042 } 8043 8044 Decl *D = DE->getDecl(); 8045 VarDecl *VD = cast<VarDecl>(D); 8046 8047 QualType Type = VD->getType(); 8048 if (Type->isDependentType() || Type->isInstantiationDependentType()) { 8049 // It will be analyzed later. 8050 Vars.push_back(DE); 8051 SrcExprs.push_back(nullptr); 8052 DstExprs.push_back(nullptr); 8053 AssignmentOps.push_back(nullptr); 8054 continue; 8055 } 8056 8057 // OpenMP [2.14.4.2, Restrictions, p.2] 8058 // A list item that appears in a copyprivate clause may not appear in a 8059 // private or firstprivate clause on the single construct. 8060 if (!DSAStack->isThreadPrivate(VD)) { 8061 auto DVar = DSAStack->getTopDSA(VD, false); 8062 if (DVar.CKind != OMPC_unknown && DVar.CKind != OMPC_copyprivate && 8063 DVar.RefExpr) { 8064 Diag(ELoc, diag::err_omp_wrong_dsa) 8065 << getOpenMPClauseName(DVar.CKind) 8066 << getOpenMPClauseName(OMPC_copyprivate); 8067 ReportOriginalDSA(*this, DSAStack, VD, DVar); 8068 continue; 8069 } 8070 8071 // OpenMP [2.11.4.2, Restrictions, p.1] 8072 // All list items that appear in a copyprivate clause must be either 8073 // threadprivate or private in the enclosing context. 8074 if (DVar.CKind == OMPC_unknown) { 8075 DVar = DSAStack->getImplicitDSA(VD, false); 8076 if (DVar.CKind == OMPC_shared) { 8077 Diag(ELoc, diag::err_omp_required_access) 8078 << getOpenMPClauseName(OMPC_copyprivate) 8079 << "threadprivate or private in the enclosing context"; 8080 ReportOriginalDSA(*this, DSAStack, VD, DVar); 8081 continue; 8082 } 8083 } 8084 } 8085 8086 // Variably modified types are not supported. 8087 if (!Type->isAnyPointerType() && Type->isVariablyModifiedType()) { 8088 Diag(ELoc, diag::err_omp_variably_modified_type_not_supported) 8089 << getOpenMPClauseName(OMPC_copyprivate) << Type 8090 << getOpenMPDirectiveName(DSAStack->getCurrentDirective()); 8091 bool IsDecl = 8092 VD->isThisDeclarationADefinition(Context) == VarDecl::DeclarationOnly; 8093 Diag(VD->getLocation(), 8094 IsDecl ? diag::note_previous_decl : diag::note_defined_here) 8095 << VD; 8096 continue; 8097 } 8098 8099 // OpenMP [2.14.4.1, Restrictions, C/C++, p.2] 8100 // A variable of class type (or array thereof) that appears in a 8101 // copyin clause requires an accessible, unambiguous copy assignment 8102 // operator for the class type. 8103 Type = Context.getBaseElementType(Type.getNonReferenceType()) 8104 .getUnqualifiedType(); 8105 auto *SrcVD = 8106 buildVarDecl(*this, DE->getLocStart(), Type, ".copyprivate.src", 8107 VD->hasAttrs() ? &VD->getAttrs() : nullptr); 8108 auto *PseudoSrcExpr = 8109 buildDeclRefExpr(*this, SrcVD, Type, DE->getExprLoc()); 8110 auto *DstVD = 8111 buildVarDecl(*this, DE->getLocStart(), Type, ".copyprivate.dst", 8112 VD->hasAttrs() ? &VD->getAttrs() : nullptr); 8113 auto *PseudoDstExpr = 8114 buildDeclRefExpr(*this, DstVD, Type, DE->getExprLoc()); 8115 auto AssignmentOp = BuildBinOp(/*S=*/nullptr, DE->getExprLoc(), BO_Assign, 8116 PseudoDstExpr, PseudoSrcExpr); 8117 if (AssignmentOp.isInvalid()) 8118 continue; 8119 AssignmentOp = ActOnFinishFullExpr(AssignmentOp.get(), DE->getExprLoc(), 8120 /*DiscardedValue=*/true); 8121 if (AssignmentOp.isInvalid()) 8122 continue; 8123 8124 // No need to mark vars as copyprivate, they are already threadprivate or 8125 // implicitly private. 8126 Vars.push_back(DE); 8127 SrcExprs.push_back(PseudoSrcExpr); 8128 DstExprs.push_back(PseudoDstExpr); 8129 AssignmentOps.push_back(AssignmentOp.get()); 8130 } 8131 8132 if (Vars.empty()) 8133 return nullptr; 8134 8135 return OMPCopyprivateClause::Create(Context, StartLoc, LParenLoc, EndLoc, 8136 Vars, SrcExprs, DstExprs, AssignmentOps); 8137 } 8138 8139 OMPClause *Sema::ActOnOpenMPFlushClause(ArrayRef<Expr *> VarList, 8140 SourceLocation StartLoc, 8141 SourceLocation LParenLoc, 8142 SourceLocation EndLoc) { 8143 if (VarList.empty()) 8144 return nullptr; 8145 8146 return OMPFlushClause::Create(Context, StartLoc, LParenLoc, EndLoc, VarList); 8147 } 8148 8149 OMPClause * 8150 Sema::ActOnOpenMPDependClause(OpenMPDependClauseKind DepKind, 8151 SourceLocation DepLoc, SourceLocation ColonLoc, 8152 ArrayRef<Expr *> VarList, SourceLocation StartLoc, 8153 SourceLocation LParenLoc, SourceLocation EndLoc) { 8154 if (DSAStack->getCurrentDirective() == OMPD_ordered && 8155 DepKind != OMPC_DEPEND_source && DepKind != OMPC_DEPEND_sink) { 8156 Diag(DepLoc, diag::err_omp_unexpected_clause_value) 8157 << "'source' or 'sink'" << getOpenMPClauseName(OMPC_depend); 8158 return nullptr; 8159 } 8160 if (DSAStack->getCurrentDirective() != OMPD_ordered && 8161 (DepKind == OMPC_DEPEND_unknown || DepKind == OMPC_DEPEND_source || 8162 DepKind == OMPC_DEPEND_sink)) { 8163 unsigned Except[] = {OMPC_DEPEND_source, OMPC_DEPEND_sink}; 8164 Diag(DepLoc, diag::err_omp_unexpected_clause_value) 8165 << getListOfPossibleValues(OMPC_depend, /*First=*/0, 8166 /*Last=*/OMPC_DEPEND_unknown, Except) 8167 << getOpenMPClauseName(OMPC_depend); 8168 return nullptr; 8169 } 8170 SmallVector<Expr *, 8> Vars; 8171 llvm::APSInt DepCounter(/*BitWidth=*/32); 8172 llvm::APSInt TotalDepCount(/*BitWidth=*/32); 8173 if (DepKind == OMPC_DEPEND_sink) { 8174 if (auto *OrderedCountExpr = DSAStack->getParentOrderedRegionParam()) { 8175 TotalDepCount = OrderedCountExpr->EvaluateKnownConstInt(Context); 8176 TotalDepCount.setIsUnsigned(/*Val=*/true); 8177 } 8178 } 8179 if ((DepKind != OMPC_DEPEND_sink && DepKind != OMPC_DEPEND_source) || 8180 DSAStack->getParentOrderedRegionParam()) { 8181 for (auto &RefExpr : VarList) { 8182 assert(RefExpr && "NULL expr in OpenMP shared clause."); 8183 if (isa<DependentScopeDeclRefExpr>(RefExpr) || 8184 (DepKind == OMPC_DEPEND_sink && CurContext->isDependentContext())) { 8185 // It will be analyzed later. 8186 Vars.push_back(RefExpr); 8187 continue; 8188 } 8189 8190 SourceLocation ELoc = RefExpr->getExprLoc(); 8191 auto *SimpleExpr = RefExpr->IgnoreParenCasts(); 8192 if (DepKind == OMPC_DEPEND_sink) { 8193 if (DepCounter >= TotalDepCount) { 8194 Diag(ELoc, diag::err_omp_depend_sink_unexpected_expr); 8195 continue; 8196 } 8197 ++DepCounter; 8198 // OpenMP [2.13.9, Summary] 8199 // depend(dependence-type : vec), where dependence-type is: 8200 // 'sink' and where vec is the iteration vector, which has the form: 8201 // x1 [+- d1], x2 [+- d2 ], . . . , xn [+- dn] 8202 // where n is the value specified by the ordered clause in the loop 8203 // directive, xi denotes the loop iteration variable of the i-th nested 8204 // loop associated with the loop directive, and di is a constant 8205 // non-negative integer. 8206 SimpleExpr = SimpleExpr->IgnoreImplicit(); 8207 auto *DE = dyn_cast<DeclRefExpr>(SimpleExpr); 8208 if (!DE) { 8209 OverloadedOperatorKind OOK = OO_None; 8210 SourceLocation OOLoc; 8211 Expr *LHS, *RHS; 8212 if (auto *BO = dyn_cast<BinaryOperator>(SimpleExpr)) { 8213 OOK = BinaryOperator::getOverloadedOperator(BO->getOpcode()); 8214 OOLoc = BO->getOperatorLoc(); 8215 LHS = BO->getLHS()->IgnoreParenImpCasts(); 8216 RHS = BO->getRHS()->IgnoreParenImpCasts(); 8217 } else if (auto *OCE = dyn_cast<CXXOperatorCallExpr>(SimpleExpr)) { 8218 OOK = OCE->getOperator(); 8219 OOLoc = OCE->getOperatorLoc(); 8220 LHS = OCE->getArg(/*Arg=*/0)->IgnoreParenImpCasts(); 8221 RHS = OCE->getArg(/*Arg=*/1)->IgnoreParenImpCasts(); 8222 } else if (auto *MCE = dyn_cast<CXXMemberCallExpr>(SimpleExpr)) { 8223 OOK = MCE->getMethodDecl() 8224 ->getNameInfo() 8225 .getName() 8226 .getCXXOverloadedOperator(); 8227 OOLoc = MCE->getCallee()->getExprLoc(); 8228 LHS = MCE->getImplicitObjectArgument()->IgnoreParenImpCasts(); 8229 RHS = MCE->getArg(/*Arg=*/0)->IgnoreParenImpCasts(); 8230 } else { 8231 Diag(ELoc, diag::err_omp_depend_sink_wrong_expr); 8232 continue; 8233 } 8234 DE = dyn_cast<DeclRefExpr>(LHS); 8235 if (!DE) { 8236 Diag(LHS->getExprLoc(), 8237 diag::err_omp_depend_sink_expected_loop_iteration) 8238 << DSAStack->getParentLoopControlVariable( 8239 DepCounter.getZExtValue()); 8240 continue; 8241 } 8242 if (OOK != OO_Plus && OOK != OO_Minus) { 8243 Diag(OOLoc, diag::err_omp_depend_sink_expected_plus_minus); 8244 continue; 8245 } 8246 ExprResult Res = VerifyPositiveIntegerConstantInClause( 8247 RHS, OMPC_depend, /*StrictlyPositive=*/false); 8248 if (Res.isInvalid()) 8249 continue; 8250 } 8251 auto *VD = dyn_cast<VarDecl>(DE->getDecl()); 8252 if (!CurContext->isDependentContext() && 8253 DSAStack->getParentOrderedRegionParam() && 8254 (!VD || DepCounter != DSAStack->isParentLoopControlVariable(VD))) { 8255 Diag(DE->getExprLoc(), 8256 diag::err_omp_depend_sink_expected_loop_iteration) 8257 << DSAStack->getParentLoopControlVariable( 8258 DepCounter.getZExtValue()); 8259 continue; 8260 } 8261 } else { 8262 // OpenMP [2.11.1.1, Restrictions, p.3] 8263 // A variable that is part of another variable (such as a field of a 8264 // structure) but is not an array element or an array section cannot 8265 // appear in a depend clause. 8266 auto *DE = dyn_cast<DeclRefExpr>(SimpleExpr); 8267 auto *ASE = dyn_cast<ArraySubscriptExpr>(SimpleExpr); 8268 auto *OASE = dyn_cast<OMPArraySectionExpr>(SimpleExpr); 8269 if (!RefExpr->IgnoreParenImpCasts()->isLValue() || 8270 (!ASE && !DE && !OASE) || (DE && !isa<VarDecl>(DE->getDecl())) || 8271 (ASE && !ASE->getBase()->getType()->isAnyPointerType() && 8272 !ASE->getBase()->getType()->isArrayType())) { 8273 Diag(ELoc, diag::err_omp_expected_var_name_or_array_item) 8274 << RefExpr->getSourceRange(); 8275 continue; 8276 } 8277 } 8278 8279 Vars.push_back(RefExpr->IgnoreParenImpCasts()); 8280 } 8281 8282 if (!CurContext->isDependentContext() && DepKind == OMPC_DEPEND_sink && 8283 TotalDepCount > VarList.size() && 8284 DSAStack->getParentOrderedRegionParam()) { 8285 Diag(EndLoc, diag::err_omp_depend_sink_expected_loop_iteration) 8286 << DSAStack->getParentLoopControlVariable(VarList.size() + 1); 8287 } 8288 if (DepKind != OMPC_DEPEND_source && DepKind != OMPC_DEPEND_sink && 8289 Vars.empty()) 8290 return nullptr; 8291 } 8292 8293 return OMPDependClause::Create(Context, StartLoc, LParenLoc, EndLoc, DepKind, 8294 DepLoc, ColonLoc, Vars); 8295 } 8296 8297 OMPClause *Sema::ActOnOpenMPDeviceClause(Expr *Device, SourceLocation StartLoc, 8298 SourceLocation LParenLoc, 8299 SourceLocation EndLoc) { 8300 Expr *ValExpr = Device; 8301 8302 // OpenMP [2.9.1, Restrictions] 8303 // The device expression must evaluate to a non-negative integer value. 8304 if (!IsNonNegativeIntegerValue(ValExpr, *this, OMPC_device, 8305 /*StrictlyPositive=*/false)) 8306 return nullptr; 8307 8308 return new (Context) OMPDeviceClause(ValExpr, StartLoc, LParenLoc, EndLoc); 8309 } 8310 8311 static bool IsCXXRecordForMappable(Sema &SemaRef, SourceLocation Loc, 8312 DSAStackTy *Stack, CXXRecordDecl *RD) { 8313 if (!RD || RD->isInvalidDecl()) 8314 return true; 8315 8316 if (auto *CTSD = dyn_cast<ClassTemplateSpecializationDecl>(RD)) 8317 if (auto *CTD = CTSD->getSpecializedTemplate()) 8318 RD = CTD->getTemplatedDecl(); 8319 auto QTy = SemaRef.Context.getRecordType(RD); 8320 if (RD->isDynamicClass()) { 8321 SemaRef.Diag(Loc, diag::err_omp_not_mappable_type) << QTy; 8322 SemaRef.Diag(RD->getLocation(), diag::note_omp_polymorphic_in_target); 8323 return false; 8324 } 8325 auto *DC = RD; 8326 bool IsCorrect = true; 8327 for (auto *I : DC->decls()) { 8328 if (I) { 8329 if (auto *MD = dyn_cast<CXXMethodDecl>(I)) { 8330 if (MD->isStatic()) { 8331 SemaRef.Diag(Loc, diag::err_omp_not_mappable_type) << QTy; 8332 SemaRef.Diag(MD->getLocation(), 8333 diag::note_omp_static_member_in_target); 8334 IsCorrect = false; 8335 } 8336 } else if (auto *VD = dyn_cast<VarDecl>(I)) { 8337 if (VD->isStaticDataMember()) { 8338 SemaRef.Diag(Loc, diag::err_omp_not_mappable_type) << QTy; 8339 SemaRef.Diag(VD->getLocation(), 8340 diag::note_omp_static_member_in_target); 8341 IsCorrect = false; 8342 } 8343 } 8344 } 8345 } 8346 8347 for (auto &I : RD->bases()) { 8348 if (!IsCXXRecordForMappable(SemaRef, I.getLocStart(), Stack, 8349 I.getType()->getAsCXXRecordDecl())) 8350 IsCorrect = false; 8351 } 8352 return IsCorrect; 8353 } 8354 8355 static bool CheckTypeMappable(SourceLocation SL, SourceRange SR, Sema &SemaRef, 8356 DSAStackTy *Stack, QualType QTy) { 8357 NamedDecl *ND; 8358 if (QTy->isIncompleteType(&ND)) { 8359 SemaRef.Diag(SL, diag::err_incomplete_type) << QTy << SR; 8360 return false; 8361 } else if (CXXRecordDecl *RD = dyn_cast_or_null<CXXRecordDecl>(ND)) { 8362 if (!RD->isInvalidDecl() && 8363 !IsCXXRecordForMappable(SemaRef, SL, Stack, RD)) 8364 return false; 8365 } 8366 return true; 8367 } 8368 8369 OMPClause *Sema::ActOnOpenMPMapClause( 8370 OpenMPMapClauseKind MapTypeModifier, OpenMPMapClauseKind MapType, 8371 SourceLocation MapLoc, SourceLocation ColonLoc, ArrayRef<Expr *> VarList, 8372 SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc) { 8373 SmallVector<Expr *, 4> Vars; 8374 8375 for (auto &RE : VarList) { 8376 assert(RE && "Null expr in omp map"); 8377 if (isa<DependentScopeDeclRefExpr>(RE)) { 8378 // It will be analyzed later. 8379 Vars.push_back(RE); 8380 continue; 8381 } 8382 SourceLocation ELoc = RE->getExprLoc(); 8383 8384 // OpenMP [2.14.5, Restrictions] 8385 // A variable that is part of another variable (such as field of a 8386 // structure) but is not an array element or an array section cannot appear 8387 // in a map clause. 8388 auto *VE = RE->IgnoreParenLValueCasts(); 8389 8390 if (VE->isValueDependent() || VE->isTypeDependent() || 8391 VE->isInstantiationDependent() || 8392 VE->containsUnexpandedParameterPack()) { 8393 // It will be analyzed later. 8394 Vars.push_back(RE); 8395 continue; 8396 } 8397 8398 auto *SimpleExpr = RE->IgnoreParenCasts(); 8399 auto *DE = dyn_cast<DeclRefExpr>(SimpleExpr); 8400 auto *ASE = dyn_cast<ArraySubscriptExpr>(SimpleExpr); 8401 auto *OASE = dyn_cast<OMPArraySectionExpr>(SimpleExpr); 8402 8403 if (!RE->IgnoreParenImpCasts()->isLValue() || 8404 (!OASE && !ASE && !DE) || 8405 (DE && !isa<VarDecl>(DE->getDecl())) || 8406 (ASE && !ASE->getBase()->getType()->isAnyPointerType() && 8407 !ASE->getBase()->getType()->isArrayType())) { 8408 Diag(ELoc, diag::err_omp_expected_var_name_or_array_item) 8409 << RE->getSourceRange(); 8410 continue; 8411 } 8412 8413 Decl *D = nullptr; 8414 if (DE) { 8415 D = DE->getDecl(); 8416 } else if (ASE) { 8417 auto *B = ASE->getBase()->IgnoreParenCasts(); 8418 D = dyn_cast<DeclRefExpr>(B)->getDecl(); 8419 } else if (OASE) { 8420 auto *B = OASE->getBase(); 8421 D = dyn_cast<DeclRefExpr>(B)->getDecl(); 8422 } 8423 assert(D && "Null decl on map clause."); 8424 auto *VD = cast<VarDecl>(D); 8425 8426 // OpenMP [2.14.5, Restrictions, p.8] 8427 // threadprivate variables cannot appear in a map clause. 8428 if (DSAStack->isThreadPrivate(VD)) { 8429 auto DVar = DSAStack->getTopDSA(VD, false); 8430 Diag(ELoc, diag::err_omp_threadprivate_in_map); 8431 ReportOriginalDSA(*this, DSAStack, VD, DVar); 8432 continue; 8433 } 8434 8435 // OpenMP [2.14.5, Restrictions, p.2] 8436 // At most one list item can be an array item derived from a given variable 8437 // in map clauses of the same construct. 8438 // OpenMP [2.14.5, Restrictions, p.3] 8439 // List items of map clauses in the same construct must not share original 8440 // storage. 8441 // OpenMP [2.14.5, Restrictions, C/C++, p.2] 8442 // A variable for which the type is pointer, reference to array, or 8443 // reference to pointer and an array section derived from that variable 8444 // must not appear as list items of map clauses of the same construct. 8445 DSAStackTy::MapInfo MI = DSAStack->IsMappedInCurrentRegion(VD); 8446 if (MI.RefExpr) { 8447 Diag(ELoc, diag::err_omp_map_shared_storage) << ELoc; 8448 Diag(MI.RefExpr->getExprLoc(), diag::note_used_here) 8449 << MI.RefExpr->getSourceRange(); 8450 continue; 8451 } 8452 8453 // OpenMP [2.14.5, Restrictions, C/C++, p.3,4] 8454 // A variable for which the type is pointer, reference to array, or 8455 // reference to pointer must not appear as a list item if the enclosing 8456 // device data environment already contains an array section derived from 8457 // that variable. 8458 // An array section derived from a variable for which the type is pointer, 8459 // reference to array, or reference to pointer must not appear as a list 8460 // item if the enclosing device data environment already contains that 8461 // variable. 8462 QualType Type = VD->getType(); 8463 MI = DSAStack->getMapInfoForVar(VD); 8464 if (MI.RefExpr && (isa<DeclRefExpr>(MI.RefExpr->IgnoreParenLValueCasts()) != 8465 isa<DeclRefExpr>(VE)) && 8466 (Type->isPointerType() || Type->isReferenceType())) { 8467 Diag(ELoc, diag::err_omp_map_shared_storage) << ELoc; 8468 Diag(MI.RefExpr->getExprLoc(), diag::note_used_here) 8469 << MI.RefExpr->getSourceRange(); 8470 continue; 8471 } 8472 8473 // OpenMP [2.14.5, Restrictions, C/C++, p.7] 8474 // A list item must have a mappable type. 8475 if (!CheckTypeMappable(VE->getExprLoc(), VE->getSourceRange(), *this, 8476 DSAStack, Type)) 8477 continue; 8478 8479 Vars.push_back(RE); 8480 MI.RefExpr = RE; 8481 DSAStack->addMapInfoForVar(VD, MI); 8482 } 8483 if (Vars.empty()) 8484 return nullptr; 8485 8486 return OMPMapClause::Create(Context, StartLoc, LParenLoc, EndLoc, Vars, 8487 MapTypeModifier, MapType, MapLoc); 8488 } 8489 8490 OMPClause *Sema::ActOnOpenMPNumTeamsClause(Expr *NumTeams, 8491 SourceLocation StartLoc, 8492 SourceLocation LParenLoc, 8493 SourceLocation EndLoc) { 8494 Expr *ValExpr = NumTeams; 8495 8496 // OpenMP [teams Constrcut, Restrictions] 8497 // The num_teams expression must evaluate to a positive integer value. 8498 if (!IsNonNegativeIntegerValue(ValExpr, *this, OMPC_num_teams, 8499 /*StrictlyPositive=*/true)) 8500 return nullptr; 8501 8502 return new (Context) OMPNumTeamsClause(ValExpr, StartLoc, LParenLoc, EndLoc); 8503 } 8504 8505 OMPClause *Sema::ActOnOpenMPThreadLimitClause(Expr *ThreadLimit, 8506 SourceLocation StartLoc, 8507 SourceLocation LParenLoc, 8508 SourceLocation EndLoc) { 8509 Expr *ValExpr = ThreadLimit; 8510 8511 // OpenMP [teams Constrcut, Restrictions] 8512 // The thread_limit expression must evaluate to a positive integer value. 8513 if (!IsNonNegativeIntegerValue(ValExpr, *this, OMPC_thread_limit, 8514 /*StrictlyPositive=*/true)) 8515 return nullptr; 8516 8517 return new (Context) OMPThreadLimitClause(ValExpr, StartLoc, LParenLoc, 8518 EndLoc); 8519 } 8520 8521 OMPClause *Sema::ActOnOpenMPPriorityClause(Expr *Priority, 8522 SourceLocation StartLoc, 8523 SourceLocation LParenLoc, 8524 SourceLocation EndLoc) { 8525 Expr *ValExpr = Priority; 8526 8527 // OpenMP [2.9.1, task Constrcut] 8528 // The priority-value is a non-negative numerical scalar expression. 8529 if (!IsNonNegativeIntegerValue(ValExpr, *this, OMPC_priority, 8530 /*StrictlyPositive=*/false)) 8531 return nullptr; 8532 8533 return new (Context) OMPPriorityClause(ValExpr, StartLoc, LParenLoc, EndLoc); 8534 } 8535 8536 OMPClause *Sema::ActOnOpenMPGrainsizeClause(Expr *Grainsize, 8537 SourceLocation StartLoc, 8538 SourceLocation LParenLoc, 8539 SourceLocation EndLoc) { 8540 Expr *ValExpr = Grainsize; 8541 8542 // OpenMP [2.9.2, taskloop Constrcut] 8543 // The parameter of the grainsize clause must be a positive integer 8544 // expression. 8545 if (!IsNonNegativeIntegerValue(ValExpr, *this, OMPC_grainsize, 8546 /*StrictlyPositive=*/true)) 8547 return nullptr; 8548 8549 return new (Context) OMPGrainsizeClause(ValExpr, StartLoc, LParenLoc, EndLoc); 8550 } 8551 8552 OMPClause *Sema::ActOnOpenMPNumTasksClause(Expr *NumTasks, 8553 SourceLocation StartLoc, 8554 SourceLocation LParenLoc, 8555 SourceLocation EndLoc) { 8556 Expr *ValExpr = NumTasks; 8557 8558 // OpenMP [2.9.2, taskloop Constrcut] 8559 // The parameter of the num_tasks clause must be a positive integer 8560 // expression. 8561 if (!IsNonNegativeIntegerValue(ValExpr, *this, OMPC_num_tasks, 8562 /*StrictlyPositive=*/true)) 8563 return nullptr; 8564 8565 return new (Context) OMPNumTasksClause(ValExpr, StartLoc, LParenLoc, EndLoc); 8566 } 8567 8568 OMPClause *Sema::ActOnOpenMPHintClause(Expr *Hint, SourceLocation StartLoc, 8569 SourceLocation LParenLoc, 8570 SourceLocation EndLoc) { 8571 // OpenMP [2.13.2, critical construct, Description] 8572 // ... where hint-expression is an integer constant expression that evaluates 8573 // to a valid lock hint. 8574 ExprResult HintExpr = VerifyPositiveIntegerConstantInClause(Hint, OMPC_hint); 8575 if (HintExpr.isInvalid()) 8576 return nullptr; 8577 return new (Context) 8578 OMPHintClause(HintExpr.get(), StartLoc, LParenLoc, EndLoc); 8579 } 8580 8581