[flang-commits] [flang] [Flang][OpenMP] Fix visibility of user-defined reductions for derived types and module imports (PR #180552)

via flang-commits flang-commits at lists.llvm.org
Mon Feb 9 07:55:04 PST 2026


llvmbot wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-flang-openmp

Author: CHANDRA GHALE (chandraghale)

<details>
<summary>Changes</summary>

User-defined reductions declared in a module were not visible to programs that imported the module via USE statements, causing valid code to be incorrectly rejected. The reduction identifier defined in the module scope wasn't being found during semantic analysis of the main program.

Ref:
OpenMP Spec 5.1 
_"If a directive appears in the specification part of a module then the behavior is as if that directive,
 with the variables, types and procedures that have PRIVATE accessibility omitted, appears in the
 specification part of any compilation unit that references the module unless otherwise specified "_

Fixes : [https://github.com/llvm/llvm-project/issues/176279](https://github.com/llvm/llvm-project/issues/176279)

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


3 Files Affected:

- (modified) flang/include/flang/Semantics/symbol.h (+16) 
- (modified) flang/lib/Semantics/check-omp-structure.cpp (+14) 
- (added) flang/test/Semantics/OpenMP/declare-reduction-derived-module.f90 (+30) 


``````````diff
diff --git a/flang/include/flang/Semantics/symbol.h b/flang/include/flang/Semantics/symbol.h
index 95efe1ae2bd5e..4c422ac5f471a 100644
--- a/flang/include/flang/Semantics/symbol.h
+++ b/flang/include/flang/Semantics/symbol.h
@@ -764,6 +764,22 @@ class UserReductionDetails {
         return true;
       }
     }
+    // For derived and class-derived types, match on the type symbol pointer.
+    if (type.category() == DeclTypeSpec::TypeDerived ||
+        type.category() == DeclTypeSpec::ClassDerived) {
+      const auto &rhs = type.derivedTypeSpec();
+      const auto &rhsSym = rhs.typeSymbol();
+      for (auto t : typeList_) {
+        if (t->category() == DeclTypeSpec::TypeDerived ||
+            t->category() == DeclTypeSpec::ClassDerived) {
+          const auto &lhs = t->derivedTypeSpec();
+          const auto &lhsSym = lhs.typeSymbol();
+          if (&lhsSym == &rhsSym) {
+            return true;
+          }
+        }
+      }
+    }
     return false;
   }
 
diff --git a/flang/lib/Semantics/check-omp-structure.cpp b/flang/lib/Semantics/check-omp-structure.cpp
index 5c4b5bb756734..0e004a8e26501 100644
--- a/flang/lib/Semantics/check-omp-structure.cpp
+++ b/flang/lib/Semantics/check-omp-structure.cpp
@@ -3691,6 +3691,20 @@ static bool CheckSymbolSupportsType(const Scope &scope,
       return reductionDetails->SupportsType(type);
     }
   }
+  // Look through module scopes in the global scope.
+  // This covers reductions declared in a module and used via USE association
+  const SemanticsContext &semCtx{scope.context()};
+  Scope &global = const_cast<SemanticsContext &>(semCtx).globalScope();
+  for (const Scope &child : global.children()) {
+    if (child.kind() == Scope::Kind::Module) {
+      if (const auto *symbol{child.FindSymbol(name)}) {
+        if (const auto *reductionDetails{
+                symbol->detailsIf<UserReductionDetails>()}) {
+          return reductionDetails->SupportsType(type);
+        }
+      }
+    }
+  }
   return false;
 }
 
diff --git a/flang/test/Semantics/OpenMP/declare-reduction-derived-module.f90 b/flang/test/Semantics/OpenMP/declare-reduction-derived-module.f90
new file mode 100644
index 0000000000000..342301ba2a8da
--- /dev/null
+++ b/flang/test/Semantics/OpenMP/declare-reduction-derived-module.f90
@@ -0,0 +1,30 @@
+! RUN: %flang_fc1 -fdebug-dump-symbols -fopenmp -fopenmp-version=50 %s | FileCheck %s
+module mod
+  type t
+     integer::i=0
+  end type t
+!$omp declare reduction (+:t:omp_out%i=omp_out%i+omp_in%i) &
+!$omp         initializer(omp_priv%i=0)
+end module mod
+
+!CHECK: Module scope: mod
+!CHECK: op.+, PUBLIC: UserReductionDetails TYPE(t)
+!CHECK: t, PUBLIC: DerivedType components: i
+
+program main
+  use mod
+  integer::i
+  type(t)::x1
+  x1%i=0
+!$omp parallel do reduction(+:x1)
+  do i=1,10
+     x1%i=x1%i+1
+  end do
+!$omp end parallel do
+  print *,'pass'
+end program main
+
+!CHECK: MainProgram scope: MAIN
+!CHECK: op.+: Use from op.+ in mod
+!CHECK: t: Use from t in mod
+!CHECK: x1 size=4 offset=4: ObjectEntity type: TYPE(t)

``````````

</details>


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


More information about the flang-commits mailing list