https://github.com/kparzysz updated https://github.com/llvm/llvm-project/pull/117917
>From 43f008a7f8b7a6377f6cb7f3ea4cc20394c2d79d Mon Sep 17 00:00:00 2001 From: Krzysztof Parzyszek <krzysztof.parzys...@amd.com> Date: Wed, 27 Nov 2024 08:34:33 -0600 Subject: [PATCH 1/2] [flang][OpenMP] Use new modifiers in DEPEND/GRAINSIZE/NUM_TASKS The usual changes, added more references to OpenMP specs. --- flang/examples/FeatureList/FeatureList.cpp | 6 +- flang/include/flang/Parser/dump-parse-tree.h | 7 ++- flang/include/flang/Parser/parse-tree.h | 42 ++++++++++---- .../flang/Semantics/openmp-modifiers.h | 1 + flang/lib/Lower/OpenMP/Clauses.cpp | 55 +++++++++---------- flang/lib/Lower/OpenMP/Clauses.h | 1 + flang/lib/Parser/openmp-parsers.cpp | 31 +++++++++-- flang/lib/Parser/parse-tree.cpp | 13 ++++- flang/lib/Parser/unparse.cpp | 16 +++--- flang/lib/Semantics/check-omp-structure.cpp | 15 ++--- flang/lib/Semantics/openmp-modifiers.cpp | 21 ++++++- flang/test/Parser/OpenMP/depobj-construct.f90 | 4 +- flang/test/Parser/OpenMP/taskloop.f90 | 8 +-- flang/test/Semantics/OpenMP/depend05.f90 | 2 +- llvm/include/llvm/Frontend/OpenMP/ClauseT.h | 5 +- 15 files changed, 146 insertions(+), 81 deletions(-) diff --git a/flang/examples/FeatureList/FeatureList.cpp b/flang/examples/FeatureList/FeatureList.cpp index 2e90f19dc2e62c..c5cb8c8fdf40bb 100644 --- a/flang/examples/FeatureList/FeatureList.cpp +++ b/flang/examples/FeatureList/FeatureList.cpp @@ -488,7 +488,9 @@ struct NodeVisitor { READ_FEATURE(OmpEndLoopDirective) READ_FEATURE(OmpEndSectionsDirective) READ_FEATURE(OmpGrainsizeClause) - READ_FEATURE(OmpGrainsizeClause::Prescriptiveness) + READ_FEATURE(OmpGrainsizeClause::Modifier) + READ_FEATURE(OmpPrescriptiveness) + READ_FEATURE(OmpPrescriptiveness::Value) READ_FEATURE(OmpIfClause) READ_FEATURE(OmpIfClause::DirectiveNameModifier) READ_FEATURE(OmpLinearClause) @@ -500,7 +502,7 @@ struct NodeVisitor { READ_FEATURE(OmpMapClause) READ_FEATURE(OmpMapClause::Modifier) READ_FEATURE(OmpNumTasksClause) - READ_FEATURE(OmpNumTasksClause::Prescriptiveness) + READ_FEATURE(OmpNumTasksClause::Modifier) READ_FEATURE(OmpObject) READ_FEATURE(OmpObjectList) READ_FEATURE(OmpOrderClause) diff --git a/flang/include/flang/Parser/dump-parse-tree.h b/flang/include/flang/Parser/dump-parse-tree.h index 3699aa34f4f8ad..1ec38de29b85d6 100644 --- a/flang/include/flang/Parser/dump-parse-tree.h +++ b/flang/include/flang/Parser/dump-parse-tree.h @@ -534,6 +534,7 @@ class ParseTreeDumper { NODE(OmpDoacross, Source) NODE(parser, OmpDependClause) NODE(OmpDependClause, TaskDep) + NODE(OmpDependClause::TaskDep, Modifier) NODE(parser, OmpDetachClause) NODE(parser, OmpDoacrossClause) NODE(parser, OmpDestroyClause) @@ -572,9 +573,11 @@ class ParseTreeDumper { NODE(parser, OmpOrderModifier) NODE_ENUM(OmpOrderModifier, Value) NODE(parser, OmpGrainsizeClause) - NODE_ENUM(OmpGrainsizeClause, Prescriptiveness) + NODE(OmpGrainsizeClause, Modifier) + NODE(parser, OmpPrescriptiveness) + NODE_ENUM(OmpPrescriptiveness, Value) NODE(parser, OmpNumTasksClause) - NODE_ENUM(OmpNumTasksClause, Prescriptiveness) + NODE(OmpNumTasksClause, Modifier) NODE(parser, OmpBindClause) NODE_ENUM(OmpBindClause, Binding) NODE(parser, OmpProcBindClause) diff --git a/flang/include/flang/Parser/parse-tree.h b/flang/include/flang/Parser/parse-tree.h index 2143e280457535..c00560b1f1726a 100644 --- a/flang/include/flang/Parser/parse-tree.h +++ b/flang/include/flang/Parser/parse-tree.h @@ -3627,6 +3627,15 @@ struct OmpOrderModifier { WRAPPER_CLASS_BOILERPLATE(OmpOrderModifier, Value); }; +// Ref: [5.1:166-171], [5.2:269-270] +// +// prescriptiveness -> +// STRICT // since 5.1 +struct OmpPrescriptiveness { + ENUM_CLASS(Value, Strict) + WRAPPER_CLASS_BOILERPLATE(OmpPrescriptiveness, Value); +}; + // Ref: [4.5:201-207], [5.0:293-299], [5.1:325-331], [5.2:124] // // reduction-identifier -> @@ -3816,8 +3825,8 @@ struct OmpDependClause { struct TaskDep { OmpTaskDependenceType::Value GetTaskDepType() const; TUPLE_CLASS_BOILERPLATE(TaskDep); - std::tuple<std::optional<OmpIterator>, OmpTaskDependenceType, OmpObjectList> - t; + MODIFIER_BOILERPLATE(OmpIterator, OmpTaskDependenceType); + std::tuple<MODIFIERS(), OmpObjectList> t; }; std::variant<TaskDep, OmpDoacross> u; }; @@ -3878,11 +3887,15 @@ struct OmpFromClause { std::tuple<MODIFIERS(), OmpObjectList, bool> t; }; -// OMP 5.2 12.6.1 grainsize-clause -> grainsize ([prescriptiveness :] value) +// Ref: [4.5:87-91], [5.0:140-146], [5.1:166-171], [5.2:269] +// +// grainsize-clause -> +// GRAINSIZE(grain-size) | // since 4.5 +// GRAINSIZE([prescriptiveness:] grain-size) // since 5.1 struct OmpGrainsizeClause { TUPLE_CLASS_BOILERPLATE(OmpGrainsizeClause); - ENUM_CLASS(Prescriptiveness, Strict); - std::tuple<std::optional<Prescriptiveness>, ScalarIntExpr> t; + MODIFIER_BOILERPLATE(OmpPrescriptiveness); + std::tuple<MODIFIERS(), ScalarIntExpr> t; }; // 2.12 if-clause -> IF ([ directive-name-modifier :] scalar-logical-expr) @@ -3948,6 +3961,17 @@ struct OmpMapClause { std::tuple<MODIFIERS(), OmpObjectList, bool> t; }; +// Ref: [4.5:87-91], [5.0:140-146], [5.1:166-171], [5.2:270] +// +// num-tasks-clause -> +// NUM_TASKS(num-tasks) | // since 4.5 +// NUM_TASKS([prescriptiveness:] num-tasks) // since 5.1 +struct OmpNumTasksClause { + TUPLE_CLASS_BOILERPLATE(OmpNumTasksClause); + MODIFIER_BOILERPLATE(OmpPrescriptiveness); + std::tuple<MODIFIERS(), ScalarIntExpr> t; +}; + // Ref: [5.0:101-109], [5.1:126-134], [5.2:233-234] // // order-clause -> @@ -4015,13 +4039,6 @@ struct OmpToClause { std::tuple<MODIFIERS(), OmpObjectList, bool> t; }; -// OMP 5.2 12.6.2 num_tasks-clause -> num_tasks ([prescriptiveness :] value) -struct OmpNumTasksClause { - TUPLE_CLASS_BOILERPLATE(OmpNumTasksClause); - ENUM_CLASS(Prescriptiveness, Strict); - std::tuple<std::optional<Prescriptiveness>, ScalarIntExpr> t; -}; - // Ref: [5.0:254-255], [5.1:287-288], [5.2:321-322] // // update-clause -> @@ -4030,6 +4047,7 @@ struct OmpNumTasksClause { // UPDATE(task-dependence-type) // since 5.2 struct OmpUpdateClause { UNION_CLASS_BOILERPLATE(OmpUpdateClause); + // The dependence type is an argument here, not a modifier. std::variant<OmpDependenceType, OmpTaskDependenceType> u; }; diff --git a/flang/include/flang/Semantics/openmp-modifiers.h b/flang/include/flang/Semantics/openmp-modifiers.h index fab4b38090b049..dbc554198df21f 100644 --- a/flang/include/flang/Semantics/openmp-modifiers.h +++ b/flang/include/flang/Semantics/openmp-modifiers.h @@ -82,6 +82,7 @@ DECLARE_DESCRIPTOR(parser::OmpMapType); DECLARE_DESCRIPTOR(parser::OmpMapTypeModifier); DECLARE_DESCRIPTOR(parser::OmpOrderModifier); DECLARE_DESCRIPTOR(parser::OmpOrderingModifier); +DECLARE_DESCRIPTOR(parser::OmpPrescriptiveness); DECLARE_DESCRIPTOR(parser::OmpReductionIdentifier); DECLARE_DESCRIPTOR(parser::OmpReductionModifier); DECLARE_DESCRIPTOR(parser::OmpTaskDependenceType); diff --git a/flang/lib/Lower/OpenMP/Clauses.cpp b/flang/lib/Lower/OpenMP/Clauses.cpp index 2792232253879f..ff2667983d4367 100644 --- a/flang/lib/Lower/OpenMP/Clauses.cpp +++ b/flang/lib/Lower/OpenMP/Clauses.cpp @@ -369,6 +369,15 @@ clause::DependenceType makeDepType(const parser::OmpTaskDependenceType &inp) { llvm_unreachable("Unexpected task dependence type"); } +clause::Prescriptiveness +makePrescriptiveness(parser::OmpPrescriptiveness::Value v) { + switch (v) { + case parser::OmpPrescriptiveness::Value::Strict: + return clause::Prescriptiveness::Strict; + } + llvm_unreachable("Unexpected prescriptiveness"); +} + // -------------------------------------------------------------------- // Actual clauses. Each T (where tomp::T exists in ClauseT) has its "make". @@ -615,15 +624,18 @@ Depend make(const parser::OmpClause::Depend &inp, using Variant = decltype(Depend::u); auto visitTaskDep = [&](const wrapped::TaskDep &s) -> Variant { - auto &t0 = std::get<std::optional<parser::OmpIterator>>(s.t); - auto &t1 = std::get<parser::OmpTaskDependenceType>(s.t); - auto &t2 = std::get<parser::OmpObjectList>(s.t); + auto &mods = semantics::OmpGetModifiers(s); + auto *m0 = semantics::OmpGetUniqueModifier<parser::OmpIterator>(mods); + auto *m1 = + semantics::OmpGetUniqueModifier<parser::OmpTaskDependenceType>(mods); + auto &t1 = std::get<parser::OmpObjectList>(s.t); + assert(m1 && "expecting task dependence type"); auto &&maybeIter = - maybeApply([&](auto &&s) { return makeIterator(s, semaCtx); }, t0); - return Depend::TaskDep{{/*DependenceType=*/makeDepType(t1), + m0 ? makeIterator(*m0, semaCtx) : std::optional<Iterator>{}; + return Depend::TaskDep{{/*DependenceType=*/makeDepType(*m1), /*Iterator=*/std::move(maybeIter), - /*LocatorList=*/makeObjects(t2, semaCtx)}}; + /*LocatorList=*/makeObjects(t1, semaCtx)}}; }; return Depend{common::visit( // @@ -785,19 +797,12 @@ From make(const parser::OmpClause::From &inp, Grainsize make(const parser::OmpClause::Grainsize &inp, semantics::SemanticsContext &semaCtx) { // inp.v -> parser::OmpGrainsizeClause - using wrapped = parser::OmpGrainsizeClause; - - CLAUSET_ENUM_CONVERT( // - convert, parser::OmpGrainsizeClause::Prescriptiveness, - Grainsize::Prescriptiveness, - // clang-format off - MS(Strict, Strict) - // clang-format on - ); - auto &t0 = std::get<std::optional<wrapped::Prescriptiveness>>(inp.v.t); + auto &mods = semantics::OmpGetModifiers(inp.v); + auto *m0 = semantics::OmpGetUniqueModifier<parser::OmpPrescriptiveness>(mods); auto &t1 = std::get<parser::ScalarIntExpr>(inp.v.t); - return Grainsize{{/*Prescriptiveness=*/maybeApply(convert, t0), - /*Grainsize=*/makeExpr(t1, semaCtx)}}; + return Grainsize{ + {/*Prescriptiveness=*/maybeApplyToV(makePrescriptiveness, m0), + /*Grainsize=*/makeExpr(t1, semaCtx)}}; } HasDeviceAddr make(const parser::OmpClause::HasDeviceAddr &inp, @@ -1047,18 +1052,10 @@ Novariants make(const parser::OmpClause::Novariants &inp, NumTasks make(const parser::OmpClause::NumTasks &inp, semantics::SemanticsContext &semaCtx) { // inp.v -> parser::OmpNumTasksClause - using wrapped = parser::OmpNumTasksClause; - - CLAUSET_ENUM_CONVERT( // - convert, parser::OmpNumTasksClause::Prescriptiveness, - NumTasks::Prescriptiveness, - // clang-format off - MS(Strict, Strict) - // clang-format on - ); - auto &t0 = std::get<std::optional<wrapped::Prescriptiveness>>(inp.v.t); + auto &mods = semantics::OmpGetModifiers(inp.v); + auto *m0 = semantics::OmpGetUniqueModifier<parser::OmpPrescriptiveness>(mods); auto &t1 = std::get<parser::ScalarIntExpr>(inp.v.t); - return NumTasks{{/*Prescriptiveness=*/maybeApply(convert, t0), + return NumTasks{{/*Prescriptiveness=*/maybeApplyToV(makePrescriptiveness, m0), /*NumTasks=*/makeExpr(t1, semaCtx)}}; } diff --git a/flang/lib/Lower/OpenMP/Clauses.h b/flang/lib/Lower/OpenMP/Clauses.h index 562685e43c13bf..65282d243d87af 100644 --- a/flang/lib/Lower/OpenMP/Clauses.h +++ b/flang/lib/Lower/OpenMP/Clauses.h @@ -176,6 +176,7 @@ using DefinedOperator = tomp::type::DefinedOperatorT<IdTy, ExprTy>; using ProcedureDesignator = tomp::type::ProcedureDesignatorT<IdTy, ExprTy>; using ReductionOperator = tomp::type::ReductionIdentifierT<IdTy, ExprTy>; using DependenceType = tomp::type::DependenceType; +using Prescriptiveness = tomp::type::Prescriptiveness; // "Requires" clauses are handled early on, and the aggregated information // is stored in the Symbol details of modules, programs, and subprograms. diff --git a/flang/lib/Parser/openmp-parsers.cpp b/flang/lib/Parser/openmp-parsers.cpp index 5b61d053ad1622..44465fd787e584 100644 --- a/flang/lib/Parser/openmp-parsers.cpp +++ b/flang/lib/Parser/openmp-parsers.cpp @@ -176,6 +176,9 @@ TYPE_PARSER(construct<OmpOrderingModifier>( "NONMONOTONIC" >> pure(OmpOrderingModifier::Value::Nonmonotonic) || "SIMD" >> pure(OmpOrderingModifier::Value::Simd))) +TYPE_PARSER(construct<OmpPrescriptiveness>( + "STRICT" >> pure(OmpPrescriptiveness::Value::Strict))) + TYPE_PARSER(construct<OmpReductionModifier>( "INSCAN" >> pure(OmpReductionModifier::Value::Inscan) || "TASK" >> pure(OmpReductionModifier::Value::Task) || @@ -213,6 +216,11 @@ TYPE_PARSER(sourced(construct<OmpAllocateClause::Modifier>(sourced( TYPE_PARSER(sourced( construct<OmpDefaultmapClause::Modifier>(Parser<OmpVariableCategory>{}))) +TYPE_PARSER(sourced(construct<OmpDependClause::TaskDep::Modifier>(sourced( + construct<OmpDependClause::TaskDep::Modifier>(Parser<OmpIterator>{}) || + construct<OmpDependClause::TaskDep::Modifier>( + Parser<OmpTaskDependenceType>{}))))) + TYPE_PARSER( sourced(construct<OmpDeviceClause::Modifier>(Parser<OmpDeviceModifier>{}))) @@ -221,6 +229,9 @@ TYPE_PARSER(sourced(construct<OmpFromClause::Modifier>( construct<OmpFromClause::Modifier>(Parser<OmpMapper>{}) || construct<OmpFromClause::Modifier>(Parser<OmpIterator>{}))))) +TYPE_PARSER(sourced(construct<OmpGrainsizeClause::Modifier>( + Parser<OmpPrescriptiveness>{}))) + TYPE_PARSER(sourced(construct<OmpMapClause::Modifier>( sourced(construct<OmpMapClause::Modifier>(Parser<OmpMapTypeModifier>{}) || construct<OmpMapClause::Modifier>(Parser<OmpMapper>{}) || @@ -230,6 +241,9 @@ TYPE_PARSER(sourced(construct<OmpMapClause::Modifier>( TYPE_PARSER( sourced(construct<OmpOrderClause::Modifier>(Parser<OmpOrderModifier>{}))) +TYPE_PARSER(sourced(construct<OmpNumTasksClause::Modifier>( + Parser<OmpPrescriptiveness>{}))) + TYPE_PARSER(sourced(construct<OmpReductionClause::Modifier>(sourced( construct<OmpReductionClause::Modifier>(Parser<OmpReductionModifier>{}) || construct<OmpReductionClause::Modifier>( @@ -382,10 +396,17 @@ TYPE_PARSER(construct<OmpDoacross>( TYPE_CONTEXT_PARSER("Omp Depend clause"_en_US, construct<OmpDependClause>( + // Try to parse OmpDoacross first, because TaskDep will succeed on + // "sink: xxx", interpreting it to not have any modifiers, and "sink" + // being an OmpObject. Parsing of the TaskDep variant will stop right + // after the "sink", leaving the ": xxx" unvisited. + construct<OmpDependClause>(Parser<OmpDoacross>{}) || + // Parse TaskDep after Doacross. construct<OmpDependClause>(construct<OmpDependClause::TaskDep>( - maybe(Parser<OmpIterator>{} / ","_tok), - Parser<OmpTaskDependenceType>{} / ":", Parser<OmpObjectList>{})) || - construct<OmpDependClause>(Parser<OmpDoacross>{}))) + maybe(nonemptyList(Parser<OmpDependClause::TaskDep::Modifier>{}) / + ": "), + Parser<OmpObjectList>{})) +)) TYPE_CONTEXT_PARSER("Omp Doacross clause"_en_US, construct<OmpDoacrossClause>(Parser<OmpDoacross>{})) @@ -427,12 +448,12 @@ TYPE_PARSER(construct<OmpOrderClause>( // OMP 5.2 12.6.1 grainsize([ prescriptiveness :] scalar-integer-expression) TYPE_PARSER(construct<OmpGrainsizeClause>( - maybe("STRICT" >> pure(OmpGrainsizeClause::Prescriptiveness::Strict) / ":"), + maybe(nonemptyList(Parser<OmpGrainsizeClause::Modifier>{}) / ":"), scalarIntExpr)) // OMP 5.2 12.6.2 num_tasks([ prescriptiveness :] scalar-integer-expression) TYPE_PARSER(construct<OmpNumTasksClause>( - maybe("STRICT" >> pure(OmpNumTasksClause::Prescriptiveness::Strict) / ":"), + maybe(nonemptyList(Parser<OmpNumTasksClause::Modifier>{}) / ":"), scalarIntExpr)) TYPE_PARSER( diff --git a/flang/lib/Parser/parse-tree.cpp b/flang/lib/Parser/parse-tree.cpp index 24b2902f286f4b..a414f226058e3e 100644 --- a/flang/lib/Parser/parse-tree.cpp +++ b/flang/lib/Parser/parse-tree.cpp @@ -267,7 +267,18 @@ OmpDependenceType::Value OmpDoacross::GetDepType() const { } OmpTaskDependenceType::Value OmpDependClause::TaskDep::GetTaskDepType() const { - return std::get<parser::OmpTaskDependenceType>(t).v; + using Modifier = OmpDependClause::TaskDep::Modifier; + auto &modifiers{std::get<std::optional<std::list<Modifier>>>(t)}; + if (modifiers) { + for (auto &m : *modifiers) { + if (auto *dep{std::get_if<OmpTaskDependenceType>(&m.u)}) { + return dep->v; + } + } + llvm_unreachable("expecting OmpTaskDependenceType in TaskDep"); + } else { + llvm_unreachable("expecting modifiers on OmpDependClause::TaskDep"); + } } } // namespace Fortran::parser diff --git a/flang/lib/Parser/unparse.cpp b/flang/lib/Parser/unparse.cpp index 80ebd692bd1192..cd025333a077d3 100644 --- a/flang/lib/Parser/unparse.cpp +++ b/flang/lib/Parser/unparse.cpp @@ -2171,13 +2171,13 @@ class UnparseVisitor { Walk(std::get<OmpOrderClause::Ordering>(x.t)); } void Unparse(const OmpGrainsizeClause &x) { - Walk(std::get<std::optional<OmpGrainsizeClause::Prescriptiveness>>(x.t), - ":"); + using Modifier = OmpGrainsizeClause::Modifier; + Walk(std::get<std::optional<std::list<Modifier>>>(x.t), ": "); Walk(std::get<ScalarIntExpr>(x.t)); } void Unparse(const OmpNumTasksClause &x) { - Walk( - std::get<std::optional<OmpNumTasksClause::Prescriptiveness>>(x.t), ":"); + using Modifier = OmpNumTasksClause::Modifier; + Walk(std::get<std::optional<std::list<Modifier>>>(x.t), ": "); Walk(std::get<ScalarIntExpr>(x.t)); } void Unparse(const OmpDoacross::Sink &x) { @@ -2186,8 +2186,8 @@ class UnparseVisitor { } void Unparse(const OmpDoacross::Source &) { Word("SOURCE"); } void Unparse(const OmpDependClause::TaskDep &x) { - Walk(std::get<OmpTaskDependenceType>(x.t)); - Put(":"); + using Modifier = OmpDependClause::TaskDep::Modifier; + Walk(std::get<std::optional<std::list<Modifier>>>(x.t), ": "); Walk(std::get<OmpObjectList>(x.t)); } void Unparse(const OmpDefaultmapClause &x) { @@ -2842,9 +2842,7 @@ class UnparseVisitor { WALK_NESTED_ENUM(OmpCancelType, Type) // OMP cancel-type WALK_NESTED_ENUM(OmpOrderClause, Ordering) // OMP ordering WALK_NESTED_ENUM(OmpOrderModifier, Value) // OMP order-modifier - WALK_NESTED_ENUM( - OmpGrainsizeClause, Prescriptiveness) // OMP grainsize-modifier - WALK_NESTED_ENUM(OmpNumTasksClause, Prescriptiveness) // OMP numtasks-modifier + WALK_NESTED_ENUM(OmpPrescriptiveness, Value) // OMP prescriptiveness WALK_NESTED_ENUM(OmpMapType, Value) // OMP map-type WALK_NESTED_ENUM(OmpMapTypeModifier, Value) // OMP map-type-modifier #undef WALK_NESTED_ENUM diff --git a/flang/lib/Semantics/check-omp-structure.cpp b/flang/lib/Semantics/check-omp-structure.cpp index ebcafb6a0e354e..9e589067c8868d 100644 --- a/flang/lib/Semantics/check-omp-structure.cpp +++ b/flang/lib/Semantics/check-omp-structure.cpp @@ -3698,18 +3698,13 @@ void OmpStructureChecker::Enter(const parser::OmpClause::Depend &x) { } } } - if (std::get<std::optional<parser::OmpIterator>>(taskDep->t)) { - unsigned allowedInVersion{50}; - if (version < allowedInVersion) { - context_.Say(GetContext().clauseSource, - "Iterator modifiers are not supported in %s, %s"_warn_en_US, - ThisVersion(version), TryVersion(allowedInVersion)); - } else { + if (OmpVerifyModifiers(*taskDep, llvm::omp::OMPC_depend, + GetContext().clauseSource, context_)) { + auto &modifiers{OmpGetModifiers(*taskDep)}; + if (OmpGetUniqueModifier<parser::OmpIterator>(modifiers)) { if (dir == llvm::omp::OMPD_depobj) { context_.Say(GetContext().clauseSource, - "An iterator-modifier may specify multiple locators, " - "a DEPEND clause on a DEPOBJ construct must only specify " - "one locator"_warn_en_US); + "An iterator-modifier may specify multiple locators, a DEPEND clause on a DEPOBJ construct must only specify one locator"_warn_en_US); } } } diff --git a/flang/lib/Semantics/openmp-modifiers.cpp b/flang/lib/Semantics/openmp-modifiers.cpp index 97227bfef0ea54..e384b0270e6eae 100644 --- a/flang/lib/Semantics/openmp-modifiers.cpp +++ b/flang/lib/Semantics/openmp-modifiers.cpp @@ -321,6 +321,22 @@ const OmpModifierDescriptor &OmpGetDescriptor<parser::OmpOrderingModifier>() { return desc; } +template <> +const OmpModifierDescriptor &OmpGetDescriptor<parser::OmpPrescriptiveness>() { + static const OmpModifierDescriptor desc{ + /*name=*/"prescriptiveness", + /*props=*/ + { + {51, {OmpProperty::Unique}}, + }, + /*clauses=*/ + { + {51, {Clause::OMPC_grainsize, Clause::OMPC_num_tasks}}, + }, + }; + return desc; +} + template <> const OmpModifierDescriptor & OmpGetDescriptor<parser::OmpReductionIdentifier>() { @@ -363,11 +379,12 @@ const OmpModifierDescriptor &OmpGetDescriptor<parser::OmpTaskDependenceType>() { /*name=*/"task-dependence-type", /*props=*/ { - {52, {OmpProperty::Required, OmpProperty::Ultimate}}, + {45, {OmpProperty::Required, OmpProperty::Ultimate}}, }, /*clauses=*/ { - {52, {Clause::OMPC_depend, Clause::OMPC_update}}, + {45, {Clause::OMPC_depend}}, + {51, {Clause::OMPC_depend, Clause::OMPC_update}}, }, }; return desc; diff --git a/flang/test/Parser/OpenMP/depobj-construct.f90 b/flang/test/Parser/OpenMP/depobj-construct.f90 index 51726a5adf99ec..f186c82a2ccc30 100644 --- a/flang/test/Parser/OpenMP/depobj-construct.f90 +++ b/flang/test/Parser/OpenMP/depobj-construct.f90 @@ -8,14 +8,14 @@ subroutine f00 !UNPARSE: SUBROUTINE f00 !UNPARSE: INTEGER x, y -!UNPARSE: !$OMP DEPOBJ(x) DEPEND(IN:y) +!UNPARSE: !$OMP DEPOBJ(x) DEPEND(IN: y) !UNPARSE: END SUBROUTINE !PARSE-TREE: ExecutionPartConstruct -> ExecutableConstruct -> OpenMPConstruct -> OpenMPStandaloneConstruct -> OpenMPDepobjConstruct !PARSE-TREE: | Verbatim !PARSE-TREE: | OmpObject -> Designator -> DataRef -> Name = 'x' !PARSE-TREE: | OmpClause -> Depend -> OmpDependClause -> TaskDep -!PARSE-TREE: | | OmpTaskDependenceType -> Value = In +!PARSE-TREE: | | Modifier -> OmpTaskDependenceType -> Value = In !PARSE-TREE: | | OmpObjectList -> OmpObject -> Designator -> DataRef -> Name = 'y' subroutine f01 diff --git a/flang/test/Parser/OpenMP/taskloop.f90 b/flang/test/Parser/OpenMP/taskloop.f90 index a9c361046bd5f5..f053aa7f0cff37 100644 --- a/flang/test/Parser/OpenMP/taskloop.f90 +++ b/flang/test/Parser/OpenMP/taskloop.f90 @@ -4,11 +4,11 @@ subroutine parallel_work integer :: i -!CHECK: !$OMP TASKLOOP GRAINSIZE(STRICT:500_4) +!CHECK: !$OMP TASKLOOP GRAINSIZE(STRICT: 500_4) !PARSE-TREE: OmpBeginLoopDirective !PARSE-TREE-NEXT: OmpLoopDirective -> llvm::omp::Directive = taskloop !PARSE-TREE-NEXT: OmpClauseList -> OmpClause -> Grainsize -> OmpGrainsizeClause -!PARSE-TREE-NEXT: Prescriptiveness = Strict +!PARSE-TREE-NEXT: Modifier -> OmpPrescriptiveness -> Value = Strict !PARSE-TREE-NEXT: Scalar -> Integer -> Expr = '500_4' !$omp taskloop grainsize(strict: 500) do i=1,10000 @@ -27,11 +27,11 @@ subroutine parallel_work end do !$omp end taskloop -!CHECK: !$OMP TASKLOOP NUM_TASKS(STRICT:500_4) +!CHECK: !$OMP TASKLOOP NUM_TASKS(STRICT: 500_4) !PARSE-TREE: OmpBeginLoopDirective !PARSE-TREE-NEXT: OmpLoopDirective -> llvm::omp::Directive = taskloop !PARSE-TREE-NEXT: OmpClauseList -> OmpClause -> NumTasks -> OmpNumTasksClause -!PARSE-TREE-NEXT: Prescriptiveness = Strict +!PARSE-TREE-NEXT: Modifier -> OmpPrescriptiveness -> Value = Strict !PARSE-TREE-NEXT: Scalar -> Integer -> Expr = '500_4' !$omp taskloop num_tasks(strict: 500) do i=1,10000 diff --git a/flang/test/Semantics/OpenMP/depend05.f90 b/flang/test/Semantics/OpenMP/depend05.f90 index 53fd82bd08a9eb..3ca091ef3187d1 100644 --- a/flang/test/Semantics/OpenMP/depend05.f90 +++ b/flang/test/Semantics/OpenMP/depend05.f90 @@ -2,7 +2,7 @@ subroutine f00(x) integer :: x(10) -!WARNING: Iterator modifiers are not supported in OpenMP v4.5, try -fopenmp-version=50 +!WARNING: 'iterator' modifier is not supported in OpenMP v4.5, try -fopenmp-version=50 !$omp task depend(iterator(i = 1:10), in: x(i)) x = 0 !$omp end task diff --git a/llvm/include/llvm/Frontend/OpenMP/ClauseT.h b/llvm/include/llvm/Frontend/OpenMP/ClauseT.h index 07efd6fd4e9da4..67632fb79f8aac 100644 --- a/llvm/include/llvm/Frontend/OpenMP/ClauseT.h +++ b/llvm/include/llvm/Frontend/OpenMP/ClauseT.h @@ -242,6 +242,7 @@ ENUM(MotionExpectation, Present); // V5.2: [15.9.1] `task-dependence-type` modifier ENUM(DependenceType, Depobj, In, Inout, Inoutset, Mutexinoutset, Out, Sink, Source); +ENUM(Prescriptiveness, Strict); template <typename I, typename E> // struct LoopIterationT { @@ -643,7 +644,7 @@ struct FullT { // V5.2: [12.6.1] `grainsize` clause template <typename T, typename I, typename E> // struct GrainsizeT { - ENUM(Prescriptiveness, Strict); + using Prescriptiveness = type::Prescriptiveness; using GrainSize = E; using TupleTrait = std::true_type; std::tuple<OPT(Prescriptiveness), GrainSize> t; @@ -876,8 +877,8 @@ struct NowaitT { // V5.2: [12.6.2] `num_tasks` clause template <typename T, typename I, typename E> // struct NumTasksT { + using Prescriptiveness = type::Prescriptiveness; using NumTasks = E; - ENUM(Prescriptiveness, Strict); using TupleTrait = std::true_type; std::tuple<OPT(Prescriptiveness), NumTasks> t; }; >From 24a9f62620e51bcbf1fad0fa21a127332597ca8c Mon Sep 17 00:00:00 2001 From: Krzysztof Parzyszek <krzysztof.parzys...@amd.com> Date: Wed, 27 Nov 2024 13:58:19 -0600 Subject: [PATCH 2/2] format --- flang/lib/Parser/openmp-parsers.cpp | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/flang/lib/Parser/openmp-parsers.cpp b/flang/lib/Parser/openmp-parsers.cpp index 44465fd787e584..1d3dd518601995 100644 --- a/flang/lib/Parser/openmp-parsers.cpp +++ b/flang/lib/Parser/openmp-parsers.cpp @@ -229,8 +229,8 @@ TYPE_PARSER(sourced(construct<OmpFromClause::Modifier>( construct<OmpFromClause::Modifier>(Parser<OmpMapper>{}) || construct<OmpFromClause::Modifier>(Parser<OmpIterator>{}))))) -TYPE_PARSER(sourced(construct<OmpGrainsizeClause::Modifier>( - Parser<OmpPrescriptiveness>{}))) +TYPE_PARSER(sourced( + construct<OmpGrainsizeClause::Modifier>(Parser<OmpPrescriptiveness>{}))) TYPE_PARSER(sourced(construct<OmpMapClause::Modifier>( sourced(construct<OmpMapClause::Modifier>(Parser<OmpMapTypeModifier>{}) || @@ -241,8 +241,8 @@ TYPE_PARSER(sourced(construct<OmpMapClause::Modifier>( TYPE_PARSER( sourced(construct<OmpOrderClause::Modifier>(Parser<OmpOrderModifier>{}))) -TYPE_PARSER(sourced(construct<OmpNumTasksClause::Modifier>( - Parser<OmpPrescriptiveness>{}))) +TYPE_PARSER(sourced( + construct<OmpNumTasksClause::Modifier>(Parser<OmpPrescriptiveness>{}))) TYPE_PARSER(sourced(construct<OmpReductionClause::Modifier>(sourced( construct<OmpReductionClause::Modifier>(Parser<OmpReductionModifier>{}) || @@ -405,8 +405,7 @@ TYPE_CONTEXT_PARSER("Omp Depend clause"_en_US, construct<OmpDependClause>(construct<OmpDependClause::TaskDep>( maybe(nonemptyList(Parser<OmpDependClause::TaskDep::Modifier>{}) / ": "), - Parser<OmpObjectList>{})) -)) + Parser<OmpObjectList>{})))) TYPE_CONTEXT_PARSER("Omp Doacross clause"_en_US, construct<OmpDoacrossClause>(Parser<OmpDoacross>{})) _______________________________________________ llvm-branch-commits mailing list llvm-branch-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits