[llvm] 13615f7 - [flang][openacc] Allow if clause on atomic directives (#135451)

via llvm-commits llvm-commits at lists.llvm.org
Tue Apr 15 11:56:40 PDT 2025


Author: Valentin Clement (バレンタイン クレメン)
Date: 2025-04-15T11:56:35-07:00
New Revision: 13615f7b506a693783764da87dc80e97cf59b95c

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

LOG: [flang][openacc] Allow if clause on atomic directives (#135451)

The new version of the OpenACC specification will allow the if clause on
the atomic directives. Allow it in `ACC.td` and update the parse node
and parser in flang to support it.

OpenACC dialect will need to be updated to support it as well.

Added: 
    

Modified: 
    flang/include/flang/Parser/parse-tree.h
    flang/lib/Parser/openacc-parsers.cpp
    flang/test/Semantics/OpenACC/acc-atomic-validity.f90
    llvm/include/llvm/Frontend/OpenACC/ACC.td

Removed: 
    


################################################################################
diff  --git a/flang/include/flang/Parser/parse-tree.h b/flang/include/flang/Parser/parse-tree.h
index eeb438991feee..0c2a5de3b71d2 100644
--- a/flang/include/flang/Parser/parse-tree.h
+++ b/flang/include/flang/Parser/parse-tree.h
@@ -5244,21 +5244,23 @@ EMPTY_CLASS(AccEndAtomic);
 // ACC ATOMIC READ
 struct AccAtomicRead {
   TUPLE_CLASS_BOILERPLATE(AccAtomicRead);
-  std::tuple<Verbatim, Statement<AssignmentStmt>, std::optional<AccEndAtomic>>
+  std::tuple<Verbatim, AccClauseList, Statement<AssignmentStmt>,
+      std::optional<AccEndAtomic>>
       t;
 };
 
 // ACC ATOMIC WRITE
 struct AccAtomicWrite {
   TUPLE_CLASS_BOILERPLATE(AccAtomicWrite);
-  std::tuple<Verbatim, Statement<AssignmentStmt>, std::optional<AccEndAtomic>>
+  std::tuple<Verbatim, AccClauseList, Statement<AssignmentStmt>,
+      std::optional<AccEndAtomic>>
       t;
 };
 
 // ACC ATOMIC UPDATE
 struct AccAtomicUpdate {
   TUPLE_CLASS_BOILERPLATE(AccAtomicUpdate);
-  std::tuple<std::optional<Verbatim>, Statement<AssignmentStmt>,
+  std::tuple<std::optional<Verbatim>, AccClauseList, Statement<AssignmentStmt>,
       std::optional<AccEndAtomic>>
       t;
 };
@@ -5268,7 +5270,7 @@ struct AccAtomicCapture {
   TUPLE_CLASS_BOILERPLATE(AccAtomicCapture);
   WRAPPER_CLASS(Stmt1, Statement<AssignmentStmt>);
   WRAPPER_CLASS(Stmt2, Statement<AssignmentStmt>);
-  std::tuple<Verbatim, Stmt1, Stmt2, AccEndAtomic> t;
+  std::tuple<Verbatim, AccClauseList, Stmt1, Stmt2, AccEndAtomic> t;
 };
 
 struct OpenACCAtomicConstruct {

diff  --git a/flang/lib/Parser/openacc-parsers.cpp b/flang/lib/Parser/openacc-parsers.cpp
index fb731ee52cbba..072eba99826a1 100644
--- a/flang/lib/Parser/openacc-parsers.cpp
+++ b/flang/lib/Parser/openacc-parsers.cpp
@@ -187,22 +187,25 @@ TYPE_PARSER(construct<AccBeginCombinedDirective>(
 // 2.12 Atomic constructs
 TYPE_PARSER(construct<AccEndAtomic>(startAccLine >> "END ATOMIC"_tok))
 
-TYPE_PARSER("ATOMIC" >>
-    construct<AccAtomicRead>(verbatim("READ"_tok) / endAccLine,
-        statement(assignmentStmt), maybe(Parser<AccEndAtomic>{} / endAccLine)))
+TYPE_PARSER("ATOMIC" >> construct<AccAtomicRead>(verbatim("READ"_tok),
+                            Parser<AccClauseList>{} / endAccLine,
+                            statement(assignmentStmt),
+                            maybe(Parser<AccEndAtomic>{} / endAccLine)))
 
-TYPE_PARSER("ATOMIC" >>
-    construct<AccAtomicWrite>(verbatim("WRITE"_tok) / endAccLine,
-        statement(assignmentStmt), maybe(Parser<AccEndAtomic>{} / endAccLine)))
+TYPE_PARSER("ATOMIC" >> construct<AccAtomicWrite>(verbatim("WRITE"_tok),
+                            Parser<AccClauseList>{} / endAccLine,
+                            statement(assignmentStmt),
+                            maybe(Parser<AccEndAtomic>{} / endAccLine)))
 
 TYPE_PARSER("ATOMIC" >>
-    construct<AccAtomicUpdate>(maybe(verbatim("UPDATE"_tok)) / endAccLine,
-        statement(assignmentStmt), maybe(Parser<AccEndAtomic>{} / endAccLine)))
+    construct<AccAtomicUpdate>(maybe(verbatim("UPDATE"_tok)),
+        Parser<AccClauseList>{} / endAccLine, statement(assignmentStmt),
+        maybe(Parser<AccEndAtomic>{} / endAccLine)))
 
 TYPE_PARSER("ATOMIC" >>
-    construct<AccAtomicCapture>(verbatim("CAPTURE"_tok) / endAccLine,
-        statement(assignmentStmt), statement(assignmentStmt),
-        Parser<AccEndAtomic>{} / endAccLine))
+    construct<AccAtomicCapture>(verbatim("CAPTURE"_tok),
+        Parser<AccClauseList>{} / endAccLine, statement(assignmentStmt),
+        statement(assignmentStmt), Parser<AccEndAtomic>{} / endAccLine))
 
 TYPE_PARSER(
     sourced(construct<OpenACCAtomicConstruct>(Parser<AccAtomicRead>{})) ||

diff  --git a/flang/test/Semantics/OpenACC/acc-atomic-validity.f90 b/flang/test/Semantics/OpenACC/acc-atomic-validity.f90
index ba68031b0f18b..07fb864695737 100644
--- a/flang/test/Semantics/OpenACC/acc-atomic-validity.f90
+++ b/flang/test/Semantics/OpenACC/acc-atomic-validity.f90
@@ -10,6 +10,7 @@ program openacc_atomic_validity
   integer :: i
   integer, parameter :: N = 256
   integer, dimension(N) :: c
+  logical :: l
 
 
   !$acc parallel
@@ -23,27 +24,58 @@ program openacc_atomic_validity
   !$acc atomic write
   c(i) = 10
 
+  !$acc atomic write if(l)
+  c(i) = 10
+
   !$acc atomic write
   c(i) = 10
   !$acc end atomic
 
+  !$acc atomic write if(.true.)
+  c(i) = 10
+  !$acc end atomic
+
   !$acc atomic read
   i = c(i)
+  
+  !$acc atomic read if(.true.)
+  i = c(i)
 
   !$acc atomic read
   i = c(i)
   !$acc end atomic
 
+  !$acc atomic read if(l) 
+  i = c(i)
+  !$acc end atomic
+
+  !ERROR: FINALIZE clause is not allowed on the ATOMIC READ FINALIZE IF(L)
+  !$acc atomic read finalize if(l) 
+  i = c(i)
+  !$acc end atomic
+
   !$acc atomic capture
   c(i) = i
   i = i + 1
   !$acc end atomic
 
+  !$acc atomic capture if(l .EQV. .false.)
+  c(i) = i
+  i = i + 1
+  !$acc end atomic
+
   !$acc atomic update
   !ERROR: RHS of atomic update statement must be scalar
   !ERROR: LHS of atomic update statement must be scalar
   c = c + 1
 
+  !$acc atomic update if(i == 0)
+  c(i) = c(i) + 1
+
+  !ERROR: At most one IF clause can appear on the ATOMIC UPDATE IF(I == 0) IF(.TRUE.)
+  !$acc atomic update if(i == 0) if(.true.)
+  c(i) = c(i) + 1
+
   !$acc end parallel
 
 end program openacc_atomic_validity

diff  --git a/llvm/include/llvm/Frontend/OpenACC/ACC.td b/llvm/include/llvm/Frontend/OpenACC/ACC.td
index 2acee9bcc7195..e1a4183785d1f 100644
--- a/llvm/include/llvm/Frontend/OpenACC/ACC.td
+++ b/llvm/include/llvm/Frontend/OpenACC/ACC.td
@@ -270,6 +270,7 @@ def ACCC_Unknown : Clause<"unknown"> {
 
 // 2.12
 def ACC_Atomic : Directive<"atomic"> {
+  let allowedOnceClauses = [VersionedClause<ACCC_If, 34>];
   let association = AS_Block;
   let category = CA_Executable;
 }


        


More information about the llvm-commits mailing list