[flang-commits] [flang] ab4f66d - [OpenMP][flang] Move `todo` for checking reduction support status on the GPU (#175172)
via flang-commits
flang-commits at lists.llvm.org
Wed Jan 21 04:22:50 PST 2026
Author: Kareem Ergawy
Date: 2026-01-21T13:22:45+01:00
New Revision: ab4f66d6f3213051f5ba27d74f8f4c7c5cc58bd5
URL: https://github.com/llvm/llvm-project/commit/ab4f66d6f3213051f5ba27d74f8f4c7c5cc58bd5
DIFF: https://github.com/llvm/llvm-project/commit/ab4f66d6f3213051f5ba27d74f8f4c7c5cc58bd5.diff
LOG: [OpenMP][flang] Move `todo` for checking reduction support status on the GPU (#175172)
Moves a `todo` to check for the current level of support for by-ref
reductions to the `FunctionFiltering` pass. This guarantees that the
check does not trigger when the same module is compiled twice: on the
CPU and on the GPU.
Added:
flang/test/Transforms/omp-function-filtering-todo.mlir
Modified:
flang/lib/Lower/Support/ReductionProcessor.cpp
flang/lib/Optimizer/OpenMP/FunctionFiltering.cpp
Removed:
################################################################################
diff --git a/flang/lib/Lower/Support/ReductionProcessor.cpp b/flang/lib/Lower/Support/ReductionProcessor.cpp
index db8ad909b1d2f..0e01268dd74ff 100644
--- a/flang/lib/Lower/Support/ReductionProcessor.cpp
+++ b/flang/lib/Lower/Support/ReductionProcessor.cpp
@@ -598,26 +598,6 @@ DeclareRedType ReductionProcessor::createDeclareReductionHelper(
genCombinerCB(builder, loc, type, op1, op2, isByRef);
if (isByRef && fir::isa_box_type(valTy)) {
- bool isBoxReductionSupported = [&]() {
- auto offloadMod = llvm::dyn_cast<mlir::omp::OffloadModuleInterface>(
- *builder.getModule());
-
- // This check tests the implementation status on the GPU. Box reductions
- // are fully supported on the CPU.
- if (!offloadMod.getIsGPU())
- return true;
-
- auto seqTy = mlir::dyn_cast<fir::SequenceType>(boxedTy);
-
- // Dynamically-shaped arrays are not supported yet on the GPU.
- return !seqTy || !fir::sequenceWithNonConstantShape(seqTy);
- }();
-
- if (!isBoxReductionSupported) {
- TODO(loc, "Reduction of dynamically-shaped arrays are not supported yet "
- "on the GPU.");
- }
-
mlir::Region &dataPtrPtrRegion = decl.getDataPtrPtrRegion();
mlir::Block &dataAddrBlock = *builder.createBlock(
&dataPtrPtrRegion, dataPtrPtrRegion.end(), {type}, {loc});
diff --git a/flang/lib/Optimizer/OpenMP/FunctionFiltering.cpp b/flang/lib/Optimizer/OpenMP/FunctionFiltering.cpp
index 3031bb5da6919..e58d5b7e7a389 100644
--- a/flang/lib/Optimizer/OpenMP/FunctionFiltering.cpp
+++ b/flang/lib/Optimizer/OpenMP/FunctionFiltering.cpp
@@ -11,6 +11,7 @@
//
//===----------------------------------------------------------------------===//
+#include "flang/Optimizer/Builder/Todo.h"
#include "flang/Optimizer/Dialect/FIRDialect.h"
#include "flang/Optimizer/Dialect/FIROpsSupport.h"
#include "flang/Optimizer/OpenMP/Passes.h"
@@ -28,6 +29,42 @@ namespace flangomp {
using namespace mlir;
+/// This function triggers TODO errors and halts compilation if it detects
+/// patterns representing unimplemented features.
+///
+/// It exclusively checks situations that cannot be detected after all of the
+/// MLIR pipeline has ran (i.e. at the MLIR to LLVM IR translation stage, where
+/// the preferred location for these types of checks is), and it only checks for
+/// features that have not been implemented for target offload, but are
+/// supported on host execution.
+void checkDeviceImplementationStatus(
+ omp::OffloadModuleInterface offloadModule) {
+ if (!offloadModule.getIsGPU())
+ return;
+
+ offloadModule->walk<WalkOrder::PreOrder>([&](omp::DeclareReductionOp redOp) {
+ if (redOp.symbolKnownUseEmpty(offloadModule))
+ return WalkResult::advance();
+
+ if (!redOp.getByrefElementType())
+ return WalkResult::advance();
+
+ auto seqTy =
+ mlir::dyn_cast<fir::SequenceType>(*redOp.getByrefElementType());
+
+ bool isByRefReductionSupported =
+ !seqTy || !fir::sequenceWithNonConstantShape(seqTy);
+
+ if (!isByRefReductionSupported) {
+ TODO(redOp.getLoc(),
+ "Reduction of dynamically-shaped arrays are not supported yet "
+ "on the GPU.");
+ }
+
+ return WalkResult::advance();
+ });
+}
+
namespace {
class FunctionFilteringPass
: public flangomp::impl::FunctionFilteringPassBase<FunctionFilteringPass> {
@@ -101,6 +138,8 @@ class FunctionFilteringPass
}
return WalkResult::advance();
});
+
+ checkDeviceImplementationStatus(op);
}
};
} // namespace
diff --git a/flang/test/Transforms/omp-function-filtering-todo.mlir b/flang/test/Transforms/omp-function-filtering-todo.mlir
new file mode 100644
index 0000000000000..c5640bb9757f7
--- /dev/null
+++ b/flang/test/Transforms/omp-function-filtering-todo.mlir
@@ -0,0 +1,33 @@
+// RUN: not fir-opt --omp-function-filtering -o - %s 2>&1 | FileCheck %s
+
+module attributes {omp.is_gpu = true, omp.is_target_device = true} {
+ // CHECK: not yet implemented: Reduction of dynamically-shaped arrays are not supported yet on the GPU.
+ omp.declare_reduction @add_reduction_byref_box_heap_Uxi32 : !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>> attributes {byref_element_type = !fir.array<?xi32>} alloc {
+ %0 = fir.alloca !fir.box<!fir.heap<!fir.array<?xi32>>>
+ omp.yield(%0 : !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>>)
+ } init {
+ ^bb0(%arg0: !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>>, %arg1: !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>>):
+ omp.yield(%arg1 : !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>>)
+ } combiner {
+ ^bb0(%arg0: !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>>, %arg1: !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>>):
+ omp.yield(%arg0 : !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>>)
+ }
+
+ func.func @foo(%ia : !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>>) {
+ %ia.map = omp.map.info var_ptr(%ia : !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>>, !fir.box<!fir.heap<!fir.array<?xi32>>>) map_clauses(always, implicit, to) capture(ByRef) -> !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>> {name = "ia"}
+
+ omp.target map_entries(%ia.map -> %arg0 : !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>>) {
+ omp.parallel {
+ %c1_i32 = arith.constant 1 : i32
+ omp.wsloop reduction(byref @add_reduction_byref_box_heap_Uxi32 %arg0 -> %arg1 : !fir.ref<!fir.box<!fir.heap<!fir.array<?xi32>>>>) {
+ omp.loop_nest (%arg2) : i32 = (%c1_i32) to (%c1_i32) inclusive step (%c1_i32) {
+ omp.yield
+ }
+ }
+ omp.terminator
+ }
+ omp.terminator
+ }
+ return
+ }
+}
More information about the flang-commits
mailing list