StmtOpenMP.h revision 0c018357b8bbb1f96bbf622a5807421e626b4228
1//===- StmtOpenMP.h - Classes for OpenMP directives and clauses --*- C++ -*-===// 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 defines OpenMP AST classes for executable directives and 11/// clauses. 12/// 13//===----------------------------------------------------------------------===// 14 15#ifndef LLVM_CLANG_AST_STMTOPENMP_H 16#define LLVM_CLANG_AST_STMTOPENMP_H 17 18#include "clang/Basic/OpenMPKinds.h" 19#include "clang/Basic/SourceLocation.h" 20#include "clang/AST/Expr.h" 21#include "clang/AST/Stmt.h" 22 23namespace clang { 24 25//===----------------------------------------------------------------------===// 26// AST classes for clauses. 27//===----------------------------------------------------------------------===// 28 29/// \brief This is a basic class for representing single OpenMP clause. 30/// 31class OMPClause { 32 /// \brief Starting location of the clause (the clause keyword). 33 SourceLocation StartLoc; 34 /// \brief Ending location of the clause. 35 SourceLocation EndLoc; 36 /// \brief Kind of the clause. 37 OpenMPClauseKind Kind; 38protected: 39 OMPClause(OpenMPClauseKind K, SourceLocation StartLoc, SourceLocation EndLoc) 40 : StartLoc(StartLoc), EndLoc(EndLoc), Kind(K) {} 41 42public: 43 44 /// \brief Returns the starting location of the clause. 45 SourceLocation getLocStart() const { return StartLoc; } 46 /// \brief Returns the ending location of the clause. 47 SourceLocation getLocEnd() const { return EndLoc; } 48 49 /// \brief Sets the starting location of the clause. 50 void setLocStart(SourceLocation Loc) { StartLoc = Loc; } 51 /// \brief Sets the ending location of the clause. 52 void setLocEnd(SourceLocation Loc) { EndLoc = Loc; } 53 54 /// \brief Returns kind of OpenMP clause (private, shared, reduction, etc.). 55 OpenMPClauseKind getClauseKind() const { return Kind; } 56 57 bool isImplicit() const { return StartLoc.isInvalid();} 58 59 StmtRange children(); 60 ConstStmtRange children() const { 61 return const_cast<OMPClause *>(this)->children(); 62 } 63 static bool classof(const OMPClause *T) { 64 return true; 65 } 66}; 67 68/// \brief This represents clauses with the list of variables like 'private', 69/// 'firstprivate', 'copyin', 'shared', or 'reduction' clauses in the 70/// '#pragma omp ...' directives. 71template <class T> 72class OMPVarList { 73 friend class OMPClauseReader; 74 /// \brief Location of '('. 75 SourceLocation LParenLoc; 76 /// \brief Number of variables in the list. 77 unsigned NumVars; 78protected: 79 /// \brief Fetches list of variables associated with this clause. 80 llvm::MutableArrayRef<Expr *> getVarRefs() { 81 return llvm::MutableArrayRef<Expr *>( 82 reinterpret_cast<Expr **>(static_cast<T *>(this) + 1), 83 NumVars); 84 } 85 86 /// \brief Sets the list of variables for this clause. 87 void setVarRefs(ArrayRef<Expr *> VL) { 88 assert(VL.size() == NumVars && 89 "Number of variables is not the same as the preallocated buffer"); 90 std::copy(VL.begin(), VL.end(), 91 reinterpret_cast<Expr **>(static_cast<T *>(this) + 1)); 92 } 93 94 /// \brief Build clause with number of variables \a N. 95 /// 96 /// \param N Number of the variables in the clause. 97 /// 98 OMPVarList(SourceLocation LParenLoc, unsigned N) 99 : LParenLoc(LParenLoc), NumVars(N) { } 100public: 101 typedef llvm::MutableArrayRef<Expr *>::iterator varlist_iterator; 102 typedef ArrayRef<const Expr *>::iterator varlist_const_iterator; 103 104 unsigned varlist_size() const { return NumVars; } 105 bool varlist_empty() const { return NumVars == 0; } 106 varlist_iterator varlist_begin() { return getVarRefs().begin(); } 107 varlist_iterator varlist_end() { return getVarRefs().end(); } 108 varlist_const_iterator varlist_begin() const { return getVarRefs().begin(); } 109 varlist_const_iterator varlist_end() const { return getVarRefs().end(); } 110 111 /// \brief Sets the location of '('. 112 void setLParenLoc(SourceLocation Loc) { LParenLoc = Loc; } 113 /// \brief Returns the location of '('. 114 SourceLocation getLParenLoc() const { return LParenLoc; } 115 116 /// \brief Fetches list of all variables in the clause. 117 ArrayRef<const Expr *> getVarRefs() const { 118 return ArrayRef<const Expr *>( 119 reinterpret_cast<const Expr *const *>(static_cast<const T *>(this) + 1), 120 NumVars); 121 } 122}; 123 124/// \brief This represents 'default' clause in the '#pragma omp ...' directive. 125/// 126/// \code 127/// #pragma omp parallel default(shared) 128/// \endcode 129/// In this example directive '#pragma omp parallel' has simple 'default' 130/// clause with kind 'shared'. 131/// 132class OMPDefaultClause : public OMPClause { 133 friend class OMPClauseReader; 134 /// \brief Location of '('. 135 SourceLocation LParenLoc; 136 /// \brief A kind of the 'default' clause. 137 OpenMPDefaultClauseKind Kind; 138 /// \brief Start location of the kind in source code. 139 SourceLocation KindKwLoc; 140 141 /// \brief Set kind of the clauses. 142 /// 143 /// \param K Argument of clause. 144 /// 145 void setDefaultKind(OpenMPDefaultClauseKind K) { Kind = K; } 146 147 /// \brief Set argument location. 148 /// 149 /// \param KLoc Argument location. 150 /// 151 void setDefaultKindKwLoc(SourceLocation KLoc) { KindKwLoc = KLoc; } 152public: 153 /// \brief Build 'default' clause with argument \a A ('none' or 'shared'). 154 /// 155 /// \param A Argument of the clause ('none' or 'shared'). 156 /// \param ALoc Starting location of the argument. 157 /// \param StartLoc Starting location of the clause. 158 /// \param LParenLoc Location of '('. 159 /// \param EndLoc Ending location of the clause. 160 /// 161 OMPDefaultClause(OpenMPDefaultClauseKind A, SourceLocation ALoc, 162 SourceLocation StartLoc, SourceLocation LParenLoc, 163 SourceLocation EndLoc) 164 : OMPClause(OMPC_default, StartLoc, EndLoc), LParenLoc(LParenLoc), 165 Kind(A), KindKwLoc(ALoc) { } 166 167 /// \brief Build an empty clause. 168 /// 169 OMPDefaultClause() 170 : OMPClause(OMPC_default, SourceLocation(), SourceLocation()), 171 LParenLoc(SourceLocation()), Kind(OMPC_DEFAULT_unknown), 172 KindKwLoc(SourceLocation()) { } 173 174 /// \brief Sets the location of '('. 175 void setLParenLoc(SourceLocation Loc) { LParenLoc = Loc; } 176 /// \brief Returns the location of '('. 177 SourceLocation getLParenLoc() const { return LParenLoc; } 178 179 /// \brief Returns kind of the clause. 180 OpenMPDefaultClauseKind getDefaultKind() const { return Kind; } 181 182 /// \brief Returns location of clause kind. 183 SourceLocation getDefaultKindKwLoc() const { return KindKwLoc; } 184 185 static bool classof(const OMPClause *T) { 186 return T->getClauseKind() == OMPC_default; 187 } 188 189 StmtRange children() { 190 return StmtRange(); 191 } 192}; 193 194/// \brief This represents clause 'private' in the '#pragma omp ...' directives. 195/// 196/// \code 197/// #pragma omp parallel private(a,b) 198/// \endcode 199/// In this example directive '#pragma omp parallel' has clause 'private' 200/// with the variables 'a' and 'b'. 201/// 202class OMPPrivateClause : public OMPClause, public OMPVarList<OMPPrivateClause> { 203 /// \brief Build clause with number of variables \a N. 204 /// 205 /// \param StartLoc Starting location of the clause. 206 /// \param LParenLoc Location of '('. 207 /// \param EndLoc Ending location of the clause. 208 /// \param N Number of the variables in the clause. 209 /// 210 OMPPrivateClause(SourceLocation StartLoc, SourceLocation LParenLoc, 211 SourceLocation EndLoc, unsigned N) 212 : OMPClause(OMPC_private, StartLoc, EndLoc), 213 OMPVarList<OMPPrivateClause>(LParenLoc, N) { } 214 215 /// \brief Build an empty clause. 216 /// 217 /// \param N Number of variables. 218 /// 219 explicit OMPPrivateClause(unsigned N) 220 : OMPClause(OMPC_private, SourceLocation(), SourceLocation()), 221 OMPVarList<OMPPrivateClause>(SourceLocation(), N) { } 222public: 223 /// \brief Creates clause with a list of variables \a VL. 224 /// 225 /// \param C AST context. 226 /// \param StartLoc Starting location of the clause. 227 /// \param LParenLoc Location of '('. 228 /// \param EndLoc Ending location of the clause. 229 /// \param VL List of references to the variables. 230 /// 231 static OMPPrivateClause *Create(const ASTContext &C, SourceLocation StartLoc, 232 SourceLocation LParenLoc, 233 SourceLocation EndLoc, 234 ArrayRef<Expr *> VL); 235 /// \brief Creates an empty clause with the place for \a N variables. 236 /// 237 /// \param C AST context. 238 /// \param N The number of variables. 239 /// 240 static OMPPrivateClause *CreateEmpty(const ASTContext &C, unsigned N); 241 242 StmtRange children() { 243 return StmtRange(reinterpret_cast<Stmt **>(varlist_begin()), 244 reinterpret_cast<Stmt **>(varlist_end())); 245 } 246 247 static bool classof(const OMPClause *T) { 248 return T->getClauseKind() == OMPC_private; 249 } 250}; 251 252/// \brief This represents clause 'shared' in the '#pragma omp ...' directives. 253/// 254/// \code 255/// #pragma omp parallel shared(a,b) 256/// \endcode 257/// In this example directive '#pragma omp parallel' has clause 'shared' 258/// with the variables 'a' and 'b'. 259/// 260class OMPSharedClause : public OMPClause, public OMPVarList<OMPSharedClause> { 261 /// \brief Build clause with number of variables \a N. 262 /// 263 /// \param StartLoc Starting location of the clause. 264 /// \param LParenLoc Location of '('. 265 /// \param EndLoc Ending location of the clause. 266 /// \param N Number of the variables in the clause. 267 /// 268 OMPSharedClause(SourceLocation StartLoc, SourceLocation LParenLoc, 269 SourceLocation EndLoc, unsigned N) 270 : OMPClause(OMPC_shared, StartLoc, EndLoc), 271 OMPVarList<OMPSharedClause>(LParenLoc, N) { } 272 273 /// \brief Build an empty clause. 274 /// 275 /// \param N Number of variables. 276 /// 277 explicit OMPSharedClause(unsigned N) 278 : OMPClause(OMPC_private, SourceLocation(), SourceLocation()), 279 OMPVarList<OMPSharedClause>(SourceLocation(), N) { } 280public: 281 /// \brief Creates clause with a list of variables \a VL. 282 /// 283 /// \param C AST context. 284 /// \param StartLoc Starting location of the clause. 285 /// \param LParenLoc Location of '('. 286 /// \param EndLoc Ending location of the clause. 287 /// \param VL List of references to the variables. 288 /// 289 static OMPSharedClause *Create(const ASTContext &C, SourceLocation StartLoc, 290 SourceLocation LParenLoc, 291 SourceLocation EndLoc, ArrayRef<Expr *> VL); 292 /// \brief Creates an empty clause with \a N variables. 293 /// 294 /// \param C AST context. 295 /// \param N The number of variables. 296 /// 297 static OMPSharedClause *CreateEmpty(const ASTContext &C, unsigned N); 298 299 StmtRange children() { 300 return StmtRange(reinterpret_cast<Stmt **>(varlist_begin()), 301 reinterpret_cast<Stmt **>(varlist_end())); 302 } 303 304 static bool classof(const OMPClause *T) { 305 return T->getClauseKind() == OMPC_shared; 306 } 307}; 308 309//===----------------------------------------------------------------------===// 310// AST classes for directives. 311//===----------------------------------------------------------------------===// 312 313/// \brief This is a basic class for representing single OpenMP executable 314/// directive. 315/// 316class OMPExecutableDirective : public Stmt { 317 friend class ASTStmtReader; 318 /// \brief Kind of the directive. 319 OpenMPDirectiveKind Kind; 320 /// \brief Starting location of the directive (directive keyword). 321 SourceLocation StartLoc; 322 /// \brief Ending location of the directive. 323 SourceLocation EndLoc; 324 /// \brief Pointer to the list of clauses. 325 llvm::MutableArrayRef<OMPClause *> Clauses; 326 /// \brief Associated statement (if any) and expressions. 327 llvm::MutableArrayRef<Stmt *> StmtAndExpressions; 328protected: 329 /// \brief Build instance of directive of class \a K. 330 /// 331 /// \param SC Statement class. 332 /// \param K Kind of OpenMP directive. 333 /// \param StartLoc Starting location of the directive (directive keyword). 334 /// \param EndLoc Ending location of the directive. 335 /// 336 template <typename T> 337 OMPExecutableDirective(const T *, StmtClass SC, OpenMPDirectiveKind K, 338 SourceLocation StartLoc, SourceLocation EndLoc, 339 unsigned NumClauses, unsigned NumberOfExpressions) 340 : Stmt(SC), Kind(K), StartLoc(StartLoc), EndLoc(EndLoc), 341 Clauses(reinterpret_cast<OMPClause **>(static_cast<T *>(this) + 1), 342 NumClauses), 343 StmtAndExpressions(reinterpret_cast<Stmt **>(Clauses.end()), 344 NumberOfExpressions) { } 345 346 /// \brief Sets the list of variables for this clause. 347 /// 348 /// \param Clauses The list of clauses for the directive. 349 /// 350 void setClauses(ArrayRef<OMPClause *> Clauses); 351 352 /// \brief Set the associated statement for the directive. 353 /// 354 /// /param S Associated statement. 355 /// 356 void setAssociatedStmt(Stmt *S) { 357 StmtAndExpressions[0] = S; 358 } 359 360public: 361 /// \brief Returns starting location of directive kind. 362 SourceLocation getLocStart() const { return StartLoc; } 363 /// \brief Returns ending location of directive. 364 SourceLocation getLocEnd() const { return EndLoc; } 365 366 /// \brief Set starting location of directive kind. 367 /// 368 /// \param Loc New starting location of directive. 369 /// 370 void setLocStart(SourceLocation Loc) { StartLoc = Loc; } 371 /// \brief Set ending location of directive. 372 /// 373 /// \param Loc New ending location of directive. 374 /// 375 void setLocEnd(SourceLocation Loc) { EndLoc = Loc; } 376 377 /// \brief Get number of clauses. 378 unsigned getNumClauses() const { return Clauses.size(); } 379 380 /// \brief Returns specified clause. 381 /// 382 /// \param i Number of clause. 383 /// 384 OMPClause *getClause(unsigned i) const { 385 assert(i < Clauses.size() && "index out of bound!"); 386 return Clauses[i]; 387 } 388 389 /// \brief Returns statement associated with the directive. 390 Stmt *getAssociatedStmt() const { 391 return StmtAndExpressions[0]; 392 } 393 394 OpenMPDirectiveKind getDirectiveKind() const { return Kind; } 395 396 static bool classof(const Stmt *S) { 397 return S->getStmtClass() >= firstOMPExecutableDirectiveConstant && 398 S->getStmtClass() <= lastOMPExecutableDirectiveConstant; 399 } 400 401 child_range children() { 402 return child_range(StmtAndExpressions.begin(), StmtAndExpressions.end()); 403 } 404 405 ArrayRef<OMPClause *> clauses() { return Clauses; } 406 407 ArrayRef<OMPClause *> clauses() const { return Clauses; } 408}; 409 410/// \brief This represents '#pragma omp parallel' directive. 411/// 412/// \code 413/// #pragma omp parallel private(a,b) reduction(+: c,d) 414/// \endcode 415/// In this example directive '#pragma omp parallel' has clauses 'private' 416/// with the variables 'a' and 'b' and 'reduction' with operator '+' and 417/// variables 'c' and 'd'. 418/// 419class OMPParallelDirective : public OMPExecutableDirective { 420 /// \brief Build directive with the given start and end location. 421 /// 422 /// \param StartLoc Starting location of the directive (directive keyword). 423 /// \param EndLoc Ending Location of the directive. 424 /// 425 OMPParallelDirective(SourceLocation StartLoc, SourceLocation EndLoc, 426 unsigned N) 427 : OMPExecutableDirective(this, OMPParallelDirectiveClass, OMPD_parallel, 428 StartLoc, EndLoc, N, 1) { } 429 430 /// \brief Build an empty directive. 431 /// 432 /// \param N Number of clauses. 433 /// 434 explicit OMPParallelDirective(unsigned N) 435 : OMPExecutableDirective(this, OMPParallelDirectiveClass, OMPD_parallel, 436 SourceLocation(), SourceLocation(), N, 1) { } 437public: 438 /// \brief Creates directive with a list of \a Clauses. 439 /// 440 /// \param C AST context. 441 /// \param StartLoc Starting location of the directive kind. 442 /// \param EndLoc Ending Location of the directive. 443 /// \param Clauses List of clauses. 444 /// \param AssociatedStmt Statement associated with the directive. 445 /// 446 static OMPParallelDirective *Create(const ASTContext &C, 447 SourceLocation StartLoc, 448 SourceLocation EndLoc, 449 ArrayRef<OMPClause *> Clauses, 450 Stmt *AssociatedStmt); 451 452 /// \brief Creates an empty directive with the place for \a N clauses. 453 /// 454 /// \param C AST context. 455 /// \param N The number of clauses. 456 /// 457 static OMPParallelDirective *CreateEmpty(const ASTContext &C, unsigned N, 458 EmptyShell); 459 460 static bool classof(const Stmt *T) { 461 return T->getStmtClass() == OMPParallelDirectiveClass; 462 } 463}; 464 465} // end namespace clang 466 467#endif 468