https://gcc.gnu.org/g:8a57ae497ad9944a48a35799f519ecbc7af996bb
commit r17-4080-g8a57ae497ad9944a48a35799f519ecbc7af996bb Author: Jose E. Marchesi <[email protected]> Date: Thu Sep 10 12:56:22 2026 +0200 a68: simplify consolidation of refs Signed-off-by: Jose E. Marchesi <[email protected]> gcc/algol68/ChangeLog * a68-low-ranges.cc (a68_pop_range): Do not consolidate refs in last unit in the range's statement list, becuase it has already been consolidated. (a68_add_completer): Just call to a68_consolidate_ref and avoid tsi_delink. (a68_pop_serial_clause_range): Likewise. * a68-low-clauses.cc (a68_lower_labeled_unit): Consolidate ref in second componend of compound expr. * a68-low.cc (a68_consolidate_ref): Simplify and do not handle compound expressions in a special way. gcc/testsuite/ChangeLog * algol68/execute/labeled-unit-1.a68: New test. * algol68/execute/plusab-5.a68: Likewise. Diff: --- gcc/algol68/a68-low-clauses.cc | 5 ++- gcc/algol68/a68-low-ranges.cc | 52 ++++-------------------- gcc/algol68/a68-low.cc | 40 ++++++++---------- gcc/testsuite/algol68/execute/labeled-unit-1.a68 | 9 ++++ gcc/testsuite/algol68/execute/plusab-5.a68 | 9 ++++ 5 files changed, 46 insertions(+), 69 deletions(-) diff --git a/gcc/algol68/a68-low-clauses.cc b/gcc/algol68/a68-low-clauses.cc index 29ccc43b0765..e67318100125 100644 --- a/gcc/algol68/a68-low-clauses.cc +++ b/gcc/algol68/a68-low-clauses.cc @@ -128,7 +128,10 @@ tree a68_lower_labeled_unit (NODE_T *p, LOW_CTX_T ctx) { tree label_expr = a68_lower_tree (SUB (p), ctx); - tree unit_expr = a68_lower_tree (NEXT (SUB (p)), ctx); + tree unit_expr = a68_lower_tree (NEXT_SUB (p), ctx); + + /* If the labeled unit yields a name, make sure an address is computed. */ + unit_expr = a68_consolidate_ref (MOID (NEXT_SUB (p)), unit_expr); return fold_build2_loc (a68_get_node_location (p), COMPOUND_EXPR, diff --git a/gcc/algol68/a68-low-ranges.cc b/gcc/algol68/a68-low-ranges.cc index 9a2008aa571b..70e189344d97 100644 --- a/gcc/algol68/a68-low-ranges.cc +++ b/gcc/algol68/a68-low-ranges.cc @@ -187,16 +187,6 @@ a68_pop_range (void) current_range = range->next; tree type = (range->mode == NULL ? void_type_node : CTYPE (range->mode)); - /* If TYPE is a pointer type and the last expression in the statement list is - a variable of the type pointed by TYPE then take its address. */ - tree_stmt_iterator i = tsi_last (range->stmt_list); - if (POINTER_TYPE_P (type) && TREE_TYPE (type) == TREE_TYPE (tsi_stmt (i))) - { - append_to_statement_list_force (a68_consolidate_ref (range->mode, tsi_stmt (i)), - &range->stmt_list); - tsi_delink (&i); - } - tree clause = NULL_TREE; if (range->frameless) clause = range->stmt_list; @@ -318,30 +308,15 @@ a68_add_completer (void) struct range *range = current_range; /* The last statement in the statements list is either a single unit or a - labeled unit, i.e a COMPOUND_EXPR whose first expression is a label and - second expression is the unit. Consolidate the unit within the labeled - unit to a ref. */ + labeled unit. Consolidate the unit within the labeled unit to a ref and + put it in the clause result decl. */ tree_stmt_iterator i = tsi_last (range->stmt_list); - tree last_expr = tsi_stmt (i); + *tsi_stmt_ptr (i) = fold_build2 (MODIFY_EXPR, + void_type_node, + range->clause_result_decl, + a68_consolidate_ref (range->mode, tsi_stmt (i))); - if (TREE_CODE (last_expr) == COMPOUND_EXPR - && TREE_CODE (TREE_OPERAND (last_expr, 0)) == LABEL_EXPR) - { - TREE_OPERAND (last_expr, 1) = a68_consolidate_ref (range->mode, - TREE_OPERAND (last_expr, 1)); - TREE_TYPE (last_expr) = TREE_TYPE (TREE_OPERAND (last_expr, 1)); - } - else - last_expr = a68_consolidate_ref (range->mode, last_expr); - - /* Now assign the labeled unit to the clause result decl then jump to the end - of the serial clause. */ - append_to_statement_list_force (fold_build2 (MODIFY_EXPR, - void_type_node, - range->clause_result_decl, - last_expr), - &range->stmt_list); - tsi_delink (&i); + /* Jump to the end of the serial clause. */ append_to_statement_list_force (fold_build1 (GOTO_EXPR, void_type_node, range->clause_exit_label_decl), &range->stmt_list); @@ -562,18 +537,7 @@ a68_pop_serial_clause_range (void) serial clause. */ { tree_stmt_iterator si = tsi_last (range->stmt_list); - tree last_expr = tsi_stmt (si); - if (TREE_CODE (last_expr) == COMPOUND_EXPR - && TREE_CODE (TREE_OPERAND (last_expr, 0)) == LABEL_EXPR) - { - TREE_OPERAND (last_expr, 1) = a68_consolidate_ref (range->mode, - TREE_OPERAND (last_expr, 1)); - TREE_TYPE (last_expr) = TREE_TYPE (TREE_OPERAND (last_expr, 1)); - } - else - last_expr = a68_consolidate_ref (range->mode, last_expr); - a68_add_stmt (last_expr); - tsi_delink (&si); + *tsi_stmt_ptr (si) = a68_consolidate_ref (range->mode, tsi_stmt (si)); } /* If the serial clause has completers, we have to make use of the diff --git a/gcc/algol68/a68-low.cc b/gcc/algol68/a68-low.cc index de7f21dc9108..40636601c036 100644 --- a/gcc/algol68/a68-low.cc +++ b/gcc/algol68/a68-low.cc @@ -403,32 +403,25 @@ a68_consolidate_ref (MOID_T *m, tree expr) /* Address EXPR as many times as necessary to match the number of REFs in the desired mode. */ - while (num_pointers < num_refs) + + if (num_pointers == num_refs) + ; /* We are good. */ + else if (num_pointers == num_refs - 1) { - if (TREE_CODE (expr) == COMPOUND_EXPR) - { - /* (..., x) -> (..., &x) */ - // gcc_assert (TREE_CODE (TREE_OPERAND (expr, 0)) == MODIFY_EXPR); - // gcc_assert (VAR_P (TREE_OPERAND (expr, 1))); - TREE_OPERAND (expr, 1) = a68_consolidate_ref (m, TREE_OPERAND (expr, 1)); - TREE_TYPE (expr) = TREE_TYPE (TREE_OPERAND (expr, 1)); - } + /* x -> &x */ + if (TREE_CODE (expr) == INDIRECT_REF) + /* expr is an indirection. Remove the pointer rather than adding an + addr. This avoids &* situations and marking stuff as addressable + unnecessarily. */ + expr = TREE_OPERAND (expr,0); else { - /* x -> &x */ - if (TREE_CODE (expr) == INDIRECT_REF) - /* expr is an indirection. Remove the pointer rather than adding - an addr. This avoids &* situations and marking stuff as - addressable unnecessarily. */ - expr = TREE_OPERAND (expr,0); - else - { - TREE_ADDRESSABLE (expr) = true; - expr = fold_build1 (ADDR_EXPR, build_pointer_type (TREE_TYPE (expr)), expr); - } + TREE_ADDRESSABLE (expr) = true; + expr = fold_build1 (ADDR_EXPR, build_pointer_type (TREE_TYPE (expr)), expr); } - num_pointers += 1; } + else + gcc_unreachable (); return expr; } @@ -450,9 +443,8 @@ a68_make_anonymous_routine_decl (MOID_T *mode) free (name); DECL_EXTERNAL (func_decl) = 0; DECL_STATIC_CHAIN (func_decl) = !a68_in_global_range (); - /* Nested functions should be addressable. - XXX this should be propagated to their containing functions, so for now - we mark them all as addressable. */ + /* Anonymous routines will always be nested, and nested functions should be + addressable. */ TREE_ADDRESSABLE (func_decl) = 1; /* A nested function is not global. */ TREE_PUBLIC (func_decl) = a68_in_global_range (); diff --git a/gcc/testsuite/algol68/execute/labeled-unit-1.a68 b/gcc/testsuite/algol68/execute/labeled-unit-1.a68 new file mode 100644 index 000000000000..b7536ce4ba69 --- /dev/null +++ b/gcc/testsuite/algol68/execute/labeled-unit-1.a68 @@ -0,0 +1,9 @@ +{ Check ref consolidation of labeled unit. } + +begin int foo; + (skip; lala: lele: foo) := 100; + assert(foo = 100); + ref int bar = loc int; + (skip; lala: lele: bar) := 200; + assert(bar = 200) +end diff --git a/gcc/testsuite/algol68/execute/plusab-5.a68 b/gcc/testsuite/algol68/execute/plusab-5.a68 new file mode 100644 index 000000000000..00925b82d3bc --- /dev/null +++ b/gcc/testsuite/algol68/execute/plusab-5.a68 @@ -0,0 +1,9 @@ +{ Check ref consolidation of var and ide. } + +begin int foo; + foo +:= 10 := 20; + assert(foo = 20); + ref int bar = loc int; + bar +:= 10 := 30; + assert(bar = 30) +end
