[flang-commits] [flang] 722e960 - [flang] Add hlfir.as_expr character scalar codegen

Jean Perier via flang-commits flang-commits at lists.llvm.org
Thu Dec 8 00:32:16 PST 2022


Author: Jean Perier
Date: 2022-12-08T09:30:44+01:00
New Revision: 722e960b2486bec892356873c8c3cc44dfe4c312

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

LOG: [flang] Add hlfir.as_expr character scalar codegen

Creates a copy of the operand.

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

Added: 
    flang/test/HLFIR/as_expr-codegen.fir

Modified: 
    flang/lib/Optimizer/HLFIR/Transforms/BufferizeHLFIR.cpp

Removed: 
    


################################################################################
diff  --git a/flang/lib/Optimizer/HLFIR/Transforms/BufferizeHLFIR.cpp b/flang/lib/Optimizer/HLFIR/Transforms/BufferizeHLFIR.cpp
index f5a70c8112a1a..b0015a1ea01ce 100644
--- a/flang/lib/Optimizer/HLFIR/Transforms/BufferizeHLFIR.cpp
+++ b/flang/lib/Optimizer/HLFIR/Transforms/BufferizeHLFIR.cpp
@@ -94,6 +94,44 @@ static mlir::Value getBufferizedExprMustFreeFlag(mlir::Value bufferizedExpr) {
   TODO(bufferizedExpr.getLoc(), "general extract storage case");
 }
 
+static std::pair<hlfir::Entity, mlir::Value>
+createTempFromMold(mlir::Location loc, fir::FirOpBuilder &builder,
+                   hlfir::Entity mold) {
+  if (mold.isArray())
+    TODO(loc, "create temps from array mold");
+  llvm::SmallVector<mlir::Value> lenParams;
+  hlfir::genLengthParameters(loc, builder, mold, lenParams);
+  llvm::StringRef tmpName{".tmp"};
+  mlir::Value alloca =
+      builder.createTemporary(loc, mold.getFortranElementType(), tmpName,
+                              /*shape*/ llvm::None, lenParams);
+  auto declareOp = builder.create<hlfir::DeclareOp>(
+      loc, alloca, tmpName, /*shapeOrShift*/ mlir::Value{}, lenParams,
+      fir::FortranVariableFlagsAttr{});
+  mlir::Value falseVal = builder.createBool(loc, false);
+  return {hlfir::Entity{declareOp.getBase()}, falseVal};
+}
+
+struct AsExprOpConversion : public mlir::OpConversionPattern<hlfir::AsExprOp> {
+  using mlir::OpConversionPattern<hlfir::AsExprOp>::OpConversionPattern;
+  explicit AsExprOpConversion(mlir::MLIRContext *ctx)
+      : mlir::OpConversionPattern<hlfir::AsExprOp>{ctx} {}
+  mlir::LogicalResult
+  matchAndRewrite(hlfir::AsExprOp asExpr, OpAdaptor adaptor,
+                  mlir::ConversionPatternRewriter &rewriter) const override {
+    mlir::Location loc = asExpr->getLoc();
+    auto module = asExpr->getParentOfType<mlir::ModuleOp>();
+    fir::FirOpBuilder builder(rewriter, fir::getKindMapping(module));
+    hlfir::Entity source = hlfir::Entity{adaptor.getVar()};
+    auto [temp, cleanup] = createTempFromMold(loc, builder, source);
+    builder.create<hlfir::AssignOp>(loc, source, temp);
+    mlir::Value bufferizedExpr =
+        packageBufferizedExpr(loc, builder, temp, cleanup);
+    rewriter.replaceOp(asExpr, bufferizedExpr);
+    return mlir::success();
+  }
+};
+
 struct AssignOpConversion : public mlir::OpConversionPattern<hlfir::AssignOp> {
   using mlir::OpConversionPattern<hlfir::AssignOp>::OpConversionPattern;
   explicit AssignOpConversion(mlir::MLIRContext *ctx)
@@ -219,8 +257,9 @@ class BufferizeHLFIR : public hlfir::impl::BufferizeHLFIRBase<BufferizeHLFIR> {
     auto module = this->getOperation();
     auto *context = &getContext();
     mlir::RewritePatternSet patterns(context);
-    patterns.insert<AssignOpConversion, AssociateOpConversion,
-                    ConcatOpConversion, EndAssociateOpConversion>(context);
+    patterns
+        .insert<AsExprOpConversion, AssignOpConversion, AssociateOpConversion,
+                ConcatOpConversion, EndAssociateOpConversion>(context);
     mlir::ConversionTarget target(*context);
     target.addIllegalOp<hlfir::AssociateOp, hlfir::EndAssociateOp>();
     target.markUnknownOpDynamicallyLegal([](mlir::Operation *op) {

diff  --git a/flang/test/HLFIR/as_expr-codegen.fir b/flang/test/HLFIR/as_expr-codegen.fir
new file mode 100644
index 0000000000000..077b5dae32e6e
--- /dev/null
+++ b/flang/test/HLFIR/as_expr-codegen.fir
@@ -0,0 +1,37 @@
+// Test hlfir.as_expr code generation
+
+// RUN: fir-opt %s -bufferize-hlfir | FileCheck %s
+
+func.func @char_expr(%addr: !fir.ref<!fir.char<1,?>>, %len: index) {
+  %0:2 = hlfir.declare %addr typeparams %len {uniq_name = "c"} : (!fir.ref<!fir.char<1,?>>, index) -> (!fir.boxchar<1>, !fir.ref<!fir.char<1,?>>)
+  %1 = hlfir.as_expr %0#0 : (!fir.boxchar<1>) -> !hlfir.expr<!fir.char<1,?>>
+  return
+}
+// CHECK-LABEL:   func.func @char_expr(
+// CHECK-SAME:    %[[VAL_0:.*]]: !fir.ref<!fir.char<1,?>>,
+// CHECK-SAME:    %[[VAL_1:.*]]: index) {
+// CHECK:  %[[VAL_2:.*]]:2 = hlfir.declare %[[VAL_0]] typeparams %[[VAL_1]] {uniq_name = "c"} : (!fir.ref<!fir.char<1,?>>, index) -> (!fir.boxchar<1>, !fir.ref<!fir.char<1,?>>)
+// CHECK:  %[[VAL_3:.*]] = fir.alloca !fir.char<1,?>(%[[VAL_1]] : index) {bindc_name = ".tmp"}
+// CHECK:  %[[VAL_4:.*]]:2 = hlfir.declare %[[VAL_3]] typeparams %[[VAL_1]] {uniq_name = ".tmp"} : (!fir.ref<!fir.char<1,?>>, index) -> (!fir.boxchar<1>, !fir.ref<!fir.char<1,?>>)
+// CHECK:  %[[VAL_5:.*]] = arith.constant false
+// CHECK:  hlfir.assign %[[VAL_2]]#0 to %[[VAL_4]]#0 : !fir.boxchar<1>, !fir.boxchar<1>
+// CHECK:  %[[VAL_6:.*]] = fir.undefined tuple<!fir.boxchar<1>, i1>
+// CHECK:  %[[VAL_7:.*]] = fir.insert_value %[[VAL_6]], %[[VAL_5]], [1 : index] : (tuple<!fir.boxchar<1>, i1>, i1) -> tuple<!fir.boxchar<1>, i1>
+// CHECK:  %[[VAL_8:.*]] = fir.insert_value %[[VAL_7]], %[[VAL_4]]#0, [0 : index] : (tuple<!fir.boxchar<1>, i1>, !fir.boxchar<1>) -> tuple<!fir.boxchar<1>, i1>
+
+func.func @char_expr_2(%addr: !fir.ref<!fir.char<1,10>>, %len: index) {
+  %0:2 = hlfir.declare %addr typeparams %len {uniq_name = "c"} : (!fir.ref<!fir.char<1,10>>, index) -> (!fir.ref<!fir.char<1,10>>, !fir.ref<!fir.char<1,10>>)
+  %1 = hlfir.as_expr %0#0 : (!fir.ref<!fir.char<1,10>>) -> !hlfir.expr<!fir.char<1,10>>
+  return
+}
+// CHECK-LABEL:   func.func @char_expr_2(
+// CHECK-SAME:    %[[VAL_0:.*]]: !fir.ref<!fir.char<1,10>>,
+// CHECK-SAME:    %[[VAL_1:.*]]: index) {
+// CHECK:  %[[VAL_2:.*]] = fir.alloca !fir.char<1,10> {bindc_name = ".tmp"}
+// CHECK:  %[[VAL_3:.*]]:2 = hlfir.declare %[[VAL_0]] typeparams %[[VAL_1]] {uniq_name = "c"} : (!fir.ref<!fir.char<1,10>>, index) -> (!fir.ref<!fir.char<1,10>>, !fir.ref<!fir.char<1,10>>)
+// CHECK:  %[[VAL_4:.*]]:2 = hlfir.declare %[[VAL_2]] typeparams %[[VAL_1]] {uniq_name = ".tmp"} : (!fir.ref<!fir.char<1,10>>, index) -> (!fir.ref<!fir.char<1,10>>, !fir.ref<!fir.char<1,10>>)
+// CHECK:  %[[VAL_5:.*]] = arith.constant false
+// CHECK:  hlfir.assign %[[VAL_3]]#0 to %[[VAL_4]]#0 : !fir.ref<!fir.char<1,10>>, !fir.ref<!fir.char<1,10>>
+// CHECK:  %[[VAL_6:.*]] = fir.undefined tuple<!fir.ref<!fir.char<1,10>>, i1>
+// CHECK:  %[[VAL_7:.*]] = fir.insert_value %[[VAL_6]], %[[VAL_5]], [1 : index] : (tuple<!fir.ref<!fir.char<1,10>>, i1>, i1) -> tuple<!fir.ref<!fir.char<1,10>>, i1>
+// CHECK:  %[[VAL_8:.*]] = fir.insert_value %[[VAL_7]], %[[VAL_4]]#0, [0 : index] : (tuple<!fir.ref<!fir.char<1,10>>, i1>, !fir.ref<!fir.char<1,10>>) -> tuple<!fir.ref<!fir.char<1,10>>, i1>


        


More information about the flang-commits mailing list