https://gcc.gnu.org/g:82b73bc0fce5aeb88c804fdc776b90f0ed5b491d
commit 82b73bc0fce5aeb88c804fdc776b90f0ed5b491d Author: Sandra Loosemore <[email protected]> Date: Sun Jun 21 04:06:15 2026 +0000 OpenMP, Fortran: Add comments to gfc_trans_omp_array_section. No functional changes in this patch. gcc/fortran/ChangeLog * trans-openmp.cc (gfc_trans_omp_array_section): Add comments and use a more descriptive variable name. (cherry picked from commit 813e1ffdfde31963ccf93af8f786c1903e56e68c) Diff: --- gcc/fortran/trans-openmp.cc | 58 ++++++++++++++++++++++++++++++++++++--------- 1 file changed, 47 insertions(+), 11 deletions(-) diff --git a/gcc/fortran/trans-openmp.cc b/gcc/fortran/trans-openmp.cc index 516b1fda83d8..fce5d221fe98 100644 --- a/gcc/fortran/trans-openmp.cc +++ b/gcc/fortran/trans-openmp.cc @@ -3352,7 +3352,24 @@ gfc_convert_expr_to_tree (stmtblock_t *block, gfc_expr *expr) static vec<tree, va_heap, vl_embed> *doacross_steps; -/* Translate an array section or array element. */ +/* Map an array section or array element. + BLOCK will hold any output statements generated; if there are iterators, + it's a block for the current iterator group. + OP is the construct containing the map clause. + N is the entry that appears in the clause namelist. It may contain iterator + variables. + DECL is the base object associated with the namelist entry. It can be an + array descriptor, a bare array, or pointer to an array. + ELEMENT is true for an array element, false for an array section. + OPENMP is true for OpenMP, false for OpenACC. + PTR_KIND is the map operation. + NODE is an input operand representing the map clause. + NODE2, NODE3, and NODE4 are output operands that will hold new map clauses + generated by this function. Not all of them are always needed. NODE2 + is for an array descriptor object, NODE3 is for its data array, NODE4 + is for a pointer mapping. + ITERATOR is a list of active iterator descriptors, chained through + TREE_CHAIN. */ static void gfc_trans_omp_array_section (stmtblock_t *block, gfc_exec_op op, @@ -3362,7 +3379,10 @@ gfc_trans_omp_array_section (stmtblock_t *block, gfc_exec_op op, tree iterator) { gfc_se se; - tree ptr, ptr2; + /* PTR is the array expression from n->expr. If iterators are this + involved expression can involve iterator variables. BASE points to the + base array object obtained from DECL. */ + tree ptr, base; tree elemsz = NULL_TREE; gfc_init_se (&se, NULL); @@ -3429,11 +3449,13 @@ gfc_trans_omp_array_section (stmtblock_t *block, gfc_exec_op op, && OMP_CLAUSE_MAP_KIND (node) != GOMP_MAP_DELETE) { + /* NODE4 is a newly-generated map clause for the pointer. */ node4 = build_omp_clause (input_location, OMP_CLAUSE_MAP); OMP_CLAUSE_SET_MAP_KIND (node4, GOMP_MAP_POINTER); OMP_CLAUSE_DECL (node4) = decl; OMP_CLAUSE_SIZE (node4) = size_int (0); + /* Make DECL be the descriptor rather than the pointer to it. */ decl = build_fold_indirect_ref (decl); } else if (ptr_kind == GOMP_MAP_ALWAYS_POINTER @@ -3457,7 +3479,8 @@ gfc_trans_omp_array_section (stmtblock_t *block, gfc_exec_op op, if (GFC_DESCRIPTOR_TYPE_P (TREE_TYPE (decl))) { tree type = TREE_TYPE (decl); - ptr2 = gfc_conv_descriptor_data_get (decl); + base = gfc_conv_descriptor_data_get (decl); + /* NODE2 is a newly-generated map clause for the array descriptor DECL. */ node2 = build_omp_clause (input_location, OMP_CLAUSE_MAP); OMP_CLAUSE_DECL (node2) = decl; OMP_CLAUSE_SIZE (node2) = TYPE_SIZE_UNIT (type); @@ -3474,6 +3497,7 @@ gfc_trans_omp_array_section (stmtblock_t *block, gfc_exec_op op, } else OMP_CLAUSE_SET_MAP_KIND (node2, GOMP_MAP_TO_PSET); + /* NODE3 is a newly-generated map clause for the array data. */ node3 = build_omp_clause (input_location, OMP_CLAUSE_MAP); OMP_CLAUSE_SET_MAP_KIND (node3, ptr_kind); OMP_CLAUSE_DECL (node3) = gfc_conv_descriptor_data_get (decl); @@ -3485,14 +3509,14 @@ gfc_trans_omp_array_section (stmtblock_t *block, gfc_exec_op op, if (ptr_kind == GOMP_MAP_ATTACH_DETACH && !openmp) STRIP_NOPS (OMP_CLAUSE_DECL (node3)); } - else + else /* DECL is bare array or pointer to an array. */ { if (TREE_CODE (TREE_TYPE (decl)) == ARRAY_TYPE) { tree offset; - ptr2 = build_fold_addr_expr (decl); + base = build_fold_addr_expr (decl); offset = fold_build2 (MINUS_EXPR, ptrdiff_type_node, ptr, - fold_convert (ptrdiff_type_node, ptr2)); + fold_convert (ptrdiff_type_node, base)); offset = build2 (TRUNC_DIV_EXPR, ptrdiff_type_node, offset, fold_convert (ptrdiff_type_node, elemsz)); offset = build4_loc (input_location, ARRAY_REF, @@ -3503,26 +3527,38 @@ gfc_trans_omp_array_section (stmtblock_t *block, gfc_exec_op op, if (ptr_kind == GOMP_MAP_ATTACH_DETACH && openmp) return; } - else + else /* DECL is a pointer. */ { gcc_assert (POINTER_TYPE_P (TREE_TYPE (decl))); - ptr2 = decl; + base = decl; } node3 = build_omp_clause (input_location, OMP_CLAUSE_MAP); OMP_CLAUSE_SET_MAP_KIND (node3, ptr_kind); OMP_CLAUSE_DECL (node3) = decl; } - ptr2 = fold_convert (ptrdiff_type_node, ptr2); + + /* FIXME: This is a broken hack. The ptr expression is based on the + namelist entry and can contain references to iterator variables, which + are not yet set to their initial values when ptr is used. This + tries to replace instances of the iterator values with the initial values + in ptr explicitly. It's broken because the expansion of ptr can also + add statements to the iterator block that also contain references to + the uninitialized variables, and substituting those similarly breaks + other things. */ + base = fold_convert (ptrdiff_type_node, base); for (tree it = iterator; it; it = TREE_CHAIN (it)) { ptr = simplify_replace_tree (ptr, TREE_VEC_ELT (it, 0), TREE_VEC_ELT (it, 1)); - ptr2 = simplify_replace_tree (ptr2, TREE_VEC_ELT (it, 0), + base = simplify_replace_tree (base, TREE_VEC_ELT (it, 0), TREE_VEC_ELT (it, 1)); } + + /* The OMP_CLAUSE_SIZE field for the array data map clause node3 + contains the initial offset of ptr from base, not the size. */ OMP_CLAUSE_SIZE (node3) = fold_build2 (MINUS_EXPR, ptrdiff_type_node, - ptr, ptr2); + ptr, base); } static tree
