diff options
Diffstat (limited to 'clang/lib/Sema')
-rw-r--r-- | clang/lib/Sema/SemaOpenMP.cpp | 57 | ||||
-rw-r--r-- | clang/lib/Sema/TreeTransform.h | 36 |
2 files changed, 92 insertions, 1 deletions
diff --git a/clang/lib/Sema/SemaOpenMP.cpp b/clang/lib/Sema/SemaOpenMP.cpp index dbccb69aad7..150b21a8c92 100644 --- a/clang/lib/Sema/SemaOpenMP.cpp +++ b/clang/lib/Sema/SemaOpenMP.cpp @@ -10152,6 +10152,10 @@ OMPClause *Sema::ActOnOpenMPVarListClause( case OMPC_is_device_ptr: Res = ActOnOpenMPIsDevicePtrClause(VarList, Locs); break; + case OMPC_allocate: + Res = ActOnOpenMPAllocateClause(TailExpr, VarList, StartLoc, LParenLoc, + ColonLoc, EndLoc); + break; case OMPC_if: case OMPC_final: case OMPC_num_threads: @@ -10167,7 +10171,6 @@ OMPClause *Sema::ActOnOpenMPVarListClause( case OMPC_untied: case OMPC_mergeable: case OMPC_threadprivate: - case OMPC_allocate: case OMPC_read: case OMPC_write: case OMPC_update: @@ -14700,3 +14703,55 @@ OMPClause *Sema::ActOnOpenMPIsDevicePtrClause(ArrayRef<Expr *> VarList, MVLI.VarBaseDeclarations, MVLI.VarComponents); } + +OMPClause *Sema::ActOnOpenMPAllocateClause( + Expr *Allocator, ArrayRef<Expr *> VarList, SourceLocation StartLoc, + SourceLocation ColonLoc, SourceLocation LParenLoc, SourceLocation EndLoc) { + if (Allocator) { + // OpenMP [2.11.4 allocate Clause, Description] + // allocator is an expression of omp_allocator_handle_t type. + if (!findOMPAllocatorHandleT(*this, Allocator->getExprLoc(), DSAStack)) + return nullptr; + + ExprResult AllocatorRes = DefaultLvalueConversion(Allocator); + if (AllocatorRes.isInvalid()) + return nullptr; + AllocatorRes = PerformImplicitConversion(AllocatorRes.get(), + DSAStack->getOMPAllocatorHandleT(), + Sema::AA_Initializing, + /*AllowExplicit=*/true); + if (AllocatorRes.isInvalid()) + return nullptr; + Allocator = AllocatorRes.get(); + } + // Analyze and build list of variables. + SmallVector<Expr *, 8> Vars; + for (Expr *RefExpr : VarList) { + assert(RefExpr && "NULL expr in OpenMP private clause."); + SourceLocation ELoc; + SourceRange ERange; + Expr *SimpleRefExpr = RefExpr; + auto Res = getPrivateItem(*this, SimpleRefExpr, ELoc, ERange); + if (Res.second) { + // It will be analyzed later. + Vars.push_back(RefExpr); + } + ValueDecl *D = Res.first; + if (!D) + continue; + + auto *VD = dyn_cast<VarDecl>(D); + DeclRefExpr *Ref = nullptr; + if (!VD && !CurContext->isDependentContext()) + Ref = buildCapture(*this, D, SimpleRefExpr, /*WithInit=*/false); + Vars.push_back((VD || CurContext->isDependentContext()) + ? RefExpr->IgnoreParens() + : Ref); + } + + if (Vars.empty()) + return nullptr; + + return OMPAllocateClause::Create(Context, StartLoc, LParenLoc, Allocator, + ColonLoc, EndLoc, Vars); +} diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index 93c5bdfed4c..a8ea6b01d1c 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/TreeTransform.h @@ -1827,6 +1827,19 @@ public: VarList, Locs, UnresolvedMappers); } + /// Build a new OpenMP 'allocate' clause. + /// + /// By default, performs semantic analysis to build the new OpenMP clause. + /// Subclasses may override this routine to provide different behavior. + OMPClause *RebuildOMPAllocateClause(Expr *Allocate, ArrayRef<Expr *> VarList, + SourceLocation StartLoc, + SourceLocation LParenLoc, + SourceLocation ColonLoc, + SourceLocation EndLoc) { + return getSema().ActOnOpenMPAllocateClause(Allocate, VarList, StartLoc, + LParenLoc, ColonLoc, EndLoc); + } + /// Build a new OpenMP 'num_teams' clause. /// /// By default, performs semantic analysis to build the new statement. @@ -8908,6 +8921,29 @@ OMPClause *TreeTransform<Derived>::TransformOMPMapClause(OMPMapClause *C) { template <typename Derived> OMPClause * +TreeTransform<Derived>::TransformOMPAllocateClause(OMPAllocateClause *C) { + Expr *Allocator = C->getAllocator(); + if (Allocator) { + ExprResult AllocatorRes = getDerived().TransformExpr(Allocator); + if (AllocatorRes.isInvalid()) + return nullptr; + Allocator = AllocatorRes.get(); + } + llvm::SmallVector<Expr *, 16> Vars; + Vars.reserve(C->varlist_size()); + for (auto *VE : C->varlists()) { + ExprResult EVar = getDerived().TransformExpr(cast<Expr>(VE)); + if (EVar.isInvalid()) + return nullptr; + Vars.push_back(EVar.get()); + } + return getDerived().RebuildOMPAllocateClause( + Allocator, Vars, C->getBeginLoc(), C->getLParenLoc(), C->getColonLoc(), + C->getEndLoc()); +} + +template <typename Derived> +OMPClause * TreeTransform<Derived>::TransformOMPNumTeamsClause(OMPNumTeamsClause *C) { ExprResult E = getDerived().TransformExpr(C->getNumTeams()); if (E.isInvalid()) |