[flang-commits] [flang] [flang] Copy back only modified data when unpacking repacked arrays (PR #228543)

via flang-commits flang-commits at lists.llvm.org
Fri Oct 2 13:01:33 PDT 2026


llvmorg-github-actions[bot] wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-flang-codegen

Author: Eugene Epshteyn (eugeneepshteyn)

<details>
<summary>Changes</summary>

With `-frepack-arrays`, `fir.unpack_array` copied the contiguous temporary back into the original array unconditionally. Since #<!-- -->222986, a named constant's own storage can be the actual argument, so the copy-back stored into read-only memory and the program crashed, even though the callee never modified the data. For example:

```fortran
module callees
contains
  subroutine take(a)
    integer :: a(:)
    print *, sum(a)
  end subroutine
end module
program repack_const
  use callees
  integer, parameter :: c(3) = [1, 0, 2]
  call take(c(::2))
end program
```

segfaults when compiled with `flang -frepack-arrays`.

Lower the copy-back to `CopyOutAssignDirect`, the runtime that the caller-side copy-out already uses. The repacking temporary is a bitwise copy of the original, so `CopyOutAssignDirect` stores only the data that the callee modified (see #<!-- -->222101), and nothing at all when the data is unchanged. `FLANG_RT_COPYOUT_MODIFIED_ONLY=0` restores the unconditional copy, as it does for the caller-side copy-out.

Assisted-by: AI


---

Patch is 26.23 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/228543.diff


3 Files Affected:

- (modified) flang/lib/Optimizer/CodeGen/LowerRepackArrays.cpp (+16-6) 
- (modified) flang/test/Integration/cold_array_repacking.f90 (+1-1) 
- (modified) flang/test/Transforms/lower-repack-arrays.fir (+45-30) 


``````````diff
diff --git a/flang/lib/Optimizer/CodeGen/LowerRepackArrays.cpp b/flang/lib/Optimizer/CodeGen/LowerRepackArrays.cpp
index 81488d75d0ab6..e5eb819fdb6b8 100644
--- a/flang/lib/Optimizer/CodeGen/LowerRepackArrays.cpp
+++ b/flang/lib/Optimizer/CodeGen/LowerRepackArrays.cpp
@@ -21,8 +21,8 @@
 ///
 /// A fir.unpack_array operations is converted into a check
 /// of whether the original and the temporary arrays are different
-/// memory. When the check passes, the temporary array might be
-/// shallow-copied into the original array, and then the temporary
+/// memory. When the check passes, the modified elements of the temporary
+/// array might be copied into the original array, and then the temporary
 /// array is deallocated (if it was allocated in stack memory,
 /// then there is no explicit deallocation).
 //===----------------------------------------------------------------------===//
@@ -33,6 +33,7 @@
 #include "flang/Optimizer/Builder/FIRBuilder.h"
 #include "flang/Optimizer/Builder/MutableBox.h"
 #include "flang/Optimizer/Builder/Runtime/Allocatable.h"
+#include "flang/Optimizer/Builder/Runtime/Assign.h"
 #include "flang/Optimizer/Builder/Runtime/Transformational.h"
 #include "flang/Optimizer/Builder/Todo.h"
 #include "flang/Optimizer/Dialect/FIRDialect.h"
@@ -344,10 +345,19 @@ UnpackArrayConversion::matchAndRewrite(fir::UnpackArrayOp op,
                                            tempAddr, originalAddr);
     builder.genIfThen(loc, isNotSame)
         .genThen([&]() {
-          // Copy from temporary to the original.
-          if (!op.getNoCopy())
-            fir::runtime::genShallowCopy(builder, loc, originalBox, tempBox,
-                                         /*resultIsAllocated=*/true);
+          // Copy from temporary to the original. The temporary was
+          // created as a bitwise copy of the original, so use the same
+          // copy-out runtime as the caller-side copy-out: it does not store
+          // the data that the callee did not modify. This keeps the copy
+          // from writing into read-only storage when the original is not
+          // definable (e.g., a named constant) and was not modified.
+          if (!op.getNoCopy()) {
+            mlir::Value tempBoxAddr =
+                builder.createTemporary(loc, tempBox.getType());
+            fir::StoreOp::create(builder, loc, tempBox, tempBoxAddr);
+            fir::runtime::genCopyOutAssignDirect(builder, loc, originalBox,
+                                                 tempBoxAddr);
+          }
 
           // Deallocate, if it was allocated in heap.
           // Note that the stack attribute does not always mean
diff --git a/flang/test/Integration/cold_array_repacking.f90 b/flang/test/Integration/cold_array_repacking.f90
index 06edd38738859..67090b504892e 100644
--- a/flang/test/Integration/cold_array_repacking.f90
+++ b/flang/test/Integration/cold_array_repacking.f90
@@ -30,7 +30,7 @@
 ! CHECK:  [[BB48]]:
 ! CHECK:    br i1 [[TMP55:.*]], label %[[BB56:.*]], label %[[NO_COPY_BACK:.*]], !prof [[PROF2]]
 ! CHECK:  [[BB56]]:
-! CHECK:    call void @_FortranAShallowCopyDirect
+! CHECK:    call void @_FortranACopyOutAssignDirect
 ! CHECK:    br label %[[NO_COPY_BACK]]
 ! CHECK:  [[NO_COPY_BACK]]:
 ! CHECK-NEXT: br label %[[BB57]]
diff --git a/flang/test/Transforms/lower-repack-arrays.fir b/flang/test/Transforms/lower-repack-arrays.fir
index 999d040a4a770..f82ca75f53094 100644
--- a/flang/test/Transforms/lower-repack-arrays.fir
+++ b/flang/test/Transforms/lower-repack-arrays.fir
@@ -52,11 +52,12 @@ func.func @_QPtest1(%arg0: !fir.box<!fir.array<?x?xf32>> {fir.bindc_name = "x"})
 // CHECK:             %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (!fir.heap<!fir.array<?x?xf32>>) -> index
 // CHECK:             %[[VAL_33:.*]] = arith.cmpi ne, %[[VAL_30]], %[[VAL_32]] : index
 // CHECK:             fir.if %[[VAL_33]] weights([0, 1]) {
+// CHECK:               fir.store %[[VAL_8]] to %[[TEMP_BOX:.*]] : !fir.ref<!fir.box<!fir.array<?x?xf32>>>
 // CHECK:               %[[VAL_34:.*]] = fir.address_of(@{{_QQcl.*}}
 // CHECK:               %[[VAL_35:.*]] = fir.convert %[[VAL_0]] : (!fir.box<!fir.array<?x?xf32>>) -> !fir.box<none>
-// CHECK:               %[[VAL_36:.*]] = fir.convert %[[VAL_8]] : (!fir.box<!fir.array<?x?xf32>>) -> !fir.box<none>
+// CHECK:               %[[VAL_36:.*]] = fir.convert %[[TEMP_BOX]] : (!fir.ref<!fir.box<!fir.array<?x?xf32>>>) -> !fir.ref<!fir.box<none>>
 // CHECK:               %[[VAL_37:.*]] = fir.convert %[[VAL_34]] : (!fir.ref<!fir.char<1,{{.*}}>>) -> !fir.ref<i8>
-// CHECK:               fir.call @_FortranAShallowCopyDirect(%[[VAL_35]], %[[VAL_36]], %[[VAL_37]], %[[VAL_1]]) : (!fir.box<none>, !fir.box<none>, !fir.ref<i8>, i32) -> ()
+// CHECK:               fir.call @_FortranACopyOutAssignDirect(%[[VAL_35]], %[[VAL_36]], %[[VAL_37]], %[[VAL_1]]) : (!fir.box<none>, !fir.ref<!fir.box<none>>, !fir.ref<i8>, i32) -> ()
 // CHECK:               fir.freemem %[[VAL_29]] : !fir.heap<!fir.array<?x?xf32>>
 // CHECK:             }
 // CHECK:           }
@@ -116,11 +117,12 @@ func.func @_QPtest1_whole(%arg0: !fir.box<!fir.array<?x?xf32>> {fir.bindc_name =
 // CHECK:             %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (!fir.heap<!fir.array<?x?xf32>>) -> index
 // CHECK:             %[[VAL_33:.*]] = arith.cmpi ne, %[[VAL_30]], %[[VAL_32]] : index
 // CHECK:             fir.if %[[VAL_33]] weights([0, 1]) {
+// CHECK:               fir.store %[[VAL_8]] to %[[TEMP_BOX:.*]] : !fir.ref<!fir.box<!fir.array<?x?xf32>>>
 // CHECK:               %[[VAL_34:.*]] = fir.address_of(@{{_QQcl.*}}
 // CHECK:               %[[VAL_35:.*]] = fir.convert %[[VAL_0]] : (!fir.box<!fir.array<?x?xf32>>) -> !fir.box<none>
-// CHECK:               %[[VAL_36:.*]] = fir.convert %[[VAL_8]] : (!fir.box<!fir.array<?x?xf32>>) -> !fir.box<none>
+// CHECK:               %[[VAL_36:.*]] = fir.convert %[[TEMP_BOX]] : (!fir.ref<!fir.box<!fir.array<?x?xf32>>>) -> !fir.ref<!fir.box<none>>
 // CHECK:               %[[VAL_37:.*]] = fir.convert %[[VAL_34]] : (!fir.ref<!fir.char<1,{{.*}}>>) -> !fir.ref<i8>
-// CHECK:               fir.call @_FortranAShallowCopyDirect(%[[VAL_35]], %[[VAL_36]], %[[VAL_37]], %[[VAL_1]]) : (!fir.box<none>, !fir.box<none>, !fir.ref<i8>, i32) -> ()
+// CHECK:               fir.call @_FortranACopyOutAssignDirect(%[[VAL_35]], %[[VAL_36]], %[[VAL_37]], %[[VAL_1]]) : (!fir.box<none>, !fir.ref<!fir.box<none>>, !fir.ref<i8>, i32) -> ()
 // CHECK:             }
 // CHECK:           }
 // CHECK:           return
@@ -231,11 +233,12 @@ func.func @_QPtest1_out(%arg0: !fir.box<!fir.array<?x?xf32>> {fir.bindc_name = "
 // CHECK:             %[[VAL_27:.*]] = fir.convert %[[VAL_26]] : (!fir.heap<!fir.array<?x?xf32>>) -> index
 // CHECK:             %[[VAL_28:.*]] = arith.cmpi ne, %[[VAL_25]], %[[VAL_27]] : index
 // CHECK:             fir.if %[[VAL_28]] weights([0, 1]) {
+// CHECK:               fir.store %[[VAL_7]] to %[[TEMP_BOX:.*]] : !fir.ref<!fir.box<!fir.array<?x?xf32>>>
 // CHECK:               %[[VAL_29:.*]] = fir.address_of(@{{_QQcl.*}}
 // CHECK:               %[[VAL_30:.*]] = fir.convert %[[VAL_0]] : (!fir.box<!fir.array<?x?xf32>>) -> !fir.box<none>
-// CHECK:               %[[VAL_31:.*]] = fir.convert %[[VAL_7]] : (!fir.box<!fir.array<?x?xf32>>) -> !fir.box<none>
+// CHECK:               %[[VAL_31:.*]] = fir.convert %[[TEMP_BOX]] : (!fir.ref<!fir.box<!fir.array<?x?xf32>>>) -> !fir.ref<!fir.box<none>>
 // CHECK:               %[[VAL_32:.*]] = fir.convert %[[VAL_29]] : (!fir.ref<!fir.char<1,{{.*}}>>) -> !fir.ref<i8>
-// CHECK:               fir.call @_FortranAShallowCopyDirect(%[[VAL_30]], %[[VAL_31]], %[[VAL_32]], %[[VAL_1]]) : (!fir.box<none>, !fir.box<none>, !fir.ref<i8>, i32) -> ()
+// CHECK:               fir.call @_FortranACopyOutAssignDirect(%[[VAL_30]], %[[VAL_31]], %[[VAL_32]], %[[VAL_1]]) : (!fir.box<none>, !fir.ref<!fir.box<none>>, !fir.ref<i8>, i32) -> ()
 // CHECK:               fir.freemem %[[VAL_24]] : !fir.heap<!fir.array<?x?xf32>>
 // CHECK:             }
 // CHECK:           }
@@ -306,11 +309,12 @@ func.func @_QPtest2(%arg0: !fir.ref<i32> {fir.bindc_name = "n"}, %arg1: !fir.box
 // CHECK:             %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (!fir.heap<!fir.array<?x?x!fir.char<1,?>>>) -> index
 // CHECK:             %[[VAL_39:.*]] = arith.cmpi ne, %[[VAL_36]], %[[VAL_38]] : index
 // CHECK:             fir.if %[[VAL_39]] weights([0, 1]) {
+// CHECK:               fir.store %[[VAL_14]] to %[[TEMP_BOX:.*]] : !fir.ref<!fir.box<!fir.array<?x?x!fir.char<1,?>>>>
 // CHECK:               %[[VAL_40:.*]] = fir.address_of(@{{_QQcl.*}}
 // CHECK:               %[[VAL_41:.*]] = fir.convert %[[VAL_1]] : (!fir.box<!fir.array<?x?x!fir.char<1,?>>>) -> !fir.box<none>
-// CHECK:               %[[VAL_42:.*]] = fir.convert %[[VAL_14]] : (!fir.box<!fir.array<?x?x!fir.char<1,?>>>) -> !fir.box<none>
+// CHECK:               %[[VAL_42:.*]] = fir.convert %[[TEMP_BOX]] : (!fir.ref<!fir.box<!fir.array<?x?x!fir.char<1,?>>>>) -> !fir.ref<!fir.box<none>>
 // CHECK:               %[[VAL_43:.*]] = fir.convert %[[VAL_40]] : (!fir.ref<!fir.char<1,{{.*}}>>) -> !fir.ref<i8>
-// CHECK:               fir.call @_FortranAShallowCopyDirect(%[[VAL_41]], %[[VAL_42]], %[[VAL_43]], %[[VAL_2]]) : (!fir.box<none>, !fir.box<none>, !fir.ref<i8>, i32) -> ()
+// CHECK:               fir.call @_FortranACopyOutAssignDirect(%[[VAL_41]], %[[VAL_42]], %[[VAL_43]], %[[VAL_2]]) : (!fir.box<none>, !fir.ref<!fir.box<none>>, !fir.ref<i8>, i32) -> ()
 // CHECK:               fir.freemem %[[VAL_35]] : !fir.heap<!fir.array<?x?x!fir.char<1,?>>>
 // CHECK:             }
 // CHECK:           }
@@ -381,11 +385,12 @@ func.func @_QPtest2_stack(%arg0: !fir.ref<i32> {fir.bindc_name = "n"}, %arg1: !f
 // CHECK:             %[[VAL_38:.*]] = fir.convert %[[VAL_37]] : (!fir.heap<!fir.array<?x?x!fir.char<1,?>>>) -> index
 // CHECK:             %[[VAL_39:.*]] = arith.cmpi ne, %[[VAL_36]], %[[VAL_38]] : index
 // CHECK:             fir.if %[[VAL_39]] weights([0, 1]) {
+// CHECK:               fir.store %[[VAL_14]] to %[[TEMP_BOX:.*]] : !fir.ref<!fir.box<!fir.array<?x?x!fir.char<1,?>>>>
 // CHECK:               %[[VAL_40:.*]] = fir.address_of(@{{_QQcl.*}}
 // CHECK:               %[[VAL_41:.*]] = fir.convert %[[VAL_1]] : (!fir.box<!fir.array<?x?x!fir.char<1,?>>>) -> !fir.box<none>
-// CHECK:               %[[VAL_42:.*]] = fir.convert %[[VAL_14]] : (!fir.box<!fir.array<?x?x!fir.char<1,?>>>) -> !fir.box<none>
+// CHECK:               %[[VAL_42:.*]] = fir.convert %[[TEMP_BOX]] : (!fir.ref<!fir.box<!fir.array<?x?x!fir.char<1,?>>>>) -> !fir.ref<!fir.box<none>>
 // CHECK:               %[[VAL_43:.*]] = fir.convert %[[VAL_40]] : (!fir.ref<!fir.char<1,{{.*}}>>) -> !fir.ref<i8>
-// CHECK:               fir.call @_FortranAShallowCopyDirect(%[[VAL_41]], %[[VAL_42]], %[[VAL_43]], %[[VAL_2]]) : (!fir.box<none>, !fir.box<none>, !fir.ref<i8>, i32) -> ()
+// CHECK:               fir.call @_FortranACopyOutAssignDirect(%[[VAL_41]], %[[VAL_42]], %[[VAL_43]], %[[VAL_2]]) : (!fir.box<none>, !fir.ref<!fir.box<none>>, !fir.ref<i8>, i32) -> ()
 // CHECK:             }
 // CHECK:           }
 // CHECK:           return
@@ -445,11 +450,12 @@ func.func @_QPtest3(%arg0: !fir.box<!fir.array<?x?x!fir.char<1,?>>> {fir.bindc_n
 // CHECK:             %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (!fir.heap<!fir.array<?x?x!fir.char<1,?>>>) -> index
 // CHECK:             %[[VAL_34:.*]] = arith.cmpi ne, %[[VAL_31]], %[[VAL_33]] : index
 // CHECK:             fir.if %[[VAL_34]] weights([0, 1]) {
+// CHECK:               fir.store %[[VAL_8]] to %[[TEMP_BOX:.*]] : !fir.ref<!fir.box<!fir.array<?x?x!fir.char<1,?>>>>
 // CHECK:               %[[VAL_35:.*]] = fir.address_of(@{{_QQcl.*}}
 // CHECK:               %[[VAL_36:.*]] = fir.convert %[[VAL_0]] : (!fir.box<!fir.array<?x?x!fir.char<1,?>>>) -> !fir.box<none>
-// CHECK:               %[[VAL_37:.*]] = fir.convert %[[VAL_8]] : (!fir.box<!fir.array<?x?x!fir.char<1,?>>>) -> !fir.box<none>
+// CHECK:               %[[VAL_37:.*]] = fir.convert %[[TEMP_BOX]] : (!fir.ref<!fir.box<!fir.array<?x?x!fir.char<1,?>>>>) -> !fir.ref<!fir.box<none>>
 // CHECK:               %[[VAL_38:.*]] = fir.convert %[[VAL_35]] : (!fir.ref<!fir.char<1,{{.*}}>>) -> !fir.ref<i8>
-// CHECK:               fir.call @_FortranAShallowCopyDirect(%[[VAL_36]], %[[VAL_37]], %[[VAL_38]], %[[VAL_1]]) : (!fir.box<none>, !fir.box<none>, !fir.ref<i8>, i32) -> ()
+// CHECK:               fir.call @_FortranACopyOutAssignDirect(%[[VAL_36]], %[[VAL_37]], %[[VAL_38]], %[[VAL_1]]) : (!fir.box<none>, !fir.ref<!fir.box<none>>, !fir.ref<i8>, i32) -> ()
 // CHECK:               fir.freemem %[[VAL_30]] : !fir.heap<!fir.array<?x?x!fir.char<1,?>>>
 // CHECK:             }
 // CHECK:           }
@@ -510,11 +516,12 @@ func.func @_QPtest3_stack(%arg0: !fir.box<!fir.array<?x?x!fir.char<1,?>>> {fir.b
 // CHECK:             %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (!fir.heap<!fir.array<?x?x!fir.char<1,?>>>) -> index
 // CHECK:             %[[VAL_34:.*]] = arith.cmpi ne, %[[VAL_31]], %[[VAL_33]] : index
 // CHECK:             fir.if %[[VAL_34]] weights([0, 1]) {
+// CHECK:               fir.store %[[VAL_8]] to %[[TEMP_BOX:.*]] : !fir.ref<!fir.box<!fir.array<?x?x!fir.char<1,?>>>>
 // CHECK:               %[[VAL_35:.*]] = fir.address_of(@{{_QQcl.*}}
 // CHECK:               %[[VAL_36:.*]] = fir.convert %[[VAL_0]] : (!fir.box<!fir.array<?x?x!fir.char<1,?>>>) -> !fir.box<none>
-// CHECK:               %[[VAL_37:.*]] = fir.convert %[[VAL_8]] : (!fir.box<!fir.array<?x?x!fir.char<1,?>>>) -> !fir.box<none>
+// CHECK:               %[[VAL_37:.*]] = fir.convert %[[TEMP_BOX]] : (!fir.ref<!fir.box<!fir.array<?x?x!fir.char<1,?>>>>) -> !fir.ref<!fir.box<none>>
 // CHECK:               %[[VAL_38:.*]] = fir.convert %[[VAL_35]] : (!fir.ref<!fir.char<1,{{.*}}>>) -> !fir.ref<i8>
-// CHECK:               fir.call @_FortranAShallowCopyDirect(%[[VAL_36]], %[[VAL_37]], %[[VAL_38]], %[[VAL_1]]) : (!fir.box<none>, !fir.box<none>, !fir.ref<i8>, i32) -> ()
+// CHECK:               fir.call @_FortranACopyOutAssignDirect(%[[VAL_36]], %[[VAL_37]], %[[VAL_38]], %[[VAL_1]]) : (!fir.box<none>, !fir.ref<!fir.box<none>>, !fir.ref<i8>, i32) -> ()
 // CHECK:             }
 // CHECK:           }
 // CHECK:           return
@@ -575,11 +582,12 @@ func.func @_QPtest4(%arg0: !fir.box<!fir.array<?x?x!fir.char<1,10>>> {fir.bindc_
 // CHECK:             %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (!fir.heap<!fir.array<?x?x!fir.char<1,10>>>) -> index
 // CHECK:             %[[VAL_34:.*]] = arith.cmpi ne, %[[VAL_31]], %[[VAL_33]] : index
 // CHECK:             fir.if %[[VAL_34]] weights([0, 1]) {
+// CHECK:               fir.store %[[VAL_9]] to %[[TEMP_BOX:.*]] : !fir.ref<!fir.box<!fir.array<?x?x!fir.char<1,10>>>>
 // CHECK:               %[[VAL_35:.*]] = fir.address_of(@{{_QQcl.*}}
 // CHECK:               %[[VAL_36:.*]] = fir.convert %[[VAL_0]] : (!fir.box<!fir.array<?x?x!fir.char<1,10>>>) -> !fir.box<none>
-// CHECK:               %[[VAL_37:.*]] = fir.convert %[[VAL_9]] : (!fir.box<!fir.array<?x?x!fir.char<1,10>>>) -> !fir.box<none>
+// CHECK:               %[[VAL_37:.*]] = fir.convert %[[TEMP_BOX]] : (!fir.ref<!fir.box<!fir.array<?x?x!fir.char<1,10>>>>) -> !fir.ref<!fir.box<none>>
 // CHECK:               %[[VAL_38:.*]] = fir.convert %[[VAL_35]] : (!fir.ref<!fir.char<1,{{.*}}>>) -> !fir.ref<i8>
-// CHECK:               fir.call @_FortranAShallowCopyDirect(%[[VAL_36]], %[[VAL_37]], %[[VAL_38]], %[[VAL_1]]) : (!fir.box<none>, !fir.box<none>, !fir.ref<i8>, i32) -> ()
+// CHECK:               fir.call @_FortranACopyOutAssignDirect(%[[VAL_36]], %[[VAL_37]], %[[VAL_38]], %[[VAL_1]]) : (!fir.box<none>, !fir.ref<!fir.box<none>>, !fir.ref<i8>, i32) -> ()
 // CHECK:               fir.freemem %[[VAL_30]] : !fir.heap<!fir.array<?x?x!fir.char<1,10>>>
 // CHECK:             }
 // CHECK:           }
@@ -641,11 +649,12 @@ func.func @_QPtest4_stack(%arg0: !fir.box<!fir.array<?x?x!fir.char<1,10>>> {fir.
 // CHECK:             %[[VAL_33:.*]] = fir.convert %[[VAL_32]] : (!fir.heap<!fir.array<?x?x!fir.char<1,10>>>) -> index
 // CHECK:             %[[VAL_34:.*]] = arith.cmpi ne, %[[VAL_31]], %[[VAL_33]] : index
 // CHECK:             fir.if %[[VAL_34]] weights([0, 1]) {
+// CHECK:               fir.store %[[VAL_9]] to %[[TEMP_BOX:.*]] : !fir.ref<!fir.box<!fir.array<?x?x!fir.char<1,10>>>>
 // CHECK:               %[[VAL_35:.*]] = fir.address_of(@{{_QQcl.*}}
 // CHECK:               %[[VAL_36:.*]] = fir.convert %[[VAL_0]] : (!fir.box<!fir.array<?x?x!fir.char<1,10>>>) -> !fir.box<none>
-// CHECK:               %[[VAL_37:.*]] = fir.convert %[[VAL_9]] : (!fir.box<!fir.array<?x?x!fir.char<1,10>>>) -> !fir.box<none>
+// CHECK:               %[[VAL_37:.*]] = fir.convert %[[TEMP_BOX]] : (!fir.ref<!fir.box<!fir.array<?x?x!fir.char<1,10>>>>) -> !fir.ref<!fir.box<none>>
 // CHECK:               %[[VAL_38:.*]] = fir.convert %[[VAL_35]] : (!fir.ref<!fir.char<1,{{.*}}>>) -> !fir.ref<i8>
-// CHECK:               fir.call @_FortranAShallowCopyDirect(%[[VAL_36]], %[[VAL_37]], %[[VAL_38]], %[[VAL_1]]) : (!fir.box<none>, !fir.box<none>, !fir.ref<i8>, i32) -> ()
+// CHECK:               fir.call @_FortranACopyOutAssignDirect(%[[VAL_36]], %[[VAL_37]], %[[VAL_38]], %[[VAL_1]]) : (!fir.box<none>, !fir.ref<!fir.box<none>>, !fir.ref<i8>, i32) -> ()
 // CHECK:             }
 // CHECK:           }
 // CHECK:           return
@@ -705,11 +714,12 @@ func.func @_QPtest5(%arg0: !fir.box<!fir.array<?x?x!fir.type<_QMmTt>>> {fir.bind
 // CHECK:             %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (!fir.heap<!fir.array<?x?x!fir.type<_QMmTt>>>) -> index
 // CHECK:             %[[VAL_33:.*]] = arith.cmpi ne, %[[VAL_30]], %[[VAL_32]] : index
 // CHECK:             fir.if %[[VAL_33]] weights([0, 1]) {
+// CHECK:               fir.store %[[VAL_8]] to %[[TEMP_BOX:.*]] : !fir.ref<!fir.box<!fir.array<?x?x!fir.type<_QMmTt>>>>
 // CHECK:               %[[VAL_34:.*]] = fir.address_of(@{{_QQcl.*}}
 // CHECK:               %[[VAL_35:.*]] = fir.convert %[[VAL_0]] : (!fir.box<!fir.array<?x?x!fir.type<_QMmTt>>>) -> !fir.box<none>
-// CHECK:               %[[VAL_36:.*]] = fir.convert %[[VAL_8]] : (!fir.box<!fir.array<?x?x!fir.type<_QMmTt>>>) -> !fir.box<none>
+// CHECK:               %[[VAL_36:.*]] = fir.convert %[[TEMP_BOX]] : (!fir.ref<!fir.box<!fir.array<?x?x!fir.type<_QMmTt>>>>) -> !fir.ref<!fir.box<none>>
 // CHECK:               %[[VAL_37:.*]] = fir.convert %[[VAL_34]] : (!fir.ref<!fir.char<1,{{.*}}>>) -> !fir.ref<i8>
-// CHECK:               fir.call @_FortranAShallowCopyDirect(%[[VAL_35]], %[[VAL_36]], %[[VAL_37]], %[[VAL_1]]) : (!fir.box<none>, !fir.box<none>, !fir.ref<i8>, i32) -> ()
+// CHECK:               fir.call @_FortranACopyOutAssignDirect(%[[VAL_35]], %[[VAL_36]], %[[VAL_37]], %[[VAL_1]]) : (!fir.box<none>, !fir.ref<!fir.box<none>>, !fir.ref<i8>, i32) -> ()
 // CHECK:               fir.freemem %[[VAL_29]] : !fir.heap<!fir.array<?x?x!fir.type<_QMmTt>>>
 // CHECK:             }
 // CHECK:           }
@@ -770,11 +780,12 @@ func.func @_QPtest5_stack(%arg0: !fir.box<!fir.array<?x?x!fir.type<_QMmTt>>> {fi
 // CHECK:             %[[VAL_32:.*]] = fir.convert %[[VAL_31]] : (!fir.heap<!fir.array<?x?x!fir.type<_QMmTt>>>) -> index
 // CHECK:             %[[VAL_33:.*]] = arith.cmpi ne, %[[VAL_30]], %[[VAL_32]] : index
 // CHECK:             fir.if %[[VAL_33]] weights([0, 1]) {
+// CHECK:               fir.store %[[VAL_8]] to %[[TEMP_BOX:.*]] : !fir.ref<!fir.box<!fir.array<?x?x!fir.type<_QMmTt>>>>
 // CHECK:               %[[VAL_34:.*]] = fir.address_of(@{{_QQcl.*}}
 // CHECK:               %[[VAL_35:.*]] = fir.convert %[[VAL_0]] : (!fir.box<!fir.array<?x?x!fir.type<_QMmTt>>>) -> !fir.box<none>
-// CHECK:               %[[VAL_36:.*]] = fir.convert %[[VAL_8]] : (!fir.box<!fir.array<?x?x!fir.type<_QMmTt>>>) -> !fir.box<none>
+// CHECK:               %[[VAL_36:.*]] = fir.convert %[[TEMP_BOX]] : (!fir.ref<!fir.box<!fir.array<?x?x!fir.type<_QMmTt>>>>) -> !fir.ref<!fir.box<none>>
 // CHECK:               %[[VAL_37:.*]] = fir.convert %[[VAL_34]] : (!fir.ref<!fir.char<1,{{.*}}>>) -> !fir.ref<i8>
-// CHECK:               fir.call @_FortranAShallowCopyDirect(%[[VAL_35]], %[[VAL_36]], %[[VAL_37]], %[[VAL_1]]) : (!fir.box<none>, !fir.box<none>, !fir.ref<i8>, i32) -> ()
+// CHECK:               fir.call @_FortranACopyOutAssignDirect(%[[VAL_35]], %[[VAL_36]], %[[VAL_37]], %[[VAL_1]]) : (!fir.box<none>, !fir.ref<!fir.box<none>>, !fir.ref<i8>, i32) -> ()
 // CHECK:             }
 // CHECK:           }
 // CHECK:           return
@@ -845,11 +856,12 @@ ...
[truncated]

``````````

</details>


https://github.com/llvm/llvm-project/pull/228543


More information about the flang-commits mailing list