[gcc(refs/users/mikael/heads/refactor_descriptor_v08)] Extraction gfc_set_temporary_descriptor
Mikael Morin
mikael@gcc.gnu.org
Wed Sep 17 16:49:58 GMT 2025
https://gcc.gnu.org/g:6dd4da98ba10271645c7a28db623554002aef630
commit 6dd4da98ba10271645c7a28db623554002aef630
Author: Mikael Morin <mikael@gcc.gnu.org>
Date: Wed Jul 23 12:12:01 2025 +0200
Extraction gfc_set_temporary_descriptor
Diff:
---
gcc/fortran/trans-array.cc | 62 +++++++++++++----------------------------
gcc/fortran/trans-descriptor.cc | 53 +++++++++++++++++++++++++++++++++++
gcc/fortran/trans-descriptor.h | 4 +++
3 files changed, 76 insertions(+), 43 deletions(-)
diff --git a/gcc/fortran/trans-array.cc b/gcc/fortran/trans-array.cc
index 31ed8a7d3079..660107aaef89 100644
--- a/gcc/fortran/trans-array.cc
+++ b/gcc/fortran/trans-array.cc
@@ -624,13 +624,14 @@ gfc_set_loop_bounds_from_array_spec (gfc_interface_mapping * mapping,
DYNAMIC is true if the caller may want to extend the array later
using realloc. This prevents us from putting the array on the stack. */
-static void
+static tree
gfc_trans_allocate_array_storage (stmtblock_t * pre, stmtblock_t * post,
gfc_array_info * info, tree size, tree nelem,
tree initial, bool dynamic, bool dealloc)
{
tree tmp;
tree desc;
+ tree ptr = NULL_TREE;
bool onstack;
desc = info->descriptor;
@@ -638,7 +639,7 @@ gfc_trans_allocate_array_storage (stmtblock_t * pre, stmtblock_t * post,
if (size == NULL_TREE || (dynamic && integer_zerop (size)))
{
/* A callee allocated array. */
- gfc_conv_descriptor_data_set (pre, desc, null_pointer_node);
+ ptr = null_pointer_node;
onstack = false;
}
else
@@ -666,8 +667,7 @@ gfc_trans_allocate_array_storage (stmtblock_t * pre, stmtblock_t * post,
fold_build1_loc (input_location,
DECL_EXPR, TREE_TYPE (tmp),
tmp));
- tmp = gfc_build_addr_expr (NULL_TREE, tmp);
- gfc_conv_descriptor_data_set (pre, desc, tmp);
+ ptr = gfc_build_addr_expr (NULL_TREE, tmp);
}
else
{
@@ -675,7 +675,7 @@ gfc_trans_allocate_array_storage (stmtblock_t * pre, stmtblock_t * post,
if (initial == NULL_TREE)
{
tmp = gfc_call_malloc (pre, NULL, size);
- tmp = gfc_evaluate_now (tmp, pre);
+ ptr = gfc_evaluate_now (tmp, pre);
}
else
{
@@ -718,18 +718,12 @@ gfc_trans_allocate_array_storage (stmtblock_t * pre, stmtblock_t * post,
build_empty_stmt (input_location));
gfc_add_expr_to_block (pre, tmp);
- tmp = fold_convert (pvoid_type_node, packed);
+ ptr = fold_convert (pvoid_type_node, packed);
}
-
- gfc_conv_descriptor_data_set (pre, desc, tmp);
}
}
info->data = gfc_conv_descriptor_data_get (desc);
- /* The offset is zero because we create temporaries with a zero
- lower bound. */
- gfc_conv_descriptor_offset_set (pre, desc, gfc_index_zero_node);
-
if (dealloc && !onstack)
{
/* Free the temporary. */
@@ -737,6 +731,8 @@ gfc_trans_allocate_array_storage (stmtblock_t * pre, stmtblock_t * post,
tmp = gfc_call_free (tmp);
gfc_add_expr_to_block (post, tmp);
}
+
+ return ptr;
}
@@ -970,6 +966,7 @@ gfc_trans_create_temp_array (stmtblock_t * pre, stmtblock_t * post, gfc_ss * ss,
gfc_ss *s;
gfc_array_info *info;
tree from[GFC_MAX_DIMENSIONS], to[GFC_MAX_DIMENSIONS];
+ tree stride[GFC_MAX_DIMENSIONS];
tree type;
tree desc;
tree tmp;
@@ -1105,13 +1102,12 @@ gfc_trans_create_temp_array (stmtblock_t * pre, stmtblock_t * post, gfc_ss * ss,
TREE_USED (desc) = 0;
}
+ bool rank_changer = false;
if (class_expr != NULL_TREE
|| (fcn_ss && fcn_ss->info && fcn_ss->info->class_container))
{
tree class_data;
- tree dtype;
gfc_expr *expr1 = fcn_ss ? fcn_ss->info->expr : NULL;
- bool rank_changer;
/* Pick out these transformational functions because they change the rank
or shape of the first argument. This requires that the class type be
@@ -1165,17 +1161,7 @@ gfc_trans_create_temp_array (stmtblock_t * pre, stmtblock_t * post, gfc_ss * ss,
class_data = gfc_class_data_get (tmp);
if (rank_changer)
- {
- /* Take the dtype from the class expression. */
- tree class_descr = gfc_class_data_get (class_expr);
- dtype = gfc_conv_descriptor_dtype_get (class_descr);
- gfc_conv_descriptor_dtype_set (pre, desc, dtype);
-
-
- /* These transformational functions change the rank. */
- gfc_conv_descriptor_rank_set (pre, desc, ss->loop->dimen);
- fcn_ss->info->class_container = NULL_TREE;
- }
+ fcn_ss->info->class_container = NULL_TREE;
/* Assign the new descriptor to the _data field. This allows the
vptr _copy to be used for scalarized assignment since the class
@@ -1187,12 +1173,6 @@ gfc_trans_create_temp_array (stmtblock_t * pre, stmtblock_t * post, gfc_ss * ss,
/* Point desc to the class _data field. */
desc = class_data;
}
- else
- {
- /* Fill in the array dtype. */
- gfc_conv_descriptor_dtype_set (pre, desc,
- gfc_get_dtype (TREE_TYPE (desc)));
- }
info->descriptor = desc;
size = gfc_index_one_node;
@@ -1239,13 +1219,7 @@ gfc_trans_create_temp_array (stmtblock_t * pre, stmtblock_t * post, gfc_ss * ss,
{
for (n = 0; n < total_dim; n++)
{
- /* Store the stride and bound components in the descriptor. */
- gfc_conv_descriptor_stride_set (pre, desc, gfc_rank_cst[n], size);
-
- gfc_conv_descriptor_lbound_set (pre, desc, gfc_rank_cst[n],
- gfc_index_zero_node);
-
- gfc_conv_descriptor_ubound_set (pre, desc, gfc_rank_cst[n], to[n]);
+ stride[n] = size;
tmp = fold_build2_loc (input_location, PLUS_EXPR,
gfc_array_index_type,
@@ -1286,12 +1260,14 @@ gfc_trans_create_temp_array (stmtblock_t * pre, stmtblock_t * post, gfc_ss * ss,
size = NULL_TREE;
}
- /* Set the span. */
- tmp = fold_convert (gfc_array_index_type, elemsize);
- gfc_conv_descriptor_span_set (pre, desc, tmp);
+ tree data_ptr = gfc_trans_allocate_array_storage (pre, post, info, size,
+ nelem, initial, dynamic,
+ dealloc);
- gfc_trans_allocate_array_storage (pre, post, info, size, nelem, initial,
- dynamic, dealloc);
+ gfc_set_temporary_descriptor (pre, desc, class_expr, elemsize, data_ptr,
+ to, stride, total_dim,
+ size == NULL_TREE || callee_alloc,
+ rank_changer);
while (ss->parent)
ss = ss->parent;
diff --git a/gcc/fortran/trans-descriptor.cc b/gcc/fortran/trans-descriptor.cc
index 65ebfeb504a6..1d85ab847073 100644
--- a/gcc/fortran/trans-descriptor.cc
+++ b/gcc/fortran/trans-descriptor.cc
@@ -2119,3 +2119,56 @@ gfc_set_gfc_from_cfi (stmtblock_t *block, stmtblock_t *block2, tree gfc_desc,
gfc_conv_descriptor_offset_set (block2, gfc_desc, offset);
}
+
+
+void
+gfc_set_temporary_descriptor (stmtblock_t *block, tree descr, tree class_src,
+ tree elemsize, tree data_ptr,
+ tree ubound[GFC_MAX_DIMENSIONS],
+ tree stride[GFC_MAX_DIMENSIONS], int rank,
+ bool callee_allocated, bool rank_changer)
+{
+ if (!class_src)
+ {
+ /* Fill in the array dtype. */
+ gfc_conv_descriptor_dtype_set (block, descr,
+ gfc_get_dtype (TREE_TYPE (descr)));
+ }
+ else if (rank_changer)
+ {
+ /* For classes, we copy the whole original class descriptor to the
+ temporary one, so we don't need to set the individual dtype fields.
+ Except for the case of rank altering intrinsics for which we
+ generate descriptors of different rank. */
+
+ /* Take the dtype from the class expression. */
+ tree class_descr = gfc_class_data_get (class_src);
+ tree dtype = gfc_conv_descriptor_dtype_get (class_descr);
+ gfc_conv_descriptor_dtype_set (block, descr, dtype);
+
+ /* These transformational functions change the rank. */
+ gfc_conv_descriptor_rank_set (block, descr, rank);
+ }
+
+ if (!callee_allocated)
+ for (int n = 0; n < rank; n++)
+ {
+ /* Store the stride and bound components in the descriptor. */
+ gfc_conv_descriptor_stride_set (block, descr, gfc_rank_cst[n],
+ stride[n]);
+
+ gfc_conv_descriptor_lbound_set (block, descr, gfc_rank_cst[n],
+ gfc_index_zero_node);
+
+ gfc_conv_descriptor_ubound_set (block, descr, gfc_rank_cst[n],
+ ubound[n]);
+ }
+
+ gfc_conv_descriptor_span_set (block, descr, elemsize);
+
+ /* The offset is zero because we create temporaries with a zero
+ lower bound. */
+ gfc_conv_descriptor_offset_set (block, descr, gfc_index_zero_node);
+
+ gfc_conv_descriptor_data_set (block, descr, data_ptr);
+}
diff --git a/gcc/fortran/trans-descriptor.h b/gcc/fortran/trans-descriptor.h
index bcc8c01dea89..3c9e99ca27a2 100644
--- a/gcc/fortran/trans-descriptor.h
+++ b/gcc/fortran/trans-descriptor.h
@@ -137,4 +137,8 @@ void gfc_set_gfc_from_cfi (stmtblock_t *, tree, gfc_expr *, tree, tree,
void gfc_set_gfc_from_cfi (stmtblock_t *, stmtblock_t *, tree, tree, tree,
gfc_symbol *, bool);
+void gfc_set_temporary_descriptor (stmtblock_t *, tree, tree, tree, tree,
+ tree [GFC_MAX_DIMENSIONS],
+ tree [GFC_MAX_DIMENSIONS], int, bool, bool);
+
#endif /* GFC_TRANS_DESCRIPTOR_H */
More information about the Gcc-cvs
mailing list