[gcc r12-7217] fortran: Unshare associate var charlen [PR104228]

Mikael Morin mikael@gcc.gnu.org
Sun Feb 13 16:01:06 GMT 2022


https://gcc.gnu.org/g:57da34939703a6e6d3267a0d25d1fb9369d3ac0e

commit r12-7217-g57da34939703a6e6d3267a0d25d1fb9369d3ac0e
Author: Mikael Morin <mikael@gcc.gnu.org>
Date:   Fri Jan 28 22:00:57 2022 +0100

    fortran: Unshare associate var charlen [PR104228]
    
    PR104228 showed that character lengths were shared between associate
    variable and associate targets.  This is problematic when the associate
    target is itself a variable and gets a variable to hold the length, as
    the length variable is added (and all the variables following it in the chain)
    to both the associate variable scope and the target variable scope.
    This caused an ICE when compiling with -O0 -fsanitize=address.
    
    This change forces the creation of a separate character length for the
    associate variable.  It also forces the initialization of the character
    length variable to avoid regressing associate_32 and associate_47 tests.
    
            PR fortran/104228
    
    gcc/fortran/ChangeLog:
    
            * resolve.cc (resolve_assoc_var): Also create a new character
            length for non-dummy associate targets.
            * trans-stmt.cc (trans_associate_var): Initialize character length
            even if no temporary is used for the associate variable.
    
    gcc/testsuite/ChangeLog:
    
            * gfortran.dg/asan/associate_58.f90: New test.
            * gfortran.dg/asan/associate_59.f90: New test.

Diff:
---
 gcc/fortran/resolve.cc                          |  1 -
 gcc/fortran/trans-stmt.cc                       |  2 +-
 gcc/testsuite/gfortran.dg/asan/associate_58.f90 | 19 +++++++++++++++++++
 gcc/testsuite/gfortran.dg/asan/associate_59.f90 | 19 +++++++++++++++++++
 4 files changed, 39 insertions(+), 2 deletions(-)

diff --git a/gcc/fortran/resolve.cc b/gcc/fortran/resolve.cc
index 835a4783718..266e41e25b1 100644
--- a/gcc/fortran/resolve.cc
+++ b/gcc/fortran/resolve.cc
@@ -9227,7 +9227,6 @@ resolve_assoc_var (gfc_symbol* sym, bool resolve_target)
 	sym->ts.u.cl = target->ts.u.cl;
 
       if (sym->ts.deferred && target->expr_type == EXPR_VARIABLE
-	  && target->symtree->n.sym->attr.dummy
 	  && sym->ts.u.cl == target->ts.u.cl)
 	{
 	  sym->ts.u.cl = gfc_new_charlen (sym->ns, NULL);
diff --git a/gcc/fortran/trans-stmt.cc b/gcc/fortran/trans-stmt.cc
index 04f8147d23b..30b6bd5dd2a 100644
--- a/gcc/fortran/trans-stmt.cc
+++ b/gcc/fortran/trans-stmt.cc
@@ -1918,7 +1918,7 @@ trans_associate_var (gfc_symbol *sym, gfc_wrapped_block *block)
       gfc_conv_expr_descriptor (&se, e);
 
       if (sym->ts.type == BT_CHARACTER
-	  && !se.direct_byref && sym->ts.deferred
+	  && sym->ts.deferred
 	  && !sym->attr.select_type_temporary
 	  && VAR_P (sym->ts.u.cl->backend_decl)
 	  && se.string_length != sym->ts.u.cl->backend_decl)
diff --git a/gcc/testsuite/gfortran.dg/asan/associate_58.f90 b/gcc/testsuite/gfortran.dg/asan/associate_58.f90
new file mode 100644
index 00000000000..b5ea75498b7
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/asan/associate_58.f90
@@ -0,0 +1,19 @@
+! { dg-do compile }
+! { dg-additional-options "-O0" }
+!
+! PR fortran/104228
+! The code generated code for the program below wrongly pushed the Y character
+! length variable to both P and S scope, which was leading to an ICE when
+! address sanitizer was in effect
+
+program p
+   character(:), save, allocatable :: x(:)
+   call s
+contains
+   subroutine s
+      associate (y => x)
+         y = [x]
+      end associate
+   end
+end
+
diff --git a/gcc/testsuite/gfortran.dg/asan/associate_59.f90 b/gcc/testsuite/gfortran.dg/asan/associate_59.f90
new file mode 100644
index 00000000000..9bfb2bfbafb
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/asan/associate_59.f90
@@ -0,0 +1,19 @@
+! { dg-do compile }
+! { dg-additional-options "-O0" }
+!
+! PR fortran/104228
+! The code generated code for the program below wrongly pushed the Y character
+! length variable to both P and S scope, which was leading to an ICE when
+! address sanitizer was in effect
+
+program p
+   character(:), allocatable :: x(:)
+   call s
+contains
+   subroutine s
+      associate (y => x)
+         y = [x]
+      end associate
+   end
+end
+


More information about the Gcc-cvs mailing list