[llvm-branch-commits] [flang] [flang][OpenMP] Use new modifiers in IF/LASTPRIVATE (PR #118128)
via llvm-branch-commits
llvm-branch-commits at lists.llvm.org
Fri Nov 29 11:41:40 PST 2024
llvmbot wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-flang-semantics
Author: Krzysztof Parzyszek (kparzysz)
<details>
<summary>Changes</summary>
The usual changes, added more references to OpenMP specs.
---
Patch is 42.91 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/118128.diff
17 Files Affected:
- (modified) flang/examples/FeatureList/FeatureList.cpp (+2-1)
- (modified) flang/examples/FlangOmpReport/FlangOmpReportVisitor.cpp (+3-2)
- (modified) flang/examples/FlangOmpReport/FlangOmpReportVisitor.h (+1-1)
- (modified) flang/include/flang/Parser/dump-parse-tree.h (+5-2)
- (modified) flang/include/flang/Parser/parse-tree.h (+41-9)
- (modified) flang/include/flang/Semantics/openmp-modifiers.h (+2)
- (modified) flang/lib/Lower/OpenMP/Clauses.cpp (+11-25)
- (modified) flang/lib/Parser/CMakeLists.txt (+1)
- (modified) flang/lib/Parser/openmp-parsers.cpp (+55-18)
- (modified) flang/lib/Parser/unparse.cpp (+8-7)
- (modified) flang/lib/Semantics/check-omp-structure.cpp (+77-44)
- (modified) flang/lib/Semantics/openmp-modifiers.cpp (+34)
- (modified) flang/test/Parser/OpenMP/if-clause-unparse.f90 (+10-10)
- (modified) flang/test/Parser/OpenMP/if-clause.f90 (+11-11)
- (modified) flang/test/Parser/OpenMP/lastprivate-clause.f90 (+2-2)
- (modified) flang/test/Semantics/OpenMP/clause-validity01.f90 (+2-2)
- (modified) flang/test/Semantics/OpenMP/if-clause.f90 (+32-32)
``````````diff
diff --git a/flang/examples/FeatureList/FeatureList.cpp b/flang/examples/FeatureList/FeatureList.cpp
index c5cb8c8fdf40bb..41a6255207976d 100644
--- a/flang/examples/FeatureList/FeatureList.cpp
+++ b/flang/examples/FeatureList/FeatureList.cpp
@@ -492,7 +492,8 @@ struct NodeVisitor {
READ_FEATURE(OmpPrescriptiveness)
READ_FEATURE(OmpPrescriptiveness::Value)
READ_FEATURE(OmpIfClause)
- READ_FEATURE(OmpIfClause::DirectiveNameModifier)
+ READ_FEATURE(OmpIfClause::Modifier)
+ READ_FEATURE(OmpDirectiveNameModifier)
READ_FEATURE(OmpLinearClause)
READ_FEATURE(OmpLinearClause::WithModifier)
READ_FEATURE(OmpLinearClause::WithoutModifier)
diff --git a/flang/examples/FlangOmpReport/FlangOmpReportVisitor.cpp b/flang/examples/FlangOmpReport/FlangOmpReportVisitor.cpp
index afabd564ad5bdc..2dc480f0c901b1 100644
--- a/flang/examples/FlangOmpReport/FlangOmpReportVisitor.cpp
+++ b/flang/examples/FlangOmpReport/FlangOmpReportVisitor.cpp
@@ -8,6 +8,7 @@
#include "FlangOmpReportVisitor.h"
#include "llvm/ADT/StringExtras.h"
+#include "llvm/Frontend/OpenMP/OMP.h"
namespace Fortran {
namespace parser {
@@ -238,9 +239,9 @@ void OpenMPCounterVisitor::Post(const OmpScheduleClause::Kind &c) {
clauseDetails +=
"type=" + std::string{OmpScheduleClause::EnumToString(c)} + ";";
}
-void OpenMPCounterVisitor::Post(const OmpIfClause::DirectiveNameModifier &c) {
+void OpenMPCounterVisitor::Post(const OmpDirectiveNameModifier &c) {
clauseDetails +=
- "name_modifier=" + std::string{OmpIfClause::EnumToString(c)} + ";";
+ "name_modifier=" + llvm::omp::getOpenMPDirectiveName(c.v).str() + ";";
}
void OpenMPCounterVisitor::Post(const OmpCancelType::Type &c) {
clauseDetails += "type=" + std::string{OmpCancelType::EnumToString(c)} + ";";
diff --git a/flang/examples/FlangOmpReport/FlangOmpReportVisitor.h b/flang/examples/FlangOmpReport/FlangOmpReportVisitor.h
index ed202e8ed2a4c7..59bdac8594cb7c 100644
--- a/flang/examples/FlangOmpReport/FlangOmpReportVisitor.h
+++ b/flang/examples/FlangOmpReport/FlangOmpReportVisitor.h
@@ -77,7 +77,7 @@ struct OpenMPCounterVisitor {
void Post(const OmpTaskDependenceType::Value &c);
void Post(const OmpMapType::Value &c);
void Post(const OmpScheduleClause::Kind &c);
- void Post(const OmpIfClause::DirectiveNameModifier &c);
+ void Post(const OmpDirectiveNameModifier &c);
void Post(const OmpCancelType::Type &c);
void Post(const OmpClause &c);
void PostClauseCommon(const ClauseInfo &ci);
diff --git a/flang/include/flang/Parser/dump-parse-tree.h b/flang/include/flang/Parser/dump-parse-tree.h
index 1ec38de29b85d6..b0b8d8d7ccc556 100644
--- a/flang/include/flang/Parser/dump-parse-tree.h
+++ b/flang/include/flang/Parser/dump-parse-tree.h
@@ -548,10 +548,13 @@ class ParseTreeDumper {
NODE(OmpFromClause, Modifier)
NODE(parser, OmpExpectation)
NODE_ENUM(OmpExpectation, Value)
+ NODE(parser, OmpDirectiveNameModifier)
NODE(parser, OmpIfClause)
- NODE_ENUM(OmpIfClause, DirectiveNameModifier)
- NODE_ENUM(OmpLastprivateClause, LastprivateModifier)
+ NODE(OmpIfClause, Modifier)
NODE(parser, OmpLastprivateClause)
+ NODE(OmpLastprivateClause, Modifier)
+ NODE(parser, OmpLastprivateModifier)
+ NODE_ENUM(OmpLastprivateModifier, Value)
NODE(parser, OmpLinearClause)
NODE(OmpLinearClause, WithModifier)
NODE(OmpLinearClause, WithoutModifier)
diff --git a/flang/include/flang/Parser/parse-tree.h b/flang/include/flang/Parser/parse-tree.h
index c00560b1f1726a..06c32831d2c60c 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -3543,6 +3543,23 @@ struct OmpDeviceModifier {
WRAPPER_CLASS_BOILERPLATE(OmpDeviceModifier, Value);
};
+// Ref: [5.2:72-73,230-323], in 4.5-5.1 it's scattered over individual
+// directives that allow the IF clause.
+//
+// directive-name-modifier ->
+// PARALLEL | TARGET | TARGET DATA |
+// TARGET ENTER DATA | TARGET EXIT DATA |
+// TARGET UPDATE | TASK | TASKLOOP | // since 4.5
+// CANCEL[*] | SIMD | // since 5.0
+// TEAMS // since 5.2
+//
+// [*] The IF clause is allowed on CANCEL in OpenMP 4.5, but only without
+// the directive-name-modifier. For the sake of uniformity CANCEL can be
+// considered a valid value in 4.5 as well.
+struct OmpDirectiveNameModifier {
+ WRAPPER_CLASS_BOILERPLATE(OmpDirectiveNameModifier, llvm::omp::Directive);
+};
+
// Ref: [5.1:205-209], [5.2:166-168]
//
// motion-modifier ->
@@ -3566,6 +3583,15 @@ struct OmpIterator {
WRAPPER_CLASS_BOILERPLATE(OmpIterator, std::list<OmpIteratorSpecifier>);
};
+// Ref: [5.0:288-290], [5.1:321-322], [5.2:115-117]
+//
+// lastprivate-modifier ->
+// CONDITIONAL // since 5.0
+struct OmpLastprivateModifier {
+ ENUM_CLASS(Value, Conditional)
+ WRAPPER_CLASS_BOILERPLATE(OmpLastprivateModifier, Value);
+};
+
// Ref: [4.5:207-210], [5.0:290-293], [5.1:323-325], [5.2:117-120]
//
// linear-modifier ->
@@ -3898,12 +3924,16 @@ struct OmpGrainsizeClause {
std::tuple<MODIFIERS(), ScalarIntExpr> t;
};
-// 2.12 if-clause -> IF ([ directive-name-modifier :] scalar-logical-expr)
+// Ref: [5.2:72-73], in 4.5-5.1 it's scattered over individual directives
+// that allow the IF clause.
+//
+// if-clause ->
+// IF([directive-name-modifier:]
+// scalar-logical-expression) // since 4.5
struct OmpIfClause {
TUPLE_CLASS_BOILERPLATE(OmpIfClause);
- ENUM_CLASS(DirectiveNameModifier, Parallel, Simd, Target, TargetData,
- TargetEnterData, TargetExitData, TargetUpdate, Task, Taskloop, Teams)
- std::tuple<std::optional<DirectiveNameModifier>, ScalarLogicalExpr> t;
+ MODIFIER_BOILERPLATE(OmpDirectiveNameModifier);
+ std::tuple<MODIFIERS(), ScalarLogicalExpr> t;
};
// OMP 5.0 2.19.5.6 in_reduction-clause -> IN_REDUCTION (reduction-identifier:
@@ -3913,13 +3943,15 @@ struct OmpInReductionClause {
std::tuple<OmpReductionIdentifier, OmpObjectList> t;
};
-// OMP 5.0 2.19.4.5 lastprivate-clause ->
-// LASTPRIVATE ([lastprivate-modifier :] list)
-// lastprivate-modifier -> CONDITIONAL
+// Ref: [4.5:199-201], [5.0:288-290], [5.1:321-322], [5.2:115-117]
+//
+// lastprivate-clause ->
+// LASTPRIVATE(list) | // since 4.5
+// LASTPRIVATE([lastprivate-modifier:] list) // since 5.0
struct OmpLastprivateClause {
TUPLE_CLASS_BOILERPLATE(OmpLastprivateClause);
- ENUM_CLASS(LastprivateModifier, Conditional);
- std::tuple<std::optional<LastprivateModifier>, OmpObjectList> t;
+ MODIFIER_BOILERPLATE(OmpLastprivateModifier);
+ std::tuple<MODIFIERS(), OmpObjectList> t;
};
// 2.15.3.7 linear-clause -> LINEAR (linear-list[ : linear-step])
diff --git a/flang/include/flang/Semantics/openmp-modifiers.h b/flang/include/flang/Semantics/openmp-modifiers.h
index dbc554198df21f..4025ce112d9cab 100644
--- a/flang/include/flang/Semantics/openmp-modifiers.h
+++ b/flang/include/flang/Semantics/openmp-modifiers.h
@@ -74,8 +74,10 @@ DECLARE_DESCRIPTOR(parser::OmpAllocatorSimpleModifier);
DECLARE_DESCRIPTOR(parser::OmpChunkModifier);
DECLARE_DESCRIPTOR(parser::OmpDependenceType);
DECLARE_DESCRIPTOR(parser::OmpDeviceModifier);
+DECLARE_DESCRIPTOR(parser::OmpDirectiveNameModifier);
DECLARE_DESCRIPTOR(parser::OmpExpectation);
DECLARE_DESCRIPTOR(parser::OmpIterator);
+DECLARE_DESCRIPTOR(parser::OmpLastprivateModifier);
DECLARE_DESCRIPTOR(parser::OmpLinearModifier);
DECLARE_DESCRIPTOR(parser::OmpMapper);
DECLARE_DESCRIPTOR(parser::OmpMapType);
diff --git a/flang/lib/Lower/OpenMP/Clauses.cpp b/flang/lib/Lower/OpenMP/Clauses.cpp
index ff2667983d4367..10c31963ec493a 100644
--- a/flang/lib/Lower/OpenMP/Clauses.cpp
+++ b/flang/lib/Lower/OpenMP/Clauses.cpp
@@ -825,27 +825,13 @@ Holds make(const parser::OmpClause::Holds &inp,
If make(const parser::OmpClause::If &inp,
semantics::SemanticsContext &semaCtx) {
// inp.v -> parser::OmpIfClause
- using wrapped = parser::OmpIfClause;
-
- CLAUSET_ENUM_CONVERT( //
- convert, wrapped::DirectiveNameModifier, llvm::omp::Directive,
- // clang-format off
- MS(Parallel, OMPD_parallel)
- MS(Simd, OMPD_simd)
- MS(Target, OMPD_target)
- MS(TargetData, OMPD_target_data)
- MS(TargetEnterData, OMPD_target_enter_data)
- MS(TargetExitData, OMPD_target_exit_data)
- MS(TargetUpdate, OMPD_target_update)
- MS(Task, OMPD_task)
- MS(Taskloop, OMPD_taskloop)
- MS(Teams, OMPD_teams)
- // clang-format on
- );
- auto &t0 = std::get<std::optional<wrapped::DirectiveNameModifier>>(inp.v.t);
+ auto &mods = semantics::OmpGetModifiers(inp.v);
+ auto *m0 =
+ semantics::OmpGetUniqueModifier<parser::OmpDirectiveNameModifier>(mods);
auto &t1 = std::get<parser::ScalarLogicalExpr>(inp.v.t);
- return If{{/*DirectiveNameModifier=*/maybeApply(convert, t0),
- /*IfExpression=*/makeExpr(t1, semaCtx)}};
+ return If{
+ {/*DirectiveNameModifier=*/maybeApplyToV([](auto &&s) { return s; }, m0),
+ /*IfExpression=*/makeExpr(t1, semaCtx)}};
}
// Inbranch: empty
@@ -889,20 +875,20 @@ IsDevicePtr make(const parser::OmpClause::IsDevicePtr &inp,
Lastprivate make(const parser::OmpClause::Lastprivate &inp,
semantics::SemanticsContext &semaCtx) {
// inp.v -> parser::OmpLastprivateClause
- using wrapped = parser::OmpLastprivateClause;
-
CLAUSET_ENUM_CONVERT( //
- convert, parser::OmpLastprivateClause::LastprivateModifier,
+ convert, parser::OmpLastprivateModifier::Value,
Lastprivate::LastprivateModifier,
// clang-format off
MS(Conditional, Conditional)
// clang-format on
);
- auto &t0 = std::get<std::optional<wrapped::LastprivateModifier>>(inp.v.t);
+ auto &mods = semantics::OmpGetModifiers(inp.v);
+ auto *m0 =
+ semantics::OmpGetUniqueModifier<parser::OmpLastprivateModifier>(mods);
auto &t1 = std::get<parser::OmpObjectList>(inp.v.t);
- return Lastprivate{{/*LastprivateModifier=*/maybeApply(convert, t0),
+ return Lastprivate{{/*LastprivateModifier=*/maybeApplyToV(convert, m0),
/*List=*/makeObjects(t1, semaCtx)}};
}
diff --git a/flang/lib/Parser/CMakeLists.txt b/flang/lib/Parser/CMakeLists.txt
index 600a2f67df4431..d364671d7a3229 100644
--- a/flang/lib/Parser/CMakeLists.txt
+++ b/flang/lib/Parser/CMakeLists.txt
@@ -30,6 +30,7 @@ add_flang_library(FortranParser
LINK_COMPONENTS
Support
FrontendOpenACC
+ FrontendOpenMP
DEPENDS
omp_gen
diff --git a/flang/lib/Parser/openmp-parsers.cpp b/flang/lib/Parser/openmp-parsers.cpp
index 1d3dd518601995..920f97f7ca0f21 100644
--- a/flang/lib/Parser/openmp-parsers.cpp
+++ b/flang/lib/Parser/openmp-parsers.cpp
@@ -16,6 +16,10 @@
#include "token-parsers.h"
#include "type-parser-implementation.h"
#include "flang/Parser/parse-tree.h"
+#include "llvm/ADT/ArrayRef.h"
+#include "llvm/ADT/STLExtras.h"
+#include "llvm/ADT/StringRef.h"
+#include "llvm/Frontend/OpenMP/OMP.h"
// OpenMP Directives and Clauses
namespace Fortran::parser {
@@ -23,6 +27,47 @@ namespace Fortran::parser {
constexpr auto startOmpLine = skipStuffBeforeStatement >> "!$OMP "_sptok;
constexpr auto endOmpLine = space >> endOfLine;
+/// Parse OpenMP directive name (this includes compound directives).
+struct OmpDirectiveNameParser {
+ using resultType = llvm::omp::Directive;
+ using Token = TokenStringMatch<false, false>;
+
+ std::optional<resultType> Parse(ParseState &state) const {
+ for (const NameWithId &nid : directives()) {
+ if (attempt(Token(nid.first.data())).Parse(state)) {
+ return nid.second;
+ }
+ }
+ return std::nullopt;
+ }
+
+private:
+ using NameWithId = std::pair<std::string, llvm::omp::Directive>;
+
+ llvm::iterator_range<const NameWithId *> directives() const;
+ void initTokens(NameWithId *) const;
+};
+
+llvm::iterator_range<const OmpDirectiveNameParser::NameWithId *>
+OmpDirectiveNameParser::directives() const {
+ static NameWithId table[llvm::omp::Directive_enumSize];
+ [[maybe_unused]] static bool init = (initTokens(table), true);
+ return llvm::make_range(std::cbegin(table), std::cend(table));
+}
+
+void OmpDirectiveNameParser::initTokens(NameWithId *table) const {
+ for (size_t i{0}, e{llvm::omp::Directive_enumSize}; i != e; ++i) {
+ auto id{static_cast<llvm::omp::Directive>(i)};
+ llvm::StringRef name{llvm::omp::getOpenMPDirectiveName(id)};
+ table[i] = std::make_pair(name.str(), id);
+ }
+ // Sort the table with respect to the directive name length in a descending
+ // order. This is to make sure that longer names are tried first, before
+ // any potential prefix (e.g. "target update" before "target").
+ std::sort(table, table + llvm::omp::Directive_enumSize,
+ [](auto &a, auto &b) { return a.first.size() > b.first.size(); });
+}
+
template <typename Clause, typename Separator> struct ModifierList {
constexpr ModifierList(Separator sep) : sep_(sep) {}
constexpr ModifierList(const ModifierList &) = default;
@@ -136,6 +181,9 @@ TYPE_PARSER(construct<OmpIterator>( //
"ITERATOR" >>
parenthesized(nonemptyList(sourced(Parser<OmpIteratorSpecifier>{})))))
+TYPE_PARSER(construct<OmpLastprivateModifier>(
+ "CONDITIONAL" >> pure(OmpLastprivateModifier::Value::Conditional)))
+
// 2.15.3.7 LINEAR (linear-list: linear-step)
// linear-list -> list | modifier(list)
// linear-modifier -> REF | VAL | UVAL
@@ -232,6 +280,11 @@ TYPE_PARSER(sourced(construct<OmpFromClause::Modifier>(
TYPE_PARSER(sourced(
construct<OmpGrainsizeClause::Modifier>(Parser<OmpPrescriptiveness>{})))
+TYPE_PARSER(sourced(construct<OmpIfClause::Modifier>(OmpDirectiveNameParser{})))
+
+TYPE_PARSER(sourced(construct<OmpLastprivateClause::Modifier>(
+ Parser<OmpLastprivateModifier>{})))
+
TYPE_PARSER(sourced(construct<OmpMapClause::Modifier>(
sourced(construct<OmpMapClause::Modifier>(Parser<OmpMapTypeModifier>{}) ||
construct<OmpMapClause::Modifier>(Parser<OmpMapper>{}) ||
@@ -345,22 +398,7 @@ TYPE_PARSER(construct<OmpDeviceTypeClause>(
// 2.12 IF (directive-name-modifier: scalar-logical-expr)
TYPE_PARSER(construct<OmpIfClause>(
- maybe(
- ("PARALLEL" >> pure(OmpIfClause::DirectiveNameModifier::Parallel) ||
- "SIMD" >> pure(OmpIfClause::DirectiveNameModifier::Simd) ||
- "TARGET ENTER DATA" >>
- pure(OmpIfClause::DirectiveNameModifier::TargetEnterData) ||
- "TARGET EXIT DATA" >>
- pure(OmpIfClause::DirectiveNameModifier::TargetExitData) ||
- "TARGET DATA" >>
- pure(OmpIfClause::DirectiveNameModifier::TargetData) ||
- "TARGET UPDATE" >>
- pure(OmpIfClause::DirectiveNameModifier::TargetUpdate) ||
- "TARGET" >> pure(OmpIfClause::DirectiveNameModifier::Target) ||
- "TASK"_id >> pure(OmpIfClause::DirectiveNameModifier::Task) ||
- "TASKLOOP" >> pure(OmpIfClause::DirectiveNameModifier::Taskloop) ||
- "TEAMS" >> pure(OmpIfClause::DirectiveNameModifier::Teams)) /
- ":"),
+ maybe(nonemptyList(Parser<OmpIfClause::Modifier>{}) / ":"),
scalarLogicalExpr))
TYPE_PARSER(construct<OmpReductionClause>(
@@ -460,8 +498,7 @@ TYPE_PARSER(
// OMP 5.0 2.19.4.5 LASTPRIVATE ([lastprivate-modifier :] list)
TYPE_PARSER(construct<OmpLastprivateClause>(
- maybe("CONDITIONAL" >>
- pure(OmpLastprivateClause::LastprivateModifier::Conditional) / ":"),
+ maybe(nonemptyList(Parser<OmpLastprivateClause::Modifier>{}) / ":"),
Parser<OmpObjectList>{}))
// OMP 5.2 11.7.1 BIND ( PARALLEL | TEAMS | THREAD )
diff --git a/flang/lib/Parser/unparse.cpp b/flang/lib/Parser/unparse.cpp
index cd025333a077d3..43c7ef540cb7af 100644
--- a/flang/lib/Parser/unparse.cpp
+++ b/flang/lib/Parser/unparse.cpp
@@ -2074,6 +2074,9 @@ class UnparseVisitor {
},
x.u);
}
+ void Unparse(const OmpDirectiveNameModifier &x) {
+ Word(llvm::omp::getOpenMPDirectiveName(x.v));
+ }
void Unparse(const OmpIteratorSpecifier &x) {
Walk(std::get<TypeDeclarationStmt>(x.t));
Put(" = ");
@@ -2090,9 +2093,8 @@ class UnparseVisitor {
Put(")");
}
void Unparse(const OmpLastprivateClause &x) {
- Walk(
- std::get<std::optional<OmpLastprivateClause::LastprivateModifier>>(x.t),
- ":");
+ using Modifier = OmpLastprivateClause::Modifier;
+ Walk(std::get<std::optional<std::list<Modifier>>>(x.t), ": ");
Walk(std::get<OmpObjectList>(x.t));
}
void Unparse(const OmpMapClause &x) {
@@ -2127,7 +2129,8 @@ class UnparseVisitor {
Walk(std::get<OmpObjectList>(x.t));
}
void Unparse(const OmpIfClause &x) {
- Walk(std::get<std::optional<OmpIfClause::DirectiveNameModifier>>(x.t), ":");
+ using Modifier = OmpIfClause::Modifier;
+ Walk(std::get<std::optional<std::list<Modifier>>>(x.t), ": ");
Walk(std::get<ScalarLogicalExpr>(x.t));
}
void Unparse(const OmpLinearClause::WithoutModifier &x) {
@@ -2826,8 +2829,7 @@ class UnparseVisitor {
WALK_NESTED_ENUM(OmpDefaultClause, DataSharingAttribute) // OMP default
WALK_NESTED_ENUM(OmpDefaultmapClause, ImplicitBehavior) // OMP defaultmap
WALK_NESTED_ENUM(OmpVariableCategory, Value) // OMP variable-category
- WALK_NESTED_ENUM(
- OmpLastprivateClause, LastprivateModifier) // OMP lastprivate-modifier
+ WALK_NESTED_ENUM(OmpLastprivateModifier, Value) // OMP lastprivate-modifier
WALK_NESTED_ENUM(OmpChunkModifier, Value) // OMP chunk-modifier
WALK_NESTED_ENUM(OmpLinearModifier, Value) // OMP linear-modifier
WALK_NESTED_ENUM(OmpOrderingModifier, Value) // OMP ordering-modifier
@@ -2838,7 +2840,6 @@ class UnparseVisitor {
OmpDeviceTypeClause, DeviceTypeDescription) // OMP device_type
WALK_NESTED_ENUM(OmpReductionModifier, Value) // OMP reduction-modifier
WALK_NESTED_ENUM(OmpExpectation, Value) // OMP motion-expectation
- WALK_NESTED_ENUM(OmpIfClause, DirectiveNameModifier) // OMP directive-modifier
WALK_NESTED_ENUM(OmpCancelType, Type) // OMP cancel-type
WALK_NESTED_ENUM(OmpOrderClause, Ordering) // OMP ordering
WALK_NESTED_ENUM(OmpOrderModifier, Value) // OMP order-modifier
diff --git a/flang/lib/Semantics/check-omp-structure.cpp b/flang/lib/Semantics/check-omp-structure.cpp
index 9e589067c8868d..a88aba5a54a023 100644
--- a/flang/lib/Semantics/check-omp-structure.cpp
+++ b/flang/lib/Semantics/check-omp-structure.cpp
@@ -3428,36 +3428,81 @@ void OmpStructureChecker::Enter(const parser::OmpClause::Defaultmap &x) {
void OmpStructureChecker::Enter(const parser::OmpClause::If &x) {
CheckAllowedClause(llvm::omp::Clause::OMPC_if);
- using dirNameModifier = parser::OmpIfClause::DirectiveNameModifier;
- // TODO Check that, when multiple 'if' clauses are applied to a combined
- // construct, at most one of them applies to each directive.
- static std::unordered_map<dirNameModifier, OmpDirectiveSet>
- dirNameModifierMap{{dirNameModifier::Parallel, llvm::omp::allParallelSet},
- {dirNameModifier::Simd, llvm::omp::allSimdSet},
- {dirNameModifier::Target, llvm::omp::allTargetSet},
- {dirNameModifier::TargetData,
- {llvm::omp::Directive::OMPD_target_data}},
- {dirNameModifier::TargetEnterData,
- {llvm::omp::Directive::OMPD_target_enter_data}},
- {dirNameModifier::TargetExitData,
- {llvm::omp::Directive::OMPD_target_exit_data}},
- {dirNameModifier::TargetUpdate,
- {llvm::omp::Directive::OMPD_target_update}},
- {dirNameModifier::Task, {llvm::omp::Directive::OMPD_task}},
- {dirNameModifier::Taskloop, llvm::omp::allTaskloopSet},
- {dirNameModifier::Teams, llvm::omp::allTeamsSet}};
- if (const auto &directiveName{
- std::get<std::optional<dirNameModifier>>(x.v.t)}) {
- auto search{dirNameModifierMap.find(*directiveName)};
- if (search == dirNameModifierMap.end() ||
- !search->second.test(GetContext().directive)) {
- context_
- .Say(GetContext().clauseSource,
- "Unmatched directive name modifier %s on the IF clause"_err_en_US,
- parser::ToUpperCaseLetters(
- parser::OmpIfClause::EnumToString(*directiveName)))
- .Attach(
- GetContext().directiveSo...
[truncated]
``````````
</details>
https://github.com/llvm/llvm-project/pull/118128
More information about the llvm-branch-commits
mailing list