[llvm] f1569b1 - [Flang][OpenMP-5.0] Semantic checks for flush construct.

Sameeran joshi via llvm-commits llvm-commits at lists.llvm.org
Mon Dec 14 00:05:06 PST 2020


Author: sameeran joshi
Date: 2020-12-14T13:30:48+05:30
New Revision: f1569b1ece5516d31d8c748f7b2981a688e32826

URL: https://github.com/llvm/llvm-project/commit/f1569b1ece5516d31d8c748f7b2981a688e32826
DIFF: https://github.com/llvm/llvm-project/commit/f1569b1ece5516d31d8c748f7b2981a688e32826.diff

LOG: [Flang][OpenMP-5.0] Semantic checks for flush construct.

>From OMP 5.0 [2.17.8]
Restriction:
If memory-order-clause is release,acquire, or acq_rel, list items must not be specified on the flush directive.

Reviewed By: kiranchandramohan, clementval

Differential Revision: https://reviews.llvm.org/D89879

Added: 
    flang/test/Semantics/omp-flush01.f90
    flang/test/Semantics/omp-flush02.f90

Modified: 
    flang/include/flang/Parser/parse-tree.h
    flang/lib/Lower/OpenMP.cpp
    flang/lib/Parser/openmp-parsers.cpp
    flang/lib/Parser/unparse.cpp
    flang/lib/Semantics/check-omp-structure.cpp
    flang/test/Semantics/omp-clause-validity01.f90
    llvm/include/llvm/Frontend/OpenMP/OMP.td

Removed: 
    


################################################################################
diff  --git a/flang/include/flang/Parser/parse-tree.h b/flang/include/flang/Parser/parse-tree.h
index 5d2909a4142a..27998c308cc0 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -3747,7 +3747,7 @@ struct OpenMPCancelConstruct {
 struct OpenMPFlushConstruct {
   TUPLE_CLASS_BOILERPLATE(OpenMPFlushConstruct);
   CharBlock source;
-  std::tuple<Verbatim, std::optional<OmpMemoryOrderClause>,
+  std::tuple<Verbatim, std::optional<std::list<OmpMemoryOrderClause>>,
       std::optional<OmpObjectList>>
       t;
 };

diff  --git a/flang/lib/Lower/OpenMP.cpp b/flang/lib/Lower/OpenMP.cpp
index cfe4b0b86b67..97946caa68a0 100644
--- a/flang/lib/Lower/OpenMP.cpp
+++ b/flang/lib/Lower/OpenMP.cpp
@@ -109,7 +109,8 @@ genOMP(Fortran::lower::AbstractConverter &converter,
                     std::get<std::optional<Fortran::parser::OmpObjectList>>(
                         flushConstruct.t))
               genObjectList(*ompObjectList, converter, operandRange);
-            if (std::get<std::optional<Fortran::parser::OmpMemoryOrderClause>>(
+            if (std::get<std::optional<
+                    std::list<Fortran::parser::OmpMemoryOrderClause>>>(
                     flushConstruct.t))
               TODO("Handle OmpMemoryOrderClause");
             converter.getFirOpBuilder().create<mlir::omp::FlushOp>(

diff  --git a/flang/lib/Parser/openmp-parsers.cpp b/flang/lib/Parser/openmp-parsers.cpp
index fd209abc4138..67c377e798ca 100644
--- a/flang/lib/Parser/openmp-parsers.cpp
+++ b/flang/lib/Parser/openmp-parsers.cpp
@@ -331,7 +331,7 @@ TYPE_PARSER(sourced(construct<OmpAtomicClauseList>(
     many(maybe(","_tok) >> sourced(Parser<OmpAtomicClause>{})))))
 
 TYPE_PARSER(sourced(construct<OpenMPFlushConstruct>(verbatim("FLUSH"_tok),
-    maybe(Parser<OmpMemoryOrderClause>{}),
+    many(maybe(","_tok) >> sourced(Parser<OmpMemoryOrderClause>{})),
     maybe(parenthesized(Parser<OmpObjectList>{})))))
 
 // Simple Standalone Directives

diff  --git a/flang/lib/Parser/unparse.cpp b/flang/lib/Parser/unparse.cpp
index c5df6990d102..bd1c1a2c71eb 100644
--- a/flang/lib/Parser/unparse.cpp
+++ b/flang/lib/Parser/unparse.cpp
@@ -2460,7 +2460,7 @@ class UnparseVisitor {
   void Unparse(const OpenMPFlushConstruct &x) {
     BeginOpenMP();
     Word("!$OMP FLUSH ");
-    Walk(std::get<std::optional<OmpMemoryOrderClause>>(x.t));
+    Walk(std::get<std::optional<std::list<OmpMemoryOrderClause>>>(x.t));
     Walk(" (", std::get<std::optional<OmpObjectList>>(x.t), ")");
     Put("\n");
     EndOpenMP();

diff  --git a/flang/lib/Semantics/check-omp-structure.cpp b/flang/lib/Semantics/check-omp-structure.cpp
index e58e2e509fb8..978e1c7962a4 100644
--- a/flang/lib/Semantics/check-omp-structure.cpp
+++ b/flang/lib/Semantics/check-omp-structure.cpp
@@ -226,7 +226,17 @@ void OmpStructureChecker::Enter(const parser::OpenMPFlushConstruct &x) {
   PushContextAndClauseSets(dir.source, llvm::omp::Directive::OMPD_flush);
 }
 
-void OmpStructureChecker::Leave(const parser::OpenMPFlushConstruct &) {
+void OmpStructureChecker::Leave(const parser::OpenMPFlushConstruct &x) {
+  if (FindClause(llvm::omp::Clause::OMPC_acquire) ||
+      FindClause(llvm::omp::Clause::OMPC_release) ||
+      FindClause(llvm::omp::Clause::OMPC_acq_rel)) {
+    if (const auto &flushList{
+            std::get<std::optional<parser::OmpObjectList>>(x.t)}) {
+      context_.Say(parser::FindSourceLocation(flushList),
+          "If memory-order-clause is RELEASE, ACQUIRE, or ACQ_REL, list items "
+          "must not be specified on the FLUSH directive"_err_en_US);
+    }
+  }
   dirContext_.pop_back();
 }
 

diff  --git a/flang/test/Semantics/omp-clause-validity01.f90 b/flang/test/Semantics/omp-clause-validity01.f90
index 601e39021e44..3f5345137866 100644
--- a/flang/test/Semantics/omp-clause-validity01.f90
+++ b/flang/test/Semantics/omp-clause-validity01.f90
@@ -487,6 +487,7 @@
   !$omp flush acq_rel
   !$omp flush release
   !$omp flush acquire
+  !ERROR: If memory-order-clause is RELEASE, ACQUIRE, or ACQ_REL, list items must not be specified on the FLUSH directive
   !$omp flush release (c)
   !ERROR: SEQ_CST clause is not allowed on the FLUSH directive
   !$omp flush seq_cst

diff  --git a/flang/test/Semantics/omp-flush01.f90 b/flang/test/Semantics/omp-flush01.f90
new file mode 100644
index 000000000000..cca78e7a09cd
--- /dev/null
+++ b/flang/test/Semantics/omp-flush01.f90
@@ -0,0 +1,39 @@
+! RUN: %S/test_errors.sh %s %t %f18 -fopenmp
+
+! 2.17.8 Flush construct [OpenMP 5.0]
+!        memory-order-clause ->
+!                               acq_rel
+!                               release
+!                               acquire
+use omp_lib
+  implicit none
+
+  integer :: i, a, b
+  real, DIMENSION(10) :: array
+
+  a = 1.0
+  !$omp parallel num_threads(4)
+  !Only memory-order-clauses.
+  if (omp_get_thread_num() == 1) then
+    ! Allowed clauses.
+    !$omp flush acq_rel
+    array = (/1, 2, 3, 4, 5, 6, 7, 8, 9, 10/)
+    !$omp flush release
+    array = (/1, 2, 3, 4, 5, 6, 7, 8, 9, 10/)
+    !$omp flush acquire
+
+    !ERROR: expected end of line
+    !ERROR: expected end of line
+    !$omp flush private(array)
+    !ERROR: expected end of line
+    !ERROR: expected end of line
+    !$omp flush num_threads(4)
+
+    ! Mix allowed and not allowed clauses.
+    !ERROR: expected end of line
+    !ERROR: expected end of line
+    !$omp flush num_threads(4) acquire
+  end if
+  !$omp end parallel
+end
+

diff  --git a/flang/test/Semantics/omp-flush02.f90 b/flang/test/Semantics/omp-flush02.f90
new file mode 100644
index 000000000000..6e417c49a3b0
--- /dev/null
+++ b/flang/test/Semantics/omp-flush02.f90
@@ -0,0 +1,86 @@
+! RUN: %S/test_errors.sh %s %t %f18 -fopenmp
+
+! Check OpenMP 5.0 - 2.17.8 flush Construct
+! Restriction -
+! If memory-order-clause is release, acquire, or acq_rel, list items must not be specified on the flush directive.
+
+use omp_lib
+  implicit none
+
+  TYPE someStruct
+    REAL :: rr
+  end TYPE
+  integer :: i, a, b
+  real, DIMENSION(10) :: array
+  TYPE(someStruct) :: structObj
+
+  a = 1.0
+  !$omp parallel num_threads(4)
+  !No list flushes all.
+  if (omp_get_thread_num() == 1) THEN
+    !$omp flush
+  END IF
+
+  array = (/1, 2, 3, 4, 5, 6, 7, 8, 9, 10/)
+  !Only memory-order-clauses.
+  if (omp_get_thread_num() == 1) THEN
+    ! Not allowed clauses.
+    !ERROR: SEQ_CST clause is not allowed on the FLUSH directive
+    !$omp flush seq_cst
+    !ERROR: RELAXED clause is not allowed on the FLUSH directive
+    !$omp flush relaxed
+
+    ! Not allowed more than once.
+    !ERROR: At most one ACQ_REL clause can appear on the FLUSH directive
+    !$omp flush acq_rel acq_rel
+    !ERROR: At most one RELEASE clause can appear on the FLUSH directive
+    !$omp flush release release
+    !ERROR: At most one ACQUIRE clause can appear on the FLUSH directive
+    !$omp flush acquire acquire
+
+    ! Mix of allowed and not allowed.
+    !ERROR: SEQ_CST clause is not allowed on the FLUSH directive
+    !$omp flush seq_cst acquire
+  END IF
+
+  array = (/1, 2, 3, 4, 5, 6, 7, 8, 9, 10/)
+  ! No memory-order-clause only list-items.
+  if (omp_get_thread_num() == 2) THEN
+    !$omp flush (a)
+    !$omp flush (i, a, b)
+    !$omp flush (array, structObj%rr)
+    ! Too many flush with repeating list items.
+    !$omp flush (i, a, b, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, b, b, b, b)
+    !ERROR: No explicit type declared for 'notpresentitem'
+    !$omp flush (notPresentItem)
+  END IF
+
+  array = (/1, 2, 3, 4, 5, 6, 7, 8, 9, 10/)
+  if (omp_get_thread_num() == 3) THEN
+    !ERROR: If memory-order-clause is RELEASE, ACQUIRE, or ACQ_REL, list items must not be specified on the FLUSH directive
+    !$omp flush acq_rel (array)
+    !ERROR: If memory-order-clause is RELEASE, ACQUIRE, or ACQ_REL, list items must not be specified on the FLUSH directive
+    !$omp flush acq_rel (array, a, i)
+
+    array = (/1, 2, 3, 4, 5, 6, 7, 8, 9, 10/)
+    !ERROR: If memory-order-clause is RELEASE, ACQUIRE, or ACQ_REL, list items must not be specified on the FLUSH directive
+    !$omp flush release (array)
+    !ERROR: If memory-order-clause is RELEASE, ACQUIRE, or ACQ_REL, list items must not be specified on the FLUSH directive
+    !$omp flush release (array, a)
+
+    array = (/1, 2, 3, 4, 5, 6, 7, 8, 9, 10/)
+    !ERROR: If memory-order-clause is RELEASE, ACQUIRE, or ACQ_REL, list items must not be specified on the FLUSH directive
+    !$omp flush acquire (array)
+    !ERROR: If memory-order-clause is RELEASE, ACQUIRE, or ACQ_REL, list items must not be specified on the FLUSH directive
+    !$omp flush acquire (array, a, structObj%rr)
+  END IF
+  !$omp end parallel
+
+  !$omp parallel num_threads(4)
+    array = (/1, 2, 3, 4, 5, 6, 7, 8, 9, 10/)
+    !$omp master
+      !$omp flush (array)
+    !$omp end master
+  !$omp end parallel
+end
+

diff  --git a/llvm/include/llvm/Frontend/OpenMP/OMP.td b/llvm/include/llvm/Frontend/OpenMP/OMP.td
index 13aa1381d679..59198f8a64fb 100644
--- a/llvm/include/llvm/Frontend/OpenMP/OMP.td
+++ b/llvm/include/llvm/Frontend/OpenMP/OMP.td
@@ -446,7 +446,7 @@ def OMP_TaskGroup : Directive<"taskgroup"> {
   ];
 }
 def OMP_Flush : Directive<"flush"> {
-  let allowedClauses = [
+  let allowedOnceClauses = [
     VersionedClause<OMPC_AcqRel, 50>,
     VersionedClause<OMPC_Acquire, 50>,
     VersionedClause<OMPC_Release, 50>,


        


More information about the llvm-commits mailing list