[flang-commits] [flang] 1ed5a90 - [fir] Add conversion patterns for slice, shape, shapeshift and shift ops

Valentin Clement via flang-commits flang-commits at lists.llvm.org
Wed Nov 17 01:36:16 PST 2021


Author: Valentin Clement
Date: 2021-11-17T10:35:56+01:00
New Revision: 1ed5a90f70eb04997a27026dfc2d9cae1d8cfa75

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

LOG: [fir] Add conversion patterns for slice, shape, shapeshift and shift ops

The information in these perations is used by other operation.
At this point they should not have anymore uses.

This patch is part of the upstreaming effort from fir-dev branch.

Reviewed By: kiranchandramohan

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

Co-authored-by: Eric Schweitz <eschweitz at nvidia.com>

Added: 
    

Modified: 
    flang/lib/Optimizer/CodeGen/CodeGen.cpp
    flang/test/Fir/convert-to-llvm-invalid.fir
    flang/test/Fir/convert-to-llvm.fir

Removed: 
    


################################################################################
diff  --git a/flang/lib/Optimizer/CodeGen/CodeGen.cpp b/flang/lib/Optimizer/CodeGen/CodeGen.cpp
index 13733113ae330..899315a1286e8 100644
--- a/flang/lib/Optimizer/CodeGen/CodeGen.cpp
+++ b/flang/lib/Optimizer/CodeGen/CodeGen.cpp
@@ -1469,6 +1469,42 @@ struct NegcOpConversion : public FIROpConversion<fir::NegcOp> {
   }
 };
 
+/// Conversion pattern for operation that must be dead. The information in these
+/// operations is used by other operation. At this point they should not have
+/// anymore uses.
+/// These operations are normally dead after the pre-codegen pass.
+template <typename FromOp>
+struct MustBeDeadConversion : public FIROpConversion<FromOp> {
+  explicit MustBeDeadConversion(fir::LLVMTypeConverter &lowering)
+      : FIROpConversion<FromOp>(lowering) {}
+  using OpAdaptor = typename FromOp::Adaptor;
+
+  mlir::LogicalResult
+  matchAndRewrite(FromOp op, OpAdaptor adaptor,
+                  mlir::ConversionPatternRewriter &rewriter) const final {
+    if (!op->getUses().empty())
+      return rewriter.notifyMatchFailure(op, "op must be dead");
+    rewriter.eraseOp(op);
+    return success();
+  }
+};
+
+struct ShapeOpConversion : public MustBeDeadConversion<fir::ShapeOp> {
+  using MustBeDeadConversion::MustBeDeadConversion;
+};
+
+struct ShapeShiftOpConversion : public MustBeDeadConversion<fir::ShapeShiftOp> {
+  using MustBeDeadConversion::MustBeDeadConversion;
+};
+
+struct ShiftOpConversion : public MustBeDeadConversion<fir::ShiftOp> {
+  using MustBeDeadConversion::MustBeDeadConversion;
+};
+
+struct SliceOpConversion : public MustBeDeadConversion<fir::SliceOp> {
+  using MustBeDeadConversion::MustBeDeadConversion;
+};
+
 /// `fir.is_present` -->
 /// ```
 ///  %0 = llvm.mlir.constant(0 : i64)
@@ -1635,10 +1671,11 @@ class FIRToLLVMLowering : public fir::FIRToLLVMLoweringBase<FIRToLLVMLowering> {
         GlobalOpConversion, InsertOnRangeOpConversion, InsertValueOpConversion,
         IsPresentOpConversion, LoadOpConversion, NegcOpConversion,
         MulcOpConversion, SelectCaseOpConversion, SelectOpConversion,
-        SelectRankOpConversion, SelectTypeOpConversion, StoreOpConversion,
-        StringLitOpConversion, SubcOpConversion, UnboxCharOpConversion,
-        UndefOpConversion, UnreachableOpConversion, ZeroOpConversion>(
-        typeConverter);
+        SelectRankOpConversion, SelectTypeOpConversion, ShapeOpConversion,
+        ShapeShiftOpConversion, ShiftOpConversion, SliceOpConversion,
+        StoreOpConversion, StringLitOpConversion, SubcOpConversion,
+        UnboxCharOpConversion, UndefOpConversion, UnreachableOpConversion,
+        ZeroOpConversion>(typeConverter);
     mlir::populateStdToLLVMConversionPatterns(typeConverter, pattern);
     mlir::arith::populateArithmeticToLLVMConversionPatterns(typeConverter,
                                                             pattern);

diff  --git a/flang/test/Fir/convert-to-llvm-invalid.fir b/flang/test/Fir/convert-to-llvm-invalid.fir
index 6aeb208451089..c8ee4e94b91ee 100644
--- a/flang/test/Fir/convert-to-llvm-invalid.fir
+++ b/flang/test/Fir/convert-to-llvm-invalid.fir
@@ -100,3 +100,51 @@ func @gentypedesc() {
 
 // expected-error at +1{{'fir.dt_entry' op expects parent op 'fir.dispatch_table'}}
 fir.dt_entry "method", @method_impl
+
+// -----
+
+// Test `fir.shape` conversion failure because the op has uses.
+
+func @shape_not_dead(%arg0: !fir.ref<!fir.array<?x?xf32>>, %i: index, %j: index) {
+  %c0 = arith.constant 1 : index
+  // expected-error at +1{{failed to legalize operation 'fir.shape'}}
+  %0 = fir.shape %c0, %c0 : (index, index) -> !fir.shape<2>
+  %1 = fir.array_coor %arg0(%0) %i, %j : (!fir.ref<!fir.array<?x?xf32>>, !fir.shape<2>, index, index) -> !fir.ref<f32>
+  return
+}
+
+// -----
+
+// Test `fir.slice` conversion failure because the op has uses.
+
+func @slice_not_dead(%arg0: !fir.ref<!fir.array<?x?xf32>>, %i: index, %j: index) {
+  %c0 = arith.constant 1 : index
+  // expected-error at +1{{failed to legalize operation 'fir.slice'}}
+  %0 = fir.slice %c0, %c0, %c0, %c0, %c0, %c0 : (index, index, index, index, index, index) -> !fir.slice<2>
+  %1 = fir.array_coor %arg0[%0] %i, %j : (!fir.ref<!fir.array<?x?xf32>>, !fir.slice<2>, index, index) -> !fir.ref<f32>
+  return
+}
+
+// -----
+
+// Test `fir.shift` conversion failure because the op has uses.
+
+func @shift_not_dead(%arg0: !fir.box<!fir.array<?xf32>>, %i: index) {
+  %c0 = arith.constant 1 : index
+  // expected-error at +1{{failed to legalize operation 'fir.shift'}}
+  %0 = fir.shift %c0 : (index) -> !fir.shift<1>
+  %1 = fir.array_coor %arg0(%0) %i : (!fir.box<!fir.array<?xf32>>, !fir.shift<1>, index) -> !fir.ref<f32>
+  return
+}
+
+// -----
+
+// Test `fir.shape_shift` conversion failure because the op has uses.
+
+func @shape_shift_not_dead(%arg0: !fir.ref<!fir.array<?x?xf32>>, %i: index, %j: index) {
+  %c0 = arith.constant 1 : index
+  // expected-error at +1{{failed to legalize operation 'fir.shape_shift'}}
+  %0 = fir.shape_shift %c0, %c0, %c0, %c0 : (index, index, index, index) -> !fir.shapeshift<2>
+  %1 = fir.array_coor %arg0(%0) %i, %j : (!fir.ref<!fir.array<?x?xf32>>, !fir.shapeshift<2>, index, index) -> !fir.ref<f32>
+  return
+}

diff  --git a/flang/test/Fir/convert-to-llvm.fir b/flang/test/Fir/convert-to-llvm.fir
index 5a9b8e12044d0..5cbee81653820 100644
--- a/flang/test/Fir/convert-to-llvm.fir
+++ b/flang/test/Fir/convert-to-llvm.fir
@@ -1271,3 +1271,51 @@ func @string_lit1() {
 
 // CHECK-LABEL: llvm.func @string_lit1
 // %{{.*}} = llvm.mlir.constant(dense<[158, 2345]> : vector<2xi16>) : !llvm.array<2 x i16>
+
+// -----
+
+// Test must be dead conversion.
+
+func @dead_shift() {
+  %c0 = arith.constant 0 : index
+  %0 = fir.shift %c0 : (index) -> !fir.shift<1>
+  return
+}
+
+// CHECK-LABEL: llvm.func @dead_shift
+// CHECK-NOT: fir.shift
+// CHECK: %{{.*}} = llvm.mlir.constant(0 : index) : i{{.*}}
+// CHECK-NEXT: llvm.return
+
+func @dead_shape() {
+  %c0 = arith.constant 0 : index
+  %0 = fir.shape %c0 : (index) -> !fir.shape<1>
+  return
+}
+
+// CHECK-LABEL: llvm.func @dead_shape
+// CHECK-NOT: fir.shape
+// CHECK: %{{.*}} = llvm.mlir.constant(0 : index) : i{{.*}}
+// CHECK-NEXT: llvm.return
+
+func @dead_shapeshift() {
+  %c0 = arith.constant 0 : index
+  %0 = fir.shape_shift %c0, %c0 : (index, index) -> !fir.shapeshift<1>
+  return
+}
+
+// CHECK-LABEL: llvm.func @dead_shapeshift
+// CHECK-NOT: fir.shape_shift
+// CHECK: %{{.*}} = llvm.mlir.constant(0 : index) : i{{.*}}
+// CHECK-NEXT: llvm.return
+
+func @dead_slice() {
+  %c0 = arith.constant 0 : index
+  %0 = fir.slice %c0, %c0, %c0 : (index, index, index) -> !fir.slice<1>
+  return
+}
+
+// CHECK-LABEL: llvm.func @dead_slice
+// CHECK-NOT: fir.slice
+// CHECK: %{{.*}} = llvm.mlir.constant(0 : index) : i{{.*}}
+// CHECK-NEXT: llvm.return


        


More information about the flang-commits mailing list