This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [PR64164] drop copyrename, integrate into expand


On Sat, Mar 28, 2015 at 8:21 PM, Alexandre Oliva <aoliva@redhat.com> wrote:
> On Mar 27, 2015, Alexandre Oliva <aoliva@redhat.com> wrote:
>
>> This patch reworks the out-of-ssa expander to enable coalescing of SSA
>> partitions that don't share the same base name.  This is done only when
>> optimizing.
>
>> The test we use to tell whether two partitions can be merged no longer
>> demands them to have the same base variable when optimizing, so they
>> become eligible for coalescing, as they would after copyrename.  We then
>> compute the partitioning we'd get if all coalescible partitions were
>> coalesced, using this partition assignment to assign base vars numbers.
>> These base var numbers are then used to identify conflicts, which used
>> to be based on shared base vars or base types.
>
>> We now propagate base var names during coalescing proper, only towards
>> the leader variable.  I'm no longer sure this is still needed, but
>> something about handling variables and results led me this way and I
>> didn't revisit it.  I might rework that with a later patch, or a later
>> revision of this patch; it would require other means to identify
>> partitions holding result_decls during merging, or allow that and deal
>> with param and result decls in a different way during expand proper.
>
>> I had to fix two lingering bugs in order for the whole thing to work: we
>> perform conflict detection after abnormal coalescing, but we computed
>> live ranges involving only the partition leaders, so conflicts with
>> other names already coalesced wouldn't be detected.
>
> This early abnormal coalescing was only present for a few days in the
> trunk, and I was lucky enough to start working on a tree that had it.
> It turns out that the fix for it was thus rendered unnecessary, so I
> dropped it.  It was the fix for it, that didn't cover the live range
> check, that caused the two ICEs I saw in the regressions tests.  Since
> the ultimate cause of the problem is gone, and the change that
> introduced the check failures, both problems went *poof* after I updated
> the tree, resolved the conflicts and dropped the redundant code.
>
>> The other problem was that we didn't track default defs for parms as
>> live at entry, so they might end up coalesced.
>
> I improved this a little bit, using the bitmap of partitions containing
> default params to check that we only process function-entry defs for
> them, rather than for all param decls in case they end up in other
> partitions.
>
>> I guess none of these problems would have been exercised in practice,
>> because we wouldn't even consider merging ssa names associated with
>> different variables.
>
>> In the end, I verified that this fixed the codegen regression in the
>> PR64164 testcase, that failed to merge two partitions that could in
>> theory be merged, but that wasn't even considered due to differences in
>> the SSA var names.
>
>> I'd agree that disregarding the var names and dropping 4 passes is too
>> much of a change to fix this one problem, but...  it's something we
>> should have long tackled, and it gets this and other jobs done, so...
>
> Regstrapped on x86_64-linux-gnu native and on i686-pc-linux-gnu native
> on x86_64, so without lto plugin.  The only regression is in
> gcc.dg/guality/pr54200.c, that explicitly disables VTA.  When
> optimization is enabled, the different coalescing we perform now causes
> VTA-less variable tracking to lose track of variable "z".  This
> regression in non-VTA var-tracking is expected and, as richi put it in
> PR 64164, I guess we don't care about that, do we? :-)

Apart from at -O0, yes.

> The other guality regressions I mentioned in my other email turned out
> not to be regressions, but preexisting failures that somehow did not
> make to the test_summary of my earlier pristine build.
>
> Is this ok to install?

I think this is stage1 material.  Some comments in-line

>
> for  gcc/ChangeLog
>
>         PR rtl-optimization/64164
>         * Makefile.in (OBJS): Drop tree-ssa-copyrename.o.
>         * tree-ssa-copyrename.c: Removed.
>         * opts.c (default_options_table): Drop -ftree-copyrename.
>         * passes.def: Drop all occurrences of pass_rename_ssa_copies.
>         * common.opt (ftree-copyrename): Ignore.
>         (ftree-coalesce-vars, ftree-coalesce-inlined-vars): Likewise.
>         * doc/invoke.texi: Remove the ignored options above.
>         * gimple-expr.c (gimple_can_coalesce_p): Allow coalescing
>         across base variables when optimizing.
>         * tree-ssa-coalesce.c (build_ssa_conflict_graph): Add
>         param_defaults argument.  Process PARM_DECLs's default defs at
>         the entry point.
>         (attempt_coalesce): Add param_defaults argument, and
>         track the presence of default defs for params in each
>         partition.  Propagate base var to leader on merge, preferring
>         parms and results, named vars, ignored vars, and then anon
>         vars.  Refuse to merge a RESULT_DECL partition with a default
>         PARM_DECL one.
>         (coalesce_partitions): Add param_defaults argument,
>         and pass it to attempt_coalesce.
>         (dump_part_var_map): New.
>         (compute_optimized_partition_bases): New, called by...
>         (coalesce_ssa_name): ... when optimizing, disabling
>         partition_view_bitmap's base assignment.  Pass local
>         param_defaults to coalescer functions.
>         * tree-ssa-live.c (var_map_base_init): Note use only when not
>         optimizing.
> ---
>  gcc/Makefile.in           |    1
>  gcc/common.opt            |   12 +
>  gcc/doc/invoke.texi       |   29 ---
>  gcc/gimple-expr.c         |    7 -
>  gcc/opts.c                |    1
>  gcc/passes.def            |    5
>  gcc/tree-ssa-coalesce.c   |  342 ++++++++++++++++++++++++++++++-
>  gcc/tree-ssa-copyrename.c |  499 ---------------------------------------------
>  gcc/tree-ssa-live.c       |    5
>  9 files changed, 347 insertions(+), 554 deletions(-)
>  delete mode 100644 gcc/tree-ssa-copyrename.c
>
> diff --git a/gcc/Makefile.in b/gcc/Makefile.in
> index f924fb8..990c4e9 100644
> --- a/gcc/Makefile.in
> +++ b/gcc/Makefile.in
> @@ -1428,7 +1428,6 @@ OBJS = \
>         tree-ssa-ccp.o \
>         tree-ssa-coalesce.o \
>         tree-ssa-copy.o \
> -       tree-ssa-copyrename.o \
>         tree-ssa-dce.o \
>         tree-ssa-dom.o \
>         tree-ssa-dse.o \
> diff --git a/gcc/common.opt b/gcc/common.opt
> index b49ac46..fefaee7 100644
> --- a/gcc/common.opt
> +++ b/gcc/common.opt
> @@ -2207,16 +2207,16 @@ Common Report Var(flag_tree_ch) Optimization
>  Enable loop header copying on trees
>
>  ftree-coalesce-inlined-vars
> -Common Report Var(flag_ssa_coalesce_vars,1) Init(2) RejectNegative Optimization
> -Enable coalescing of copy-related user variables that are inlined
> +Common Ignore RejectNegative
> +Does nothing.  Preserved for backward compatibility.
>
>  ftree-coalesce-vars
> -Common Report Var(flag_ssa_coalesce_vars,2) Optimization
> -Enable coalescing of all copy-related user variables
> +Common Ignore
> +Does nothing.  Preserved for backward compatibility.
>
>  ftree-copyrename
> -Common Report Var(flag_tree_copyrename) Optimization
> -Replace SSA temporaries with better names in copies
> +Common Ignore
> +Does nothing.  Preserved for backward compatibility.
>
>  ftree-copy-prop
>  Common Report Var(flag_tree_copy_prop) Optimization
> diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi
> index 9749727..5d2c516 100644
> --- a/gcc/doc/invoke.texi
> +++ b/gcc/doc/invoke.texi
> @@ -442,8 +442,7 @@ Objective-C and Objective-C++ Dialects}.
>  -fstack-protector-explicit -fstdarg-opt -fstrict-aliasing @gol
>  -fstrict-overflow -fthread-jumps -ftracer -ftree-bit-ccp @gol
>  -ftree-builtin-call-dce -ftree-ccp -ftree-ch @gol
> --ftree-coalesce-inline-vars -ftree-coalesce-vars -ftree-copy-prop @gol
> --ftree-copyrename -ftree-dce -ftree-dominator-opts -ftree-dse @gol
> +-ftree-copy-prop -ftree-dce -ftree-dominator-opts -ftree-dse @gol
>  -ftree-forwprop -ftree-fre -ftree-loop-if-convert @gol
>  -ftree-loop-if-convert-stores -ftree-loop-im @gol
>  -ftree-phiprop -ftree-loop-distribution -ftree-loop-distribute-patterns @gol
> @@ -8822,32 +8821,6 @@ Perform scalar replacement of aggregates.  This pass replaces structure
>  references with scalars to prevent committing structures to memory too
>  early.  This flag is enabled by default at @option{-O} and higher.
>
> -@item -ftree-copyrename
> -@opindex ftree-copyrename
> -Perform copy renaming on trees.  This pass attempts to rename compiler
> -temporaries to other variables at copy locations, usually resulting in
> -variable names which more closely resemble the original variables.  This flag
> -is enabled by default at @option{-O} and higher.
> -
> -@item -ftree-coalesce-inlined-vars
> -@opindex ftree-coalesce-inlined-vars
> -Tell the copyrename pass (see @option{-ftree-copyrename}) to attempt to
> -combine small user-defined variables too, but only if they are inlined
> -from other functions.  It is a more limited form of
> -@option{-ftree-coalesce-vars}.  This may harm debug information of such
> -inlined variables, but it keeps variables of the inlined-into
> -function apart from each other, such that they are more likely to
> -contain the expected values in a debugging session.
> -
> -@item -ftree-coalesce-vars
> -@opindex ftree-coalesce-vars
> -Tell the copyrename pass (see @option{-ftree-copyrename}) to attempt to
> -combine small user-defined variables too, instead of just compiler
> -temporaries.  This may severely limit the ability to debug an optimized
> -program compiled with @option{-fno-var-tracking-assignments}.  In the
> -negated form, this flag prevents SSA coalescing of user variables,
> -including inlined ones.  This option is enabled by default.
> -
>  @item -ftree-ter
>  @opindex ftree-ter
>  Perform temporary expression replacement during the SSA->normal phase.  Single
> diff --git a/gcc/gimple-expr.c b/gcc/gimple-expr.c
> index efc93b7..62ae577 100644
> --- a/gcc/gimple-expr.c
> +++ b/gcc/gimple-expr.c
> @@ -399,13 +399,14 @@ copy_var_decl (tree var, tree name, tree type)
>  bool
>  gimple_can_coalesce_p (tree name1, tree name2)
>  {
> -  /* First check the SSA_NAME's associated DECL.  We only want to
> -     coalesce if they have the same DECL or both have no associated DECL.  */
> +  /* First check the SSA_NAME's associated DECL.  Without
> +     optimization, we only want to coalesce if they have the same DECL
> +     or both have no associated DECL.  */
>    tree var1 = SSA_NAME_VAR (name1);
>    tree var2 = SSA_NAME_VAR (name2);
>    var1 = (var1 && (!VAR_P (var1) || !DECL_IGNORED_P (var1))) ? var1 : NULL_TREE;
>    var2 = (var2 && (!VAR_P (var2) || !DECL_IGNORED_P (var2))) ? var2 : NULL_TREE;
> -  if (var1 != var2)
> +  if (var1 != var2 && !optimize)
>      return false;
>
>    /* Now check the types.  If the types are the same, then we should
> diff --git a/gcc/opts.c b/gcc/opts.c
> index 39c190d..8149421 100644
> --- a/gcc/opts.c
> +++ b/gcc/opts.c
> @@ -453,7 +453,6 @@ static const struct default_options default_options_table[] =
>      { OPT_LEVELS_1_PLUS, OPT_ftree_dse, NULL, 1 },
>      { OPT_LEVELS_1_PLUS, OPT_ftree_ter, NULL, 1 },
>      { OPT_LEVELS_1_PLUS_NOT_DEBUG, OPT_ftree_sra, NULL, 1 },
> -    { OPT_LEVELS_1_PLUS, OPT_ftree_copyrename, NULL, 1 },
>      { OPT_LEVELS_1_PLUS, OPT_ftree_fre, NULL, 1 },
>      { OPT_LEVELS_1_PLUS, OPT_ftree_copy_prop, NULL, 1 },
>      { OPT_LEVELS_1_PLUS, OPT_ftree_sink, NULL, 1 },
> diff --git a/gcc/passes.def b/gcc/passes.def
> index 1d598b2..f8fd0ef 100644
> --- a/gcc/passes.def
> +++ b/gcc/passes.def
> @@ -77,7 +77,6 @@ along with GCC; see the file COPYING3.  If not see
>        NEXT_PASS (pass_all_early_optimizations);
>        PUSH_INSERT_PASSES_WITHIN (pass_all_early_optimizations)
>           NEXT_PASS (pass_remove_cgraph_callee_edges);
> -         NEXT_PASS (pass_rename_ssa_copies);
>           NEXT_PASS (pass_object_sizes);
>           NEXT_PASS (pass_ccp);
>           /* After CCP we rewrite no longer addressed locals into SSA
> @@ -154,7 +153,6 @@ along with GCC; see the file COPYING3.  If not see
>        /* Initial scalar cleanups before alias computation.
>          They ensure memory accesses are not indirect wherever possible.  */
>        NEXT_PASS (pass_strip_predict_hints);
> -      NEXT_PASS (pass_rename_ssa_copies);
>        NEXT_PASS (pass_ccp);
>        /* After CCP we rewrite no longer addressed locals into SSA
>          form if possible.  */
> @@ -182,7 +180,6 @@ along with GCC; see the file COPYING3.  If not see
>        NEXT_PASS (pass_stdarg);
>        NEXT_PASS (pass_lower_complex);
>        NEXT_PASS (pass_sra);
> -      NEXT_PASS (pass_rename_ssa_copies);
>        /* The dom pass will also resolve all __builtin_constant_p calls
>           that are still there to 0.  This has to be done after some
>          propagations have already run, but before some more dead code
> @@ -291,7 +288,6 @@ along with GCC; see the file COPYING3.  If not see
>        NEXT_PASS (pass_fold_builtins);
>        NEXT_PASS (pass_optimize_widening_mul);
>        NEXT_PASS (pass_tail_calls);
> -      NEXT_PASS (pass_rename_ssa_copies);
>        /* FIXME: If DCE is not run before checking for uninitialized uses,
>          we may get false warnings (e.g., testsuite/gcc.dg/uninit-5.c).
>          However, this also causes us to misdiagnose cases that should be
> @@ -326,7 +322,6 @@ along with GCC; see the file COPYING3.  If not see
>        NEXT_PASS (pass_dce);
>        NEXT_PASS (pass_asan);
>        NEXT_PASS (pass_tsan);
> -      NEXT_PASS (pass_rename_ssa_copies);
>        /* ???  We do want some kind of loop invariant motion, but we possibly
>           need to adjust LIM to be more friendly towards preserving accurate
>          debug information here.  */
> diff --git a/gcc/tree-ssa-coalesce.c b/gcc/tree-ssa-coalesce.c
> index 1afeefe..8557d84 100644
> --- a/gcc/tree-ssa-coalesce.c
> +++ b/gcc/tree-ssa-coalesce.c
> @@ -825,13 +825,23 @@ live_track_clear_base_vars (live_track_p ptr)
>     base variable are added.  */
>
>  static ssa_conflicts_p
> -build_ssa_conflict_graph (tree_live_info_p liveinfo)
> +build_ssa_conflict_graph (tree_live_info_p liveinfo, bitmap param_defaults)
>  {
>    ssa_conflicts_p graph;
>    var_map map;
>    basic_block bb;
>    ssa_op_iter iter;
>    live_track_p live;
> +  basic_block entry;
> +
> +  /* If we are optimizing, we may attempt to coalesce variables from
> +     different base variables, including different parameters, so we
> +     have to make sure default defs live at the entry block conflict
> +     with each other.  */
> +  if (optimize)
> +    entry = single_succ (ENTRY_BLOCK_PTR_FOR_FN (cfun));
> +  else
> +    entry = NULL;
>
>    map = live_var_map (liveinfo);
>    graph = ssa_conflicts_new (num_var_partitions (map));
> @@ -890,6 +900,36 @@ build_ssa_conflict_graph (tree_live_info_p liveinfo)
>             live_track_process_def (live, result, graph);
>         }
>
> +      /* Pretend there are defs for params' default defs at the start
> +        of the (post-)entry block.  We run after abnormal coalescing,
> +        so we can't assume the leader variable is the default
> +        definition, but because of SSA_NAME_VAR adjustments in
> +        attempt_coalesce, we can assume that if there is any
> +        PARM_DECL in the partition, it will be the leader's
> +        SSA_NAME_VAR.  */
> +      if (bb == entry)
> +       {
> +         unsigned base;
> +         bitmap_iterator bi;
> +         EXECUTE_IF_SET_IN_BITMAP (live->live_base_var, 0, base, bi)
> +           {
> +             bitmap_iterator bi2;
> +             unsigned part;
> +             EXECUTE_IF_SET_IN_BITMAP (live->live_base_partitions[base],
> +                                       0, part, bi2)
> +               {
> +                 tree var = partition_to_var (map, part);
> +                 if (!SSA_NAME_VAR (var)
> +                     || TREE_CODE (SSA_NAME_VAR (var)) != PARM_DECL
> +                     || !(SSA_NAME_IS_DEFAULT_DEF (var)
> +                          || (param_defaults
> +                              && bitmap_bit_p (param_defaults, part))))
> +                   continue;
> +                 live_track_process_def (live, var, graph);
> +               }
> +           }
> +       }
> +

This looks somewhat awkward to me ;)  Is it really important to allow
coalescing PARM_DECL-based SSA vars with sth else?  At least
abnormal coalescing doesn't need to do that, so just walking over
the function decls parameters and making their default-def live
should be enough?

That is, that param_defaults bitmap looks ugly to me.

>       live_track_clear_base_vars (live);
>      }
>
> @@ -1126,11 +1166,12 @@ create_outofssa_var_map (coalesce_list_p cl, bitmap used_in_copy)
>
>  static inline bool
>  attempt_coalesce (var_map map, ssa_conflicts_p graph, int x, int y,
> -                 FILE *debug)
> +                 bitmap param_defaults, FILE *debug)
>  {
>    int z;
>    tree var1, var2;
>    int p1, p2;
> +  bool default_def = false;
>
>    p1 = var_to_partition (map, ssa_name (x));
>    p2 = var_to_partition (map, ssa_name (y));
> @@ -1158,6 +1199,70 @@ attempt_coalesce (var_map map, ssa_conflicts_p graph, int x, int y,
>      {
>        var1 = partition_to_var (map, p1);
>        var2 = partition_to_var (map, p2);
> +
> +      tree leader;
> +
> +      if (var1 == var2 || !SSA_NAME_VAR (var2)
> +         || SSA_NAME_VAR (var1) == SSA_NAME_VAR (var2))
> +       {
> +         leader = SSA_NAME_VAR (var1);
> +         default_def = (leader && TREE_CODE (leader) == PARM_DECL
> +                        && (SSA_NAME_IS_DEFAULT_DEF (var1)
> +                            || bitmap_bit_p (param_defaults, p1)));
> +       }
> +      else if (!SSA_NAME_VAR (var1))
> +       {
> +         leader = SSA_NAME_VAR (var2);
> +         default_def = (leader && TREE_CODE (leader) == PARM_DECL
> +                        && (SSA_NAME_IS_DEFAULT_DEF (var2)
> +                            || bitmap_bit_p (param_defaults, p2)));
> +       }
> +      else if ((TREE_CODE (SSA_NAME_VAR (var1)) == PARM_DECL
> +               && (SSA_NAME_IS_DEFAULT_DEF (var1)
> +                   || bitmap_bit_p (param_defaults, p1)))
> +              || TREE_CODE (SSA_NAME_VAR (var1)) == RESULT_DECL)
> +       {
> +         if ((TREE_CODE (SSA_NAME_VAR (var2)) == PARM_DECL
> +              && (SSA_NAME_IS_DEFAULT_DEF (var2)
> +                  || bitmap_bit_p (param_defaults, p2)))
> +             || TREE_CODE (SSA_NAME_VAR (var2)) == RESULT_DECL)
> +           {
> +             /* We only have one RESULT_DECL, and two PARM_DECL
> +                DEFAULT_DEFs would have conflicted, so we know either
> +                one of var1 or var2 is a PARM_DECL, and the other is
> +                a RESULT_DECL.  */
> +             if (debug)
> +               fprintf (debug, ": Cannot coalesce PARM_DECL and RESULT_DECL\n");
> +             return false;
> +           }
> +         leader = SSA_NAME_VAR (var1);
> +         default_def = TREE_CODE (leader) == PARM_DECL;
> +       }
> +      else if ((TREE_CODE (SSA_NAME_VAR (var2)) == PARM_DECL
> +               && (SSA_NAME_IS_DEFAULT_DEF (var2)
> +                   || bitmap_bit_p (param_defaults, p2)))
> +              || TREE_CODE (SSA_NAME_VAR (var2)) == RESULT_DECL)
> +       {
> +         leader = SSA_NAME_VAR (var2);
> +         default_def = TREE_CODE (leader) == PARM_DECL;
> +       }
> +      else if (TREE_CODE (SSA_NAME_VAR (var1)) == PARM_DECL)
> +       leader = SSA_NAME_VAR (var1);
> +      else if (TREE_CODE (SSA_NAME_VAR (var2)) == PARM_DECL)
> +       leader = SSA_NAME_VAR (var2);
> +      else if (TREE_CODE (SSA_NAME_VAR (var1)) == VAR_DECL
> +              && !DECL_IGNORED_P (SSA_NAME_VAR (var1)))
> +       leader = SSA_NAME_VAR (var1);
> +      else if (TREE_CODE (SSA_NAME_VAR (var2)) == VAR_DECL
> +              && !DECL_IGNORED_P (SSA_NAME_VAR (var2)))
> +       leader = SSA_NAME_VAR (var2);
> +      else if (TREE_CODE (SSA_NAME_VAR (var1)) == VAR_DECL)
> +       leader = SSA_NAME_VAR (var1);
> +      else if (TREE_CODE (SSA_NAME_VAR (var2)) == VAR_DECL)
> +       leader = SSA_NAME_VAR (var2);
> +      else /* What else could it be?  */
> +       gcc_unreachable ();
> +

definitely comments missing in this spaghetti...

>        z = var_union (map, var1, var2);
>        if (z == NO_PARTITION)
>         {
> @@ -1173,8 +1278,46 @@ attempt_coalesce (var_map map, ssa_conflicts_p graph, int x, int y,
>        else
>         ssa_conflicts_merge (graph, p2, p1);
>
> +      if (z == p1)
> +       {
> +         if (SSA_NAME_VAR (var1) != leader)
> +           {
> +             replace_ssa_name_symbol (var1, leader);
> +             if (debug)
> +               {
> +                 fprintf (debug, ": Renamed ");
> +                 print_generic_expr (debug, var1, TDF_SLIM);
> +               }
> +           }
> +         if (default_def)
> +           {
> +             if (SSA_NAME_IS_DEFAULT_DEF (var2))
> +               bitmap_clear_bit (param_defaults, p2);
> +             bitmap_set_bit (param_defaults, p1);
> +           }
> +       }
> +      else
> +       {
> +         if (SSA_NAME_VAR (var2) != leader)
> +           {
> +             replace_ssa_name_symbol (var2, leader);
> +             if (debug)
> +               {
> +                 fprintf (debug, ": Renamed ");
> +                 print_generic_expr (debug, var2, TDF_SLIM);
> +               }
> +           }
> +         if (default_def)
> +           {
> +             if (SSA_NAME_IS_DEFAULT_DEF (var1))
> +               bitmap_clear_bit (param_defaults, p1);
> +             bitmap_set_bit (param_defaults, p2);
> +           }
> +       }

or seeing this, why coalesce default-defs at all?  Either they are param values
or they have indetermined values (and thus we can and do pick whatever is
available at expansion time)?

> +
>        if (debug)
>         fprintf (debug, ": Success -> %d\n", z);
> +
>        return true;
>      }
>
> @@ -1190,7 +1333,7 @@ attempt_coalesce (var_map map, ssa_conflicts_p graph, int x, int y,
>
>  static void
>  coalesce_partitions (var_map map, ssa_conflicts_p graph, coalesce_list_p cl,
> -                    FILE *debug)
> +                    bitmap param_defaults, FILE *debug)
>  {
>    int x = 0, y = 0;
>    tree var1, var2;
> @@ -1226,7 +1369,7 @@ coalesce_partitions (var_map map, ssa_conflicts_p graph, coalesce_list_p cl,
>                 if (debug)
>                   fprintf (debug, "Abnormal coalesce: ");
>
> -               if (!attempt_coalesce (map, graph, v1, v2, debug))
> +               if (!attempt_coalesce (map, graph, v1, v2, param_defaults, debug))
>                   fail_abnormal_edge_coalesce (v1, v2);
>               }
>           }
> @@ -1244,7 +1387,7 @@ coalesce_partitions (var_map map, ssa_conflicts_p graph, coalesce_list_p cl,
>
>        if (debug)
>         fprintf (debug, "Coalesce list: ");
> -      attempt_coalesce (map, graph, x, y, debug);
> +      attempt_coalesce (map, graph, x, y, param_defaults, debug);
>      }
>  }
>
> @@ -1272,6 +1415,178 @@ ssa_name_var_hash::equal (const value_type *n1, const compare_type *n2)
>  }
>
>
> +/* Output partition map MAP with coalescing plan PART to file F.  */
> +
> +void
> +dump_part_var_map (FILE *f, partition part, var_map map)
> +{
> +  int t;
> +  unsigned x, y;
> +  int p;
> +
> +  fprintf (f, "\nCoalescible Partition map \n\n");
> +
> +  for (x = 0; x < map->num_partitions; x++)
> +    {
> +      if (map->view_to_partition != NULL)
> +       p = map->view_to_partition[x];
> +      else
> +       p = x;
> +
> +      if (ssa_name (p) == NULL_TREE
> +         || virtual_operand_p (ssa_name (p)))
> +        continue;
> +
> +      t = 0;
> +      for (y = 1; y < num_ssa_names; y++)
> +        {
> +         tree var = version_to_var (map, y);
> +         if (!var)
> +           continue;
> +         int q = var_to_partition (map, var);
> +         p = partition_find (part, q);
> +         gcc_assert (map->partition_to_base_index[q]
> +                     == map->partition_to_base_index[p]);
> +
> +         if (p == (int)x)
> +           {
> +             if (t++ == 0)
> +               {
> +                 fprintf (f, "Partition %d, base %d (", x,
> +                          map->partition_to_base_index[q]);
> +                 print_generic_expr (f, partition_to_var (map, q), TDF_SLIM);
> +                 fprintf (f, " - ");
> +               }
> +             fprintf (f, "%d ", y);
> +           }
> +       }
> +      if (t != 0)
> +       fprintf (f, ")\n");
> +    }
> +  fprintf (f, "\n");
> +}
> +
> +/* Fill in MAP's partition_to_base_index, with one index for each
> +   partition of SSA names USED_IN_COPIES and related by CL
> +   coalesce possibilities.  */
> +
> +static void
> +compute_optimized_partition_bases (var_map map, bitmap used_in_copies,
> +                                  coalesce_list_p cl)
> +{
> +  int parts = num_var_partitions (map);
> +  partition tentative = partition_new (parts);
> +
> +  /* Partition the SSA versions so that, for each coalescible
> +     pair, both of its members are in the same partition in
> +     TENTATIVE.  */
> +  gcc_assert (!cl->sorted);
> +  coalesce_pair_p node;
> +  coalesce_iterator_type ppi;
> +  FOR_EACH_PARTITION_PAIR (node, ppi, cl)
> +    {
> +      tree v1 = ssa_name (node->first_element);
> +      int p1 = partition_find (tentative, var_to_partition (map, v1));
> +      tree v2 = ssa_name (node->second_element);
> +      int p2 = partition_find (tentative, var_to_partition (map, v2));
> +
> +      if (p1 == p2)
> +       continue;
> +
> +      partition_union (tentative, p1, p2);
> +    }
> +
> +  /* We have to deal with cost one pairs too.  */
> +  for (cost_one_pair_d *co = cl->cost_one_list; co; co = co->next)
> +    {
> +      tree v1 = ssa_name (co->first_element);
> +      int p1 = partition_find (tentative, var_to_partition (map, v1));
> +      tree v2 = ssa_name (co->second_element);
> +      int p2 = partition_find (tentative, var_to_partition (map, v2));
> +
> +      if (p1 == p2)
> +       continue;
> +
> +      partition_union (tentative, p1, p2);
> +    }
> +
> +  /* And also with abnormal edges.  */
> +  basic_block bb;
> +  edge e;
> +  edge_iterator ei;
> +  FOR_EACH_BB_FN (bb, cfun)
> +    {
> +      FOR_EACH_EDGE (e, ei, bb->preds)
> +       if (e->flags & EDGE_ABNORMAL)
> +         {
> +           gphi_iterator gsi;
> +           for (gsi = gsi_start_phis (bb); !gsi_end_p (gsi);
> +                gsi_next (&gsi))
> +             {
> +               gphi *phi = gsi.phi ();
> +               tree arg = PHI_ARG_DEF (phi, e->dest_idx);
> +               if (SSA_NAME_IS_DEFAULT_DEF (arg)
> +                   && (!SSA_NAME_VAR (arg)
> +                       || TREE_CODE (SSA_NAME_VAR (arg)) != PARM_DECL))
> +                 continue;
> +
> +               tree res = PHI_RESULT (phi);
> +
> +               int p1 = partition_find (tentative, var_to_partition (map, res));
> +               int p2 = partition_find (tentative, var_to_partition (map, arg));
> +
> +               if (p1 == p2)
> +                 continue;
> +
> +               partition_union (tentative, p1, p2);
> +             }
> +         }
> +    }

So the above does full coalescing ignoring conflicts.

> +
> +  map->partition_to_base_index = XCNEWVEC (int, parts);
> +  auto_vec<unsigned int> index_map (parts);
> +  if (parts)
> +    index_map.quick_grow (parts);
> +
> +  const unsigned no_part = -1;
> +  unsigned count = parts;
> +  while (count)
> +    index_map[--count] = no_part;
> +
> +  /* Initialize MAP's mapping from partition to base index, using
> +     as base indices an enumeration of the TENTATIVE partitions in
> +     which each SSA version ended up, so that we compute conflicts
> +     between all SSA versions that ended up in the same potential
> +     coalesce partition.  */
> +  bitmap_iterator bi;
> +  unsigned i;
> +  EXECUTE_IF_SET_IN_BITMAP (used_in_copies, 0, i, bi)
> +    {
> +      int pidx = var_to_partition (map, ssa_name (i));
> +      int base = partition_find (tentative, pidx);
> +      if (index_map[base] != no_part)
> +       continue;
> +      index_map[base] = count++;
> +    }
> +
> +  map->num_basevars = count;

Did you do any statistics on how the number of basevars changes with your patch
compared to trunk?

So apart from possibly simplifying the patch by not dealing with
default-def coalesces
of PARAM_DECLs and ignoring them for conflict purposes for others (as
tree-ssa-live.c
does) the patch looks good to me.

Richard.

> +  EXECUTE_IF_SET_IN_BITMAP (used_in_copies, 0, i, bi)
> +    {
> +      int pidx = var_to_partition (map, ssa_name (i));
> +      int base = partition_find (tentative, pidx);
> +      gcc_assert (index_map[base] < count);
> +      map->partition_to_base_index[pidx] = index_map[base];
> +    }
> +
> +  if (dump_file && (dump_flags & TDF_DETAILS))
> +    dump_part_var_map (dump_file, tentative, map);
> +
> +  partition_delete (tentative);
> +}
> +
> +
>  /* Reduce the number of copies by coalescing variables in the function.  Return
>     a partition map with the resulting coalesces.  */
>
> @@ -1332,7 +1647,12 @@ coalesce_ssa_name (void)
>      dump_var_map (dump_file, map);
>
>    /* Don't calculate live ranges for variables not in the coalesce list.  */
> -  partition_view_bitmap (map, used_in_copies, true);
> +  partition_view_bitmap (map, used_in_copies, !optimize);
> +
> +  /* If we are optimizing, compute the base indices ourselves.  */
> +  if (optimize)
> +    compute_optimized_partition_bases (map, used_in_copies, cl);
> +
>    BITMAP_FREE (used_in_copies);
>
>    if (num_var_partitions (map) < 1)
> @@ -1341,6 +1661,8 @@ coalesce_ssa_name (void)
>        return map;
>      }
>
> +  bitmap param_defaults = BITMAP_ALLOC (NULL);
> +
>    if (dump_file && (dump_flags & TDF_DETAILS))
>      dump_var_map (dump_file, map);
>
> @@ -1350,7 +1672,7 @@ coalesce_ssa_name (void)
>      dump_live_info (dump_file, liveinfo, LIVEDUMP_ENTRY);
>
>    /* Build a conflict graph.  */
> -  graph = build_ssa_conflict_graph (liveinfo);
> +  graph = build_ssa_conflict_graph (liveinfo, param_defaults);
>    delete_tree_live_info (liveinfo);
>    if (dump_file && (dump_flags & TDF_DETAILS))
>      ssa_conflicts_dump (dump_file, graph);
> @@ -1370,10 +1692,10 @@ coalesce_ssa_name (void)
>      dump_var_map (dump_file, map);
>
>    /* Now coalesce everything in the list.  */
> -  coalesce_partitions (map, graph, cl,
> -                      ((dump_flags & TDF_DETAILS) ? dump_file
> -                                                  : NULL));
> +  coalesce_partitions (map, graph, cl, param_defaults,
> +                      ((dump_flags & TDF_DETAILS) ? dump_file : NULL));
>
> +  BITMAP_FREE (param_defaults);
>    delete_coalesce_list (cl);
>    ssa_conflicts_delete (graph);
>
> diff --git a/gcc/tree-ssa-copyrename.c b/gcc/tree-ssa-copyrename.c
> deleted file mode 100644
> index f3cb56e..0000000
> --- a/gcc/tree-ssa-copyrename.c
> +++ /dev/null
> @@ -1,499 +0,0 @@
> -/* Rename SSA copies.
> -   Copyright (C) 2004-2015 Free Software Foundation, Inc.
> -   Contributed by Andrew MacLeod <amacleod@redhat.com>
> -
> -This file is part of GCC.
> -
> -GCC is free software; you can redistribute it and/or modify
> -it under the terms of the GNU General Public License as published by
> -the Free Software Foundation; either version 3, or (at your option)
> -any later version.
> -
> -GCC is distributed in the hope that it will be useful,
> -but WITHOUT ANY WARRANTY; without even the implied warranty of
> -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> -GNU General Public License for more details.
> -
> -You should have received a copy of the GNU General Public License
> -along with GCC; see the file COPYING3.  If not see
> -<http://www.gnu.org/licenses/>.  */
> -
> -#include "config.h"
> -#include "system.h"
> -#include "coretypes.h"
> -#include "tm.h"
> -#include "hash-set.h"
> -#include "machmode.h"
> -#include "vec.h"
> -#include "double-int.h"
> -#include "input.h"
> -#include "alias.h"
> -#include "symtab.h"
> -#include "wide-int.h"
> -#include "inchash.h"
> -#include "tree.h"
> -#include "fold-const.h"
> -#include "predict.h"
> -#include "hard-reg-set.h"
> -#include "function.h"
> -#include "dominance.h"
> -#include "cfg.h"
> -#include "basic-block.h"
> -#include "tree-ssa-alias.h"
> -#include "internal-fn.h"
> -#include "gimple-expr.h"
> -#include "is-a.h"
> -#include "gimple.h"
> -#include "gimple-iterator.h"
> -#include "flags.h"
> -#include "tree-pretty-print.h"
> -#include "bitmap.h"
> -#include "gimple-ssa.h"
> -#include "stringpool.h"
> -#include "tree-ssanames.h"
> -#include "hashtab.h"
> -#include "rtl.h"
> -#include "statistics.h"
> -#include "real.h"
> -#include "fixed-value.h"
> -#include "insn-config.h"
> -#include "expmed.h"
> -#include "dojump.h"
> -#include "explow.h"
> -#include "calls.h"
> -#include "emit-rtl.h"
> -#include "varasm.h"
> -#include "stmt.h"
> -#include "expr.h"
> -#include "tree-dfa.h"
> -#include "tree-inline.h"
> -#include "tree-ssa-live.h"
> -#include "tree-pass.h"
> -#include "langhooks.h"
> -
> -static struct
> -{
> -  /* Number of copies coalesced.  */
> -  int coalesced;
> -} stats;
> -
> -/* The following routines implement the SSA copy renaming phase.
> -
> -   This optimization looks for copies between 2 SSA_NAMES, either through a
> -   direct copy, or an implicit one via a PHI node result and its arguments.
> -
> -   Each copy is examined to determine if it is possible to rename the base
> -   variable of one of the operands to the same variable as the other operand.
> -   i.e.
> -   T.3_5 = <blah>
> -   a_1 = T.3_5
> -
> -   If this copy couldn't be copy propagated, it could possibly remain in the
> -   program throughout the optimization phases.   After SSA->normal, it would
> -   become:
> -
> -   T.3 = <blah>
> -   a = T.3
> -
> -   Since T.3_5 is distinct from all other SSA versions of T.3, there is no
> -   fundamental reason why the base variable needs to be T.3, subject to
> -   certain restrictions.  This optimization attempts to determine if we can
> -   change the base variable on copies like this, and result in code such as:
> -
> -   a_5 = <blah>
> -   a_1 = a_5
> -
> -   This gives the SSA->normal pass a shot at coalescing a_1 and a_5. If it is
> -   possible, the copy goes away completely. If it isn't possible, a new temp
> -   will be created for a_5, and you will end up with the exact same code:
> -
> -   a.8 = <blah>
> -   a = a.8
> -
> -   The other benefit of performing this optimization relates to what variables
> -   are chosen in copies.  Gimplification of the program uses temporaries for
> -   a lot of things. expressions like
> -
> -   a_1 = <blah>
> -   <blah2> = a_1
> -
> -   get turned into
> -
> -   T.3_5 = <blah>
> -   a_1 = T.3_5
> -   <blah2> = a_1
> -
> -   Copy propagation is done in a forward direction, and if we can propagate
> -   through the copy, we end up with:
> -
> -   T.3_5 = <blah>
> -   <blah2> = T.3_5
> -
> -   The copy is gone, but so is all reference to the user variable 'a'. By
> -   performing this optimization, we would see the sequence:
> -
> -   a_5 = <blah>
> -   a_1 = a_5
> -   <blah2> = a_1
> -
> -   which copy propagation would then turn into:
> -
> -   a_5 = <blah>
> -   <blah2> = a_5
> -
> -   and so we still retain the user variable whenever possible.  */
> -
> -
> -/* Coalesce the partitions in MAP representing VAR1 and VAR2 if it is valid.
> -   Choose a representative for the partition, and send debug info to DEBUG.  */
> -
> -static void
> -copy_rename_partition_coalesce (var_map map, tree var1, tree var2, FILE *debug)
> -{
> -  int p1, p2, p3;
> -  tree root1, root2;
> -  tree rep1, rep2;
> -  bool ign1, ign2, abnorm;
> -
> -  gcc_assert (TREE_CODE (var1) == SSA_NAME);
> -  gcc_assert (TREE_CODE (var2) == SSA_NAME);
> -
> -  register_ssa_partition (map, var1);
> -  register_ssa_partition (map, var2);
> -
> -  p1 = partition_find (map->var_partition, SSA_NAME_VERSION (var1));
> -  p2 = partition_find (map->var_partition, SSA_NAME_VERSION (var2));
> -
> -  if (debug)
> -    {
> -      fprintf (debug, "Try : ");
> -      print_generic_expr (debug, var1, TDF_SLIM);
> -      fprintf (debug, "(P%d) & ", p1);
> -      print_generic_expr (debug, var2, TDF_SLIM);
> -      fprintf (debug, "(P%d)", p2);
> -    }
> -
> -  gcc_assert (p1 != NO_PARTITION);
> -  gcc_assert (p2 != NO_PARTITION);
> -
> -  if (p1 == p2)
> -    {
> -      if (debug)
> -       fprintf (debug, " : Already coalesced.\n");
> -      return;
> -    }
> -
> -  rep1 = partition_to_var (map, p1);
> -  rep2 = partition_to_var (map, p2);
> -  root1 = SSA_NAME_VAR (rep1);
> -  root2 = SSA_NAME_VAR (rep2);
> -  if (!root1 && !root2)
> -    return;
> -
> -  /* Don't coalesce if one of the variables occurs in an abnormal PHI.  */
> -  abnorm = (SSA_NAME_OCCURS_IN_ABNORMAL_PHI (rep1)
> -           || SSA_NAME_OCCURS_IN_ABNORMAL_PHI (rep2));
> -  if (abnorm)
> -    {
> -      if (debug)
> -       fprintf (debug, " : Abnormal PHI barrier.  No coalesce.\n");
> -      return;
> -    }
> -
> -  /* Partitions already have the same root, simply merge them.  */
> -  if (root1 == root2)
> -    {
> -      p1 = partition_union (map->var_partition, p1, p2);
> -      if (debug)
> -       fprintf (debug, " : Same root, coalesced --> P%d.\n", p1);
> -      return;
> -    }
> -
> -  /* Never attempt to coalesce 2 different parameters.  */
> -  if ((root1 && TREE_CODE (root1) == PARM_DECL)
> -      && (root2 && TREE_CODE (root2) == PARM_DECL))
> -    {
> -      if (debug)
> -        fprintf (debug, " : 2 different PARM_DECLS. No coalesce.\n");
> -      return;
> -    }
> -
> -  if ((root1 && TREE_CODE (root1) == RESULT_DECL)
> -      != (root2 && TREE_CODE (root2) == RESULT_DECL))
> -    {
> -      if (debug)
> -        fprintf (debug, " : One root a RESULT_DECL. No coalesce.\n");
> -      return;
> -    }
> -
> -  ign1 = !root1 || (TREE_CODE (root1) == VAR_DECL && DECL_IGNORED_P (root1));
> -  ign2 = !root2 || (TREE_CODE (root2) == VAR_DECL && DECL_IGNORED_P (root2));
> -
> -  /* Refrain from coalescing user variables, if requested.  */
> -  if (!ign1 && !ign2)
> -    {
> -      if (flag_ssa_coalesce_vars && DECL_FROM_INLINE (root2))
> -       ign2 = true;
> -      else if (flag_ssa_coalesce_vars && DECL_FROM_INLINE (root1))
> -       ign1 = true;
> -      else if (flag_ssa_coalesce_vars != 2)
> -       {
> -         if (debug)
> -           fprintf (debug, " : 2 different USER vars. No coalesce.\n");
> -         return;
> -       }
> -      else
> -       ign2 = true;
> -    }
> -
> -  /* If both values have default defs, we can't coalesce.  If only one has a
> -     tag, make sure that variable is the new root partition.  */
> -  if (root1 && ssa_default_def (cfun, root1))
> -    {
> -      if (root2 && ssa_default_def (cfun, root2))
> -       {
> -         if (debug)
> -           fprintf (debug, " : 2 default defs. No coalesce.\n");
> -         return;
> -       }
> -      else
> -        {
> -         ign2 = true;
> -         ign1 = false;
> -       }
> -    }
> -  else if (root2 && ssa_default_def (cfun, root2))
> -    {
> -      ign1 = true;
> -      ign2 = false;
> -    }
> -
> -  /* Do not coalesce if we cannot assign a symbol to the partition.  */
> -  if (!(!ign2 && root2)
> -      && !(!ign1 && root1))
> -    {
> -      if (debug)
> -       fprintf (debug, " : Choosen variable has no root.  No coalesce.\n");
> -      return;
> -    }
> -
> -  /* Don't coalesce if the new chosen root variable would be read-only.
> -     If both ign1 && ign2, then the root var of the larger partition
> -     wins, so reject in that case if any of the root vars is TREE_READONLY.
> -     Otherwise reject only if the root var, on which replace_ssa_name_symbol
> -     will be called below, is readonly.  */
> -  if (((root1 && TREE_READONLY (root1)) && ign2)
> -      || ((root2 && TREE_READONLY (root2)) && ign1))
> -    {
> -      if (debug)
> -       fprintf (debug, " : Readonly variable.  No coalesce.\n");
> -      return;
> -    }
> -
> -  /* Don't coalesce if the two variables aren't type compatible .  */
> -  if (!types_compatible_p (TREE_TYPE (var1), TREE_TYPE (var2))
> -      /* There is a disconnect between the middle-end type-system and
> -         VRP, avoid coalescing enum types with different bounds.  */
> -      || ((TREE_CODE (TREE_TYPE (var1)) == ENUMERAL_TYPE
> -          || TREE_CODE (TREE_TYPE (var2)) == ENUMERAL_TYPE)
> -         && TREE_TYPE (var1) != TREE_TYPE (var2)))
> -    {
> -      if (debug)
> -       fprintf (debug, " : Incompatible types.  No coalesce.\n");
> -      return;
> -    }
> -
> -  /* Merge the two partitions.  */
> -  p3 = partition_union (map->var_partition, p1, p2);
> -
> -  /* Set the root variable of the partition to the better choice, if there is
> -     one.  */
> -  if (!ign2 && root2)
> -    replace_ssa_name_symbol (partition_to_var (map, p3), root2);
> -  else if (!ign1 && root1)
> -    replace_ssa_name_symbol (partition_to_var (map, p3), root1);
> -  else
> -    gcc_unreachable ();
> -
> -  if (debug)
> -    {
> -      fprintf (debug, " --> P%d ", p3);
> -      print_generic_expr (debug, SSA_NAME_VAR (partition_to_var (map, p3)),
> -                         TDF_SLIM);
> -      fprintf (debug, "\n");
> -    }
> -}
> -
> -
> -namespace {
> -
> -const pass_data pass_data_rename_ssa_copies =
> -{
> -  GIMPLE_PASS, /* type */
> -  "copyrename", /* name */
> -  OPTGROUP_NONE, /* optinfo_flags */
> -  TV_TREE_COPY_RENAME, /* tv_id */
> -  ( PROP_cfg | PROP_ssa ), /* properties_required */
> -  0, /* properties_provided */
> -  0, /* properties_destroyed */
> -  0, /* todo_flags_start */
> -  0, /* todo_flags_finish */
> -};
> -
> -class pass_rename_ssa_copies : public gimple_opt_pass
> -{
> -public:
> -  pass_rename_ssa_copies (gcc::context *ctxt)
> -    : gimple_opt_pass (pass_data_rename_ssa_copies, ctxt)
> -  {}
> -
> -  /* opt_pass methods: */
> -  opt_pass * clone () { return new pass_rename_ssa_copies (m_ctxt); }
> -  virtual bool gate (function *) { return flag_tree_copyrename != 0; }
> -  virtual unsigned int execute (function *);
> -
> -}; // class pass_rename_ssa_copies
> -
> -/* This function will make a pass through the IL, and attempt to coalesce any
> -   SSA versions which occur in PHI's or copies.  Coalescing is accomplished by
> -   changing the underlying root variable of all coalesced version.  This will
> -   then cause the SSA->normal pass to attempt to coalesce them all to the same
> -   variable.  */
> -
> -unsigned int
> -pass_rename_ssa_copies::execute (function *fun)
> -{
> -  var_map map;
> -  basic_block bb;
> -  tree var, part_var;
> -  gimple stmt;
> -  unsigned x;
> -  FILE *debug;
> -
> -  memset (&stats, 0, sizeof (stats));
> -
> -  if (dump_file && (dump_flags & TDF_DETAILS))
> -    debug = dump_file;
> -  else
> -    debug = NULL;
> -
> -  map = init_var_map (num_ssa_names);
> -
> -  FOR_EACH_BB_FN (bb, fun)
> -    {
> -      /* Scan for real copies.  */
> -      for (gimple_stmt_iterator gsi = gsi_start_bb (bb); !gsi_end_p (gsi);
> -          gsi_next (&gsi))
> -       {
> -         stmt = gsi_stmt (gsi);
> -         if (gimple_assign_ssa_name_copy_p (stmt))
> -           {
> -             tree lhs = gimple_assign_lhs (stmt);
> -             tree rhs = gimple_assign_rhs1 (stmt);
> -
> -             copy_rename_partition_coalesce (map, lhs, rhs, debug);
> -           }
> -       }
> -    }
> -
> -  FOR_EACH_BB_FN (bb, fun)
> -    {
> -      /* Treat PHI nodes as copies between the result and each argument.  */
> -      for (gphi_iterator gsi = gsi_start_phis (bb); !gsi_end_p (gsi);
> -          gsi_next (&gsi))
> -        {
> -          size_t i;
> -         tree res;
> -         gphi *phi = gsi.phi ();
> -         res = gimple_phi_result (phi);
> -
> -         /* Do not process virtual SSA_NAMES.  */
> -         if (virtual_operand_p (res))
> -           continue;
> -
> -         /* Make sure to only use the same partition for an argument
> -            as the result but never the other way around.  */
> -         if (SSA_NAME_VAR (res)
> -             && !DECL_IGNORED_P (SSA_NAME_VAR (res)))
> -           for (i = 0; i < gimple_phi_num_args (phi); i++)
> -             {
> -               tree arg = PHI_ARG_DEF (phi, i);
> -               if (TREE_CODE (arg) == SSA_NAME)
> -                 copy_rename_partition_coalesce (map, res, arg,
> -                                                 debug);
> -             }
> -         /* Else if all arguments are in the same partition try to merge
> -            it with the result.  */
> -         else
> -           {
> -             int all_p_same = -1;
> -             int p = -1;
> -             for (i = 0; i < gimple_phi_num_args (phi); i++)
> -               {
> -                 tree arg = PHI_ARG_DEF (phi, i);
> -                 if (TREE_CODE (arg) != SSA_NAME)
> -                   {
> -                     all_p_same = 0;
> -                     break;
> -                   }
> -                 else if (all_p_same == -1)
> -                   {
> -                     p = partition_find (map->var_partition,
> -                                         SSA_NAME_VERSION (arg));
> -                     all_p_same = 1;
> -                   }
> -                 else if (all_p_same == 1
> -                          && p != partition_find (map->var_partition,
> -                                                  SSA_NAME_VERSION (arg)))
> -                   {
> -                     all_p_same = 0;
> -                     break;
> -                   }
> -               }
> -             if (all_p_same == 1)
> -               copy_rename_partition_coalesce (map, res,
> -                                               PHI_ARG_DEF (phi, 0),
> -                                               debug);
> -           }
> -        }
> -    }
> -
> -  if (debug)
> -    dump_var_map (debug, map);
> -
> -  /* Now one more pass to make all elements of a partition share the same
> -     root variable.  */
> -
> -  for (x = 1; x < num_ssa_names; x++)
> -    {
> -      part_var = partition_to_var (map, x);
> -      if (!part_var)
> -        continue;
> -      var = ssa_name (x);
> -      if (SSA_NAME_VAR (var) == SSA_NAME_VAR (part_var))
> -       continue;
> -      if (debug)
> -        {
> -         fprintf (debug, "Coalesced ");
> -         print_generic_expr (debug, var, TDF_SLIM);
> -         fprintf (debug, " to ");
> -         print_generic_expr (debug, part_var, TDF_SLIM);
> -         fprintf (debug, "\n");
> -       }
> -      stats.coalesced++;
> -      replace_ssa_name_symbol (var, SSA_NAME_VAR (part_var));
> -    }
> -
> -  statistics_counter_event (fun, "copies coalesced",
> -                           stats.coalesced);
> -  delete_var_map (map);
> -  return 0;
> -}
> -
> -} // anon namespace
> -
> -gimple_opt_pass *
> -make_pass_rename_ssa_copies (gcc::context *ctxt)
> -{
> -  return new pass_rename_ssa_copies (ctxt);
> -}
> diff --git a/gcc/tree-ssa-live.c b/gcc/tree-ssa-live.c
> index e0c42669..46b1869 100644
> --- a/gcc/tree-ssa-live.c
> +++ b/gcc/tree-ssa-live.c
> @@ -119,7 +119,10 @@ tree_int_map_hasher::equal (const value_type *v, const compare_type *c)
>  }
>
>
> -/* This routine will initialize the basevar fields of MAP.  */
> +/* This routine will initialize the basevar fields of MAP with base
> +   names, when we are not optimizing.  When optimizing, we'll use
> +   partition numbers as base index numbers, see coalesce_ssa_name in
> +   tree-ssa-coalesce.c.  */
>
>  static void
>  var_map_base_init (var_map map)
>
>
> --
> Alexandre Oliva, freedom fighter    http://FSFLA.org/~lxoliva/
> You must be the change you wish to see in the world. -- Gandhi
> Be Free! -- http://FSFLA.org/   FSF Latin America board member
> Free Software Evangelist|Red Hat Brasil GNU Toolchain Engineer


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]