[flang-commits] [flang] a060102 - [flang][openacc] Support static slice in reduction lowering

Valentin Clement via flang-commits flang-commits at lists.llvm.org
Tue Jul 18 14:14:16 PDT 2023


Author: Valentin Clement
Date: 2023-07-18T14:14:10-07:00
New Revision: a060102b3cb09d0710a58f783e18679858b3fdfc

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

LOG: [flang][openacc] Support static slice in reduction lowering

Lower static array slices reduction with the correct
type.

Reviewed By: razvanlupusoru

Differential Revision: https://reviews.llvm.org/D155519

Added: 
    

Modified: 
    flang/include/flang/Lower/OpenACC.h
    flang/lib/Lower/OpenACC.cpp
    flang/test/Lower/OpenACC/acc-reduction.f90

Removed: 
    


################################################################################
diff  --git a/flang/include/flang/Lower/OpenACC.h b/flang/include/flang/Lower/OpenACC.h
index f9b4c1f2c62ae1..6424e6ba65f3a8 100644
--- a/flang/include/flang/Lower/OpenACC.h
+++ b/flang/include/flang/Lower/OpenACC.h
@@ -16,6 +16,8 @@
 #include "mlir/Dialect/OpenACC/OpenACC.h"
 
 namespace llvm {
+template <typename T, unsigned N>
+class SmallVector;
 class StringRef;
 }
 
@@ -23,6 +25,7 @@ namespace mlir {
 class Location;
 class Type;
 class OpBuilder;
+class Value;
 } // namespace mlir
 
 namespace fir {
@@ -64,7 +67,8 @@ mlir::acc::PrivateRecipeOp createOrGetPrivateRecipe(mlir::OpBuilder &,
 /// exist yet.
 mlir::acc::ReductionRecipeOp
 createOrGetReductionRecipe(fir::FirOpBuilder &, llvm::StringRef, mlir::Location,
-                           mlir::Type, mlir::acc::ReductionOperator);
+                           mlir::Type, mlir::acc::ReductionOperator,
+                           llvm::SmallVector<mlir::Value> &);
 
 /// Get a acc.firstprivate.recipe op for the given type or create it if it does
 /// not exist yet.

diff  --git a/flang/lib/Lower/OpenACC.cpp b/flang/lib/Lower/OpenACC.cpp
index f94c1de173c9f3..e1332f17d27711 100644
--- a/flang/lib/Lower/OpenACC.cpp
+++ b/flang/lib/Lower/OpenACC.cpp
@@ -680,9 +680,24 @@ static R getReductionInitValue(mlir::acc::ReductionOperator op, mlir::Type ty) {
   llvm_unreachable("OpenACC reduction unsupported type");
 }
 
-static mlir::Value genReductionInitValue(fir::FirOpBuilder &builder,
-                                         mlir::Location loc, mlir::Type ty,
-                                         mlir::acc::ReductionOperator op) {
+/// Determine if the bounds represent a dynamic shape.
+bool hasDynamicShape(llvm::SmallVector<mlir::Value> &bounds) {
+  if (bounds.empty())
+    return false;
+  for (auto b : bounds) {
+    auto op = mlir::dyn_cast<mlir::acc::DataBoundsOp>(b.getDefiningOp());
+    if (((op.getLowerbound() && !fir::getIntIfConstant(op.getLowerbound())) ||
+         (op.getUpperbound() && !fir::getIntIfConstant(op.getUpperbound()))) &&
+        op.getExtent() && !fir::getIntIfConstant(op.getExtent()))
+      return true;
+  }
+  return false;
+}
+
+static mlir::Value
+genReductionInitValue(fir::FirOpBuilder &builder, mlir::Location loc,
+                      mlir::Type ty, mlir::acc::ReductionOperator op,
+                      llvm::SmallVector<mlir::Value> &bounds) {
   if (op == mlir::acc::ReductionOperator::AccLand ||
       op == mlir::acc::ReductionOperator::AccLor ||
       op == mlir::acc::ReductionOperator::AccEqv ||
@@ -861,7 +876,8 @@ static mlir::Value genCombiner(fir::FirOpBuilder &builder, mlir::Location loc,
 
 mlir::acc::ReductionRecipeOp Fortran::lower::createOrGetReductionRecipe(
     fir::FirOpBuilder &builder, llvm::StringRef recipeName, mlir::Location loc,
-    mlir::Type ty, mlir::acc::ReductionOperator op) {
+    mlir::Type ty, mlir::acc::ReductionOperator op,
+    llvm::SmallVector<mlir::Value> &bounds) {
   mlir::ModuleOp mod =
       builder.getBlock()->getParent()->getParentOfType<mlir::ModuleOp>();
   if (auto recipe = mod.lookupSymbol<mlir::acc::ReductionRecipeOp>(recipeName))
@@ -874,7 +890,7 @@ mlir::acc::ReductionRecipeOp Fortran::lower::createOrGetReductionRecipe(
   builder.createBlock(&recipe.getInitRegion(), recipe.getInitRegion().end(),
                       {ty}, {loc});
   builder.setInsertionPointToEnd(&recipe.getInitRegion().back());
-  mlir::Value initValue = genReductionInitValue(builder, loc, ty, op);
+  mlir::Value initValue = genReductionInitValue(builder, loc, ty, op, bounds);
   builder.create<mlir::acc::YieldOp>(loc, initValue);
 
   builder.createBlock(&recipe.getCombinerRegion(),
@@ -888,20 +904,6 @@ mlir::acc::ReductionRecipeOp Fortran::lower::createOrGetReductionRecipe(
   return recipe;
 }
 
-/// Determine if the bounds represent a dynamic shape.
-bool hasDynamicShape(llvm::SmallVector<mlir::Value> &bounds) {
-  if (bounds.empty())
-    return false;
-  for (auto b : bounds) {
-    auto op = mlir::dyn_cast<mlir::acc::DataBoundsOp>(b.getDefiningOp());
-    if (((op.getLowerbound() && !fir::getIntIfConstant(op.getLowerbound())) ||
-         (op.getUpperbound() && !fir::getIntIfConstant(op.getUpperbound()))) &&
-        op.getExtent() && !fir::getIntIfConstant(op.getExtent()))
-      return true;
-  }
-  return false;
-}
-
 static void
 genReductions(const Fortran::parser::AccObjectListWithReduction &objectList,
               Fortran::lower::AbstractConverter &converter,
@@ -935,19 +937,19 @@ genReductions(const Fortran::parser::AccObjectListWithReduction &objectList,
          !bounds.empty()))
       TODO(operandLocation, "reduction with unsupported type");
 
+    mlir::Type retTy = getTypeFromBounds(bounds, baseAddr.getType());
     auto op = createDataEntryOp<mlir::acc::ReductionOp>(
         builder, operandLocation, baseAddr, asFortran, bounds,
-        /*structured=*/true, mlir::acc::DataClause::acc_reduction,
-        baseAddr.getType());
+        /*structured=*/true, mlir::acc::DataClause::acc_reduction, retTy);
     mlir::Type ty = fir::unwrapRefType(op.getAccPtr().getType());
     if (!fir::isa_trivial(ty))
-      ty = baseAddr.getType();
+      ty = retTy;
     std::string recipeName = fir::getTypeAsString(
         ty, converter.getKindMap(),
         ("reduction_" + stringifyReductionOperator(mlirOp)).str());
     mlir::acc::ReductionRecipeOp recipe =
-        Fortran::lower::createOrGetReductionRecipe(builder, recipeName,
-                                                   operandLocation, ty, mlirOp);
+        Fortran::lower::createOrGetReductionRecipe(
+            builder, recipeName, operandLocation, ty, mlirOp, bounds);
     reductionRecipes.push_back(mlir::SymbolRefAttr::get(
         builder.getContext(), recipe.getSymName().str()));
     reductionOperands.push_back(op.getAccPtr());

diff  --git a/flang/test/Lower/OpenACC/acc-reduction.f90 b/flang/test/Lower/OpenACC/acc-reduction.f90
index b84d2fa5ba9fe3..ae900c096ab185 100644
--- a/flang/test/Lower/OpenACC/acc-reduction.f90
+++ b/flang/test/Lower/OpenACC/acc-reduction.f90
@@ -2,6 +2,26 @@
 
 ! RUN: bbc -fopenacc -emit-fir %s -o - | FileCheck %s
 
+! CHECK-LABEL: acc.reduction.recipe @reduction_add_ref_10xi32 : !fir.ref<!fir.array<10xi32>> reduction_operator <add> init {
+! CHECK: ^bb0(%{{.*}}: !fir.ref<!fir.array<10xi32>>):
+! CHECK:   %[[CST:.*]] = arith.constant dense<0> : vector<10xi32>
+! CHECK:   acc.yield %[[CST]] : vector<10xi32>
+! CHECK: } combiner {
+! CHECK: ^bb0(%[[ARG0:.*]]: !fir.ref<!fir.array<10xi32>>, %[[ARG1:.*]]: !fir.ref<!fir.array<10xi32>>):
+! CHECK:   %[[LB:.*]] = arith.constant 0 : index
+! CHECK:   %[[UB:.*]] = arith.constant 9 : index
+! CHECK:   %[[STEP:.*]] = arith.constant 1 : index
+! CHECK:   fir.do_loop %[[IV:.*]] = %[[LB]] to %[[UB]] step %[[STEP]] {
+! CHECK:     %[[COORD1:.*]] = fir.coordinate_of %[[ARG0]], %[[IV]] : (!fir.ref<!fir.array<10xi32>>, index) -> !fir.ref<i32>
+! CHECK:     %[[COORD2:.*]] = fir.coordinate_of %[[ARG1]], %[[IV]] : (!fir.ref<!fir.array<10xi32>>, index) -> !fir.ref<i32>
+! CHECK:     %[[LOAD1:.*]] = fir.load %[[COORD1]] : !fir.ref<i32>
+! CHECK:     %[[LOAD2:.*]] = fir.load %[[COORD2]] : !fir.ref<i32>
+! CHECK:     %[[COMBINED:.*]] = arith.addi %[[LOAD1]], %[[LOAD2]] : i32
+! CHECK:     fir.store %[[COMBINED]] to %[[COORD1]] : !fir.ref<i32>
+! CHECK:   }
+! CHECK:   acc.yield %[[ARG0]] : !fir.ref<!fir.array<10xi32>>
+! CHECK: }
+
 ! CHECK-LABEL: acc.reduction.recipe @reduction_mul_z32 : !fir.complex<4> reduction_operator <mul> init {
 ! CHECK: ^bb0(%{{.*}}: !fir.complex<4>):
 ! CHECK:   %[[REAL:.*]] = arith.constant 1.000000e+00 : f32
@@ -804,3 +824,18 @@ subroutine acc_reduction_add_pointer(i)
 ! CHECK: %[[BOX_ADDR:.*]] = fir.box_addr %[[LOAD]] : (!fir.box<!fir.ptr<i32>>) -> !fir.ptr<i32>
 ! CHECK: %[[RED:.*]] = acc.reduction varPtr(%[[BOX_ADDR]] : !fir.ptr<i32>) -> !fir.ptr<i32> {name = "i"}
 ! CHECK: acc.parallel reduction(@reduction_add_i32 -> %[[RED]] : !fir.ptr<i32>)
+
+subroutine acc_reduction_add_static_slice(a)
+  integer :: a(100)
+  !$acc parallel reduction(+:a(11:20))
+  !$acc end parallel
+end subroutine
+
+! CHECK-LABEL: func.func @_QPacc_reduction_add_static_slice(
+! CHECK-SAME: %[[ARG0:.*]]: !fir.ref<!fir.array<100xi32>> {fir.bindc_name = "a"})
+! CHECK: %[[C1:.*]] = arith.constant 1 : index
+! CHECK: %[[LB:.*]] = arith.constant 10 : index
+! CHECK: %[[UB:.*]] = arith.constant 19 : index
+! CHECK: %[[BOUND:.*]] = acc.bounds lowerbound(%[[LB]] : index) upperbound(%[[UB]] : index) stride(%[[C1]] : index) startIdx(%[[C1]] : index)
+! CHECK: %[[RED:.*]] = acc.reduction varPtr(%[[ARG0]] : !fir.ref<!fir.array<100xi32>>) bounds(%[[BOUND]]) -> !fir.ref<!fir.array<10xi32>> {name = "a(11:20)"}
+! CHECK: acc.parallel reduction(@reduction_add_ref_10xi32 -> %[[RED]] : !fir.ref<!fir.array<10xi32>>)


        


More information about the flang-commits mailing list