Skip to content

Commit a49ce92

Browse files
zahiraamIcohedron
authored andcommitted
[Clang] [OpenMP] Add support for '#pragma omp stripe'. (llvm#119891)
Implement basic parsing and semantic support for `#pragma omp stripe` constuct introduced in https://www.openmp.org/wp-content/uploads/[OpenMP-API-Specification-6-0.pdf](https://www.openmp.org/wp-content/uploads/OpenMP-API-Specification-6-0.pdf), section 11.7.
1 parent 9ad5843 commit a49ce92

File tree

29 files changed

+2404
-32
lines changed

29 files changed

+2404
-32
lines changed

clang/bindings/python/clang/cindex.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1410,6 +1410,9 @@ def is_unexposed(self):
14101410
# OpenMP scope directive.
14111411
OMP_SCOPE_DIRECTIVE = 306
14121412

1413+
# OpenMP stripe directive.
1414+
OMP_STRIPE_DIRECTIVE = 310
1415+
14131416
# OpenACC Compute Construct.
14141417
OPEN_ACC_COMPUTE_DIRECTIVE = 320
14151418

clang/docs/OpenMPSupport.rst

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -374,6 +374,8 @@ implementation.
374374
+-------------------------------------------------------------+---------------------------+---------------------------+--------------------------------------------------------------------------+
375375
| Loop transformation constructs | :none:`unclaimed` | :none:`unclaimed` | |
376376
+-------------------------------------------------------------+---------------------------+---------------------------+--------------------------------------------------------------------------+
377+
| loop stripe transformation | :good:`done` | https://github.com/llvm/llvm-project/pull/119891 |
378+
+-------------------------------------------------------------+---------------------------+---------------------------+--------------------------------------------------------------------------+
377379
| work distribute construct | :none:`unclaimed` | :none:`unclaimed` | |
378380
+-------------------------------------------------------------+---------------------------+---------------------------+--------------------------------------------------------------------------+
379381
| task_iteration | :none:`unclaimed` | :none:`unclaimed` | |

clang/docs/ReleaseNotes.rst

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -291,6 +291,7 @@ Python Binding Changes
291291
OpenMP Support
292292
--------------
293293
- Added support 'no_openmp_constructs' assumption clause.
294+
- Added support for 'omp stripe' directive.
294295

295296
Improvements
296297
^^^^^^^^^^^^

clang/include/clang-c/Index.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2158,6 +2158,10 @@ enum CXCursorKind {
21582158
*/
21592159
CXCursor_OMPAssumeDirective = 309,
21602160

2161+
/** OpenMP assume directive.
2162+
*/
2163+
CXCursor_OMPStripeDirective = 310,
2164+
21612165
/** OpenACC Compute Construct.
21622166
*/
21632167
CXCursor_OpenACCComputeConstruct = 320,

clang/include/clang/AST/RecursiveASTVisitor.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3056,6 +3056,9 @@ DEF_TRAVERSE_STMT(OMPSimdDirective,
30563056
DEF_TRAVERSE_STMT(OMPTileDirective,
30573057
{ TRY_TO(TraverseOMPExecutableDirective(S)); })
30583058

3059+
DEF_TRAVERSE_STMT(OMPStripeDirective,
3060+
{ TRY_TO(TraverseOMPExecutableDirective(S)); })
3061+
30593062
DEF_TRAVERSE_STMT(OMPUnrollDirective,
30603063
{ TRY_TO(TraverseOMPExecutableDirective(S)); })
30613064

clang/include/clang/AST/StmtOpenMP.h

Lines changed: 80 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -994,7 +994,9 @@ class OMPLoopTransformationDirective : public OMPLoopBasedDirective {
994994
static bool classof(const Stmt *T) {
995995
Stmt::StmtClass C = T->getStmtClass();
996996
return C == OMPTileDirectiveClass || C == OMPUnrollDirectiveClass ||
997-
C == OMPReverseDirectiveClass || C == OMPInterchangeDirectiveClass;
997+
C == OMPReverseDirectiveClass || C == OMPInterchangeDirectiveClass ||
998+
C == OMPStripeDirectiveClass;
999+
;
9981000
}
9991001
};
10001002

@@ -5560,7 +5562,7 @@ class OMPTileDirective final : public OMPLoopTransformationDirective {
55605562
: OMPLoopTransformationDirective(OMPTileDirectiveClass,
55615563
llvm::omp::OMPD_tile, StartLoc, EndLoc,
55625564
NumLoops) {
5563-
setNumGeneratedLoops(3 * NumLoops);
5565+
setNumGeneratedLoops(2 * NumLoops);
55645566
}
55655567

55665568
void setPreInits(Stmt *PreInits) {
@@ -5621,6 +5623,82 @@ class OMPTileDirective final : public OMPLoopTransformationDirective {
56215623
}
56225624
};
56235625

5626+
/// This represents the '#pragma omp stripe' loop transformation directive.
5627+
class OMPStripeDirective final : public OMPLoopTransformationDirective {
5628+
friend class ASTStmtReader;
5629+
friend class OMPExecutableDirective;
5630+
5631+
/// Default list of offsets.
5632+
enum {
5633+
PreInitsOffset = 0,
5634+
TransformedStmtOffset,
5635+
};
5636+
5637+
explicit OMPStripeDirective(SourceLocation StartLoc, SourceLocation EndLoc,
5638+
unsigned NumLoops)
5639+
: OMPLoopTransformationDirective(OMPStripeDirectiveClass,
5640+
llvm::omp::OMPD_stripe, StartLoc, EndLoc,
5641+
NumLoops) {
5642+
setNumGeneratedLoops(2 * NumLoops);
5643+
}
5644+
5645+
void setPreInits(Stmt *PreInits) {
5646+
Data->getChildren()[PreInitsOffset] = PreInits;
5647+
}
5648+
5649+
void setTransformedStmt(Stmt *S) {
5650+
Data->getChildren()[TransformedStmtOffset] = S;
5651+
}
5652+
5653+
public:
5654+
/// Create a new AST node representation for '#pragma omp stripe'.
5655+
///
5656+
/// \param C Context of the AST.
5657+
/// \param StartLoc Location of the introducer (e.g. the 'omp' token).
5658+
/// \param EndLoc Location of the directive's end (e.g. the tok::eod).
5659+
/// \param Clauses The directive's clauses.
5660+
/// \param NumLoops Number of associated loops (number of items in the
5661+
/// 'sizes' clause).
5662+
/// \param AssociatedStmt The outermost associated loop.
5663+
/// \param TransformedStmt The loop nest after striping, or nullptr in
5664+
/// dependent contexts.
5665+
/// \param PreInits Helper preinits statements for the loop nest.
5666+
static OMPStripeDirective *
5667+
Create(const ASTContext &C, SourceLocation StartLoc, SourceLocation EndLoc,
5668+
ArrayRef<OMPClause *> Clauses, unsigned NumLoops, Stmt *AssociatedStmt,
5669+
Stmt *TransformedStmt, Stmt *PreInits);
5670+
5671+
/// Build an empty '#pragma omp stripe' AST node for deserialization.
5672+
///
5673+
/// \param C Context of the AST.
5674+
/// \param NumClauses Number of clauses to allocate.
5675+
/// \param NumLoops Number of associated loops to allocate.
5676+
static OMPStripeDirective *
5677+
CreateEmpty(const ASTContext &C, unsigned NumClauses, unsigned NumLoops);
5678+
5679+
/// Gets/sets the associated loops after striping.
5680+
///
5681+
/// This is in de-sugared format stored as a CompoundStmt.
5682+
///
5683+
/// \code
5684+
/// for (...)
5685+
/// ...
5686+
/// \endcode
5687+
///
5688+
/// Note that if the generated loops a become associated loops of another
5689+
/// directive, they may need to be hoisted before them.
5690+
Stmt *getTransformedStmt() const {
5691+
return Data->getChildren()[TransformedStmtOffset];
5692+
}
5693+
5694+
/// Return preinits statement.
5695+
Stmt *getPreInits() const { return Data->getChildren()[PreInitsOffset]; }
5696+
5697+
static bool classof(const Stmt *T) {
5698+
return T->getStmtClass() == OMPStripeDirectiveClass;
5699+
}
5700+
};
5701+
56245702
/// This represents the '#pragma omp unroll' loop transformation directive.
56255703
///
56265704
/// \code

clang/include/clang/Basic/StmtNodes.td

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -231,6 +231,7 @@ def OMPParallelDirective : StmtNode<OMPExecutableDirective>;
231231
def OMPSimdDirective : StmtNode<OMPLoopDirective>;
232232
def OMPLoopTransformationDirective : StmtNode<OMPLoopBasedDirective, 1>;
233233
def OMPTileDirective : StmtNode<OMPLoopTransformationDirective>;
234+
def OMPStripeDirective : StmtNode<OMPLoopTransformationDirective>;
234235
def OMPUnrollDirective : StmtNode<OMPLoopTransformationDirective>;
235236
def OMPReverseDirective : StmtNode<OMPLoopTransformationDirective>;
236237
def OMPInterchangeDirective : StmtNode<OMPLoopTransformationDirective>;

clang/include/clang/Sema/SemaOpenMP.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -440,6 +440,9 @@ class SemaOpenMP : public SemaBase {
440440
StmtResult ActOnOpenMPTileDirective(ArrayRef<OMPClause *> Clauses,
441441
Stmt *AStmt, SourceLocation StartLoc,
442442
SourceLocation EndLoc);
443+
StmtResult ActOnOpenMPStripeDirective(ArrayRef<OMPClause *> Clauses,
444+
Stmt *AStmt, SourceLocation StartLoc,
445+
SourceLocation EndLoc);
443446
/// Called on well-formed '#pragma omp unroll' after parsing of its clauses
444447
/// and the associated statement.
445448
StmtResult ActOnOpenMPUnrollDirective(ArrayRef<OMPClause *> Clauses,

clang/include/clang/Serialization/ASTBitCodes.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1939,6 +1939,7 @@ enum StmtCode {
19391939
STMT_OMP_PARALLEL_DIRECTIVE,
19401940
STMT_OMP_SIMD_DIRECTIVE,
19411941
STMT_OMP_TILE_DIRECTIVE,
1942+
STMP_OMP_STRIPE_DIRECTIVE,
19421943
STMT_OMP_UNROLL_DIRECTIVE,
19431944
STMT_OMP_REVERSE_DIRECTIVE,
19441945
STMT_OMP_INTERCHANGE_DIRECTIVE,

clang/lib/AST/StmtOpenMP.cpp

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -417,6 +417,27 @@ OMPTileDirective::Create(const ASTContext &C, SourceLocation StartLoc,
417417
return Dir;
418418
}
419419

420+
OMPStripeDirective *
421+
OMPStripeDirective::Create(const ASTContext &C, SourceLocation StartLoc,
422+
SourceLocation EndLoc, ArrayRef<OMPClause *> Clauses,
423+
unsigned NumLoops, Stmt *AssociatedStmt,
424+
Stmt *TransformedStmt, Stmt *PreInits) {
425+
OMPStripeDirective *Dir = createDirective<OMPStripeDirective>(
426+
C, Clauses, AssociatedStmt, TransformedStmtOffset + 1, StartLoc, EndLoc,
427+
NumLoops);
428+
Dir->setTransformedStmt(TransformedStmt);
429+
Dir->setPreInits(PreInits);
430+
return Dir;
431+
}
432+
433+
OMPStripeDirective *OMPStripeDirective::CreateEmpty(const ASTContext &C,
434+
unsigned NumClauses,
435+
unsigned NumLoops) {
436+
return createEmptyDirective<OMPStripeDirective>(
437+
C, NumClauses, /*HasAssociatedStmt=*/true, TransformedStmtOffset + 1,
438+
SourceLocation(), SourceLocation(), NumLoops);
439+
}
440+
420441
OMPTileDirective *OMPTileDirective::CreateEmpty(const ASTContext &C,
421442
unsigned NumClauses,
422443
unsigned NumLoops) {

clang/lib/AST/StmtPrinter.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -764,6 +764,11 @@ void StmtPrinter::VisitOMPTileDirective(OMPTileDirective *Node) {
764764
PrintOMPExecutableDirective(Node);
765765
}
766766

767+
void StmtPrinter::VisitOMPStripeDirective(OMPStripeDirective *Node) {
768+
Indent() << "#pragma omp stripe";
769+
PrintOMPExecutableDirective(Node);
770+
}
771+
767772
void StmtPrinter::VisitOMPUnrollDirective(OMPUnrollDirective *Node) {
768773
Indent() << "#pragma omp unroll";
769774
PrintOMPExecutableDirective(Node);

clang/lib/AST/StmtProfile.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1007,6 +1007,10 @@ void StmtProfiler::VisitOMPTileDirective(const OMPTileDirective *S) {
10071007
VisitOMPLoopTransformationDirective(S);
10081008
}
10091009

1010+
void StmtProfiler::VisitOMPStripeDirective(const OMPStripeDirective *S) {
1011+
VisitOMPLoopTransformationDirective(S);
1012+
}
1013+
10101014
void StmtProfiler::VisitOMPUnrollDirective(const OMPUnrollDirective *S) {
10111015
VisitOMPLoopTransformationDirective(S);
10121016
}

clang/lib/Basic/OpenMPKinds.cpp

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -700,7 +700,7 @@ bool clang::isOpenMPLoopBoundSharingDirective(OpenMPDirectiveKind Kind) {
700700

701701
bool clang::isOpenMPLoopTransformationDirective(OpenMPDirectiveKind DKind) {
702702
return DKind == OMPD_tile || DKind == OMPD_unroll || DKind == OMPD_reverse ||
703-
DKind == OMPD_interchange;
703+
DKind == OMPD_interchange || DKind == OMPD_stripe;
704704
}
705705

706706
bool clang::isOpenMPCombinedParallelADirective(OpenMPDirectiveKind DKind) {
@@ -827,6 +827,7 @@ void clang::getOpenMPCaptureRegions(
827827
case OMPD_single:
828828
case OMPD_target_data:
829829
case OMPD_taskgroup:
830+
case OMPD_stripe:
830831
// These directives (when standalone) use OMPD_unknown as the region,
831832
// but when they're constituents of a compound directive, and other
832833
// leafs from that directive have specific regions, then these directives

clang/lib/CodeGen/CGStmtOpenMP.cpp

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -187,6 +187,8 @@ class OMPLoopScope : public CodeGenFunction::RunCleanupsScope {
187187
PreInits = LD->getPreInits();
188188
} else if (const auto *Tile = dyn_cast<OMPTileDirective>(&S)) {
189189
PreInits = Tile->getPreInits();
190+
} else if (const auto *Stripe = dyn_cast<OMPStripeDirective>(&S)) {
191+
PreInits = Stripe->getPreInits();
190192
} else if (const auto *Unroll = dyn_cast<OMPUnrollDirective>(&S)) {
191193
PreInits = Unroll->getPreInits();
192194
} else if (const auto *Reverse = dyn_cast<OMPReverseDirective>(&S)) {
@@ -2820,6 +2822,12 @@ void CodeGenFunction::EmitOMPTileDirective(const OMPTileDirective &S) {
28202822
EmitStmt(S.getTransformedStmt());
28212823
}
28222824

2825+
void CodeGenFunction::EmitOMPStripeDirective(const OMPStripeDirective &S) {
2826+
// Emit the de-sugared statement.
2827+
OMPTransformDirectiveScopeRAII StripeScope(*this, &S);
2828+
EmitStmt(S.getTransformedStmt());
2829+
}
2830+
28232831
void CodeGenFunction::EmitOMPReverseDirective(const OMPReverseDirective &S) {
28242832
// Emit the de-sugared statement.
28252833
OMPTransformDirectiveScopeRAII ReverseScope(*this, &S);

clang/lib/CodeGen/CodeGenFunction.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3837,6 +3837,7 @@ class CodeGenFunction : public CodeGenTypeCache {
38373837
void EmitOMPParallelDirective(const OMPParallelDirective &S);
38383838
void EmitOMPSimdDirective(const OMPSimdDirective &S);
38393839
void EmitOMPTileDirective(const OMPTileDirective &S);
3840+
void EmitOMPStripeDirective(const OMPStripeDirective &S);
38403841
void EmitOMPUnrollDirective(const OMPUnrollDirective &S);
38413842
void EmitOMPReverseDirective(const OMPReverseDirective &S);
38423843
void EmitOMPInterchangeDirective(const OMPInterchangeDirective &S);

clang/lib/Parse/ParseOpenMP.cpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2548,9 +2548,10 @@ StmtResult Parser::ParseOpenMPExecutableDirective(
25482548
}
25492549
}
25502550

2551-
if (DKind == OMPD_tile && !SeenClauses[unsigned(OMPC_sizes)]) {
2551+
if ((DKind == OMPD_tile || DKind == OMPD_stripe) &&
2552+
!SeenClauses[unsigned(OMPC_sizes)]) {
25522553
Diag(Loc, diag::err_omp_required_clause)
2553-
<< getOpenMPDirectiveName(OMPD_tile) << "sizes";
2554+
<< getOpenMPDirectiveName(DKind) << "sizes";
25542555
}
25552556

25562557
StmtResult AssociatedStmt;

clang/lib/Sema/SemaExceptionSpec.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1488,6 +1488,7 @@ CanThrowResult Sema::canThrow(const Stmt *S) {
14881488
case Stmt::OMPSectionsDirectiveClass:
14891489
case Stmt::OMPSimdDirectiveClass:
14901490
case Stmt::OMPTileDirectiveClass:
1491+
case Stmt::OMPStripeDirectiveClass:
14911492
case Stmt::OMPUnrollDirectiveClass:
14921493
case Stmt::OMPReverseDirectiveClass:
14931494
case Stmt::OMPInterchangeDirectiveClass:

0 commit comments

Comments
 (0)