Hi all,
for some recreation after all the coarray stuff, I found this pr cc'ed to me.
Taking a look at it, I figured that using a SAVE_EXPR on the lhs of the
assignment was doing the harm. The data seems to be not written back into the
vector shaped data type (like a complex number in this case). The current fix
just removes the save_expr from the lhs in an assignment and everything is fine.
Regtest ok on x86_64-pc-linux-gnu / F41. Ok for mainline?
Regards,
Andre
--
Andre Vehreschild * Email: vehre ad gmx dot de
From 9307720090584a324b24b32e187a2da43ceaf969 Mon Sep 17 00:00:00 2001
From: Andre Vehreschild <[email protected]>
Date: Tue, 25 Feb 2025 14:17:16 +0100
Subject: [PATCH] Fortran: Remove SAVE_EXPR on lhs in assign [PR108233]
With vectorial shaped datatypes like e.g. complex numbers, fold_convert
inserts a SAVE_EXPR. Using that on the lhs in an assignment prevented
the update of the variable, when in a coarray.
PR fortran/108233
gcc/fortran/ChangeLog:
* trans-expr.cc (gfc_trans_assignment_1): Remove SAVE_EXPR on lhs.
gcc/testsuite/ChangeLog:
* gfortran.dg/coarray/complex_1.f90: New test.
---
gcc/fortran/trans-expr.cc | 13 +++++---
.../gfortran.dg/coarray/complex_1.f90 | 31 +++++++++++++++++++
2 files changed, 39 insertions(+), 5 deletions(-)
create mode 100644 gcc/testsuite/gfortran.dg/coarray/complex_1.f90
diff --git a/gcc/fortran/trans-expr.cc b/gcc/fortran/trans-expr.cc
index 8a3e737a6a8..ab55940638e 100644
--- a/gcc/fortran/trans-expr.cc
+++ b/gcc/fortran/trans-expr.cc
@@ -13017,11 +13017,14 @@ gfc_trans_assignment_1 (gfc_expr * expr1, gfc_expr * expr2, bool init_flag,
else
{
gfc_conv_expr (&lse, expr1);
- if (gfc_option.rtcheck & GFC_RTCHECK_MEM
- && !init_flag
- && gfc_expr_attr (expr1).allocatable
- && expr1->rank
- && !expr2->rank)
+ /* For some expression (e.g. complex numbers) fold_convert uses a
+ SAVE_EXPR, which is hazardous on the lhs, because the value is
+ not updated when assigned to. */
+ if (TREE_CODE (lse.expr) == SAVE_EXPR)
+ lse.expr = TREE_OPERAND (lse.expr, 0);
+
+ if (gfc_option.rtcheck & GFC_RTCHECK_MEM && !init_flag
+ && gfc_expr_attr (expr1).allocatable && expr1->rank && !expr2->rank)
{
tree cond;
const char* msg;
diff --git a/gcc/testsuite/gfortran.dg/coarray/complex_1.f90 b/gcc/testsuite/gfortran.dg/coarray/complex_1.f90
new file mode 100644
index 00000000000..5db0b795278
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/coarray/complex_1.f90
@@ -0,0 +1,31 @@
+!{ dg-do run }
+
+! Check that complex numbers in coarrays can get assigned to.
+! Contributed by Harald Anlauf <[email protected]>
+
+program pr108233
+ implicit none
+ complex :: c = (3.0,4.0), z[*] = (6.0, 7.0)
+ complex, allocatable :: y[:]
+ allocate (y[*])
+ y = c ! allocatable complex scalar coarray is OK
+ if (c /= y) error stop 1
+ z = c ! non-allocatable complex scalar coarray was bad
+ if (c /= z) error stop 2
+ call bcast_scalar (z, c) ! failed too
+ if (c /= z) error stop 3
+ call assign_scalar (z, c) ! this works
+ if (c /= z) error stop 4
+contains
+ subroutine assign_scalar (out, in)
+ complex, intent(out) :: out
+ complex, intent(in) :: in
+ out = in
+ end subroutine assign_scalar
+ subroutine bcast_scalar (out, in)
+ complex, intent(out) :: out[*]
+ complex, intent(in) :: in
+ out = in
+ end subroutine bcast_scalar
+end
+
--
2.48.1