https://gcc.gnu.org/g:bf227915607abbe3952859d9dabb885a389fcde0

commit bf227915607abbe3952859d9dabb885a389fcde0
Author: Mikael Morin <mik...@gcc.gnu.org>
Date:   Sat Jul 19 13:55:28 2025 +0200

    Creation gfc_conv_null_array_descriptor, gfc_conv_scalar_null_to_descriptor
    
    Revert "Renommage gfc_clear_descriptor -> gfc_init_descriptor_variable"
    
    This reverts commit 6a87820bffc834c09c5dcf8edb61f55cf6eec34c.
    
    Revert "Correction compilation"
    
    This reverts commit 5131afedc5568d33c68046a098a0143f9ae03eb9.
    
    Revert partiel
    
    Renseignement expression
    
    Renommage
    
    Correction régression null_actual_6

Diff:
---
 gcc/fortran/trans-descriptor.cc | 47 +++++++++++++++++++--
 gcc/fortran/trans-descriptor.h  |  5 ++-
 gcc/fortran/trans-expr.cc       | 93 +++++++++++++++++++++++++++++++++--------
 gcc/fortran/trans-types.cc      |  9 +++-
 gcc/fortran/trans-types.h       |  1 +
 gcc/fortran/trans.h             |  1 +
 6 files changed, 132 insertions(+), 24 deletions(-)

diff --git a/gcc/fortran/trans-descriptor.cc b/gcc/fortran/trans-descriptor.cc
index e3762d70bb36..2d48a1834ba1 100644
--- a/gcc/fortran/trans-descriptor.cc
+++ b/gcc/fortran/trans-descriptor.cc
@@ -671,7 +671,8 @@ gfc_get_descriptor_offsets_for_info (const_tree desc_type, 
tree *data_off,
 #undef UBOUND_SUBFIELD
 
 void
-gfc_init_descriptor_variable (stmtblock_t *block, gfc_symbol *sym, gfc_expr 
*expr, tree descr)
+gfc_nullify_descriptor (stmtblock_t *block, gfc_symbol *sym, gfc_expr *expr,
+                       tree descr, tree string_length)
 {
   symbol_attribute attr = gfc_symbol_attr (sym);
 
@@ -705,8 +706,15 @@ gfc_init_descriptor_variable (stmtblock_t *block, 
gfc_symbol *sym, gfc_expr *exp
     rank = -1;
 
   etype = gfc_get_element_type (TREE_TYPE (descr));
-  gfc_conv_descriptor_dtype_set (block, descr,
-                                gfc_get_dtype_rank_type (rank, etype));
+  tree dtype = gfc_get_dtype_rank_type_slen (rank, etype, string_length);
+  gfc_conv_descriptor_dtype_set (block, descr, dtype);
+}
+
+void
+gfc_init_descriptor_variable (stmtblock_t *block, gfc_symbol *sym,
+                             gfc_expr *expr, tree descr)
+{
+  return gfc_nullify_descriptor (block, sym, expr, descr, NULL_TREE);
 }
 
 
@@ -771,3 +779,36 @@ gfc_init_absent_descriptor (stmtblock_t *block, tree descr)
   gfc_conv_descriptor_data_set (block, descr, null_pointer_node);
 }
 
+
+void
+gfc_set_scalar_descriptor (stmtblock_t *block, tree descr, tree value)
+{
+  tree etype = TREE_TYPE (value);
+
+  if (POINTER_TYPE_P (etype)
+      && TREE_TYPE (etype)
+      && TREE_CODE (TREE_TYPE (etype)) == ARRAY_TYPE)
+    etype = TREE_TYPE (etype);
+  gfc_conv_descriptor_dtype_set (block, descr,
+                                gfc_get_dtype_rank_type (0, etype));
+  gfc_conv_descriptor_data_set (block, descr, value);
+  gfc_conv_descriptor_span_set (block, descr,
+                               gfc_conv_descriptor_elem_len_get (descr));
+}
+
+
+void
+gfc_nullify_descriptor (stmtblock_t *block, gfc_expr *expr, tree descr,
+                       tree string_length)
+{
+  tree etype = gfc_get_element_type (TREE_TYPE (descr));
+  if (TREE_TYPE (etype) && TREE_CODE (TREE_TYPE (etype)) == ARRAY_TYPE)
+    etype = TREE_TYPE (etype);
+  gfc_conv_descriptor_dtype_set (block, descr,
+                                gfc_get_dtype_rank_type_slen (expr->rank, 
etype,
+                                                              string_length));
+  gfc_conv_descriptor_data_set (block, descr, null_pointer_node);
+  gfc_conv_descriptor_span_set (block, descr,
+                               gfc_conv_descriptor_elem_len_get (descr));
+}
+
diff --git a/gcc/fortran/trans-descriptor.h b/gcc/fortran/trans-descriptor.h
index de57a8e606e8..92603cde494a 100644
--- a/gcc/fortran/trans-descriptor.h
+++ b/gcc/fortran/trans-descriptor.h
@@ -19,9 +19,7 @@ along with GCC; see the file COPYING3.  If not see
 #ifndef GFC_TRANS_DESCRIPTOR_H
 #define GFC_TRANS_DESCRIPTOR_H
 
-/* Build a null array descriptor constructor.  */
 tree gfc_build_default_class_descriptor (const gfc_typespec &, tree);
-void gfc_nullify_descriptor (stmtblock_t *block, gfc_expr *, tree);
 void gfc_set_scalar_null_descriptor (stmtblock_t *block, tree, gfc_symbol *, 
gfc_expr *, tree);
 void gfc_set_descriptor_with_shape (stmtblock_t *, tree, tree,
                                    gfc_expr *, locus *);
@@ -95,7 +93,10 @@ gfc_get_descriptor_offsets_for_info (const_tree desc_type, 
tree *data_off,
 
 void gfc_init_descriptor_variable (stmtblock_t *block, gfc_symbol *sym, tree 
descr);
 void gfc_init_descriptor_result (stmtblock_t *block, tree descr);
+void gfc_nullify_descriptor (stmtblock_t *block, gfc_symbol *, gfc_expr *, 
tree, tree);
 void gfc_init_static_descriptor (tree descr);
 void gfc_init_absent_descriptor (stmtblock_t *block, tree descr);
+void gfc_set_scalar_descriptor (stmtblock_t *, tree, tree);
+void gfc_nullify_descriptor (stmtblock_t *, gfc_expr *, tree, tree);
 
 #endif /* GFC_TRANS_DESCRIPTOR_H */
diff --git a/gcc/fortran/trans-expr.cc b/gcc/fortran/trans-expr.cc
index 1e345c1ee9f6..a6cb3d7d6240 100644
--- a/gcc/fortran/trans-expr.cc
+++ b/gcc/fortran/trans-expr.cc
@@ -66,7 +66,7 @@ gfc_get_character_len (tree type)
 /* Calculate the number of bytes in a string.  */
 
 tree
-gfc_get_character_len_in_bytes (tree type)
+gfc_get_character_len_in_bytes (tree type, tree slen)
 {
   tree tmp, len;
 
@@ -76,7 +76,7 @@ gfc_get_character_len_in_bytes (tree type)
   tmp = TYPE_SIZE_UNIT (TREE_TYPE (type));
   tmp = (tmp && !integer_zerop (tmp))
     ? (fold_convert (gfc_charlen_type_node, tmp)) : (NULL_TREE);
-  len = gfc_get_character_len (type);
+  len = slen ? slen : gfc_get_character_len (type);
   if (tmp && len && !integer_zerop (len))
     len = fold_build2_loc (input_location, MULT_EXPR,
                           gfc_charlen_type_node, len, tmp);
@@ -84,6 +84,13 @@ gfc_get_character_len_in_bytes (tree type)
 }
 
 
+tree
+gfc_get_character_len_in_bytes (tree type)
+{
+  return gfc_get_character_len_in_bytes (type, NULL_TREE);
+}
+
+
 /* Convert a scalar to an array descriptor. To be used for assumed-rank
    arrays.  */
 
@@ -105,6 +112,56 @@ get_scalar_to_descriptor_type (tree scalar, 
symbol_attribute attr)
                                    akind, !(attr.pointer || attr.target));
 }
 
+tree
+gfc_conv_scalar_null_to_descriptor (gfc_se *se, gfc_symbol *sym, tree scalar)
+{
+  symbol_attribute attr = sym->attr;
+
+  tree type = get_scalar_to_descriptor_type (scalar, attr);
+  tree desc = gfc_create_var (type, "desc");
+  DECL_ARTIFICIAL (desc) = 1;
+
+  if (CONSTANT_CLASS_P (scalar))
+    {
+      tree tmp;
+      tmp = gfc_create_var (TREE_TYPE (scalar), "scalar");
+      gfc_add_modify (&se->pre, tmp, scalar);
+      scalar = tmp;
+    }
+  if (!POINTER_TYPE_P (TREE_TYPE (scalar)))
+    scalar = gfc_build_addr_expr (NULL_TREE, scalar);
+
+  gfc_set_scalar_descriptor (&se->pre, desc, scalar);
+
+  return desc;
+}
+
+
+tree
+gfc_conv_null_array_descriptor (gfc_se *se, gfc_symbol *sym, gfc_expr *expr)
+{
+  tree lower[GFC_MAX_DIMENSIONS], upper[GFC_MAX_DIMENSIONS];
+
+  for (int i = 0; i < expr->rank; i++)
+    {
+      lower[i] = NULL_TREE;
+      upper[i] = NULL_TREE;
+    }
+
+  tree elt_type = gfc_typenode_for_spec (&sym->ts);
+  tree desc_type = gfc_get_array_type_bounds (elt_type, expr->rank, 0,
+                                             lower, upper, 0,
+                                             GFC_ARRAY_UNKNOWN, false);
+
+  tree desc = gfc_create_var (desc_type, "desc");
+  DECL_ARTIFICIAL (desc) = 1;
+
+  gfc_nullify_descriptor (&se->pre, expr, desc, se->string_length);
+
+  return desc;
+}
+
+
 tree
 gfc_conv_scalar_to_descriptor (gfc_se *se, tree scalar, symbol_attribute attr)
 {
@@ -6631,14 +6688,29 @@ conv_null_actual (gfc_se * parmse, gfc_expr * e, 
gfc_symbol * fsym)
       if (e->ts.type == BT_CHARACTER
          && e->symtree->n.sym->ts.type == BT_CHARACTER)
        {
+         /* Ensure that a usable length is available.  */
+         if (parmse->string_length == NULL_TREE)
+           {
+             gfc_typespec *ts = &e->symtree->n.sym->ts;
+
+             if (ts->u.cl->length != NULL
+                 && ts->u.cl->length->expr_type == EXPR_CONSTANT)
+               gfc_conv_const_charlen (ts->u.cl);
+
+             if (ts->u.cl->backend_decl)
+               parmse->string_length = ts->u.cl->backend_decl;
+           }
+
          /* MOLD is present.  Substitute a temporary character NULL pointer.
             For an assumed-rank dummy we need a descriptor that passes the
             correct rank.  */
          if (fsym->as && fsym->as->type == AS_ASSUMED_RANK)
            {
              tree tmp = parmse->expr;
-             tmp = gfc_conv_scalar_to_descriptor (parmse, tmp, fsym->attr);
-             gfc_conv_descriptor_rank_set (&parmse->pre, tmp, e->rank);
+             if (e->rank == 0)
+               tmp = gfc_conv_scalar_null_to_descriptor (parmse, fsym, tmp);
+             else
+               tmp = gfc_conv_null_array_descriptor (parmse, fsym, e);
              parmse->expr = gfc_build_addr_expr (NULL_TREE, tmp);
            }
          else
@@ -6648,19 +6720,6 @@ conv_null_actual (gfc_se * parmse, gfc_expr * e, 
gfc_symbol * fsym)
                              build_zero_cst (TREE_TYPE (tmp)));
              parmse->expr = gfc_build_addr_expr (NULL_TREE, tmp);
            }
-
-         /* Ensure that a usable length is available.  */
-         if (parmse->string_length == NULL_TREE)
-           {
-             gfc_typespec *ts = &e->symtree->n.sym->ts;
-
-             if (ts->u.cl->length != NULL
-                 && ts->u.cl->length->expr_type == EXPR_CONSTANT)
-               gfc_conv_const_charlen (ts->u.cl);
-
-             if (ts->u.cl->backend_decl)
-               parmse->string_length = ts->u.cl->backend_decl;
-           }
        }
       else if (e->ts.type == BT_UNKNOWN && parmse->string_length == NULL_TREE)
        {
diff --git a/gcc/fortran/trans-types.cc b/gcc/fortran/trans-types.cc
index 1754d9821532..e324fb9c41ea 100644
--- a/gcc/fortran/trans-types.cc
+++ b/gcc/fortran/trans-types.cc
@@ -1695,7 +1695,7 @@ gfc_get_desc_dim_type (void)
    unknown cases abort.  */
 
 tree
-gfc_get_dtype_rank_type (int rank, tree etype)
+gfc_get_dtype_rank_type_slen (int rank, tree etype, tree length)
 {
   tree ptype;
   tree size;
@@ -1764,7 +1764,7 @@ gfc_get_dtype_rank_type (int rank, tree etype)
     {
     case BT_CHARACTER:
       gcc_assert (TREE_CODE (ptype) == ARRAY_TYPE);
-      size = gfc_get_character_len_in_bytes (ptype);
+      size = gfc_get_character_len_in_bytes (ptype, length);
       break;
     case BT_VOID:
       gcc_assert (TREE_CODE (ptype) == POINTER_TYPE);
@@ -1805,6 +1805,11 @@ gfc_get_dtype_rank_type (int rank, tree etype)
   return dtype;
 }
 
+tree
+gfc_get_dtype_rank_type (int rank, tree etype)
+{
+  return gfc_get_dtype_rank_type_slen (rank, etype, NULL_TREE);
+}
 
 tree
 gfc_get_dtype (tree type, int * rank)
diff --git a/gcc/fortran/trans-types.h b/gcc/fortran/trans-types.h
index aba841da9cb5..dc75cd82a841 100644
--- a/gcc/fortran/trans-types.h
+++ b/gcc/fortran/trans-types.h
@@ -116,6 +116,7 @@ bool gfc_return_by_reference (gfc_symbol *);
 bool gfc_is_nodesc_array (gfc_symbol *);
 
 /* Return the DTYPE for an array.  */
+tree gfc_get_dtype_rank_type_slen (int, tree, tree);
 tree gfc_get_dtype_rank_type (int, tree);
 tree gfc_get_dtype (tree, int *rank = NULL);
 
diff --git a/gcc/fortran/trans.h b/gcc/fortran/trans.h
index 798bf0e8a0dc..d6651b31a40f 100644
--- a/gcc/fortran/trans.h
+++ b/gcc/fortran/trans.h
@@ -523,6 +523,7 @@ void gfc_conv_expr_type (gfc_se * se, gfc_expr *, tree);
 
 /* trans-expr.cc */
 tree gfc_get_character_len_in_bytes (tree);
+tree gfc_get_character_len_in_bytes (tree, tree);
 tree gfc_conv_scalar_to_descriptor (gfc_se *, tree, symbol_attribute);
 tree gfc_get_ultimate_alloc_ptr_comps_caf_token (gfc_se *, gfc_expr *);
 tree gfc_string_to_single_character (tree len, tree str, int kind);

Reply via email to