Le 11/09/2025 à 22:46, Harald Anlauf a écrit :
Am 11.09.25 um 22:27 schrieb Mikael Morin:
Le 11/09/2025 à 20:28, Harald Anlauf a écrit :
Dear all,

here's a - once found - seemingly simple and obvious fix for a memory
corruption happening when intrinsic assignment is used to set a scalar
allocatable polymorphic component of a derived type when the latter
is instanciated as an array of rank > 0.  Just get the dimension
attribute right when using gfc_variable_attr ...

The testcase is an extended version of the reporter's with unlimited
polymorphism, including another simpler one contributed by a friend.
Without the fix, both tests crash with memory corruption of various
kinds.

Regtested on x86_64-pc-linux-gnu.  OK for mainline?

Hello Harald,

diff --git a/gcc/fortran/primary.cc b/gcc/fortran/primary.cc
index 6df95558bb1..2cb930d83b8 100644
--- a/gcc/fortran/primary.cc
+++ b/gcc/fortran/primary.cc
@@ -3057,12 +3057,14 @@ gfc_variable_attr (gfc_expr *expr, gfc_typespec *ts)

     if (comp->ts.type == BT_CLASS)
       {
+        dimension = CLASS_DATA (comp)->attr.dimension;
         codimension = CLASS_DATA (comp)->attr.codimension;
         pointer = CLASS_DATA (comp)->attr.class_pointer;
         allocatable = CLASS_DATA (comp)->attr.allocatable;
       }
     else
       {
+        dimension = comp->attr.dimension;
         codimension = comp->attr.codimension;
         if (expr->ts.type == BT_CLASS && strcmp (comp->name, "_data") == 0)
           pointer = comp->attr.class_pointer;

I think the dimension flag should additionally be cleared if there is an array element reference after the component.  Otherwise one could get the dimension attribute for a scalar expression (say derived%array_comp(123)). I don't really have a testcase that would exhibit a failure, I'm just being overly cautious.
Thanks for the patch in any case.

You mean further up?

     switch (ref->type)
       {
       case REF_ARRAY:

     switch (ref->u.ar.type)
       {
...
       case AR_ELEMENT:
         /* Handle coarrays.  */
         if (ref->u.ar.dimen > 0)
           allocatable = pointer = optional = false;
         break;

Yes, that's the place.

The more I look at your patch, the less I understand it.
So, given an array expression such as array(:)%scalar_comp, gfc_variable_attr on it would return a result without the dimension attribute?

Reply via email to