[flang-commits] [flang] [flang][OpenMP] Detect DSA conflicts in nested loop constructs (PR #195323)

via flang-commits flang-commits at lists.llvm.org
Fri May 1 11:47:00 PDT 2026


llvmorg-github-actions[bot] wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-flang-semantics

Author: Krzysztof Parzyszek (kparzysz)

<details>
<summary>Changes</summary>

Follow-up to https://github.com/llvm/llvm-project/pull/194961

The fix from PR194961 did not detect explicit/predefined DSA conflicts on an iteration variable in a nested loop construct. For example, in a testcase inspired by Fujitsu 0165_0035.f90:
```
  !$omp parallel do private(i) shared(j)
  do i=1,1
    do j=1,1
      !$omp parallel do default(none) shared(k)
      do k=1,1
      end do
      !$omp end parallel do
    end do
  end do
```
the "shared(k)" was not flagged as incorrect.

Adjust the fix to traverse the host-association chain until the symbol from the DSA clause is found.

---
Full diff: https://github.com/llvm/llvm-project/pull/195323.diff


2 Files Affected:

- (modified) flang/lib/Semantics/check-omp-loop.cpp (+13-5) 
- (modified) flang/test/Semantics/OpenMP/do01.f90 (+17) 


``````````diff
diff --git a/flang/lib/Semantics/check-omp-loop.cpp b/flang/lib/Semantics/check-omp-loop.cpp
index 2c40185b23011..50fbcc20a98aa 100644
--- a/flang/lib/Semantics/check-omp-loop.cpp
+++ b/flang/lib/Semantics/check-omp-loop.cpp
@@ -484,6 +484,10 @@ void OmpStructureChecker::CheckIterationVariables(
 
   std::vector<parser::Name> ivs;
   for (const parser::DoConstruct *loop : *doLoops) {
+    // Skip DO CONCURRENT, since their iteration variables are local.
+    if (loop->IsDoConcurrent()) {
+      continue;
+    }
     for (auto &control : GetLoopControls(*loop)) {
       if (control.iv.symbol) {
         ivs.push_back(control.iv);
@@ -498,15 +502,19 @@ void OmpStructureChecker::CheckIterationVariables(
           "The DO loop iteration variable must be of integer type"_err_en_US,
           iv.ToString());
     }
-    const Symbol *host{GetHostSymbol(*iv.symbol)};
-    if (!host) {
-      continue;
-    }
-    if (host->test(Symbol::Flag::OmpThreadprivate)) {
+    if (iv.symbol->GetUltimate().test(Symbol::Flag::OmpThreadprivate)) {
       context_.Say(iv.source,
           "Loop iteration variable of an affected loop cannot be THREADPRIVATE"_err_en_US,
           iv.ToString());
     }
+    // Get the symbol from the variable that was listed in a DSA clause.
+    const Symbol *host{iv.symbol};
+    while (host && !dsa.count(host)) {
+      host = GetHostSymbol(*host);
+    }
+    if (!host) {
+      continue;
+    }
     // Check conflict between a predetermined DSA and explicit DSA.
     assert(iv.symbol->test(Symbol::Flag::OmpPreDetermined) &&
         "Expecting affected iteration variable to have predetermined DSA");
diff --git a/flang/test/Semantics/OpenMP/do01.f90 b/flang/test/Semantics/OpenMP/do01.f90
index b4e9dcf753895..38815b4f774b2 100644
--- a/flang/test/Semantics/OpenMP/do01.f90
+++ b/flang/test/Semantics/OpenMP/do01.f90
@@ -31,3 +31,20 @@ subroutine f01
     end do
   end block
 end
+
+! Check DSA clause on a nested construct
+subroutine f02
+  integer :: i, j, k
+  !$omp parallel do private(i) shared(j)
+  do i = 1, 10
+    do j = 1, 10
+      !ERROR: Loop iteration variable with a predetermined data sharing attribute cannot appear in a SHARED clause
+      !$omp parallel do default(none) shared(k)
+      !BECAUSE: 'k' is an iteration variable of an affected loop
+      do k = 1, 10
+      end do
+      !$omp end parallel do
+    end do
+  end do
+  !$omp end parallel do
+end

``````````

</details>


https://github.com/llvm/llvm-project/pull/195323


More information about the flang-commits mailing list