[flang-commits] [flang] [flang] `do concurrent`: fix reduction symbol resolution when mapping to OpenMP (PR #155355)
Kareem Ergawy via flang-commits
flang-commits at lists.llvm.org
Mon Aug 25 22:17:41 PDT 2025
https://github.com/ergawy created https://github.com/llvm/llvm-project/pull/155355
Fixes 155273
This PR introduces 2 changes:
1. The `do concurrent` to OpenMP pass is now a module pass rather than a function pass.
2. Reduction ops are looked up in the parent module before being created.
The benefit of using a module pass is that the same reduction operation can be used across multiple functions if the reduction type matches.
>From 009bcaf5da666e8dd95c71542a5b0880bd7de8b5 Mon Sep 17 00:00:00 2001
From: ergawy <kareem.ergawy at amd.com>
Date: Tue, 26 Aug 2025 00:13:35 -0500
Subject: [PATCH] [flang] `do concurrent`: fix reduction symbol resolution when
mapping to OpenMP
Fixes 155273
This PR introduces 2 changes:
1. The `do concurrent` to OpenMP pass is now a module pass rather than a
function pass.
2. Reduction ops are looked up in the parent module before being
created.
The benefit of using a module pass is that the same reduction operation
can be used across multiple functions if the reduction type matches.
---
.../include/flang/Optimizer/OpenMP/Passes.td | 2 +-
.../OpenMP/DoConcurrentConversion.cpp | 48 ++++++++++---------
.../reduction_symbol_resultion.f90 | 34 +++++++++++++
3 files changed, 60 insertions(+), 24 deletions(-)
create mode 100644 flang/test/Transforms/DoConcurrent/reduction_symbol_resultion.f90
diff --git a/flang/include/flang/Optimizer/OpenMP/Passes.td b/flang/include/flang/Optimizer/OpenMP/Passes.td
index 99202f6ee81e7..e2f092024c250 100644
--- a/flang/include/flang/Optimizer/OpenMP/Passes.td
+++ b/flang/include/flang/Optimizer/OpenMP/Passes.td
@@ -50,7 +50,7 @@ def FunctionFilteringPass : Pass<"omp-function-filtering"> {
];
}
-def DoConcurrentConversionPass : Pass<"omp-do-concurrent-conversion", "mlir::func::FuncOp"> {
+def DoConcurrentConversionPass : Pass<"omp-do-concurrent-conversion", "mlir::ModuleOp"> {
let summary = "Map `DO CONCURRENT` loops to OpenMP worksharing loops.";
let description = [{ This is an experimental pass to map `DO CONCURRENT` loops
diff --git a/flang/lib/Optimizer/OpenMP/DoConcurrentConversion.cpp b/flang/lib/Optimizer/OpenMP/DoConcurrentConversion.cpp
index 2b3ac169e8b5b..3c08ad0a54001 100644
--- a/flang/lib/Optimizer/OpenMP/DoConcurrentConversion.cpp
+++ b/flang/lib/Optimizer/OpenMP/DoConcurrentConversion.cpp
@@ -368,22 +368,28 @@ class DoConcurrentConversion
mlir::OpBuilder::InsertionGuard guard(rewriter);
rewriter.setInsertionPointAfter(firReducer);
-
- auto ompReducer = mlir::omp::DeclareReductionOp::create(
- rewriter, firReducer.getLoc(),
- sym.getLeafReference().str() + ".omp",
- firReducer.getTypeAttr().getValue());
-
- cloneFIRRegionToOMP(firReducer.getAllocRegion(),
- ompReducer.getAllocRegion());
- cloneFIRRegionToOMP(firReducer.getInitializerRegion(),
- ompReducer.getInitializerRegion());
- cloneFIRRegionToOMP(firReducer.getReductionRegion(),
- ompReducer.getReductionRegion());
- cloneFIRRegionToOMP(firReducer.getAtomicReductionRegion(),
- ompReducer.getAtomicReductionRegion());
- cloneFIRRegionToOMP(firReducer.getCleanupRegion(),
- ompReducer.getCleanupRegion());
+ std::string ompReducerName = sym.getLeafReference().str() + ".omp";
+
+ auto ompReducer = mlir::SymbolTable::lookupNearestSymbolFrom<
+ mlir::omp::DeclareReductionOp>(
+ loop, rewriter.getStringAttr(ompReducerName));
+
+ if (!ompReducer) {
+ ompReducer = mlir::omp::DeclareReductionOp::create(
+ rewriter, firReducer.getLoc(), ompReducerName,
+ firReducer.getTypeAttr().getValue());
+
+ cloneFIRRegionToOMP(firReducer.getAllocRegion(),
+ ompReducer.getAllocRegion());
+ cloneFIRRegionToOMP(firReducer.getInitializerRegion(),
+ ompReducer.getInitializerRegion());
+ cloneFIRRegionToOMP(firReducer.getReductionRegion(),
+ ompReducer.getReductionRegion());
+ cloneFIRRegionToOMP(firReducer.getAtomicReductionRegion(),
+ ompReducer.getAtomicReductionRegion());
+ cloneFIRRegionToOMP(firReducer.getCleanupRegion(),
+ ompReducer.getCleanupRegion());
+ }
wsloopClauseOps.reductionVars.push_back(op);
wsloopClauseOps.reductionByref.push_back(byRef);
@@ -444,11 +450,7 @@ class DoConcurrentConversionPass
: DoConcurrentConversionPassBase(options) {}
void runOnOperation() override {
- mlir::func::FuncOp func = getOperation();
-
- if (func.isDeclaration())
- return;
-
+ mlir::ModuleOp module = getOperation();
mlir::MLIRContext *context = &getContext();
if (mapTo != flangomp::DoConcurrentMappingKind::DCMK_Host &&
@@ -472,8 +474,8 @@ class DoConcurrentConversionPass
target.markUnknownOpDynamicallyLegal(
[](mlir::Operation *) { return true; });
- if (mlir::failed(mlir::applyFullConversion(getOperation(), target,
- std::move(patterns)))) {
+ if (mlir::failed(
+ mlir::applyFullConversion(module, target, std::move(patterns)))) {
signalPassFailure();
}
}
diff --git a/flang/test/Transforms/DoConcurrent/reduction_symbol_resultion.f90 b/flang/test/Transforms/DoConcurrent/reduction_symbol_resultion.f90
new file mode 100644
index 0000000000000..1b2b8461cca63
--- /dev/null
+++ b/flang/test/Transforms/DoConcurrent/reduction_symbol_resultion.f90
@@ -0,0 +1,34 @@
+! RUN: %flang_fc1 -emit-hlfir -fopenmp -fdo-concurrent-to-openmp=host %s -o - \
+! RUN: | FileCheck %s
+
+subroutine test1(x,s,N)
+ real :: x(N), s
+ integer :: N
+ do concurrent(i=1:N) reduce(+:s)
+ s=s+x(i)
+ end do
+end subroutine test1
+subroutine test2(x,s,N)
+ real :: x(N), s
+ integer :: N
+ do concurrent(i=1:N) reduce(+:s)
+ s=s+x(i)
+ end do
+end subroutine test2
+
+! CHECK: omp.declare_reduction @[[RED_SYM:.*]] : f32 init
+! CHECK-NOT: omp.declare_reduction
+
+! CHECK-LABEL: func.func @_QPtest1
+! CHECK: omp.parallel {
+! CHECK: omp.wsloop reduction(@[[RED_SYM]] {{.*}} : !fir.ref<f32>) {
+! CHECK: }
+! CHECK: }
+
+! CHECK-LABEL: func.func @_QPtest2
+! CHECK: omp.parallel {
+! CHECK: omp.wsloop reduction(@[[RED_SYM]] {{.*}} : !fir.ref<f32>) {
+! CHECK: }
+! CHECK: }
+
+
More information about the flang-commits
mailing list