//===--- OpenMPClause.cpp - Classes for OpenMP clauses --------------------===// // // The LLVM Compiler Infrastructure // // This file is distributed under the University of Illinois Open Source // License. See LICENSE.TXT for details. // //===----------------------------------------------------------------------===// // // This file implements the subclesses of Stmt class declared in OpenMPClause.h // //===----------------------------------------------------------------------===// #include "clang/AST/OpenMPClause.h" #include "clang/AST/ASTContext.h" using namespace clang; OMPClause::child_range OMPClause::children() { switch (getClauseKind()) { default: break; #define OPENMP_CLAUSE(Name, Class) \ case OMPC_##Name: \ return static_cast(this)->children(); #include "clang/Basic/OpenMPKinds.def" } llvm_unreachable("unknown OMPClause"); } OMPClauseWithPreInit *OMPClauseWithPreInit::get(OMPClause *C) { auto *Res = OMPClauseWithPreInit::get(const_cast(C)); return Res ? const_cast(Res) : nullptr; } const OMPClauseWithPreInit *OMPClauseWithPreInit::get(const OMPClause *C) { switch (C->getClauseKind()) { case OMPC_schedule: return static_cast(C); case OMPC_dist_schedule: return static_cast(C); case OMPC_firstprivate: return static_cast(C); case OMPC_lastprivate: return static_cast(C); case OMPC_reduction: return static_cast(C); case OMPC_linear: return static_cast(C); case OMPC_default: case OMPC_proc_bind: case OMPC_if: case OMPC_final: case OMPC_num_threads: case OMPC_safelen: case OMPC_simdlen: case OMPC_collapse: case OMPC_private: case OMPC_shared: case OMPC_aligned: case OMPC_copyin: case OMPC_copyprivate: case OMPC_ordered: case OMPC_nowait: case OMPC_untied: case OMPC_mergeable: case OMPC_threadprivate: case OMPC_flush: case OMPC_read: case OMPC_write: case OMPC_update: case OMPC_capture: case OMPC_seq_cst: case OMPC_depend: case OMPC_device: case OMPC_threads: case OMPC_simd: case OMPC_map: case OMPC_num_teams: case OMPC_thread_limit: case OMPC_priority: case OMPC_grainsize: case OMPC_nogroup: case OMPC_num_tasks: case OMPC_hint: case OMPC_defaultmap: case OMPC_unknown: case OMPC_uniform: case OMPC_to: case OMPC_from: case OMPC_use_device_ptr: case OMPC_is_device_ptr: break; } return nullptr; } OMPClauseWithPostUpdate *OMPClauseWithPostUpdate::get(OMPClause *C) { auto *Res = OMPClauseWithPostUpdate::get(const_cast(C)); return Res ? const_cast(Res) : nullptr; } const OMPClauseWithPostUpdate *OMPClauseWithPostUpdate::get(const OMPClause *C) { switch (C->getClauseKind()) { case OMPC_lastprivate: return static_cast(C); case OMPC_reduction: return static_cast(C); case OMPC_linear: return static_cast(C); case OMPC_schedule: case OMPC_dist_schedule: case OMPC_firstprivate: case OMPC_default: case OMPC_proc_bind: case OMPC_if: case OMPC_final: case OMPC_num_threads: case OMPC_safelen: case OMPC_simdlen: case OMPC_collapse: case OMPC_private: case OMPC_shared: case OMPC_aligned: case OMPC_copyin: case OMPC_copyprivate: case OMPC_ordered: case OMPC_nowait: case OMPC_untied: case OMPC_mergeable: case OMPC_threadprivate: case OMPC_flush: case OMPC_read: case OMPC_write: case OMPC_update: case OMPC_capture: case OMPC_seq_cst: case OMPC_depend: case OMPC_device: case OMPC_threads: case OMPC_simd: case OMPC_map: case OMPC_num_teams: case OMPC_thread_limit: case OMPC_priority: case OMPC_grainsize: case OMPC_nogroup: case OMPC_num_tasks: case OMPC_hint: case OMPC_defaultmap: case OMPC_unknown: case OMPC_uniform: case OMPC_to: case OMPC_from: case OMPC_use_device_ptr: case OMPC_is_device_ptr: break; } return nullptr; } void OMPPrivateClause::setPrivateCopies(ArrayRef VL) { assert(VL.size() == varlist_size() && "Number of private copies is not the same as the preallocated buffer"); std::copy(VL.begin(), VL.end(), varlist_end()); } OMPPrivateClause * OMPPrivateClause::Create(const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, ArrayRef VL, ArrayRef PrivateVL) { // Allocate space for private variables and initializer expressions. void *Mem = C.Allocate(totalSizeToAlloc(2 * VL.size())); OMPPrivateClause *Clause = new (Mem) OMPPrivateClause(StartLoc, LParenLoc, EndLoc, VL.size()); Clause->setVarRefs(VL); Clause->setPrivateCopies(PrivateVL); return Clause; } OMPPrivateClause *OMPPrivateClause::CreateEmpty(const ASTContext &C, unsigned N) { void *Mem = C.Allocate(totalSizeToAlloc(2 * N)); return new (Mem) OMPPrivateClause(N); } void OMPFirstprivateClause::setPrivateCopies(ArrayRef VL) { assert(VL.size() == varlist_size() && "Number of private copies is not the same as the preallocated buffer"); std::copy(VL.begin(), VL.end(), varlist_end()); } void OMPFirstprivateClause::setInits(ArrayRef VL) { assert(VL.size() == varlist_size() && "Number of inits is not the same as the preallocated buffer"); std::copy(VL.begin(), VL.end(), getPrivateCopies().end()); } OMPFirstprivateClause * OMPFirstprivateClause::Create(const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, ArrayRef VL, ArrayRef PrivateVL, ArrayRef InitVL, Stmt *PreInit) { void *Mem = C.Allocate(totalSizeToAlloc(3 * VL.size())); OMPFirstprivateClause *Clause = new (Mem) OMPFirstprivateClause(StartLoc, LParenLoc, EndLoc, VL.size()); Clause->setVarRefs(VL); Clause->setPrivateCopies(PrivateVL); Clause->setInits(InitVL); Clause->setPreInitStmt(PreInit); return Clause; } OMPFirstprivateClause *OMPFirstprivateClause::CreateEmpty(const ASTContext &C, unsigned N) { void *Mem = C.Allocate(totalSizeToAlloc(3 * N)); return new (Mem) OMPFirstprivateClause(N); } void OMPLastprivateClause::setPrivateCopies(ArrayRef PrivateCopies) { assert(PrivateCopies.size() == varlist_size() && "Number of private copies is not the same as the preallocated buffer"); std::copy(PrivateCopies.begin(), PrivateCopies.end(), varlist_end()); } void OMPLastprivateClause::setSourceExprs(ArrayRef SrcExprs) { assert(SrcExprs.size() == varlist_size() && "Number of source expressions is " "not the same as the " "preallocated buffer"); std::copy(SrcExprs.begin(), SrcExprs.end(), getPrivateCopies().end()); } void OMPLastprivateClause::setDestinationExprs(ArrayRef DstExprs) { assert(DstExprs.size() == varlist_size() && "Number of destination " "expressions is not the same as " "the preallocated buffer"); std::copy(DstExprs.begin(), DstExprs.end(), getSourceExprs().end()); } void OMPLastprivateClause::setAssignmentOps(ArrayRef AssignmentOps) { assert(AssignmentOps.size() == varlist_size() && "Number of assignment expressions is not the same as the preallocated " "buffer"); std::copy(AssignmentOps.begin(), AssignmentOps.end(), getDestinationExprs().end()); } OMPLastprivateClause *OMPLastprivateClause::Create( const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, ArrayRef VL, ArrayRef SrcExprs, ArrayRef DstExprs, ArrayRef AssignmentOps, Stmt *PreInit, Expr *PostUpdate) { void *Mem = C.Allocate(totalSizeToAlloc(5 * VL.size())); OMPLastprivateClause *Clause = new (Mem) OMPLastprivateClause(StartLoc, LParenLoc, EndLoc, VL.size()); Clause->setVarRefs(VL); Clause->setSourceExprs(SrcExprs); Clause->setDestinationExprs(DstExprs); Clause->setAssignmentOps(AssignmentOps); Clause->setPreInitStmt(PreInit); Clause->setPostUpdateExpr(PostUpdate); return Clause; } OMPLastprivateClause *OMPLastprivateClause::CreateEmpty(const ASTContext &C, unsigned N) { void *Mem = C.Allocate(totalSizeToAlloc(5 * N)); return new (Mem) OMPLastprivateClause(N); } OMPSharedClause *OMPSharedClause::Create(const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, ArrayRef VL) { void *Mem = C.Allocate(totalSizeToAlloc(VL.size())); OMPSharedClause *Clause = new (Mem) OMPSharedClause(StartLoc, LParenLoc, EndLoc, VL.size()); Clause->setVarRefs(VL); return Clause; } OMPSharedClause *OMPSharedClause::CreateEmpty(const ASTContext &C, unsigned N) { void *Mem = C.Allocate(totalSizeToAlloc(N)); return new (Mem) OMPSharedClause(N); } void OMPLinearClause::setPrivates(ArrayRef PL) { assert(PL.size() == varlist_size() && "Number of privates is not the same as the preallocated buffer"); std::copy(PL.begin(), PL.end(), varlist_end()); } void OMPLinearClause::setInits(ArrayRef IL) { assert(IL.size() == varlist_size() && "Number of inits is not the same as the preallocated buffer"); std::copy(IL.begin(), IL.end(), getPrivates().end()); } void OMPLinearClause::setUpdates(ArrayRef UL) { assert(UL.size() == varlist_size() && "Number of updates is not the same as the preallocated buffer"); std::copy(UL.begin(), UL.end(), getInits().end()); } void OMPLinearClause::setFinals(ArrayRef FL) { assert(FL.size() == varlist_size() && "Number of final updates is not the same as the preallocated buffer"); std::copy(FL.begin(), FL.end(), getUpdates().end()); } OMPLinearClause *OMPLinearClause::Create( const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, OpenMPLinearClauseKind Modifier, SourceLocation ModifierLoc, SourceLocation ColonLoc, SourceLocation EndLoc, ArrayRef VL, ArrayRef PL, ArrayRef IL, Expr *Step, Expr *CalcStep, Stmt *PreInit, Expr *PostUpdate) { // Allocate space for 4 lists (Vars, Inits, Updates, Finals) and 2 expressions // (Step and CalcStep). void *Mem = C.Allocate(totalSizeToAlloc(5 * VL.size() + 2)); OMPLinearClause *Clause = new (Mem) OMPLinearClause( StartLoc, LParenLoc, Modifier, ModifierLoc, ColonLoc, EndLoc, VL.size()); Clause->setVarRefs(VL); Clause->setPrivates(PL); Clause->setInits(IL); // Fill update and final expressions with zeroes, they are provided later, // after the directive construction. std::fill(Clause->getInits().end(), Clause->getInits().end() + VL.size(), nullptr); std::fill(Clause->getUpdates().end(), Clause->getUpdates().end() + VL.size(), nullptr); Clause->setStep(Step); Clause->setCalcStep(CalcStep); Clause->setPreInitStmt(PreInit); Clause->setPostUpdateExpr(PostUpdate); return Clause; } OMPLinearClause *OMPLinearClause::CreateEmpty(const ASTContext &C, unsigned NumVars) { // Allocate space for 4 lists (Vars, Inits, Updates, Finals) and 2 expressions // (Step and CalcStep). void *Mem = C.Allocate(totalSizeToAlloc(5 * NumVars + 2)); return new (Mem) OMPLinearClause(NumVars); } OMPAlignedClause * OMPAlignedClause::Create(const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation ColonLoc, SourceLocation EndLoc, ArrayRef VL, Expr *A) { void *Mem = C.Allocate(totalSizeToAlloc(VL.size() + 1)); OMPAlignedClause *Clause = new (Mem) OMPAlignedClause(StartLoc, LParenLoc, ColonLoc, EndLoc, VL.size()); Clause->setVarRefs(VL); Clause->setAlignment(A); return Clause; } OMPAlignedClause *OMPAlignedClause::CreateEmpty(const ASTContext &C, unsigned NumVars) { void *Mem = C.Allocate(totalSizeToAlloc(NumVars + 1)); return new (Mem) OMPAlignedClause(NumVars); } void OMPCopyinClause::setSourceExprs(ArrayRef SrcExprs) { assert(SrcExprs.size() == varlist_size() && "Number of source expressions is " "not the same as the " "preallocated buffer"); std::copy(SrcExprs.begin(), SrcExprs.end(), varlist_end()); } void OMPCopyinClause::setDestinationExprs(ArrayRef DstExprs) { assert(DstExprs.size() == varlist_size() && "Number of destination " "expressions is not the same as " "the preallocated buffer"); std::copy(DstExprs.begin(), DstExprs.end(), getSourceExprs().end()); } void OMPCopyinClause::setAssignmentOps(ArrayRef AssignmentOps) { assert(AssignmentOps.size() == varlist_size() && "Number of assignment expressions is not the same as the preallocated " "buffer"); std::copy(AssignmentOps.begin(), AssignmentOps.end(), getDestinationExprs().end()); } OMPCopyinClause *OMPCopyinClause::Create( const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, ArrayRef VL, ArrayRef SrcExprs, ArrayRef DstExprs, ArrayRef AssignmentOps) { void *Mem = C.Allocate(totalSizeToAlloc(4 * VL.size())); OMPCopyinClause *Clause = new (Mem) OMPCopyinClause(StartLoc, LParenLoc, EndLoc, VL.size()); Clause->setVarRefs(VL); Clause->setSourceExprs(SrcExprs); Clause->setDestinationExprs(DstExprs); Clause->setAssignmentOps(AssignmentOps); return Clause; } OMPCopyinClause *OMPCopyinClause::CreateEmpty(const ASTContext &C, unsigned N) { void *Mem = C.Allocate(totalSizeToAlloc(4 * N)); return new (Mem) OMPCopyinClause(N); } void OMPCopyprivateClause::setSourceExprs(ArrayRef SrcExprs) { assert(SrcExprs.size() == varlist_size() && "Number of source expressions is " "not the same as the " "preallocated buffer"); std::copy(SrcExprs.begin(), SrcExprs.end(), varlist_end()); } void OMPCopyprivateClause::setDestinationExprs(ArrayRef DstExprs) { assert(DstExprs.size() == varlist_size() && "Number of destination " "expressions is not the same as " "the preallocated buffer"); std::copy(DstExprs.begin(), DstExprs.end(), getSourceExprs().end()); } void OMPCopyprivateClause::setAssignmentOps(ArrayRef AssignmentOps) { assert(AssignmentOps.size() == varlist_size() && "Number of assignment expressions is not the same as the preallocated " "buffer"); std::copy(AssignmentOps.begin(), AssignmentOps.end(), getDestinationExprs().end()); } OMPCopyprivateClause *OMPCopyprivateClause::Create( const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, ArrayRef VL, ArrayRef SrcExprs, ArrayRef DstExprs, ArrayRef AssignmentOps) { void *Mem = C.Allocate(totalSizeToAlloc(4 * VL.size())); OMPCopyprivateClause *Clause = new (Mem) OMPCopyprivateClause(StartLoc, LParenLoc, EndLoc, VL.size()); Clause->setVarRefs(VL); Clause->setSourceExprs(SrcExprs); Clause->setDestinationExprs(DstExprs); Clause->setAssignmentOps(AssignmentOps); return Clause; } OMPCopyprivateClause *OMPCopyprivateClause::CreateEmpty(const ASTContext &C, unsigned N) { void *Mem = C.Allocate(totalSizeToAlloc(4 * N)); return new (Mem) OMPCopyprivateClause(N); } void OMPReductionClause::setPrivates(ArrayRef Privates) { assert(Privates.size() == varlist_size() && "Number of private copies is not the same as the preallocated buffer"); std::copy(Privates.begin(), Privates.end(), varlist_end()); } void OMPReductionClause::setLHSExprs(ArrayRef LHSExprs) { assert( LHSExprs.size() == varlist_size() && "Number of LHS expressions is not the same as the preallocated buffer"); std::copy(LHSExprs.begin(), LHSExprs.end(), getPrivates().end()); } void OMPReductionClause::setRHSExprs(ArrayRef RHSExprs) { assert( RHSExprs.size() == varlist_size() && "Number of RHS expressions is not the same as the preallocated buffer"); std::copy(RHSExprs.begin(), RHSExprs.end(), getLHSExprs().end()); } void OMPReductionClause::setReductionOps(ArrayRef ReductionOps) { assert(ReductionOps.size() == varlist_size() && "Number of reduction " "expressions is not the same " "as the preallocated buffer"); std::copy(ReductionOps.begin(), ReductionOps.end(), getRHSExprs().end()); } OMPReductionClause *OMPReductionClause::Create( const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, SourceLocation ColonLoc, ArrayRef VL, NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo, ArrayRef Privates, ArrayRef LHSExprs, ArrayRef RHSExprs, ArrayRef ReductionOps, Stmt *PreInit, Expr *PostUpdate) { void *Mem = C.Allocate(totalSizeToAlloc(5 * VL.size())); OMPReductionClause *Clause = new (Mem) OMPReductionClause( StartLoc, LParenLoc, EndLoc, ColonLoc, VL.size(), QualifierLoc, NameInfo); Clause->setVarRefs(VL); Clause->setPrivates(Privates); Clause->setLHSExprs(LHSExprs); Clause->setRHSExprs(RHSExprs); Clause->setReductionOps(ReductionOps); Clause->setPreInitStmt(PreInit); Clause->setPostUpdateExpr(PostUpdate); return Clause; } OMPReductionClause *OMPReductionClause::CreateEmpty(const ASTContext &C, unsigned N) { void *Mem = C.Allocate(totalSizeToAlloc(5 * N)); return new (Mem) OMPReductionClause(N); } OMPFlushClause *OMPFlushClause::Create(const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, ArrayRef VL) { void *Mem = C.Allocate(totalSizeToAlloc(VL.size() + 1)); OMPFlushClause *Clause = new (Mem) OMPFlushClause(StartLoc, LParenLoc, EndLoc, VL.size()); Clause->setVarRefs(VL); return Clause; } OMPFlushClause *OMPFlushClause::CreateEmpty(const ASTContext &C, unsigned N) { void *Mem = C.Allocate(totalSizeToAlloc(N)); return new (Mem) OMPFlushClause(N); } OMPDependClause *OMPDependClause::Create( const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, OpenMPDependClauseKind DepKind, SourceLocation DepLoc, SourceLocation ColonLoc, ArrayRef VL) { void *Mem = C.Allocate(totalSizeToAlloc(VL.size() + 1)); OMPDependClause *Clause = new (Mem) OMPDependClause(StartLoc, LParenLoc, EndLoc, VL.size()); Clause->setVarRefs(VL); Clause->setDependencyKind(DepKind); Clause->setDependencyLoc(DepLoc); Clause->setColonLoc(ColonLoc); Clause->setCounterValue(nullptr); return Clause; } OMPDependClause *OMPDependClause::CreateEmpty(const ASTContext &C, unsigned N) { void *Mem = C.Allocate(totalSizeToAlloc(N + 1)); return new (Mem) OMPDependClause(N); } void OMPDependClause::setCounterValue(Expr *V) { assert(getDependencyKind() == OMPC_DEPEND_sink || getDependencyKind() == OMPC_DEPEND_source || V == nullptr); *getVarRefs().end() = V; } const Expr *OMPDependClause::getCounterValue() const { auto *V = *getVarRefs().end(); assert(getDependencyKind() == OMPC_DEPEND_sink || getDependencyKind() == OMPC_DEPEND_source || V == nullptr); return V; } Expr *OMPDependClause::getCounterValue() { auto *V = *getVarRefs().end(); assert(getDependencyKind() == OMPC_DEPEND_sink || getDependencyKind() == OMPC_DEPEND_source || V == nullptr); return V; } unsigned OMPClauseMappableExprCommon::getComponentsTotalNumber( MappableExprComponentListsRef ComponentLists) { unsigned TotalNum = 0u; for (auto &C : ComponentLists) TotalNum += C.size(); return TotalNum; } unsigned OMPClauseMappableExprCommon::getUniqueDeclarationsTotalNumber( ArrayRef Declarations) { unsigned TotalNum = 0u; llvm::SmallPtrSet Cache; for (auto *D : Declarations) { const ValueDecl *VD = D ? cast(D->getCanonicalDecl()) : nullptr; if (Cache.count(VD)) continue; ++TotalNum; Cache.insert(VD); } return TotalNum; } OMPMapClause * OMPMapClause::Create(const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, ArrayRef Vars, ArrayRef Declarations, MappableExprComponentListsRef ComponentLists, OpenMPMapClauseKind TypeModifier, OpenMPMapClauseKind Type, bool TypeIsImplicit, SourceLocation TypeLoc) { unsigned NumVars = Vars.size(); unsigned NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations); unsigned NumComponentLists = ComponentLists.size(); unsigned NumComponents = getComponentsTotalNumber(ComponentLists); // We need to allocate: // NumVars x Expr* - we have an original list expression for each clause list // entry. // NumUniqueDeclarations x ValueDecl* - unique base declarations associated // with each component list. // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the // number of lists for each unique declaration and the size of each component // list. // NumComponents x MappableComponent - the total of all the components in all // the lists. void *Mem = C.Allocate( totalSizeToAlloc( NumVars, NumUniqueDeclarations, NumUniqueDeclarations + NumComponentLists, NumComponents)); OMPMapClause *Clause = new (Mem) OMPMapClause( TypeModifier, Type, TypeIsImplicit, TypeLoc, StartLoc, LParenLoc, EndLoc, NumVars, NumUniqueDeclarations, NumComponentLists, NumComponents); Clause->setVarRefs(Vars); Clause->setClauseInfo(Declarations, ComponentLists); Clause->setMapTypeModifier(TypeModifier); Clause->setMapType(Type); Clause->setMapLoc(TypeLoc); return Clause; } OMPMapClause *OMPMapClause::CreateEmpty(const ASTContext &C, unsigned NumVars, unsigned NumUniqueDeclarations, unsigned NumComponentLists, unsigned NumComponents) { void *Mem = C.Allocate( totalSizeToAlloc( NumVars, NumUniqueDeclarations, NumUniqueDeclarations + NumComponentLists, NumComponents)); return new (Mem) OMPMapClause(NumVars, NumUniqueDeclarations, NumComponentLists, NumComponents); } OMPToClause *OMPToClause::Create(const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, ArrayRef Vars, ArrayRef Declarations, MappableExprComponentListsRef ComponentLists) { unsigned NumVars = Vars.size(); unsigned NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations); unsigned NumComponentLists = ComponentLists.size(); unsigned NumComponents = getComponentsTotalNumber(ComponentLists); // We need to allocate: // NumVars x Expr* - we have an original list expression for each clause list // entry. // NumUniqueDeclarations x ValueDecl* - unique base declarations associated // with each component list. // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the // number of lists for each unique declaration and the size of each component // list. // NumComponents x MappableComponent - the total of all the components in all // the lists. void *Mem = C.Allocate( totalSizeToAlloc( NumVars, NumUniqueDeclarations, NumUniqueDeclarations + NumComponentLists, NumComponents)); OMPToClause *Clause = new (Mem) OMPToClause(StartLoc, LParenLoc, EndLoc, NumVars, NumUniqueDeclarations, NumComponentLists, NumComponents); Clause->setVarRefs(Vars); Clause->setClauseInfo(Declarations, ComponentLists); return Clause; } OMPToClause *OMPToClause::CreateEmpty(const ASTContext &C, unsigned NumVars, unsigned NumUniqueDeclarations, unsigned NumComponentLists, unsigned NumComponents) { void *Mem = C.Allocate( totalSizeToAlloc( NumVars, NumUniqueDeclarations, NumUniqueDeclarations + NumComponentLists, NumComponents)); return new (Mem) OMPToClause(NumVars, NumUniqueDeclarations, NumComponentLists, NumComponents); } OMPFromClause * OMPFromClause::Create(const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, ArrayRef Vars, ArrayRef Declarations, MappableExprComponentListsRef ComponentLists) { unsigned NumVars = Vars.size(); unsigned NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations); unsigned NumComponentLists = ComponentLists.size(); unsigned NumComponents = getComponentsTotalNumber(ComponentLists); // We need to allocate: // NumVars x Expr* - we have an original list expression for each clause list // entry. // NumUniqueDeclarations x ValueDecl* - unique base declarations associated // with each component list. // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the // number of lists for each unique declaration and the size of each component // list. // NumComponents x MappableComponent - the total of all the components in all // the lists. void *Mem = C.Allocate( totalSizeToAlloc( NumVars, NumUniqueDeclarations, NumUniqueDeclarations + NumComponentLists, NumComponents)); OMPFromClause *Clause = new (Mem) OMPFromClause(StartLoc, LParenLoc, EndLoc, NumVars, NumUniqueDeclarations, NumComponentLists, NumComponents); Clause->setVarRefs(Vars); Clause->setClauseInfo(Declarations, ComponentLists); return Clause; } OMPFromClause *OMPFromClause::CreateEmpty(const ASTContext &C, unsigned NumVars, unsigned NumUniqueDeclarations, unsigned NumComponentLists, unsigned NumComponents) { void *Mem = C.Allocate( totalSizeToAlloc( NumVars, NumUniqueDeclarations, NumUniqueDeclarations + NumComponentLists, NumComponents)); return new (Mem) OMPFromClause(NumVars, NumUniqueDeclarations, NumComponentLists, NumComponents); } OMPUseDevicePtrClause *OMPUseDevicePtrClause::Create(const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, ArrayRef VL) { void *Mem = C.Allocate(totalSizeToAlloc(VL.size())); OMPUseDevicePtrClause *Clause = new (Mem) OMPUseDevicePtrClause(StartLoc, LParenLoc, EndLoc, VL.size()); Clause->setVarRefs(VL); return Clause; } OMPUseDevicePtrClause *OMPUseDevicePtrClause::CreateEmpty(const ASTContext &C, unsigned N) { void *Mem = C.Allocate(totalSizeToAlloc(N)); return new (Mem) OMPUseDevicePtrClause(N); } OMPIsDevicePtrClause *OMPIsDevicePtrClause::Create(const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, SourceLocation EndLoc, ArrayRef VL) { void *Mem = C.Allocate(totalSizeToAlloc(VL.size())); OMPIsDevicePtrClause *Clause = new (Mem) OMPIsDevicePtrClause(StartLoc, LParenLoc, EndLoc, VL.size()); Clause->setVarRefs(VL); return Clause; } OMPIsDevicePtrClause *OMPIsDevicePtrClause::CreateEmpty(const ASTContext &C, unsigned N) { void *Mem = C.Allocate(totalSizeToAlloc(N)); return new (Mem) OMPIsDevicePtrClause(N); }