1 //===- OpenMPClause.cpp - Classes for OpenMP clauses ----------------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file implements the subclesses of Stmt class declared in OpenMPClause.h 10 // 11 //===----------------------------------------------------------------------===// 12 13 #include "clang/AST/OpenMPClause.h" 14 #include "clang/AST/ASTContext.h" 15 #include "clang/AST/Decl.h" 16 #include "clang/AST/DeclOpenMP.h" 17 #include "clang/Basic/LLVM.h" 18 #include "llvm/ADT/SmallPtrSet.h" 19 #include "llvm/Support/Casting.h" 20 #include "llvm/Support/ErrorHandling.h" 21 #include <algorithm> 22 #include <cassert> 23 24 using namespace clang; 25 26 OMPClause::child_range OMPClause::children() { 27 switch (getClauseKind()) { 28 default: 29 break; 30 #define OPENMP_CLAUSE(Name, Class) \ 31 case OMPC_##Name: \ 32 return static_cast<Class *>(this)->children(); 33 #include "clang/Basic/OpenMPKinds.def" 34 } 35 llvm_unreachable("unknown OMPClause"); 36 } 37 38 OMPClause::child_range OMPClause::used_children() { 39 switch (getClauseKind()) { 40 #define OPENMP_CLAUSE(Name, Class) \ 41 case OMPC_##Name: \ 42 return static_cast<Class *>(this)->used_children(); 43 #include "clang/Basic/OpenMPKinds.def" 44 case OMPC_threadprivate: 45 case OMPC_uniform: 46 case OMPC_unknown: 47 break; 48 } 49 llvm_unreachable("unknown OMPClause"); 50 } 51 52 OMPClauseWithPreInit *OMPClauseWithPreInit::get(OMPClause *C) { 53 auto *Res = OMPClauseWithPreInit::get(const_cast<const OMPClause *>(C)); 54 return Res ? const_cast<OMPClauseWithPreInit *>(Res) : nullptr; 55 } 56 57 const OMPClauseWithPreInit *OMPClauseWithPreInit::get(const OMPClause *C) { 58 switch (C->getClauseKind()) { 59 case OMPC_schedule: 60 return static_cast<const OMPScheduleClause *>(C); 61 case OMPC_dist_schedule: 62 return static_cast<const OMPDistScheduleClause *>(C); 63 case OMPC_firstprivate: 64 return static_cast<const OMPFirstprivateClause *>(C); 65 case OMPC_lastprivate: 66 return static_cast<const OMPLastprivateClause *>(C); 67 case OMPC_reduction: 68 return static_cast<const OMPReductionClause *>(C); 69 case OMPC_task_reduction: 70 return static_cast<const OMPTaskReductionClause *>(C); 71 case OMPC_in_reduction: 72 return static_cast<const OMPInReductionClause *>(C); 73 case OMPC_linear: 74 return static_cast<const OMPLinearClause *>(C); 75 case OMPC_if: 76 return static_cast<const OMPIfClause *>(C); 77 case OMPC_num_threads: 78 return static_cast<const OMPNumThreadsClause *>(C); 79 case OMPC_num_teams: 80 return static_cast<const OMPNumTeamsClause *>(C); 81 case OMPC_thread_limit: 82 return static_cast<const OMPThreadLimitClause *>(C); 83 case OMPC_device: 84 return static_cast<const OMPDeviceClause *>(C); 85 case OMPC_default: 86 case OMPC_proc_bind: 87 case OMPC_final: 88 case OMPC_safelen: 89 case OMPC_simdlen: 90 case OMPC_allocator: 91 case OMPC_allocate: 92 case OMPC_collapse: 93 case OMPC_private: 94 case OMPC_shared: 95 case OMPC_aligned: 96 case OMPC_copyin: 97 case OMPC_copyprivate: 98 case OMPC_ordered: 99 case OMPC_nowait: 100 case OMPC_untied: 101 case OMPC_mergeable: 102 case OMPC_threadprivate: 103 case OMPC_flush: 104 case OMPC_read: 105 case OMPC_write: 106 case OMPC_update: 107 case OMPC_capture: 108 case OMPC_seq_cst: 109 case OMPC_depend: 110 case OMPC_threads: 111 case OMPC_simd: 112 case OMPC_map: 113 case OMPC_priority: 114 case OMPC_grainsize: 115 case OMPC_nogroup: 116 case OMPC_num_tasks: 117 case OMPC_hint: 118 case OMPC_defaultmap: 119 case OMPC_unknown: 120 case OMPC_uniform: 121 case OMPC_to: 122 case OMPC_from: 123 case OMPC_use_device_ptr: 124 case OMPC_is_device_ptr: 125 case OMPC_unified_address: 126 case OMPC_unified_shared_memory: 127 case OMPC_reverse_offload: 128 case OMPC_dynamic_allocators: 129 case OMPC_atomic_default_mem_order: 130 break; 131 } 132 133 return nullptr; 134 } 135 136 OMPClauseWithPostUpdate *OMPClauseWithPostUpdate::get(OMPClause *C) { 137 auto *Res = OMPClauseWithPostUpdate::get(const_cast<const OMPClause *>(C)); 138 return Res ? const_cast<OMPClauseWithPostUpdate *>(Res) : nullptr; 139 } 140 141 const OMPClauseWithPostUpdate *OMPClauseWithPostUpdate::get(const OMPClause *C) { 142 switch (C->getClauseKind()) { 143 case OMPC_lastprivate: 144 return static_cast<const OMPLastprivateClause *>(C); 145 case OMPC_reduction: 146 return static_cast<const OMPReductionClause *>(C); 147 case OMPC_task_reduction: 148 return static_cast<const OMPTaskReductionClause *>(C); 149 case OMPC_in_reduction: 150 return static_cast<const OMPInReductionClause *>(C); 151 case OMPC_linear: 152 return static_cast<const OMPLinearClause *>(C); 153 case OMPC_schedule: 154 case OMPC_dist_schedule: 155 case OMPC_firstprivate: 156 case OMPC_default: 157 case OMPC_proc_bind: 158 case OMPC_if: 159 case OMPC_final: 160 case OMPC_num_threads: 161 case OMPC_safelen: 162 case OMPC_simdlen: 163 case OMPC_allocator: 164 case OMPC_allocate: 165 case OMPC_collapse: 166 case OMPC_private: 167 case OMPC_shared: 168 case OMPC_aligned: 169 case OMPC_copyin: 170 case OMPC_copyprivate: 171 case OMPC_ordered: 172 case OMPC_nowait: 173 case OMPC_untied: 174 case OMPC_mergeable: 175 case OMPC_threadprivate: 176 case OMPC_flush: 177 case OMPC_read: 178 case OMPC_write: 179 case OMPC_update: 180 case OMPC_capture: 181 case OMPC_seq_cst: 182 case OMPC_depend: 183 case OMPC_device: 184 case OMPC_threads: 185 case OMPC_simd: 186 case OMPC_map: 187 case OMPC_num_teams: 188 case OMPC_thread_limit: 189 case OMPC_priority: 190 case OMPC_grainsize: 191 case OMPC_nogroup: 192 case OMPC_num_tasks: 193 case OMPC_hint: 194 case OMPC_defaultmap: 195 case OMPC_unknown: 196 case OMPC_uniform: 197 case OMPC_to: 198 case OMPC_from: 199 case OMPC_use_device_ptr: 200 case OMPC_is_device_ptr: 201 case OMPC_unified_address: 202 case OMPC_unified_shared_memory: 203 case OMPC_reverse_offload: 204 case OMPC_dynamic_allocators: 205 case OMPC_atomic_default_mem_order: 206 break; 207 } 208 209 return nullptr; 210 } 211 212 OMPOrderedClause *OMPOrderedClause::Create(const ASTContext &C, Expr *Num, 213 unsigned NumLoops, 214 SourceLocation StartLoc, 215 SourceLocation LParenLoc, 216 SourceLocation EndLoc) { 217 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * NumLoops)); 218 auto *Clause = 219 new (Mem) OMPOrderedClause(Num, NumLoops, StartLoc, LParenLoc, EndLoc); 220 for (unsigned I = 0; I < NumLoops; ++I) { 221 Clause->setLoopNumIterations(I, nullptr); 222 Clause->setLoopCounter(I, nullptr); 223 } 224 return Clause; 225 } 226 227 OMPOrderedClause *OMPOrderedClause::CreateEmpty(const ASTContext &C, 228 unsigned NumLoops) { 229 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * NumLoops)); 230 auto *Clause = new (Mem) OMPOrderedClause(NumLoops); 231 for (unsigned I = 0; I < NumLoops; ++I) { 232 Clause->setLoopNumIterations(I, nullptr); 233 Clause->setLoopCounter(I, nullptr); 234 } 235 return Clause; 236 } 237 238 void OMPOrderedClause::setLoopNumIterations(unsigned NumLoop, 239 Expr *NumIterations) { 240 assert(NumLoop < NumberOfLoops && "out of loops number."); 241 getTrailingObjects<Expr *>()[NumLoop] = NumIterations; 242 } 243 244 ArrayRef<Expr *> OMPOrderedClause::getLoopNumIterations() const { 245 return llvm::makeArrayRef(getTrailingObjects<Expr *>(), NumberOfLoops); 246 } 247 248 void OMPOrderedClause::setLoopCounter(unsigned NumLoop, Expr *Counter) { 249 assert(NumLoop < NumberOfLoops && "out of loops number."); 250 getTrailingObjects<Expr *>()[NumberOfLoops + NumLoop] = Counter; 251 } 252 253 Expr *OMPOrderedClause::getLoopCounter(unsigned NumLoop) { 254 assert(NumLoop < NumberOfLoops && "out of loops number."); 255 return getTrailingObjects<Expr *>()[NumberOfLoops + NumLoop]; 256 } 257 258 const Expr *OMPOrderedClause::getLoopCounter(unsigned NumLoop) const { 259 assert(NumLoop < NumberOfLoops && "out of loops number."); 260 return getTrailingObjects<Expr *>()[NumberOfLoops + NumLoop]; 261 } 262 263 void OMPPrivateClause::setPrivateCopies(ArrayRef<Expr *> VL) { 264 assert(VL.size() == varlist_size() && 265 "Number of private copies is not the same as the preallocated buffer"); 266 std::copy(VL.begin(), VL.end(), varlist_end()); 267 } 268 269 OMPPrivateClause * 270 OMPPrivateClause::Create(const ASTContext &C, SourceLocation StartLoc, 271 SourceLocation LParenLoc, SourceLocation EndLoc, 272 ArrayRef<Expr *> VL, ArrayRef<Expr *> PrivateVL) { 273 // Allocate space for private variables and initializer expressions. 274 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * VL.size())); 275 OMPPrivateClause *Clause = 276 new (Mem) OMPPrivateClause(StartLoc, LParenLoc, EndLoc, VL.size()); 277 Clause->setVarRefs(VL); 278 Clause->setPrivateCopies(PrivateVL); 279 return Clause; 280 } 281 282 OMPPrivateClause *OMPPrivateClause::CreateEmpty(const ASTContext &C, 283 unsigned N) { 284 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(2 * N)); 285 return new (Mem) OMPPrivateClause(N); 286 } 287 288 void OMPFirstprivateClause::setPrivateCopies(ArrayRef<Expr *> VL) { 289 assert(VL.size() == varlist_size() && 290 "Number of private copies is not the same as the preallocated buffer"); 291 std::copy(VL.begin(), VL.end(), varlist_end()); 292 } 293 294 void OMPFirstprivateClause::setInits(ArrayRef<Expr *> VL) { 295 assert(VL.size() == varlist_size() && 296 "Number of inits is not the same as the preallocated buffer"); 297 std::copy(VL.begin(), VL.end(), getPrivateCopies().end()); 298 } 299 300 OMPFirstprivateClause * 301 OMPFirstprivateClause::Create(const ASTContext &C, SourceLocation StartLoc, 302 SourceLocation LParenLoc, SourceLocation EndLoc, 303 ArrayRef<Expr *> VL, ArrayRef<Expr *> PrivateVL, 304 ArrayRef<Expr *> InitVL, Stmt *PreInit) { 305 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(3 * VL.size())); 306 OMPFirstprivateClause *Clause = 307 new (Mem) OMPFirstprivateClause(StartLoc, LParenLoc, EndLoc, VL.size()); 308 Clause->setVarRefs(VL); 309 Clause->setPrivateCopies(PrivateVL); 310 Clause->setInits(InitVL); 311 Clause->setPreInitStmt(PreInit); 312 return Clause; 313 } 314 315 OMPFirstprivateClause *OMPFirstprivateClause::CreateEmpty(const ASTContext &C, 316 unsigned N) { 317 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(3 * N)); 318 return new (Mem) OMPFirstprivateClause(N); 319 } 320 321 void OMPLastprivateClause::setPrivateCopies(ArrayRef<Expr *> PrivateCopies) { 322 assert(PrivateCopies.size() == varlist_size() && 323 "Number of private copies is not the same as the preallocated buffer"); 324 std::copy(PrivateCopies.begin(), PrivateCopies.end(), varlist_end()); 325 } 326 327 void OMPLastprivateClause::setSourceExprs(ArrayRef<Expr *> SrcExprs) { 328 assert(SrcExprs.size() == varlist_size() && "Number of source expressions is " 329 "not the same as the " 330 "preallocated buffer"); 331 std::copy(SrcExprs.begin(), SrcExprs.end(), getPrivateCopies().end()); 332 } 333 334 void OMPLastprivateClause::setDestinationExprs(ArrayRef<Expr *> DstExprs) { 335 assert(DstExprs.size() == varlist_size() && "Number of destination " 336 "expressions is not the same as " 337 "the preallocated buffer"); 338 std::copy(DstExprs.begin(), DstExprs.end(), getSourceExprs().end()); 339 } 340 341 void OMPLastprivateClause::setAssignmentOps(ArrayRef<Expr *> AssignmentOps) { 342 assert(AssignmentOps.size() == varlist_size() && 343 "Number of assignment expressions is not the same as the preallocated " 344 "buffer"); 345 std::copy(AssignmentOps.begin(), AssignmentOps.end(), 346 getDestinationExprs().end()); 347 } 348 349 OMPLastprivateClause *OMPLastprivateClause::Create( 350 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, 351 SourceLocation EndLoc, ArrayRef<Expr *> VL, ArrayRef<Expr *> SrcExprs, 352 ArrayRef<Expr *> DstExprs, ArrayRef<Expr *> AssignmentOps, Stmt *PreInit, 353 Expr *PostUpdate) { 354 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * VL.size())); 355 OMPLastprivateClause *Clause = 356 new (Mem) OMPLastprivateClause(StartLoc, LParenLoc, EndLoc, VL.size()); 357 Clause->setVarRefs(VL); 358 Clause->setSourceExprs(SrcExprs); 359 Clause->setDestinationExprs(DstExprs); 360 Clause->setAssignmentOps(AssignmentOps); 361 Clause->setPreInitStmt(PreInit); 362 Clause->setPostUpdateExpr(PostUpdate); 363 return Clause; 364 } 365 366 OMPLastprivateClause *OMPLastprivateClause::CreateEmpty(const ASTContext &C, 367 unsigned N) { 368 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * N)); 369 return new (Mem) OMPLastprivateClause(N); 370 } 371 372 OMPSharedClause *OMPSharedClause::Create(const ASTContext &C, 373 SourceLocation StartLoc, 374 SourceLocation LParenLoc, 375 SourceLocation EndLoc, 376 ArrayRef<Expr *> VL) { 377 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size())); 378 OMPSharedClause *Clause = 379 new (Mem) OMPSharedClause(StartLoc, LParenLoc, EndLoc, VL.size()); 380 Clause->setVarRefs(VL); 381 return Clause; 382 } 383 384 OMPSharedClause *OMPSharedClause::CreateEmpty(const ASTContext &C, unsigned N) { 385 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N)); 386 return new (Mem) OMPSharedClause(N); 387 } 388 389 void OMPLinearClause::setPrivates(ArrayRef<Expr *> PL) { 390 assert(PL.size() == varlist_size() && 391 "Number of privates is not the same as the preallocated buffer"); 392 std::copy(PL.begin(), PL.end(), varlist_end()); 393 } 394 395 void OMPLinearClause::setInits(ArrayRef<Expr *> IL) { 396 assert(IL.size() == varlist_size() && 397 "Number of inits is not the same as the preallocated buffer"); 398 std::copy(IL.begin(), IL.end(), getPrivates().end()); 399 } 400 401 void OMPLinearClause::setUpdates(ArrayRef<Expr *> UL) { 402 assert(UL.size() == varlist_size() && 403 "Number of updates is not the same as the preallocated buffer"); 404 std::copy(UL.begin(), UL.end(), getInits().end()); 405 } 406 407 void OMPLinearClause::setFinals(ArrayRef<Expr *> FL) { 408 assert(FL.size() == varlist_size() && 409 "Number of final updates is not the same as the preallocated buffer"); 410 std::copy(FL.begin(), FL.end(), getUpdates().end()); 411 } 412 413 OMPLinearClause *OMPLinearClause::Create( 414 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, 415 OpenMPLinearClauseKind Modifier, SourceLocation ModifierLoc, 416 SourceLocation ColonLoc, SourceLocation EndLoc, ArrayRef<Expr *> VL, 417 ArrayRef<Expr *> PL, ArrayRef<Expr *> IL, Expr *Step, Expr *CalcStep, 418 Stmt *PreInit, Expr *PostUpdate) { 419 // Allocate space for 4 lists (Vars, Inits, Updates, Finals) and 2 expressions 420 // (Step and CalcStep). 421 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * VL.size() + 2)); 422 OMPLinearClause *Clause = new (Mem) OMPLinearClause( 423 StartLoc, LParenLoc, Modifier, ModifierLoc, ColonLoc, EndLoc, VL.size()); 424 Clause->setVarRefs(VL); 425 Clause->setPrivates(PL); 426 Clause->setInits(IL); 427 // Fill update and final expressions with zeroes, they are provided later, 428 // after the directive construction. 429 std::fill(Clause->getInits().end(), Clause->getInits().end() + VL.size(), 430 nullptr); 431 std::fill(Clause->getUpdates().end(), Clause->getUpdates().end() + VL.size(), 432 nullptr); 433 Clause->setStep(Step); 434 Clause->setCalcStep(CalcStep); 435 Clause->setPreInitStmt(PreInit); 436 Clause->setPostUpdateExpr(PostUpdate); 437 return Clause; 438 } 439 440 OMPLinearClause *OMPLinearClause::CreateEmpty(const ASTContext &C, 441 unsigned NumVars) { 442 // Allocate space for 4 lists (Vars, Inits, Updates, Finals) and 2 expressions 443 // (Step and CalcStep). 444 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * NumVars + 2)); 445 return new (Mem) OMPLinearClause(NumVars); 446 } 447 448 OMPAlignedClause * 449 OMPAlignedClause::Create(const ASTContext &C, SourceLocation StartLoc, 450 SourceLocation LParenLoc, SourceLocation ColonLoc, 451 SourceLocation EndLoc, ArrayRef<Expr *> VL, Expr *A) { 452 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size() + 1)); 453 OMPAlignedClause *Clause = new (Mem) 454 OMPAlignedClause(StartLoc, LParenLoc, ColonLoc, EndLoc, VL.size()); 455 Clause->setVarRefs(VL); 456 Clause->setAlignment(A); 457 return Clause; 458 } 459 460 OMPAlignedClause *OMPAlignedClause::CreateEmpty(const ASTContext &C, 461 unsigned NumVars) { 462 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(NumVars + 1)); 463 return new (Mem) OMPAlignedClause(NumVars); 464 } 465 466 void OMPCopyinClause::setSourceExprs(ArrayRef<Expr *> SrcExprs) { 467 assert(SrcExprs.size() == varlist_size() && "Number of source expressions is " 468 "not the same as the " 469 "preallocated buffer"); 470 std::copy(SrcExprs.begin(), SrcExprs.end(), varlist_end()); 471 } 472 473 void OMPCopyinClause::setDestinationExprs(ArrayRef<Expr *> DstExprs) { 474 assert(DstExprs.size() == varlist_size() && "Number of destination " 475 "expressions is not the same as " 476 "the preallocated buffer"); 477 std::copy(DstExprs.begin(), DstExprs.end(), getSourceExprs().end()); 478 } 479 480 void OMPCopyinClause::setAssignmentOps(ArrayRef<Expr *> AssignmentOps) { 481 assert(AssignmentOps.size() == varlist_size() && 482 "Number of assignment expressions is not the same as the preallocated " 483 "buffer"); 484 std::copy(AssignmentOps.begin(), AssignmentOps.end(), 485 getDestinationExprs().end()); 486 } 487 488 OMPCopyinClause *OMPCopyinClause::Create( 489 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, 490 SourceLocation EndLoc, ArrayRef<Expr *> VL, ArrayRef<Expr *> SrcExprs, 491 ArrayRef<Expr *> DstExprs, ArrayRef<Expr *> AssignmentOps) { 492 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(4 * VL.size())); 493 OMPCopyinClause *Clause = 494 new (Mem) OMPCopyinClause(StartLoc, LParenLoc, EndLoc, VL.size()); 495 Clause->setVarRefs(VL); 496 Clause->setSourceExprs(SrcExprs); 497 Clause->setDestinationExprs(DstExprs); 498 Clause->setAssignmentOps(AssignmentOps); 499 return Clause; 500 } 501 502 OMPCopyinClause *OMPCopyinClause::CreateEmpty(const ASTContext &C, unsigned N) { 503 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(4 * N)); 504 return new (Mem) OMPCopyinClause(N); 505 } 506 507 void OMPCopyprivateClause::setSourceExprs(ArrayRef<Expr *> SrcExprs) { 508 assert(SrcExprs.size() == varlist_size() && "Number of source expressions is " 509 "not the same as the " 510 "preallocated buffer"); 511 std::copy(SrcExprs.begin(), SrcExprs.end(), varlist_end()); 512 } 513 514 void OMPCopyprivateClause::setDestinationExprs(ArrayRef<Expr *> DstExprs) { 515 assert(DstExprs.size() == varlist_size() && "Number of destination " 516 "expressions is not the same as " 517 "the preallocated buffer"); 518 std::copy(DstExprs.begin(), DstExprs.end(), getSourceExprs().end()); 519 } 520 521 void OMPCopyprivateClause::setAssignmentOps(ArrayRef<Expr *> AssignmentOps) { 522 assert(AssignmentOps.size() == varlist_size() && 523 "Number of assignment expressions is not the same as the preallocated " 524 "buffer"); 525 std::copy(AssignmentOps.begin(), AssignmentOps.end(), 526 getDestinationExprs().end()); 527 } 528 529 OMPCopyprivateClause *OMPCopyprivateClause::Create( 530 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, 531 SourceLocation EndLoc, ArrayRef<Expr *> VL, ArrayRef<Expr *> SrcExprs, 532 ArrayRef<Expr *> DstExprs, ArrayRef<Expr *> AssignmentOps) { 533 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(4 * VL.size())); 534 OMPCopyprivateClause *Clause = 535 new (Mem) OMPCopyprivateClause(StartLoc, LParenLoc, EndLoc, VL.size()); 536 Clause->setVarRefs(VL); 537 Clause->setSourceExprs(SrcExprs); 538 Clause->setDestinationExprs(DstExprs); 539 Clause->setAssignmentOps(AssignmentOps); 540 return Clause; 541 } 542 543 OMPCopyprivateClause *OMPCopyprivateClause::CreateEmpty(const ASTContext &C, 544 unsigned N) { 545 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(4 * N)); 546 return new (Mem) OMPCopyprivateClause(N); 547 } 548 549 void OMPReductionClause::setPrivates(ArrayRef<Expr *> Privates) { 550 assert(Privates.size() == varlist_size() && 551 "Number of private copies is not the same as the preallocated buffer"); 552 std::copy(Privates.begin(), Privates.end(), varlist_end()); 553 } 554 555 void OMPReductionClause::setLHSExprs(ArrayRef<Expr *> LHSExprs) { 556 assert( 557 LHSExprs.size() == varlist_size() && 558 "Number of LHS expressions is not the same as the preallocated buffer"); 559 std::copy(LHSExprs.begin(), LHSExprs.end(), getPrivates().end()); 560 } 561 562 void OMPReductionClause::setRHSExprs(ArrayRef<Expr *> RHSExprs) { 563 assert( 564 RHSExprs.size() == varlist_size() && 565 "Number of RHS expressions is not the same as the preallocated buffer"); 566 std::copy(RHSExprs.begin(), RHSExprs.end(), getLHSExprs().end()); 567 } 568 569 void OMPReductionClause::setReductionOps(ArrayRef<Expr *> ReductionOps) { 570 assert(ReductionOps.size() == varlist_size() && "Number of reduction " 571 "expressions is not the same " 572 "as the preallocated buffer"); 573 std::copy(ReductionOps.begin(), ReductionOps.end(), getRHSExprs().end()); 574 } 575 576 OMPReductionClause *OMPReductionClause::Create( 577 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, 578 SourceLocation EndLoc, SourceLocation ColonLoc, ArrayRef<Expr *> VL, 579 NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo, 580 ArrayRef<Expr *> Privates, ArrayRef<Expr *> LHSExprs, 581 ArrayRef<Expr *> RHSExprs, ArrayRef<Expr *> ReductionOps, Stmt *PreInit, 582 Expr *PostUpdate) { 583 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * VL.size())); 584 OMPReductionClause *Clause = new (Mem) OMPReductionClause( 585 StartLoc, LParenLoc, EndLoc, ColonLoc, VL.size(), QualifierLoc, NameInfo); 586 Clause->setVarRefs(VL); 587 Clause->setPrivates(Privates); 588 Clause->setLHSExprs(LHSExprs); 589 Clause->setRHSExprs(RHSExprs); 590 Clause->setReductionOps(ReductionOps); 591 Clause->setPreInitStmt(PreInit); 592 Clause->setPostUpdateExpr(PostUpdate); 593 return Clause; 594 } 595 596 OMPReductionClause *OMPReductionClause::CreateEmpty(const ASTContext &C, 597 unsigned N) { 598 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * N)); 599 return new (Mem) OMPReductionClause(N); 600 } 601 602 void OMPTaskReductionClause::setPrivates(ArrayRef<Expr *> Privates) { 603 assert(Privates.size() == varlist_size() && 604 "Number of private copies is not the same as the preallocated buffer"); 605 std::copy(Privates.begin(), Privates.end(), varlist_end()); 606 } 607 608 void OMPTaskReductionClause::setLHSExprs(ArrayRef<Expr *> LHSExprs) { 609 assert( 610 LHSExprs.size() == varlist_size() && 611 "Number of LHS expressions is not the same as the preallocated buffer"); 612 std::copy(LHSExprs.begin(), LHSExprs.end(), getPrivates().end()); 613 } 614 615 void OMPTaskReductionClause::setRHSExprs(ArrayRef<Expr *> RHSExprs) { 616 assert( 617 RHSExprs.size() == varlist_size() && 618 "Number of RHS expressions is not the same as the preallocated buffer"); 619 std::copy(RHSExprs.begin(), RHSExprs.end(), getLHSExprs().end()); 620 } 621 622 void OMPTaskReductionClause::setReductionOps(ArrayRef<Expr *> ReductionOps) { 623 assert(ReductionOps.size() == varlist_size() && "Number of task reduction " 624 "expressions is not the same " 625 "as the preallocated buffer"); 626 std::copy(ReductionOps.begin(), ReductionOps.end(), getRHSExprs().end()); 627 } 628 629 OMPTaskReductionClause *OMPTaskReductionClause::Create( 630 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, 631 SourceLocation EndLoc, SourceLocation ColonLoc, ArrayRef<Expr *> VL, 632 NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo, 633 ArrayRef<Expr *> Privates, ArrayRef<Expr *> LHSExprs, 634 ArrayRef<Expr *> RHSExprs, ArrayRef<Expr *> ReductionOps, Stmt *PreInit, 635 Expr *PostUpdate) { 636 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * VL.size())); 637 OMPTaskReductionClause *Clause = new (Mem) OMPTaskReductionClause( 638 StartLoc, LParenLoc, EndLoc, ColonLoc, VL.size(), QualifierLoc, NameInfo); 639 Clause->setVarRefs(VL); 640 Clause->setPrivates(Privates); 641 Clause->setLHSExprs(LHSExprs); 642 Clause->setRHSExprs(RHSExprs); 643 Clause->setReductionOps(ReductionOps); 644 Clause->setPreInitStmt(PreInit); 645 Clause->setPostUpdateExpr(PostUpdate); 646 return Clause; 647 } 648 649 OMPTaskReductionClause *OMPTaskReductionClause::CreateEmpty(const ASTContext &C, 650 unsigned N) { 651 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(5 * N)); 652 return new (Mem) OMPTaskReductionClause(N); 653 } 654 655 void OMPInReductionClause::setPrivates(ArrayRef<Expr *> Privates) { 656 assert(Privates.size() == varlist_size() && 657 "Number of private copies is not the same as the preallocated buffer"); 658 std::copy(Privates.begin(), Privates.end(), varlist_end()); 659 } 660 661 void OMPInReductionClause::setLHSExprs(ArrayRef<Expr *> LHSExprs) { 662 assert( 663 LHSExprs.size() == varlist_size() && 664 "Number of LHS expressions is not the same as the preallocated buffer"); 665 std::copy(LHSExprs.begin(), LHSExprs.end(), getPrivates().end()); 666 } 667 668 void OMPInReductionClause::setRHSExprs(ArrayRef<Expr *> RHSExprs) { 669 assert( 670 RHSExprs.size() == varlist_size() && 671 "Number of RHS expressions is not the same as the preallocated buffer"); 672 std::copy(RHSExprs.begin(), RHSExprs.end(), getLHSExprs().end()); 673 } 674 675 void OMPInReductionClause::setReductionOps(ArrayRef<Expr *> ReductionOps) { 676 assert(ReductionOps.size() == varlist_size() && "Number of in reduction " 677 "expressions is not the same " 678 "as the preallocated buffer"); 679 std::copy(ReductionOps.begin(), ReductionOps.end(), getRHSExprs().end()); 680 } 681 682 void OMPInReductionClause::setTaskgroupDescriptors( 683 ArrayRef<Expr *> TaskgroupDescriptors) { 684 assert(TaskgroupDescriptors.size() == varlist_size() && 685 "Number of in reduction descriptors is not the same as the " 686 "preallocated buffer"); 687 std::copy(TaskgroupDescriptors.begin(), TaskgroupDescriptors.end(), 688 getReductionOps().end()); 689 } 690 691 OMPInReductionClause *OMPInReductionClause::Create( 692 const ASTContext &C, SourceLocation StartLoc, SourceLocation LParenLoc, 693 SourceLocation EndLoc, SourceLocation ColonLoc, ArrayRef<Expr *> VL, 694 NestedNameSpecifierLoc QualifierLoc, const DeclarationNameInfo &NameInfo, 695 ArrayRef<Expr *> Privates, ArrayRef<Expr *> LHSExprs, 696 ArrayRef<Expr *> RHSExprs, ArrayRef<Expr *> ReductionOps, 697 ArrayRef<Expr *> TaskgroupDescriptors, Stmt *PreInit, Expr *PostUpdate) { 698 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(6 * VL.size())); 699 OMPInReductionClause *Clause = new (Mem) OMPInReductionClause( 700 StartLoc, LParenLoc, EndLoc, ColonLoc, VL.size(), QualifierLoc, NameInfo); 701 Clause->setVarRefs(VL); 702 Clause->setPrivates(Privates); 703 Clause->setLHSExprs(LHSExprs); 704 Clause->setRHSExprs(RHSExprs); 705 Clause->setReductionOps(ReductionOps); 706 Clause->setTaskgroupDescriptors(TaskgroupDescriptors); 707 Clause->setPreInitStmt(PreInit); 708 Clause->setPostUpdateExpr(PostUpdate); 709 return Clause; 710 } 711 712 OMPInReductionClause *OMPInReductionClause::CreateEmpty(const ASTContext &C, 713 unsigned N) { 714 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(6 * N)); 715 return new (Mem) OMPInReductionClause(N); 716 } 717 718 OMPAllocateClause * 719 OMPAllocateClause::Create(const ASTContext &C, SourceLocation StartLoc, 720 SourceLocation LParenLoc, Expr *Allocator, 721 SourceLocation ColonLoc, SourceLocation EndLoc, 722 ArrayRef<Expr *> VL) { 723 // Allocate space for private variables and initializer expressions. 724 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size())); 725 auto *Clause = new (Mem) OMPAllocateClause(StartLoc, LParenLoc, Allocator, 726 ColonLoc, EndLoc, VL.size()); 727 Clause->setVarRefs(VL); 728 return Clause; 729 } 730 731 OMPAllocateClause *OMPAllocateClause::CreateEmpty(const ASTContext &C, 732 unsigned N) { 733 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N)); 734 return new (Mem) OMPAllocateClause(N); 735 } 736 737 OMPFlushClause *OMPFlushClause::Create(const ASTContext &C, 738 SourceLocation StartLoc, 739 SourceLocation LParenLoc, 740 SourceLocation EndLoc, 741 ArrayRef<Expr *> VL) { 742 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size() + 1)); 743 OMPFlushClause *Clause = 744 new (Mem) OMPFlushClause(StartLoc, LParenLoc, EndLoc, VL.size()); 745 Clause->setVarRefs(VL); 746 return Clause; 747 } 748 749 OMPFlushClause *OMPFlushClause::CreateEmpty(const ASTContext &C, unsigned N) { 750 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N)); 751 return new (Mem) OMPFlushClause(N); 752 } 753 754 OMPDependClause * 755 OMPDependClause::Create(const ASTContext &C, SourceLocation StartLoc, 756 SourceLocation LParenLoc, SourceLocation EndLoc, 757 OpenMPDependClauseKind DepKind, SourceLocation DepLoc, 758 SourceLocation ColonLoc, ArrayRef<Expr *> VL, 759 unsigned NumLoops) { 760 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(VL.size() + NumLoops)); 761 OMPDependClause *Clause = new (Mem) 762 OMPDependClause(StartLoc, LParenLoc, EndLoc, VL.size(), NumLoops); 763 Clause->setVarRefs(VL); 764 Clause->setDependencyKind(DepKind); 765 Clause->setDependencyLoc(DepLoc); 766 Clause->setColonLoc(ColonLoc); 767 for (unsigned I = 0 ; I < NumLoops; ++I) 768 Clause->setLoopData(I, nullptr); 769 return Clause; 770 } 771 772 OMPDependClause *OMPDependClause::CreateEmpty(const ASTContext &C, unsigned N, 773 unsigned NumLoops) { 774 void *Mem = C.Allocate(totalSizeToAlloc<Expr *>(N + NumLoops)); 775 return new (Mem) OMPDependClause(N, NumLoops); 776 } 777 778 void OMPDependClause::setLoopData(unsigned NumLoop, Expr *Cnt) { 779 assert((getDependencyKind() == OMPC_DEPEND_sink || 780 getDependencyKind() == OMPC_DEPEND_source) && 781 NumLoop < NumLoops && 782 "Expected sink or source depend + loop index must be less number of " 783 "loops."); 784 auto It = std::next(getVarRefs().end(), NumLoop); 785 *It = Cnt; 786 } 787 788 Expr *OMPDependClause::getLoopData(unsigned NumLoop) { 789 assert((getDependencyKind() == OMPC_DEPEND_sink || 790 getDependencyKind() == OMPC_DEPEND_source) && 791 NumLoop < NumLoops && 792 "Expected sink or source depend + loop index must be less number of " 793 "loops."); 794 auto It = std::next(getVarRefs().end(), NumLoop); 795 return *It; 796 } 797 798 const Expr *OMPDependClause::getLoopData(unsigned NumLoop) const { 799 assert((getDependencyKind() == OMPC_DEPEND_sink || 800 getDependencyKind() == OMPC_DEPEND_source) && 801 NumLoop < NumLoops && 802 "Expected sink or source depend + loop index must be less number of " 803 "loops."); 804 auto It = std::next(getVarRefs().end(), NumLoop); 805 return *It; 806 } 807 808 unsigned OMPClauseMappableExprCommon::getComponentsTotalNumber( 809 MappableExprComponentListsRef ComponentLists) { 810 unsigned TotalNum = 0u; 811 for (auto &C : ComponentLists) 812 TotalNum += C.size(); 813 return TotalNum; 814 } 815 816 unsigned OMPClauseMappableExprCommon::getUniqueDeclarationsTotalNumber( 817 ArrayRef<const ValueDecl *> Declarations) { 818 unsigned TotalNum = 0u; 819 llvm::SmallPtrSet<const ValueDecl *, 8> Cache; 820 for (const ValueDecl *D : Declarations) { 821 const ValueDecl *VD = D ? cast<ValueDecl>(D->getCanonicalDecl()) : nullptr; 822 if (Cache.count(VD)) 823 continue; 824 ++TotalNum; 825 Cache.insert(VD); 826 } 827 return TotalNum; 828 } 829 830 OMPMapClause *OMPMapClause::Create( 831 const ASTContext &C, const OMPVarListLocTy &Locs, ArrayRef<Expr *> Vars, 832 ArrayRef<ValueDecl *> Declarations, 833 MappableExprComponentListsRef ComponentLists, ArrayRef<Expr *> UDMapperRefs, 834 ArrayRef<OpenMPMapModifierKind> MapModifiers, 835 ArrayRef<SourceLocation> MapModifiersLoc, 836 NestedNameSpecifierLoc UDMQualifierLoc, DeclarationNameInfo MapperId, 837 OpenMPMapClauseKind Type, bool TypeIsImplicit, SourceLocation TypeLoc) { 838 OMPMappableExprListSizeTy Sizes; 839 Sizes.NumVars = Vars.size(); 840 Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations); 841 Sizes.NumComponentLists = ComponentLists.size(); 842 Sizes.NumComponents = getComponentsTotalNumber(ComponentLists); 843 844 // We need to allocate: 845 // 2 x NumVars x Expr* - we have an original list expression and an associated 846 // user-defined mapper for each clause list entry. 847 // NumUniqueDeclarations x ValueDecl* - unique base declarations associated 848 // with each component list. 849 // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the 850 // number of lists for each unique declaration and the size of each component 851 // list. 852 // NumComponents x MappableComponent - the total of all the components in all 853 // the lists. 854 void *Mem = C.Allocate( 855 totalSizeToAlloc<Expr *, ValueDecl *, unsigned, 856 OMPClauseMappableExprCommon::MappableComponent>( 857 2 * Sizes.NumVars, Sizes.NumUniqueDeclarations, 858 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists, 859 Sizes.NumComponents)); 860 OMPMapClause *Clause = new (Mem) 861 OMPMapClause(MapModifiers, MapModifiersLoc, UDMQualifierLoc, MapperId, 862 Type, TypeIsImplicit, TypeLoc, Locs, Sizes); 863 864 Clause->setVarRefs(Vars); 865 Clause->setUDMapperRefs(UDMapperRefs); 866 Clause->setClauseInfo(Declarations, ComponentLists); 867 Clause->setMapType(Type); 868 Clause->setMapLoc(TypeLoc); 869 return Clause; 870 } 871 872 OMPMapClause * 873 OMPMapClause::CreateEmpty(const ASTContext &C, 874 const OMPMappableExprListSizeTy &Sizes) { 875 void *Mem = C.Allocate( 876 totalSizeToAlloc<Expr *, ValueDecl *, unsigned, 877 OMPClauseMappableExprCommon::MappableComponent>( 878 2 * Sizes.NumVars, Sizes.NumUniqueDeclarations, 879 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists, 880 Sizes.NumComponents)); 881 return new (Mem) OMPMapClause(Sizes); 882 } 883 884 OMPToClause *OMPToClause::Create( 885 const ASTContext &C, const OMPVarListLocTy &Locs, ArrayRef<Expr *> Vars, 886 ArrayRef<ValueDecl *> Declarations, 887 MappableExprComponentListsRef ComponentLists, ArrayRef<Expr *> UDMapperRefs, 888 NestedNameSpecifierLoc UDMQualifierLoc, DeclarationNameInfo MapperId) { 889 OMPMappableExprListSizeTy Sizes; 890 Sizes.NumVars = Vars.size(); 891 Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations); 892 Sizes.NumComponentLists = ComponentLists.size(); 893 Sizes.NumComponents = getComponentsTotalNumber(ComponentLists); 894 895 // We need to allocate: 896 // 2 x NumVars x Expr* - we have an original list expression and an associated 897 // user-defined mapper for each clause list entry. 898 // NumUniqueDeclarations x ValueDecl* - unique base declarations associated 899 // with each component list. 900 // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the 901 // number of lists for each unique declaration and the size of each component 902 // list. 903 // NumComponents x MappableComponent - the total of all the components in all 904 // the lists. 905 void *Mem = C.Allocate( 906 totalSizeToAlloc<Expr *, ValueDecl *, unsigned, 907 OMPClauseMappableExprCommon::MappableComponent>( 908 2 * Sizes.NumVars, Sizes.NumUniqueDeclarations, 909 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists, 910 Sizes.NumComponents)); 911 912 auto *Clause = new (Mem) OMPToClause(UDMQualifierLoc, MapperId, Locs, Sizes); 913 914 Clause->setVarRefs(Vars); 915 Clause->setUDMapperRefs(UDMapperRefs); 916 Clause->setClauseInfo(Declarations, ComponentLists); 917 return Clause; 918 } 919 920 OMPToClause *OMPToClause::CreateEmpty(const ASTContext &C, 921 const OMPMappableExprListSizeTy &Sizes) { 922 void *Mem = C.Allocate( 923 totalSizeToAlloc<Expr *, ValueDecl *, unsigned, 924 OMPClauseMappableExprCommon::MappableComponent>( 925 2 * Sizes.NumVars, Sizes.NumUniqueDeclarations, 926 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists, 927 Sizes.NumComponents)); 928 return new (Mem) OMPToClause(Sizes); 929 } 930 931 OMPFromClause *OMPFromClause::Create( 932 const ASTContext &C, const OMPVarListLocTy &Locs, ArrayRef<Expr *> Vars, 933 ArrayRef<ValueDecl *> Declarations, 934 MappableExprComponentListsRef ComponentLists, ArrayRef<Expr *> UDMapperRefs, 935 NestedNameSpecifierLoc UDMQualifierLoc, DeclarationNameInfo MapperId) { 936 OMPMappableExprListSizeTy Sizes; 937 Sizes.NumVars = Vars.size(); 938 Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations); 939 Sizes.NumComponentLists = ComponentLists.size(); 940 Sizes.NumComponents = getComponentsTotalNumber(ComponentLists); 941 942 // We need to allocate: 943 // 2 x NumVars x Expr* - we have an original list expression and an associated 944 // user-defined mapper for each clause list entry. 945 // NumUniqueDeclarations x ValueDecl* - unique base declarations associated 946 // with each component list. 947 // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the 948 // number of lists for each unique declaration and the size of each component 949 // list. 950 // NumComponents x MappableComponent - the total of all the components in all 951 // the lists. 952 void *Mem = C.Allocate( 953 totalSizeToAlloc<Expr *, ValueDecl *, unsigned, 954 OMPClauseMappableExprCommon::MappableComponent>( 955 2 * Sizes.NumVars, Sizes.NumUniqueDeclarations, 956 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists, 957 Sizes.NumComponents)); 958 959 auto *Clause = 960 new (Mem) OMPFromClause(UDMQualifierLoc, MapperId, Locs, Sizes); 961 962 Clause->setVarRefs(Vars); 963 Clause->setUDMapperRefs(UDMapperRefs); 964 Clause->setClauseInfo(Declarations, ComponentLists); 965 return Clause; 966 } 967 968 OMPFromClause * 969 OMPFromClause::CreateEmpty(const ASTContext &C, 970 const OMPMappableExprListSizeTy &Sizes) { 971 void *Mem = C.Allocate( 972 totalSizeToAlloc<Expr *, ValueDecl *, unsigned, 973 OMPClauseMappableExprCommon::MappableComponent>( 974 2 * Sizes.NumVars, Sizes.NumUniqueDeclarations, 975 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists, 976 Sizes.NumComponents)); 977 return new (Mem) OMPFromClause(Sizes); 978 } 979 980 void OMPUseDevicePtrClause::setPrivateCopies(ArrayRef<Expr *> VL) { 981 assert(VL.size() == varlist_size() && 982 "Number of private copies is not the same as the preallocated buffer"); 983 std::copy(VL.begin(), VL.end(), varlist_end()); 984 } 985 986 void OMPUseDevicePtrClause::setInits(ArrayRef<Expr *> VL) { 987 assert(VL.size() == varlist_size() && 988 "Number of inits is not the same as the preallocated buffer"); 989 std::copy(VL.begin(), VL.end(), getPrivateCopies().end()); 990 } 991 992 OMPUseDevicePtrClause *OMPUseDevicePtrClause::Create( 993 const ASTContext &C, const OMPVarListLocTy &Locs, ArrayRef<Expr *> Vars, 994 ArrayRef<Expr *> PrivateVars, ArrayRef<Expr *> Inits, 995 ArrayRef<ValueDecl *> Declarations, 996 MappableExprComponentListsRef ComponentLists) { 997 OMPMappableExprListSizeTy Sizes; 998 Sizes.NumVars = Vars.size(); 999 Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations); 1000 Sizes.NumComponentLists = ComponentLists.size(); 1001 Sizes.NumComponents = getComponentsTotalNumber(ComponentLists); 1002 1003 // We need to allocate: 1004 // 3 x NumVars x Expr* - we have an original list expression for each clause 1005 // list entry and an equal number of private copies and inits. 1006 // NumUniqueDeclarations x ValueDecl* - unique base declarations associated 1007 // with each component list. 1008 // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the 1009 // number of lists for each unique declaration and the size of each component 1010 // list. 1011 // NumComponents x MappableComponent - the total of all the components in all 1012 // the lists. 1013 void *Mem = C.Allocate( 1014 totalSizeToAlloc<Expr *, ValueDecl *, unsigned, 1015 OMPClauseMappableExprCommon::MappableComponent>( 1016 3 * Sizes.NumVars, Sizes.NumUniqueDeclarations, 1017 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists, 1018 Sizes.NumComponents)); 1019 1020 OMPUseDevicePtrClause *Clause = new (Mem) OMPUseDevicePtrClause(Locs, Sizes); 1021 1022 Clause->setVarRefs(Vars); 1023 Clause->setPrivateCopies(PrivateVars); 1024 Clause->setInits(Inits); 1025 Clause->setClauseInfo(Declarations, ComponentLists); 1026 return Clause; 1027 } 1028 1029 OMPUseDevicePtrClause * 1030 OMPUseDevicePtrClause::CreateEmpty(const ASTContext &C, 1031 const OMPMappableExprListSizeTy &Sizes) { 1032 void *Mem = C.Allocate( 1033 totalSizeToAlloc<Expr *, ValueDecl *, unsigned, 1034 OMPClauseMappableExprCommon::MappableComponent>( 1035 3 * Sizes.NumVars, Sizes.NumUniqueDeclarations, 1036 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists, 1037 Sizes.NumComponents)); 1038 return new (Mem) OMPUseDevicePtrClause(Sizes); 1039 } 1040 1041 OMPIsDevicePtrClause * 1042 OMPIsDevicePtrClause::Create(const ASTContext &C, const OMPVarListLocTy &Locs, 1043 ArrayRef<Expr *> Vars, 1044 ArrayRef<ValueDecl *> Declarations, 1045 MappableExprComponentListsRef ComponentLists) { 1046 OMPMappableExprListSizeTy Sizes; 1047 Sizes.NumVars = Vars.size(); 1048 Sizes.NumUniqueDeclarations = getUniqueDeclarationsTotalNumber(Declarations); 1049 Sizes.NumComponentLists = ComponentLists.size(); 1050 Sizes.NumComponents = getComponentsTotalNumber(ComponentLists); 1051 1052 // We need to allocate: 1053 // NumVars x Expr* - we have an original list expression for each clause list 1054 // entry. 1055 // NumUniqueDeclarations x ValueDecl* - unique base declarations associated 1056 // with each component list. 1057 // (NumUniqueDeclarations + NumComponentLists) x unsigned - we specify the 1058 // number of lists for each unique declaration and the size of each component 1059 // list. 1060 // NumComponents x MappableComponent - the total of all the components in all 1061 // the lists. 1062 void *Mem = C.Allocate( 1063 totalSizeToAlloc<Expr *, ValueDecl *, unsigned, 1064 OMPClauseMappableExprCommon::MappableComponent>( 1065 Sizes.NumVars, Sizes.NumUniqueDeclarations, 1066 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists, 1067 Sizes.NumComponents)); 1068 1069 OMPIsDevicePtrClause *Clause = new (Mem) OMPIsDevicePtrClause(Locs, Sizes); 1070 1071 Clause->setVarRefs(Vars); 1072 Clause->setClauseInfo(Declarations, ComponentLists); 1073 return Clause; 1074 } 1075 1076 OMPIsDevicePtrClause * 1077 OMPIsDevicePtrClause::CreateEmpty(const ASTContext &C, 1078 const OMPMappableExprListSizeTy &Sizes) { 1079 void *Mem = C.Allocate( 1080 totalSizeToAlloc<Expr *, ValueDecl *, unsigned, 1081 OMPClauseMappableExprCommon::MappableComponent>( 1082 Sizes.NumVars, Sizes.NumUniqueDeclarations, 1083 Sizes.NumUniqueDeclarations + Sizes.NumComponentLists, 1084 Sizes.NumComponents)); 1085 return new (Mem) OMPIsDevicePtrClause(Sizes); 1086 } 1087 1088 //===----------------------------------------------------------------------===// 1089 // OpenMP clauses printing methods 1090 //===----------------------------------------------------------------------===// 1091 1092 void OMPClausePrinter::VisitOMPIfClause(OMPIfClause *Node) { 1093 OS << "if("; 1094 if (Node->getNameModifier() != OMPD_unknown) 1095 OS << getOpenMPDirectiveName(Node->getNameModifier()) << ": "; 1096 Node->getCondition()->printPretty(OS, nullptr, Policy, 0); 1097 OS << ")"; 1098 } 1099 1100 void OMPClausePrinter::VisitOMPFinalClause(OMPFinalClause *Node) { 1101 OS << "final("; 1102 Node->getCondition()->printPretty(OS, nullptr, Policy, 0); 1103 OS << ")"; 1104 } 1105 1106 void OMPClausePrinter::VisitOMPNumThreadsClause(OMPNumThreadsClause *Node) { 1107 OS << "num_threads("; 1108 Node->getNumThreads()->printPretty(OS, nullptr, Policy, 0); 1109 OS << ")"; 1110 } 1111 1112 void OMPClausePrinter::VisitOMPSafelenClause(OMPSafelenClause *Node) { 1113 OS << "safelen("; 1114 Node->getSafelen()->printPretty(OS, nullptr, Policy, 0); 1115 OS << ")"; 1116 } 1117 1118 void OMPClausePrinter::VisitOMPSimdlenClause(OMPSimdlenClause *Node) { 1119 OS << "simdlen("; 1120 Node->getSimdlen()->printPretty(OS, nullptr, Policy, 0); 1121 OS << ")"; 1122 } 1123 1124 void OMPClausePrinter::VisitOMPAllocatorClause(OMPAllocatorClause *Node) { 1125 OS << "allocator("; 1126 Node->getAllocator()->printPretty(OS, nullptr, Policy, 0); 1127 OS << ")"; 1128 } 1129 1130 void OMPClausePrinter::VisitOMPCollapseClause(OMPCollapseClause *Node) { 1131 OS << "collapse("; 1132 Node->getNumForLoops()->printPretty(OS, nullptr, Policy, 0); 1133 OS << ")"; 1134 } 1135 1136 void OMPClausePrinter::VisitOMPDefaultClause(OMPDefaultClause *Node) { 1137 OS << "default(" 1138 << getOpenMPSimpleClauseTypeName(OMPC_default, Node->getDefaultKind()) 1139 << ")"; 1140 } 1141 1142 void OMPClausePrinter::VisitOMPProcBindClause(OMPProcBindClause *Node) { 1143 OS << "proc_bind(" 1144 << getOpenMPSimpleClauseTypeName(OMPC_proc_bind, Node->getProcBindKind()) 1145 << ")"; 1146 } 1147 1148 void OMPClausePrinter::VisitOMPUnifiedAddressClause(OMPUnifiedAddressClause *) { 1149 OS << "unified_address"; 1150 } 1151 1152 void OMPClausePrinter::VisitOMPUnifiedSharedMemoryClause( 1153 OMPUnifiedSharedMemoryClause *) { 1154 OS << "unified_shared_memory"; 1155 } 1156 1157 void OMPClausePrinter::VisitOMPReverseOffloadClause(OMPReverseOffloadClause *) { 1158 OS << "reverse_offload"; 1159 } 1160 1161 void OMPClausePrinter::VisitOMPDynamicAllocatorsClause( 1162 OMPDynamicAllocatorsClause *) { 1163 OS << "dynamic_allocators"; 1164 } 1165 1166 void OMPClausePrinter::VisitOMPAtomicDefaultMemOrderClause( 1167 OMPAtomicDefaultMemOrderClause *Node) { 1168 OS << "atomic_default_mem_order(" 1169 << getOpenMPSimpleClauseTypeName(OMPC_atomic_default_mem_order, 1170 Node->getAtomicDefaultMemOrderKind()) 1171 << ")"; 1172 } 1173 1174 void OMPClausePrinter::VisitOMPScheduleClause(OMPScheduleClause *Node) { 1175 OS << "schedule("; 1176 if (Node->getFirstScheduleModifier() != OMPC_SCHEDULE_MODIFIER_unknown) { 1177 OS << getOpenMPSimpleClauseTypeName(OMPC_schedule, 1178 Node->getFirstScheduleModifier()); 1179 if (Node->getSecondScheduleModifier() != OMPC_SCHEDULE_MODIFIER_unknown) { 1180 OS << ", "; 1181 OS << getOpenMPSimpleClauseTypeName(OMPC_schedule, 1182 Node->getSecondScheduleModifier()); 1183 } 1184 OS << ": "; 1185 } 1186 OS << getOpenMPSimpleClauseTypeName(OMPC_schedule, Node->getScheduleKind()); 1187 if (auto *E = Node->getChunkSize()) { 1188 OS << ", "; 1189 E->printPretty(OS, nullptr, Policy); 1190 } 1191 OS << ")"; 1192 } 1193 1194 void OMPClausePrinter::VisitOMPOrderedClause(OMPOrderedClause *Node) { 1195 OS << "ordered"; 1196 if (auto *Num = Node->getNumForLoops()) { 1197 OS << "("; 1198 Num->printPretty(OS, nullptr, Policy, 0); 1199 OS << ")"; 1200 } 1201 } 1202 1203 void OMPClausePrinter::VisitOMPNowaitClause(OMPNowaitClause *) { 1204 OS << "nowait"; 1205 } 1206 1207 void OMPClausePrinter::VisitOMPUntiedClause(OMPUntiedClause *) { 1208 OS << "untied"; 1209 } 1210 1211 void OMPClausePrinter::VisitOMPNogroupClause(OMPNogroupClause *) { 1212 OS << "nogroup"; 1213 } 1214 1215 void OMPClausePrinter::VisitOMPMergeableClause(OMPMergeableClause *) { 1216 OS << "mergeable"; 1217 } 1218 1219 void OMPClausePrinter::VisitOMPReadClause(OMPReadClause *) { OS << "read"; } 1220 1221 void OMPClausePrinter::VisitOMPWriteClause(OMPWriteClause *) { OS << "write"; } 1222 1223 void OMPClausePrinter::VisitOMPUpdateClause(OMPUpdateClause *) { 1224 OS << "update"; 1225 } 1226 1227 void OMPClausePrinter::VisitOMPCaptureClause(OMPCaptureClause *) { 1228 OS << "capture"; 1229 } 1230 1231 void OMPClausePrinter::VisitOMPSeqCstClause(OMPSeqCstClause *) { 1232 OS << "seq_cst"; 1233 } 1234 1235 void OMPClausePrinter::VisitOMPThreadsClause(OMPThreadsClause *) { 1236 OS << "threads"; 1237 } 1238 1239 void OMPClausePrinter::VisitOMPSIMDClause(OMPSIMDClause *) { OS << "simd"; } 1240 1241 void OMPClausePrinter::VisitOMPDeviceClause(OMPDeviceClause *Node) { 1242 OS << "device("; 1243 Node->getDevice()->printPretty(OS, nullptr, Policy, 0); 1244 OS << ")"; 1245 } 1246 1247 void OMPClausePrinter::VisitOMPNumTeamsClause(OMPNumTeamsClause *Node) { 1248 OS << "num_teams("; 1249 Node->getNumTeams()->printPretty(OS, nullptr, Policy, 0); 1250 OS << ")"; 1251 } 1252 1253 void OMPClausePrinter::VisitOMPThreadLimitClause(OMPThreadLimitClause *Node) { 1254 OS << "thread_limit("; 1255 Node->getThreadLimit()->printPretty(OS, nullptr, Policy, 0); 1256 OS << ")"; 1257 } 1258 1259 void OMPClausePrinter::VisitOMPPriorityClause(OMPPriorityClause *Node) { 1260 OS << "priority("; 1261 Node->getPriority()->printPretty(OS, nullptr, Policy, 0); 1262 OS << ")"; 1263 } 1264 1265 void OMPClausePrinter::VisitOMPGrainsizeClause(OMPGrainsizeClause *Node) { 1266 OS << "grainsize("; 1267 Node->getGrainsize()->printPretty(OS, nullptr, Policy, 0); 1268 OS << ")"; 1269 } 1270 1271 void OMPClausePrinter::VisitOMPNumTasksClause(OMPNumTasksClause *Node) { 1272 OS << "num_tasks("; 1273 Node->getNumTasks()->printPretty(OS, nullptr, Policy, 0); 1274 OS << ")"; 1275 } 1276 1277 void OMPClausePrinter::VisitOMPHintClause(OMPHintClause *Node) { 1278 OS << "hint("; 1279 Node->getHint()->printPretty(OS, nullptr, Policy, 0); 1280 OS << ")"; 1281 } 1282 1283 template<typename T> 1284 void OMPClausePrinter::VisitOMPClauseList(T *Node, char StartSym) { 1285 for (typename T::varlist_iterator I = Node->varlist_begin(), 1286 E = Node->varlist_end(); 1287 I != E; ++I) { 1288 assert(*I && "Expected non-null Stmt"); 1289 OS << (I == Node->varlist_begin() ? StartSym : ','); 1290 if (auto *DRE = dyn_cast<DeclRefExpr>(*I)) { 1291 if (isa<OMPCapturedExprDecl>(DRE->getDecl())) 1292 DRE->printPretty(OS, nullptr, Policy, 0); 1293 else 1294 DRE->getDecl()->printQualifiedName(OS); 1295 } else 1296 (*I)->printPretty(OS, nullptr, Policy, 0); 1297 } 1298 } 1299 1300 void OMPClausePrinter::VisitOMPAllocateClause(OMPAllocateClause *Node) { 1301 if (Node->varlist_empty()) 1302 return; 1303 OS << "allocate"; 1304 if (Expr *Allocator = Node->getAllocator()) { 1305 OS << "("; 1306 Allocator->printPretty(OS, nullptr, Policy, 0); 1307 OS << ":"; 1308 VisitOMPClauseList(Node, ' '); 1309 } else { 1310 VisitOMPClauseList(Node, '('); 1311 } 1312 OS << ")"; 1313 } 1314 1315 void OMPClausePrinter::VisitOMPPrivateClause(OMPPrivateClause *Node) { 1316 if (!Node->varlist_empty()) { 1317 OS << "private"; 1318 VisitOMPClauseList(Node, '('); 1319 OS << ")"; 1320 } 1321 } 1322 1323 void OMPClausePrinter::VisitOMPFirstprivateClause(OMPFirstprivateClause *Node) { 1324 if (!Node->varlist_empty()) { 1325 OS << "firstprivate"; 1326 VisitOMPClauseList(Node, '('); 1327 OS << ")"; 1328 } 1329 } 1330 1331 void OMPClausePrinter::VisitOMPLastprivateClause(OMPLastprivateClause *Node) { 1332 if (!Node->varlist_empty()) { 1333 OS << "lastprivate"; 1334 VisitOMPClauseList(Node, '('); 1335 OS << ")"; 1336 } 1337 } 1338 1339 void OMPClausePrinter::VisitOMPSharedClause(OMPSharedClause *Node) { 1340 if (!Node->varlist_empty()) { 1341 OS << "shared"; 1342 VisitOMPClauseList(Node, '('); 1343 OS << ")"; 1344 } 1345 } 1346 1347 void OMPClausePrinter::VisitOMPReductionClause(OMPReductionClause *Node) { 1348 if (!Node->varlist_empty()) { 1349 OS << "reduction("; 1350 NestedNameSpecifier *QualifierLoc = 1351 Node->getQualifierLoc().getNestedNameSpecifier(); 1352 OverloadedOperatorKind OOK = 1353 Node->getNameInfo().getName().getCXXOverloadedOperator(); 1354 if (QualifierLoc == nullptr && OOK != OO_None) { 1355 // Print reduction identifier in C format 1356 OS << getOperatorSpelling(OOK); 1357 } else { 1358 // Use C++ format 1359 if (QualifierLoc != nullptr) 1360 QualifierLoc->print(OS, Policy); 1361 OS << Node->getNameInfo(); 1362 } 1363 OS << ":"; 1364 VisitOMPClauseList(Node, ' '); 1365 OS << ")"; 1366 } 1367 } 1368 1369 void OMPClausePrinter::VisitOMPTaskReductionClause( 1370 OMPTaskReductionClause *Node) { 1371 if (!Node->varlist_empty()) { 1372 OS << "task_reduction("; 1373 NestedNameSpecifier *QualifierLoc = 1374 Node->getQualifierLoc().getNestedNameSpecifier(); 1375 OverloadedOperatorKind OOK = 1376 Node->getNameInfo().getName().getCXXOverloadedOperator(); 1377 if (QualifierLoc == nullptr && OOK != OO_None) { 1378 // Print reduction identifier in C format 1379 OS << getOperatorSpelling(OOK); 1380 } else { 1381 // Use C++ format 1382 if (QualifierLoc != nullptr) 1383 QualifierLoc->print(OS, Policy); 1384 OS << Node->getNameInfo(); 1385 } 1386 OS << ":"; 1387 VisitOMPClauseList(Node, ' '); 1388 OS << ")"; 1389 } 1390 } 1391 1392 void OMPClausePrinter::VisitOMPInReductionClause(OMPInReductionClause *Node) { 1393 if (!Node->varlist_empty()) { 1394 OS << "in_reduction("; 1395 NestedNameSpecifier *QualifierLoc = 1396 Node->getQualifierLoc().getNestedNameSpecifier(); 1397 OverloadedOperatorKind OOK = 1398 Node->getNameInfo().getName().getCXXOverloadedOperator(); 1399 if (QualifierLoc == nullptr && OOK != OO_None) { 1400 // Print reduction identifier in C format 1401 OS << getOperatorSpelling(OOK); 1402 } else { 1403 // Use C++ format 1404 if (QualifierLoc != nullptr) 1405 QualifierLoc->print(OS, Policy); 1406 OS << Node->getNameInfo(); 1407 } 1408 OS << ":"; 1409 VisitOMPClauseList(Node, ' '); 1410 OS << ")"; 1411 } 1412 } 1413 1414 void OMPClausePrinter::VisitOMPLinearClause(OMPLinearClause *Node) { 1415 if (!Node->varlist_empty()) { 1416 OS << "linear"; 1417 if (Node->getModifierLoc().isValid()) { 1418 OS << '(' 1419 << getOpenMPSimpleClauseTypeName(OMPC_linear, Node->getModifier()); 1420 } 1421 VisitOMPClauseList(Node, '('); 1422 if (Node->getModifierLoc().isValid()) 1423 OS << ')'; 1424 if (Node->getStep() != nullptr) { 1425 OS << ": "; 1426 Node->getStep()->printPretty(OS, nullptr, Policy, 0); 1427 } 1428 OS << ")"; 1429 } 1430 } 1431 1432 void OMPClausePrinter::VisitOMPAlignedClause(OMPAlignedClause *Node) { 1433 if (!Node->varlist_empty()) { 1434 OS << "aligned"; 1435 VisitOMPClauseList(Node, '('); 1436 if (Node->getAlignment() != nullptr) { 1437 OS << ": "; 1438 Node->getAlignment()->printPretty(OS, nullptr, Policy, 0); 1439 } 1440 OS << ")"; 1441 } 1442 } 1443 1444 void OMPClausePrinter::VisitOMPCopyinClause(OMPCopyinClause *Node) { 1445 if (!Node->varlist_empty()) { 1446 OS << "copyin"; 1447 VisitOMPClauseList(Node, '('); 1448 OS << ")"; 1449 } 1450 } 1451 1452 void OMPClausePrinter::VisitOMPCopyprivateClause(OMPCopyprivateClause *Node) { 1453 if (!Node->varlist_empty()) { 1454 OS << "copyprivate"; 1455 VisitOMPClauseList(Node, '('); 1456 OS << ")"; 1457 } 1458 } 1459 1460 void OMPClausePrinter::VisitOMPFlushClause(OMPFlushClause *Node) { 1461 if (!Node->varlist_empty()) { 1462 VisitOMPClauseList(Node, '('); 1463 OS << ")"; 1464 } 1465 } 1466 1467 void OMPClausePrinter::VisitOMPDependClause(OMPDependClause *Node) { 1468 OS << "depend("; 1469 OS << getOpenMPSimpleClauseTypeName(Node->getClauseKind(), 1470 Node->getDependencyKind()); 1471 if (!Node->varlist_empty()) { 1472 OS << " :"; 1473 VisitOMPClauseList(Node, ' '); 1474 } 1475 OS << ")"; 1476 } 1477 1478 void OMPClausePrinter::VisitOMPMapClause(OMPMapClause *Node) { 1479 if (!Node->varlist_empty()) { 1480 OS << "map("; 1481 if (Node->getMapType() != OMPC_MAP_unknown) { 1482 for (unsigned I = 0; I < OMPMapClause::NumberOfModifiers; ++I) { 1483 if (Node->getMapTypeModifier(I) != OMPC_MAP_MODIFIER_unknown) { 1484 OS << getOpenMPSimpleClauseTypeName(OMPC_map, 1485 Node->getMapTypeModifier(I)); 1486 if (Node->getMapTypeModifier(I) == OMPC_MAP_MODIFIER_mapper) { 1487 OS << '('; 1488 NestedNameSpecifier *MapperNNS = 1489 Node->getMapperQualifierLoc().getNestedNameSpecifier(); 1490 if (MapperNNS) 1491 MapperNNS->print(OS, Policy); 1492 OS << Node->getMapperIdInfo() << ')'; 1493 } 1494 OS << ','; 1495 } 1496 } 1497 OS << getOpenMPSimpleClauseTypeName(OMPC_map, Node->getMapType()); 1498 OS << ':'; 1499 } 1500 VisitOMPClauseList(Node, ' '); 1501 OS << ")"; 1502 } 1503 } 1504 1505 void OMPClausePrinter::VisitOMPToClause(OMPToClause *Node) { 1506 if (!Node->varlist_empty()) { 1507 OS << "to"; 1508 DeclarationNameInfo MapperId = Node->getMapperIdInfo(); 1509 if (MapperId.getName() && !MapperId.getName().isEmpty()) { 1510 OS << '('; 1511 OS << "mapper("; 1512 NestedNameSpecifier *MapperNNS = 1513 Node->getMapperQualifierLoc().getNestedNameSpecifier(); 1514 if (MapperNNS) 1515 MapperNNS->print(OS, Policy); 1516 OS << MapperId << "):"; 1517 VisitOMPClauseList(Node, ' '); 1518 } else { 1519 VisitOMPClauseList(Node, '('); 1520 } 1521 OS << ")"; 1522 } 1523 } 1524 1525 void OMPClausePrinter::VisitOMPFromClause(OMPFromClause *Node) { 1526 if (!Node->varlist_empty()) { 1527 OS << "from"; 1528 DeclarationNameInfo MapperId = Node->getMapperIdInfo(); 1529 if (MapperId.getName() && !MapperId.getName().isEmpty()) { 1530 OS << '('; 1531 OS << "mapper("; 1532 NestedNameSpecifier *MapperNNS = 1533 Node->getMapperQualifierLoc().getNestedNameSpecifier(); 1534 if (MapperNNS) 1535 MapperNNS->print(OS, Policy); 1536 OS << MapperId << "):"; 1537 VisitOMPClauseList(Node, ' '); 1538 } else { 1539 VisitOMPClauseList(Node, '('); 1540 } 1541 OS << ")"; 1542 } 1543 } 1544 1545 void OMPClausePrinter::VisitOMPDistScheduleClause(OMPDistScheduleClause *Node) { 1546 OS << "dist_schedule(" << getOpenMPSimpleClauseTypeName( 1547 OMPC_dist_schedule, Node->getDistScheduleKind()); 1548 if (auto *E = Node->getChunkSize()) { 1549 OS << ", "; 1550 E->printPretty(OS, nullptr, Policy); 1551 } 1552 OS << ")"; 1553 } 1554 1555 void OMPClausePrinter::VisitOMPDefaultmapClause(OMPDefaultmapClause *Node) { 1556 OS << "defaultmap("; 1557 OS << getOpenMPSimpleClauseTypeName(OMPC_defaultmap, 1558 Node->getDefaultmapModifier()); 1559 OS << ": "; 1560 OS << getOpenMPSimpleClauseTypeName(OMPC_defaultmap, 1561 Node->getDefaultmapKind()); 1562 OS << ")"; 1563 } 1564 1565 void OMPClausePrinter::VisitOMPUseDevicePtrClause(OMPUseDevicePtrClause *Node) { 1566 if (!Node->varlist_empty()) { 1567 OS << "use_device_ptr"; 1568 VisitOMPClauseList(Node, '('); 1569 OS << ")"; 1570 } 1571 } 1572 1573 void OMPClausePrinter::VisitOMPIsDevicePtrClause(OMPIsDevicePtrClause *Node) { 1574 if (!Node->varlist_empty()) { 1575 OS << "is_device_ptr"; 1576 VisitOMPClauseList(Node, '('); 1577 OS << ")"; 1578 } 1579 } 1580 1581