-
Notifications
You must be signed in to change notification settings - Fork 13.1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Revert "Revert "[flang][openmp] Adds Parser and Semantic Support for Interop Construct, and Init and Use Clauses."" #132343
Conversation
@llvm/pr-subscribers-flang-parser @llvm/pr-subscribers-flang-semantics Author: None (swatheesh-mcw) ChangesReverts llvm/llvm-project#132005 Patch is 32.21 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/132343.diff 14 Files Affected:
diff --git a/flang/examples/FeatureList/FeatureList.cpp b/flang/examples/FeatureList/FeatureList.cpp
index 25485bbb8ff4d..94fdfa3e4dea9 100644
--- a/flang/examples/FeatureList/FeatureList.cpp
+++ b/flang/examples/FeatureList/FeatureList.cpp
@@ -522,6 +522,13 @@ struct NodeVisitor {
READ_FEATURE(OmpScheduleClause)
READ_FEATURE(OmpScheduleClause::Kind)
READ_FEATURE(OmpScheduleClause::Modifier)
+ READ_FEATURE(OmpInteropRuntimeIdentifier)
+ READ_FEATURE(OmpInteropPreference)
+ READ_FEATURE(OmpInteropType)
+ READ_FEATURE(OmpInteropType::Value)
+ READ_FEATURE(OmpInitClause)
+ READ_FEATURE(OmpInitClause::Modifier)
+ READ_FEATURE(OmpUseClause)
READ_FEATURE(OmpDeviceModifier)
READ_FEATURE(OmpDeviceClause)
READ_FEATURE(OmpDeviceClause::Modifier)
@@ -541,6 +548,7 @@ struct NodeVisitor {
READ_FEATURE(OpenACCConstruct)
READ_FEATURE(OpenACCDeclarativeConstruct)
READ_FEATURE(OpenACCLoopConstruct)
+ READ_FEATURE(OpenMPInteropConstruct)
READ_FEATURE(OpenACCRoutineConstruct)
READ_FEATURE(OpenACCStandaloneDeclarativeConstruct)
READ_FEATURE(OpenACCStandaloneConstruct)
diff --git a/flang/include/flang/Parser/dump-parse-tree.h b/flang/include/flang/Parser/dump-parse-tree.h
index 9bff2dab974ec..41ad15794ad15 100644
--- a/flang/include/flang/Parser/dump-parse-tree.h
+++ b/flang/include/flang/Parser/dump-parse-tree.h
@@ -657,6 +657,13 @@ class ParseTreeDumper {
NODE_ENUM(OmpDeviceModifier, Value)
NODE(parser, OmpDeviceTypeClause)
NODE_ENUM(OmpDeviceTypeClause, DeviceTypeDescription)
+ NODE(parser, OmpInteropRuntimeIdentifier)
+ NODE(parser, OmpInteropPreference)
+ NODE(parser, OmpInteropType)
+ NODE_ENUM(OmpInteropType, Value)
+ NODE(parser, OmpInitClause)
+ NODE(OmpInitClause, Modifier)
+ NODE(parser, OmpUseClause)
NODE(parser, OmpUpdateClause)
NODE(parser, OmpChunkModifier)
NODE_ENUM(OmpChunkModifier, Value)
@@ -675,6 +682,7 @@ class ParseTreeDumper {
NODE(parser, OpenACCDeclarativeConstruct)
NODE(parser, OpenACCEndConstruct)
NODE(parser, OpenACCLoopConstruct)
+ NODE(parser, OpenMPInteropConstruct)
NODE(parser, OpenACCRoutineConstruct)
NODE(parser, OpenACCStandaloneDeclarativeConstruct)
NODE(parser, OpenACCStandaloneConstruct)
diff --git a/flang/include/flang/Parser/parse-tree.h b/flang/include/flang/Parser/parse-tree.h
index 029c3de354b66..76cd3380e203c 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -3829,6 +3829,33 @@ struct OmpExpectation {
WRAPPER_CLASS_BOILERPLATE(OmpExpectation, Value);
};
+// REF: [5.1:217-220], [5.2:293-294]
+//
+// OmpInteropRuntimeIdentifier -> // since 5.2
+// CharLiteralConstant || ScalarIntConstantExpr
+struct OmpInteropRuntimeIdentifier {
+ UNION_CLASS_BOILERPLATE(OmpInteropRuntimeIdentifier);
+ std::variant<CharLiteralConstant, ScalarIntConstantExpr> u;
+};
+
+// REF: [5.1:217-220], [5.2:293-294]
+//
+// OmpInteropPreference -> // since 5.2
+// ([OmpRuntimeIdentifier, ...])
+struct OmpInteropPreference {
+ WRAPPER_CLASS_BOILERPLATE(
+ OmpInteropPreference, std::list<OmpInteropRuntimeIdentifier>);
+};
+
+// REF: [5.1:217-220], [5.2:293-294]
+//
+// InteropType -> target || targetsync // since 5.2
+// There can be at most only two interop-type.
+struct OmpInteropType {
+ ENUM_CLASS(Value, Target, TargetSync)
+ WRAPPER_CLASS_BOILERPLATE(OmpInteropType, Value);
+};
+
// Ref: [5.0:47-49], [5.1:49-51], [5.2:67-69]
//
// iterator-modifier ->
@@ -4486,6 +4513,25 @@ struct OmpWhenClause {
t;
};
+// REF: [5.1:217-220], [5.2:293-294]
+//
+// init-clause -> INIT ([interop-modifier,] [interop-type,]
+// interop-type: interop-var)
+// interop-modifier: prefer_type(preference-list)
+// interop-type: target, targetsync
+// interop-var: Ompobject
+// There can be at most only two interop-type.
+struct OmpInitClause {
+ TUPLE_CLASS_BOILERPLATE(OmpInitClause);
+ MODIFIER_BOILERPLATE(OmpInteropPreference, OmpInteropType);
+ std::tuple<MODIFIERS(), OmpObject> t;
+};
+
+// REF: [5.1:217-220], [5.2:294]
+//
+// 14.1.3 use-clause -> USE (interop-var)
+WRAPPER_CLASS(OmpUseClause, OmpObject);
+
// OpenMP Clauses
struct OmpClause {
UNION_CLASS_BOILERPLATE(OmpClause);
@@ -4935,6 +4981,15 @@ struct OpenMPFlushConstruct {
CharBlock source;
};
+// Ref: [5.1:217-220], [5.2:291-292]
+//
+// interop -> INTEROP clause[ [ [,] clause]...]
+struct OpenMPInteropConstruct {
+ TUPLE_CLASS_BOILERPLATE(OpenMPInteropConstruct);
+ CharBlock source;
+ std::tuple<Verbatim, OmpClauseList> t;
+};
+
struct OpenMPSimpleStandaloneConstruct {
WRAPPER_CLASS_BOILERPLATE(
OpenMPSimpleStandaloneConstruct, OmpDirectiveSpecification);
@@ -4946,7 +5001,7 @@ struct OpenMPStandaloneConstruct {
CharBlock source;
std::variant<OpenMPSimpleStandaloneConstruct, OpenMPFlushConstruct,
OpenMPCancelConstruct, OpenMPCancellationPointConstruct,
- OpenMPDepobjConstruct, OmpMetadirectiveDirective>
+ OpenMPDepobjConstruct, OmpMetadirectiveDirective, OpenMPInteropConstruct>
u;
};
diff --git a/flang/include/flang/Semantics/openmp-modifiers.h b/flang/include/flang/Semantics/openmp-modifiers.h
index 7cdbf65adebe1..4fbd80f989e72 100644
--- a/flang/include/flang/Semantics/openmp-modifiers.h
+++ b/flang/include/flang/Semantics/openmp-modifiers.h
@@ -77,6 +77,8 @@ DECLARE_DESCRIPTOR(parser::OmpDependenceType);
DECLARE_DESCRIPTOR(parser::OmpDeviceModifier);
DECLARE_DESCRIPTOR(parser::OmpDirectiveNameModifier);
DECLARE_DESCRIPTOR(parser::OmpExpectation);
+DECLARE_DESCRIPTOR(parser::OmpInteropPreference);
+DECLARE_DESCRIPTOR(parser::OmpInteropType);
DECLARE_DESCRIPTOR(parser::OmpIterator);
DECLARE_DESCRIPTOR(parser::OmpLastprivateModifier);
DECLARE_DESCRIPTOR(parser::OmpLinearModifier);
diff --git a/flang/lib/Lower/OpenMP/OpenMP.cpp b/flang/lib/Lower/OpenMP/OpenMP.cpp
index b8ef18860e9b4..1304f06ed28cf 100644
--- a/flang/lib/Lower/OpenMP/OpenMP.cpp
+++ b/flang/lib/Lower/OpenMP/OpenMP.cpp
@@ -424,6 +424,9 @@ extractOmpDirective(const parser::OpenMPConstruct &ompConstruct) {
},
[](const parser::OpenMPDepobjConstruct &c) {
return llvm::omp::OMPD_depobj;
+ },
+ [](const parser::OpenMPInteropConstruct &c) {
+ return llvm::omp::OMPD_interop;
}},
c.u);
},
@@ -3363,6 +3366,13 @@ static void genOMP(lower::AbstractConverter &converter, lower::SymMap &symTable,
TODO(converter.getCurrentLocation(), "OpenMPDepobjConstruct");
}
+static void genOMP(lower::AbstractConverter &converter, lower::SymMap &symTable,
+ semantics::SemanticsContext &semaCtx,
+ lower::pft::Evaluation &eval,
+ const parser::OpenMPInteropConstruct &interopConstruct) {
+ TODO(converter.getCurrentLocation(), "OpenMPInteropConstruct");
+}
+
static void
genOMP(lower::AbstractConverter &converter, lower::SymMap &symTable,
semantics::SemanticsContext &semaCtx, lower::pft::Evaluation &eval,
diff --git a/flang/lib/Parser/openmp-parsers.cpp b/flang/lib/Parser/openmp-parsers.cpp
index f76a136655478..601cd72c79bf5 100644
--- a/flang/lib/Parser/openmp-parsers.cpp
+++ b/flang/lib/Parser/openmp-parsers.cpp
@@ -425,6 +425,17 @@ TYPE_PARSER(construct<OmpDeviceModifier>(
TYPE_PARSER(construct<OmpExpectation>( //
"PRESENT" >> pure(OmpExpectation::Value::Present)))
+TYPE_PARSER(construct<OmpInteropRuntimeIdentifier>(
+ construct<OmpInteropRuntimeIdentifier>(charLiteralConstant) ||
+ construct<OmpInteropRuntimeIdentifier>(scalarIntConstantExpr)))
+
+TYPE_PARSER(construct<OmpInteropPreference>(verbatim("PREFER_TYPE"_tok) >>
+ parenthesized(nonemptyList(Parser<OmpInteropRuntimeIdentifier>{}))))
+
+TYPE_PARSER(construct<OmpInteropType>(
+ "TARGETSYNC" >> pure(OmpInteropType::Value::TargetSync) ||
+ "TARGET" >> pure(OmpInteropType::Value::Target)))
+
TYPE_PARSER(construct<OmpIteratorSpecifier>(
// Using Parser<TypeDeclarationStmt> or Parser<EntityDecl> has the problem
// that they will attempt to treat what follows the '=' as initialization.
@@ -552,6 +563,11 @@ TYPE_PARSER(sourced(
TYPE_PARSER(sourced(construct<OmpIfClause::Modifier>(OmpDirectiveNameParser{})))
+TYPE_PARSER(sourced(
+ construct<OmpInitClause::Modifier>(
+ construct<OmpInitClause::Modifier>(Parser<OmpInteropPreference>{})) ||
+ construct<OmpInitClause::Modifier>(Parser<OmpInteropType>{})))
+
TYPE_PARSER(sourced(construct<OmpInReductionClause::Modifier>(
Parser<OmpReductionIdentifier>{})))
@@ -788,6 +804,11 @@ TYPE_PARSER(
// OpenMPv5.2 12.5.2 detach-clause -> DETACH (event-handle)
TYPE_PARSER(construct<OmpDetachClause>(Parser<OmpObject>{}))
+// init clause
+TYPE_PARSER(construct<OmpInitClause>(
+ maybe(nonemptyList(Parser<OmpInitClause::Modifier>{}) / ":"),
+ Parser<OmpObject>{}))
+
// 2.8.1 ALIGNED (list: alignment)
TYPE_PARSER(construct<OmpAlignedClause>(Parser<OmpObjectList>{},
maybe(":" >> nonemptyList(Parser<OmpAlignedClause::Modifier>{}))))
@@ -927,6 +948,8 @@ TYPE_PARSER( //
"IF" >> construct<OmpClause>(construct<OmpClause::If>(
parenthesized(Parser<OmpIfClause>{}))) ||
"INBRANCH" >> construct<OmpClause>(construct<OmpClause::Inbranch>()) ||
+ "INIT" >> construct<OmpClause>(construct<OmpClause::Init>(
+ parenthesized(Parser<OmpInitClause>{}))) ||
"INCLUSIVE" >> construct<OmpClause>(construct<OmpClause::Inclusive>(
parenthesized(Parser<OmpObjectList>{}))) ||
"INITIALIZER" >> construct<OmpClause>(construct<OmpClause::Initializer>(
@@ -1016,6 +1039,8 @@ TYPE_PARSER( //
parenthesized(scalarIntExpr))) ||
"TO" >> construct<OmpClause>(construct<OmpClause::To>(
parenthesized(Parser<OmpToClause>{}))) ||
+ "USE" >> construct<OmpClause>(construct<OmpClause::Use>(
+ parenthesized(Parser<OmpObject>{}))) ||
"USE_DEVICE_PTR" >> construct<OmpClause>(construct<OmpClause::UseDevicePtr>(
parenthesized(Parser<OmpObjectList>{}))) ||
"USE_DEVICE_ADDR" >>
@@ -1251,6 +1276,10 @@ TYPE_PARSER(sourced( //
IsDirective(llvm::omp::Directive::OMPD_depobj)) >=
Parser<OmpDirectiveSpecification>{})))
+// OMP 5.2 14.1 Interop construct
+TYPE_PARSER(sourced(construct<OpenMPInteropConstruct>(
+ verbatim("INTEROP"_tok), sourced(Parser<OmpClauseList>{}))))
+
// Standalone Constructs
TYPE_PARSER(
sourced( //
@@ -1263,7 +1292,9 @@ TYPE_PARSER(
construct<OpenMPStandaloneConstruct>(Parser<OpenMPCancelConstruct>{}) ||
construct<OpenMPStandaloneConstruct>(
Parser<OmpMetadirectiveDirective>{}) ||
- construct<OpenMPStandaloneConstruct>(Parser<OpenMPDepobjConstruct>{})) /
+ construct<OpenMPStandaloneConstruct>(Parser<OpenMPDepobjConstruct>{}) ||
+ construct<OpenMPStandaloneConstruct>(
+ Parser<OpenMPInteropConstruct>{})) /
endOfLine)
// Directives enclosing structured-block
diff --git a/flang/lib/Parser/unparse.cpp b/flang/lib/Parser/unparse.cpp
index 8cdbf8ed2a672..1674c45ac3096 100644
--- a/flang/lib/Parser/unparse.cpp
+++ b/flang/lib/Parser/unparse.cpp
@@ -2180,6 +2180,30 @@ class UnparseVisitor {
Walk(std::get<std::optional<std::list<Modifier>>>(x.t), ": ");
Walk(std::get<OmpObjectList>(x.t));
}
+ void Unparse(const OmpInteropPreference &x) { Walk(x.v, ","); }
+ void Unparse(const OmpInitClause &x) {
+ using Modifier = OmpInitClause::Modifier;
+ auto &modifiers{std::get<std::optional<std::list<Modifier>>>(x.t)};
+ bool isTypeStart{true};
+ for (const Modifier &m : *modifiers) {
+ if (auto *interopPreferenceMod{
+ std::get_if<parser::OmpInteropPreference>(&m.u)}) {
+ Put("PREFER_TYPE(");
+ Walk(*interopPreferenceMod);
+ Put("),");
+ } else if (auto *interopTypeMod{
+ std::get_if<parser::OmpInteropType>(&m.u)}) {
+ if (isTypeStart) {
+ isTypeStart = false;
+ } else {
+ Put(",");
+ }
+ Walk(*interopTypeMod);
+ }
+ }
+ Put(": ");
+ Walk(std::get<OmpObject>(x.t));
+ }
void Unparse(const OmpMapClause &x) {
using Modifier = OmpMapClause::Modifier;
Walk(std::get<std::optional<std::list<Modifier>>>(x.t), ": ");
@@ -2710,6 +2734,15 @@ class UnparseVisitor {
Put("\n");
EndOpenMP();
}
+
+ void Unparse(const OpenMPInteropConstruct &x) {
+ BeginOpenMP();
+ Word("!$OMP INTEROP");
+ Walk(std::get<OmpClauseList>(x.t));
+ Put("\n");
+ EndOpenMP();
+ }
+
void Unparse(const OpenMPDeclarativeAssumes &x) {
BeginOpenMP();
Word("!$OMP ASSUMES ");
@@ -3004,6 +3037,7 @@ 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(OmpInteropType, Value) // OMP InteropType
WALK_NESTED_ENUM(OmpOrderClause, Ordering) // OMP ordering
WALK_NESTED_ENUM(OmpOrderModifier, Value) // OMP order-modifier
WALK_NESTED_ENUM(OmpPrescriptiveness, Value) // OMP prescriptiveness
diff --git a/flang/lib/Semantics/check-omp-structure.cpp b/flang/lib/Semantics/check-omp-structure.cpp
index 6bddd629d607e..1e2ae6300114c 100644
--- a/flang/lib/Semantics/check-omp-structure.cpp
+++ b/flang/lib/Semantics/check-omp-structure.cpp
@@ -5720,6 +5720,88 @@ void OmpStructureChecker::Leave(const parser::DoConstruct &x) {
Base::Leave(x);
}
+void OmpStructureChecker::Enter(const parser::OpenMPInteropConstruct &x) {
+ bool isDependClauseOccured{false};
+ int targetCount{0}, targetSyncCount{0};
+ const auto &dir{std::get<parser::Verbatim>(x.t)};
+ std::set<const Symbol *> objectSymbolList;
+ PushContextAndClauseSets(dir.source, llvm::omp::Directive::OMPD_interop);
+ const auto &clauseList{std::get<parser::OmpClauseList>(x.t)};
+ for (const auto &clause : clauseList.v) {
+ common::visit(
+ common::visitors{
+ [&](const parser::OmpClause::Init &initClause) {
+ if (OmpVerifyModifiers(initClause.v, llvm::omp::OMPC_init,
+ GetContext().directiveSource, context_)) {
+
+ auto &modifiers{OmpGetModifiers(initClause.v)};
+ auto &&interopTypeModifier{
+ OmpGetRepeatableModifier<parser::OmpInteropType>(
+ modifiers)};
+ for (const auto &it : interopTypeModifier) {
+ if (it->v == parser::OmpInteropType::Value::TargetSync) {
+ ++targetSyncCount;
+ } else {
+ ++targetCount;
+ }
+ }
+ }
+ const auto &interopVar{parser::Unwrap<parser::OmpObject>(
+ std::get<parser::OmpObject>(initClause.v.t))};
+ const auto *name{parser::Unwrap<parser::Name>(interopVar)};
+ const auto *objectSymbol{name->symbol};
+ if (llvm::is_contained(objectSymbolList, objectSymbol)) {
+ context_.Say(GetContext().directiveSource,
+ "Each interop-var may be specified for at most one action-clause of each INTEROP construct."_err_en_US);
+ } else {
+ objectSymbolList.insert(objectSymbol);
+ }
+ },
+ [&](const parser::OmpClause::Depend &dependClause) {
+ isDependClauseOccured = true;
+ },
+ [&](const parser::OmpClause::Destroy &destroyClause) {
+ const auto &interopVar{
+ parser::Unwrap<parser::OmpObject>(destroyClause.v)};
+ const auto *name{parser::Unwrap<parser::Name>(interopVar)};
+ const auto *objectSymbol{name->symbol};
+ if (llvm::is_contained(objectSymbolList, objectSymbol)) {
+ context_.Say(GetContext().directiveSource,
+ "Each interop-var may be specified for at most one action-clause of each INTEROP construct."_err_en_US);
+ } else {
+ objectSymbolList.insert(objectSymbol);
+ }
+ },
+ [&](const parser::OmpClause::Use &useClause) {
+ const auto &interopVar{
+ parser::Unwrap<parser::OmpObject>(useClause.v)};
+ const auto *name{parser::Unwrap<parser::Name>(interopVar)};
+ const auto *objectSymbol{name->symbol};
+ if (llvm::is_contained(objectSymbolList, objectSymbol)) {
+ context_.Say(GetContext().directiveSource,
+ "Each interop-var may be specified for at most one action-clause of each INTEROP construct."_err_en_US);
+ } else {
+ objectSymbolList.insert(objectSymbol);
+ }
+ },
+ [&](const auto &) {},
+ },
+ clause.u);
+ }
+ if (targetCount > 1 || targetSyncCount > 1) {
+ context_.Say(GetContext().directiveSource,
+ "Each interop-type may be specified at most once."_err_en_US);
+ }
+ if (isDependClauseOccured && !targetSyncCount) {
+ context_.Say(GetContext().directiveSource,
+ "A DEPEND clause can only appear on the directive if the interop-type includes TARGETSYNC"_err_en_US);
+ }
+}
+
+void OmpStructureChecker::Leave(const parser::OpenMPInteropConstruct &) {
+ dirContext_.pop_back();
+}
+
void OmpStructureChecker::CheckAllowedRequiresClause(llvmOmpClause clause) {
CheckAllowedClause(clause);
diff --git a/flang/lib/Semantics/check-omp-structure.h b/flang/lib/Semantics/check-omp-structure.h
index d802afeefe72f..a8869561cf5ea 100644
--- a/flang/lib/Semantics/check-omp-structure.h
+++ b/flang/lib/Semantics/check-omp-structure.h
@@ -73,6 +73,8 @@ class OmpStructureChecker
void Enter(const parser::OpenMPConstruct &);
void Leave(const parser::OpenMPConstruct &);
+ void Enter(const parser::OpenMPInteropConstruct &);
+ void Leave(const parser::OpenMPInteropConstruct &);
void Enter(const parser::OpenMPDeclarativeConstruct &);
void Leave(const parser::OpenMPDeclarativeConstruct &);
diff --git a/flang/lib/Semantics/openmp-modifiers.cpp b/flang/lib/Semantics/openmp-modifiers.cpp
index 73ad7751ee517..c84e832ee52a1 100644
--- a/flang/lib/Semantics/openmp-modifiers.cpp
+++ b/flang/lib/Semantics/openmp-modifiers.cpp
@@ -240,6 +240,38 @@ const OmpModifierDescriptor &OmpGetDescriptor<parser::OmpExpectation>() {
return desc;
}
+template <>
+const OmpModifierDescriptor &OmpGetDescriptor<parser::OmpInteropPreference>() {
+ static const OmpModifierDescriptor desc{
+ /*name=*/"interop-preference",
+ /*props=*/
+ {
+ {52, {OmpProperty::Unique}},
+ },
+ /*clauses=*/
+ {
+ {52, {Clause::OMPC_init}},
+ },
+ };
+ return desc;
+}
+
+template <>
+const OmpModifierDescriptor &OmpGetDescriptor<parser::OmpInteropType>() {
+ static const OmpModifierDescriptor desc{
+ /*name=*/"interop-type",
+ /*props=*/
+ {
+ {52, {OmpProperty::Required}},
+ },
+ /*clauses=*/
+ {
+ {52, {Clause::OMPC_init}},
+ },
+ };
+ return desc;
+}
+
template <>
const OmpModifierDescriptor &OmpGetDescriptor<parser::OmpIterator>() {
static const OmpModifierDescriptor desc{
diff --git a/flang/test/Lower/OpenMP/Todo/inteorp-construct.f90 b/flang/test/Lower/OpenMP/Todo/inteorp-construct.f90
new file mode 100644
index 0000000000000..f7920c09464ed
--- /dev/null
+++ b/flang/test/Lower/OpenMP/Todo/inteorp-construct.f90
@@ -0,0 +1,9 @@
+! REQUIRES: openmp_runtime
+! RUN: %not_todo_cmd %flang_fc1 -emit-fir -fopenmp -fopenmp-version=52 -o - %s 2>&1 | FileCheck %s
+
+! CHECK: not yet implemented: OpenMPInteropConstruct
+program interop_test
+ use omp_lib
+ integer(omp_interop_kind) :: obj
+ !$omp interop init(targetsync,target: obj)
+end program interop_test
diff --git a/flang/test/Parser/OpenMP/interop-construct.f90 b/flang/test/Parser/OpenMP/interop-construct.f90
new file mode 100644
index 0000000000000..a1781d559b46d
--- /dev/null
+++ b/flang/test/Parser/OpenMP/interop-construct.f90
@@ -0,0 +1,204 @@
+! REQUIRES: openmp_runtime
+! RUN: %flang_fc1 -fdebug-unparse -fopenmp-version...
[truncated]
|
@llvm/pr-subscribers-flang-openmp Author: None (swatheesh-mcw) ChangesReverts llvm/llvm-project#132005 Patch is 32.21 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/132343.diff 14 Files Affected:
diff --git a/flang/examples/FeatureList/FeatureList.cpp b/flang/examples/FeatureList/FeatureList.cpp
index 25485bbb8ff4d..94fdfa3e4dea9 100644
--- a/flang/examples/FeatureList/FeatureList.cpp
+++ b/flang/examples/FeatureList/FeatureList.cpp
@@ -522,6 +522,13 @@ struct NodeVisitor {
READ_FEATURE(OmpScheduleClause)
READ_FEATURE(OmpScheduleClause::Kind)
READ_FEATURE(OmpScheduleClause::Modifier)
+ READ_FEATURE(OmpInteropRuntimeIdentifier)
+ READ_FEATURE(OmpInteropPreference)
+ READ_FEATURE(OmpInteropType)
+ READ_FEATURE(OmpInteropType::Value)
+ READ_FEATURE(OmpInitClause)
+ READ_FEATURE(OmpInitClause::Modifier)
+ READ_FEATURE(OmpUseClause)
READ_FEATURE(OmpDeviceModifier)
READ_FEATURE(OmpDeviceClause)
READ_FEATURE(OmpDeviceClause::Modifier)
@@ -541,6 +548,7 @@ struct NodeVisitor {
READ_FEATURE(OpenACCConstruct)
READ_FEATURE(OpenACCDeclarativeConstruct)
READ_FEATURE(OpenACCLoopConstruct)
+ READ_FEATURE(OpenMPInteropConstruct)
READ_FEATURE(OpenACCRoutineConstruct)
READ_FEATURE(OpenACCStandaloneDeclarativeConstruct)
READ_FEATURE(OpenACCStandaloneConstruct)
diff --git a/flang/include/flang/Parser/dump-parse-tree.h b/flang/include/flang/Parser/dump-parse-tree.h
index 9bff2dab974ec..41ad15794ad15 100644
--- a/flang/include/flang/Parser/dump-parse-tree.h
+++ b/flang/include/flang/Parser/dump-parse-tree.h
@@ -657,6 +657,13 @@ class ParseTreeDumper {
NODE_ENUM(OmpDeviceModifier, Value)
NODE(parser, OmpDeviceTypeClause)
NODE_ENUM(OmpDeviceTypeClause, DeviceTypeDescription)
+ NODE(parser, OmpInteropRuntimeIdentifier)
+ NODE(parser, OmpInteropPreference)
+ NODE(parser, OmpInteropType)
+ NODE_ENUM(OmpInteropType, Value)
+ NODE(parser, OmpInitClause)
+ NODE(OmpInitClause, Modifier)
+ NODE(parser, OmpUseClause)
NODE(parser, OmpUpdateClause)
NODE(parser, OmpChunkModifier)
NODE_ENUM(OmpChunkModifier, Value)
@@ -675,6 +682,7 @@ class ParseTreeDumper {
NODE(parser, OpenACCDeclarativeConstruct)
NODE(parser, OpenACCEndConstruct)
NODE(parser, OpenACCLoopConstruct)
+ NODE(parser, OpenMPInteropConstruct)
NODE(parser, OpenACCRoutineConstruct)
NODE(parser, OpenACCStandaloneDeclarativeConstruct)
NODE(parser, OpenACCStandaloneConstruct)
diff --git a/flang/include/flang/Parser/parse-tree.h b/flang/include/flang/Parser/parse-tree.h
index 029c3de354b66..76cd3380e203c 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -3829,6 +3829,33 @@ struct OmpExpectation {
WRAPPER_CLASS_BOILERPLATE(OmpExpectation, Value);
};
+// REF: [5.1:217-220], [5.2:293-294]
+//
+// OmpInteropRuntimeIdentifier -> // since 5.2
+// CharLiteralConstant || ScalarIntConstantExpr
+struct OmpInteropRuntimeIdentifier {
+ UNION_CLASS_BOILERPLATE(OmpInteropRuntimeIdentifier);
+ std::variant<CharLiteralConstant, ScalarIntConstantExpr> u;
+};
+
+// REF: [5.1:217-220], [5.2:293-294]
+//
+// OmpInteropPreference -> // since 5.2
+// ([OmpRuntimeIdentifier, ...])
+struct OmpInteropPreference {
+ WRAPPER_CLASS_BOILERPLATE(
+ OmpInteropPreference, std::list<OmpInteropRuntimeIdentifier>);
+};
+
+// REF: [5.1:217-220], [5.2:293-294]
+//
+// InteropType -> target || targetsync // since 5.2
+// There can be at most only two interop-type.
+struct OmpInteropType {
+ ENUM_CLASS(Value, Target, TargetSync)
+ WRAPPER_CLASS_BOILERPLATE(OmpInteropType, Value);
+};
+
// Ref: [5.0:47-49], [5.1:49-51], [5.2:67-69]
//
// iterator-modifier ->
@@ -4486,6 +4513,25 @@ struct OmpWhenClause {
t;
};
+// REF: [5.1:217-220], [5.2:293-294]
+//
+// init-clause -> INIT ([interop-modifier,] [interop-type,]
+// interop-type: interop-var)
+// interop-modifier: prefer_type(preference-list)
+// interop-type: target, targetsync
+// interop-var: Ompobject
+// There can be at most only two interop-type.
+struct OmpInitClause {
+ TUPLE_CLASS_BOILERPLATE(OmpInitClause);
+ MODIFIER_BOILERPLATE(OmpInteropPreference, OmpInteropType);
+ std::tuple<MODIFIERS(), OmpObject> t;
+};
+
+// REF: [5.1:217-220], [5.2:294]
+//
+// 14.1.3 use-clause -> USE (interop-var)
+WRAPPER_CLASS(OmpUseClause, OmpObject);
+
// OpenMP Clauses
struct OmpClause {
UNION_CLASS_BOILERPLATE(OmpClause);
@@ -4935,6 +4981,15 @@ struct OpenMPFlushConstruct {
CharBlock source;
};
+// Ref: [5.1:217-220], [5.2:291-292]
+//
+// interop -> INTEROP clause[ [ [,] clause]...]
+struct OpenMPInteropConstruct {
+ TUPLE_CLASS_BOILERPLATE(OpenMPInteropConstruct);
+ CharBlock source;
+ std::tuple<Verbatim, OmpClauseList> t;
+};
+
struct OpenMPSimpleStandaloneConstruct {
WRAPPER_CLASS_BOILERPLATE(
OpenMPSimpleStandaloneConstruct, OmpDirectiveSpecification);
@@ -4946,7 +5001,7 @@ struct OpenMPStandaloneConstruct {
CharBlock source;
std::variant<OpenMPSimpleStandaloneConstruct, OpenMPFlushConstruct,
OpenMPCancelConstruct, OpenMPCancellationPointConstruct,
- OpenMPDepobjConstruct, OmpMetadirectiveDirective>
+ OpenMPDepobjConstruct, OmpMetadirectiveDirective, OpenMPInteropConstruct>
u;
};
diff --git a/flang/include/flang/Semantics/openmp-modifiers.h b/flang/include/flang/Semantics/openmp-modifiers.h
index 7cdbf65adebe1..4fbd80f989e72 100644
--- a/flang/include/flang/Semantics/openmp-modifiers.h
+++ b/flang/include/flang/Semantics/openmp-modifiers.h
@@ -77,6 +77,8 @@ DECLARE_DESCRIPTOR(parser::OmpDependenceType);
DECLARE_DESCRIPTOR(parser::OmpDeviceModifier);
DECLARE_DESCRIPTOR(parser::OmpDirectiveNameModifier);
DECLARE_DESCRIPTOR(parser::OmpExpectation);
+DECLARE_DESCRIPTOR(parser::OmpInteropPreference);
+DECLARE_DESCRIPTOR(parser::OmpInteropType);
DECLARE_DESCRIPTOR(parser::OmpIterator);
DECLARE_DESCRIPTOR(parser::OmpLastprivateModifier);
DECLARE_DESCRIPTOR(parser::OmpLinearModifier);
diff --git a/flang/lib/Lower/OpenMP/OpenMP.cpp b/flang/lib/Lower/OpenMP/OpenMP.cpp
index b8ef18860e9b4..1304f06ed28cf 100644
--- a/flang/lib/Lower/OpenMP/OpenMP.cpp
+++ b/flang/lib/Lower/OpenMP/OpenMP.cpp
@@ -424,6 +424,9 @@ extractOmpDirective(const parser::OpenMPConstruct &ompConstruct) {
},
[](const parser::OpenMPDepobjConstruct &c) {
return llvm::omp::OMPD_depobj;
+ },
+ [](const parser::OpenMPInteropConstruct &c) {
+ return llvm::omp::OMPD_interop;
}},
c.u);
},
@@ -3363,6 +3366,13 @@ static void genOMP(lower::AbstractConverter &converter, lower::SymMap &symTable,
TODO(converter.getCurrentLocation(), "OpenMPDepobjConstruct");
}
+static void genOMP(lower::AbstractConverter &converter, lower::SymMap &symTable,
+ semantics::SemanticsContext &semaCtx,
+ lower::pft::Evaluation &eval,
+ const parser::OpenMPInteropConstruct &interopConstruct) {
+ TODO(converter.getCurrentLocation(), "OpenMPInteropConstruct");
+}
+
static void
genOMP(lower::AbstractConverter &converter, lower::SymMap &symTable,
semantics::SemanticsContext &semaCtx, lower::pft::Evaluation &eval,
diff --git a/flang/lib/Parser/openmp-parsers.cpp b/flang/lib/Parser/openmp-parsers.cpp
index f76a136655478..601cd72c79bf5 100644
--- a/flang/lib/Parser/openmp-parsers.cpp
+++ b/flang/lib/Parser/openmp-parsers.cpp
@@ -425,6 +425,17 @@ TYPE_PARSER(construct<OmpDeviceModifier>(
TYPE_PARSER(construct<OmpExpectation>( //
"PRESENT" >> pure(OmpExpectation::Value::Present)))
+TYPE_PARSER(construct<OmpInteropRuntimeIdentifier>(
+ construct<OmpInteropRuntimeIdentifier>(charLiteralConstant) ||
+ construct<OmpInteropRuntimeIdentifier>(scalarIntConstantExpr)))
+
+TYPE_PARSER(construct<OmpInteropPreference>(verbatim("PREFER_TYPE"_tok) >>
+ parenthesized(nonemptyList(Parser<OmpInteropRuntimeIdentifier>{}))))
+
+TYPE_PARSER(construct<OmpInteropType>(
+ "TARGETSYNC" >> pure(OmpInteropType::Value::TargetSync) ||
+ "TARGET" >> pure(OmpInteropType::Value::Target)))
+
TYPE_PARSER(construct<OmpIteratorSpecifier>(
// Using Parser<TypeDeclarationStmt> or Parser<EntityDecl> has the problem
// that they will attempt to treat what follows the '=' as initialization.
@@ -552,6 +563,11 @@ TYPE_PARSER(sourced(
TYPE_PARSER(sourced(construct<OmpIfClause::Modifier>(OmpDirectiveNameParser{})))
+TYPE_PARSER(sourced(
+ construct<OmpInitClause::Modifier>(
+ construct<OmpInitClause::Modifier>(Parser<OmpInteropPreference>{})) ||
+ construct<OmpInitClause::Modifier>(Parser<OmpInteropType>{})))
+
TYPE_PARSER(sourced(construct<OmpInReductionClause::Modifier>(
Parser<OmpReductionIdentifier>{})))
@@ -788,6 +804,11 @@ TYPE_PARSER(
// OpenMPv5.2 12.5.2 detach-clause -> DETACH (event-handle)
TYPE_PARSER(construct<OmpDetachClause>(Parser<OmpObject>{}))
+// init clause
+TYPE_PARSER(construct<OmpInitClause>(
+ maybe(nonemptyList(Parser<OmpInitClause::Modifier>{}) / ":"),
+ Parser<OmpObject>{}))
+
// 2.8.1 ALIGNED (list: alignment)
TYPE_PARSER(construct<OmpAlignedClause>(Parser<OmpObjectList>{},
maybe(":" >> nonemptyList(Parser<OmpAlignedClause::Modifier>{}))))
@@ -927,6 +948,8 @@ TYPE_PARSER( //
"IF" >> construct<OmpClause>(construct<OmpClause::If>(
parenthesized(Parser<OmpIfClause>{}))) ||
"INBRANCH" >> construct<OmpClause>(construct<OmpClause::Inbranch>()) ||
+ "INIT" >> construct<OmpClause>(construct<OmpClause::Init>(
+ parenthesized(Parser<OmpInitClause>{}))) ||
"INCLUSIVE" >> construct<OmpClause>(construct<OmpClause::Inclusive>(
parenthesized(Parser<OmpObjectList>{}))) ||
"INITIALIZER" >> construct<OmpClause>(construct<OmpClause::Initializer>(
@@ -1016,6 +1039,8 @@ TYPE_PARSER( //
parenthesized(scalarIntExpr))) ||
"TO" >> construct<OmpClause>(construct<OmpClause::To>(
parenthesized(Parser<OmpToClause>{}))) ||
+ "USE" >> construct<OmpClause>(construct<OmpClause::Use>(
+ parenthesized(Parser<OmpObject>{}))) ||
"USE_DEVICE_PTR" >> construct<OmpClause>(construct<OmpClause::UseDevicePtr>(
parenthesized(Parser<OmpObjectList>{}))) ||
"USE_DEVICE_ADDR" >>
@@ -1251,6 +1276,10 @@ TYPE_PARSER(sourced( //
IsDirective(llvm::omp::Directive::OMPD_depobj)) >=
Parser<OmpDirectiveSpecification>{})))
+// OMP 5.2 14.1 Interop construct
+TYPE_PARSER(sourced(construct<OpenMPInteropConstruct>(
+ verbatim("INTEROP"_tok), sourced(Parser<OmpClauseList>{}))))
+
// Standalone Constructs
TYPE_PARSER(
sourced( //
@@ -1263,7 +1292,9 @@ TYPE_PARSER(
construct<OpenMPStandaloneConstruct>(Parser<OpenMPCancelConstruct>{}) ||
construct<OpenMPStandaloneConstruct>(
Parser<OmpMetadirectiveDirective>{}) ||
- construct<OpenMPStandaloneConstruct>(Parser<OpenMPDepobjConstruct>{})) /
+ construct<OpenMPStandaloneConstruct>(Parser<OpenMPDepobjConstruct>{}) ||
+ construct<OpenMPStandaloneConstruct>(
+ Parser<OpenMPInteropConstruct>{})) /
endOfLine)
// Directives enclosing structured-block
diff --git a/flang/lib/Parser/unparse.cpp b/flang/lib/Parser/unparse.cpp
index 8cdbf8ed2a672..1674c45ac3096 100644
--- a/flang/lib/Parser/unparse.cpp
+++ b/flang/lib/Parser/unparse.cpp
@@ -2180,6 +2180,30 @@ class UnparseVisitor {
Walk(std::get<std::optional<std::list<Modifier>>>(x.t), ": ");
Walk(std::get<OmpObjectList>(x.t));
}
+ void Unparse(const OmpInteropPreference &x) { Walk(x.v, ","); }
+ void Unparse(const OmpInitClause &x) {
+ using Modifier = OmpInitClause::Modifier;
+ auto &modifiers{std::get<std::optional<std::list<Modifier>>>(x.t)};
+ bool isTypeStart{true};
+ for (const Modifier &m : *modifiers) {
+ if (auto *interopPreferenceMod{
+ std::get_if<parser::OmpInteropPreference>(&m.u)}) {
+ Put("PREFER_TYPE(");
+ Walk(*interopPreferenceMod);
+ Put("),");
+ } else if (auto *interopTypeMod{
+ std::get_if<parser::OmpInteropType>(&m.u)}) {
+ if (isTypeStart) {
+ isTypeStart = false;
+ } else {
+ Put(",");
+ }
+ Walk(*interopTypeMod);
+ }
+ }
+ Put(": ");
+ Walk(std::get<OmpObject>(x.t));
+ }
void Unparse(const OmpMapClause &x) {
using Modifier = OmpMapClause::Modifier;
Walk(std::get<std::optional<std::list<Modifier>>>(x.t), ": ");
@@ -2710,6 +2734,15 @@ class UnparseVisitor {
Put("\n");
EndOpenMP();
}
+
+ void Unparse(const OpenMPInteropConstruct &x) {
+ BeginOpenMP();
+ Word("!$OMP INTEROP");
+ Walk(std::get<OmpClauseList>(x.t));
+ Put("\n");
+ EndOpenMP();
+ }
+
void Unparse(const OpenMPDeclarativeAssumes &x) {
BeginOpenMP();
Word("!$OMP ASSUMES ");
@@ -3004,6 +3037,7 @@ 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(OmpInteropType, Value) // OMP InteropType
WALK_NESTED_ENUM(OmpOrderClause, Ordering) // OMP ordering
WALK_NESTED_ENUM(OmpOrderModifier, Value) // OMP order-modifier
WALK_NESTED_ENUM(OmpPrescriptiveness, Value) // OMP prescriptiveness
diff --git a/flang/lib/Semantics/check-omp-structure.cpp b/flang/lib/Semantics/check-omp-structure.cpp
index 6bddd629d607e..1e2ae6300114c 100644
--- a/flang/lib/Semantics/check-omp-structure.cpp
+++ b/flang/lib/Semantics/check-omp-structure.cpp
@@ -5720,6 +5720,88 @@ void OmpStructureChecker::Leave(const parser::DoConstruct &x) {
Base::Leave(x);
}
+void OmpStructureChecker::Enter(const parser::OpenMPInteropConstruct &x) {
+ bool isDependClauseOccured{false};
+ int targetCount{0}, targetSyncCount{0};
+ const auto &dir{std::get<parser::Verbatim>(x.t)};
+ std::set<const Symbol *> objectSymbolList;
+ PushContextAndClauseSets(dir.source, llvm::omp::Directive::OMPD_interop);
+ const auto &clauseList{std::get<parser::OmpClauseList>(x.t)};
+ for (const auto &clause : clauseList.v) {
+ common::visit(
+ common::visitors{
+ [&](const parser::OmpClause::Init &initClause) {
+ if (OmpVerifyModifiers(initClause.v, llvm::omp::OMPC_init,
+ GetContext().directiveSource, context_)) {
+
+ auto &modifiers{OmpGetModifiers(initClause.v)};
+ auto &&interopTypeModifier{
+ OmpGetRepeatableModifier<parser::OmpInteropType>(
+ modifiers)};
+ for (const auto &it : interopTypeModifier) {
+ if (it->v == parser::OmpInteropType::Value::TargetSync) {
+ ++targetSyncCount;
+ } else {
+ ++targetCount;
+ }
+ }
+ }
+ const auto &interopVar{parser::Unwrap<parser::OmpObject>(
+ std::get<parser::OmpObject>(initClause.v.t))};
+ const auto *name{parser::Unwrap<parser::Name>(interopVar)};
+ const auto *objectSymbol{name->symbol};
+ if (llvm::is_contained(objectSymbolList, objectSymbol)) {
+ context_.Say(GetContext().directiveSource,
+ "Each interop-var may be specified for at most one action-clause of each INTEROP construct."_err_en_US);
+ } else {
+ objectSymbolList.insert(objectSymbol);
+ }
+ },
+ [&](const parser::OmpClause::Depend &dependClause) {
+ isDependClauseOccured = true;
+ },
+ [&](const parser::OmpClause::Destroy &destroyClause) {
+ const auto &interopVar{
+ parser::Unwrap<parser::OmpObject>(destroyClause.v)};
+ const auto *name{parser::Unwrap<parser::Name>(interopVar)};
+ const auto *objectSymbol{name->symbol};
+ if (llvm::is_contained(objectSymbolList, objectSymbol)) {
+ context_.Say(GetContext().directiveSource,
+ "Each interop-var may be specified for at most one action-clause of each INTEROP construct."_err_en_US);
+ } else {
+ objectSymbolList.insert(objectSymbol);
+ }
+ },
+ [&](const parser::OmpClause::Use &useClause) {
+ const auto &interopVar{
+ parser::Unwrap<parser::OmpObject>(useClause.v)};
+ const auto *name{parser::Unwrap<parser::Name>(interopVar)};
+ const auto *objectSymbol{name->symbol};
+ if (llvm::is_contained(objectSymbolList, objectSymbol)) {
+ context_.Say(GetContext().directiveSource,
+ "Each interop-var may be specified for at most one action-clause of each INTEROP construct."_err_en_US);
+ } else {
+ objectSymbolList.insert(objectSymbol);
+ }
+ },
+ [&](const auto &) {},
+ },
+ clause.u);
+ }
+ if (targetCount > 1 || targetSyncCount > 1) {
+ context_.Say(GetContext().directiveSource,
+ "Each interop-type may be specified at most once."_err_en_US);
+ }
+ if (isDependClauseOccured && !targetSyncCount) {
+ context_.Say(GetContext().directiveSource,
+ "A DEPEND clause can only appear on the directive if the interop-type includes TARGETSYNC"_err_en_US);
+ }
+}
+
+void OmpStructureChecker::Leave(const parser::OpenMPInteropConstruct &) {
+ dirContext_.pop_back();
+}
+
void OmpStructureChecker::CheckAllowedRequiresClause(llvmOmpClause clause) {
CheckAllowedClause(clause);
diff --git a/flang/lib/Semantics/check-omp-structure.h b/flang/lib/Semantics/check-omp-structure.h
index d802afeefe72f..a8869561cf5ea 100644
--- a/flang/lib/Semantics/check-omp-structure.h
+++ b/flang/lib/Semantics/check-omp-structure.h
@@ -73,6 +73,8 @@ class OmpStructureChecker
void Enter(const parser::OpenMPConstruct &);
void Leave(const parser::OpenMPConstruct &);
+ void Enter(const parser::OpenMPInteropConstruct &);
+ void Leave(const parser::OpenMPInteropConstruct &);
void Enter(const parser::OpenMPDeclarativeConstruct &);
void Leave(const parser::OpenMPDeclarativeConstruct &);
diff --git a/flang/lib/Semantics/openmp-modifiers.cpp b/flang/lib/Semantics/openmp-modifiers.cpp
index 73ad7751ee517..c84e832ee52a1 100644
--- a/flang/lib/Semantics/openmp-modifiers.cpp
+++ b/flang/lib/Semantics/openmp-modifiers.cpp
@@ -240,6 +240,38 @@ const OmpModifierDescriptor &OmpGetDescriptor<parser::OmpExpectation>() {
return desc;
}
+template <>
+const OmpModifierDescriptor &OmpGetDescriptor<parser::OmpInteropPreference>() {
+ static const OmpModifierDescriptor desc{
+ /*name=*/"interop-preference",
+ /*props=*/
+ {
+ {52, {OmpProperty::Unique}},
+ },
+ /*clauses=*/
+ {
+ {52, {Clause::OMPC_init}},
+ },
+ };
+ return desc;
+}
+
+template <>
+const OmpModifierDescriptor &OmpGetDescriptor<parser::OmpInteropType>() {
+ static const OmpModifierDescriptor desc{
+ /*name=*/"interop-type",
+ /*props=*/
+ {
+ {52, {OmpProperty::Required}},
+ },
+ /*clauses=*/
+ {
+ {52, {Clause::OMPC_init}},
+ },
+ };
+ return desc;
+}
+
template <>
const OmpModifierDescriptor &OmpGetDescriptor<parser::OmpIterator>() {
static const OmpModifierDescriptor desc{
diff --git a/flang/test/Lower/OpenMP/Todo/inteorp-construct.f90 b/flang/test/Lower/OpenMP/Todo/inteorp-construct.f90
new file mode 100644
index 0000000000000..f7920c09464ed
--- /dev/null
+++ b/flang/test/Lower/OpenMP/Todo/inteorp-construct.f90
@@ -0,0 +1,9 @@
+! REQUIRES: openmp_runtime
+! RUN: %not_todo_cmd %flang_fc1 -emit-fir -fopenmp -fopenmp-version=52 -o - %s 2>&1 | FileCheck %s
+
+! CHECK: not yet implemented: OpenMPInteropConstruct
+program interop_test
+ use omp_lib
+ integer(omp_interop_kind) :: obj
+ !$omp interop init(targetsync,target: obj)
+end program interop_test
diff --git a/flang/test/Parser/OpenMP/interop-construct.f90 b/flang/test/Parser/OpenMP/interop-construct.f90
new file mode 100644
index 0000000000000..a1781d559b46d
--- /dev/null
+++ b/flang/test/Parser/OpenMP/interop-construct.f90
@@ -0,0 +1,204 @@
+! REQUIRES: openmp_runtime
+! RUN: %flang_fc1 -fdebug-unparse -fopenmp-version...
[truncated]
|
@swatheesh-mcw Can you reproduce the CI failure locally? Can you have a look to find out why the CI is failing? |
Sure @kiranchandramohan! |
Hi @kiranchandramohan, the build is working fine locally. I don't see any failures. But checking the logs with the CI, I could see the following:
|
Thanks. Hope you can fix the issue in FlangOmpReportVisitor.cpp. |
The examples can be built even without that flag, but you need to specify the targets manually, i.e.
|
aaaf865
to
8efec33
Compare
Hi @kiranchandramohan, I have refactored the code and modified the test case. Please let me know if any changes are required. Thanks! |
Have you added
|
I have added
Thanks! |
|
Great! I will add the flag then. Thanks! |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LG. Thanks for the updates.
Reverts #132005