-
Notifications
You must be signed in to change notification settings - Fork 14.4k
[flang][OpenMP]Add symbls omp_in, omp_out and omp_priv in DECLARE RED… #129908
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
Changes from 1 commit
eaff8c5
df74037
2708306
05c5f83
1c8e0b9
f83bcd8
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -2705,11 +2705,14 @@ class UnparseVisitor { | |
Walk(std::get<std::list<ActualArgSpec>>(x.t)); | ||
Put(")"); | ||
} | ||
void Unparse(const OmpInitializerExpr &x) { | ||
Word("OMP_PRIV = "); | ||
Walk(x.v); | ||
void Unparse(const OmpInitializerClause &x) { | ||
// Don't let the visitor go to the normal AssignmentStmt Unparse function, | ||
// it adds an extra newline that we don't want. | ||
if (const auto *assignment = std::get_if<AssignmentStmt>(&x.u)) | ||
Walk(assignment->t, "="); | ||
else | ||
Walk(x.u); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The convention in Parser is to use braces even with single statements. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Done |
||
} | ||
void Unparse(const OmpInitializerClause &x) { Walk(x.u); } | ||
void Unparse(const OpenMPDeclareReductionConstruct &x) { | ||
BeginOpenMP(); | ||
Word("!$OMP DECLARE REDUCTION "); | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -1656,6 +1656,7 @@ class OmpVisitor : public virtual DeclarationVisitor { | |
const parser::OmpClauseList &clauses); | ||
void ProcessReductionSpecifier(const parser::OmpReductionSpecifier &spec, | ||
const std::optional<parser::OmpClauseList> &clauses); | ||
void CreateTempSymbol(const parser::CharBlock &name, const DeclTypeSpec &dts); | ||
}; | ||
|
||
bool OmpVisitor::NeedsScope(const parser::OpenMPBlockConstruct &x) { | ||
|
@@ -1748,6 +1749,14 @@ void OmpVisitor::ProcessMapperSpecifier(const parser::OmpMapperSpecifier &spec, | |
PopScope(); | ||
} | ||
|
||
void OmpVisitor::CreateTempSymbol( | ||
kiranchandramohan marked this conversation as resolved.
Show resolved
Hide resolved
|
||
const parser::CharBlock &name, const DeclTypeSpec &dts) { | ||
ObjectEntityDetails details; | ||
kiranchandramohan marked this conversation as resolved.
Show resolved
Hide resolved
|
||
details.set_type(dts); | ||
|
||
MakeSymbol(name, Attrs{}, std::move(details)); | ||
} | ||
|
||
void OmpVisitor::ProcessReductionSpecifier( | ||
const parser::OmpReductionSpecifier &spec, | ||
const std::optional<parser::OmpClauseList> &clauses) { | ||
|
@@ -1761,11 +1770,26 @@ void OmpVisitor::ProcessReductionSpecifier( | |
// Creating a new scope in case the combiner expression (or clauses) use | ||
// reerved identifiers, like "omp_in". This is a temporary solution until | ||
// we deal with these in a more thorough way. | ||
PushScope(Scope::Kind::OtherConstruct, nullptr); | ||
Walk(std::get<parser::OmpTypeNameList>(spec.t)); | ||
Walk(std::get<std::optional<parser::OmpReductionCombiner>>(spec.t)); | ||
Walk(clauses); | ||
PopScope(); | ||
auto &typeList = std::get<parser::OmpTypeNameList>(spec.t); | ||
kiranchandramohan marked this conversation as resolved.
Show resolved
Hide resolved
|
||
for (auto &t : typeList.v) { | ||
PushScope(Scope::Kind::OtherConstruct, nullptr); | ||
BeginDeclTypeSpec(); | ||
// We need to walk t.u because Walk(t) does it's own BeginDeclTypeSpec. | ||
Walk(t.u); | ||
|
||
auto *typeSpec = GetDeclTypeSpec(); | ||
kiranchandramohan marked this conversation as resolved.
Show resolved
Hide resolved
|
||
assert(typeSpec && "We should have a type here"); | ||
const parser::CharBlock ompVarNames[] = { | ||
{"omp_in", 6}, {"omp_out", 7}, {"omp_priv", 8}}; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Are these always present? Are they not bound to any names? Braced init if possible. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. As I understand it, these are the names that need to be present with the correct type for the reduction combiner and initializesr. The code here is to introduce Changed to braced initializer. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. But the initializer clause itself is optional, so There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. We could add that code into the I guess to avoid generating a symbol that isn'g used, we could check if there is an initializer (relatively easy in terms of code, as there is only one valid clause allowed here, so it's either an initializer clause or the clauselist is empty. It does add a bit more complication to this code, and I'm not sure it's worth the extra complexity to avoid generating the Is the concern here that these symbols will somehow cause a problem elsewhere? Or simply that we shouldn't do things that aren't required in general. They are in a local scope, so won't be visible outside of the declaration of the reduction. [In theory, the There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think it will be good to comment on what you are trying to do here. Are you trying to create as many sets of symbols as there are in the typeList? And you chose to do it here because this is where the typeList is processed? Also, if these symbols are not tied to names, what is the use of these symbols? It will be good to not generate symbols that are not required. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. There is one test, flang/test/Parser/OpenMP/metadirective-dirspec.f90 that has multiple types, I have some more comprehensive tests when more functionality has been implemented (being worked on now)
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @Leporacanthicus I am not following you here. Could you reply to my following questions?
Are you ignoring the case of There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. They are bound to something because otherwise we'd get an assertion that not all names have been resolved. If I was to guess, I'd say that they are most likely declared implicitly. I assumed that since this patch worked, having symbols with the same name but different types was valid. I think we could declare them once with whatever type (integer for example) and avoid using core Fortran parse tree nodes to store the initialization/update that could trigger semantic errors (such as AssignmentStmt). The types of these symbols would then become irrelevant, but we'd have to type-check the update expression ourselves. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Completely missed that one. Partly because there's no test at all for that name... Is it ok to add a separate patch for that, or do you want me to add this on this patch? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Well, I pushed a patch to fix it. There's still no test other than the one checking generated symbols. I will add one or two that uses |
||
|
||
for (auto &nm : ompVarNames) { | ||
CreateTempSymbol(nm, *typeSpec); | ||
kiranchandramohan marked this conversation as resolved.
Show resolved
Hide resolved
|
||
} | ||
EndDeclTypeSpec(); | ||
Walk(std::get<std::optional<parser::OmpReductionCombiner>>(spec.t)); | ||
Walk(clauses); | ||
PopScope(); | ||
} | ||
} | ||
|
||
bool OmpVisitor::Pre(const parser::OmpDirectiveSpecification &x) { | ||
|
Uh oh!
There was an error while loading. Please reload this page.