[flang] [OpenMP] Add structural checks for `TASK`

1. fix `OmpIfClause` on `Task`
2. add structural checks

Original-commit: flang-compiler/f18@a77830a191
This commit is contained in:
Jinxin Yang 2019-09-04 23:35:44 -07:00 committed by Jinxin (Brian) Yang
parent 77ed1df8a7
commit c4fa8b867e
3 changed files with 52 additions and 5 deletions

View File

@ -107,8 +107,8 @@ TYPE_PARSER(construct<OmpIfClause>(
"TARGET UPDATE" >>
pure(OmpIfClause::DirectiveNameModifier::TargetUpdate) ||
"TARGET" >> pure(OmpIfClause::DirectiveNameModifier::Target) ||
"TASK"_id >> pure(OmpIfClause::DirectiveNameModifier::Taskloop) ||
"TASKLOOP" >> pure(OmpIfClause::DirectiveNameModifier::Task)) /
"TASK"_id >> pure(OmpIfClause::DirectiveNameModifier::Task) ||
"TASKLOOP" >> pure(OmpIfClause::DirectiveNameModifier::Taskloop)) /
":"),
scalarLogicalExpr))

View File

@ -97,7 +97,8 @@ void OmpStructureChecker::CheckAllowed(OmpClause type) {
});
for (const auto &e : others) {
context_.Say(GetContext().clauseSource,
"%s and %s are mutually exclusive and may not appear on the same %s directive"_err_en_US,
"%s and %s are mutually exclusive and may not appear on the "
"same %s directive"_err_en_US,
EnumToString(type), EnumToString(e),
parser::ToUpperCaseLetters(GetContext().directiveSource.ToString()));
}
@ -326,6 +327,26 @@ void OmpStructureChecker::Enter(const parser::OpenMPBlockConstruct &x) {
case parser::OmpBlockDirective::Directive::Workshare:
PushContext(beginDir.source, OmpDirective::WORKSHARE);
break;
// 2.9.1 task-clause -> if-clause |
// final-clause |
// untied-clause |
// default-clause |
// mergeable-clause |
// private-clause |
// firstprivate-clause |
// shared-clause |
// depend-clause |
// priority-clause
case parser::OmpBlockDirective::Directive::Task: {
PushContext(beginDir.source, OmpDirective::TASK);
OmpClauseSet allowed{OmpClause::UNTIED, OmpClause::DEFAULT,
OmpClause::MERGEABLE, OmpClause::PRIVATE, OmpClause::FIRSTPRIVATE,
OmpClause::SHARED, OmpClause::DEPEND};
SetContextAllowed(allowed);
OmpClauseSet allowedOnce{
OmpClause::IF, OmpClause::FINAL, OmpClause::PRIORITY};
SetContextAllowedOnce(allowedOnce);
} break;
default:
// TODO others
break;
@ -695,8 +716,9 @@ void OmpStructureChecker::Enter(const parser::OmpClause::Ordered &x) {
}
}
}
void OmpStructureChecker::Enter(const parser::OmpClause::Priority &) {
void OmpStructureChecker::Enter(const parser::OmpClause::Priority &x) {
CheckAllowed(OmpClause::PRIORITY);
RequiresPositiveParameter(OmpClause::PRIORITY, x.v);
}
void OmpStructureChecker::Enter(const parser::OmpClause::Private &) {
CheckAllowed(OmpClause::PRIVATE);

View File

@ -376,7 +376,6 @@
a = 3.14
enddo
! Standalone Directives (basic)
!$omp taskyield
@ -399,4 +398,30 @@
a = 3.14
!ERROR: Internal: no symbol found for 'first'
!$omp end critical (first)
! 2.9.1 task-clause -> if-clause |
! final-clause |
! untied-clause |
! default-clause |
! mergeable-clause |
! private-clause |
! firstprivate-clause |
! shared-clause |
! depend-clause |
! priority-clause
!$omp task shared(a) default(none) if(task:a > 1.)
a = 1.
!$omp end task
!ERROR: LASTPRIVATE clause is not allowed on the TASK directive
!ERROR: At most one FINAL clause can appear on the TASK directive
!$omp task lastprivate(b) final(a.GE.1) final(.false.)
b = 1
!$omp end task
!ERROR: The parameter of the PRIORITY clause must be a positive integer expression
!$omp task priority(-1) firstprivate(a) mergeable
a = 3.14
!$omp end task
end program